summaryrefslogtreecommitdiffstats
path: root/arch/arm/mach-omap2
diff options
context:
space:
mode:
Diffstat (limited to 'arch/arm/mach-omap2')
-rw-r--r--arch/arm/mach-omap2/Kconfig1
-rwxr-xr-xarch/arm/mach-omap2/board-zoom-peripherals.c8
-rw-r--r--arch/arm/mach-omap2/clock2xxx.c57
-rw-r--r--arch/arm/mach-omap2/clock34xx.c1
-rw-r--r--arch/arm/mach-omap2/clock34xx_data.c10
-rw-r--r--arch/arm/mach-omap2/clock44xx_data.c62
-rw-r--r--arch/arm/mach-omap2/clockdomain.c4
-rw-r--r--arch/arm/mach-omap2/cpuidle34xx.c2
-rw-r--r--arch/arm/mach-omap2/gpmc.c7
-rw-r--r--arch/arm/mach-omap2/id.c41
-rw-r--r--arch/arm/mach-omap2/io.c19
-rw-r--r--arch/arm/mach-omap2/irq.c22
-rw-r--r--arch/arm/mach-omap2/mmc-twl4030.c7
-rw-r--r--arch/arm/mach-omap2/mux.c43
-rw-r--r--arch/arm/mach-omap2/mux.h24
-rw-r--r--arch/arm/mach-omap2/mux34xx.c47
-rw-r--r--arch/arm/mach-omap2/omap_hwmod.c3
-rw-r--r--arch/arm/mach-omap2/opp2420_data.c38
-rw-r--r--arch/arm/mach-omap2/opp2430_data.c30
-rw-r--r--arch/arm/mach-omap2/pm-debug.c12
-rw-r--r--arch/arm/mach-omap2/pm.h8
-rw-r--r--arch/arm/mach-omap2/pm34xx.c51
-rw-r--r--arch/arm/mach-omap2/prcm.c11
-rw-r--r--arch/arm/mach-omap2/prm.h2
-rw-r--r--arch/arm/mach-omap2/prm44xx.h32
-rw-r--r--arch/arm/mach-omap2/serial.c23
-rw-r--r--arch/arm/mach-omap2/sleep34xx.S13
27 files changed, 378 insertions, 200 deletions
diff --git a/arch/arm/mach-omap2/Kconfig b/arch/arm/mach-omap2/Kconfig
index 10eafa70a909..606bf04f51b6 100644
--- a/arch/arm/mach-omap2/Kconfig
+++ b/arch/arm/mach-omap2/Kconfig
@@ -80,6 +80,7 @@ config MACH_OVERO
config MACH_OMAP3EVM
bool "OMAP 3530 EVM board"
depends on ARCH_OMAP3 && ARCH_OMAP34XX
+ select OMAP_PACKAGE_CBB
config MACH_OMAP3517EVM
bool "OMAP3517/ AM3517 EVM board"
diff --git a/arch/arm/mach-omap2/board-zoom-peripherals.c b/arch/arm/mach-omap2/board-zoom-peripherals.c
index 8dd277c36661..1e3dfb652acc 100755
--- a/arch/arm/mach-omap2/board-zoom-peripherals.c
+++ b/arch/arm/mach-omap2/board-zoom-peripherals.c
@@ -63,21 +63,21 @@ static int board_keymap[] = {
KEY(5, 1, KEY_H),
KEY(5, 2, KEY_J),
KEY(5, 3, KEY_F3),
+ KEY(5, 4, KEY_UNKNOWN),
KEY(5, 5, KEY_VOLUMEDOWN),
KEY(5, 6, KEY_M),
- KEY(5, 7, KEY_ENTER),
+ KEY(5, 7, KEY_RIGHT),
KEY(6, 0, KEY_Q),
KEY(6, 1, KEY_A),
KEY(6, 2, KEY_N),
KEY(6, 3, KEY_BACKSPACE),
KEY(6, 6, KEY_P),
- KEY(6, 7, KEY_SELECT),
+ KEY(6, 7, KEY_UP),
KEY(7, 0, KEY_PROG1), /*MACRO 1 <User defined> */
KEY(7, 1, KEY_PROG2), /*MACRO 2 <User defined> */
KEY(7, 2, KEY_PROG3), /*MACRO 3 <User defined> */
KEY(7, 3, KEY_PROG4), /*MACRO 4 <User defined> */
- KEY(7, 5, KEY_RIGHT),
- KEY(7, 6, KEY_UP),
+ KEY(7, 6, KEY_SELECT),
KEY(7, 7, KEY_DOWN)
};
diff --git a/arch/arm/mach-omap2/clock2xxx.c b/arch/arm/mach-omap2/clock2xxx.c
index d0e3fb7f9298..5420356eb407 100644
--- a/arch/arm/mach-omap2/clock2xxx.c
+++ b/arch/arm/mach-omap2/clock2xxx.c
@@ -449,40 +449,78 @@ int omap2_select_table_rate(struct clk *clk, unsigned long rate)
#ifdef CONFIG_CPU_FREQ
/*
* Walk PRCM rate table and fillout cpufreq freq_table
+ * XXX This should be replaced by an OPP layer in the near future
*/
-static struct cpufreq_frequency_table freq_table[ARRAY_SIZE(rate_table)];
+static struct cpufreq_frequency_table *freq_table;
void omap2_clk_init_cpufreq_table(struct cpufreq_frequency_table **table)
{
- struct prcm_config *prcm;
+ const struct prcm_config *prcm;
+ long sys_ck_rate;
int i = 0;
+ int tbl_sz = 0;
+
+ sys_ck_rate = clk_get_rate(sclk);
for (prcm = rate_table; prcm->mpu_speed; prcm++) {
if (!(prcm->flags & cpu_mask))
continue;
- if (prcm->xtal_speed != sys_ck.rate)
+ if (prcm->xtal_speed != sys_ck_rate)
continue;
/* don't put bypass rates in table */
if (prcm->dpll_speed == prcm->xtal_speed)
continue;
- freq_table[i].index = i;
- freq_table[i].frequency = prcm->mpu_speed / 1000;
- i++;
+ tbl_sz++;
}
- if (i == 0) {
- printk(KERN_WARNING "%s: failed to initialize frequency "
- "table\n", __func__);
+ /*
+ * XXX Ensure that we're doing what CPUFreq expects for this error
+ * case and the following one
+ */
+ if (tbl_sz == 0) {
+ pr_warning("%s: no matching entries in rate_table\n",
+ __func__);
+ return;
+ }
+
+ /* Include the CPUFREQ_TABLE_END terminator entry */
+ tbl_sz++;
+
+ freq_table = kzalloc(sizeof(struct cpufreq_frequency_table) * tbl_sz,
+ GFP_ATOMIC);
+ if (!freq_table) {
+ pr_err("%s: could not kzalloc frequency table\n", __func__);
return;
}
+ for (prcm = rate_table; prcm->mpu_speed; prcm++) {
+ if (!(prcm->flags & cpu_mask))
+ continue;
+ if (prcm->xtal_speed != sys_ck_rate)
+ continue;
+
+ /* don't put bypass rates in table */
+ if (prcm->dpll_speed == prcm->xtal_speed)
+ continue;
+
+ freq_table[i].index = i;
+ freq_table[i].frequency = prcm->mpu_speed / 1000;
+ i++;
+ }
+
freq_table[i].index = i;
freq_table[i].frequency = CPUFREQ_TABLE_END;
*table = &freq_table[0];
}
+
+void omap2_clk_exit_cpufreq_table(struct cpufreq_frequency_table **table)
+{
+ kfree(freq_table);
+}
+
#endif
struct clk_functions omap2_clk_functions = {
@@ -494,6 +532,7 @@ struct clk_functions omap2_clk_functions = {
.clk_disable_unused = omap2_clk_disable_unused,
#ifdef CONFIG_CPU_FREQ
.clk_init_cpufreq_table = omap2_clk_init_cpufreq_table,
+ .clk_exit_cpufreq_table = omap2_clk_exit_cpufreq_table,
#endif
};
diff --git a/arch/arm/mach-omap2/clock34xx.c b/arch/arm/mach-omap2/clock34xx.c
index ded32364f32b..d4217b93e10b 100644
--- a/arch/arm/mach-omap2/clock34xx.c
+++ b/arch/arm/mach-omap2/clock34xx.c
@@ -34,7 +34,6 @@
#include <asm/div64.h>
#include <asm/clkdev.h>
-#include <plat/sdrc.h>
#include "clock.h"
#include "clock34xx.h"
#include "sdrc.h"
diff --git a/arch/arm/mach-omap2/clock34xx_data.c b/arch/arm/mach-omap2/clock34xx_data.c
index 8bdcc9cc7f9a..74930e3158e3 100644
--- a/arch/arm/mach-omap2/clock34xx_data.c
+++ b/arch/arm/mach-omap2/clock34xx_data.c
@@ -671,7 +671,6 @@ static struct clk dpll4_m3x2_ck = {
.name = "dpll4_m3x2_ck",
.ops = &clkops_omap2_dflt_wait,
.parent = &dpll4_m3_ck,
- .init = &omap2_init_clksel_parent,
.enable_reg = OMAP_CM_REGADDR(PLL_MOD, CM_CLKEN),
.enable_bit = OMAP3430_PWRDN_TV_SHIFT,
.flags = INVERT_ENABLE,
@@ -776,6 +775,8 @@ static struct clk dpll4_m5_ck = {
.clksel_mask = OMAP3430_CLKSEL_CAM_MASK,
.clksel = div16_dpll4_clksel,
.clkdm_name = "dpll4_clkdm",
+ .set_rate = &omap2_clksel_set_rate,
+ .round_rate = &omap2_clksel_round_rate,
.recalc = &omap2_clksel_recalc,
};
@@ -809,7 +810,6 @@ static struct clk dpll4_m6x2_ck = {
.name = "dpll4_m6x2_ck",
.ops = &clkops_omap2_dflt_wait,
.parent = &dpll4_m6_ck,
- .init = &omap2_init_clksel_parent,
.enable_reg = OMAP_CM_REGADDR(PLL_MOD, CM_CLKEN),
.enable_bit = OMAP3430_PWRDN_EMU_PERIPH_SHIFT,
.flags = INVERT_ENABLE,
@@ -1045,7 +1045,6 @@ static struct clk iva2_ck = {
.name = "iva2_ck",
.ops = &clkops_omap2_dflt_wait,
.parent = &dpll2_m2_ck,
- .init = &omap2_init_clksel_parent,
.enable_reg = OMAP_CM_REGADDR(OMAP3430_IVA2_MOD, CM_FCLKEN),
.enable_bit = OMAP3430_CM_FCLKEN_IVA2_EN_IVA2_SHIFT,
.clkdm_name = "iva2_clkdm",
@@ -1119,7 +1118,6 @@ static struct clk gfx_l3_ck = {
.name = "gfx_l3_ck",
.ops = &clkops_omap2_dflt_wait,
.parent = &l3_ick,
- .init = &omap2_init_clksel_parent,
.enable_reg = OMAP_CM_REGADDR(GFX_MOD, CM_ICLKEN),
.enable_bit = OMAP_EN_GFX_SHIFT,
.recalc = &followparent_recalc,
@@ -1500,6 +1498,7 @@ static struct clk uart2_fck = {
.parent = &core_48m_fck,
.enable_reg = OMAP_CM_REGADDR(CORE_MOD, CM_FCLKEN1),
.enable_bit = OMAP3430_EN_UART2_SHIFT,
+ .clkdm_name = "core_l4_clkdm",
.recalc = &followparent_recalc,
};
@@ -1509,6 +1508,7 @@ static struct clk uart1_fck = {
.parent = &core_48m_fck,
.enable_reg = OMAP_CM_REGADDR(CORE_MOD, CM_FCLKEN1),
.enable_bit = OMAP3430_EN_UART1_SHIFT,
+ .clkdm_name = "core_l4_clkdm",
.recalc = &followparent_recalc,
};
@@ -2745,7 +2745,7 @@ static struct clk mcbsp4_ick = {
};
static const struct clksel mcbsp_234_clksel[] = {
- { .parent = &core_96m_fck, .rates = common_mcbsp_96m_rates },
+ { .parent = &per_96m_fck, .rates = common_mcbsp_96m_rates },
{ .parent = &mcbsp_clks, .rates = common_mcbsp_mcbsp_rates },
{ .parent = NULL }
};
diff --git a/arch/arm/mach-omap2/clock44xx_data.c b/arch/arm/mach-omap2/clock44xx_data.c
index 2210e227d78a..9d882bcb56e3 100644
--- a/arch/arm/mach-omap2/clock44xx_data.c
+++ b/arch/arm/mach-omap2/clock44xx_data.c
@@ -346,37 +346,37 @@ static struct clk aess_fclk = {
};
static const struct clksel_rate div31_1to31_rates[] = {
- { .div = 1, .val = 0, .flags = RATE_IN_4430 },
- { .div = 2, .val = 1, .flags = RATE_IN_4430 },
- { .div = 3, .val = 2, .flags = RATE_IN_4430 },
- { .div = 4, .val = 3, .flags = RATE_IN_4430 },
- { .div = 5, .val = 4, .flags = RATE_IN_4430 },
- { .div = 6, .val = 5, .flags = RATE_IN_4430 },
- { .div = 7, .val = 6, .flags = RATE_IN_4430 },
- { .div = 8, .val = 7, .flags = RATE_IN_4430 },
- { .div = 9, .val = 8, .flags = RATE_IN_4430 },
- { .div = 10, .val = 9, .flags = RATE_IN_4430 },
- { .div = 11, .val = 10, .flags = RATE_IN_4430 },
- { .div = 12, .val = 11, .flags = RATE_IN_4430 },
- { .div = 13, .val = 12, .flags = RATE_IN_4430 },
- { .div = 14, .val = 13, .flags = RATE_IN_4430 },
- { .div = 15, .val = 14, .flags = RATE_IN_4430 },
- { .div = 16, .val = 15, .flags = RATE_IN_4430 },
- { .div = 17, .val = 16, .flags = RATE_IN_4430 },
- { .div = 18, .val = 17, .flags = RATE_IN_4430 },
- { .div = 19, .val = 18, .flags = RATE_IN_4430 },
- { .div = 20, .val = 19, .flags = RATE_IN_4430 },
- { .div = 21, .val = 20, .flags = RATE_IN_4430 },
- { .div = 22, .val = 21, .flags = RATE_IN_4430 },
- { .div = 23, .val = 22, .flags = RATE_IN_4430 },
- { .div = 24, .val = 23, .flags = RATE_IN_4430 },
- { .div = 25, .val = 24, .flags = RATE_IN_4430 },
- { .div = 26, .val = 25, .flags = RATE_IN_4430 },
- { .div = 27, .val = 26, .flags = RATE_IN_4430 },
- { .div = 28, .val = 27, .flags = RATE_IN_4430 },
- { .div = 29, .val = 28, .flags = RATE_IN_4430 },
- { .div = 30, .val = 29, .flags = RATE_IN_4430 },
- { .div = 31, .val = 30, .flags = RATE_IN_4430 },
+ { .div = 1, .val = 1, .flags = RATE_IN_4430 },
+ { .div = 2, .val = 2, .flags = RATE_IN_4430 },
+ { .div = 3, .val = 3, .flags = RATE_IN_4430 },
+ { .div = 4, .val = 4, .flags = RATE_IN_4430 },
+ { .div = 5, .val = 5, .flags = RATE_IN_4430 },
+ { .div = 6, .val = 6, .flags = RATE_IN_4430 },
+ { .div = 7, .val = 7, .flags = RATE_IN_4430 },
+ { .div = 8, .val = 8, .flags = RATE_IN_4430 },
+ { .div = 9, .val = 9, .flags = RATE_IN_4430 },
+ { .div = 10, .val = 10, .flags = RATE_IN_4430 },
+ { .div = 11, .val = 11, .flags = RATE_IN_4430 },
+ { .div = 12, .val = 12, .flags = RATE_IN_4430 },
+ { .div = 13, .val = 13, .flags = RATE_IN_4430 },
+ { .div = 14, .val = 14, .flags = RATE_IN_4430 },
+ { .div = 15, .val = 15, .flags = RATE_IN_4430 },
+ { .div = 16, .val = 16, .flags = RATE_IN_4430 },
+ { .div = 17, .val = 17, .flags = RATE_IN_4430 },
+ { .div = 18, .val = 18, .flags = RATE_IN_4430 },
+ { .div = 19, .val = 19, .flags = RATE_IN_4430 },
+ { .div = 20, .val = 20, .flags = RATE_IN_4430 },
+ { .div = 21, .val = 21, .flags = RATE_IN_4430 },
+ { .div = 22, .val = 22, .flags = RATE_IN_4430 },
+ { .div = 23, .val = 23, .flags = RATE_IN_4430 },
+ { .div = 24, .val = 24, .flags = RATE_IN_4430 },
+ { .div = 25, .val = 25, .flags = RATE_IN_4430 },
+ { .div = 26, .val = 26, .flags = RATE_IN_4430 },
+ { .div = 27, .val = 27, .flags = RATE_IN_4430 },
+ { .div = 28, .val = 28, .flags = RATE_IN_4430 },
+ { .div = 29, .val = 29, .flags = RATE_IN_4430 },
+ { .div = 30, .val = 30, .flags = RATE_IN_4430 },
+ { .div = 31, .val = 31, .flags = RATE_IN_4430 },
{ .div = 0 },
};
diff --git a/arch/arm/mach-omap2/clockdomain.c b/arch/arm/mach-omap2/clockdomain.c
index 1a45ed1e8ba1..dd285f001467 100644
--- a/arch/arm/mach-omap2/clockdomain.c
+++ b/arch/arm/mach-omap2/clockdomain.c
@@ -559,7 +559,7 @@ int omap2_clkdm_clk_enable(struct clockdomain *clkdm, struct clk *clk)
* downstream clocks for debugging purposes?
*/
- if (!clkdm || !clk)
+ if (!clkdm || !clk || !clkdm->clktrctrl_mask)
return -EINVAL;
if (atomic_inc_return(&clkdm->usecount) > 1)
@@ -610,7 +610,7 @@ int omap2_clkdm_clk_disable(struct clockdomain *clkdm, struct clk *clk)
* downstream clocks for debugging purposes?
*/
- if (!clkdm || !clk)
+ if (!clkdm || !clk || !clkdm->clktrctrl_mask)
return -EINVAL;
#ifdef DEBUG
diff --git a/arch/arm/mach-omap2/cpuidle34xx.c b/arch/arm/mach-omap2/cpuidle34xx.c
index a26d6a08ae3f..12f0cbfc2894 100644
--- a/arch/arm/mach-omap2/cpuidle34xx.c
+++ b/arch/arm/mach-omap2/cpuidle34xx.c
@@ -137,7 +137,7 @@ return_sleep_time:
local_irq_enable();
local_fiq_enable();
- return (u32)timespec_to_ns(&ts_idle)/1000;
+ return ts_idle.tv_nsec / NSEC_PER_USEC + ts_idle.tv_sec * USEC_PER_SEC;
}
/**
diff --git a/arch/arm/mach-omap2/gpmc.c b/arch/arm/mach-omap2/gpmc.c
index bd8cb5974726..7027cdc1ba49 100644
--- a/arch/arm/mach-omap2/gpmc.c
+++ b/arch/arm/mach-omap2/gpmc.c
@@ -505,7 +505,7 @@ static void __init gpmc_mem_init(void)
void __init gpmc_init(void)
{
u32 l;
- char *ck;
+ char *ck = NULL;
if (cpu_is_omap24xx()) {
ck = "core_l3_ck";
@@ -521,6 +521,9 @@ void __init gpmc_init(void)
l = OMAP44XX_GPMC_BASE;
}
+ if (WARN_ON(!ck))
+ return;
+
gpmc_l3_clk = clk_get(NULL, ck);
if (IS_ERR(gpmc_l3_clk)) {
printk(KERN_ERR "Could not get GPMC clock %s\n", ck);
@@ -534,6 +537,8 @@ void __init gpmc_init(void)
BUG();
}
+ clk_enable(gpmc_l3_clk);
+
l = gpmc_read_reg(GPMC_REVISION);
printk(KERN_INFO "GPMC revision %d.%d\n", (l >> 4) & 0x0f, l & 0x0f);
/* Set smart idle mode and automatic L3 clock gating */
diff --git a/arch/arm/mach-omap2/id.c b/arch/arm/mach-omap2/id.c
index a091b53657b9..3d65c50bd017 100644
--- a/arch/arm/mach-omap2/id.c
+++ b/arch/arm/mach-omap2/id.c
@@ -188,6 +188,8 @@ void __init omap3_check_revision(void)
u16 hawkeye;
u8 rev;
+ omap_chip.oc = CHIP_IS_OMAP3430;
+
/*
* We cannot access revision registers on ES1.0.
* If the processor type is Cortex-A8 and the revision is 0x0
@@ -196,6 +198,7 @@ void __init omap3_check_revision(void)
cpuid = read_cpuid(CPUID_ID);
if ((((cpuid >> 4) & 0xfff) == 0xc08) && ((cpuid & 0xf) == 0x0)) {
omap_revision = OMAP3430_REV_ES1_0;
+ omap_chip.oc |= CHIP_IS_OMAP3430ES1;
return;
}
@@ -216,18 +219,28 @@ void __init omap3_check_revision(void)
case 0: /* Take care of early samples */
case 1:
omap_revision = OMAP3430_REV_ES2_0;
+ omap_chip.oc |= CHIP_IS_OMAP3430ES2;
break;
case 2:
omap_revision = OMAP3430_REV_ES2_1;
+ omap_chip.oc |= CHIP_IS_OMAP3430ES2;
break;
case 3:
omap_revision = OMAP3430_REV_ES3_0;
+ omap_chip.oc |= CHIP_IS_OMAP3430ES3_0;
break;
case 4:
+ omap_revision = OMAP3430_REV_ES3_1;
+ omap_chip.oc |= CHIP_IS_OMAP3430ES3_1;
+ break;
+ case 7:
/* FALLTHROUGH */
default:
/* Use the latest known revision as default */
- omap_revision = OMAP3430_REV_ES3_1;
+ omap_revision = OMAP3430_REV_ES3_1_2;
+
+ /* REVISIT: Add CHIP_IS_OMAP3430ES3_1_2? */
+ omap_chip.oc |= CHIP_IS_OMAP3430ES3_1;
}
break;
case 0xb868:
@@ -235,14 +248,18 @@ void __init omap3_check_revision(void)
*
* Set the device to be OMAP3505 here. Actual device
* is identified later based on the features.
+ *
+ * REVISIT: AM3505/AM3517 should have their own CHIP_IS
*/
omap_revision = OMAP3505_REV(rev);
+ omap_chip.oc |= CHIP_IS_OMAP3430ES3_1;
break;
case 0xb891:
/* FALLTHROUGH */
default:
/* Unknown default to latest silicon rev as default*/
omap_revision = OMAP3630_REV_ES1_0;
+ omap_chip.oc |= CHIP_IS_OMAP3630ES1;
}
}
@@ -360,6 +377,7 @@ void __init omap2_check_revision(void)
omap3_check_revision();
omap3_check_features();
omap3_cpuinfo();
+ return;
} else if (cpu_is_omap44xx()) {
omap4_check_revision();
return;
@@ -374,27 +392,14 @@ void __init omap2_check_revision(void)
if (cpu_is_omap243x()) {
/* Currently only supports 2430ES2.1 and 2430-all */
omap_chip.oc |= CHIP_IS_OMAP2430;
+ return;
} else if (cpu_is_omap242x()) {
/* Currently only supports 2420ES2.1.1 and 2420-all */
omap_chip.oc |= CHIP_IS_OMAP2420;
- } else if (cpu_is_omap3505() || cpu_is_omap3517()) {
- omap_chip.oc = CHIP_IS_OMAP3430 | CHIP_IS_OMAP3430ES3_1;
- } else if (cpu_is_omap343x()) {
- omap_chip.oc = CHIP_IS_OMAP3430;
- if (omap_rev() == OMAP3430_REV_ES1_0)
- omap_chip.oc |= CHIP_IS_OMAP3430ES1;
- else if (omap_rev() >= OMAP3430_REV_ES2_0 &&
- omap_rev() <= OMAP3430_REV_ES2_1)
- omap_chip.oc |= CHIP_IS_OMAP3430ES2;
- else if (omap_rev() == OMAP3430_REV_ES3_0)
- omap_chip.oc |= CHIP_IS_OMAP3430ES3_0;
- else if (omap_rev() == OMAP3430_REV_ES3_1)
- omap_chip.oc |= CHIP_IS_OMAP3430ES3_1;
- else if (omap_rev() == OMAP3630_REV_ES1_0)
- omap_chip.oc |= CHIP_IS_OMAP3630ES1;
- } else {
- pr_err("Uninitialized omap_chip, please fix!\n");
+ return;
}
+
+ pr_err("Uninitialized omap_chip, please fix!\n");
}
/*
diff --git a/arch/arm/mach-omap2/io.c b/arch/arm/mach-omap2/io.c
index a8749e8017b9..5a7996402c53 100644
--- a/arch/arm/mach-omap2/io.c
+++ b/arch/arm/mach-omap2/io.c
@@ -33,7 +33,6 @@
#include <plat/sdrc.h>
#include <plat/gpmc.h>
#include <plat/serial.h>
-#include <plat/mux.h>
#include <plat/vram.h>
#include "clock.h"
@@ -73,21 +72,21 @@ static struct map_desc omap24xx_io_desc[] __initdata = {
#ifdef CONFIG_ARCH_OMAP2420
static struct map_desc omap242x_io_desc[] __initdata = {
{
- .virtual = DSP_MEM_24XX_VIRT,
- .pfn = __phys_to_pfn(DSP_MEM_24XX_PHYS),
- .length = DSP_MEM_24XX_SIZE,
+ .virtual = DSP_MEM_2420_VIRT,
+ .pfn = __phys_to_pfn(DSP_MEM_2420_PHYS),
+ .length = DSP_MEM_2420_SIZE,
.type = MT_DEVICE
},
{
- .virtual = DSP_IPI_24XX_VIRT,
- .pfn = __phys_to_pfn(DSP_IPI_24XX_PHYS),
- .length = DSP_IPI_24XX_SIZE,
+ .virtual = DSP_IPI_2420_VIRT,
+ .pfn = __phys_to_pfn(DSP_IPI_2420_PHYS),
+ .length = DSP_IPI_2420_SIZE,
.type = MT_DEVICE
},
{
- .virtual = DSP_MMU_24XX_VIRT,
- .pfn = __phys_to_pfn(DSP_MMU_24XX_PHYS),
- .length = DSP_MMU_24XX_SIZE,
+ .virtual = DSP_MMU_2420_VIRT,
+ .pfn = __phys_to_pfn(DSP_MMU_2420_PHYS),
+ .length = DSP_MMU_2420_SIZE,
.type = MT_DEVICE
},
};
diff --git a/arch/arm/mach-omap2/irq.c b/arch/arm/mach-omap2/irq.c
index e9bc782fa414..26aeef560aa3 100644
--- a/arch/arm/mach-omap2/irq.c
+++ b/arch/arm/mach-omap2/irq.c
@@ -194,7 +194,7 @@ void __init omap_init_irq(void)
int i;
for (i = 0; i < ARRAY_SIZE(irq_banks); i++) {
- unsigned long base;
+ unsigned long base = 0;
struct omap_irq_bank *bank = irq_banks + i;
if (cpu_is_omap24xx())
@@ -202,6 +202,8 @@ void __init omap_init_irq(void)
else if (cpu_is_omap34xx())
base = OMAP34XX_IC_BASE;
+ BUG_ON(!base);
+
/* Static mapping, never released */
bank->base_reg = ioremap(base, SZ_4K);
if (!bank->base_reg) {
@@ -274,4 +276,22 @@ void omap_intc_restore_context(void)
}
/* MIRs are saved and restore with other PRCM registers */
}
+
+void omap3_intc_suspend(void)
+{
+ /* A pending interrupt would prevent OMAP from entering suspend */
+ omap_ack_irq(0);
+}
+
+void omap3_intc_prepare_idle(void)
+{
+ /* Disable autoidle as it can stall interrupt controller */
+ intc_bank_write_reg(0, &irq_banks[0], INTC_SYSCONFIG);
+}
+
+void omap3_intc_resume_idle(void)
+{
+ /* Re-enable autoidle */
+ intc_bank_write_reg(1, &irq_banks[0], INTC_SYSCONFIG);
+}
#endif /* CONFIG_ARCH_OMAP3 */
diff --git a/arch/arm/mach-omap2/mmc-twl4030.c b/arch/arm/mach-omap2/mmc-twl4030.c
index 0c3c72d934bf..8afe9dd3f150 100644
--- a/arch/arm/mach-omap2/mmc-twl4030.c
+++ b/arch/arm/mach-omap2/mmc-twl4030.c
@@ -408,6 +408,7 @@ void __init twl4030_mmc_init(struct twl4030_hsmmc_info *controllers)
{
struct twl4030_hsmmc_info *c;
int nr_hsmmc = ARRAY_SIZE(hsmmc_data);
+ int i;
if (cpu_is_omap2430()) {
control_pbias_offset = OMAP243X_CONTROL_PBIAS_LITE;
@@ -434,7 +435,7 @@ void __init twl4030_mmc_init(struct twl4030_hsmmc_info *controllers)
mmc = kzalloc(sizeof(struct omap_mmc_platform_data), GFP_KERNEL);
if (!mmc) {
pr_err("Cannot allocate memory for mmc device!\n");
- return;
+ goto done;
}
if (c->name)
@@ -532,6 +533,10 @@ void __init twl4030_mmc_init(struct twl4030_hsmmc_info *controllers)
continue;
c->dev = mmc->dev;
}
+
+done:
+ for (i = 0; i < nr_hsmmc; i++)
+ kfree(hsmmc_data[i]);
}
#endif
diff --git a/arch/arm/mach-omap2/mux.c b/arch/arm/mach-omap2/mux.c
index e071b3fd1878..5fef73f4743d 100644
--- a/arch/arm/mach-omap2/mux.c
+++ b/arch/arm/mach-omap2/mux.c
@@ -51,7 +51,7 @@ struct omap_mux_entry {
static unsigned long mux_phys;
static void __iomem *mux_base;
-static inline u16 omap_mux_read(u16 reg)
+u16 omap_mux_read(u16 reg)
{
if (cpu_is_omap24xx())
return __raw_readb(mux_base + reg);
@@ -59,7 +59,7 @@ static inline u16 omap_mux_read(u16 reg)
return __raw_readw(mux_base + reg);
}
-static inline void omap_mux_write(u16 val, u16 reg)
+void omap_mux_write(u16 val, u16 reg)
{
if (cpu_is_omap24xx())
__raw_writeb(val, mux_base + reg);
@@ -67,6 +67,14 @@ static inline void omap_mux_write(u16 val, u16 reg)
__raw_writew(val, mux_base + reg);
}
+void omap_mux_write_array(struct omap_board_mux *board_mux)
+{
+ while (board_mux->reg_offset != OMAP_MUX_TERMINATOR) {
+ omap_mux_write(board_mux->value, board_mux->reg_offset);
+ board_mux++;
+ }
+}
+
#if defined(CONFIG_ARCH_OMAP24XX) && defined(CONFIG_OMAP_MUX)
static struct omap_mux_cfg arch_mux_cfg;
@@ -478,7 +486,7 @@ int __init omap_mux_init_signal(char *muxname, int val)
static inline void omap_mux_decode(struct seq_file *s, u16 val)
{
char *flags[OMAP_MUX_MAX_NR_FLAGS];
- char mode[14];
+ char mode[sizeof("OMAP_MUX_MODE") + 1];
int i = -1;
sprintf(mode, "OMAP_MUX_MODE%d", val & 0x7);
@@ -545,6 +553,7 @@ static int omap_mux_dbg_board_show(struct seq_file *s, void *unused)
if (!m0_name)
continue;
+ /* REVISIT: Needs to be updated if mode0 names get longer */
for (i = 0; i < OMAP_MUX_DEFNAME_LEN; i++) {
if (m0_name[i] == '\0') {
m0_def[i] = m0_name[i];
@@ -833,14 +842,6 @@ static void __init omap_mux_set_cmdline_signals(void)
kfree(options);
}
-static void __init omap_mux_set_board_signals(struct omap_board_mux *board_mux)
-{
- while (board_mux->reg_offset != OMAP_MUX_TERMINATOR) {
- omap_mux_write(board_mux->value, board_mux->reg_offset);
- board_mux++;
- }
-}
-
static int __init omap_mux_copy_names(struct omap_mux *src,
struct omap_mux *dst)
{
@@ -960,7 +961,12 @@ static void __init omap_mux_init_list(struct omap_mux *superset)
while (superset->reg_offset != OMAP_MUX_TERMINATOR) {
struct omap_mux *entry;
-#ifndef CONFIG_OMAP_MUX
+#ifdef CONFIG_OMAP_MUX
+ if (!superset->muxnames || !superset->muxnames[0]) {
+ superset++;
+ continue;
+ }
+#else
/* Skip pins that are not muxed as GPIO by bootloader */
if (!OMAP_MODE_GPIO(omap_mux_read(superset->reg_offset))) {
superset++;
@@ -994,14 +1000,19 @@ int __init omap_mux_init(u32 mux_pbase, u32 mux_size,
}
#ifdef CONFIG_OMAP_MUX
- omap_mux_package_fixup(package_subset, superset);
- omap_mux_package_init_balls(package_balls, superset);
- omap_mux_set_cmdline_signals();
- omap_mux_set_board_signals(board_mux);
+ if (package_subset)
+ omap_mux_package_fixup(package_subset, superset);
+ if (package_balls)
+ omap_mux_package_init_balls(package_balls, superset);
#endif
omap_mux_init_list(superset);
+#ifdef CONFIG_OMAP_MUX
+ omap_mux_set_cmdline_signals();
+ omap_mux_write_array(board_mux);
+#endif
+
return 0;
}
diff --git a/arch/arm/mach-omap2/mux.h b/arch/arm/mach-omap2/mux.h
index d8b4d5ad2278..f8c2e7a8f063 100644
--- a/arch/arm/mach-omap2/mux.h
+++ b/arch/arm/mach-omap2/mux.h
@@ -147,6 +147,30 @@ u16 omap_mux_get_gpio(int gpio);
void omap_mux_set_gpio(u16 val, int gpio);
/**
+ * omap_mux_read() - read mux register
+ * @mux_offset: Offset of the mux register
+ *
+ */
+u16 omap_mux_read(u16 mux_offset);
+
+/**
+ * omap_mux_write() - write mux register
+ * @val: New mux register value
+ * @mux_offset: Offset of the mux register
+ *
+ * This should be only needed for dynamic remuxing of non-gpio signals.
+ */
+void omap_mux_write(u16 val, u16 mux_offset);
+
+/**
+ * omap_mux_write_array() - write an array of mux registers
+ * @board_mux: Array of mux registers terminated by MAP_MUX_TERMINATOR
+ *
+ * This should be only needed for dynamic remuxing of non-gpio signals.
+ */
+void omap_mux_write_array(struct omap_board_mux *board_mux);
+
+/**
* omap3_mux_init() - initialize mux system with board specific set
* @board_mux: Board specific mux table
* @flags: OMAP package type used for the board
diff --git a/arch/arm/mach-omap2/mux34xx.c b/arch/arm/mach-omap2/mux34xx.c
index 68e0a595f9a1..07aa7b3c95f7 100644
--- a/arch/arm/mach-omap2/mux34xx.c
+++ b/arch/arm/mach-omap2/mux34xx.c
@@ -649,6 +649,53 @@ static struct omap_mux __initdata omap3_muxmodes[] = {
_OMAP3_MUXENTRY(UART3_TX_IRTX, 166,
"uart3_tx_irtx", NULL, NULL, NULL,
"gpio_166", NULL, NULL, "safe_mode"),
+
+ /* Only on 3630, see omap36xx_cbp_subset for the signals */
+ _OMAP3_MUXENTRY(GPMC_A11, 0,
+ NULL, NULL, NULL, NULL,
+ NULL, NULL, NULL, NULL),
+ _OMAP3_MUXENTRY(SAD2D_MBUSFLAG, 0,
+ NULL, NULL, NULL, NULL,
+ NULL, NULL, NULL, NULL),
+ _OMAP3_MUXENTRY(SAD2D_MREAD, 0,
+ NULL, NULL, NULL, NULL,
+ NULL, NULL, NULL, NULL),
+ _OMAP3_MUXENTRY(SAD2D_MWRITE, 0,
+ NULL, NULL, NULL, NULL,
+ NULL, NULL, NULL, NULL),
+ _OMAP3_MUXENTRY(SAD2D_SBUSFLAG, 0,
+ NULL, NULL, NULL, NULL,
+ NULL, NULL, NULL, NULL),
+ _OMAP3_MUXENTRY(SAD2D_SREAD, 0,
+ NULL, NULL, NULL, NULL,
+ NULL, NULL, NULL, NULL),
+ _OMAP3_MUXENTRY(SAD2D_SWRITE, 0,
+ NULL, NULL, NULL, NULL,
+ NULL, NULL, NULL, NULL),
+ _OMAP3_MUXENTRY(GPMC_A11, 0,
+ NULL, NULL, NULL, NULL,
+ NULL, NULL, NULL, NULL),
+ _OMAP3_MUXENTRY(SAD2D_MCAD28, 0,
+ NULL, NULL, NULL, NULL,
+ NULL, NULL, NULL, NULL),
+ _OMAP3_MUXENTRY(SAD2D_MCAD29, 0,
+ NULL, NULL, NULL, NULL,
+ NULL, NULL, NULL, NULL),
+ _OMAP3_MUXENTRY(SAD2D_MCAD32, 0,
+ NULL, NULL, NULL, NULL,
+ NULL, NULL, NULL, NULL),
+ _OMAP3_MUXENTRY(SAD2D_MCAD33, 0,
+ NULL, NULL, NULL, NULL,
+ NULL, NULL, NULL, NULL),
+ _OMAP3_MUXENTRY(SAD2D_MCAD34, 0,
+ NULL, NULL, NULL, NULL,
+ NULL, NULL, NULL, NULL),
+ _OMAP3_MUXENTRY(SAD2D_MCAD35, 0,
+ NULL, NULL, NULL, NULL,
+ NULL, NULL, NULL, NULL),
+ _OMAP3_MUXENTRY(SAD2D_MCAD36, 0,
+ NULL, NULL, NULL, NULL,
+ NULL, NULL, NULL, NULL),
{ .reg_offset = OMAP_MUX_TERMINATOR },
};
diff --git a/arch/arm/mach-omap2/omap_hwmod.c b/arch/arm/mach-omap2/omap_hwmod.c
index d8c8545875b1..478ae585ca39 100644
--- a/arch/arm/mach-omap2/omap_hwmod.c
+++ b/arch/arm/mach-omap2/omap_hwmod.c
@@ -94,7 +94,8 @@ static int _update_sysc_cache(struct omap_hwmod *oh)
oh->_sysc_cache = omap_hwmod_readl(oh, oh->sysconfig->sysc_offs);
- oh->_int_flags |= _HWMOD_SYSCONFIG_LOADED;
+ if (!(oh->sysconfig->sysc_flags & SYSC_NO_CACHE))
+ oh->_int_flags |= _HWMOD_SYSCONFIG_LOADED;
return 0;
}
diff --git a/arch/arm/mach-omap2/opp2420_data.c b/arch/arm/mach-omap2/opp2420_data.c
index 126a9396b3a8..e6dda694fd5c 100644
--- a/arch/arm/mach-omap2/opp2420_data.c
+++ b/arch/arm/mach-omap2/opp2420_data.c
@@ -9,45 +9,47 @@
* The OMAP2 processor can be run at several discrete 'PRCM configurations'.
* These configurations are characterized by voltage and speed for clocks.
* The device is only validated for certain combinations. One way to express
- * these combinations is via the 'ratio's' which the clocks operate with
+ * these combinations is via the 'ratios' which the clocks operate with
* respect to each other. These ratio sets are for a given voltage/DPLL
- * setting. All configurations can be described by a DPLL setting and a ratio
- * There are 3 ratio sets for the 2430 and X ratio sets for 2420.
- *
- * 2430 differs from 2420 in that there are no more phase synchronizers used.
- * They both have a slightly different clock domain setup. 2420(iva1,dsp) vs
- * 2430 (iva2.1, NOdsp, mdm)
+ * setting. All configurations can be described by a DPLL setting and a ratio.
*
* XXX Missing voltage data.
+ * XXX Missing 19.2MHz sys_clk rate sets (needed for N800/N810)
*
* THe format described in this file is deprecated. Once a reasonable
* OPP API exists, the data in this file should be converted to use it.
*
* This is technically part of the OMAP2xxx clock code.
+ *
+ * Considerable work is still needed to fully support dynamic frequency
+ * changes on OMAP2xxx-series chips. Readers interested in such a
+ * project are encouraged to review the Maemo Diablo RX-34 and RX-44
+ * kernel source at:
+ * http://repository.maemo.org/pool/diablo/free/k/kernel-source-diablo/
*/
#include "opp2xxx.h"
#include "sdrc.h"
#include "clock.h"
-/*-------------------------------------------------------------------------
- * Key dividers which make up a PRCM set. Ratio's for a PRCM are mandated.
+/*
+ * Key dividers which make up a PRCM set. Ratios for a PRCM are mandated.
* xtal_speed, dpll_speed, mpu_speed, CM_CLKSEL_MPU,
* CM_CLKSEL_DSP, CM_CLKSEL_GFX, CM_CLKSEL1_CORE, CM_CLKSEL1_PLL,
* CM_CLKSEL2_PLL, CM_CLKSEL_MDM
*
- * Filling in table based on H4 boards and 2430-SDPs variants available.
- * There are quite a few more rates combinations which could be defined.
+ * Filling in table based on H4 boards available. There are quite a
+ * few more rate combinations which could be defined.
*
- * When multiple values are defined the start up will try and choose the
- * fastest one. If a 'fast' value is defined, then automatically, the /2
- * one should be included as it can be used. Generally having more that
- * one fast set does not make sense, as static timings need to be changed
- * to change the set. The exception is the bypass setting which is
- * availble for low power bypass.
+ * When multiple values are defined the start up will try and choose
+ * the fastest one. If a 'fast' value is defined, then automatically,
+ * the /2 one should be included as it can be used. Generally having
+ * more than one fast set does not make sense, as static timings need
+ * to be changed to change the set. The exception is the bypass
+ * setting which is available for low power bypass.
*
* Note: This table needs to be sorted, fastest to slowest.
- *-------------------------------------------------------------------------*/
+ **/
const struct prcm_config omap2420_rate_table[] = {
/* PRCM I - FAST */
{S12M, S660M, S330M, RI_CM_CLKSEL_MPU_VAL, /* 330MHz ARM */
diff --git a/arch/arm/mach-omap2/opp2430_data.c b/arch/arm/mach-omap2/opp2430_data.c
index edb81672c844..1b9596ae201e 100644
--- a/arch/arm/mach-omap2/opp2430_data.c
+++ b/arch/arm/mach-omap2/opp2430_data.c
@@ -1,5 +1,5 @@
/*
- * opp2420_data.c - old-style "OPP" table for OMAP2420
+ * opp2430_data.c - old-style "OPP" table for OMAP2430
*
* Copyright (C) 2005-2009 Texas Instruments, Inc.
* Copyright (C) 2004-2009 Nokia Corporation
@@ -9,16 +9,16 @@
* The OMAP2 processor can be run at several discrete 'PRCM configurations'.
* These configurations are characterized by voltage and speed for clocks.
* The device is only validated for certain combinations. One way to express
- * these combinations is via the 'ratio's' which the clocks operate with
+ * these combinations is via the 'ratios' which the clocks operate with
* respect to each other. These ratio sets are for a given voltage/DPLL
- * setting. All configurations can be described by a DPLL setting and a ratio
- * There are 3 ratio sets for the 2430 and X ratio sets for 2420.
+ * setting. All configurations can be described by a DPLL setting and a ratio.
*
* 2430 differs from 2420 in that there are no more phase synchronizers used.
* They both have a slightly different clock domain setup. 2420(iva1,dsp) vs
* 2430 (iva2.1, NOdsp, mdm)
*
* XXX Missing voltage data.
+ * XXX Missing 19.2MHz sys_clk rate sets.
*
* THe format described in this file is deprecated. Once a reasonable
* OPP API exists, the data in this file should be converted to use it.
@@ -30,24 +30,24 @@
#include "sdrc.h"
#include "clock.h"
-/*-------------------------------------------------------------------------
- * Key dividers which make up a PRCM set. Ratio's for a PRCM are mandated.
+/*
+ * Key dividers which make up a PRCM set. Ratios for a PRCM are mandated.
* xtal_speed, dpll_speed, mpu_speed, CM_CLKSEL_MPU,
* CM_CLKSEL_DSP, CM_CLKSEL_GFX, CM_CLKSEL1_CORE, CM_CLKSEL1_PLL,
* CM_CLKSEL2_PLL, CM_CLKSEL_MDM
*
- * Filling in table based on H4 boards and 2430-SDPs variants available.
- * There are quite a few more rates combinations which could be defined.
+ * Filling in table based on 2430-SDPs variants available. There are
+ * quite a few more rate combinations which could be defined.
*
- * When multiple values are defined the start up will try and choose the
- * fastest one. If a 'fast' value is defined, then automatically, the /2
- * one should be included as it can be used. Generally having more that
- * one fast set does not make sense, as static timings need to be changed
- * to change the set. The exception is the bypass setting which is
- * availble for low power bypass.
+ * When multiple values are defined the start up will try and choose
+ * the fastest one. If a 'fast' value is defined, then automatically,
+ * the /2 one should be included as it can be used. Generally having
+ * more than one fast set does not make sense, as static timings need
+ * to be changed to change the set. The exception is the bypass
+ * setting which is available for low power bypass.
*
* Note: This table needs to be sorted, fastest to slowest.
- *-------------------------------------------------------------------------*/
+ */
const struct prcm_config omap2430_rate_table[] = {
/* PRCM #4 - ratio2 (ES2.1) - FAST */
{S13M, S798M, S399M, R2_CM_CLKSEL_MPU_VAL, /* 399MHz ARM */
diff --git a/arch/arm/mach-omap2/pm-debug.c b/arch/arm/mach-omap2/pm-debug.c
index 860b755d2220..a0866268aa41 100644
--- a/arch/arm/mach-omap2/pm-debug.c
+++ b/arch/arm/mach-omap2/pm-debug.c
@@ -54,8 +54,6 @@ int omap2_pm_debug;
regs[reg_count++].val = \
__raw_readl(OMAP2_L4_IO_ADDRESS(0x480fe000 + (off)))
-static int __init pm_dbg_init(void);
-
void omap2_pm_dump(int mode, int resume, unsigned int us)
{
struct reg {
@@ -167,6 +165,8 @@ struct dentry *pm_dbg_dir;
static int pm_dbg_init_done;
+static int __init pm_dbg_init(void);
+
enum {
DEBUG_FILE_COUNTERS = 0,
DEBUG_FILE_TIMERS,
@@ -488,9 +488,11 @@ int pm_dbg_regset_init(int reg_set)
static int pwrdm_suspend_get(void *data, u64 *val)
{
- *val = omap3_pm_get_suspend_state((struct powerdomain *)data);
+ int ret;
+ ret = omap3_pm_get_suspend_state((struct powerdomain *)data);
+ *val = ret;
- if (*val >= 0)
+ if (ret >= 0)
return 0;
return *val;
}
@@ -604,6 +606,4 @@ static int __init pm_dbg_init(void)
}
arch_initcall(pm_dbg_init);
-#else
-void pm_dbg_update_time(struct powerdomain *pwrdm, int prev) {}
#endif
diff --git a/arch/arm/mach-omap2/pm.h b/arch/arm/mach-omap2/pm.h
index 0bf345db7147..7a9c2d004511 100644
--- a/arch/arm/mach-omap2/pm.h
+++ b/arch/arm/mach-omap2/pm.h
@@ -32,12 +32,16 @@ extern struct omap_dm_timer *gptimer_wakeup;
#ifdef CONFIG_PM_DEBUG
extern void omap2_pm_dump(int mode, int resume, unsigned int us);
extern int omap2_pm_debug;
+#else
+#define omap2_pm_dump(mode, resume, us) do {} while (0);
+#define omap2_pm_debug 0
+#endif
+
+#if defined(CONFIG_PM_DEBUG) && defined(CONFIG_DEBUG_FS)
extern void pm_dbg_update_time(struct powerdomain *pwrdm, int prev);
extern int pm_dbg_regset_save(int reg_set);
extern int pm_dbg_regset_init(int reg_set);
#else
-#define omap2_pm_dump(mode, resume, us) do {} while (0);
-#define omap2_pm_debug 0
#define pm_dbg_update_time(pwrdm, prev) do {} while (0);
#define pm_dbg_regset_save(reg_set) do {} while (0);
#define pm_dbg_regset_init(reg_set) do {} while (0);
diff --git a/arch/arm/mach-omap2/pm34xx.c b/arch/arm/mach-omap2/pm34xx.c
index 81ed252a0f8a..910a7acf542d 100644
--- a/arch/arm/mach-omap2/pm34xx.c
+++ b/arch/arm/mach-omap2/pm34xx.c
@@ -26,6 +26,7 @@
#include <linux/err.h>
#include <linux/gpio.h>
#include <linux/clk.h>
+#include <linux/delay.h>
#include <plat/sram.h>
#include <plat/clockdomain.h>
@@ -124,9 +125,17 @@ static void omap3_core_save_context(void)
control_padconf_off |= START_PADCONF_SAVE;
omap_ctrl_writel(control_padconf_off, OMAP343X_CONTROL_PADCONF_OFF);
/* wait for the save to complete */
- while (!omap_ctrl_readl(OMAP343X_CONTROL_GENERAL_PURPOSE_STATUS)
- & PADCONF_SAVE_DONE)
- ;
+ while (!(omap_ctrl_readl(OMAP343X_CONTROL_GENERAL_PURPOSE_STATUS)
+ & PADCONF_SAVE_DONE))
+ udelay(1);
+
+ /*
+ * Force write last pad into memory, as this can fail in some
+ * cases according to erratas 1.157, 1.185
+ */
+ omap_ctrl_writel(omap_ctrl_readl(OMAP343X_PADCONF_ETK_D14),
+ OMAP343X_CONTROL_MEM_WKUP + 0x2a0);
+
/* Save the Interrupt controller context */
omap_intc_save_context();
/* Save the GPMC context */
@@ -392,6 +401,7 @@ void omap_sram_idle(void)
prm_set_mod_reg_bits(OMAP3430_EN_IO, WKUP_MOD, PM_WKEN);
omap3_enable_io_chain();
}
+ omap3_intc_prepare_idle();
/*
* On EMU/HS devices ROM code restores a SRDC value
@@ -438,6 +448,7 @@ void omap_sram_idle(void)
OMAP3430_GR_MOD,
OMAP3_PRM_VOLTCTRL_OFFSET);
}
+ omap3_intc_resume_idle();
/* PER */
if (per_next_state < PWRDM_POWER_ON) {
@@ -578,6 +589,8 @@ static int omap3_pm_suspend(void)
}
omap_uart_prepare_suspend();
+ omap3_intc_suspend();
+
omap_sram_idle();
restore:
@@ -835,6 +848,8 @@ static void __init prcm_setup_regs(void)
CM_AUTOIDLE);
}
+ omap_ctrl_writel(OMAP3430_AUTOIDLE, OMAP2_CONTROL_SYSCONFIG);
+
/*
* Set all plls to autoidle. This is needed until autoidle is
* enabled by clockfw
@@ -875,15 +890,23 @@ static void __init prcm_setup_regs(void)
prm_write_mod_reg(OMAP3430_IO_EN | OMAP3430_WKUP_EN,
OCP_MOD, OMAP3_PRM_IRQENABLE_MPU_OFFSET);
+ /* Enable PM_WKEN to support DSS LPR */
+ prm_write_mod_reg(OMAP3430_PM_WKEN_DSS_EN_DSS,
+ OMAP3430_DSS_MOD, PM_WKEN);
+
/* Enable wakeups in PER */
prm_write_mod_reg(OMAP3430_EN_GPIO2 | OMAP3430_EN_GPIO3 |
OMAP3430_EN_GPIO4 | OMAP3430_EN_GPIO5 |
- OMAP3430_EN_GPIO6 | OMAP3430_EN_UART3,
+ OMAP3430_EN_GPIO6 | OMAP3430_EN_UART3 |
+ OMAP3430_EN_MCBSP2 | OMAP3430_EN_MCBSP3 |
+ OMAP3430_EN_MCBSP4,
OMAP3430_PER_MOD, PM_WKEN);
/* and allow them to wake up MPU */
prm_write_mod_reg(OMAP3430_GRPSEL_GPIO2 | OMAP3430_EN_GPIO3 |
OMAP3430_GRPSEL_GPIO4 | OMAP3430_EN_GPIO5 |
- OMAP3430_GRPSEL_GPIO6 | OMAP3430_EN_UART3,
+ OMAP3430_GRPSEL_GPIO6 | OMAP3430_EN_UART3 |
+ OMAP3430_EN_MCBSP2 | OMAP3430_EN_MCBSP3 |
+ OMAP3430_EN_MCBSP4,
OMAP3430_PER_MOD, OMAP3430_PM_MPUGRPSEL);
/* Don't attach IVA interrupts */
@@ -904,24 +927,6 @@ static void __init prcm_setup_regs(void)
/* Clear any pending PRCM interrupts */
prm_write_mod_reg(0, OCP_MOD, OMAP3_PRM_IRQSTATUS_MPU_OFFSET);
- /* Don't attach IVA interrupts */
- prm_write_mod_reg(0, WKUP_MOD, OMAP3430_PM_IVAGRPSEL);
- prm_write_mod_reg(0, CORE_MOD, OMAP3430_PM_IVAGRPSEL1);
- prm_write_mod_reg(0, CORE_MOD, OMAP3430ES2_PM_IVAGRPSEL3);
- prm_write_mod_reg(0, OMAP3430_PER_MOD, OMAP3430_PM_IVAGRPSEL);
-
- /* Clear any pending 'reset' flags */
- prm_write_mod_reg(0xffffffff, MPU_MOD, RM_RSTST);
- prm_write_mod_reg(0xffffffff, CORE_MOD, RM_RSTST);
- prm_write_mod_reg(0xffffffff, OMAP3430_PER_MOD, RM_RSTST);
- prm_write_mod_reg(0xffffffff, OMAP3430_EMU_MOD, RM_RSTST);
- prm_write_mod_reg(0xffffffff, OMAP3430_NEON_MOD, RM_RSTST);
- prm_write_mod_reg(0xffffffff, OMAP3430_DSS_MOD, RM_RSTST);
- prm_write_mod_reg(0xffffffff, OMAP3430ES2_USBHOST_MOD, RM_RSTST);
-
- /* Clear any pending PRCM interrupts */
- prm_write_mod_reg(0, OCP_MOD, OMAP3_PRM_IRQSTATUS_MPU_OFFSET);
-
omap3_iva_idle();
omap3_d2d_idle();
}
diff --git a/arch/arm/mach-omap2/prcm.c b/arch/arm/mach-omap2/prcm.c
index 3ea8177ffb25..cf466ea1dffc 100644
--- a/arch/arm/mach-omap2/prcm.c
+++ b/arch/arm/mach-omap2/prcm.c
@@ -44,7 +44,6 @@ struct omap3_prcm_regs {
u32 iva2_cm_clksel2;
u32 cm_sysconfig;
u32 sgx_cm_clksel;
- u32 wkup_cm_clksel;
u32 dss_cm_clksel;
u32 cam_cm_clksel;
u32 per_cm_clksel;
@@ -53,7 +52,6 @@ struct omap3_prcm_regs {
u32 pll_cm_autoidle2;
u32 pll_cm_clksel4;
u32 pll_cm_clksel5;
- u32 pll_cm_clken;
u32 pll_cm_clken2;
u32 cm_polctrl;
u32 iva2_cm_fclken;
@@ -77,7 +75,6 @@ struct omap3_prcm_regs {
u32 usbhost_cm_iclken;
u32 iva2_cm_autiidle2;
u32 mpu_cm_autoidle2;
- u32 pll_cm_autoidle;
u32 iva2_cm_clkstctrl;
u32 mpu_cm_clkstctrl;
u32 core_cm_clkstctrl;
@@ -274,7 +271,6 @@ void omap3_prcm_save_context(void)
prcm_context.cm_sysconfig = __raw_readl(OMAP3430_CM_SYSCONFIG);
prcm_context.sgx_cm_clksel =
cm_read_mod_reg(OMAP3430ES2_SGX_MOD, CM_CLKSEL);
- prcm_context.wkup_cm_clksel = cm_read_mod_reg(WKUP_MOD, CM_CLKSEL);
prcm_context.dss_cm_clksel =
cm_read_mod_reg(OMAP3430_DSS_MOD, CM_CLKSEL);
prcm_context.cam_cm_clksel =
@@ -291,8 +287,6 @@ void omap3_prcm_save_context(void)
cm_read_mod_reg(PLL_MOD, OMAP3430ES2_CM_CLKSEL4);
prcm_context.pll_cm_clksel5 =
cm_read_mod_reg(PLL_MOD, OMAP3430ES2_CM_CLKSEL5);
- prcm_context.pll_cm_clken =
- cm_read_mod_reg(PLL_MOD, CM_CLKEN);
prcm_context.pll_cm_clken2 =
cm_read_mod_reg(PLL_MOD, OMAP3430ES2_CM_CLKEN2);
prcm_context.cm_polctrl = __raw_readl(OMAP3430_CM_POLCTRL);
@@ -338,8 +332,6 @@ void omap3_prcm_save_context(void)
cm_read_mod_reg(OMAP3430_IVA2_MOD, CM_AUTOIDLE2);
prcm_context.mpu_cm_autoidle2 =
cm_read_mod_reg(MPU_MOD, CM_AUTOIDLE2);
- prcm_context.pll_cm_autoidle =
- cm_read_mod_reg(PLL_MOD, CM_AUTOIDLE);
prcm_context.iva2_cm_clkstctrl =
cm_read_mod_reg(OMAP3430_IVA2_MOD, CM_CLKSTCTRL);
prcm_context.mpu_cm_clkstctrl =
@@ -431,7 +423,6 @@ void omap3_prcm_restore_context(void)
__raw_writel(prcm_context.cm_sysconfig, OMAP3430_CM_SYSCONFIG);
cm_write_mod_reg(prcm_context.sgx_cm_clksel, OMAP3430ES2_SGX_MOD,
CM_CLKSEL);
- cm_write_mod_reg(prcm_context.wkup_cm_clksel, WKUP_MOD, CM_CLKSEL);
cm_write_mod_reg(prcm_context.dss_cm_clksel, OMAP3430_DSS_MOD,
CM_CLKSEL);
cm_write_mod_reg(prcm_context.cam_cm_clksel, OMAP3430_CAM_MOD,
@@ -448,7 +439,6 @@ void omap3_prcm_restore_context(void)
OMAP3430ES2_CM_CLKSEL4);
cm_write_mod_reg(prcm_context.pll_cm_clksel5, PLL_MOD,
OMAP3430ES2_CM_CLKSEL5);
- cm_write_mod_reg(prcm_context.pll_cm_clken, PLL_MOD, CM_CLKEN);
cm_write_mod_reg(prcm_context.pll_cm_clken2, PLL_MOD,
OMAP3430ES2_CM_CLKEN2);
__raw_writel(prcm_context.cm_polctrl, OMAP3430_CM_POLCTRL);
@@ -487,7 +477,6 @@ void omap3_prcm_restore_context(void)
cm_write_mod_reg(prcm_context.iva2_cm_autiidle2, OMAP3430_IVA2_MOD,
CM_AUTOIDLE2);
cm_write_mod_reg(prcm_context.mpu_cm_autoidle2, MPU_MOD, CM_AUTOIDLE2);
- cm_write_mod_reg(prcm_context.pll_cm_autoidle, PLL_MOD, CM_AUTOIDLE);
cm_write_mod_reg(prcm_context.iva2_cm_clkstctrl, OMAP3430_IVA2_MOD,
CM_CLKSTCTRL);
cm_write_mod_reg(prcm_context.mpu_cm_clkstctrl, MPU_MOD, CM_CLKSTCTRL);
diff --git a/arch/arm/mach-omap2/prm.h b/arch/arm/mach-omap2/prm.h
index ea050ce188a7..40f006285163 100644
--- a/arch/arm/mach-omap2/prm.h
+++ b/arch/arm/mach-omap2/prm.h
@@ -24,6 +24,8 @@
OMAP2_L4_IO_ADDRESS(OMAP3430_PRM_BASE + (module) + (reg))
#define OMAP44XX_PRM_REGADDR(module, reg) \
OMAP2_L4_IO_ADDRESS(OMAP4430_PRM_BASE + (module) + (reg))
+#define OMAP44XX_CHIRONSS_REGADDR(module, reg) \
+ OMAP2_L4_IO_ADDRESS(OMAP4430_CHIRONSS_BASE + (module) + (reg))
#include "prm44xx.h"
diff --git a/arch/arm/mach-omap2/prm44xx.h b/arch/arm/mach-omap2/prm44xx.h
index 89be97f0589d..adb2558bb121 100644
--- a/arch/arm/mach-omap2/prm44xx.h
+++ b/arch/arm/mach-omap2/prm44xx.h
@@ -386,26 +386,26 @@
/* CHIRON_PRCM.CHIRONSS_OCP_SOCKET_PRCM register offsets */
-#define OMAP4430_REVISION_PRCM OMAP44XX_PRM_REGADDR(OMAP4430_CHIRONSS_CHIRONSS_OCP_SOCKET_PRCM_MOD, 0x0000)
+#define OMAP4430_REVISION_PRCM OMAP44XX_CHIRONSS_REGADDR(OMAP4430_CHIRONSS_CHIRONSS_OCP_SOCKET_PRCM_MOD, 0x0000)
/* CHIRON_PRCM.CHIRONSS_DEVICE_PRM register offsets */
-#define OMAP4430_CHIRON_PRCM_PRM_RSTST OMAP44XX_PRM_REGADDR(OMAP4430_CHIRONSS_CHIRONSS_DEVICE_PRM_MOD, 0x0000)
+#define OMAP4430_CHIRON_PRCM_PRM_RSTST OMAP44XX_CHIRONSS_REGADDR(OMAP4430_CHIRONSS_CHIRONSS_DEVICE_PRM_MOD, 0x0000)
/* CHIRON_PRCM.CHIRONSS_CPU0 register offsets */
-#define OMAP4430_PM_PDA_CPU0_PWRSTCTRL OMAP44XX_PRM_REGADDR(OMAP4430_CHIRONSS_CHIRONSS_CPU0_MOD, 0x0000)
-#define OMAP4430_PM_PDA_CPU0_PWRSTST OMAP44XX_PRM_REGADDR(OMAP4430_CHIRONSS_CHIRONSS_CPU0_MOD, 0x0004)
-#define OMAP4430_RM_PDA_CPU0_CPU0_CONTEXT OMAP44XX_PRM_REGADDR(OMAP4430_CHIRONSS_CHIRONSS_CPU0_MOD, 0x0008)
-#define OMAP4430_RM_PDA_CPU0_CPU0_RSTCTRL OMAP44XX_PRM_REGADDR(OMAP4430_CHIRONSS_CHIRONSS_CPU0_MOD, 0x000c)
-#define OMAP4430_RM_PDA_CPU0_CPU0_RSTST OMAP44XX_PRM_REGADDR(OMAP4430_CHIRONSS_CHIRONSS_CPU0_MOD, 0x0010)
-#define OMAP4430_CM_PDA_CPU0_CPU0_CLKCTRL OMAP44XX_PRM_REGADDR(OMAP4430_CHIRONSS_CHIRONSS_CPU0_MOD, 0x0014)
-#define OMAP4430_CM_PDA_CPU0_CLKSTCTRL OMAP44XX_PRM_REGADDR(OMAP4430_CHIRONSS_CHIRONSS_CPU0_MOD, 0x0018)
+#define OMAP4430_PM_PDA_CPU0_PWRSTCTRL OMAP44XX_CHIRONSS_REGADDR(OMAP4430_CHIRONSS_CHIRONSS_CPU0_MOD, 0x0000)
+#define OMAP4430_PM_PDA_CPU0_PWRSTST OMAP44XX_CHIRONSS_REGADDR(OMAP4430_CHIRONSS_CHIRONSS_CPU0_MOD, 0x0004)
+#define OMAP4430_RM_PDA_CPU0_CPU0_CONTEXT OMAP44XX_CHIRONSS_REGADDR(OMAP4430_CHIRONSS_CHIRONSS_CPU0_MOD, 0x0008)
+#define OMAP4430_RM_PDA_CPU0_CPU0_RSTCTRL OMAP44XX_CHIRONSS_REGADDR(OMAP4430_CHIRONSS_CHIRONSS_CPU0_MOD, 0x000c)
+#define OMAP4430_RM_PDA_CPU0_CPU0_RSTST OMAP44XX_CHIRONSS_REGADDR(OMAP4430_CHIRONSS_CHIRONSS_CPU0_MOD, 0x0010)
+#define OMAP4430_CM_PDA_CPU0_CPU0_CLKCTRL OMAP44XX_CHIRONSS_REGADDR(OMAP4430_CHIRONSS_CHIRONSS_CPU0_MOD, 0x0014)
+#define OMAP4430_CM_PDA_CPU0_CLKSTCTRL OMAP44XX_CHIRONSS_REGADDR(OMAP4430_CHIRONSS_CHIRONSS_CPU0_MOD, 0x0018)
/* CHIRON_PRCM.CHIRONSS_CPU1 register offsets */
-#define OMAP4430_PM_PDA_CPU1_PWRSTCTRL OMAP44XX_PRM_REGADDR(OMAP4430_CHIRONSS_CHIRONSS_CPU1_MOD, 0x0000)
-#define OMAP4430_PM_PDA_CPU1_PWRSTST OMAP44XX_PRM_REGADDR(OMAP4430_CHIRONSS_CHIRONSS_CPU1_MOD, 0x0004)
-#define OMAP4430_RM_PDA_CPU1_CPU1_CONTEXT OMAP44XX_PRM_REGADDR(OMAP4430_CHIRONSS_CHIRONSS_CPU1_MOD, 0x0008)
-#define OMAP4430_RM_PDA_CPU1_CPU1_RSTCTRL OMAP44XX_PRM_REGADDR(OMAP4430_CHIRONSS_CHIRONSS_CPU1_MOD, 0x000c)
-#define OMAP4430_RM_PDA_CPU1_CPU1_RSTST OMAP44XX_PRM_REGADDR(OMAP4430_CHIRONSS_CHIRONSS_CPU1_MOD, 0x0010)
-#define OMAP4430_CM_PDA_CPU1_CPU1_CLKCTRL OMAP44XX_PRM_REGADDR(OMAP4430_CHIRONSS_CHIRONSS_CPU1_MOD, 0x0014)
-#define OMAP4430_CM_PDA_CPU1_CLKSTCTRL OMAP44XX_PRM_REGADDR(OMAP4430_CHIRONSS_CHIRONSS_CPU1_MOD, 0x0018)
+#define OMAP4430_PM_PDA_CPU1_PWRSTCTRL OMAP44XX_CHIRONSS_REGADDR(OMAP4430_CHIRONSS_CHIRONSS_CPU1_MOD, 0x0000)
+#define OMAP4430_PM_PDA_CPU1_PWRSTST OMAP44XX_CHIRONSS_REGADDR(OMAP4430_CHIRONSS_CHIRONSS_CPU1_MOD, 0x0004)
+#define OMAP4430_RM_PDA_CPU1_CPU1_CONTEXT OMAP44XX_CHIRONSS_REGADDR(OMAP4430_CHIRONSS_CHIRONSS_CPU1_MOD, 0x0008)
+#define OMAP4430_RM_PDA_CPU1_CPU1_RSTCTRL OMAP44XX_CHIRONSS_REGADDR(OMAP4430_CHIRONSS_CHIRONSS_CPU1_MOD, 0x000c)
+#define OMAP4430_RM_PDA_CPU1_CPU1_RSTST OMAP44XX_CHIRONSS_REGADDR(OMAP4430_CHIRONSS_CHIRONSS_CPU1_MOD, 0x0010)
+#define OMAP4430_CM_PDA_CPU1_CPU1_CLKCTRL OMAP44XX_CHIRONSS_REGADDR(OMAP4430_CHIRONSS_CHIRONSS_CPU1_MOD, 0x0014)
+#define OMAP4430_CM_PDA_CPU1_CLKSTCTRL OMAP44XX_CHIRONSS_REGADDR(OMAP4430_CHIRONSS_CHIRONSS_CPU1_MOD, 0x0018)
#endif
diff --git a/arch/arm/mach-omap2/serial.c b/arch/arm/mach-omap2/serial.c
index 19805a7de06c..e10a02df6e1d 100644
--- a/arch/arm/mach-omap2/serial.c
+++ b/arch/arm/mach-omap2/serial.c
@@ -36,7 +36,13 @@
#define UART_OMAP_NO_EMPTY_FIFO_READ_IP_REV 0x52
#define UART_OMAP_WER 0x17 /* Wake-up enable register */
-#define DEFAULT_TIMEOUT (5 * HZ)
+/*
+ * NOTE: By default the serial timeout is disabled as it causes lost characters
+ * over the serial ports. This means that the UART clocks will stay on until
+ * disabled via sysfs. This also causes that any deeper omap sleep states are
+ * blocked.
+ */
+#define DEFAULT_TIMEOUT 0
struct omap_uart_state {
int num;
@@ -125,6 +131,13 @@ static struct plat_serial8250_port serial_platform_data3[] = {
}
};
#endif
+static inline unsigned int __serial_read_reg(struct uart_port *up,
+ int offset)
+{
+ offset <<= up->regshift;
+ return (unsigned int)__raw_readb(up->membase + offset);
+}
+
static inline unsigned int serial_read_reg(struct plat_serial8250_port *up,
int offset)
{
@@ -415,7 +428,8 @@ static void omap_uart_idle_init(struct omap_uart_state *uart)
uart->timeout = DEFAULT_TIMEOUT;
setup_timer(&uart->timer, omap_uart_idle_timer,
(unsigned long) uart);
- mod_timer(&uart->timer, jiffies + uart->timeout);
+ if (uart->timeout)
+ mod_timer(&uart->timer, jiffies + uart->timeout);
omap_uart_smart_idle_enable(uart, 0);
if (cpu_is_omap34xx()) {
@@ -583,11 +597,12 @@ static unsigned int serial_in_override(struct uart_port *up, int offset)
{
if (UART_RX == offset) {
unsigned int lsr;
- lsr = serial_read_reg(omap_uart[up->line].p, UART_LSR);
+ lsr = __serial_read_reg(up, UART_LSR);
if (!(lsr & UART_LSR_DR))
return -EPERM;
}
- return serial_read_reg(omap_uart[up->line].p, offset);
+
+ return __serial_read_reg(up, offset);
}
void __init omap_serial_early_init(void)
diff --git a/arch/arm/mach-omap2/sleep34xx.S b/arch/arm/mach-omap2/sleep34xx.S
index 15268f8b61de..c3626ea48143 100644
--- a/arch/arm/mach-omap2/sleep34xx.S
+++ b/arch/arm/mach-omap2/sleep34xx.S
@@ -245,7 +245,8 @@ restore:
mov r1, #0 @ set task id for ROM code in r1
mov r2, #4 @ set some flags in r2, r6
mov r6, #0xff
- adr r3, write_aux_control_params @ r3 points to parameters
+ ldr r4, scratchpad_base
+ ldr r3, [r4, #0xBC] @ r3 points to parameters
mcr p15, 0, r0, c7, c10, 4 @ data write barrier
mcr p15, 0, r0, c7, c10, 5 @ data memory barrier
.word 0xE1600071 @ call SMI monitor (smi #1)
@@ -253,14 +254,14 @@ restore:
b logic_l1_restore
l2_inv_api_params:
.word 0x1, 0x00
-write_aux_control_params:
- .word 0x1, 0x72
l2_inv_gp:
/* Execute smi to invalidate L2 cache */
mov r12, #0x1 @ set up to invalide L2
smi: .word 0xE1600070 @ Call SMI monitor (smieq)
/* Write to Aux control register to set some bits */
- mov r0, #0x72
+ ldr r4, scratchpad_base
+ ldr r3, [r4,#0xBC]
+ ldr r0, [r3,#4]
mov r12, #0x3
.word 0xE1600070 @ Call SMI monitor (smieq)
logic_l1_restore:
@@ -271,6 +272,7 @@ logic_l1_restore:
ldr r4, scratchpad_base
ldr r3, [r4,#0xBC]
+ adds r3, r3, #8
ldmia r3!, {r4-r6}
mov sp, r4
msr spsr_cxsf, r5
@@ -387,6 +389,9 @@ usettbr0:
save_context_wfi:
/*b save_context_wfi*/ @ enable to debug save code
mov r8, r0 /* Store SDRAM address in r8 */
+ mrc p15, 0, r5, c1, c0, 1 @ Read Auxiliary Control Register
+ mov r4, #0x1 @ Number of parameters for restore call
+ stmia r8!, {r4-r5}
/* Check what that target sleep state is:stored in r1*/
/* 1 - Only L1 and logic lost */
/* 2 - Only L2 lost */