summaryrefslogtreecommitdiff
path: root/arch/arm
diff options
context:
space:
mode:
Diffstat (limited to 'arch/arm')
-rw-r--r--arch/arm/Kconfig4
-rw-r--r--arch/arm/Kconfig.debug7
-rw-r--r--arch/arm/include/asm/fiq.h23
-rw-r--r--arch/arm/include/asm/page.h2
-rw-r--r--arch/arm/include/asm/smp.h7
-rw-r--r--arch/arm/include/asm/tlb.h53
-rw-r--r--arch/arm/include/asm/unistd.h1
-rw-r--r--arch/arm/kernel/Makefile2
-rw-r--r--arch/arm/kernel/calls.S1
-rw-r--r--arch/arm/kernel/fiq.c45
-rw-r--r--arch/arm/kernel/fiqasm.S49
-rw-r--r--arch/arm/kernel/head.S7
-rw-r--r--arch/arm/kernel/smp.c1
-rw-r--r--arch/arm/lib/lib1funcs.S25
-rw-r--r--arch/arm/mach-ixp4xx/include/mach/ixp46x_ts.h78
-rw-r--r--arch/arm/mach-netx/fb.c1
-rw-r--r--arch/arm/mach-omap2/board-3430sdp.c4
-rw-r--r--arch/arm/mach-omap2/board-4430sdp.c11
-rw-r--r--arch/arm/mach-omap2/board-am3517evm.c4
-rw-r--r--arch/arm/mach-omap2/board-cm-t35.c4
-rw-r--r--arch/arm/mach-omap2/board-devkit8000.c4
-rw-r--r--arch/arm/mach-omap2/board-igep0020.c4
-rw-r--r--arch/arm/mach-omap2/board-omap3beagle.c4
-rw-r--r--arch/arm/mach-omap2/board-omap3evm.c4
-rw-r--r--arch/arm/mach-omap2/board-omap3pandora.c2
-rw-r--r--arch/arm/mach-omap2/board-omap3stalker.c4
-rw-r--r--arch/arm/mach-omap2/board-omap4panda.c4
-rw-r--r--arch/arm/mach-omap2/board-overo.c4
-rw-r--r--arch/arm/mach-omap2/board-rx51-video.c2
-rw-r--r--arch/arm/mach-omap2/board-zoom-display.c2
-rw-r--r--arch/arm/mach-omap2/display.c77
-rw-r--r--arch/arm/mach-omap2/include/mach/board-zoom.h2
-rw-r--r--arch/arm/mach-shmobile/Makefile5
-rw-r--r--arch/arm/mach-shmobile/board-ag5evm.c118
-rw-r--r--arch/arm/mach-shmobile/board-ap4evb.c30
-rw-r--r--arch/arm/mach-shmobile/board-g4evm.c2
-rw-r--r--arch/arm/mach-shmobile/board-mackerel.c272
-rw-r--r--arch/arm/mach-shmobile/clock-sh7372.c21
-rw-r--r--arch/arm/mach-shmobile/clock-sh73a0.c19
-rw-r--r--arch/arm/mach-shmobile/cpuidle.c92
-rw-r--r--arch/arm/mach-shmobile/headsmp.S2
-rw-r--r--arch/arm/mach-shmobile/include/mach/common.h7
-rw-r--r--arch/arm/mach-shmobile/include/mach/head-ap4evb.txt3
-rw-r--r--arch/arm/mach-shmobile/include/mach/head-mackerel.txt3
-rw-r--r--arch/arm/mach-shmobile/include/mach/sh7372.h1
-rw-r--r--arch/arm/mach-shmobile/include/mach/sh73a0.h30
-rw-r--r--arch/arm/mach-shmobile/intc-sh7372.c46
-rw-r--r--arch/arm/mach-shmobile/pm-sh7372.c108
-rw-r--r--arch/arm/mach-shmobile/setup-sh7367.c223
-rw-r--r--arch/arm/mach-shmobile/setup-sh7372.c217
-rw-r--r--arch/arm/mach-shmobile/setup-sh7377.c239
-rw-r--r--arch/arm/mach-shmobile/setup-sh73a0.c244
-rw-r--r--arch/arm/mach-shmobile/sleep-sh7372.S260
-rw-r--r--arch/arm/mach-shmobile/smp-sh73a0.c9
-rw-r--r--arch/arm/mach-shmobile/suspend.c47
-rw-r--r--arch/arm/mach-tegra/include/mach/sdhci.h1
-rw-r--r--arch/arm/mach-ux500/Kconfig3
-rw-r--r--arch/arm/mach-ux500/Makefile4
-rw-r--r--arch/arm/mach-ux500/board-mop500-sdi.c16
-rw-r--r--arch/arm/mach-ux500/cpu-db5500.c2
-rw-r--r--arch/arm/mach-ux500/cpu-db8500.c7
-rw-r--r--arch/arm/mach-ux500/cpu.c7
-rw-r--r--arch/arm/mach-ux500/cpufreq.c211
-rw-r--r--arch/arm/mach-ux500/devices-common.h10
-rw-r--r--arch/arm/mach-ux500/devices-db5500.h28
-rw-r--r--arch/arm/mach-ux500/devices-db8500.h34
-rw-r--r--arch/arm/mach-ux500/include/mach/db5500-regs.h20
-rw-r--r--arch/arm/mach-ux500/include/mach/db8500-regs.h37
-rw-r--r--arch/arm/mach-ux500/include/mach/hardware.h4
-rw-r--r--arch/arm/mach-ux500/include/mach/id.h20
-rw-r--r--arch/arm/mach-ux500/include/mach/irqs-board-mop500.h5
-rw-r--r--arch/arm/mach-ux500/include/mach/irqs-board-u5500.h21
-rw-r--r--arch/arm/mach-ux500/include/mach/irqs-db5500.h27
-rw-r--r--arch/arm/mach-ux500/include/mach/irqs-db8500.h54
-rw-r--r--arch/arm/mach-ux500/include/mach/irqs.h46
-rw-r--r--arch/arm/mach-ux500/include/mach/prcmu-defs.h30
-rw-r--r--arch/arm/mach-ux500/include/mach/prcmu-regs.h96
-rw-r--r--arch/arm/mach-ux500/include/mach/prcmu.h28
-rw-r--r--arch/arm/mach-ux500/prcmu.c394
-rw-r--r--arch/arm/mm/cache-v6.S1
-rw-r--r--arch/arm/mm/cache-v7.S2
-rw-r--r--arch/arm/mm/context.c17
-rw-r--r--arch/arm/mm/init.c6
-rw-r--r--arch/arm/mm/mm.h7
-rw-r--r--arch/arm/mm/mmu.c11
-rw-r--r--arch/arm/mm/proc-v6.S4
-rw-r--r--arch/arm/mm/proc-v7.S14
-rw-r--r--arch/arm/plat-omap/include/plat/display.h591
-rw-r--r--arch/arm/plat-omap/include/plat/nokia-dsi-panel.h31
-rw-r--r--arch/arm/plat-omap/include/plat/panel-generic-dpi.h37
90 files changed, 2519 insertions, 1747 deletions
diff --git a/arch/arm/Kconfig b/arch/arm/Kconfig
index f59758dd86cf..9adc278a22ab 100644
--- a/arch/arm/Kconfig
+++ b/arch/arm/Kconfig
@@ -1389,7 +1389,6 @@ config NR_CPUS
config HOTPLUG_CPU
bool "Support for hot-pluggable CPUs (EXPERIMENTAL)"
depends on SMP && HOTPLUG && EXPERIMENTAL
- depends on !ARCH_MSM
help
Say Y here to experiment with turning CPUs off and on. CPUs
can be controlled through /sys/devices/system/cpu.
@@ -1506,6 +1505,9 @@ config ARCH_SPARSEMEM_DEFAULT
config ARCH_SELECT_MEMORY_MODEL
def_bool ARCH_SPARSEMEM_ENABLE
+config HAVE_ARCH_PFN_VALID
+ def_bool ARCH_HAS_HOLES_MEMORYMODEL || !SPARSEMEM
+
config HIGHMEM
bool "High Memory Support"
depends on MMU
diff --git a/arch/arm/Kconfig.debug b/arch/arm/Kconfig.debug
index 03d01d783e3b..81cbe40c159c 100644
--- a/arch/arm/Kconfig.debug
+++ b/arch/arm/Kconfig.debug
@@ -63,13 +63,6 @@ config DEBUG_USER
8 - SIGSEGV faults
16 - SIGBUS faults
-config DEBUG_STACK_USAGE
- bool "Enable stack utilization instrumentation"
- depends on DEBUG_KERNEL
- help
- Enables the display of the minimum amount of free stack which each
- task has ever had available in the sysrq-T output.
-
# These options are only for real kernel hackers who want to get their hands dirty.
config DEBUG_LL
bool "Kernel low-level debugging functions"
diff --git a/arch/arm/include/asm/fiq.h b/arch/arm/include/asm/fiq.h
index 2242ce22ec6c..d493d0b742a1 100644
--- a/arch/arm/include/asm/fiq.h
+++ b/arch/arm/include/asm/fiq.h
@@ -4,6 +4,13 @@
* Support for FIQ on ARM architectures.
* Written by Philip Blundell <philb@gnu.org>, 1998
* Re-written by Russell King
+ *
+ * NOTE: The FIQ mode registers are not magically preserved across
+ * suspend/resume.
+ *
+ * Drivers which require these registers to be preserved across power
+ * management operations must implement appropriate suspend/resume handlers to
+ * save and restore them.
*/
#ifndef __ASM_FIQ_H
@@ -29,9 +36,21 @@ struct fiq_handler {
extern int claim_fiq(struct fiq_handler *f);
extern void release_fiq(struct fiq_handler *f);
extern void set_fiq_handler(void *start, unsigned int length);
-extern void set_fiq_regs(struct pt_regs *regs);
-extern void get_fiq_regs(struct pt_regs *regs);
extern void enable_fiq(int fiq);
extern void disable_fiq(int fiq);
+/* helpers defined in fiqasm.S: */
+extern void __set_fiq_regs(unsigned long const *regs);
+extern void __get_fiq_regs(unsigned long *regs);
+
+static inline void set_fiq_regs(struct pt_regs const *regs)
+{
+ __set_fiq_regs(&regs->ARM_r8);
+}
+
+static inline void get_fiq_regs(struct pt_regs *regs)
+{
+ __get_fiq_regs(&regs->ARM_r8);
+}
+
#endif
diff --git a/arch/arm/include/asm/page.h b/arch/arm/include/asm/page.h
index f51a69595f6e..ac75d0848889 100644
--- a/arch/arm/include/asm/page.h
+++ b/arch/arm/include/asm/page.h
@@ -197,7 +197,7 @@ typedef unsigned long pgprot_t;
typedef struct page *pgtable_t;
-#ifndef CONFIG_SPARSEMEM
+#ifdef CONFIG_HAVE_ARCH_PFN_VALID
extern int pfn_valid(unsigned long);
#endif
diff --git a/arch/arm/include/asm/smp.h b/arch/arm/include/asm/smp.h
index a87664f54f93..e42d96a45d3e 100644
--- a/arch/arm/include/asm/smp.h
+++ b/arch/arm/include/asm/smp.h
@@ -20,12 +20,6 @@
#define raw_smp_processor_id() (current_thread_info()->cpu)
-/*
- * at the moment, there's not a big penalty for changing CPUs
- * (the >big< penalty is running SMP in the first place)
- */
-#define PROC_CHANGE_PENALTY 15
-
struct seq_file;
/*
@@ -76,6 +70,7 @@ extern void platform_smp_prepare_cpus(unsigned int);
*/
struct secondary_data {
unsigned long pgdir;
+ unsigned long swapper_pg_dir;
void *stack;
};
extern struct secondary_data secondary_data;
diff --git a/arch/arm/include/asm/tlb.h b/arch/arm/include/asm/tlb.h
index 82dfe5d0c41e..265f908c4a6e 100644
--- a/arch/arm/include/asm/tlb.h
+++ b/arch/arm/include/asm/tlb.h
@@ -41,12 +41,12 @@
*/
#if defined(CONFIG_SMP) || defined(CONFIG_CPU_32v7)
#define tlb_fast_mode(tlb) 0
-#define FREE_PTE_NR 500
#else
#define tlb_fast_mode(tlb) 1
-#define FREE_PTE_NR 0
#endif
+#define MMU_GATHER_BUNDLE 8
+
/*
* TLB handling. This allows us to remove pages from the page
* tables, and efficiently handle the TLB issues.
@@ -58,7 +58,9 @@ struct mmu_gather {
unsigned long range_start;
unsigned long range_end;
unsigned int nr;
- struct page *pages[FREE_PTE_NR];
+ unsigned int max;
+ struct page **pages;
+ struct page *local[MMU_GATHER_BUNDLE];
};
DECLARE_PER_CPU(struct mmu_gather, mmu_gathers);
@@ -97,26 +99,37 @@ static inline void tlb_add_flush(struct mmu_gather *tlb, unsigned long addr)
}
}
+static inline void __tlb_alloc_page(struct mmu_gather *tlb)
+{
+ unsigned long addr = __get_free_pages(GFP_NOWAIT | __GFP_NOWARN, 0);
+
+ if (addr) {
+ tlb->pages = (void *)addr;
+ tlb->max = PAGE_SIZE / sizeof(struct page *);
+ }
+}
+
static inline void tlb_flush_mmu(struct mmu_gather *tlb)
{
tlb_flush(tlb);
if (!tlb_fast_mode(tlb)) {
free_pages_and_swap_cache(tlb->pages, tlb->nr);
tlb->nr = 0;
+ if (tlb->pages == tlb->local)
+ __tlb_alloc_page(tlb);
}
}
-static inline struct mmu_gather *
-tlb_gather_mmu(struct mm_struct *mm, unsigned int full_mm_flush)
+static inline void
+tlb_gather_mmu(struct mmu_gather *tlb, struct mm_struct *mm, unsigned int fullmm)
{
- struct mmu_gather *tlb = &get_cpu_var(mmu_gathers);
-
tlb->mm = mm;
- tlb->fullmm = full_mm_flush;
+ tlb->fullmm = fullmm;
tlb->vma = NULL;
+ tlb->max = ARRAY_SIZE(tlb->local);
+ tlb->pages = tlb->local;
tlb->nr = 0;
-
- return tlb;
+ __tlb_alloc_page(tlb);
}
static inline void
@@ -127,7 +140,8 @@ tlb_finish_mmu(struct mmu_gather *tlb, unsigned long start, unsigned long end)
/* keep the page table cache within bounds */
check_pgt_cache();
- put_cpu_var(mmu_gathers);
+ if (tlb->pages != tlb->local)
+ free_pages((unsigned long)tlb->pages, 0);
}
/*
@@ -162,15 +176,22 @@ tlb_end_vma(struct mmu_gather *tlb, struct vm_area_struct *vma)
tlb_flush(tlb);
}
-static inline void tlb_remove_page(struct mmu_gather *tlb, struct page *page)
+static inline int __tlb_remove_page(struct mmu_gather *tlb, struct page *page)
{
if (tlb_fast_mode(tlb)) {
free_page_and_swap_cache(page);
- } else {
- tlb->pages[tlb->nr++] = page;
- if (tlb->nr >= FREE_PTE_NR)
- tlb_flush_mmu(tlb);
+ return 1; /* avoid calling tlb_flush_mmu */
}
+
+ tlb->pages[tlb->nr++] = page;
+ VM_BUG_ON(tlb->nr > tlb->max);
+ return tlb->max - tlb->nr;
+}
+
+static inline void tlb_remove_page(struct mmu_gather *tlb, struct page *page)
+{
+ if (!__tlb_remove_page(tlb, page))
+ tlb_flush_mmu(tlb);
}
static inline void __pte_free_tlb(struct mmu_gather *tlb, pgtable_t pte,
diff --git a/arch/arm/include/asm/unistd.h b/arch/arm/include/asm/unistd.h
index 87dbe3e21970..3de689aa6f68 100644
--- a/arch/arm/include/asm/unistd.h
+++ b/arch/arm/include/asm/unistd.h
@@ -400,6 +400,7 @@
#define __NR_open_by_handle_at (__NR_SYSCALL_BASE+371)
#define __NR_clock_adjtime (__NR_SYSCALL_BASE+372)
#define __NR_syncfs (__NR_SYSCALL_BASE+373)
+#define __NR_sendmmsg (__NR_SYSCALL_BASE+374)
/*
* The following SWIs are ARM private.
diff --git a/arch/arm/kernel/Makefile b/arch/arm/kernel/Makefile
index 908c78cb1d1c..a5b31af5c2b8 100644
--- a/arch/arm/kernel/Makefile
+++ b/arch/arm/kernel/Makefile
@@ -24,7 +24,7 @@ obj-$(CONFIG_OC_ETM) += etm.o
obj-$(CONFIG_ISA_DMA_API) += dma.o
obj-$(CONFIG_ARCH_ACORN) += ecard.o
-obj-$(CONFIG_FIQ) += fiq.o
+obj-$(CONFIG_FIQ) += fiq.o fiqasm.o
obj-$(CONFIG_MODULES) += armksyms.o module.o
obj-$(CONFIG_ARTHUR) += arthur.o
obj-$(CONFIG_ISA_DMA) += dma-isa.o
diff --git a/arch/arm/kernel/calls.S b/arch/arm/kernel/calls.S
index 7fbf28c35bb2..24cdac3ce2e3 100644
--- a/arch/arm/kernel/calls.S
+++ b/arch/arm/kernel/calls.S
@@ -383,6 +383,7 @@
CALL(sys_open_by_handle_at)
CALL(sys_clock_adjtime)
CALL(sys_syncfs)
+ CALL(sys_sendmmsg)
#ifndef syscalls_counted
.equ syscalls_padding, ((NR_syscalls + 3) & ~3) - NR_syscalls
#define syscalls_counted
diff --git a/arch/arm/kernel/fiq.c b/arch/arm/kernel/fiq.c
index e72dc34eea1c..4c164ece5891 100644
--- a/arch/arm/kernel/fiq.c
+++ b/arch/arm/kernel/fiq.c
@@ -89,47 +89,6 @@ void set_fiq_handler(void *start, unsigned int length)
flush_icache_range(0x1c, 0x1c + length);
}
-/*
- * Taking an interrupt in FIQ mode is death, so both these functions
- * disable irqs for the duration. Note - these functions are almost
- * entirely coded in assembly.
- */
-void __naked set_fiq_regs(struct pt_regs *regs)
-{
- register unsigned long tmp;
- asm volatile (
- "mov ip, sp\n\
- stmfd sp!, {fp, ip, lr, pc}\n\
- sub fp, ip, #4\n\
- mrs %0, cpsr\n\
- msr cpsr_c, %2 @ select FIQ mode\n\
- mov r0, r0\n\
- ldmia %1, {r8 - r14}\n\
- msr cpsr_c, %0 @ return to SVC mode\n\
- mov r0, r0\n\
- ldmfd sp, {fp, sp, pc}"
- : "=&r" (tmp)
- : "r" (&regs->ARM_r8), "I" (PSR_I_BIT | PSR_F_BIT | FIQ_MODE));
-}
-
-void __naked get_fiq_regs(struct pt_regs *regs)
-{
- register unsigned long tmp;
- asm volatile (
- "mov ip, sp\n\
- stmfd sp!, {fp, ip, lr, pc}\n\
- sub fp, ip, #4\n\
- mrs %0, cpsr\n\
- msr cpsr_c, %2 @ select FIQ mode\n\
- mov r0, r0\n\
- stmia %1, {r8 - r14}\n\
- msr cpsr_c, %0 @ return to SVC mode\n\
- mov r0, r0\n\
- ldmfd sp, {fp, sp, pc}"
- : "=&r" (tmp)
- : "r" (&regs->ARM_r8), "I" (PSR_I_BIT | PSR_F_BIT | FIQ_MODE));
-}
-
int claim_fiq(struct fiq_handler *f)
{
int ret = 0;
@@ -174,8 +133,8 @@ void disable_fiq(int fiq)
}
EXPORT_SYMBOL(set_fiq_handler);
-EXPORT_SYMBOL(set_fiq_regs);
-EXPORT_SYMBOL(get_fiq_regs);
+EXPORT_SYMBOL(__set_fiq_regs); /* defined in fiqasm.S */
+EXPORT_SYMBOL(__get_fiq_regs); /* defined in fiqasm.S */
EXPORT_SYMBOL(claim_fiq);
EXPORT_SYMBOL(release_fiq);
EXPORT_SYMBOL(enable_fiq);
diff --git a/arch/arm/kernel/fiqasm.S b/arch/arm/kernel/fiqasm.S
new file mode 100644
index 000000000000..207f9d652010
--- /dev/null
+++ b/arch/arm/kernel/fiqasm.S
@@ -0,0 +1,49 @@
+/*
+ * linux/arch/arm/kernel/fiqasm.S
+ *
+ * Derived from code originally in linux/arch/arm/kernel/fiq.c:
+ *
+ * Copyright (C) 1998 Russell King
+ * Copyright (C) 1998, 1999 Phil Blundell
+ * Copyright (C) 2011, Linaro Limited
+ *
+ * FIQ support written by Philip Blundell <philb@gnu.org>, 1998.
+ *
+ * FIQ support re-written by Russell King to be more generic
+ *
+ * v7/Thumb-2 compatibility modifications by Linaro Limited, 2011.
+ */
+
+#include <linux/linkage.h>
+#include <asm/assembler.h>
+
+/*
+ * Taking an interrupt in FIQ mode is death, so both these functions
+ * disable irqs for the duration.
+ */
+
+ENTRY(__set_fiq_regs)
+ mov r2, #PSR_I_BIT | PSR_F_BIT | FIQ_MODE
+ mrs r1, cpsr
+ msr cpsr_c, r2 @ select FIQ mode
+ mov r0, r0 @ avoid hazard prior to ARMv4
+ ldmia r0!, {r8 - r12}
+ ldr sp, [r0], #4
+ ldr lr, [r0]
+ msr cpsr_c, r1 @ return to SVC mode
+ mov r0, r0 @ avoid hazard prior to ARMv4
+ mov pc, lr
+ENDPROC(__set_fiq_regs)
+
+ENTRY(__get_fiq_regs)
+ mov r2, #PSR_I_BIT | PSR_F_BIT | FIQ_MODE
+ mrs r1, cpsr
+ msr cpsr_c, r2 @ select FIQ mode
+ mov r0, r0 @ avoid hazard prior to ARMv4
+ stmia r0!, {r8 - r12}
+ str sp, [r0], #4
+ str lr, [r0]
+ msr cpsr_c, r1 @ return to SVC mode
+ mov r0, r0 @ avoid hazard prior to ARMv4
+ mov pc, lr
+ENDPROC(__get_fiq_regs)
diff --git a/arch/arm/kernel/head.S b/arch/arm/kernel/head.S
index a5e5c5b9b48e..278c1b0ebb2e 100644
--- a/arch/arm/kernel/head.S
+++ b/arch/arm/kernel/head.S
@@ -113,6 +113,7 @@ ENTRY(stext)
ldr r13, =__mmap_switched @ address to jump to after
@ mmu has been enabled
adr lr, BSYM(1f) @ return (PIC) address
+ mov r8, r4 @ set TTBR1 to swapper_pg_dir
ARM( add pc, r10, #PROCINFO_INITFUNC )
THUMB( add r12, r10, #PROCINFO_INITFUNC )
THUMB( mov pc, r12 )
@@ -302,8 +303,10 @@ ENTRY(secondary_startup)
*/
adr r4, __secondary_data
ldmia r4, {r5, r7, r12} @ address to jump to after
- sub r4, r4, r5 @ mmu has been enabled
- ldr r4, [r7, r4] @ get secondary_data.pgdir
+ sub lr, r4, r5 @ mmu has been enabled
+ ldr r4, [r7, lr] @ get secondary_data.pgdir
+ add r7, r7, #4
+ ldr r8, [r7, lr] @ get secondary_data.swapper_pg_dir
adr lr, BSYM(__enable_mmu) @ return address
mov r13, r12 @ __secondary_switched address
ARM( add pc, r10, #PROCINFO_INITFUNC ) @ initialise processor
diff --git a/arch/arm/kernel/smp.c b/arch/arm/kernel/smp.c
index d439a8f4c078..344e52b16c8c 100644
--- a/arch/arm/kernel/smp.c
+++ b/arch/arm/kernel/smp.c
@@ -105,6 +105,7 @@ int __cpuinit __cpu_up(unsigned int cpu)
*/
secondary_data.stack = task_stack_page(idle) + THREAD_START_SP;
secondary_data.pgdir = virt_to_phys(pgd);
+ secondary_data.swapper_pg_dir = virt_to_phys(swapper_pg_dir);
__cpuc_flush_dcache_area(&secondary_data, sizeof(secondary_data));
outer_clean_range(__pa(&secondary_data), __pa(&secondary_data + 1));
diff --git a/arch/arm/lib/lib1funcs.S b/arch/arm/lib/lib1funcs.S
index 6dc06487f3c3..c562f649734c 100644
--- a/arch/arm/lib/lib1funcs.S
+++ b/arch/arm/lib/lib1funcs.S
@@ -35,7 +35,7 @@ Boston, MA 02111-1307, USA. */
#include <linux/linkage.h>
#include <asm/assembler.h>
-
+#include <asm/unwind.h>
.macro ARM_DIV_BODY dividend, divisor, result, curbit
@@ -207,6 +207,7 @@ Boston, MA 02111-1307, USA. */
ENTRY(__udivsi3)
ENTRY(__aeabi_uidiv)
+UNWIND(.fnstart)
subs r2, r1, #1
moveq pc, lr
@@ -230,10 +231,12 @@ ENTRY(__aeabi_uidiv)
mov r0, r0, lsr r2
mov pc, lr
+UNWIND(.fnend)
ENDPROC(__udivsi3)
ENDPROC(__aeabi_uidiv)
ENTRY(__umodsi3)
+UNWIND(.fnstart)
subs r2, r1, #1 @ compare divisor with 1
bcc Ldiv0
@@ -247,10 +250,12 @@ ENTRY(__umodsi3)
mov pc, lr
+UNWIND(.fnend)
ENDPROC(__umodsi3)
ENTRY(__divsi3)
ENTRY(__aeabi_idiv)
+UNWIND(.fnstart)
cmp r1, #0
eor ip, r0, r1 @ save the sign of the result.
@@ -287,10 +292,12 @@ ENTRY(__aeabi_idiv)
rsbmi r0, r0, #0
mov pc, lr
+UNWIND(.fnend)
ENDPROC(__divsi3)
ENDPROC(__aeabi_idiv)
ENTRY(__modsi3)
+UNWIND(.fnstart)
cmp r1, #0
beq Ldiv0
@@ -310,11 +317,14 @@ ENTRY(__modsi3)
rsbmi r0, r0, #0
mov pc, lr
+UNWIND(.fnend)
ENDPROC(__modsi3)
#ifdef CONFIG_AEABI
ENTRY(__aeabi_uidivmod)
+UNWIND(.fnstart)
+UNWIND(.save {r0, r1, ip, lr} )
stmfd sp!, {r0, r1, ip, lr}
bl __aeabi_uidiv
@@ -323,10 +333,12 @@ ENTRY(__aeabi_uidivmod)
sub r1, r1, r3
mov pc, lr
+UNWIND(.fnend)
ENDPROC(__aeabi_uidivmod)
ENTRY(__aeabi_idivmod)
-
+UNWIND(.fnstart)
+UNWIND(.save {r0, r1, ip, lr} )
stmfd sp!, {r0, r1, ip, lr}
bl __aeabi_idiv
ldmfd sp!, {r1, r2, ip, lr}
@@ -334,15 +346,18 @@ ENTRY(__aeabi_idivmod)
sub r1, r1, r3
mov pc, lr
+UNWIND(.fnend)
ENDPROC(__aeabi_idivmod)
#endif
Ldiv0:
-
+UNWIND(.fnstart)
+UNWIND(.pad #4)
+UNWIND(.save {lr})
str lr, [sp, #-8]!
bl __div0
mov r0, #0 @ About as wrong as it could be.
ldr pc, [sp], #8
-
-
+UNWIND(.fnend)
+ENDPROC(Ldiv0)
diff --git a/arch/arm/mach-ixp4xx/include/mach/ixp46x_ts.h b/arch/arm/mach-ixp4xx/include/mach/ixp46x_ts.h
new file mode 100644
index 000000000000..292d55ed2113
--- /dev/null
+++ b/arch/arm/mach-ixp4xx/include/mach/ixp46x_ts.h
@@ -0,0 +1,78 @@
+/*
+ * PTP 1588 clock using the IXP46X
+ *
+ * Copyright (C) 2010 OMICRON electronics GmbH
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
+ */
+
+#ifndef _IXP46X_TS_H_
+#define _IXP46X_TS_H_
+
+#define DEFAULT_ADDEND 0xF0000029
+#define TICKS_NS_SHIFT 4
+
+struct ixp46x_channel_ctl {
+ u32 ch_control; /* 0x40 Time Synchronization Channel Control */
+ u32 ch_event; /* 0x44 Time Synchronization Channel Event */
+ u32 tx_snap_lo; /* 0x48 Transmit Snapshot Low Register */
+ u32 tx_snap_hi; /* 0x4C Transmit Snapshot High Register */
+ u32 rx_snap_lo; /* 0x50 Receive Snapshot Low Register */
+ u32 rx_snap_hi; /* 0x54 Receive Snapshot High Register */
+ u32 src_uuid_lo; /* 0x58 Source UUID0 Low Register */
+ u32 src_uuid_hi; /* 0x5C Sequence Identifier/Source UUID0 High */
+};
+
+struct ixp46x_ts_regs {
+ u32 control; /* 0x00 Time Sync Control Register */
+ u32 event; /* 0x04 Time Sync Event Register */
+ u32 addend; /* 0x08 Time Sync Addend Register */
+ u32 accum; /* 0x0C Time Sync Accumulator Register */
+ u32 test; /* 0x10 Time Sync Test Register */
+ u32 unused; /* 0x14 */
+ u32 rsystime_lo; /* 0x18 RawSystemTime_Low Register */
+ u32 rsystime_hi; /* 0x1C RawSystemTime_High Register */
+ u32 systime_lo; /* 0x20 SystemTime_Low Register */
+ u32 systime_hi; /* 0x24 SystemTime_High Register */
+ u32 trgt_lo; /* 0x28 TargetTime_Low Register */
+ u32 trgt_hi; /* 0x2C TargetTime_High Register */
+ u32 asms_lo; /* 0x30 Auxiliary Slave Mode Snapshot Low */
+ u32 asms_hi; /* 0x34 Auxiliary Slave Mode Snapshot High */
+ u32 amms_lo; /* 0x38 Auxiliary Master Mode Snapshot Low */
+ u32 amms_hi; /* 0x3C Auxiliary Master Mode Snapshot High */
+
+ struct ixp46x_channel_ctl channel[3];
+};
+
+/* 0x00 Time Sync Control Register Bits */
+#define TSCR_AMM (1<<3)
+#define TSCR_ASM (1<<2)
+#define TSCR_TTM (1<<1)
+#define TSCR_RST (1<<0)
+
+/* 0x04 Time Sync Event Register Bits */
+#define TSER_SNM (1<<3)
+#define TSER_SNS (1<<2)
+#define TTIPEND (1<<1)
+
+/* 0x40 Time Synchronization Channel Control Register Bits */
+#define MASTER_MODE (1<<0)
+#define TIMESTAMP_ALL (1<<1)
+
+/* 0x44 Time Synchronization Channel Event Register Bits */
+#define TX_SNAPSHOT_LOCKED (1<<0)
+#define RX_SNAPSHOT_LOCKED (1<<1)
+
+#endif
diff --git a/arch/arm/mach-netx/fb.c b/arch/arm/mach-netx/fb.c
index 5b84bcd30271..b9913234bbf6 100644
--- a/arch/arm/mach-netx/fb.c
+++ b/arch/arm/mach-netx/fb.c
@@ -103,7 +103,6 @@ static struct amba_device fb_device = {
.flags = IORESOURCE_MEM,
},
.irq = { NETX_IRQ_LCD, NO_IRQ },
- .periphid = 0x10112400,
};
int netx_fb_init(struct clcd_board *board, struct clcd_panel *panel)
diff --git a/arch/arm/mach-omap2/board-3430sdp.c b/arch/arm/mach-omap2/board-3430sdp.c
index 9afd087cc29c..23244cd0a5b6 100644
--- a/arch/arm/mach-omap2/board-3430sdp.c
+++ b/arch/arm/mach-omap2/board-3430sdp.c
@@ -37,8 +37,8 @@
#include <plat/common.h>
#include <plat/dma.h>
#include <plat/gpmc.h>
-#include <plat/display.h>
-#include <plat/panel-generic-dpi.h>
+#include <video/omapdss.h>
+#include <video/omap-panel-generic-dpi.h>
#include <plat/gpmc-smc91x.h>
diff --git a/arch/arm/mach-omap2/board-4430sdp.c b/arch/arm/mach-omap2/board-4430sdp.c
index 56702c5e577f..93edd7fcf451 100644
--- a/arch/arm/mach-omap2/board-4430sdp.c
+++ b/arch/arm/mach-omap2/board-4430sdp.c
@@ -36,7 +36,7 @@
#include <plat/usb.h>
#include <plat/mmc.h>
#include <plat/omap4-keypad.h>
-#include <plat/display.h>
+#include <video/omapdss.h>
#include "mux.h"
#include "hsmmc.h"
@@ -680,6 +680,15 @@ static struct omap_dss_device sdp4430_hdmi_device = {
.name = "hdmi",
.driver_name = "hdmi_panel",
.type = OMAP_DISPLAY_TYPE_HDMI,
+ .clocks = {
+ .dispc = {
+ .dispc_fclk_src = OMAP_DSS_CLK_SRC_FCK,
+ },
+ .hdmi = {
+ .regn = 15,
+ .regm2 = 1,
+ },
+ },
.platform_enable = sdp4430_panel_enable_hdmi,
.platform_disable = sdp4430_panel_disable_hdmi,
.channel = OMAP_DSS_CHANNEL_DIGIT,
diff --git a/arch/arm/mach-omap2/board-am3517evm.c b/arch/arm/mach-omap2/board-am3517evm.c
index ce7d5e6e4150..ff8c59be36e5 100644
--- a/arch/arm/mach-omap2/board-am3517evm.c
+++ b/arch/arm/mach-omap2/board-am3517evm.c
@@ -34,8 +34,8 @@
#include <plat/board.h>
#include <plat/common.h>
#include <plat/usb.h>
-#include <plat/display.h>
-#include <plat/panel-generic-dpi.h>
+#include <video/omapdss.h>
+#include <video/omap-panel-generic-dpi.h>
#include "mux.h"
#include "control.h"
diff --git a/arch/arm/mach-omap2/board-cm-t35.c b/arch/arm/mach-omap2/board-cm-t35.c
index 02a12b41c0ff..9340f6a06f4a 100644
--- a/arch/arm/mach-omap2/board-cm-t35.c
+++ b/arch/arm/mach-omap2/board-cm-t35.c
@@ -45,8 +45,8 @@
#include <plat/nand.h>
#include <plat/gpmc.h>
#include <plat/usb.h>
-#include <plat/display.h>
-#include <plat/panel-generic-dpi.h>
+#include <video/omapdss.h>
+#include <video/omap-panel-generic-dpi.h>
#include <plat/mcspi.h>
#include <mach/hardware.h>
diff --git a/arch/arm/mach-omap2/board-devkit8000.c b/arch/arm/mach-omap2/board-devkit8000.c
index 65f9fde2c567..1d1b56a29fb1 100644
--- a/arch/arm/mach-omap2/board-devkit8000.c
+++ b/arch/arm/mach-omap2/board-devkit8000.c
@@ -45,8 +45,8 @@
#include <plat/gpmc.h>
#include <plat/nand.h>
#include <plat/usb.h>
-#include <plat/display.h>
-#include <plat/panel-generic-dpi.h>
+#include <video/omapdss.h>
+#include <video/omap-panel-generic-dpi.h>
#include <plat/mcspi.h>
#include <linux/input/matrix_keypad.h>
diff --git a/arch/arm/mach-omap2/board-igep0020.c b/arch/arm/mach-omap2/board-igep0020.c
index 34cf982b9679..3da64d361651 100644
--- a/arch/arm/mach-omap2/board-igep0020.c
+++ b/arch/arm/mach-omap2/board-igep0020.c
@@ -31,8 +31,8 @@
#include <plat/common.h>
#include <plat/gpmc.h>
#include <plat/usb.h>
-#include <plat/display.h>
-#include <plat/panel-generic-dpi.h>
+#include <video/omapdss.h>
+#include <video/omap-panel-generic-dpi.h>
#include <plat/onenand.h>
#include "mux.h"
diff --git a/arch/arm/mach-omap2/board-omap3beagle.c b/arch/arm/mach-omap2/board-omap3beagle.c
index 33007fd4a083..97750d483a70 100644
--- a/arch/arm/mach-omap2/board-omap3beagle.c
+++ b/arch/arm/mach-omap2/board-omap3beagle.c
@@ -41,8 +41,8 @@
#include <plat/board.h>
#include <plat/common.h>
-#include <plat/display.h>
-#include <plat/panel-generic-dpi.h>
+#include <video/omapdss.h>
+#include <video/omap-panel-generic-dpi.h>
#include <plat/gpmc.h>
#include <plat/nand.h>
#include <plat/usb.h>
diff --git a/arch/arm/mach-omap2/board-omap3evm.c b/arch/arm/mach-omap2/board-omap3evm.c
index 5a1a916e5cc8..7f94cccdb076 100644
--- a/arch/arm/mach-omap2/board-omap3evm.c
+++ b/arch/arm/mach-omap2/board-omap3evm.c
@@ -44,8 +44,8 @@
#include <plat/usb.h>
#include <plat/common.h>
#include <plat/mcspi.h>
-#include <plat/display.h>
-#include <plat/panel-generic-dpi.h>
+#include <video/omapdss.h>
+#include <video/omap-panel-generic-dpi.h>
#include "mux.h"
#include "sdram-micron-mt46h32m32lf-6.h"
diff --git a/arch/arm/mach-omap2/board-omap3pandora.c b/arch/arm/mach-omap2/board-omap3pandora.c
index 07dba888f450..1db15492d82b 100644
--- a/arch/arm/mach-omap2/board-omap3pandora.c
+++ b/arch/arm/mach-omap2/board-omap3pandora.c
@@ -46,7 +46,7 @@
#include <mach/hardware.h>
#include <plat/mcspi.h>
#include <plat/usb.h>
-#include <plat/display.h>
+#include <video/omapdss.h>
#include <plat/nand.h>
#include "mux.h"
diff --git a/arch/arm/mach-omap2/board-omap3stalker.c b/arch/arm/mach-omap2/board-omap3stalker.c
index a6e0b9161c99..a72c90a08c8a 100644
--- a/arch/arm/mach-omap2/board-omap3stalker.c
+++ b/arch/arm/mach-omap2/board-omap3stalker.c
@@ -39,8 +39,8 @@
#include <plat/gpmc.h>
#include <plat/nand.h>
#include <plat/usb.h>
-#include <plat/display.h>
-#include <plat/panel-generic-dpi.h>
+#include <video/omapdss.h>
+#include <video/omap-panel-generic-dpi.h>
#include <plat/mcspi.h>
#include <linux/input/matrix_keypad.h>
diff --git a/arch/arm/mach-omap2/board-omap4panda.c b/arch/arm/mach-omap2/board-omap4panda.c
index f3a7b1011914..e4973ac77cbc 100644
--- a/arch/arm/mach-omap2/board-omap4panda.c
+++ b/arch/arm/mach-omap2/board-omap4panda.c
@@ -34,13 +34,13 @@
#include <asm/mach-types.h>
#include <asm/mach/arch.h>
#include <asm/mach/map.h>
-#include <plat/display.h>
+#include <video/omapdss.h>
#include <plat/board.h>
#include <plat/common.h>
#include <plat/usb.h>
#include <plat/mmc.h>
-#include <plat/panel-generic-dpi.h>
+#include <video/omap-panel-generic-dpi.h>
#include "timer-gp.h"
#include "hsmmc.h"
diff --git a/arch/arm/mach-omap2/board-overo.c b/arch/arm/mach-omap2/board-overo.c
index 59ca33326b8c..9d192ff3b9ac 100644
--- a/arch/arm/mach-omap2/board-overo.c
+++ b/arch/arm/mach-omap2/board-overo.c
@@ -43,8 +43,8 @@
#include <plat/board.h>
#include <plat/common.h>
-#include <plat/display.h>
-#include <plat/panel-generic-dpi.h>
+#include <video/omapdss.h>
+#include <video/omap-panel-generic-dpi.h>
#include <mach/gpio.h>
#include <plat/gpmc.h>
#include <mach/hardware.h>
diff --git a/arch/arm/mach-omap2/board-rx51-video.c b/arch/arm/mach-omap2/board-rx51-video.c
index 89a66db8b77d..2df10b6a5940 100644
--- a/arch/arm/mach-omap2/board-rx51-video.c
+++ b/arch/arm/mach-omap2/board-rx51-video.c
@@ -15,7 +15,7 @@
#include <linux/spi/spi.h>
#include <linux/mm.h>
#include <asm/mach-types.h>
-#include <plat/display.h>
+#include <video/omapdss.h>
#include <plat/vram.h>
#include <plat/mcspi.h>
diff --git a/arch/arm/mach-omap2/board-zoom-display.c b/arch/arm/mach-omap2/board-zoom-display.c
index 37b84c2b850f..60e8645db59d 100644
--- a/arch/arm/mach-omap2/board-zoom-display.c
+++ b/arch/arm/mach-omap2/board-zoom-display.c
@@ -15,7 +15,7 @@
#include <linux/i2c/twl.h>
#include <linux/spi/spi.h>
#include <plat/mcspi.h>
-#include <plat/display.h>
+#include <video/omapdss.h>
#define LCD_PANEL_RESET_GPIO_PROD 96
#define LCD_PANEL_RESET_GPIO_PILOT 55
diff --git a/arch/arm/mach-omap2/display.c b/arch/arm/mach-omap2/display.c
index 256d23fb79ab..543fcb8b518c 100644
--- a/arch/arm/mach-omap2/display.c
+++ b/arch/arm/mach-omap2/display.c
@@ -22,7 +22,7 @@
#include <linux/clk.h>
#include <linux/err.h>
-#include <plat/display.h>
+#include <video/omapdss.h>
#include <plat/omap_hwmod.h>
#include <plat/omap_device.h>
@@ -56,37 +56,58 @@ static bool opt_clock_available(const char *clk_role)
return false;
}
+struct omap_dss_hwmod_data {
+ const char *oh_name;
+ const char *dev_name;
+ const int id;
+};
+
+static const struct omap_dss_hwmod_data omap2_dss_hwmod_data[] __initdata = {
+ { "dss_core", "omapdss_dss", -1 },
+ { "dss_dispc", "omapdss_dispc", -1 },
+ { "dss_rfbi", "omapdss_rfbi", -1 },
+ { "dss_venc", "omapdss_venc", -1 },
+};
+
+static const struct omap_dss_hwmod_data omap3_dss_hwmod_data[] __initdata = {
+ { "dss_core", "omapdss_dss", -1 },
+ { "dss_dispc", "omapdss_dispc", -1 },
+ { "dss_rfbi", "omapdss_rfbi", -1 },
+ { "dss_venc", "omapdss_venc", -1 },
+ { "dss_dsi1", "omapdss_dsi1", -1 },
+};
+
+static const struct omap_dss_hwmod_data omap4_dss_hwmod_data[] __initdata = {
+ { "dss_core", "omapdss_dss", -1 },
+ { "dss_dispc", "omapdss_dispc", -1 },
+ { "dss_rfbi", "omapdss_rfbi", -1 },
+ { "dss_venc", "omapdss_venc", -1 },
+ { "dss_dsi1", "omapdss_dsi1", -1 },
+ { "dss_dsi2", "omapdss_dsi2", -1 },
+ { "dss_hdmi", "omapdss_hdmi", -1 },
+};
+
int __init omap_display_init(struct omap_dss_board_info *board_data)
{
int r = 0;
struct omap_hwmod *oh;
struct omap_device *od;
- int i;
+ int i, oh_count;
struct omap_display_platform_data pdata;
-
- /*
- * omap: valid DSS hwmod names
- * omap2,3,4: dss_core, dss_dispc, dss_rfbi, dss_venc
- * omap3,4: dss_dsi1
- * omap4: dss_dsi2, dss_hdmi
- */
- char *oh_name[] = { "dss_core", "dss_dispc", "dss_rfbi", "dss_venc",
- "dss_dsi1", "dss_dsi2", "dss_hdmi" };
- char *dev_name[] = { "omapdss_dss", "omapdss_dispc", "omapdss_rfbi",
- "omapdss_venc", "omapdss_dsi1", "omapdss_dsi2",
- "omapdss_hdmi" };
- int oh_count;
+ const struct omap_dss_hwmod_data *curr_dss_hwmod;
memset(&pdata, 0, sizeof(pdata));
- if (cpu_is_omap24xx())
- oh_count = ARRAY_SIZE(oh_name) - 3;
- /* last 3 hwmod dev in oh_name are not available for omap2 */
- else if (cpu_is_omap44xx())
- oh_count = ARRAY_SIZE(oh_name);
- else
- oh_count = ARRAY_SIZE(oh_name) - 2;
- /* last 2 hwmod dev in oh_name are not available for omap3 */
+ if (cpu_is_omap24xx()) {
+ curr_dss_hwmod = omap2_dss_hwmod_data;
+ oh_count = ARRAY_SIZE(omap2_dss_hwmod_data);
+ } else if (cpu_is_omap34xx()) {
+ curr_dss_hwmod = omap3_dss_hwmod_data;
+ oh_count = ARRAY_SIZE(omap3_dss_hwmod_data);
+ } else {
+ curr_dss_hwmod = omap4_dss_hwmod_data;
+ oh_count = ARRAY_SIZE(omap4_dss_hwmod_data);
+ }
/* opt_clks are always associated with dss hwmod */
oh_core = omap_hwmod_lookup("dss_core");
@@ -100,19 +121,21 @@ int __init omap_display_init(struct omap_dss_board_info *board_data)
pdata.opt_clock_available = opt_clock_available;
for (i = 0; i < oh_count; i++) {
- oh = omap_hwmod_lookup(oh_name[i]);
+ oh = omap_hwmod_lookup(curr_dss_hwmod[i].oh_name);
if (!oh) {
- pr_err("Could not look up %s\n", oh_name[i]);
+ pr_err("Could not look up %s\n",
+ curr_dss_hwmod[i].oh_name);
return -ENODEV;
}
- od = omap_device_build(dev_name[i], -1, oh, &pdata,
+ od = omap_device_build(curr_dss_hwmod[i].dev_name,
+ curr_dss_hwmod[i].id, oh, &pdata,
sizeof(struct omap_display_platform_data),
omap_dss_latency,
ARRAY_SIZE(omap_dss_latency), 0);
if (WARN((IS_ERR(od)), "Could not build omap_device for %s\n",
- oh_name[i]))
+ curr_dss_hwmod[i].oh_name))
return -ENODEV;
}
omap_display_device.dev.platform_data = board_data;
diff --git a/arch/arm/mach-omap2/include/mach/board-zoom.h b/arch/arm/mach-omap2/include/mach/board-zoom.h
index d20bd9c1a106..775fdc3b000b 100644
--- a/arch/arm/mach-omap2/include/mach/board-zoom.h
+++ b/arch/arm/mach-omap2/include/mach/board-zoom.h
@@ -1,7 +1,7 @@
/*
* Defines for zoom boards
*/
-#include <plat/display.h>
+#include <video/omapdss.h>
#define ZOOM_NAND_CS 0
diff --git a/arch/arm/mach-shmobile/Makefile b/arch/arm/mach-shmobile/Makefile
index e2507f66f9d5..612b27000c3e 100644
--- a/arch/arm/mach-shmobile/Makefile
+++ b/arch/arm/mach-shmobile/Makefile
@@ -30,6 +30,11 @@ obj-$(CONFIG_ARCH_SH7377) += entry-intc.o
obj-$(CONFIG_ARCH_SH7372) += entry-intc.o
obj-$(CONFIG_ARCH_SH73A0) += entry-gic.o
+# PM objects
+obj-$(CONFIG_SUSPEND) += suspend.o
+obj-$(CONFIG_CPU_IDLE) += cpuidle.o
+obj-$(CONFIG_ARCH_SH7372) += pm-sh7372.o sleep-sh7372.o
+
# Board objects
obj-$(CONFIG_MACH_G3EVM) += board-g3evm.o
obj-$(CONFIG_MACH_G4EVM) += board-g4evm.o
diff --git a/arch/arm/mach-shmobile/board-ag5evm.c b/arch/arm/mach-shmobile/board-ag5evm.c
index 3e6f0aab460b..c95258c274c1 100644
--- a/arch/arm/mach-shmobile/board-ag5evm.c
+++ b/arch/arm/mach-shmobile/board-ag5evm.c
@@ -34,6 +34,8 @@
#include <linux/input/sh_keysc.h>
#include <linux/mmc/host.h>
#include <linux/mmc/sh_mmcif.h>
+#include <linux/mmc/sh_mobile_sdhi.h>
+#include <linux/mfd/tmio.h>
#include <linux/sh_clk.h>
#include <video/sh_mobile_lcdc.h>
#include <video/sh_mipi_dsi.h>
@@ -156,10 +158,19 @@ static struct resource sh_mmcif_resources[] = {
},
};
+static struct sh_mmcif_dma sh_mmcif_dma = {
+ .chan_priv_rx = {
+ .slave_id = SHDMA_SLAVE_MMCIF_RX,
+ },
+ .chan_priv_tx = {
+ .slave_id = SHDMA_SLAVE_MMCIF_TX,
+ },
+};
static struct sh_mmcif_plat_data sh_mmcif_platdata = {
.sup_pclk = 0,
.ocr = MMC_VDD_165_195,
.caps = MMC_CAP_8_BIT_DATA | MMC_CAP_NONREMOVABLE,
+ .dma = &sh_mmcif_dma,
};
static struct platform_device mmc_device = {
@@ -296,11 +307,13 @@ static struct platform_device lcdc0_device = {
/* MIPI-DSI */
static struct resource mipidsi0_resources[] = {
[0] = {
+ .name = "DSI0",
.start = 0xfeab0000,
.end = 0xfeab3fff,
.flags = IORESOURCE_MEM,
},
[1] = {
+ .name = "DSI0",
.start = 0xfeab4000,
.end = 0xfeab7fff,
.flags = IORESOURCE_MEM,
@@ -325,6 +338,89 @@ static struct platform_device mipidsi0_device = {
},
};
+static struct sh_mobile_sdhi_info sdhi0_info = {
+ .dma_slave_tx = SHDMA_SLAVE_SDHI0_TX,
+ .dma_slave_rx = SHDMA_SLAVE_SDHI0_RX,
+ .tmio_caps = MMC_CAP_SD_HIGHSPEED,
+ .tmio_ocr_mask = MMC_VDD_27_28 | MMC_VDD_28_29,
+};
+
+static struct resource sdhi0_resources[] = {
+ [0] = {
+ .name = "SDHI0",
+ .start = 0xee100000,
+ .end = 0xee1000ff,
+ .flags = IORESOURCE_MEM,
+ },
+ [1] = {
+ .start = gic_spi(83),
+ .flags = IORESOURCE_IRQ,
+ },
+ [2] = {
+ .start = gic_spi(84),
+ .flags = IORESOURCE_IRQ,
+ },
+ [3] = {
+ .start = gic_spi(85),
+ .flags = IORESOURCE_IRQ,
+ },
+};
+
+static struct platform_device sdhi0_device = {
+ .name = "sh_mobile_sdhi",
+ .id = 0,
+ .num_resources = ARRAY_SIZE(sdhi0_resources),
+ .resource = sdhi0_resources,
+ .dev = {
+ .platform_data = &sdhi0_info,
+ },
+};
+
+void ag5evm_sdhi1_set_pwr(struct platform_device *pdev, int state)
+{
+ gpio_set_value(GPIO_PORT114, state);
+}
+
+static struct sh_mobile_sdhi_info sh_sdhi1_platdata = {
+ .dma_slave_tx = SHDMA_SLAVE_SDHI1_TX,
+ .dma_slave_rx = SHDMA_SLAVE_SDHI1_RX,
+ .tmio_flags = TMIO_MMC_WRPROTECT_DISABLE,
+ .tmio_caps = MMC_CAP_NONREMOVABLE,
+ .tmio_ocr_mask = MMC_VDD_32_33 | MMC_VDD_33_34,
+ .set_pwr = ag5evm_sdhi1_set_pwr,
+};
+
+static struct resource sdhi1_resources[] = {
+ [0] = {
+ .name = "SDHI1",
+ .start = 0xee120000,
+ .end = 0xee1200ff,
+ .flags = IORESOURCE_MEM,
+ },
+ [1] = {
+ .start = gic_spi(87),
+ .flags = IORESOURCE_IRQ,
+ },
+ [2] = {
+ .start = gic_spi(88),
+ .flags = IORESOURCE_IRQ,
+ },
+ [3] = {
+ .start = gic_spi(89),
+ .flags = IORESOURCE_IRQ,
+ },
+};
+
+static struct platform_device sdhi1_device = {
+ .name = "sh_mobile_sdhi",
+ .id = 1,
+ .dev = {
+ .platform_data = &sh_sdhi1_platdata,
+ },
+ .num_resources = ARRAY_SIZE(sdhi1_resources),
+ .resource = sdhi1_resources,
+};
+
static struct platform_device *ag5evm_devices[] __initdata = {
&eth_device,
&keysc_device,
@@ -333,6 +429,8 @@ static struct platform_device *ag5evm_devices[] __initdata = {
&irda_device,
&lcdc0_device,
&mipidsi0_device,
+ &sdhi0_device,
+ &sdhi1_device,
};
static struct map_desc ag5evm_io_desc[] __initdata = {
@@ -454,6 +552,26 @@ static void __init ag5evm_init(void)
/* MIPI-DSI clock setup */
__raw_writel(0x2a809010, DSI0PHYCR);
+ /* enable SDHI0 on CN15 [SD I/F] */
+ gpio_request(GPIO_FN_SDHICD0, NULL);
+ gpio_request(GPIO_FN_SDHIWP0, NULL);
+ gpio_request(GPIO_FN_SDHICMD0, NULL);
+ gpio_request(GPIO_FN_SDHICLK0, NULL);
+ gpio_request(GPIO_FN_SDHID0_3, NULL);
+ gpio_request(GPIO_FN_SDHID0_2, NULL);
+ gpio_request(GPIO_FN_SDHID0_1, NULL);
+ gpio_request(GPIO_FN_SDHID0_0, NULL);
+
+ /* enable SDHI1 on CN4 [WLAN I/F] */
+ gpio_request(GPIO_FN_SDHICLK1, NULL);
+ gpio_request(GPIO_FN_SDHICMD1_PU, NULL);
+ gpio_request(GPIO_FN_SDHID1_3_PU, NULL);
+ gpio_request(GPIO_FN_SDHID1_2_PU, NULL);
+ gpio_request(GPIO_FN_SDHID1_1_PU, NULL);
+ gpio_request(GPIO_FN_SDHID1_0_PU, NULL);
+ gpio_request(GPIO_PORT114, "sdhi1_power");
+ gpio_direction_output(GPIO_PORT114, 0);
+
#ifdef CONFIG_CACHE_L2X0
/* Shared attribute override enable, 64K*8way */
l2x0_init(__io(0xf0100000), 0x00460000, 0xc2000fff);
diff --git a/arch/arm/mach-shmobile/board-ap4evb.c b/arch/arm/mach-shmobile/board-ap4evb.c
index 1e35fa976d64..08acb6ec8139 100644
--- a/arch/arm/mach-shmobile/board-ap4evb.c
+++ b/arch/arm/mach-shmobile/board-ap4evb.c
@@ -316,8 +316,16 @@ static struct resource sdhi0_resources[] = {
.flags = IORESOURCE_MEM,
},
[1] = {
- .start = evt2irq(0x0e00) /* SDHI0 */,
- .flags = IORESOURCE_IRQ,
+ .start = evt2irq(0x0e00) /* SDHI0_SDHI0I0 */,
+ .flags = IORESOURCE_IRQ,
+ },
+ [2] = {
+ .start = evt2irq(0x0e20) /* SDHI0_SDHI0I1 */,
+ .flags = IORESOURCE_IRQ,
+ },
+ [3] = {
+ .start = evt2irq(0x0e40) /* SDHI0_SDHI0I2 */,
+ .flags = IORESOURCE_IRQ,
},
};
@@ -349,8 +357,16 @@ static struct resource sdhi1_resources[] = {
.flags = IORESOURCE_MEM,
},
[1] = {
- .start = evt2irq(0x0e80),
- .flags = IORESOURCE_IRQ,
+ .start = evt2irq(0x0e80), /* SDHI1_SDHI1I0 */
+ .flags = IORESOURCE_IRQ,
+ },
+ [2] = {
+ .start = evt2irq(0x0ea0), /* SDHI1_SDHI1I1 */
+ .flags = IORESOURCE_IRQ,
+ },
+ [3] = {
+ .start = evt2irq(0x0ec0), /* SDHI1_SDHI1I2 */
+ .flags = IORESOURCE_IRQ,
},
};
@@ -980,11 +996,6 @@ static void __init hdmi_init_pm_clock(void)
goto out;
}
- ret = clk_enable(&sh7372_pllc2_clk);
- if (ret < 0) {
- pr_err("Cannot enable pllc2 clock\n");
- goto out;
- }
pr_debug("PLLC2 set frequency %lu\n", rate);
ret = clk_set_parent(hdmi_ick, &sh7372_pllc2_clk);
@@ -1343,6 +1354,7 @@ static void __init ap4evb_init(void)
hdmi_init_pm_clock();
fsi_init_pm_clock();
+ sh7372_pm_init();
}
static void __init ap4evb_timer_init(void)
diff --git a/arch/arm/mach-shmobile/board-g4evm.c b/arch/arm/mach-shmobile/board-g4evm.c
index c87a7b7c5832..8e3c5559f27f 100644
--- a/arch/arm/mach-shmobile/board-g4evm.c
+++ b/arch/arm/mach-shmobile/board-g4evm.c
@@ -205,7 +205,7 @@ static struct resource sdhi0_resources[] = {
[0] = {
.name = "SDHI0",
.start = 0xe6d50000,
- .end = 0xe6d50nff,
+ .end = 0xe6d500ff,
.flags = IORESOURCE_MEM,
},
[1] = {
diff --git a/arch/arm/mach-shmobile/board-mackerel.c b/arch/arm/mach-shmobile/board-mackerel.c
index 7da2ca24229d..448ddbe43335 100644
--- a/arch/arm/mach-shmobile/board-mackerel.c
+++ b/arch/arm/mach-shmobile/board-mackerel.c
@@ -43,6 +43,7 @@
#include <linux/sh_intc.h>
#include <linux/tca6416_keypad.h>
#include <linux/usb/r8a66597.h>
+#include <linux/usb/renesas_usbhs.h>
#include <video/sh_mobile_hdmi.h>
#include <video/sh_mobile_lcdc.h>
@@ -143,7 +144,30 @@
* open | external VBUS | Function
*
* *1
- * CN31 is used as Host in Linux.
+ * CN31 is used as
+ * CONFIG_USB_R8A66597_HCD Host
+ * CONFIG_USB_RENESAS_USBHS Function
+ *
+ * CAUTION
+ *
+ * renesas_usbhs driver can use external interrupt mode
+ * (which come from USB-PHY) or autonomy mode (it use own interrupt)
+ * for detecting connection/disconnection when Function.
+ * USB will be power OFF while it has been disconnecting
+ * if external interrupt mode, and it is always power ON if autonomy mode,
+ *
+ * mackerel can not use external interrupt (IRQ7-PORT167) mode on "USB0",
+ * because Touchscreen is using IRQ7-PORT40.
+ * It is impossible to use IRQ7 demux on this board.
+ *
+ * We can use external interrupt mode USB-Function on "USB1".
+ * USB1 can become Host by r8a66597, and become Function by renesas_usbhs.
+ * But don't select both drivers in same time.
+ * These uses same IRQ number for request_irq(), and aren't supporting
+ * IRQF_SHARD / IORESOURCE_IRQ_SHAREABLE.
+ *
+ * Actually these are old/new version of USB driver.
+ * This mean its register will be broken if it supports SHARD IRQ,
*/
/*
@@ -185,6 +209,7 @@
* FIXME !!
*
* gpio_no_direction
+ * gpio_pull_down
* are quick_hack.
*
* current gpio frame work doesn't have
@@ -196,6 +221,16 @@ static void __init gpio_no_direction(u32 addr)
__raw_writeb(0x00, addr);
}
+static void __init gpio_pull_down(u32 addr)
+{
+ u8 data = __raw_readb(addr);
+
+ data &= 0x0F;
+ data |= 0xA0;
+
+ __raw_writeb(data, addr);
+}
+
/* MTD */
static struct mtd_partition nor_flash_partitions[] = {
{
@@ -458,12 +493,6 @@ static void __init hdmi_init_pm_clock(void)
goto out;
}
- ret = clk_enable(&sh7372_pllc2_clk);
- if (ret < 0) {
- pr_err("Cannot enable pllc2 clock\n");
- goto out;
- }
-
pr_debug("PLLC2 set frequency %lu\n", rate);
ret = clk_set_parent(hdmi_ick, &sh7372_pllc2_clk);
@@ -515,6 +544,157 @@ static struct platform_device usb1_host_device = {
.resource = usb1_host_resources,
};
+/* USB1 (Function) */
+#define USB_PHY_MODE (1 << 4)
+#define USB_PHY_INT_EN ((1 << 3) | (1 << 2))
+#define USB_PHY_ON (1 << 1)
+#define USB_PHY_OFF (1 << 0)
+#define USB_PHY_INT_CLR (USB_PHY_ON | USB_PHY_OFF)
+
+struct usbhs_private {
+ unsigned int irq;
+ unsigned int usbphyaddr;
+ unsigned int usbcrcaddr;
+ struct renesas_usbhs_platform_info info;
+};
+
+#define usbhs_get_priv(pdev) \
+ container_of(renesas_usbhs_get_info(pdev), \
+ struct usbhs_private, info)
+
+#define usbhs_is_connected(priv) \
+ (!((1 << 7) & __raw_readw(priv->usbcrcaddr)))
+
+static int usbhs1_get_id(struct platform_device *pdev)
+{
+ return USBHS_GADGET;
+}
+
+static int usbhs1_get_vbus(struct platform_device *pdev)
+{
+ return usbhs_is_connected(usbhs_get_priv(pdev));
+}
+
+static irqreturn_t usbhs1_interrupt(int irq, void *data)
+{
+ struct platform_device *pdev = data;
+ struct usbhs_private *priv = usbhs_get_priv(pdev);
+
+ dev_dbg(&pdev->dev, "%s\n", __func__);
+
+ renesas_usbhs_call_notify_hotplug(pdev);
+
+ /* clear status */
+ __raw_writew(__raw_readw(priv->usbphyaddr) | USB_PHY_INT_CLR,
+ priv->usbphyaddr);
+
+ return IRQ_HANDLED;
+}
+
+static int usbhs1_hardware_init(struct platform_device *pdev)
+{
+ struct usbhs_private *priv = usbhs_get_priv(pdev);
+ int ret;
+
+ irq_set_irq_type(priv->irq, IRQ_TYPE_LEVEL_HIGH);
+
+ /* clear interrupt status */
+ __raw_writew(USB_PHY_MODE | USB_PHY_INT_CLR, priv->usbphyaddr);
+
+ ret = request_irq(priv->irq, usbhs1_interrupt, 0,
+ dev_name(&pdev->dev), pdev);
+ if (ret) {
+ dev_err(&pdev->dev, "request_irq err\n");
+ return ret;
+ }
+
+ /* enable USB phy interrupt */
+ __raw_writew(USB_PHY_MODE | USB_PHY_INT_EN, priv->usbphyaddr);
+
+ return 0;
+}
+
+static void usbhs1_hardware_exit(struct platform_device *pdev)
+{
+ struct usbhs_private *priv = usbhs_get_priv(pdev);
+
+ /* clear interrupt status */
+ __raw_writew(USB_PHY_MODE | USB_PHY_INT_CLR, priv->usbphyaddr);
+
+ free_irq(priv->irq, pdev);
+}
+
+static void usbhs1_phy_reset(struct platform_device *pdev)
+{
+ struct usbhs_private *priv = usbhs_get_priv(pdev);
+
+ /* init phy */
+ __raw_writew(0x8a0a, priv->usbcrcaddr);
+}
+
+static u32 usbhs1_pipe_cfg[] = {
+ USB_ENDPOINT_XFER_CONTROL,
+ USB_ENDPOINT_XFER_ISOC,
+ USB_ENDPOINT_XFER_ISOC,
+ USB_ENDPOINT_XFER_BULK,
+ USB_ENDPOINT_XFER_BULK,
+ USB_ENDPOINT_XFER_BULK,
+ USB_ENDPOINT_XFER_INT,
+ USB_ENDPOINT_XFER_INT,
+ USB_ENDPOINT_XFER_INT,
+ USB_ENDPOINT_XFER_BULK,
+ USB_ENDPOINT_XFER_BULK,
+ USB_ENDPOINT_XFER_BULK,
+ USB_ENDPOINT_XFER_BULK,
+ USB_ENDPOINT_XFER_BULK,
+ USB_ENDPOINT_XFER_BULK,
+ USB_ENDPOINT_XFER_BULK,
+};
+
+static struct usbhs_private usbhs1_private = {
+ .irq = evt2irq(0x0300), /* IRQ8 */
+ .usbphyaddr = 0xE60581E2, /* USBPHY1INTAP */
+ .usbcrcaddr = 0xE6058130, /* USBCR4 */
+ .info = {
+ .platform_callback = {
+ .hardware_init = usbhs1_hardware_init,
+ .hardware_exit = usbhs1_hardware_exit,
+ .phy_reset = usbhs1_phy_reset,
+ .get_id = usbhs1_get_id,
+ .get_vbus = usbhs1_get_vbus,
+ },
+ .driver_param = {
+ .buswait_bwait = 4,
+ .pipe_type = usbhs1_pipe_cfg,
+ .pipe_size = ARRAY_SIZE(usbhs1_pipe_cfg),
+ },
+ },
+};
+
+static struct resource usbhs1_resources[] = {
+ [0] = {
+ .name = "USBHS",
+ .start = 0xE68B0000,
+ .end = 0xE68B00E6 - 1,
+ .flags = IORESOURCE_MEM,
+ },
+ [1] = {
+ .start = evt2irq(0x1ce0) /* USB1_USB1I0 */,
+ .flags = IORESOURCE_IRQ,
+ },
+};
+
+static struct platform_device usbhs1_device = {
+ .name = "renesas_usbhs",
+ .id = 1,
+ .dev = {
+ .platform_data = &usbhs1_private.info,
+ },
+ .num_resources = ARRAY_SIZE(usbhs1_resources),
+ .resource = usbhs1_resources,
+};
+
+
/* LED */
static struct gpio_led mackerel_leds[] = {
{
@@ -690,7 +870,15 @@ static struct resource sdhi0_resources[] = {
.flags = IORESOURCE_MEM,
},
[1] = {
- .start = evt2irq(0x0e00) /* SDHI0 */,
+ .start = evt2irq(0x0e00) /* SDHI0_SDHI0I0 */,
+ .flags = IORESOURCE_IRQ,
+ },
+ [2] = {
+ .start = evt2irq(0x0e20) /* SDHI0_SDHI0I1 */,
+ .flags = IORESOURCE_IRQ,
+ },
+ [3] = {
+ .start = evt2irq(0x0e40) /* SDHI0_SDHI0I2 */,
.flags = IORESOURCE_IRQ,
},
};
@@ -705,7 +893,7 @@ static struct platform_device sdhi0_device = {
},
};
-#if !defined(CONFIG_MMC_SH_MMCIF)
+#if !defined(CONFIG_MMC_SH_MMCIF) && !defined(CONFIG_MMC_SH_MMCIF_MODULE)
/* SDHI1 */
static struct sh_mobile_sdhi_info sdhi1_info = {
.dma_slave_tx = SHDMA_SLAVE_SDHI1_TX,
@@ -725,7 +913,15 @@ static struct resource sdhi1_resources[] = {
.flags = IORESOURCE_MEM,
},
[1] = {
- .start = evt2irq(0x0e80),
+ .start = evt2irq(0x0e80), /* SDHI1_SDHI1I0 */
+ .flags = IORESOURCE_IRQ,
+ },
+ [2] = {
+ .start = evt2irq(0x0ea0), /* SDHI1_SDHI1I1 */
+ .flags = IORESOURCE_IRQ,
+ },
+ [3] = {
+ .start = evt2irq(0x0ec0), /* SDHI1_SDHI1I2 */
.flags = IORESOURCE_IRQ,
},
};
@@ -768,7 +964,15 @@ static struct resource sdhi2_resources[] = {
.flags = IORESOURCE_MEM,
},
[1] = {
- .start = evt2irq(0x1200),
+ .start = evt2irq(0x1200), /* SDHI2_SDHI2I0 */
+ .flags = IORESOURCE_IRQ,
+ },
+ [2] = {
+ .start = evt2irq(0x1220), /* SDHI2_SDHI2I1 */
+ .flags = IORESOURCE_IRQ,
+ },
+ [3] = {
+ .start = evt2irq(0x1240), /* SDHI2_SDHI2I2 */
.flags = IORESOURCE_IRQ,
},
};
@@ -803,6 +1007,15 @@ static struct resource sh_mmcif_resources[] = {
},
};
+static struct sh_mmcif_dma sh_mmcif_dma = {
+ .chan_priv_rx = {
+ .slave_id = SHDMA_SLAVE_MMCIF_RX,
+ },
+ .chan_priv_tx = {
+ .slave_id = SHDMA_SLAVE_MMCIF_TX,
+ },
+};
+
static struct sh_mmcif_plat_data sh_mmcif_plat = {
.sup_pclk = 0,
.ocr = MMC_VDD_165_195 | MMC_VDD_32_33 | MMC_VDD_33_34,
@@ -810,6 +1023,7 @@ static struct sh_mmcif_plat_data sh_mmcif_plat = {
MMC_CAP_8_BIT_DATA |
MMC_CAP_NEEDS_POLL,
.get_cd = slot_cn7_get_cd,
+ .dma = &sh_mmcif_dma,
};
static struct platform_device sh_mmcif_device = {
@@ -858,37 +1072,23 @@ static struct soc_camera_link camera_link = {
.priv = &camera_info,
};
-static void dummy_release(struct device *dev)
+static struct platform_device *camera_device;
+
+static void mackerel_camera_release(struct device *dev)
{
+ soc_camera_platform_release(&camera_device);
}
-static struct platform_device camera_device = {
- .name = "soc_camera_platform",
- .dev = {
- .platform_data = &camera_info,
- .release = dummy_release,
- },
-};
-
static int mackerel_camera_add(struct soc_camera_link *icl,
struct device *dev)
{
- if (icl != &camera_link)
- return -ENODEV;
-
- camera_info.dev = dev;
-
- return platform_device_register(&camera_device);
+ return soc_camera_platform_add(icl, dev, &camera_device, &camera_link,
+ mackerel_camera_release, 0);
}
static void mackerel_camera_del(struct soc_camera_link *icl)
{
- if (icl != &camera_link)
- return;
-
- platform_device_unregister(&camera_device);
- memset(&camera_device.dev.kobj, 0,
- sizeof(camera_device.dev.kobj));
+ soc_camera_platform_del(icl, camera_device, &camera_link);
}
static struct sh_mobile_ceu_info sh_mobile_ceu_info = {
@@ -935,12 +1135,13 @@ static struct platform_device *mackerel_devices[] __initdata = {
&smc911x_device,
&lcdc_device,
&usb1_host_device,
+ &usbhs1_device,
&leds_device,
&fsi_device,
&fsi_ak4643_device,
&fsi_hdmi_device,
&sdhi0_device,
-#if !defined(CONFIG_MMC_SH_MMCIF)
+#if !defined(CONFIG_MMC_SH_MMCIF) && !defined(CONFIG_MMC_SH_MMCIF_MODULE)
&sdhi1_device,
#endif
&sdhi2_device,
@@ -1030,6 +1231,7 @@ static void __init mackerel_map_io(void)
#define GPIO_PORT9CR 0xE6051009
#define GPIO_PORT10CR 0xE605100A
+#define GPIO_PORT168CR 0xE60520A8
#define SRCR4 0xe61580bc
#define USCCR1 0xE6058144
static void __init mackerel_init(void)
@@ -1088,6 +1290,7 @@ static void __init mackerel_init(void)
gpio_request(GPIO_FN_OVCN_1_114, NULL);
gpio_request(GPIO_FN_EXTLP_1, NULL);
gpio_request(GPIO_FN_OVCN2_1, NULL);
+ gpio_pull_down(GPIO_PORT168CR);
/* setup USB phy */
__raw_writew(0x8a0a, 0xE6058130); /* USBCR4 */
@@ -1140,7 +1343,7 @@ static void __init mackerel_init(void)
gpio_request(GPIO_FN_SDHID0_1, NULL);
gpio_request(GPIO_FN_SDHID0_0, NULL);
-#if !defined(CONFIG_MMC_SH_MMCIF)
+#if !defined(CONFIG_MMC_SH_MMCIF) && !defined(CONFIG_MMC_SH_MMCIF_MODULE)
/* enable SDHI1 */
gpio_request(GPIO_FN_SDHICMD1, NULL);
gpio_request(GPIO_FN_SDHICLK1, NULL);
@@ -1216,6 +1419,7 @@ static void __init mackerel_init(void)
platform_add_devices(mackerel_devices, ARRAY_SIZE(mackerel_devices));
hdmi_init_pm_clock();
+ sh7372_pm_init();
}
static void __init mackerel_timer_init(void)
diff --git a/arch/arm/mach-shmobile/clock-sh7372.c b/arch/arm/mach-shmobile/clock-sh7372.c
index e9731b5a73ed..d17eb66f4ac2 100644
--- a/arch/arm/mach-shmobile/clock-sh7372.c
+++ b/arch/arm/mach-shmobile/clock-sh7372.c
@@ -44,6 +44,11 @@
#define DSI1PCKCR 0xe6150098
#define PLLC01CR 0xe6150028
#define PLLC2CR 0xe615002c
+#define RMSTPCR0 0xe6150110
+#define RMSTPCR1 0xe6150114
+#define RMSTPCR2 0xe6150118
+#define RMSTPCR3 0xe615011c
+#define RMSTPCR4 0xe6150120
#define SMSTPCR0 0xe6150130
#define SMSTPCR1 0xe6150134
#define SMSTPCR2 0xe6150138
@@ -421,9 +426,6 @@ static unsigned long fsidiv_recalc(struct clk *clk)
value = __raw_readl(clk->mapping->base);
- if ((value & 0x3) != 0x3)
- return 0;
-
value >>= 16;
if (value < 2)
return 0;
@@ -504,7 +506,7 @@ static struct clk *late_main_clks[] = {
enum { MSTP001,
MSTP131, MSTP130,
MSTP129, MSTP128, MSTP127, MSTP126, MSTP125,
- MSTP118, MSTP117, MSTP116,
+ MSTP118, MSTP117, MSTP116, MSTP113,
MSTP106, MSTP101, MSTP100,
MSTP223,
MSTP207, MSTP206, MSTP204, MSTP203, MSTP202, MSTP201, MSTP200,
@@ -527,6 +529,7 @@ static struct clk mstp_clks[MSTP_NR] = {
[MSTP118] = MSTP(&div4_clks[DIV4_B], SMSTPCR1, 18, 0), /* DSITX */
[MSTP117] = MSTP(&div4_clks[DIV4_B], SMSTPCR1, 17, 0), /* LCDC1 */
[MSTP116] = MSTP(&div6_clks[DIV6_SUB], SMSTPCR1, 16, 0), /* IIC0 */
+ [MSTP113] = MSTP(&div6_clks[DIV6_SUB], SMSTPCR1, 13, 0), /* MERAM */
[MSTP106] = MSTP(&div4_clks[DIV4_B], SMSTPCR1, 6, 0), /* JPU */
[MSTP101] = MSTP(&div4_clks[DIV4_M1], SMSTPCR1, 1, 0), /* VPU */
[MSTP100] = MSTP(&div4_clks[DIV4_B], SMSTPCR1, 0, 0), /* LCDC0 */
@@ -617,6 +620,7 @@ static struct clk_lookup lookups[] = {
CLKDEV_DEV_ID("sh-mipi-dsi.0", &mstp_clks[MSTP118]), /* DSITX0 */
CLKDEV_DEV_ID("sh_mobile_lcdc_fb.1", &mstp_clks[MSTP117]), /* LCDC1 */
CLKDEV_DEV_ID("i2c-sh_mobile.0", &mstp_clks[MSTP116]), /* IIC0 */
+ CLKDEV_DEV_ID("sh_mobile_meram.0", &mstp_clks[MSTP113]), /* MERAM */
CLKDEV_DEV_ID("uio_pdrv_genirq.5", &mstp_clks[MSTP106]), /* JPU */
CLKDEV_DEV_ID("uio_pdrv_genirq.0", &mstp_clks[MSTP101]), /* VPU */
CLKDEV_DEV_ID("sh_mobile_lcdc_fb.0", &mstp_clks[MSTP100]), /* LCDC0 */
@@ -634,6 +638,7 @@ static struct clk_lookup lookups[] = {
CLKDEV_DEV_ID("i2c-sh_mobile.1", &mstp_clks[MSTP323]), /* IIC1 */
CLKDEV_DEV_ID("r8a66597_hcd.0", &mstp_clks[MSTP322]), /* USB0 */
CLKDEV_DEV_ID("r8a66597_udc.0", &mstp_clks[MSTP322]), /* USB0 */
+ CLKDEV_DEV_ID("renesas_usbhs.0", &mstp_clks[MSTP322]), /* USB0 */
CLKDEV_DEV_ID("sh_mobile_sdhi.0", &mstp_clks[MSTP314]), /* SDHI0 */
CLKDEV_DEV_ID("sh_mobile_sdhi.1", &mstp_clks[MSTP313]), /* SDHI1 */
CLKDEV_DEV_ID("sh_mmcif.0", &mstp_clks[MSTP312]), /* MMC */
@@ -644,6 +649,7 @@ static struct clk_lookup lookups[] = {
CLKDEV_DEV_ID("i2c-sh_mobile.4", &mstp_clks[MSTP410]), /* IIC4 */
CLKDEV_DEV_ID("r8a66597_hcd.1", &mstp_clks[MSTP406]), /* USB1 */
CLKDEV_DEV_ID("r8a66597_udc.1", &mstp_clks[MSTP406]), /* USB1 */
+ CLKDEV_DEV_ID("renesas_usbhs.1", &mstp_clks[MSTP406]), /* USB1 */
CLKDEV_DEV_ID("sh_keysc.0", &mstp_clks[MSTP403]), /* KEYSC */
CLKDEV_ICK_ID("ick", "sh-mobile-hdmi", &div6_reparent_clks[DIV6_HDMI]),
@@ -655,6 +661,13 @@ void __init sh7372_clock_init(void)
{
int k, ret = 0;
+ /* make sure MSTP bits on the RT/SH4AL-DSP side are off */
+ __raw_writel(0xe4ef8087, RMSTPCR0);
+ __raw_writel(0xffffffff, RMSTPCR1);
+ __raw_writel(0x37c7f7ff, RMSTPCR2);
+ __raw_writel(0xffffffff, RMSTPCR3);
+ __raw_writel(0xffe0fffd, RMSTPCR4);
+
for (k = 0; !ret && (k < ARRAY_SIZE(main_clks)); k++)
ret = clk_register(main_clks[k]);
diff --git a/arch/arm/mach-shmobile/clock-sh73a0.c b/arch/arm/mach-shmobile/clock-sh73a0.c
index 7e58904c1c8c..bcacb1e8cf85 100644
--- a/arch/arm/mach-shmobile/clock-sh73a0.c
+++ b/arch/arm/mach-shmobile/clock-sh73a0.c
@@ -266,7 +266,8 @@ enum { MSTP001,
MSTP129, MSTP128, MSTP127, MSTP126, MSTP125, MSTP118, MSTP116, MSTP100,
MSTP219,
MSTP207, MSTP206, MSTP204, MSTP203, MSTP202, MSTP201, MSTP200,
- MSTP331, MSTP329, MSTP325, MSTP323, MSTP312,
+ MSTP331, MSTP329, MSTP325, MSTP323, MSTP318,
+ MSTP314, MSTP313, MSTP312, MSTP311,
MSTP411, MSTP410, MSTP403,
MSTP_NR };
@@ -295,7 +296,11 @@ static struct clk mstp_clks[MSTP_NR] = {
[MSTP329] = MSTP(&r_clk, SMSTPCR3, 29, 0), /* CMT10 */
[MSTP325] = MSTP(&div6_clks[DIV6_SUB], SMSTPCR3, 25, 0), /* IrDA */
[MSTP323] = MSTP(&div4_clks[DIV4_HP], SMSTPCR3, 23, 0), /* IIC1 */
+ [MSTP318] = MSTP(&div4_clks[DIV4_HP], SMSTPCR3, 18, 0), /* SY-DMAC */
+ [MSTP314] = MSTP(&div6_clks[DIV6_SDHI0], SMSTPCR3, 14, 0), /* SDHI0 */
+ [MSTP313] = MSTP(&div6_clks[DIV6_SDHI1], SMSTPCR3, 13, 0), /* SDHI1 */
[MSTP312] = MSTP(&div4_clks[DIV4_HP], SMSTPCR3, 12, 0), /* MMCIF0 */
+ [MSTP311] = MSTP(&div6_clks[DIV6_SDHI2], SMSTPCR3, 11, 0), /* SDHI2 */
[MSTP411] = MSTP(&div4_clks[DIV4_HP], SMSTPCR4, 11, 0), /* IIC3 */
[MSTP410] = MSTP(&div4_clks[DIV4_HP], SMSTPCR4, 10, 0), /* IIC4 */
[MSTP403] = MSTP(&r_clk, SMSTPCR4, 3, 0), /* KEYSC */
@@ -313,6 +318,9 @@ static struct clk_lookup lookups[] = {
CLKDEV_CON_ID("vck1_clk", &div6_clks[DIV6_VCK1]),
CLKDEV_CON_ID("vck2_clk", &div6_clks[DIV6_VCK2]),
CLKDEV_CON_ID("vck3_clk", &div6_clks[DIV6_VCK3]),
+ CLKDEV_CON_ID("sdhi0_clk", &div6_clks[DIV6_SDHI0]),
+ CLKDEV_CON_ID("sdhi1_clk", &div6_clks[DIV6_SDHI1]),
+ CLKDEV_CON_ID("sdhi2_clk", &div6_clks[DIV6_SDHI2]),
CLKDEV_ICK_ID("dsit_clk", "sh-mipi-dsi.0", &div6_clks[DIV6_DSIT]),
CLKDEV_ICK_ID("dsit_clk", "sh-mipi-dsi.1", &div6_clks[DIV6_DSIT]),
CLKDEV_ICK_ID("dsi0p_clk", "sh-mipi-dsi.0", &div6_clks[DIV6_DSI0P]),
@@ -341,7 +349,11 @@ static struct clk_lookup lookups[] = {
CLKDEV_DEV_ID("sh_cmt.10", &mstp_clks[MSTP329]), /* CMT10 */
CLKDEV_DEV_ID("sh_irda.0", &mstp_clks[MSTP325]), /* IrDA */
CLKDEV_DEV_ID("i2c-sh_mobile.1", &mstp_clks[MSTP323]), /* I2C1 */
+ CLKDEV_DEV_ID("sh-dma-engine.0", &mstp_clks[MSTP318]), /* SY-DMAC */
+ CLKDEV_DEV_ID("sh_mobile_sdhi.0", &mstp_clks[MSTP314]), /* SDHI0 */
+ CLKDEV_DEV_ID("sh_mobile_sdhi.1", &mstp_clks[MSTP313]), /* SDHI1 */
CLKDEV_DEV_ID("sh_mmcif.0", &mstp_clks[MSTP312]), /* MMCIF0 */
+ CLKDEV_DEV_ID("sh_mobile_sdhi.2", &mstp_clks[MSTP311]), /* SDHI2 */
CLKDEV_DEV_ID("i2c-sh_mobile.3", &mstp_clks[MSTP411]), /* I2C3 */
CLKDEV_DEV_ID("i2c-sh_mobile.4", &mstp_clks[MSTP410]), /* I2C4 */
CLKDEV_DEV_ID("sh_keysc.0", &mstp_clks[MSTP403]), /* KEYSC */
@@ -351,6 +363,11 @@ void __init sh73a0_clock_init(void)
{
int k, ret = 0;
+ /* Set SDHI clocks to a known state */
+ __raw_writel(0x108, SD0CKCR);
+ __raw_writel(0x108, SD1CKCR);
+ __raw_writel(0x108, SD2CKCR);
+
/* detect main clock parent */
switch ((__raw_readl(CKSCR) >> 24) & 0x03) {
case 0:
diff --git a/arch/arm/mach-shmobile/cpuidle.c b/arch/arm/mach-shmobile/cpuidle.c
new file mode 100644
index 000000000000..2e44f11f592e
--- /dev/null
+++ b/arch/arm/mach-shmobile/cpuidle.c
@@ -0,0 +1,92 @@
+/*
+ * CPUIdle support code for SH-Mobile ARM
+ *
+ * Copyright (C) 2011 Magnus Damm
+ *
+ * This file is subject to the terms and conditions of the GNU General Public
+ * License. See the file "COPYING" in the main directory of this archive
+ * for more details.
+ */
+
+#include <linux/pm.h>
+#include <linux/cpuidle.h>
+#include <linux/suspend.h>
+#include <linux/module.h>
+#include <linux/err.h>
+#include <asm/system.h>
+#include <asm/io.h>
+
+static void shmobile_enter_wfi(void)
+{
+ cpu_do_idle();
+}
+
+void (*shmobile_cpuidle_modes[CPUIDLE_STATE_MAX])(void) = {
+ shmobile_enter_wfi, /* regular sleep mode */
+};
+
+static int shmobile_cpuidle_enter(struct cpuidle_device *dev,
+ struct cpuidle_state *state)
+{
+ ktime_t before, after;
+ int requested_state = state - &dev->states[0];
+
+ dev->last_state = &dev->states[requested_state];
+ before = ktime_get();
+
+ local_irq_disable();
+ local_fiq_disable();
+
+ shmobile_cpuidle_modes[requested_state]();
+
+ local_irq_enable();
+ local_fiq_enable();
+
+ after = ktime_get();
+ return ktime_to_ns(ktime_sub(after, before)) >> 10;
+}
+
+static struct cpuidle_device shmobile_cpuidle_dev;
+static struct cpuidle_driver shmobile_cpuidle_driver = {
+ .name = "shmobile_cpuidle",
+ .owner = THIS_MODULE,
+};
+
+void (*shmobile_cpuidle_setup)(struct cpuidle_device *dev);
+
+static int shmobile_cpuidle_init(void)
+{
+ struct cpuidle_device *dev = &shmobile_cpuidle_dev;
+ struct cpuidle_state *state;
+ int i;
+
+ cpuidle_register_driver(&shmobile_cpuidle_driver);
+
+ for (i = 0; i < CPUIDLE_STATE_MAX; i++) {
+ dev->states[i].name[0] = '\0';
+ dev->states[i].desc[0] = '\0';
+ dev->states[i].enter = shmobile_cpuidle_enter;
+ }
+
+ i = CPUIDLE_DRIVER_STATE_START;
+
+ state = &dev->states[i++];
+ snprintf(state->name, CPUIDLE_NAME_LEN, "C1");
+ strncpy(state->desc, "WFI", CPUIDLE_DESC_LEN);
+ state->exit_latency = 1;
+ state->target_residency = 1 * 2;
+ state->power_usage = 3;
+ state->flags = 0;
+ state->flags |= CPUIDLE_FLAG_TIME_VALID;
+
+ dev->safe_state = state;
+ dev->state_count = i;
+
+ if (shmobile_cpuidle_setup)
+ shmobile_cpuidle_setup(dev);
+
+ cpuidle_register_device(dev);
+
+ return 0;
+}
+late_initcall(shmobile_cpuidle_init);
diff --git a/arch/arm/mach-shmobile/headsmp.S b/arch/arm/mach-shmobile/headsmp.S
index d4cec6b4c7d9..26079d933d91 100644
--- a/arch/arm/mach-shmobile/headsmp.S
+++ b/arch/arm/mach-shmobile/headsmp.S
@@ -24,4 +24,4 @@
.align 12
ENTRY(shmobile_secondary_vector)
ldr pc, 1f
-1: .long secondary_startup - PAGE_OFFSET + PHYS_OFFSET
+1: .long secondary_startup - PAGE_OFFSET + PLAT_PHYS_OFFSET
diff --git a/arch/arm/mach-shmobile/include/mach/common.h b/arch/arm/mach-shmobile/include/mach/common.h
index 013ac0ee8256..06aecb31d9c7 100644
--- a/arch/arm/mach-shmobile/include/mach/common.h
+++ b/arch/arm/mach-shmobile/include/mach/common.h
@@ -8,6 +8,10 @@ struct clk;
extern int clk_init(void);
extern void shmobile_handle_irq_intc(struct pt_regs *);
extern void shmobile_handle_irq_gic(struct pt_regs *);
+extern struct platform_suspend_ops shmobile_suspend_ops;
+struct cpuidle_device;
+extern void (*shmobile_cpuidle_modes[])(void);
+extern void (*shmobile_cpuidle_setup)(struct cpuidle_device *dev);
extern void sh7367_init_irq(void);
extern void sh7367_add_early_devices(void);
@@ -30,6 +34,9 @@ extern void sh7372_add_early_devices(void);
extern void sh7372_add_standard_devices(void);
extern void sh7372_clock_init(void);
extern void sh7372_pinmux_init(void);
+extern void sh7372_pm_init(void);
+extern void sh7372_cpu_suspend(void);
+extern void sh7372_cpu_resume(void);
extern struct clk sh7372_extal1_clk;
extern struct clk sh7372_extal2_clk;
diff --git a/arch/arm/mach-shmobile/include/mach/head-ap4evb.txt b/arch/arm/mach-shmobile/include/mach/head-ap4evb.txt
index 3029aba38688..9f134dfeffdc 100644
--- a/arch/arm/mach-shmobile/include/mach/head-ap4evb.txt
+++ b/arch/arm/mach-shmobile/include/mach/head-ap4evb.txt
@@ -87,8 +87,7 @@ WAIT 1, 0xFE40009C
ED 0xFE400354, 0x01AD8002
LIST "SCIF0 - Serial port for earlyprintk"
-EB 0xE6053098, 0x11
EB 0xE6053098, 0xe1
EW 0xE6C40000, 0x0000
EB 0xE6C40004, 0x19
-EW 0xE6C40008, 0x3000
+EW 0xE6C40008, 0x0030
diff --git a/arch/arm/mach-shmobile/include/mach/head-mackerel.txt b/arch/arm/mach-shmobile/include/mach/head-mackerel.txt
index 3029aba38688..9f134dfeffdc 100644
--- a/arch/arm/mach-shmobile/include/mach/head-mackerel.txt
+++ b/arch/arm/mach-shmobile/include/mach/head-mackerel.txt
@@ -87,8 +87,7 @@ WAIT 1, 0xFE40009C
ED 0xFE400354, 0x01AD8002
LIST "SCIF0 - Serial port for earlyprintk"
-EB 0xE6053098, 0x11
EB 0xE6053098, 0xe1
EW 0xE6C40000, 0x0000
EB 0xE6C40004, 0x19
-EW 0xE6C40008, 0x3000
+EW 0xE6C40008, 0x0030
diff --git a/arch/arm/mach-shmobile/include/mach/sh7372.h b/arch/arm/mach-shmobile/include/mach/sh7372.h
index 5736efcca60c..df20d7670172 100644
--- a/arch/arm/mach-shmobile/include/mach/sh7372.h
+++ b/arch/arm/mach-shmobile/include/mach/sh7372.h
@@ -435,6 +435,7 @@ enum {
/* DMA slave IDs */
enum {
+ SHDMA_SLAVE_INVALID,
SHDMA_SLAVE_SCIF0_TX,
SHDMA_SLAVE_SCIF0_RX,
SHDMA_SLAVE_SCIF1_TX,
diff --git a/arch/arm/mach-shmobile/include/mach/sh73a0.h b/arch/arm/mach-shmobile/include/mach/sh73a0.h
index ceb2cdc92bf9..216c3d695ef1 100644
--- a/arch/arm/mach-shmobile/include/mach/sh73a0.h
+++ b/arch/arm/mach-shmobile/include/mach/sh73a0.h
@@ -463,5 +463,35 @@ enum {
GPIO_FN_FSIAIBT_PU,
GPIO_FN_FSIAISLD_PU,
};
+/* DMA slave IDs */
+enum {
+ SHDMA_SLAVE_INVALID,
+ SHDMA_SLAVE_SCIF0_TX,
+ SHDMA_SLAVE_SCIF0_RX,
+ SHDMA_SLAVE_SCIF1_TX,
+ SHDMA_SLAVE_SCIF1_RX,
+ SHDMA_SLAVE_SCIF2_TX,
+ SHDMA_SLAVE_SCIF2_RX,
+ SHDMA_SLAVE_SCIF3_TX,
+ SHDMA_SLAVE_SCIF3_RX,
+ SHDMA_SLAVE_SCIF4_TX,
+ SHDMA_SLAVE_SCIF4_RX,
+ SHDMA_SLAVE_SCIF5_TX,
+ SHDMA_SLAVE_SCIF5_RX,
+ SHDMA_SLAVE_SCIF6_TX,
+ SHDMA_SLAVE_SCIF6_RX,
+ SHDMA_SLAVE_SCIF7_TX,
+ SHDMA_SLAVE_SCIF7_RX,
+ SHDMA_SLAVE_SCIF8_TX,
+ SHDMA_SLAVE_SCIF8_RX,
+ SHDMA_SLAVE_SDHI0_TX,
+ SHDMA_SLAVE_SDHI0_RX,
+ SHDMA_SLAVE_SDHI1_TX,
+ SHDMA_SLAVE_SDHI1_RX,
+ SHDMA_SLAVE_SDHI2_TX,
+ SHDMA_SLAVE_SDHI2_RX,
+ SHDMA_SLAVE_MMCIF_TX,
+ SHDMA_SLAVE_MMCIF_RX,
+};
#endif /* __ASM_SH73A0_H__ */
diff --git a/arch/arm/mach-shmobile/intc-sh7372.c b/arch/arm/mach-shmobile/intc-sh7372.c
index 7a4960f9c1e3..3b28743c77eb 100644
--- a/arch/arm/mach-shmobile/intc-sh7372.c
+++ b/arch/arm/mach-shmobile/intc-sh7372.c
@@ -27,8 +27,6 @@
enum {
UNUSED_INTCA = 0,
- ENABLED,
- DISABLED,
/* interrupt sources INTCA */
IRQ0A, IRQ1A, IRQ2A, IRQ3A, IRQ4A, IRQ5A, IRQ6A, IRQ7A,
@@ -49,14 +47,14 @@ enum {
MSIOF2, MSIOF1,
SCIFA4, SCIFA5, SCIFB,
FLCTL_FLSTEI, FLCTL_FLTENDI, FLCTL_FLTREQ0I, FLCTL_FLTREQ1I,
- SDHI0,
- SDHI1,
+ SDHI0_SDHI0I0, SDHI0_SDHI0I1, SDHI0_SDHI0I2, SDHI0_SDHI0I3,
+ SDHI1_SDHI1I0, SDHI1_SDHI1I1, SDHI1_SDHI1I2,
IRREM,
IRDA,
TPU0,
TTI20,
DDM,
- SDHI2,
+ SDHI2_SDHI2I0, SDHI2_SDHI2I1, SDHI2_SDHI2I2, SDHI2_SDHI2I3,
RWDT0,
DMAC1_1_DEI0, DMAC1_1_DEI1, DMAC1_1_DEI2, DMAC1_1_DEI3,
DMAC1_2_DEI4, DMAC1_2_DEI5, DMAC1_2_DADERR,
@@ -84,7 +82,7 @@ enum {
/* interrupt groups INTCA */
DMAC1_1, DMAC1_2, DMAC2_1, DMAC2_2, DMAC3_1, DMAC3_2, SHWYSTAT,
- AP_ARM1, AP_ARM2, SPU2, FLCTL, IIC1
+ AP_ARM1, AP_ARM2, SPU2, FLCTL, IIC1, SDHI0, SDHI1, SDHI2
};
static struct intc_vect intca_vectors[] __initdata = {
@@ -125,17 +123,17 @@ static struct intc_vect intca_vectors[] __initdata = {
INTC_VECT(SCIFB, 0x0d60),
INTC_VECT(FLCTL_FLSTEI, 0x0d80), INTC_VECT(FLCTL_FLTENDI, 0x0da0),
INTC_VECT(FLCTL_FLTREQ0I, 0x0dc0), INTC_VECT(FLCTL_FLTREQ1I, 0x0de0),
- INTC_VECT(SDHI0, 0x0e00), INTC_VECT(SDHI0, 0x0e20),
- INTC_VECT(SDHI0, 0x0e40), INTC_VECT(SDHI0, 0x0e60),
- INTC_VECT(SDHI1, 0x0e80), INTC_VECT(SDHI1, 0x0ea0),
- INTC_VECT(SDHI1, 0x0ec0),
+ INTC_VECT(SDHI0_SDHI0I0, 0x0e00), INTC_VECT(SDHI0_SDHI0I1, 0x0e20),
+ INTC_VECT(SDHI0_SDHI0I2, 0x0e40), INTC_VECT(SDHI0_SDHI0I3, 0x0e60),
+ INTC_VECT(SDHI1_SDHI1I0, 0x0e80), INTC_VECT(SDHI1_SDHI1I1, 0x0ea0),
+ INTC_VECT(SDHI1_SDHI1I2, 0x0ec0),
INTC_VECT(IRREM, 0x0f60),
INTC_VECT(IRDA, 0x0480),
INTC_VECT(TPU0, 0x04a0),
INTC_VECT(TTI20, 0x1100),
INTC_VECT(DDM, 0x1140),
- INTC_VECT(SDHI2, 0x1200), INTC_VECT(SDHI2, 0x1220),
- INTC_VECT(SDHI2, 0x1240), INTC_VECT(SDHI2, 0x1260),
+ INTC_VECT(SDHI2_SDHI2I0, 0x1200), INTC_VECT(SDHI2_SDHI2I1, 0x1220),
+ INTC_VECT(SDHI2_SDHI2I2, 0x1240), INTC_VECT(SDHI2_SDHI2I3, 0x1260),
INTC_VECT(RWDT0, 0x1280),
INTC_VECT(DMAC1_1_DEI0, 0x2000), INTC_VECT(DMAC1_1_DEI1, 0x2020),
INTC_VECT(DMAC1_1_DEI2, 0x2040), INTC_VECT(DMAC1_1_DEI3, 0x2060),
@@ -195,6 +193,12 @@ static struct intc_group intca_groups[] __initdata = {
INTC_GROUP(FLCTL, FLCTL_FLSTEI, FLCTL_FLTENDI,
FLCTL_FLTREQ0I, FLCTL_FLTREQ1I),
INTC_GROUP(IIC1, IIC1_ALI1, IIC1_TACKI1, IIC1_WAITI1, IIC1_DTEI1),
+ INTC_GROUP(SDHI0, SDHI0_SDHI0I0, SDHI0_SDHI0I1,
+ SDHI0_SDHI0I2, SDHI0_SDHI0I3),
+ INTC_GROUP(SDHI1, SDHI1_SDHI1I0, SDHI1_SDHI1I1,
+ SDHI1_SDHI1I2),
+ INTC_GROUP(SDHI2, SDHI2_SDHI2I0, SDHI2_SDHI2I1,
+ SDHI2_SDHI2I2, SDHI2_SDHI2I3),
INTC_GROUP(SHWYSTAT, SHWYSTAT_RT, SHWYSTAT_HS, SHWYSTAT_COM),
};
@@ -230,10 +234,10 @@ static struct intc_mask_reg intca_mask_registers[] __initdata = {
{ SCIFB, SCIFA5, SCIFA4, MSIOF1,
0, 0, MSIOF2, 0 } },
{ 0xe694009c, 0xe69400dc, 8, /* IMR7A / IMCR7A */
- { DISABLED, ENABLED, ENABLED, ENABLED,
+ { SDHI0_SDHI0I3, SDHI0_SDHI0I2, SDHI0_SDHI0I1, SDHI0_SDHI0I0,
FLCTL_FLTREQ1I, FLCTL_FLTREQ0I, FLCTL_FLTENDI, FLCTL_FLSTEI } },
{ 0xe69400a0, 0xe69400e0, 8, /* IMR8A / IMCR8A */
- { 0, ENABLED, ENABLED, ENABLED,
+ { 0, SDHI1_SDHI1I2, SDHI1_SDHI1I1, SDHI1_SDHI1I0,
TTI20, USBHSDMAC0_USHDMI, 0, 0 } },
{ 0xe69400a4, 0xe69400e4, 8, /* IMR9A / IMCR9A */
{ CMT1_CMT13, CMT1_CMT12, CMT1_CMT11, CMT1_CMT10,
@@ -248,7 +252,7 @@ static struct intc_mask_reg intca_mask_registers[] __initdata = {
{ 0, 0, TPU0, 0,
0, 0, 0, 0 } },
{ 0xe69400b4, 0xe69400f4, 8, /* IMR13A / IMCR13A */
- { DISABLED, DISABLED, ENABLED, ENABLED,
+ { SDHI2_SDHI2I3, SDHI2_SDHI2I2, SDHI2_SDHI2I1, SDHI2_SDHI2I0,
0, CMT3, 0, RWDT0 } },
{ 0xe6950080, 0xe69500c0, 8, /* IMR0A3 / IMCR0A3 */
{ SHWYSTAT_RT, SHWYSTAT_HS, SHWYSTAT_COM, 0,
@@ -354,14 +358,10 @@ static struct intc_mask_reg intca_ack_registers[] __initdata = {
{ IRQ24A, IRQ25A, IRQ26A, IRQ27A, IRQ28A, IRQ29A, IRQ30A, IRQ31A } },
};
-static struct intc_desc intca_desc __initdata = {
- .name = "sh7372-intca",
- .force_enable = ENABLED,
- .force_disable = DISABLED,
- .hw = INTC_HW_DESC(intca_vectors, intca_groups,
- intca_mask_registers, intca_prio_registers,
- intca_sense_registers, intca_ack_registers),
-};
+static DECLARE_INTC_DESC_ACK(intca_desc, "sh7372-intca",
+ intca_vectors, intca_groups,
+ intca_mask_registers, intca_prio_registers,
+ intca_sense_registers, intca_ack_registers);
enum {
UNUSED_INTCS = 0,
diff --git a/arch/arm/mach-shmobile/pm-sh7372.c b/arch/arm/mach-shmobile/pm-sh7372.c
new file mode 100644
index 000000000000..8e4aadf14c9f
--- /dev/null
+++ b/arch/arm/mach-shmobile/pm-sh7372.c
@@ -0,0 +1,108 @@
+/*
+ * sh7372 Power management support
+ *
+ * Copyright (C) 2011 Magnus Damm
+ *
+ * This file is subject to the terms and conditions of the GNU General Public
+ * License. See the file "COPYING" in the main directory of this archive
+ * for more details.
+ */
+
+#include <linux/pm.h>
+#include <linux/suspend.h>
+#include <linux/cpuidle.h>
+#include <linux/module.h>
+#include <linux/list.h>
+#include <linux/err.h>
+#include <linux/slab.h>
+#include <asm/system.h>
+#include <asm/io.h>
+#include <asm/tlbflush.h>
+#include <mach/common.h>
+
+#define SMFRAM 0xe6a70000
+#define SYSTBCR 0xe6150024
+#define SBAR 0xe6180020
+#define APARMBAREA 0xe6f10020
+
+static void sh7372_enter_core_standby(void)
+{
+ void __iomem *smfram = (void __iomem *)SMFRAM;
+
+ __raw_writel(0, APARMBAREA); /* translate 4k */
+ __raw_writel(__pa(sh7372_cpu_resume), SBAR); /* set reset vector */
+ __raw_writel(0x10, SYSTBCR); /* enable core standby */
+
+ __raw_writel(0, smfram + 0x3c); /* clear page table address */
+
+ sh7372_cpu_suspend();
+ cpu_init();
+
+ /* if page table address is non-NULL then we have been powered down */
+ if (__raw_readl(smfram + 0x3c)) {
+ __raw_writel(__raw_readl(smfram + 0x40),
+ __va(__raw_readl(smfram + 0x3c)));
+
+ flush_tlb_all();
+ set_cr(__raw_readl(smfram + 0x38));
+ }
+
+ __raw_writel(0, SYSTBCR); /* disable core standby */
+ __raw_writel(0, SBAR); /* disable reset vector translation */
+}
+
+#ifdef CONFIG_CPU_IDLE
+static void sh7372_cpuidle_setup(struct cpuidle_device *dev)
+{
+ struct cpuidle_state *state;
+ int i = dev->state_count;
+
+ state = &dev->states[i];
+ snprintf(state->name, CPUIDLE_NAME_LEN, "C2");
+ strncpy(state->desc, "Core Standby Mode", CPUIDLE_DESC_LEN);
+ state->exit_latency = 10;
+ state->target_residency = 20 + 10;
+ state->power_usage = 1; /* perhaps not */
+ state->flags = 0;
+ state->flags |= CPUIDLE_FLAG_TIME_VALID;
+ shmobile_cpuidle_modes[i] = sh7372_enter_core_standby;
+
+ dev->state_count = i + 1;
+}
+
+static void sh7372_cpuidle_init(void)
+{
+ shmobile_cpuidle_setup = sh7372_cpuidle_setup;
+}
+#else
+static void sh7372_cpuidle_init(void) {}
+#endif
+
+#ifdef CONFIG_SUSPEND
+static int sh7372_enter_suspend(suspend_state_t suspend_state)
+{
+ sh7372_enter_core_standby();
+ return 0;
+}
+
+static void sh7372_suspend_init(void)
+{
+ shmobile_suspend_ops.enter = sh7372_enter_suspend;
+}
+#else
+static void sh7372_suspend_init(void) {}
+#endif
+
+#define DBGREG1 0xe6100020
+#define DBGREG9 0xe6100040
+
+void __init sh7372_pm_init(void)
+{
+ /* enable DBG hardware block to kick SYSC */
+ __raw_writel(0x0000a500, DBGREG9);
+ __raw_writel(0x0000a501, DBGREG9);
+ __raw_writel(0x00000000, DBGREG1);
+
+ sh7372_suspend_init();
+ sh7372_cpuidle_init();
+}
diff --git a/arch/arm/mach-shmobile/setup-sh7367.c b/arch/arm/mach-shmobile/setup-sh7367.c
index ce28141662da..2c10190dbb55 100644
--- a/arch/arm/mach-shmobile/setup-sh7367.c
+++ b/arch/arm/mach-shmobile/setup-sh7367.c
@@ -22,6 +22,7 @@
#include <linux/interrupt.h>
#include <linux/irq.h>
#include <linux/platform_device.h>
+#include <linux/uio_driver.h>
#include <linux/delay.h>
#include <linux/input.h>
#include <linux/io.h>
@@ -195,6 +196,214 @@ static struct platform_device cmt10_device = {
.num_resources = ARRAY_SIZE(cmt10_resources),
};
+/* VPU */
+static struct uio_info vpu_platform_data = {
+ .name = "VPU5",
+ .version = "0",
+ .irq = intcs_evt2irq(0x980),
+};
+
+static struct resource vpu_resources[] = {
+ [0] = {
+ .name = "VPU",
+ .start = 0xfe900000,
+ .end = 0xfe902807,
+ .flags = IORESOURCE_MEM,
+ },
+};
+
+static struct platform_device vpu_device = {
+ .name = "uio_pdrv_genirq",
+ .id = 0,
+ .dev = {
+ .platform_data = &vpu_platform_data,
+ },
+ .resource = vpu_resources,
+ .num_resources = ARRAY_SIZE(vpu_resources),
+};
+
+/* VEU0 */
+static struct uio_info veu0_platform_data = {
+ .name = "VEU0",
+ .version = "0",
+ .irq = intcs_evt2irq(0x700),
+};
+
+static struct resource veu0_resources[] = {
+ [0] = {
+ .name = "VEU0",
+ .start = 0xfe920000,
+ .end = 0xfe9200b7,
+ .flags = IORESOURCE_MEM,
+ },
+};
+
+static struct platform_device veu0_device = {
+ .name = "uio_pdrv_genirq",
+ .id = 1,
+ .dev = {
+ .platform_data = &veu0_platform_data,
+ },
+ .resource = veu0_resources,
+ .num_resources = ARRAY_SIZE(veu0_resources),
+};
+
+/* VEU1 */
+static struct uio_info veu1_platform_data = {
+ .name = "VEU1",
+ .version = "0",
+ .irq = intcs_evt2irq(0x720),
+};
+
+static struct resource veu1_resources[] = {
+ [0] = {
+ .name = "VEU1",
+ .start = 0xfe924000,
+ .end = 0xfe9240b7,
+ .flags = IORESOURCE_MEM,
+ },
+};
+
+static struct platform_device veu1_device = {
+ .name = "uio_pdrv_genirq",
+ .id = 2,
+ .dev = {
+ .platform_data = &veu1_platform_data,
+ },
+ .resource = veu1_resources,
+ .num_resources = ARRAY_SIZE(veu1_resources),
+};
+
+/* VEU2 */
+static struct uio_info veu2_platform_data = {
+ .name = "VEU2",
+ .version = "0",
+ .irq = intcs_evt2irq(0x740),
+};
+
+static struct resource veu2_resources[] = {
+ [0] = {
+ .name = "VEU2",
+ .start = 0xfe928000,
+ .end = 0xfe9280b7,
+ .flags = IORESOURCE_MEM,
+ },
+};
+
+static struct platform_device veu2_device = {
+ .name = "uio_pdrv_genirq",
+ .id = 3,
+ .dev = {
+ .platform_data = &veu2_platform_data,
+ },
+ .resource = veu2_resources,
+ .num_resources = ARRAY_SIZE(veu2_resources),
+};
+
+/* VEU3 */
+static struct uio_info veu3_platform_data = {
+ .name = "VEU3",
+ .version = "0",
+ .irq = intcs_evt2irq(0x760),
+};
+
+static struct resource veu3_resources[] = {
+ [0] = {
+ .name = "VEU3",
+ .start = 0xfe92c000,
+ .end = 0xfe92c0b7,
+ .flags = IORESOURCE_MEM,
+ },
+};
+
+static struct platform_device veu3_device = {
+ .name = "uio_pdrv_genirq",
+ .id = 4,
+ .dev = {
+ .platform_data = &veu3_platform_data,
+ },
+ .resource = veu3_resources,
+ .num_resources = ARRAY_SIZE(veu3_resources),
+};
+
+/* VEU2H */
+static struct uio_info veu2h_platform_data = {
+ .name = "VEU2H",
+ .version = "0",
+ .irq = intcs_evt2irq(0x520),
+};
+
+static struct resource veu2h_resources[] = {
+ [0] = {
+ .name = "VEU2H",
+ .start = 0xfe93c000,
+ .end = 0xfe93c27b,
+ .flags = IORESOURCE_MEM,
+ },
+};
+
+static struct platform_device veu2h_device = {
+ .name = "uio_pdrv_genirq",
+ .id = 5,
+ .dev = {
+ .platform_data = &veu2h_platform_data,
+ },
+ .resource = veu2h_resources,
+ .num_resources = ARRAY_SIZE(veu2h_resources),
+};
+
+/* JPU */
+static struct uio_info jpu_platform_data = {
+ .name = "JPU",
+ .version = "0",
+ .irq = intcs_evt2irq(0x560),
+};
+
+static struct resource jpu_resources[] = {
+ [0] = {
+ .name = "JPU",
+ .start = 0xfe980000,
+ .end = 0xfe9902d3,
+ .flags = IORESOURCE_MEM,
+ },
+};
+
+static struct platform_device jpu_device = {
+ .name = "uio_pdrv_genirq",
+ .id = 6,
+ .dev = {
+ .platform_data = &jpu_platform_data,
+ },
+ .resource = jpu_resources,
+ .num_resources = ARRAY_SIZE(jpu_resources),
+};
+
+/* SPU1 */
+static struct uio_info spu1_platform_data = {
+ .name = "SPU1",
+ .version = "0",
+ .irq = evt2irq(0xfc0),
+};
+
+static struct resource spu1_resources[] = {
+ [0] = {
+ .name = "SPU1",
+ .start = 0xfe300000,
+ .end = 0xfe3fffff,
+ .flags = IORESOURCE_MEM,
+ },
+};
+
+static struct platform_device spu1_device = {
+ .name = "uio_pdrv_genirq",
+ .id = 7,
+ .dev = {
+ .platform_data = &spu1_platform_data,
+ },
+ .resource = spu1_resources,
+ .num_resources = ARRAY_SIZE(spu1_resources),
+};
+
static struct platform_device *sh7367_early_devices[] __initdata = {
&scif0_device,
&scif1_device,
@@ -206,10 +415,24 @@ static struct platform_device *sh7367_early_devices[] __initdata = {
&cmt10_device,
};
+static struct platform_device *sh7367_devices[] __initdata = {
+ &vpu_device,
+ &veu0_device,
+ &veu1_device,
+ &veu2_device,
+ &veu3_device,
+ &veu2h_device,
+ &jpu_device,
+ &spu1_device,
+};
+
void __init sh7367_add_standard_devices(void)
{
platform_add_devices(sh7367_early_devices,
ARRAY_SIZE(sh7367_early_devices));
+
+ platform_add_devices(sh7367_devices,
+ ARRAY_SIZE(sh7367_devices));
}
#define SYMSTPCR2 0xe6158048
diff --git a/arch/arm/mach-shmobile/setup-sh7372.c b/arch/arm/mach-shmobile/setup-sh7372.c
index ff0494f3d00c..cd807eea69e2 100644
--- a/arch/arm/mach-shmobile/setup-sh7372.c
+++ b/arch/arm/mach-shmobile/setup-sh7372.c
@@ -22,6 +22,7 @@
#include <linux/interrupt.h>
#include <linux/irq.h>
#include <linux/platform_device.h>
+#include <linux/uio_driver.h>
#include <linux/delay.h>
#include <linux/input.h>
#include <linux/io.h>
@@ -601,6 +602,214 @@ static struct platform_device dma2_device = {
},
};
+/* VPU */
+static struct uio_info vpu_platform_data = {
+ .name = "VPU5HG",
+ .version = "0",
+ .irq = intcs_evt2irq(0x980),
+};
+
+static struct resource vpu_resources[] = {
+ [0] = {
+ .name = "VPU",
+ .start = 0xfe900000,
+ .end = 0xfe900157,
+ .flags = IORESOURCE_MEM,
+ },
+};
+
+static struct platform_device vpu_device = {
+ .name = "uio_pdrv_genirq",
+ .id = 0,
+ .dev = {
+ .platform_data = &vpu_platform_data,
+ },
+ .resource = vpu_resources,
+ .num_resources = ARRAY_SIZE(vpu_resources),
+};
+
+/* VEU0 */
+static struct uio_info veu0_platform_data = {
+ .name = "VEU0",
+ .version = "0",
+ .irq = intcs_evt2irq(0x700),
+};
+
+static struct resource veu0_resources[] = {
+ [0] = {
+ .name = "VEU0",
+ .start = 0xfe920000,
+ .end = 0xfe9200cb,
+ .flags = IORESOURCE_MEM,
+ },
+};
+
+static struct platform_device veu0_device = {
+ .name = "uio_pdrv_genirq",
+ .id = 1,
+ .dev = {
+ .platform_data = &veu0_platform_data,
+ },
+ .resource = veu0_resources,
+ .num_resources = ARRAY_SIZE(veu0_resources),
+};
+
+/* VEU1 */
+static struct uio_info veu1_platform_data = {
+ .name = "VEU1",
+ .version = "0",
+ .irq = intcs_evt2irq(0x720),
+};
+
+static struct resource veu1_resources[] = {
+ [0] = {
+ .name = "VEU1",
+ .start = 0xfe924000,
+ .end = 0xfe9240cb,
+ .flags = IORESOURCE_MEM,
+ },
+};
+
+static struct platform_device veu1_device = {
+ .name = "uio_pdrv_genirq",
+ .id = 2,
+ .dev = {
+ .platform_data = &veu1_platform_data,
+ },
+ .resource = veu1_resources,
+ .num_resources = ARRAY_SIZE(veu1_resources),
+};
+
+/* VEU2 */
+static struct uio_info veu2_platform_data = {
+ .name = "VEU2",
+ .version = "0",
+ .irq = intcs_evt2irq(0x740),
+};
+
+static struct resource veu2_resources[] = {
+ [0] = {
+ .name = "VEU2",
+ .start = 0xfe928000,
+ .end = 0xfe928307,
+ .flags = IORESOURCE_MEM,
+ },
+};
+
+static struct platform_device veu2_device = {
+ .name = "uio_pdrv_genirq",
+ .id = 3,
+ .dev = {
+ .platform_data = &veu2_platform_data,
+ },
+ .resource = veu2_resources,
+ .num_resources = ARRAY_SIZE(veu2_resources),
+};
+
+/* VEU3 */
+static struct uio_info veu3_platform_data = {
+ .name = "VEU3",
+ .version = "0",
+ .irq = intcs_evt2irq(0x760),
+};
+
+static struct resource veu3_resources[] = {
+ [0] = {
+ .name = "VEU3",
+ .start = 0xfe92c000,
+ .end = 0xfe92c307,
+ .flags = IORESOURCE_MEM,
+ },
+};
+
+static struct platform_device veu3_device = {
+ .name = "uio_pdrv_genirq",
+ .id = 4,
+ .dev = {
+ .platform_data = &veu3_platform_data,
+ },
+ .resource = veu3_resources,
+ .num_resources = ARRAY_SIZE(veu3_resources),
+};
+
+/* JPU */
+static struct uio_info jpu_platform_data = {
+ .name = "JPU",
+ .version = "0",
+ .irq = intcs_evt2irq(0x560),
+};
+
+static struct resource jpu_resources[] = {
+ [0] = {
+ .name = "JPU",
+ .start = 0xfe980000,
+ .end = 0xfe9902d3,
+ .flags = IORESOURCE_MEM,
+ },
+};
+
+static struct platform_device jpu_device = {
+ .name = "uio_pdrv_genirq",
+ .id = 5,
+ .dev = {
+ .platform_data = &jpu_platform_data,
+ },
+ .resource = jpu_resources,
+ .num_resources = ARRAY_SIZE(jpu_resources),
+};
+
+/* SPU2DSP0 */
+static struct uio_info spu0_platform_data = {
+ .name = "SPU2DSP0",
+ .version = "0",
+ .irq = evt2irq(0x1800),
+};
+
+static struct resource spu0_resources[] = {
+ [0] = {
+ .name = "SPU2DSP0",
+ .start = 0xfe200000,
+ .end = 0xfe2fffff,
+ .flags = IORESOURCE_MEM,
+ },
+};
+
+static struct platform_device spu0_device = {
+ .name = "uio_pdrv_genirq",
+ .id = 6,
+ .dev = {
+ .platform_data = &spu0_platform_data,
+ },
+ .resource = spu0_resources,
+ .num_resources = ARRAY_SIZE(spu0_resources),
+};
+
+/* SPU2DSP1 */
+static struct uio_info spu1_platform_data = {
+ .name = "SPU2DSP1",
+ .version = "0",
+ .irq = evt2irq(0x1820),
+};
+
+static struct resource spu1_resources[] = {
+ [0] = {
+ .name = "SPU2DSP1",
+ .start = 0xfe300000,
+ .end = 0xfe3fffff,
+ .flags = IORESOURCE_MEM,
+ },
+};
+
+static struct platform_device spu1_device = {
+ .name = "uio_pdrv_genirq",
+ .id = 7,
+ .dev = {
+ .platform_data = &spu1_platform_data,
+ },
+ .resource = spu1_resources,
+ .num_resources = ARRAY_SIZE(spu1_resources),
+};
+
static struct platform_device *sh7372_early_devices[] __initdata = {
&scif0_device,
&scif1_device,
@@ -620,6 +829,14 @@ static struct platform_device *sh7372_late_devices[] __initdata = {
&dma0_device,
&dma1_device,
&dma2_device,
+ &vpu_device,
+ &veu0_device,
+ &veu1_device,
+ &veu2_device,
+ &veu3_device,
+ &jpu_device,
+ &spu0_device,
+ &spu1_device,
};
void __init sh7372_add_standard_devices(void)
diff --git a/arch/arm/mach-shmobile/setup-sh7377.c b/arch/arm/mach-shmobile/setup-sh7377.c
index 8099b0b8a934..bb405b8e459b 100644
--- a/arch/arm/mach-shmobile/setup-sh7377.c
+++ b/arch/arm/mach-shmobile/setup-sh7377.c
@@ -22,6 +22,7 @@
#include <linux/interrupt.h>
#include <linux/irq.h>
#include <linux/platform_device.h>
+#include <linux/uio_driver.h>
#include <linux/delay.h>
#include <linux/input.h>
#include <linux/io.h>
@@ -38,7 +39,7 @@ static struct plat_sci_port scif0_platform_data = {
.flags = UPF_BOOT_AUTOCONF,
.scscr = SCSCR_RE | SCSCR_TE,
.scbrr_algo_id = SCBRR_ALGO_4,
- .type = PORT_SCIF,
+ .type = PORT_SCIFA,
.irqs = { evt2irq(0xc00), evt2irq(0xc00),
evt2irq(0xc00), evt2irq(0xc00) },
};
@@ -57,7 +58,7 @@ static struct plat_sci_port scif1_platform_data = {
.flags = UPF_BOOT_AUTOCONF,
.scscr = SCSCR_RE | SCSCR_TE,
.scbrr_algo_id = SCBRR_ALGO_4,
- .type = PORT_SCIF,
+ .type = PORT_SCIFA,
.irqs = { evt2irq(0xc20), evt2irq(0xc20),
evt2irq(0xc20), evt2irq(0xc20) },
};
@@ -76,7 +77,7 @@ static struct plat_sci_port scif2_platform_data = {
.flags = UPF_BOOT_AUTOCONF,
.scscr = SCSCR_RE | SCSCR_TE,
.scbrr_algo_id = SCBRR_ALGO_4,
- .type = PORT_SCIF,
+ .type = PORT_SCIFA,
.irqs = { evt2irq(0xc40), evt2irq(0xc40),
evt2irq(0xc40), evt2irq(0xc40) },
};
@@ -95,7 +96,7 @@ static struct plat_sci_port scif3_platform_data = {
.flags = UPF_BOOT_AUTOCONF,
.scscr = SCSCR_RE | SCSCR_TE,
.scbrr_algo_id = SCBRR_ALGO_4,
- .type = PORT_SCIF,
+ .type = PORT_SCIFA,
.irqs = { evt2irq(0xc60), evt2irq(0xc60),
evt2irq(0xc60), evt2irq(0xc60) },
};
@@ -114,7 +115,7 @@ static struct plat_sci_port scif4_platform_data = {
.flags = UPF_BOOT_AUTOCONF,
.scscr = SCSCR_RE | SCSCR_TE,
.scbrr_algo_id = SCBRR_ALGO_4,
- .type = PORT_SCIF,
+ .type = PORT_SCIFA,
.irqs = { evt2irq(0xd20), evt2irq(0xd20),
evt2irq(0xd20), evt2irq(0xd20) },
};
@@ -133,7 +134,7 @@ static struct plat_sci_port scif5_platform_data = {
.flags = UPF_BOOT_AUTOCONF,
.scscr = SCSCR_RE | SCSCR_TE,
.scbrr_algo_id = SCBRR_ALGO_4,
- .type = PORT_SCIF,
+ .type = PORT_SCIFA,
.irqs = { evt2irq(0xd40), evt2irq(0xd40),
evt2irq(0xd40), evt2irq(0xd40) },
};
@@ -152,7 +153,7 @@ static struct plat_sci_port scif6_platform_data = {
.flags = UPF_BOOT_AUTOCONF,
.scscr = SCSCR_RE | SCSCR_TE,
.scbrr_algo_id = SCBRR_ALGO_4,
- .type = PORT_SCIF,
+ .type = PORT_SCIFA,
.irqs = { intcs_evt2irq(0x1a80), intcs_evt2irq(0x1a80),
intcs_evt2irq(0x1a80), intcs_evt2irq(0x1a80) },
};
@@ -171,7 +172,7 @@ static struct plat_sci_port scif7_platform_data = {
.flags = UPF_BOOT_AUTOCONF,
.scscr = SCSCR_RE | SCSCR_TE,
.scbrr_algo_id = SCBRR_ALGO_4,
- .type = PORT_SCIF,
+ .type = PORT_SCIFB,
.irqs = { evt2irq(0xd60), evt2irq(0xd60),
evt2irq(0xd60), evt2irq(0xd60) },
};
@@ -215,6 +216,214 @@ static struct platform_device cmt10_device = {
.num_resources = ARRAY_SIZE(cmt10_resources),
};
+/* VPU */
+static struct uio_info vpu_platform_data = {
+ .name = "VPU5HG",
+ .version = "0",
+ .irq = intcs_evt2irq(0x980),
+};
+
+static struct resource vpu_resources[] = {
+ [0] = {
+ .name = "VPU",
+ .start = 0xfe900000,
+ .end = 0xfe900157,
+ .flags = IORESOURCE_MEM,
+ },
+};
+
+static struct platform_device vpu_device = {
+ .name = "uio_pdrv_genirq",
+ .id = 0,
+ .dev = {
+ .platform_data = &vpu_platform_data,
+ },
+ .resource = vpu_resources,
+ .num_resources = ARRAY_SIZE(vpu_resources),
+};
+
+/* VEU0 */
+static struct uio_info veu0_platform_data = {
+ .name = "VEU0",
+ .version = "0",
+ .irq = intcs_evt2irq(0x700),
+};
+
+static struct resource veu0_resources[] = {
+ [0] = {
+ .name = "VEU0",
+ .start = 0xfe920000,
+ .end = 0xfe9200cb,
+ .flags = IORESOURCE_MEM,
+ },
+};
+
+static struct platform_device veu0_device = {
+ .name = "uio_pdrv_genirq",
+ .id = 1,
+ .dev = {
+ .platform_data = &veu0_platform_data,
+ },
+ .resource = veu0_resources,
+ .num_resources = ARRAY_SIZE(veu0_resources),
+};
+
+/* VEU1 */
+static struct uio_info veu1_platform_data = {
+ .name = "VEU1",
+ .version = "0",
+ .irq = intcs_evt2irq(0x720),
+};
+
+static struct resource veu1_resources[] = {
+ [0] = {
+ .name = "VEU1",
+ .start = 0xfe924000,
+ .end = 0xfe9240cb,
+ .flags = IORESOURCE_MEM,
+ },
+};
+
+static struct platform_device veu1_device = {
+ .name = "uio_pdrv_genirq",
+ .id = 2,
+ .dev = {
+ .platform_data = &veu1_platform_data,
+ },
+ .resource = veu1_resources,
+ .num_resources = ARRAY_SIZE(veu1_resources),
+};
+
+/* VEU2 */
+static struct uio_info veu2_platform_data = {
+ .name = "VEU2",
+ .version = "0",
+ .irq = intcs_evt2irq(0x740),
+};
+
+static struct resource veu2_resources[] = {
+ [0] = {
+ .name = "VEU2",
+ .start = 0xfe928000,
+ .end = 0xfe928307,
+ .flags = IORESOURCE_MEM,
+ },
+};
+
+static struct platform_device veu2_device = {
+ .name = "uio_pdrv_genirq",
+ .id = 3,
+ .dev = {
+ .platform_data = &veu2_platform_data,
+ },
+ .resource = veu2_resources,
+ .num_resources = ARRAY_SIZE(veu2_resources),
+};
+
+/* VEU3 */
+static struct uio_info veu3_platform_data = {
+ .name = "VEU3",
+ .version = "0",
+ .irq = intcs_evt2irq(0x760),
+};
+
+static struct resource veu3_resources[] = {
+ [0] = {
+ .name = "VEU3",
+ .start = 0xfe92c000,
+ .end = 0xfe92c307,
+ .flags = IORESOURCE_MEM,
+ },
+};
+
+static struct platform_device veu3_device = {
+ .name = "uio_pdrv_genirq",
+ .id = 4,
+ .dev = {
+ .platform_data = &veu3_platform_data,
+ },
+ .resource = veu3_resources,
+ .num_resources = ARRAY_SIZE(veu3_resources),
+};
+
+/* JPU */
+static struct uio_info jpu_platform_data = {
+ .name = "JPU",
+ .version = "0",
+ .irq = intcs_evt2irq(0x560),
+};
+
+static struct resource jpu_resources[] = {
+ [0] = {
+ .name = "JPU",
+ .start = 0xfe980000,
+ .end = 0xfe9902d3,
+ .flags = IORESOURCE_MEM,
+ },
+};
+
+static struct platform_device jpu_device = {
+ .name = "uio_pdrv_genirq",
+ .id = 5,
+ .dev = {
+ .platform_data = &jpu_platform_data,
+ },
+ .resource = jpu_resources,
+ .num_resources = ARRAY_SIZE(jpu_resources),
+};
+
+/* SPU2DSP0 */
+static struct uio_info spu0_platform_data = {
+ .name = "SPU2DSP0",
+ .version = "0",
+ .irq = evt2irq(0x1800),
+};
+
+static struct resource spu0_resources[] = {
+ [0] = {
+ .name = "SPU2DSP0",
+ .start = 0xfe200000,
+ .end = 0xfe2fffff,
+ .flags = IORESOURCE_MEM,
+ },
+};
+
+static struct platform_device spu0_device = {
+ .name = "uio_pdrv_genirq",
+ .id = 6,
+ .dev = {
+ .platform_data = &spu0_platform_data,
+ },
+ .resource = spu0_resources,
+ .num_resources = ARRAY_SIZE(spu0_resources),
+};
+
+/* SPU2DSP1 */
+static struct uio_info spu1_platform_data = {
+ .name = "SPU2DSP1",
+ .version = "0",
+ .irq = evt2irq(0x1820),
+};
+
+static struct resource spu1_resources[] = {
+ [0] = {
+ .name = "SPU2DSP1",
+ .start = 0xfe300000,
+ .end = 0xfe3fffff,
+ .flags = IORESOURCE_MEM,
+ },
+};
+
+static struct platform_device spu1_device = {
+ .name = "uio_pdrv_genirq",
+ .id = 7,
+ .dev = {
+ .platform_data = &spu1_platform_data,
+ },
+ .resource = spu1_resources,
+ .num_resources = ARRAY_SIZE(spu1_resources),
+};
+
static struct platform_device *sh7377_early_devices[] __initdata = {
&scif0_device,
&scif1_device,
@@ -227,10 +436,24 @@ static struct platform_device *sh7377_early_devices[] __initdata = {
&cmt10_device,
};
+static struct platform_device *sh7377_devices[] __initdata = {
+ &vpu_device,
+ &veu0_device,
+ &veu1_device,
+ &veu2_device,
+ &veu3_device,
+ &jpu_device,
+ &spu0_device,
+ &spu1_device,
+};
+
void __init sh7377_add_standard_devices(void)
{
platform_add_devices(sh7377_early_devices,
ARRAY_SIZE(sh7377_early_devices));
+
+ platform_add_devices(sh7377_devices,
+ ARRAY_SIZE(sh7377_devices));
}
#define SMSTPCR3 0xe615013c
diff --git a/arch/arm/mach-shmobile/setup-sh73a0.c b/arch/arm/mach-shmobile/setup-sh73a0.c
index 685c40a2f5e6..e46821c0a62e 100644
--- a/arch/arm/mach-shmobile/setup-sh73a0.c
+++ b/arch/arm/mach-shmobile/setup-sh73a0.c
@@ -27,9 +27,11 @@
#include <linux/input.h>
#include <linux/io.h>
#include <linux/serial_sci.h>
+#include <linux/sh_dma.h>
#include <linux/sh_intc.h>
#include <linux/sh_timer.h>
#include <mach/hardware.h>
+#include <mach/sh73a0.h>
#include <asm/mach-types.h>
#include <asm/mach/arch.h>
@@ -392,6 +394,242 @@ static struct platform_device i2c4_device = {
.num_resources = ARRAY_SIZE(i2c4_resources),
};
+/* Transmit sizes and respective CHCR register values */
+enum {
+ XMIT_SZ_8BIT = 0,
+ XMIT_SZ_16BIT = 1,
+ XMIT_SZ_32BIT = 2,
+ XMIT_SZ_64BIT = 7,
+ XMIT_SZ_128BIT = 3,
+ XMIT_SZ_256BIT = 4,
+ XMIT_SZ_512BIT = 5,
+};
+
+/* log2(size / 8) - used to calculate number of transfers */
+#define TS_SHIFT { \
+ [XMIT_SZ_8BIT] = 0, \
+ [XMIT_SZ_16BIT] = 1, \
+ [XMIT_SZ_32BIT] = 2, \
+ [XMIT_SZ_64BIT] = 3, \
+ [XMIT_SZ_128BIT] = 4, \
+ [XMIT_SZ_256BIT] = 5, \
+ [XMIT_SZ_512BIT] = 6, \
+}
+
+#define TS_INDEX2VAL(i) ((((i) & 3) << 3) | (((i) & 0xc) << (20 - 2)))
+#define CHCR_TX(xmit_sz) (DM_FIX | SM_INC | 0x800 | TS_INDEX2VAL((xmit_sz)))
+#define CHCR_RX(xmit_sz) (DM_INC | SM_FIX | 0x800 | TS_INDEX2VAL((xmit_sz)))
+
+static const struct sh_dmae_slave_config sh73a0_dmae_slaves[] = {
+ {
+ .slave_id = SHDMA_SLAVE_SCIF0_TX,
+ .addr = 0xe6c40020,
+ .chcr = CHCR_TX(XMIT_SZ_8BIT),
+ .mid_rid = 0x21,
+ }, {
+ .slave_id = SHDMA_SLAVE_SCIF0_RX,
+ .addr = 0xe6c40024,
+ .chcr = CHCR_RX(XMIT_SZ_8BIT),
+ .mid_rid = 0x22,
+ }, {
+ .slave_id = SHDMA_SLAVE_SCIF1_TX,
+ .addr = 0xe6c50020,
+ .chcr = CHCR_TX(XMIT_SZ_8BIT),
+ .mid_rid = 0x25,
+ }, {
+ .slave_id = SHDMA_SLAVE_SCIF1_RX,
+ .addr = 0xe6c50024,
+ .chcr = CHCR_RX(XMIT_SZ_8BIT),
+ .mid_rid = 0x26,
+ }, {
+ .slave_id = SHDMA_SLAVE_SCIF2_TX,
+ .addr = 0xe6c60020,
+ .chcr = CHCR_TX(XMIT_SZ_8BIT),
+ .mid_rid = 0x29,
+ }, {
+ .slave_id = SHDMA_SLAVE_SCIF2_RX,
+ .addr = 0xe6c60024,
+ .chcr = CHCR_RX(XMIT_SZ_8BIT),
+ .mid_rid = 0x2a,
+ }, {
+ .slave_id = SHDMA_SLAVE_SCIF3_TX,
+ .addr = 0xe6c70020,
+ .chcr = CHCR_TX(XMIT_SZ_8BIT),
+ .mid_rid = 0x2d,
+ }, {
+ .slave_id = SHDMA_SLAVE_SCIF3_RX,
+ .addr = 0xe6c70024,
+ .chcr = CHCR_RX(XMIT_SZ_8BIT),
+ .mid_rid = 0x2e,
+ }, {
+ .slave_id = SHDMA_SLAVE_SCIF4_TX,
+ .addr = 0xe6c80020,
+ .chcr = CHCR_TX(XMIT_SZ_8BIT),
+ .mid_rid = 0x39,
+ }, {
+ .slave_id = SHDMA_SLAVE_SCIF4_RX,
+ .addr = 0xe6c80024,
+ .chcr = CHCR_RX(XMIT_SZ_8BIT),
+ .mid_rid = 0x3a,
+ }, {
+ .slave_id = SHDMA_SLAVE_SCIF5_TX,
+ .addr = 0xe6cb0020,
+ .chcr = CHCR_TX(XMIT_SZ_8BIT),
+ .mid_rid = 0x35,
+ }, {
+ .slave_id = SHDMA_SLAVE_SCIF5_RX,
+ .addr = 0xe6cb0024,
+ .chcr = CHCR_RX(XMIT_SZ_8BIT),
+ .mid_rid = 0x36,
+ }, {
+ .slave_id = SHDMA_SLAVE_SCIF6_TX,
+ .addr = 0xe6cc0020,
+ .chcr = CHCR_TX(XMIT_SZ_8BIT),
+ .mid_rid = 0x1d,
+ }, {
+ .slave_id = SHDMA_SLAVE_SCIF6_RX,
+ .addr = 0xe6cc0024,
+ .chcr = CHCR_RX(XMIT_SZ_8BIT),
+ .mid_rid = 0x1e,
+ }, {
+ .slave_id = SHDMA_SLAVE_SCIF7_TX,
+ .addr = 0xe6cd0020,
+ .chcr = CHCR_TX(XMIT_SZ_8BIT),
+ .mid_rid = 0x19,
+ }, {
+ .slave_id = SHDMA_SLAVE_SCIF7_RX,
+ .addr = 0xe6cd0024,
+ .chcr = CHCR_RX(XMIT_SZ_8BIT),
+ .mid_rid = 0x1a,
+ }, {
+ .slave_id = SHDMA_SLAVE_SCIF8_TX,
+ .addr = 0xe6c30040,
+ .chcr = CHCR_TX(XMIT_SZ_8BIT),
+ .mid_rid = 0x3d,
+ }, {
+ .slave_id = SHDMA_SLAVE_SCIF8_RX,
+ .addr = 0xe6c30060,
+ .chcr = CHCR_RX(XMIT_SZ_8BIT),
+ .mid_rid = 0x3e,
+ }, {
+ .slave_id = SHDMA_SLAVE_SDHI0_TX,
+ .addr = 0xee100030,
+ .chcr = CHCR_TX(XMIT_SZ_16BIT),
+ .mid_rid = 0xc1,
+ }, {
+ .slave_id = SHDMA_SLAVE_SDHI0_RX,
+ .addr = 0xee100030,
+ .chcr = CHCR_RX(XMIT_SZ_16BIT),
+ .mid_rid = 0xc2,
+ }, {
+ .slave_id = SHDMA_SLAVE_SDHI1_TX,
+ .addr = 0xee120030,
+ .chcr = CHCR_TX(XMIT_SZ_16BIT),
+ .mid_rid = 0xc9,
+ }, {
+ .slave_id = SHDMA_SLAVE_SDHI1_RX,
+ .addr = 0xee120030,
+ .chcr = CHCR_RX(XMIT_SZ_16BIT),
+ .mid_rid = 0xca,
+ }, {
+ .slave_id = SHDMA_SLAVE_SDHI2_TX,
+ .addr = 0xee140030,
+ .chcr = CHCR_TX(XMIT_SZ_16BIT),
+ .mid_rid = 0xcd,
+ }, {
+ .slave_id = SHDMA_SLAVE_SDHI2_RX,
+ .addr = 0xee140030,
+ .chcr = CHCR_RX(XMIT_SZ_16BIT),
+ .mid_rid = 0xce,
+ }, {
+ .slave_id = SHDMA_SLAVE_MMCIF_TX,
+ .addr = 0xe6bd0034,
+ .chcr = CHCR_TX(XMIT_SZ_32BIT),
+ .mid_rid = 0xd1,
+ }, {
+ .slave_id = SHDMA_SLAVE_MMCIF_RX,
+ .addr = 0xe6bd0034,
+ .chcr = CHCR_RX(XMIT_SZ_32BIT),
+ .mid_rid = 0xd2,
+ },
+};
+
+#define DMAE_CHANNEL(_offset) \
+ { \
+ .offset = _offset - 0x20, \
+ .dmars = _offset - 0x20 + 0x40, \
+ }
+
+static const struct sh_dmae_channel sh73a0_dmae_channels[] = {
+ DMAE_CHANNEL(0x8000),
+ DMAE_CHANNEL(0x8080),
+ DMAE_CHANNEL(0x8100),
+ DMAE_CHANNEL(0x8180),
+ DMAE_CHANNEL(0x8200),
+ DMAE_CHANNEL(0x8280),
+ DMAE_CHANNEL(0x8300),
+ DMAE_CHANNEL(0x8380),
+ DMAE_CHANNEL(0x8400),
+ DMAE_CHANNEL(0x8480),
+ DMAE_CHANNEL(0x8500),
+ DMAE_CHANNEL(0x8580),
+ DMAE_CHANNEL(0x8600),
+ DMAE_CHANNEL(0x8680),
+ DMAE_CHANNEL(0x8700),
+ DMAE_CHANNEL(0x8780),
+ DMAE_CHANNEL(0x8800),
+ DMAE_CHANNEL(0x8880),
+ DMAE_CHANNEL(0x8900),
+ DMAE_CHANNEL(0x8980),
+};
+
+static const unsigned int ts_shift[] = TS_SHIFT;
+
+static struct sh_dmae_pdata sh73a0_dmae_platform_data = {
+ .slave = sh73a0_dmae_slaves,
+ .slave_num = ARRAY_SIZE(sh73a0_dmae_slaves),
+ .channel = sh73a0_dmae_channels,
+ .channel_num = ARRAY_SIZE(sh73a0_dmae_channels),
+ .ts_low_shift = 3,
+ .ts_low_mask = 0x18,
+ .ts_high_shift = (20 - 2), /* 2 bits for shifted low TS */
+ .ts_high_mask = 0x00300000,
+ .ts_shift = ts_shift,
+ .ts_shift_num = ARRAY_SIZE(ts_shift),
+ .dmaor_init = DMAOR_DME,
+};
+
+static struct resource sh73a0_dmae_resources[] = {
+ {
+ /* Registers including DMAOR and channels including DMARSx */
+ .start = 0xfe000020,
+ .end = 0xfe008a00 - 1,
+ .flags = IORESOURCE_MEM,
+ },
+ {
+ /* DMA error IRQ */
+ .start = gic_spi(129),
+ .end = gic_spi(129),
+ .flags = IORESOURCE_IRQ,
+ },
+ {
+ /* IRQ for channels 0-19 */
+ .start = gic_spi(109),
+ .end = gic_spi(128),
+ .flags = IORESOURCE_IRQ,
+ },
+};
+
+static struct platform_device dma0_device = {
+ .name = "sh-dma-engine",
+ .id = 0,
+ .resource = sh73a0_dmae_resources,
+ .num_resources = ARRAY_SIZE(sh73a0_dmae_resources),
+ .dev = {
+ .platform_data = &sh73a0_dmae_platform_data,
+ },
+};
+
static struct platform_device *sh73a0_early_devices[] __initdata = {
&scif0_device,
&scif1_device,
@@ -413,10 +651,16 @@ static struct platform_device *sh73a0_late_devices[] __initdata = {
&i2c2_device,
&i2c3_device,
&i2c4_device,
+ &dma0_device,
};
+#define SRCR2 0xe61580b0
+
void __init sh73a0_add_standard_devices(void)
{
+ /* Clear software reset bit on SY-DMAC module */
+ __raw_writel(__raw_readl(SRCR2) & ~(1 << 18), SRCR2);
+
platform_add_devices(sh73a0_early_devices,
ARRAY_SIZE(sh73a0_early_devices));
platform_add_devices(sh73a0_late_devices,
diff --git a/arch/arm/mach-shmobile/sleep-sh7372.S b/arch/arm/mach-shmobile/sleep-sh7372.S
new file mode 100644
index 000000000000..d37d3ca4d18f
--- /dev/null
+++ b/arch/arm/mach-shmobile/sleep-sh7372.S
@@ -0,0 +1,260 @@
+/*
+ * sh7372 lowlevel sleep code for "Core Standby Mode"
+ *
+ * Copyright (C) 2011 Magnus Damm
+ *
+ * In "Core Standby Mode" the ARM core is off, but L2 cache is still on
+ *
+ * Based on mach-omap2/sleep34xx.S
+ *
+ * (C) Copyright 2007 Texas Instruments
+ * Karthik Dasu <karthik-dp@ti.com>
+ *
+ * (C) Copyright 2004 Texas Instruments, <www.ti.com>
+ * Richard Woodruff <r-woodruff2@ti.com>
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License as
+ * published by the Free Software Foundation; either version 2 of
+ * the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR /PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston,
+ * MA 02111-1307 USA
+ */
+
+#include <linux/linkage.h>
+#include <asm/assembler.h>
+
+#define SMFRAM 0xe6a70000
+
+ .align
+kernel_flush:
+ .word v7_flush_dcache_all
+
+ .align 3
+ENTRY(sh7372_cpu_suspend)
+ stmfd sp!, {r0-r12, lr} @ save registers on stack
+
+ ldr r8, =SMFRAM
+
+ mov r4, sp @ Store sp
+ mrs r5, spsr @ Store spsr
+ mov r6, lr @ Store lr
+ stmia r8!, {r4-r6}
+
+ mrc p15, 0, r4, c1, c0, 2 @ Coprocessor access control register
+ mrc p15, 0, r5, c2, c0, 0 @ TTBR0
+ mrc p15, 0, r6, c2, c0, 1 @ TTBR1
+ mrc p15, 0, r7, c2, c0, 2 @ TTBCR
+ stmia r8!, {r4-r7}
+
+ mrc p15, 0, r4, c3, c0, 0 @ Domain access Control Register
+ mrc p15, 0, r5, c10, c2, 0 @ PRRR
+ mrc p15, 0, r6, c10, c2, 1 @ NMRR
+ stmia r8!,{r4-r6}
+
+ mrc p15, 0, r4, c13, c0, 1 @ Context ID
+ mrc p15, 0, r5, c13, c0, 2 @ User r/w thread and process ID
+ mrc p15, 0, r6, c12, c0, 0 @ Secure or NS vector base address
+ mrs r7, cpsr @ Store current cpsr
+ stmia r8!, {r4-r7}
+
+ mrc p15, 0, r4, c1, c0, 0 @ save control register
+ stmia r8!, {r4}
+
+ /*
+ * jump out to kernel flush routine
+ * - reuse that code is better
+ * - it executes in a cached space so is faster than refetch per-block
+ * - should be faster and will change with kernel
+ * - 'might' have to copy address, load and jump to it
+ * Flush all data from the L1 data cache before disabling
+ * SCTLR.C bit.
+ */
+ ldr r1, kernel_flush
+ mov lr, pc
+ bx r1
+
+ /*
+ * Clear the SCTLR.C bit to prevent further data cache
+ * allocation. Clearing SCTLR.C would make all the data accesses
+ * strongly ordered and would not hit the cache.
+ */
+ mrc p15, 0, r0, c1, c0, 0
+ bic r0, r0, #(1 << 2) @ Disable the C bit
+ mcr p15, 0, r0, c1, c0, 0
+ isb
+
+ /*
+ * Invalidate L1 data cache. Even though only invalidate is
+ * necessary exported flush API is used here. Doing clean
+ * on already clean cache would be almost NOP.
+ */
+ ldr r1, kernel_flush
+ blx r1
+ /*
+ * The kernel doesn't interwork: v7_flush_dcache_all in particluar will
+ * always return in Thumb state when CONFIG_THUMB2_KERNEL is enabled.
+ * This sequence switches back to ARM. Note that .align may insert a
+ * nop: bx pc needs to be word-aligned in order to work.
+ */
+ THUMB( .thumb )
+ THUMB( .align )
+ THUMB( bx pc )
+ THUMB( nop )
+ .arm
+
+ /* Data memory barrier and Data sync barrier */
+ dsb
+ dmb
+
+/*
+ * ===================================
+ * == WFI instruction => Enter idle ==
+ * ===================================
+ */
+ wfi @ wait for interrupt
+
+/*
+ * ===================================
+ * == Resume path for non-OFF modes ==
+ * ===================================
+ */
+ mrc p15, 0, r0, c1, c0, 0
+ tst r0, #(1 << 2) @ Check C bit enabled?
+ orreq r0, r0, #(1 << 2) @ Enable the C bit if cleared
+ mcreq p15, 0, r0, c1, c0, 0
+ isb
+
+/*
+ * ===================================
+ * == Exit point from non-OFF modes ==
+ * ===================================
+ */
+ ldmfd sp!, {r0-r12, pc} @ restore regs and return
+
+ .pool
+
+ .align 12
+ .text
+ .global sh7372_cpu_resume
+sh7372_cpu_resume:
+
+ mov r1, #0
+ /*
+ * Invalidate all instruction caches to PoU
+ * and flush branch target cache
+ */
+ mcr p15, 0, r1, c7, c5, 0
+
+ ldr r3, =SMFRAM
+
+ ldmia r3!, {r4-r6}
+ mov sp, r4 @ Restore sp
+ msr spsr_cxsf, r5 @ Restore spsr
+ mov lr, r6 @ Restore lr
+
+ ldmia r3!, {r4-r7}
+ mcr p15, 0, r4, c1, c0, 2 @ Coprocessor access Control Register
+ mcr p15, 0, r5, c2, c0, 0 @ TTBR0
+ mcr p15, 0, r6, c2, c0, 1 @ TTBR1
+ mcr p15, 0, r7, c2, c0, 2 @ TTBCR
+
+ ldmia r3!,{r4-r6}
+ mcr p15, 0, r4, c3, c0, 0 @ Domain access Control Register
+ mcr p15, 0, r5, c10, c2, 0 @ PRRR
+ mcr p15, 0, r6, c10, c2, 1 @ NMRR
+
+ ldmia r3!,{r4-r7}
+ mcr p15, 0, r4, c13, c0, 1 @ Context ID
+ mcr p15, 0, r5, c13, c0, 2 @ User r/w thread and process ID
+ mrc p15, 0, r6, c12, c0, 0 @ Secure or NS vector base address
+ msr cpsr, r7 @ store cpsr
+
+ /* Starting to enable MMU here */
+ mrc p15, 0, r7, c2, c0, 2 @ Read TTBRControl
+ /* Extract N (0:2) bits and decide whether to use TTBR0 or TTBR1 */
+ and r7, #0x7
+ cmp r7, #0x0
+ beq usettbr0
+ttbr_error:
+ /*
+ * More work needs to be done to support N[0:2] value other than 0
+ * So looping here so that the error can be detected
+ */
+ b ttbr_error
+
+ .align
+cache_pred_disable_mask:
+ .word 0xFFFFE7FB
+ttbrbit_mask:
+ .word 0xFFFFC000
+table_index_mask:
+ .word 0xFFF00000
+table_entry:
+ .word 0x00000C02
+usettbr0:
+
+ mrc p15, 0, r2, c2, c0, 0
+ ldr r5, ttbrbit_mask
+ and r2, r5
+ mov r4, pc
+ ldr r5, table_index_mask
+ and r4, r5 @ r4 = 31 to 20 bits of pc
+ /* Extract the value to be written to table entry */
+ ldr r6, table_entry
+ /* r6 has the value to be written to table entry */
+ add r6, r6, r4
+ /* Getting the address of table entry to modify */
+ lsr r4, #18
+ /* r2 has the location which needs to be modified */
+ add r2, r4
+ ldr r4, [r2]
+ str r6, [r2] /* modify the table entry */
+
+ mov r7, r6
+ mov r5, r2
+ mov r6, r4
+ /* r5 = original page table address */
+ /* r6 = original page table data */
+
+ mov r0, #0
+ mcr p15, 0, r0, c7, c5, 4 @ Flush prefetch buffer
+ mcr p15, 0, r0, c7, c5, 6 @ Invalidate branch predictor array
+ mcr p15, 0, r0, c8, c5, 0 @ Invalidate instruction TLB
+ mcr p15, 0, r0, c8, c6, 0 @ Invalidate data TLB
+
+ /*
+ * Restore control register. This enables the MMU.
+ * The caches and prediction are not enabled here, they
+ * will be enabled after restoring the MMU table entry.
+ */
+ ldmia r3!, {r4}
+ stmia r3!, {r5} /* save original page table address */
+ stmia r3!, {r6} /* save original page table data */
+ stmia r3!, {r7} /* save modified page table data */
+
+ ldr r2, cache_pred_disable_mask
+ and r4, r2
+ mcr p15, 0, r4, c1, c0, 0
+ dsb
+ isb
+
+ ldr r0, =restoremmu_on
+ bx r0
+
+/*
+ * ==============================
+ * == Exit point from OFF mode ==
+ * ==============================
+ */
+restoremmu_on:
+
+ ldmfd sp!, {r0-r12, pc} @ restore regs and return
diff --git a/arch/arm/mach-shmobile/smp-sh73a0.c b/arch/arm/mach-shmobile/smp-sh73a0.c
index a156d2108df1..3ffdbc92ba82 100644
--- a/arch/arm/mach-shmobile/smp-sh73a0.c
+++ b/arch/arm/mach-shmobile/smp-sh73a0.c
@@ -59,6 +59,11 @@ unsigned int __init sh73a0_get_core_count(void)
{
void __iomem *scu_base = scu_base_addr();
+#ifdef CONFIG_HAVE_ARM_TWD
+ /* twd_base needs to be initialized before percpu_timer_setup() */
+ twd_base = (void __iomem *)0xf0000600;
+#endif
+
return scu_get_core_count(scu_base);
}
@@ -82,10 +87,6 @@ int __cpuinit sh73a0_boot_secondary(unsigned int cpu)
void __init sh73a0_smp_prepare_cpus(void)
{
-#ifdef CONFIG_HAVE_ARM_TWD
- twd_base = (void __iomem *)0xf0000600;
-#endif
-
scu_enable(scu_base_addr());
/* Map the reset vector (in headsmp.S) */
diff --git a/arch/arm/mach-shmobile/suspend.c b/arch/arm/mach-shmobile/suspend.c
new file mode 100644
index 000000000000..c1febe13f709
--- /dev/null
+++ b/arch/arm/mach-shmobile/suspend.c
@@ -0,0 +1,47 @@
+/*
+ * Suspend-to-RAM support code for SH-Mobile ARM
+ *
+ * Copyright (C) 2011 Magnus Damm
+ *
+ * This file is subject to the terms and conditions of the GNU General Public
+ * License. See the file "COPYING" in the main directory of this archive
+ * for more details.
+ */
+
+#include <linux/pm.h>
+#include <linux/suspend.h>
+#include <linux/module.h>
+#include <linux/err.h>
+#include <asm/system.h>
+#include <asm/io.h>
+
+static int shmobile_suspend_default_enter(suspend_state_t suspend_state)
+{
+ cpu_do_idle();
+ return 0;
+}
+
+static int shmobile_suspend_begin(suspend_state_t state)
+{
+ disable_hlt();
+ return 0;
+}
+
+static void shmobile_suspend_end(void)
+{
+ enable_hlt();
+}
+
+struct platform_suspend_ops shmobile_suspend_ops = {
+ .begin = shmobile_suspend_begin,
+ .end = shmobile_suspend_end,
+ .enter = shmobile_suspend_default_enter,
+ .valid = suspend_valid_only_mem,
+};
+
+static int __init shmobile_suspend_init(void)
+{
+ suspend_set_ops(&shmobile_suspend_ops);
+ return 0;
+}
+late_initcall(shmobile_suspend_init);
diff --git a/arch/arm/mach-tegra/include/mach/sdhci.h b/arch/arm/mach-tegra/include/mach/sdhci.h
index 3ad086e859c3..4231bc7b8652 100644
--- a/arch/arm/mach-tegra/include/mach/sdhci.h
+++ b/arch/arm/mach-tegra/include/mach/sdhci.h
@@ -24,6 +24,7 @@ struct tegra_sdhci_platform_data {
int wp_gpio;
int power_gpio;
int is_8bit;
+ int pm_flags;
};
#endif
diff --git a/arch/arm/mach-ux500/Kconfig b/arch/arm/mach-ux500/Kconfig
index 58626013aa32..54429d015954 100644
--- a/arch/arm/mach-ux500/Kconfig
+++ b/arch/arm/mach-ux500/Kconfig
@@ -12,9 +12,12 @@ menu "Ux500 SoC"
config UX500_SOC_DB5500
bool "DB5500"
+ select MFD_DB5500_PRCMU
config UX500_SOC_DB8500
bool "DB8500"
+ select MFD_DB8500_PRCMU
+ select REGULATOR_DB8500_PRCMU
endmenu
diff --git a/arch/arm/mach-ux500/Makefile b/arch/arm/mach-ux500/Makefile
index b549a8fb4231..1694916e6822 100644
--- a/arch/arm/mach-ux500/Makefile
+++ b/arch/arm/mach-ux500/Makefile
@@ -5,7 +5,7 @@
obj-y := clock.o cpu.o devices.o devices-common.o \
id.o usb.o
obj-$(CONFIG_UX500_SOC_DB5500) += cpu-db5500.o dma-db5500.o
-obj-$(CONFIG_UX500_SOC_DB8500) += cpu-db8500.o devices-db8500.o prcmu.o
+obj-$(CONFIG_UX500_SOC_DB8500) += cpu-db8500.o devices-db8500.o
obj-$(CONFIG_MACH_U8500) += board-mop500.o board-mop500-sdi.o \
board-mop500-regulators.o \
board-mop500-uib.o board-mop500-stuib.o \
@@ -17,4 +17,4 @@ obj-$(CONFIG_HOTPLUG_CPU) += hotplug.o
obj-$(CONFIG_LOCAL_TIMERS) += localtimer.o
obj-$(CONFIG_U5500_MODEM_IRQ) += modem-irq-db5500.o
obj-$(CONFIG_U5500_MBOX) += mbox-db5500.o
-obj-$(CONFIG_CPU_FREQ) += cpufreq.o
+
diff --git a/arch/arm/mach-ux500/board-mop500-sdi.c b/arch/arm/mach-ux500/board-mop500-sdi.c
index bf0b02414e5b..7c6cb4fa47a9 100644
--- a/arch/arm/mach-ux500/board-mop500-sdi.c
+++ b/arch/arm/mach-ux500/board-mop500-sdi.c
@@ -99,8 +99,11 @@ static void sdi0_configure(void)
gpio_direction_output(sdi0_vsel, 0);
gpio_direction_output(sdi0_en, 1);
- /* Add the device */
- db8500_add_sdi0(&mop500_sdi0_data);
+ /* Add the device, force v2 to subrevision 1 */
+ if (cpu_is_u8500v2())
+ db8500_add_sdi0(&mop500_sdi0_data, 0x10480180);
+ else
+ db8500_add_sdi0(&mop500_sdi0_data, 0);
}
void mop500_sdi_tc35892_init(void)
@@ -188,13 +191,18 @@ static struct mmci_platform_data mop500_sdi4_data = {
void __init mop500_sdi_init(void)
{
+ u32 periphid = 0;
+
+ /* v2 has a new version of this block that need to be forced */
+ if (cpu_is_u8500v2())
+ periphid = 0x10480180;
/* PoP:ed eMMC on top of DB8500 v1.0 has problems with high speed */
if (!cpu_is_u8500v10())
mop500_sdi2_data.capabilities |= MMC_CAP_MMC_HIGHSPEED;
- db8500_add_sdi2(&mop500_sdi2_data);
+ db8500_add_sdi2(&mop500_sdi2_data, periphid);
/* On-board eMMC */
- db8500_add_sdi4(&mop500_sdi4_data);
+ db8500_add_sdi4(&mop500_sdi4_data, periphid);
if (machine_is_hrefv60()) {
mop500_sdi0_data.gpio_cd = HREFV60_SDMMC_CD_GPIO;
diff --git a/arch/arm/mach-ux500/cpu-db5500.c b/arch/arm/mach-ux500/cpu-db5500.c
index c9dc2eff3cb2..c01bc19e3c5e 100644
--- a/arch/arm/mach-ux500/cpu-db5500.c
+++ b/arch/arm/mach-ux500/cpu-db5500.c
@@ -188,6 +188,8 @@ void __init u5500_map_io(void)
ux500_map_io();
iotable_init(u5500_io_desc, ARRAY_SIZE(u5500_io_desc));
+
+ _PRCMU_BASE = __io_address(U5500_PRCMU_BASE);
}
static int usb_db5500_rx_dma_cfg[] = {
diff --git a/arch/arm/mach-ux500/cpu-db8500.c b/arch/arm/mach-ux500/cpu-db8500.c
index 516126cb357d..c3c417656bd9 100644
--- a/arch/arm/mach-ux500/cpu-db8500.c
+++ b/arch/arm/mach-ux500/cpu-db8500.c
@@ -87,6 +87,8 @@ void __init u8500_map_io(void)
iotable_init(u8500_v1_io_desc, ARRAY_SIZE(u8500_v1_io_desc));
else if (cpu_is_u8500v2())
iotable_init(u8500_v2_io_desc, ARRAY_SIZE(u8500_v2_io_desc));
+
+ _PRCMU_BASE = __io_address(U8500_PRCMU_BASE);
}
static struct resource db8500_pmu_resources[] = {
@@ -129,9 +131,14 @@ static struct platform_device db8500_pmu_device = {
.dev.platform_data = &db8500_pmu_platdata,
};
+static struct platform_device db8500_prcmu_device = {
+ .name = "db8500-prcmu",
+};
+
static struct platform_device *platform_devs[] __initdata = {
&u8500_dma40_device,
&db8500_pmu_device,
+ &db8500_prcmu_device,
};
static resource_size_t __initdata db8500_gpio_base[] = {
diff --git a/arch/arm/mach-ux500/cpu.c b/arch/arm/mach-ux500/cpu.c
index 5a43107c6232..1da23bb87c16 100644
--- a/arch/arm/mach-ux500/cpu.c
+++ b/arch/arm/mach-ux500/cpu.c
@@ -8,6 +8,8 @@
#include <linux/platform_device.h>
#include <linux/io.h>
#include <linux/clk.h>
+#include <linux/mfd/db8500-prcmu.h>
+#include <linux/mfd/db5500-prcmu.h>
#include <asm/cacheflush.h>
#include <asm/hardware/cache-l2x0.h>
@@ -19,10 +21,11 @@
#include <mach/hardware.h>
#include <mach/setup.h>
#include <mach/devices.h>
-#include <mach/prcmu.h>
#include "clock.h"
+void __iomem *_PRCMU_BASE;
+
#ifdef CONFIG_CACHE_L2X0
static void __iomem *l2x0_base;
#endif
@@ -47,6 +50,8 @@ void __init ux500_init_irq(void)
* Init clocks here so that they are available for system timer
* initialization.
*/
+ if (cpu_is_u5500())
+ db5500_prcmu_early_init();
if (cpu_is_u8500())
prcmu_early_init();
clk_init();
diff --git a/arch/arm/mach-ux500/cpufreq.c b/arch/arm/mach-ux500/cpufreq.c
deleted file mode 100644
index 5c5b747f134d..000000000000
--- a/arch/arm/mach-ux500/cpufreq.c
+++ /dev/null
@@ -1,211 +0,0 @@
-/*
- * CPU frequency scaling for u8500
- * Inspired by linux/arch/arm/mach-davinci/cpufreq.c
- *
- * Copyright (C) STMicroelectronics 2009
- * Copyright (C) ST-Ericsson SA 2010
- *
- * License Terms: GNU General Public License v2
- *
- * Author: Sundar Iyer <sundar.iyer@stericsson.com>
- * Author: Martin Persson <martin.persson@stericsson.com>
- * Author: Jonas Aaberg <jonas.aberg@stericsson.com>
- *
- */
-
-#include <linux/platform_device.h>
-#include <linux/kernel.h>
-#include <linux/cpufreq.h>
-#include <linux/delay.h>
-
-#include <mach/hardware.h>
-#include <mach/prcmu.h>
-#include <mach/prcmu-defs.h>
-
-#define DRIVER_NAME "cpufreq-u8500"
-#define CPUFREQ_NAME "u8500"
-
-static struct device *dev;
-
-static struct cpufreq_frequency_table freq_table[] = {
- [0] = {
- .index = 0,
- .frequency = 200000,
- },
- [1] = {
- .index = 1,
- .frequency = 300000,
- },
- [2] = {
- .index = 2,
- .frequency = 600000,
- },
- [3] = {
- /* Used for CPU_OPP_MAX, if available */
- .index = 3,
- .frequency = CPUFREQ_TABLE_END,
- },
- [4] = {
- .index = 4,
- .frequency = CPUFREQ_TABLE_END,
- },
-};
-
-static enum prcmu_cpu_opp index2opp[] = {
- CPU_OPP_EXT_CLK,
- CPU_OPP_50,
- CPU_OPP_100,
- CPU_OPP_MAX
-};
-
-static int u8500_cpufreq_verify_speed(struct cpufreq_policy *policy)
-{
- return cpufreq_frequency_table_verify(policy, freq_table);
-}
-
-static int u8500_cpufreq_target(struct cpufreq_policy *policy,
- unsigned int target_freq,
- unsigned int relation)
-{
- struct cpufreq_freqs freqs;
- unsigned int index;
- int ret = 0;
-
- /*
- * Ensure desired rate is within allowed range. Some govenors
- * (ondemand) will just pass target_freq=0 to get the minimum.
- */
- if (target_freq < policy->cpuinfo.min_freq)
- target_freq = policy->cpuinfo.min_freq;
- if (target_freq > policy->cpuinfo.max_freq)
- target_freq = policy->cpuinfo.max_freq;
-
- ret = cpufreq_frequency_table_target(policy, freq_table,
- target_freq, relation, &index);
- if (ret < 0) {
- dev_err(dev, "Could not look up next frequency\n");
- return ret;
- }
-
- freqs.old = policy->cur;
- freqs.new = freq_table[index].frequency;
- freqs.cpu = policy->cpu;
-
- if (freqs.old == freqs.new) {
- dev_dbg(dev, "Current and target frequencies are equal\n");
- return 0;
- }
-
- dev_dbg(dev, "transition: %u --> %u\n", freqs.old, freqs.new);
- cpufreq_notify_transition(&freqs, CPUFREQ_PRECHANGE);
-
- ret = prcmu_set_cpu_opp(index2opp[index]);
- if (ret < 0) {
- dev_err(dev, "Failed to set OPP level\n");
- return ret;
- }
-
- cpufreq_notify_transition(&freqs, CPUFREQ_POSTCHANGE);
-
- return ret;
-}
-
-static unsigned int u8500_cpufreq_getspeed(unsigned int cpu)
-{
- int i;
-
- for (i = 0; prcmu_get_cpu_opp() != index2opp[i]; i++)
- ;
- return freq_table[i].frequency;
-}
-
-static int __cpuinit u8500_cpu_init(struct cpufreq_policy *policy)
-{
- int res;
-
- BUILD_BUG_ON(ARRAY_SIZE(index2opp) + 1 != ARRAY_SIZE(freq_table));
-
- if (cpu_is_u8500v2()) {
- freq_table[1].frequency = 400000;
- freq_table[2].frequency = 800000;
- if (prcmu_has_arm_maxopp())
- freq_table[3].frequency = 1000000;
- }
-
- /* get policy fields based on the table */
- res = cpufreq_frequency_table_cpuinfo(policy, freq_table);
- if (!res)
- cpufreq_frequency_table_get_attr(freq_table, policy->cpu);
- else {
- dev_err(dev, "u8500-cpufreq : Failed to read policy table\n");
- return res;
- }
-
- policy->min = policy->cpuinfo.min_freq;
- policy->max = policy->cpuinfo.max_freq;
- policy->cur = u8500_cpufreq_getspeed(policy->cpu);
- policy->governor = CPUFREQ_DEFAULT_GOVERNOR;
-
- /*
- * FIXME : Need to take time measurement across the target()
- * function with no/some/all drivers in the notification
- * list.
- */
- policy->cpuinfo.transition_latency = 200 * 1000; /* in ns */
-
- /* policy sharing between dual CPUs */
- cpumask_copy(policy->cpus, &cpu_present_map);
-
- policy->shared_type = CPUFREQ_SHARED_TYPE_ALL;
-
- return res;
-}
-
-static struct freq_attr *u8500_cpufreq_attr[] = {
- &cpufreq_freq_attr_scaling_available_freqs,
- NULL,
-};
-static int u8500_cpu_exit(struct cpufreq_policy *policy)
-{
- cpufreq_frequency_table_put_attr(policy->cpu);
- return 0;
-}
-
-static struct cpufreq_driver u8500_driver = {
- .owner = THIS_MODULE,
- .flags = CPUFREQ_STICKY,
- .verify = u8500_cpufreq_verify_speed,
- .target = u8500_cpufreq_target,
- .get = u8500_cpufreq_getspeed,
- .init = u8500_cpu_init,
- .exit = u8500_cpu_exit,
- .name = CPUFREQ_NAME,
- .attr = u8500_cpufreq_attr,
-};
-
-static int __init u8500_cpufreq_probe(struct platform_device *pdev)
-{
- dev = &pdev->dev;
- return cpufreq_register_driver(&u8500_driver);
-}
-
-static int __exit u8500_cpufreq_remove(struct platform_device *pdev)
-{
- return cpufreq_unregister_driver(&u8500_driver);
-}
-
-static struct platform_driver u8500_cpufreq_driver = {
- .driver = {
- .name = DRIVER_NAME,
- .owner = THIS_MODULE,
- },
- .remove = __exit_p(u8500_cpufreq_remove),
-};
-
-static int __init u8500_cpufreq_init(void)
-{
- return platform_driver_probe(&u8500_cpufreq_driver,
- &u8500_cpufreq_probe);
-}
-
-device_initcall(u8500_cpufreq_init);
diff --git a/arch/arm/mach-ux500/devices-common.h b/arch/arm/mach-ux500/devices-common.h
index c719b5a1d913..7825705033bf 100644
--- a/arch/arm/mach-ux500/devices-common.h
+++ b/arch/arm/mach-ux500/devices-common.h
@@ -28,18 +28,20 @@ dbx500_add_msp_spi(const char *name, resource_size_t base, int irq,
static inline struct amba_device *
dbx500_add_spi(const char *name, resource_size_t base, int irq,
- struct spi_master_cntlr *pdata)
+ struct spi_master_cntlr *pdata,
+ u32 periphid)
{
- return dbx500_add_amba_device(name, base, irq, pdata, 0);
+ return dbx500_add_amba_device(name, base, irq, pdata, periphid);
}
struct mmci_platform_data;
static inline struct amba_device *
dbx500_add_sdi(const char *name, resource_size_t base, int irq,
- struct mmci_platform_data *pdata)
+ struct mmci_platform_data *pdata,
+ u32 periphid)
{
- return dbx500_add_amba_device(name, base, irq, pdata, 0);
+ return dbx500_add_amba_device(name, base, irq, pdata, periphid);
}
struct amba_pl011_data;
diff --git a/arch/arm/mach-ux500/devices-db5500.h b/arch/arm/mach-ux500/devices-db5500.h
index 94627f7783b0..0c4bccd02b90 100644
--- a/arch/arm/mach-ux500/devices-db5500.h
+++ b/arch/arm/mach-ux500/devices-db5500.h
@@ -38,24 +38,34 @@
ux500_add_usb(U5500_USBOTG_BASE, IRQ_DB5500_USBOTG, rx_cfg, tx_cfg)
#define db5500_add_sdi0(pdata) \
- dbx500_add_sdi("sdi0", U5500_SDI0_BASE, IRQ_DB5500_SDMMC0, pdata)
+ dbx500_add_sdi("sdi0", U5500_SDI0_BASE, IRQ_DB5500_SDMMC0, pdata, \
+ 0x10480180)
#define db5500_add_sdi1(pdata) \
- dbx500_add_sdi("sdi1", U5500_SDI1_BASE, IRQ_DB5500_SDMMC1, pdata)
+ dbx500_add_sdi("sdi1", U5500_SDI1_BASE, IRQ_DB5500_SDMMC1, pdata, \
+ 0x10480180)
#define db5500_add_sdi2(pdata) \
- dbx500_add_sdi("sdi2", U5500_SDI2_BASE, IRQ_DB5500_SDMMC2, pdata)
+ dbx500_add_sdi("sdi2", U5500_SDI2_BASE, IRQ_DB5500_SDMMC2, pdata \
+ 0x10480180)
#define db5500_add_sdi3(pdata) \
- dbx500_add_sdi("sdi3", U5500_SDI3_BASE, IRQ_DB5500_SDMMC3, pdata)
+ dbx500_add_sdi("sdi3", U5500_SDI3_BASE, IRQ_DB5500_SDMMC3, pdata \
+ 0x10480180)
#define db5500_add_sdi4(pdata) \
- dbx500_add_sdi("sdi4", U5500_SDI4_BASE, IRQ_DB5500_SDMMC4, pdata)
+ dbx500_add_sdi("sdi4", U5500_SDI4_BASE, IRQ_DB5500_SDMMC4, pdata \
+ 0x10480180)
+/* This one has a bad peripheral ID in the U5500 silicon */
#define db5500_add_spi0(pdata) \
- dbx500_add_spi("spi0", U5500_SPI0_BASE, IRQ_DB5500_SPI0, pdata)
+ dbx500_add_spi("spi0", U5500_SPI0_BASE, IRQ_DB5500_SPI0, pdata, \
+ 0x10080023)
#define db5500_add_spi1(pdata) \
- dbx500_add_spi("spi1", U5500_SPI1_BASE, IRQ_DB5500_SPI1, pdata)
+ dbx500_add_spi("spi1", U5500_SPI1_BASE, IRQ_DB5500_SPI1, pdata, \
+ 0x10080023)
#define db5500_add_spi2(pdata) \
- dbx500_add_spi("spi2", U5500_SPI2_BASE, IRQ_DB5500_SPI2, pdata)
+ dbx500_add_spi("spi2", U5500_SPI2_BASE, IRQ_DB5500_SPI2, pdata \
+ 0x10080023)
#define db5500_add_spi3(pdata) \
- dbx500_add_spi("spi3", U5500_SPI3_BASE, IRQ_DB5500_SPI3, pdata)
+ dbx500_add_spi("spi3", U5500_SPI3_BASE, IRQ_DB5500_SPI3, pdata \
+ 0x10080023)
#define db5500_add_uart0(plat) \
dbx500_add_uart("uart0", U5500_UART0_BASE, IRQ_DB5500_UART0, plat)
diff --git a/arch/arm/mach-ux500/devices-db8500.h b/arch/arm/mach-ux500/devices-db8500.h
index 9cc6f8f5d3e6..cbd4a9ae8109 100644
--- a/arch/arm/mach-ux500/devices-db8500.h
+++ b/arch/arm/mach-ux500/devices-db8500.h
@@ -25,7 +25,7 @@ static inline struct amba_device *
db8500_add_ssp(const char *name, resource_size_t base, int irq,
struct pl022_ssp_controller *pdata)
{
- return dbx500_add_amba_device(name, base, irq, pdata, SSP_PER_ID);
+ return dbx500_add_amba_device(name, base, irq, pdata, 0);
}
@@ -64,18 +64,18 @@ db8500_add_ssp(const char *name, resource_size_t base, int irq,
#define db8500_add_usb(rx_cfg, tx_cfg) \
ux500_add_usb(U8500_USBOTG_BASE, IRQ_DB8500_USBOTG, rx_cfg, tx_cfg)
-#define db8500_add_sdi0(pdata) \
- dbx500_add_sdi("sdi0", U8500_SDI0_BASE, IRQ_DB8500_SDMMC0, pdata)
-#define db8500_add_sdi1(pdata) \
- dbx500_add_sdi("sdi1", U8500_SDI1_BASE, IRQ_DB8500_SDMMC1, pdata)
-#define db8500_add_sdi2(pdata) \
- dbx500_add_sdi("sdi2", U8500_SDI2_BASE, IRQ_DB8500_SDMMC2, pdata)
-#define db8500_add_sdi3(pdata) \
- dbx500_add_sdi("sdi3", U8500_SDI3_BASE, IRQ_DB8500_SDMMC3, pdata)
-#define db8500_add_sdi4(pdata) \
- dbx500_add_sdi("sdi4", U8500_SDI4_BASE, IRQ_DB8500_SDMMC4, pdata)
-#define db8500_add_sdi5(pdata) \
- dbx500_add_sdi("sdi5", U8500_SDI5_BASE, IRQ_DB8500_SDMMC5, pdata)
+#define db8500_add_sdi0(pdata, pid) \
+ dbx500_add_sdi("sdi0", U8500_SDI0_BASE, IRQ_DB8500_SDMMC0, pdata, pid)
+#define db8500_add_sdi1(pdata, pid) \
+ dbx500_add_sdi("sdi1", U8500_SDI1_BASE, IRQ_DB8500_SDMMC1, pdata, pid)
+#define db8500_add_sdi2(pdata, pid) \
+ dbx500_add_sdi("sdi2", U8500_SDI2_BASE, IRQ_DB8500_SDMMC2, pdata, pid)
+#define db8500_add_sdi3(pdata, pid) \
+ dbx500_add_sdi("sdi3", U8500_SDI3_BASE, IRQ_DB8500_SDMMC3, pdata, pid)
+#define db8500_add_sdi4(pdata, pid) \
+ dbx500_add_sdi("sdi4", U8500_SDI4_BASE, IRQ_DB8500_SDMMC4, pdata, pid)
+#define db8500_add_sdi5(pdata, pid) \
+ dbx500_add_sdi("sdi5", U8500_SDI5_BASE, IRQ_DB8500_SDMMC5, pdata, pid)
#define db8500_add_ssp0(pdata) \
db8500_add_ssp("ssp0", U8500_SSP0_BASE, IRQ_DB8500_SSP0, pdata)
@@ -83,13 +83,13 @@ db8500_add_ssp(const char *name, resource_size_t base, int irq,
db8500_add_ssp("ssp1", U8500_SSP1_BASE, IRQ_DB8500_SSP1, pdata)
#define db8500_add_spi0(pdata) \
- dbx500_add_spi("spi0", U8500_SPI0_BASE, IRQ_DB8500_SPI0, pdata)
+ dbx500_add_spi("spi0", U8500_SPI0_BASE, IRQ_DB8500_SPI0, pdata, 0)
#define db8500_add_spi1(pdata) \
- dbx500_add_spi("spi1", U8500_SPI1_BASE, IRQ_DB8500_SPI1, pdata)
+ dbx500_add_spi("spi1", U8500_SPI1_BASE, IRQ_DB8500_SPI1, pdata, 0)
#define db8500_add_spi2(pdata) \
- dbx500_add_spi("spi2", U8500_SPI2_BASE, IRQ_DB8500_SPI2, pdata)
+ dbx500_add_spi("spi2", U8500_SPI2_BASE, IRQ_DB8500_SPI2, pdata, 0)
#define db8500_add_spi3(pdata) \
- dbx500_add_spi("spi3", U8500_SPI3_BASE, IRQ_DB8500_SPI3, pdata)
+ dbx500_add_spi("spi3", U8500_SPI3_BASE, IRQ_DB8500_SPI3, pdata, 0)
#define db8500_add_uart0(pdata) \
dbx500_add_uart("uart0", U8500_UART0_BASE, IRQ_DB8500_UART0, pdata)
diff --git a/arch/arm/mach-ux500/include/mach/db5500-regs.h b/arch/arm/mach-ux500/include/mach/db5500-regs.h
index bd88c1e74060..6ad983294103 100644
--- a/arch/arm/mach-ux500/include/mach/db5500-regs.h
+++ b/arch/arm/mach-ux500/include/mach/db5500-regs.h
@@ -17,6 +17,8 @@
#define U5500_GIC_DIST_BASE 0xA0411000
#define U5500_GIC_CPU_BASE 0xA0410100
#define U5500_DMA_BASE 0x90030000
+#define U5500_STM_BASE 0x90020000
+#define U5500_STM_REG_BASE (U5500_STM_BASE + 0xF000)
#define U5500_MCDE_BASE 0xA0400000
#define U5500_MODEM_BASE 0xB0000000
#define U5500_L2CC_BASE 0xA0412000
@@ -29,7 +31,9 @@
#define U5500_NAND0_BASE 0x60000000
#define U5500_NAND1_BASE 0x70000000
#define U5500_TWD_BASE 0xa0410600
+#define U5500_ICN_BASE 0xA0040000
#define U5500_B2R2_BASE 0xa0200000
+#define U5500_BOOT_ROM_BASE 0x90000000
#define U5500_FSMC_BASE (U5500_PER1_BASE + 0x0000)
#define U5500_SDI0_BASE (U5500_PER1_BASE + 0x1000)
@@ -60,6 +64,7 @@
#define U5500_MSP1_BASE (U5500_PER4_BASE + 0x9000)
#define U5500_GPIO2_BASE (U5500_PER4_BASE + 0xA000)
#define U5500_CDETECT_BASE (U5500_PER4_BASE + 0xF000)
+#define U5500_PRCMU_TCDM_BASE (U5500_PER4_BASE + 0x18000)
#define U5500_SPI0_BASE (U5500_PER5_BASE + 0x0000)
#define U5500_SPI1_BASE (U5500_PER5_BASE + 0x1000)
@@ -83,7 +88,7 @@
#define U5500_HASH0_BASE (U5500_PER6_BASE + 0x1000)
#define U5500_HASH1_BASE (U5500_PER6_BASE + 0x2000)
#define U5500_PKA_BASE (U5500_PER6_BASE + 0x4000)
-#define U5500_PKAM_BASE (U5500_PER6_BASE + 0x5000)
+#define U5500_PKAM_BASE (U5500_PER6_BASE + 0x5100)
#define U5500_MTU0_BASE (U5500_PER6_BASE + 0x6000)
#define U5500_MTU1_BASE (U5500_PER6_BASE + 0x7000)
#define U5500_CR_BASE (U5500_PER6_BASE + 0x8000)
@@ -114,8 +119,19 @@
#define U5500_MBOX2_LOCAL_START (U5500_MBOX_BASE + 0x20)
#define U5500_MBOX2_LOCAL_END (U5500_MBOX_BASE + 0x3F)
-#define U5500_ESRAM_BASE 0x40000000
+#define U5500_ACCCON_BASE_SEC (0xBFFF0000)
+#define U5500_ACCCON_BASE (0xBFFF1000)
+#define U5500_ACCCON_CPUVEC_RESET_ADDR_OFFSET (0x00000020)
+#define U5500_ACCCON_ACC_CPU_CTRL_OFFSET (0x000000BC)
+
+#define U5500_ESRAM_BASE 0x40000000
#define U5500_ESRAM_DMA_LCPA_OFFSET 0x10000
#define U5500_DMA_LCPA_BASE (U5500_ESRAM_BASE + U5500_ESRAM_DMA_LCPA_OFFSET)
+#define U5500_MCDE_SIZE 0x1000
+#define U5500_DSI_LINK_SIZE 0x1000
+#define U5500_DSI_LINK_COUNT 0x2
+#define U5500_DSI_LINK1_BASE (U5500_MCDE_BASE + U5500_MCDE_SIZE)
+#define U5500_DSI_LINK2_BASE (U5500_DSI_LINK1_BASE + U5500_DSI_LINK_SIZE)
+
#endif
diff --git a/arch/arm/mach-ux500/include/mach/db8500-regs.h b/arch/arm/mach-ux500/include/mach/db8500-regs.h
index 16647b255378..049997109cf9 100644
--- a/arch/arm/mach-ux500/include/mach/db8500-regs.h
+++ b/arch/arm/mach-ux500/include/mach/db8500-regs.h
@@ -15,8 +15,13 @@
#define U8500_ESRAM_BANK2 (U8500_ESRAM_BANK1 + U8500_ESRAM_BANK_SIZE)
#define U8500_ESRAM_BANK3 (U8500_ESRAM_BANK2 + U8500_ESRAM_BANK_SIZE)
#define U8500_ESRAM_BANK4 (U8500_ESRAM_BANK3 + U8500_ESRAM_BANK_SIZE)
-/* Use bank 4 for DMA LCPA */
-#define U8500_DMA_LCPA_BASE U8500_ESRAM_BANK4
+/*
+ * on V1 DMA uses 4KB for logical parameters position is right after the 64KB
+ * reserved for security
+ */
+#define U8500_ESRAM_DMA_LCPA_OFFSET 0x10000
+
+#define U8500_DMA_LCPA_BASE (U8500_ESRAM_BANK0 + U8500_ESRAM_DMA_LCPA_OFFSET)
#define U8500_DMA_LCPA_BASE_ED (U8500_ESRAM_BANK4 + 0x4000)
#define U8500_PER3_BASE 0x80000000
@@ -27,9 +32,12 @@
#define U8500_B2R2_BASE 0x80130000
#define U8500_HSEM_BASE 0x80140000
#define U8500_PER4_BASE 0x80150000
+#define U8500_TPIU_BASE 0x80190000
#define U8500_ICN_BASE 0x81000000
#define U8500_BOOT_ROM_BASE 0x90000000
+/* ASIC ID is at 0xbf4 offset within this region */
+#define U8500_ASIC_ID_BASE 0x9001D000
#define U8500_PER6_BASE 0xa03c0000
#define U8500_PER5_BASE 0xa03e0000
@@ -70,13 +78,15 @@
/* per6 base addresses */
#define U8500_RNG_BASE (U8500_PER6_BASE + 0x0000)
-#define U8500_PKA_BASE (U8500_PER6_BASE + 0x1000)
-#define U8500_PKAM_BASE (U8500_PER6_BASE + 0x2000)
+#define U8500_HASH0_BASE (U8500_PER6_BASE + 0x1000)
+#define U8500_HASH1_BASE (U8500_PER6_BASE + 0x2000)
+#define U8500_PKA_BASE (U8500_PER6_BASE + 0x4000)
+#define U8500_PKAM_BASE (U8500_PER6_BASE + 0x5100)
#define U8500_MTU0_BASE (U8500_PER6_BASE + 0x6000) /* v1 */
#define U8500_MTU1_BASE (U8500_PER6_BASE + 0x7000) /* v1 */
#define U8500_CR_BASE (U8500_PER6_BASE + 0x8000) /* v1 */
-#define U8500_CRYPTO0_BASE (U8500_PER6_BASE + 0xa000)
-#define U8500_CRYPTO1_BASE (U8500_PER6_BASE + 0xb000)
+#define U8500_CRYP0_BASE (U8500_PER6_BASE + 0xa000)
+#define U8500_CRYP1_BASE (U8500_PER6_BASE + 0xb000)
#define U8500_CLKRST6_BASE (U8500_PER6_BASE + 0xf000)
/* per5 base addresses */
@@ -93,7 +103,8 @@
#define U8500_DMC_BASE (U8500_PER4_BASE + 0x06000)
#define U8500_PRCMU_BASE (U8500_PER4_BASE + 0x07000)
#define U8500_PRCMU_TCDM_BASE_V1 (U8500_PER4_BASE + 0x0f000)
-#define U8500_PRCMU_TCDM_BASE (U8500_PER4_BASE + 0x68000)
+#define U8500_PRCMU_TCDM_BASE (U8500_PER4_BASE + 0x68000)
+#define U8500_PRCMU_TCPM_BASE (U8500_PER4_BASE + 0x60000)
/* per3 base addresses */
#define U8500_FSMC_BASE (U8500_PER3_BASE + 0x0000)
@@ -124,6 +135,7 @@
#define U8500_I2C1_BASE (U8500_PER1_BASE + 0x2000)
#define U8500_MSP0_BASE (U8500_PER1_BASE + 0x3000)
#define U8500_MSP1_BASE (U8500_PER1_BASE + 0x4000)
+#define U8500_MSP3_BASE (U8500_PER1_BASE + 0x5000)
#define U8500_SDI0_BASE (U8500_PER1_BASE + 0x6000)
#define U8500_I2C2_BASE (U8500_PER1_BASE + 0x8000)
#define U8500_SPI3_BASE (U8500_PER1_BASE + 0x9000)
@@ -143,4 +155,15 @@
#define U8500_GPIOBANK7_BASE (U8500_GPIO2_BASE + 0x80)
#define U8500_GPIOBANK8_BASE U8500_GPIO3_BASE
+#define U8500_MCDE_SIZE 0x1000
+#define U8500_DSI_LINK_SIZE 0x1000
+#define U8500_DSI_LINK1_BASE (U8500_MCDE_BASE + U8500_MCDE_SIZE)
+#define U8500_DSI_LINK2_BASE (U8500_DSI_LINK1_BASE + U8500_DSI_LINK_SIZE)
+#define U8500_DSI_LINK3_BASE (U8500_DSI_LINK2_BASE + U8500_DSI_LINK_SIZE)
+#define U8500_DSI_LINK_COUNT 0x3
+
+/* Modem and APE physical addresses */
+#define U8500_MODEM_BASE 0xe000000
+#define U8500_APE_BASE 0x6000000
+
#endif
diff --git a/arch/arm/mach-ux500/include/mach/hardware.h b/arch/arm/mach-ux500/include/mach/hardware.h
index bf63f2631ba0..470ac52663d6 100644
--- a/arch/arm/mach-ux500/include/mach/hardware.h
+++ b/arch/arm/mach-ux500/include/mach/hardware.h
@@ -29,12 +29,10 @@
#include <mach/db8500-regs.h>
#include <mach/db5500-regs.h>
-/* ST-Ericsson modified pl022 id */
-#define SSP_PER_ID 0x01080022
-
#ifndef __ASSEMBLY__
#include <mach/id.h>
+extern void __iomem *_PRCMU_BASE;
#define ARRAY_AND_SIZE(x) (x), ARRAY_SIZE(x)
diff --git a/arch/arm/mach-ux500/include/mach/id.h b/arch/arm/mach-ux500/include/mach/id.h
index f1288d10b6ab..02b541a37ee5 100644
--- a/arch/arm/mach-ux500/include/mach/id.h
+++ b/arch/arm/mach-ux500/include/mach/id.h
@@ -75,6 +75,26 @@ static inline bool __attribute_const__ cpu_is_u8500v2(void)
return cpu_is_u8500() && ((dbx500_revision() & 0xf0) == 0xB0);
}
+static inline bool cpu_is_u8500v20(void)
+{
+ return cpu_is_u8500() && (dbx500_revision() == 0xB0);
+}
+
+static inline bool cpu_is_u8500v21(void)
+{
+ return cpu_is_u8500() && (dbx500_revision() == 0xB1);
+}
+
+static inline bool cpu_is_u8500v20_or_later(void)
+{
+ return cpu_is_u8500() && !cpu_is_u8500v10() && !cpu_is_u8500v11();
+}
+
+static inline bool ux500_is_svp(void)
+{
+ return false;
+}
+
#define ux500_unknown_soc() BUG()
#endif
diff --git a/arch/arm/mach-ux500/include/mach/irqs-board-mop500.h b/arch/arm/mach-ux500/include/mach/irqs-board-mop500.h
index 97ef55f84934..47969909836c 100644
--- a/arch/arm/mach-ux500/include/mach/irqs-board-mop500.h
+++ b/arch/arm/mach-ux500/include/mach/irqs-board-mop500.h
@@ -50,6 +50,11 @@
#define MOP500_IRQ_END MOP500_NR_IRQS
+/*
+ * We may have several boards, but only one will run at a
+ * time, so the one with most IRQs will bump this ahead,
+ * but the IRQ_BOARD_START remains the same for either board.
+ */
#if MOP500_IRQ_END > IRQ_BOARD_END
#undef IRQ_BOARD_END
#define IRQ_BOARD_END MOP500_IRQ_END
diff --git a/arch/arm/mach-ux500/include/mach/irqs-board-u5500.h b/arch/arm/mach-ux500/include/mach/irqs-board-u5500.h
new file mode 100644
index 000000000000..29d972c7717b
--- /dev/null
+++ b/arch/arm/mach-ux500/include/mach/irqs-board-u5500.h
@@ -0,0 +1,21 @@
+/*
+ * Copyright (C) ST-Ericsson SA 2010
+ *
+ * License terms: GNU General Public License (GPL) version 2
+ */
+
+#ifndef __MACH_IRQS_BOARD_U5500_H
+#define __MACH_IRQS_BOARD_U5500_H
+
+#define AB5500_NR_IRQS 5
+#define IRQ_AB5500_BASE IRQ_BOARD_START
+#define IRQ_AB5500_END (IRQ_AB5500_BASE + AB5500_NR_IRQS)
+
+#define U5500_IRQ_END IRQ_AB5500_END
+
+#if IRQ_BOARD_END < U5500_IRQ_END
+#undef IRQ_BOARD_END
+#define IRQ_BOARD_END U5500_IRQ_END
+#endif
+
+#endif
diff --git a/arch/arm/mach-ux500/include/mach/irqs-db5500.h b/arch/arm/mach-ux500/include/mach/irqs-db5500.h
index bfa123dbec3b..77239776a6f2 100644
--- a/arch/arm/mach-ux500/include/mach/irqs-db5500.h
+++ b/arch/arm/mach-ux500/include/mach/irqs-db5500.h
@@ -83,4 +83,31 @@
#define IRQ_DB5500_GPIO6 (IRQ_SHPI_START + 125)
#define IRQ_DB5500_GPIO7 (IRQ_SHPI_START + 126)
+#ifdef CONFIG_UX500_SOC_DB5500
+
+/*
+ * After the GPIO ones we reserve a range of IRQ:s in which virtual
+ * IRQ:s representing modem IRQ:s can be allocated
+ */
+#define IRQ_MODEM_EVENTS_BASE IRQ_SOC_START
+#define IRQ_MODEM_EVENTS_NBR 72
+#define IRQ_MODEM_EVENTS_END (IRQ_MODEM_EVENTS_BASE + IRQ_MODEM_EVENTS_NBR)
+
+/* List of virtual IRQ:s that are allocated from the range above */
+#define MBOX_PAIR0_VIRT_IRQ (IRQ_MODEM_EVENTS_BASE + 43)
+#define MBOX_PAIR1_VIRT_IRQ (IRQ_MODEM_EVENTS_BASE + 45)
+#define MBOX_PAIR2_VIRT_IRQ (IRQ_MODEM_EVENTS_BASE + 41)
+
+/*
+ * We may have several SoCs, but only one will run at a
+ * time, so the one with most IRQs will bump this ahead,
+ * but the IRQ_SOC_START remains the same for either SoC.
+ */
+#if IRQ_SOC_END < IRQ_MODEM_EVENTS_END
+#undef IRQ_SOC_END
+#define IRQ_SOC_END IRQ_MODEM_EVENTS_END
+#endif
+
+#endif /* CONFIG_UX500_SOC_DB5500 */
+
#endif
diff --git a/arch/arm/mach-ux500/include/mach/irqs-db8500.h b/arch/arm/mach-ux500/include/mach/irqs-db8500.h
index 8b5d9f0a1633..68bc14974608 100644
--- a/arch/arm/mach-ux500/include/mach/irqs-db8500.h
+++ b/arch/arm/mach-ux500/include/mach/irqs-db8500.h
@@ -93,4 +93,58 @@
#define IRQ_DB8500_GPIO7 (IRQ_SHPI_START + 126)
#define IRQ_DB8500_GPIO8 (IRQ_SHPI_START + 127)
+#define IRQ_CA_WAKE_REQ_ED (IRQ_SHPI_START + 71)
+#define IRQ_AC_READ_NOTIFICATION_0_ED (IRQ_SHPI_START + 66)
+#define IRQ_AC_READ_NOTIFICATION_1_ED (IRQ_SHPI_START + 64)
+#define IRQ_CA_MSG_PEND_NOTIFICATION_0_ED (IRQ_SHPI_START + 67)
+#define IRQ_CA_MSG_PEND_NOTIFICATION_1_ED (IRQ_SHPI_START + 65)
+
+#define IRQ_CA_WAKE_REQ_V1 (IRQ_SHPI_START + 83)
+#define IRQ_AC_READ_NOTIFICATION_0_V1 (IRQ_SHPI_START + 78)
+#define IRQ_AC_READ_NOTIFICATION_1_V1 (IRQ_SHPI_START + 76)
+#define IRQ_CA_MSG_PEND_NOTIFICATION_0_V1 (IRQ_SHPI_START + 79)
+#define IRQ_CA_MSG_PEND_NOTIFICATION_1_V1 (IRQ_SHPI_START + 77)
+
+#ifdef CONFIG_UX500_SOC_DB8500
+
+/* Virtual interrupts corresponding to the PRCMU wakeups. */
+#define IRQ_PRCMU_BASE IRQ_SOC_START
+#define NUM_PRCMU_WAKEUPS (IRQ_PRCMU_END - IRQ_PRCMU_BASE)
+
+#define IRQ_PRCMU_RTC (IRQ_PRCMU_BASE)
+#define IRQ_PRCMU_RTT0 (IRQ_PRCMU_BASE + 1)
+#define IRQ_PRCMU_RTT1 (IRQ_PRCMU_BASE + 2)
+#define IRQ_PRCMU_HSI0 (IRQ_PRCMU_BASE + 3)
+#define IRQ_PRCMU_HSI1 (IRQ_PRCMU_BASE + 4)
+#define IRQ_PRCMU_CA_WAKE (IRQ_PRCMU_BASE + 5)
+#define IRQ_PRCMU_USB (IRQ_PRCMU_BASE + 6)
+#define IRQ_PRCMU_ABB (IRQ_PRCMU_BASE + 7)
+#define IRQ_PRCMU_ABB_FIFO (IRQ_PRCMU_BASE + 8)
+#define IRQ_PRCMU_ARM (IRQ_PRCMU_BASE + 9)
+#define IRQ_PRCMU_MODEM_SW_RESET_REQ (IRQ_PRCMU_BASE + 10)
+#define IRQ_PRCMU_GPIO0 (IRQ_PRCMU_BASE + 11)
+#define IRQ_PRCMU_GPIO1 (IRQ_PRCMU_BASE + 12)
+#define IRQ_PRCMU_GPIO2 (IRQ_PRCMU_BASE + 13)
+#define IRQ_PRCMU_GPIO3 (IRQ_PRCMU_BASE + 14)
+#define IRQ_PRCMU_GPIO4 (IRQ_PRCMU_BASE + 15)
+#define IRQ_PRCMU_GPIO5 (IRQ_PRCMU_BASE + 16)
+#define IRQ_PRCMU_GPIO6 (IRQ_PRCMU_BASE + 17)
+#define IRQ_PRCMU_GPIO7 (IRQ_PRCMU_BASE + 18)
+#define IRQ_PRCMU_GPIO8 (IRQ_PRCMU_BASE + 19)
+#define IRQ_PRCMU_CA_SLEEP (IRQ_PRCMU_BASE + 20)
+#define IRQ_PRCMU_HOTMON_LOW (IRQ_PRCMU_BASE + 21)
+#define IRQ_PRCMU_HOTMON_HIGH (IRQ_PRCMU_BASE + 22)
+#define IRQ_PRCMU_END (IRQ_PRCMU_BASE + 23)
+
+/*
+ * We may have several SoCs, but only one will run at a
+ * time, so the one with most IRQs will bump this ahead,
+ * but the IRQ_SOC_START remains the same for either SoC.
+ */
+#if IRQ_SOC_END < IRQ_PRCMU_END
+#undef IRQ_SOC_END
+#define IRQ_SOC_END IRQ_PRCMU_END
+#endif
+
+#endif /* CONFIG_UX500_SOC_DB8500 */
#endif
diff --git a/arch/arm/mach-ux500/include/mach/irqs.h b/arch/arm/mach-ux500/include/mach/irqs.h
index ba1294c13c4d..9db68d264c5f 100644
--- a/arch/arm/mach-ux500/include/mach/irqs.h
+++ b/arch/arm/mach-ux500/include/mach/irqs.h
@@ -10,49 +10,47 @@
#ifndef ASM_ARCH_IRQS_H
#define ASM_ARCH_IRQS_H
-#include <mach/irqs-db5500.h>
-#include <mach/irqs-db8500.h>
+#include <mach/hardware.h>
-#define IRQ_LOCALTIMER 29
-#define IRQ_LOCALWDOG 30
+#define IRQ_LOCALTIMER 29
+#define IRQ_LOCALWDOG 30
/* Shared Peripheral Interrupt (SHPI) */
#define IRQ_SHPI_START 32
-/* Interrupt numbers generic for shared peripheral */
+/*
+ * MTU0 preserved for now until plat-nomadik is taught not to use it. Don't
+ * add any other IRQs here, use the irqs-dbx500.h files.
+ */
#define IRQ_MTU0 (IRQ_SHPI_START + 4)
-/* There are 128 shared peripheral interrupts assigned to
- * INTID[160:32]. The first 32 interrupts are reserved.
- */
-#define DBX500_NR_INTERNAL_IRQS 161
+#define DBX500_NR_INTERNAL_IRQS 160
/* After chip-specific IRQ numbers we have the GPIO ones */
#define NOMADIK_NR_GPIO 288
#define NOMADIK_GPIO_TO_IRQ(gpio) ((gpio) + DBX500_NR_INTERNAL_IRQS)
#define NOMADIK_IRQ_TO_GPIO(irq) ((irq) - DBX500_NR_INTERNAL_IRQS)
-#define IRQ_BOARD_START NOMADIK_GPIO_TO_IRQ(NOMADIK_NR_GPIO)
+#define IRQ_GPIO_END NOMADIK_GPIO_TO_IRQ(NOMADIK_NR_GPIO)
+
+#define IRQ_SOC_START IRQ_GPIO_END
+/* This will be overridden by SoC-specific irq headers */
+#define IRQ_SOC_END IRQ_SOC_START
+#include <mach/irqs-db5500.h>
+#include <mach/irqs-db8500.h>
+
+#define IRQ_BOARD_START IRQ_SOC_END
/* This will be overridden by board-specific irq headers */
-#define IRQ_BOARD_END IRQ_BOARD_START
+#define IRQ_BOARD_END IRQ_BOARD_START
#ifdef CONFIG_MACH_U8500
#include <mach/irqs-board-mop500.h>
#endif
-/*
- * After the board specific IRQ:s we reserve a range of IRQ:s in which virtual
- * IRQ:s representing modem IRQ:s can be allocated
- */
-#define IRQ_MODEM_EVENTS_BASE (IRQ_BOARD_END + 1)
-#define IRQ_MODEM_EVENTS_NBR 72
-#define IRQ_MODEM_EVENTS_END (IRQ_MODEM_EVENTS_BASE + IRQ_MODEM_EVENTS_NBR)
-
-/* List of virtual IRQ:s that are allocated from the range above */
-#define MBOX_PAIR0_VIRT_IRQ (IRQ_MODEM_EVENTS_BASE + 43)
-#define MBOX_PAIR1_VIRT_IRQ (IRQ_MODEM_EVENTS_BASE + 45)
-#define MBOX_PAIR2_VIRT_IRQ (IRQ_MODEM_EVENTS_BASE + 41)
+#ifdef CONFIG_MACH_U5500
+#include <mach/irqs-board-u5500.h>
+#endif
-#define NR_IRQS IRQ_MODEM_EVENTS_END
+#define NR_IRQS IRQ_BOARD_END
#endif /* ASM_ARCH_IRQS_H */
diff --git a/arch/arm/mach-ux500/include/mach/prcmu-defs.h b/arch/arm/mach-ux500/include/mach/prcmu-defs.h
deleted file mode 100644
index 848ba64b561f..000000000000
--- a/arch/arm/mach-ux500/include/mach/prcmu-defs.h
+++ /dev/null
@@ -1,30 +0,0 @@
-/*
- * Copyright (C) STMicroelectronics 2009
- * Copyright (C) ST-Ericsson SA 2010
- *
- * Author: Sundar Iyer <sundar.iyer@stericsson.com>
- * Author: Martin Persson <martin.persson@stericsson.com>
- *
- * License Terms: GNU General Public License v2
- *
- * PRCM Unit definitions
- */
-
-#ifndef __MACH_PRCMU_DEFS_H
-#define __MACH_PRCMU_DEFS_H
-
-enum prcmu_cpu_opp {
- CPU_OPP_INIT = 0x00,
- CPU_OPP_NO_CHANGE = 0x01,
- CPU_OPP_100 = 0x02,
- CPU_OPP_50 = 0x03,
- CPU_OPP_MAX = 0x04,
- CPU_OPP_EXT_CLK = 0x07
-};
-enum prcmu_ape_opp {
- APE_OPP_NO_CHANGE = 0x00,
- APE_OPP_100 = 0x02,
- APE_OPP_50 = 0x03,
-};
-
-#endif /* __MACH_PRCMU_DEFS_H */
diff --git a/arch/arm/mach-ux500/include/mach/prcmu-regs.h b/arch/arm/mach-ux500/include/mach/prcmu-regs.h
deleted file mode 100644
index 455467e88791..000000000000
--- a/arch/arm/mach-ux500/include/mach/prcmu-regs.h
+++ /dev/null
@@ -1,96 +0,0 @@
-/*
- * Copyright (C) STMicroelectronics 2009
- * Copyright (C) ST-Ericsson SA 2010
- *
- * Author: Kumar Sanghvi <kumar.sanghvi@stericsson.com>
- * Author: Sundar Iyer <sundar.iyer@stericsson.com>
- *
- * License Terms: GNU General Public License v2
- *
- * PRCM Unit registers
- */
-
-#ifndef __MACH_PRCMU_REGS_H
-#define __MACH_PRCMU_REGS_H
-
-#include <mach/hardware.h>
-
-#define _PRCMU_BASE IO_ADDRESS(U8500_PRCMU_BASE)
-
-#define PRCM_ARM_PLLDIVPS (_PRCMU_BASE + 0x118)
-#define PRCM_ARM_CHGCLKREQ (_PRCMU_BASE + 0x114)
-#define PRCM_PLLARM_ENABLE (_PRCMU_BASE + 0x98)
-#define PRCM_ARMCLKFIX_MGT (_PRCMU_BASE + 0x0)
-#define PRCM_A9_RESETN_CLR (_PRCMU_BASE + 0x1f4)
-#define PRCM_A9_RESETN_SET (_PRCMU_BASE + 0x1f0)
-#define PRCM_ARM_LS_CLAMP (_PRCMU_BASE + 0x30c)
-#define PRCM_SRAM_A9 (_PRCMU_BASE + 0x308)
-
-/* ARM WFI Standby signal register */
-#define PRCM_ARM_WFI_STANDBY (_PRCMU_BASE + 0x130)
-#define PRCMU_IOCR (_PRCMU_BASE + 0x310)
-
-/* CPU mailbox registers */
-#define PRCM_MBOX_CPU_VAL (_PRCMU_BASE + 0x0fc)
-#define PRCM_MBOX_CPU_SET (_PRCMU_BASE + 0x100)
-#define PRCM_MBOX_CPU_CLR (_PRCMU_BASE + 0x104)
-
-/* Dual A9 core interrupt management unit registers */
-#define PRCM_A9_MASK_REQ (_PRCMU_BASE + 0x328)
-#define PRCM_A9_MASK_ACK (_PRCMU_BASE + 0x32c)
-#define PRCM_ARMITMSK31TO0 (_PRCMU_BASE + 0x11c)
-#define PRCM_ARMITMSK63TO32 (_PRCMU_BASE + 0x120)
-#define PRCM_ARMITMSK95TO64 (_PRCMU_BASE + 0x124)
-#define PRCM_ARMITMSK127TO96 (_PRCMU_BASE + 0x128)
-#define PRCM_POWER_STATE_VAL (_PRCMU_BASE + 0x25C)
-#define PRCM_ARMITVAL31TO0 (_PRCMU_BASE + 0x260)
-#define PRCM_ARMITVAL63TO32 (_PRCMU_BASE + 0x264)
-#define PRCM_ARMITVAL95TO64 (_PRCMU_BASE + 0x268)
-#define PRCM_ARMITVAL127TO96 (_PRCMU_BASE + 0x26C)
-
-#define PRCM_HOSTACCESS_REQ (_PRCMU_BASE + 0x334)
-#define ARM_WAKEUP_MODEM 0x1
-
-#define PRCM_ARM_IT1_CLEAR (_PRCMU_BASE + 0x48C)
-#define PRCM_ARM_IT1_VAL (_PRCMU_BASE + 0x494)
-#define PRCM_HOLD_EVT (_PRCMU_BASE + 0x174)
-
-#define PRCM_ITSTATUS0 (_PRCMU_BASE + 0x148)
-#define PRCM_ITSTATUS1 (_PRCMU_BASE + 0x150)
-#define PRCM_ITSTATUS2 (_PRCMU_BASE + 0x158)
-#define PRCM_ITSTATUS3 (_PRCMU_BASE + 0x160)
-#define PRCM_ITSTATUS4 (_PRCMU_BASE + 0x168)
-#define PRCM_ITSTATUS5 (_PRCMU_BASE + 0x484)
-#define PRCM_ITCLEAR5 (_PRCMU_BASE + 0x488)
-#define PRCM_ARMIT_MASKXP70_IT (_PRCMU_BASE + 0x1018)
-
-/* System reset register */
-#define PRCM_APE_SOFTRST (_PRCMU_BASE + 0x228)
-
-/* Level shifter and clamp control registers */
-#define PRCM_MMIP_LS_CLAMP_SET (_PRCMU_BASE + 0x420)
-#define PRCM_MMIP_LS_CLAMP_CLR (_PRCMU_BASE + 0x424)
-
-/* PRCMU clock/PLL/reset registers */
-#define PRCM_PLLDSI_FREQ (_PRCMU_BASE + 0x500)
-#define PRCM_PLLDSI_ENABLE (_PRCMU_BASE + 0x504)
-#define PRCM_LCDCLK_MGT (_PRCMU_BASE + 0x044)
-#define PRCM_MCDECLK_MGT (_PRCMU_BASE + 0x064)
-#define PRCM_HDMICLK_MGT (_PRCMU_BASE + 0x058)
-#define PRCM_TVCLK_MGT (_PRCMU_BASE + 0x07c)
-#define PRCM_DSI_PLLOUT_SEL (_PRCMU_BASE + 0x530)
-#define PRCM_DSITVCLK_DIV (_PRCMU_BASE + 0x52C)
-#define PRCM_APE_RESETN_SET (_PRCMU_BASE + 0x1E4)
-#define PRCM_APE_RESETN_CLR (_PRCMU_BASE + 0x1E8)
-
-/* ePOD and memory power signal control registers */
-#define PRCM_EPOD_C_SET (_PRCMU_BASE + 0x410)
-#define PRCM_SRAM_LS_SLEEP (_PRCMU_BASE + 0x304)
-
-/* Debug power control unit registers */
-#define PRCM_POWER_STATE_SET (_PRCMU_BASE + 0x254)
-
-/* Miscellaneous unit registers */
-#define PRCM_DSI_SW_RESET (_PRCMU_BASE + 0x324)
-
-#endif /* __MACH_PRCMU_REGS_H */
diff --git a/arch/arm/mach-ux500/include/mach/prcmu.h b/arch/arm/mach-ux500/include/mach/prcmu.h
deleted file mode 100644
index c49e456162ef..000000000000
--- a/arch/arm/mach-ux500/include/mach/prcmu.h
+++ /dev/null
@@ -1,28 +0,0 @@
-/*
- * Copyright (C) STMicroelectronics 2009
- * Copyright (C) ST-Ericsson SA 2010
- *
- * Author: Kumar Sanghvi <kumar.sanghvi@stericsson.com>
- * Author: Sundar Iyer <sundar.iyer@stericsson.com>
- * Author: Mattias Nilsson <mattias.i.nilsson@stericsson.com>
- *
- * License Terms: GNU General Public License v2
- *
- * PRCM Unit f/w API
- */
-#ifndef __MACH_PRCMU_H
-#define __MACH_PRCMU_H
-#include <mach/prcmu-defs.h>
-
-void __init prcmu_early_init(void);
-int prcmu_abb_read(u8 slave, u8 reg, u8 *value, u8 size);
-int prcmu_abb_write(u8 slave, u8 reg, u8 *value, u8 size);
-int prcmu_set_ape_opp(enum prcmu_ape_opp opp);
-int prcmu_set_cpu_opp(enum prcmu_cpu_opp opp);
-int prcmu_set_ape_cpu_opps(enum prcmu_ape_opp ape_opp,
- enum prcmu_cpu_opp cpu_opp);
-int prcmu_get_ape_opp(void);
-int prcmu_get_cpu_opp(void);
-bool prcmu_has_arm_maxopp(void);
-
-#endif /* __MACH_PRCMU_H */
diff --git a/arch/arm/mach-ux500/prcmu.c b/arch/arm/mach-ux500/prcmu.c
deleted file mode 100644
index c522d26ef348..000000000000
--- a/arch/arm/mach-ux500/prcmu.c
+++ /dev/null
@@ -1,394 +0,0 @@
-/*
- * Copyright (C) STMicroelectronics 2009
- * Copyright (C) ST-Ericsson SA 2010
- *
- * License Terms: GNU General Public License v2
- * Author: Kumar Sanghvi <kumar.sanghvi@stericsson.com>
- * Author: Sundar Iyer <sundar.iyer@stericsson.com>
- * Author: Mattias Nilsson <mattias.i.nilsson@stericsson.com>
- *
- * U8500 PRCM Unit interface driver
- *
- */
-#include <linux/kernel.h>
-#include <linux/module.h>
-#include <linux/errno.h>
-#include <linux/err.h>
-#include <linux/io.h>
-#include <linux/mutex.h>
-#include <linux/completion.h>
-#include <linux/jiffies.h>
-#include <linux/bitops.h>
-#include <linux/interrupt.h>
-
-#include <mach/hardware.h>
-#include <mach/prcmu-regs.h>
-#include <mach/prcmu-defs.h>
-
-/* Global var to runtime determine TCDM base for v2 or v1 */
-static __iomem void *tcdm_base;
-
-#define _MBOX_HEADER (tcdm_base + 0xFE8)
-#define MBOX_HEADER_REQ_MB0 (_MBOX_HEADER + 0x0)
-
-#define REQ_MB1 (tcdm_base + 0xFD0)
-#define REQ_MB5 (tcdm_base + 0xE44)
-
-#define REQ_MB1_ARMOPP (REQ_MB1 + 0x0)
-#define REQ_MB1_APEOPP (REQ_MB1 + 0x1)
-#define REQ_MB1_BOOSTOPP (REQ_MB1 + 0x2)
-
-#define ACK_MB1 (tcdm_base + 0xE04)
-#define ACK_MB5 (tcdm_base + 0xDF4)
-
-#define ACK_MB1_CURR_ARMOPP (ACK_MB1 + 0x0)
-#define ACK_MB1_CURR_APEOPP (ACK_MB1 + 0x1)
-
-#define REQ_MB5_I2C_SLAVE_OP (REQ_MB5)
-#define REQ_MB5_I2C_HW_BITS (REQ_MB5 + 1)
-#define REQ_MB5_I2C_REG (REQ_MB5 + 2)
-#define REQ_MB5_I2C_VAL (REQ_MB5 + 3)
-
-#define ACK_MB5_I2C_STATUS (ACK_MB5 + 1)
-#define ACK_MB5_I2C_VAL (ACK_MB5 + 3)
-
-#define PRCM_AVS_VARM_MAX_OPP (tcdm_base + 0x2E4)
-#define PRCM_AVS_ISMODEENABLE 7
-#define PRCM_AVS_ISMODEENABLE_MASK (1 << PRCM_AVS_ISMODEENABLE)
-
-#define I2C_WRITE(slave) \
- (((slave) << 1) | (cpu_is_u8500v2() ? BIT(6) : 0))
-#define I2C_READ(slave) \
- (((slave) << 1) | (cpu_is_u8500v2() ? BIT(6) : 0) | BIT(0))
-#define I2C_STOP_EN BIT(3)
-
-enum mb1_h {
- MB1H_ARM_OPP = 1,
- MB1H_APE_OPP,
- MB1H_ARM_APE_OPP,
-};
-
-static struct {
- struct mutex lock;
- struct completion work;
- struct {
- u8 arm_opp;
- u8 ape_opp;
- u8 arm_status;
- u8 ape_status;
- } ack;
-} mb1_transfer;
-
-enum ack_mb5_status {
- I2C_WR_OK = 0x01,
- I2C_RD_OK = 0x02,
-};
-
-#define MBOX_BIT BIT
-#define NUM_MBOX 8
-
-static struct {
- struct mutex lock;
- struct completion work;
- bool failed;
- struct {
- u8 status;
- u8 value;
- } ack;
-} mb5_transfer;
-
-/**
- * prcmu_abb_read() - Read register value(s) from the ABB.
- * @slave: The I2C slave address.
- * @reg: The (start) register address.
- * @value: The read out value(s).
- * @size: The number of registers to read.
- *
- * Reads register value(s) from the ABB.
- * @size has to be 1 for the current firmware version.
- */
-int prcmu_abb_read(u8 slave, u8 reg, u8 *value, u8 size)
-{
- int r;
-
- if (size != 1)
- return -EINVAL;
-
- r = mutex_lock_interruptible(&mb5_transfer.lock);
- if (r)
- return r;
-
- while (readl(PRCM_MBOX_CPU_VAL) & MBOX_BIT(5))
- cpu_relax();
-
- writeb(I2C_READ(slave), REQ_MB5_I2C_SLAVE_OP);
- writeb(I2C_STOP_EN, REQ_MB5_I2C_HW_BITS);
- writeb(reg, REQ_MB5_I2C_REG);
-
- writel(MBOX_BIT(5), PRCM_MBOX_CPU_SET);
- if (!wait_for_completion_timeout(&mb5_transfer.work,
- msecs_to_jiffies(500))) {
- pr_err("prcmu: prcmu_abb_read timed out.\n");
- r = -EIO;
- goto unlock_and_return;
- }
- r = ((mb5_transfer.ack.status == I2C_RD_OK) ? 0 : -EIO);
- if (!r)
- *value = mb5_transfer.ack.value;
-
-unlock_and_return:
- mutex_unlock(&mb5_transfer.lock);
- return r;
-}
-EXPORT_SYMBOL(prcmu_abb_read);
-
-/**
- * prcmu_abb_write() - Write register value(s) to the ABB.
- * @slave: The I2C slave address.
- * @reg: The (start) register address.
- * @value: The value(s) to write.
- * @size: The number of registers to write.
- *
- * Reads register value(s) from the ABB.
- * @size has to be 1 for the current firmware version.
- */
-int prcmu_abb_write(u8 slave, u8 reg, u8 *value, u8 size)
-{
- int r;
-
- if (size != 1)
- return -EINVAL;
-
- r = mutex_lock_interruptible(&mb5_transfer.lock);
- if (r)
- return r;
-
-
- while (readl(PRCM_MBOX_CPU_VAL) & MBOX_BIT(5))
- cpu_relax();
-
- writeb(I2C_WRITE(slave), REQ_MB5_I2C_SLAVE_OP);
- writeb(I2C_STOP_EN, REQ_MB5_I2C_HW_BITS);
- writeb(reg, REQ_MB5_I2C_REG);
- writeb(*value, REQ_MB5_I2C_VAL);
-
- writel(MBOX_BIT(5), PRCM_MBOX_CPU_SET);
- if (!wait_for_completion_timeout(&mb5_transfer.work,
- msecs_to_jiffies(500))) {
- pr_err("prcmu: prcmu_abb_write timed out.\n");
- r = -EIO;
- goto unlock_and_return;
- }
- r = ((mb5_transfer.ack.status == I2C_WR_OK) ? 0 : -EIO);
-
-unlock_and_return:
- mutex_unlock(&mb5_transfer.lock);
- return r;
-}
-EXPORT_SYMBOL(prcmu_abb_write);
-
-static int set_ape_cpu_opps(u8 header, enum prcmu_ape_opp ape_opp,
- enum prcmu_cpu_opp cpu_opp)
-{
- bool do_ape;
- bool do_arm;
- int err = 0;
-
- do_ape = ((header == MB1H_APE_OPP) || (header == MB1H_ARM_APE_OPP));
- do_arm = ((header == MB1H_ARM_OPP) || (header == MB1H_ARM_APE_OPP));
-
- mutex_lock(&mb1_transfer.lock);
-
- while (readl(PRCM_MBOX_CPU_VAL) & MBOX_BIT(1))
- cpu_relax();
-
- writeb(0, MBOX_HEADER_REQ_MB0);
- writeb(cpu_opp, REQ_MB1_ARMOPP);
- writeb(ape_opp, REQ_MB1_APEOPP);
- writeb(0, REQ_MB1_BOOSTOPP);
- writel(MBOX_BIT(1), PRCM_MBOX_CPU_SET);
- wait_for_completion(&mb1_transfer.work);
- if ((do_ape) && (mb1_transfer.ack.ape_status != 0))
- err = -EIO;
- if ((do_arm) && (mb1_transfer.ack.arm_status != 0))
- err = -EIO;
-
- mutex_unlock(&mb1_transfer.lock);
-
- return err;
-}
-
-/**
- * prcmu_set_ape_opp() - Set the OPP of the APE.
- * @opp: The OPP to set.
- *
- * This function sets the OPP of the APE.
- */
-int prcmu_set_ape_opp(enum prcmu_ape_opp opp)
-{
- return set_ape_cpu_opps(MB1H_APE_OPP, opp, APE_OPP_NO_CHANGE);
-}
-EXPORT_SYMBOL(prcmu_set_ape_opp);
-
-/**
- * prcmu_set_cpu_opp() - Set the OPP of the CPU.
- * @opp: The OPP to set.
- *
- * This function sets the OPP of the CPU.
- */
-int prcmu_set_cpu_opp(enum prcmu_cpu_opp opp)
-{
- return set_ape_cpu_opps(MB1H_ARM_OPP, CPU_OPP_NO_CHANGE, opp);
-}
-EXPORT_SYMBOL(prcmu_set_cpu_opp);
-
-/**
- * prcmu_set_ape_cpu_opps() - Set the OPPs of the APE and the CPU.
- * @ape_opp: The APE OPP to set.
- * @cpu_opp: The CPU OPP to set.
- *
- * This function sets the OPPs of the APE and the CPU.
- */
-int prcmu_set_ape_cpu_opps(enum prcmu_ape_opp ape_opp,
- enum prcmu_cpu_opp cpu_opp)
-{
- return set_ape_cpu_opps(MB1H_ARM_APE_OPP, ape_opp, cpu_opp);
-}
-EXPORT_SYMBOL(prcmu_set_ape_cpu_opps);
-
-/**
- * prcmu_get_ape_opp() - Get the OPP of the APE.
- *
- * This function gets the OPP of the APE.
- */
-enum prcmu_ape_opp prcmu_get_ape_opp(void)
-{
- return readb(ACK_MB1_CURR_APEOPP);
-}
-EXPORT_SYMBOL(prcmu_get_ape_opp);
-
-/**
- * prcmu_get_cpu_opp() - Get the OPP of the CPU.
- *
- * This function gets the OPP of the CPU. The OPP is specified in %%.
- * PRCMU_OPP_EXT is a special OPP value, not specified in %%.
- */
-int prcmu_get_cpu_opp(void)
-{
- return readb(ACK_MB1_CURR_ARMOPP);
-}
-EXPORT_SYMBOL(prcmu_get_cpu_opp);
-
-bool prcmu_has_arm_maxopp(void)
-{
- return (readb(PRCM_AVS_VARM_MAX_OPP) & PRCM_AVS_ISMODEENABLE_MASK)
- == PRCM_AVS_ISMODEENABLE_MASK;
-}
-
-static void read_mailbox_0(void)
-{
- writel(MBOX_BIT(0), PRCM_ARM_IT1_CLEAR);
-}
-
-static void read_mailbox_1(void)
-{
- mb1_transfer.ack.arm_opp = readb(ACK_MB1_CURR_ARMOPP);
- mb1_transfer.ack.ape_opp = readb(ACK_MB1_CURR_APEOPP);
- complete(&mb1_transfer.work);
- writel(MBOX_BIT(1), PRCM_ARM_IT1_CLEAR);
-}
-
-static void read_mailbox_2(void)
-{
- writel(MBOX_BIT(2), PRCM_ARM_IT1_CLEAR);
-}
-
-static void read_mailbox_3(void)
-{
- writel(MBOX_BIT(3), PRCM_ARM_IT1_CLEAR);
-}
-
-static void read_mailbox_4(void)
-{
- writel(MBOX_BIT(4), PRCM_ARM_IT1_CLEAR);
-}
-
-static void read_mailbox_5(void)
-{
- mb5_transfer.ack.status = readb(ACK_MB5_I2C_STATUS);
- mb5_transfer.ack.value = readb(ACK_MB5_I2C_VAL);
- complete(&mb5_transfer.work);
- writel(MBOX_BIT(5), PRCM_ARM_IT1_CLEAR);
-}
-
-static void read_mailbox_6(void)
-{
- writel(MBOX_BIT(6), PRCM_ARM_IT1_CLEAR);
-}
-
-static void read_mailbox_7(void)
-{
- writel(MBOX_BIT(7), PRCM_ARM_IT1_CLEAR);
-}
-
-static void (* const read_mailbox[NUM_MBOX])(void) = {
- read_mailbox_0,
- read_mailbox_1,
- read_mailbox_2,
- read_mailbox_3,
- read_mailbox_4,
- read_mailbox_5,
- read_mailbox_6,
- read_mailbox_7
-};
-
-static irqreturn_t prcmu_irq_handler(int irq, void *data)
-{
- u32 bits;
- u8 n;
-
- bits = (readl(PRCM_ARM_IT1_VAL) & (MBOX_BIT(NUM_MBOX) - 1));
- if (unlikely(!bits))
- return IRQ_NONE;
-
- for (n = 0; bits; n++) {
- if (bits & MBOX_BIT(n)) {
- bits -= MBOX_BIT(n);
- read_mailbox[n]();
- }
- }
- return IRQ_HANDLED;
-}
-
-void __init prcmu_early_init(void)
-{
- if (cpu_is_u8500v11() || cpu_is_u8500ed()) {
- tcdm_base = __io_address(U8500_PRCMU_TCDM_BASE_V1);
- } else if (cpu_is_u8500v2()) {
- tcdm_base = __io_address(U8500_PRCMU_TCDM_BASE);
- } else {
- pr_err("prcmu: Unsupported chip version\n");
- BUG();
- }
-}
-
-static int __init prcmu_init(void)
-{
- if (cpu_is_u8500ed()) {
- pr_err("prcmu: Unsupported chip version\n");
- return 0;
- }
-
- mutex_init(&mb1_transfer.lock);
- init_completion(&mb1_transfer.work);
- mutex_init(&mb5_transfer.lock);
- init_completion(&mb5_transfer.work);
-
- /* Clean up the mailbox interrupts after pre-kernel code. */
- writel((MBOX_BIT(NUM_MBOX) - 1), PRCM_ARM_IT1_CLEAR);
-
- return request_irq(IRQ_DB8500_PRCMU1, prcmu_irq_handler, 0,
- "prcmu", NULL);
-}
-
-arch_initcall(prcmu_init);
diff --git a/arch/arm/mm/cache-v6.S b/arch/arm/mm/cache-v6.S
index c96fa1b3f49f..73b4a8b66a57 100644
--- a/arch/arm/mm/cache-v6.S
+++ b/arch/arm/mm/cache-v6.S
@@ -176,6 +176,7 @@ ENDPROC(v6_coherent_kern_range)
*/
ENTRY(v6_flush_kern_dcache_area)
add r1, r0, r1
+ bic r0, r0, #D_CACHE_LINE_SIZE - 1
1:
#ifdef HARVARD_CACHE
mcr p15, 0, r0, c7, c14, 1 @ clean & invalidate D line
diff --git a/arch/arm/mm/cache-v7.S b/arch/arm/mm/cache-v7.S
index dc18d81ef8ce..d32f02b61866 100644
--- a/arch/arm/mm/cache-v7.S
+++ b/arch/arm/mm/cache-v7.S
@@ -221,6 +221,8 @@ ENDPROC(v7_coherent_user_range)
ENTRY(v7_flush_kern_dcache_area)
dcache_line_size r2, r3
add r1, r0, r1
+ sub r3, r2, #1
+ bic r0, r0, r3
1:
mcr p15, 0, r0, c7, c14, 1 @ clean & invalidate D line / unified line
add r0, r0, r2
diff --git a/arch/arm/mm/context.c b/arch/arm/mm/context.c
index b0ee9ba3cfab..8bfae964b133 100644
--- a/arch/arm/mm/context.c
+++ b/arch/arm/mm/context.c
@@ -24,9 +24,7 @@ DEFINE_PER_CPU(struct mm_struct *, current_mm);
/*
* We fork()ed a process, and we need a new context for the child
- * to run in. We reserve version 0 for initial tasks so we will
- * always allocate an ASID. The ASID 0 is reserved for the TTBR
- * register changing sequence.
+ * to run in.
*/
void __init_new_context(struct task_struct *tsk, struct mm_struct *mm)
{
@@ -36,8 +34,11 @@ void __init_new_context(struct task_struct *tsk, struct mm_struct *mm)
static void flush_context(void)
{
- /* set the reserved ASID before flushing the TLB */
- asm("mcr p15, 0, %0, c13, c0, 1\n" : : "r" (0));
+ u32 ttb;
+ /* Copy TTBR1 into TTBR0 */
+ asm volatile("mrc p15, 0, %0, c2, c0, 1\n"
+ "mcr p15, 0, %0, c2, c0, 0"
+ : "=r" (ttb));
isb();
local_flush_tlb_all();
if (icache_is_vivt_asid_tagged()) {
@@ -93,7 +94,7 @@ static void reset_context(void *info)
return;
smp_rmb();
- asid = cpu_last_asid + cpu + 1;
+ asid = cpu_last_asid + cpu;
flush_context();
set_mm_context(mm, asid);
@@ -143,13 +144,13 @@ void __new_context(struct mm_struct *mm)
* to start a new version and flush the TLB.
*/
if (unlikely((asid & ~ASID_MASK) == 0)) {
- asid = cpu_last_asid + smp_processor_id() + 1;
+ asid = cpu_last_asid + smp_processor_id();
flush_context();
#ifdef CONFIG_SMP
smp_wmb();
smp_call_function(reset_context, NULL, 1);
#endif
- cpu_last_asid += NR_CPUS;
+ cpu_last_asid += NR_CPUS - 1;
}
set_mm_context(mm, asid);
diff --git a/arch/arm/mm/init.c b/arch/arm/mm/init.c
index 751767279b3e..2c2cce9cd8c8 100644
--- a/arch/arm/mm/init.c
+++ b/arch/arm/mm/init.c
@@ -95,7 +95,7 @@ void show_mem(unsigned int filter)
struct meminfo * mi = &meminfo;
printk("Mem-info:\n");
- show_free_areas();
+ show_free_areas(filter);
for_each_bank (i, mi) {
struct membank *bank = &mi->bank[i];
@@ -283,13 +283,15 @@ static void __init arm_bootmem_free(unsigned long min, unsigned long max_low,
free_area_init_node(0, zone_size, min, zhole_size);
}
-#ifndef CONFIG_SPARSEMEM
+#ifdef CONFIG_HAVE_ARCH_PFN_VALID
int pfn_valid(unsigned long pfn)
{
return memblock_is_memory(pfn << PAGE_SHIFT);
}
EXPORT_SYMBOL(pfn_valid);
+#endif
+#ifndef CONFIG_SPARSEMEM
static void arm_memory_present(void)
{
}
diff --git a/arch/arm/mm/mm.h b/arch/arm/mm/mm.h
index d2384106af9c..5b3d7d543659 100644
--- a/arch/arm/mm/mm.h
+++ b/arch/arm/mm/mm.h
@@ -5,14 +5,9 @@ extern pmd_t *top_pmd;
#define TOP_PTE(x) pte_offset_kernel(top_pmd, x)
-static inline pmd_t *pmd_off(pgd_t *pgd, unsigned long virt)
-{
- return pmd_offset(pud_offset(pgd, virt), virt);
-}
-
static inline pmd_t *pmd_off_k(unsigned long virt)
{
- return pmd_off(pgd_offset_k(virt), virt);
+ return pmd_offset(pud_offset(pgd_offset_k(virt), virt), virt);
}
struct mem_type {
diff --git a/arch/arm/mm/mmu.c b/arch/arm/mm/mmu.c
index 6cf76b3b68d1..9d9e736c2b4f 100644
--- a/arch/arm/mm/mmu.c
+++ b/arch/arm/mm/mmu.c
@@ -31,8 +31,6 @@
#include "mm.h"
-DEFINE_PER_CPU(struct mmu_gather, mmu_gathers);
-
/*
* empty_zero_page is a special page that is used for
* zero-initialized data and COW.
@@ -765,15 +763,12 @@ static void __init sanity_check_meminfo(void)
{
int i, j, highmem = 0;
- lowmem_limit = __pa(vmalloc_min - 1) + 1;
- memblock_set_current_limit(lowmem_limit);
-
for (i = 0, j = 0; i < meminfo.nr_banks; i++) {
struct membank *bank = &meminfo.bank[j];
*bank = meminfo.bank[i];
#ifdef CONFIG_HIGHMEM
- if (__va(bank->start) > vmalloc_min ||
+ if (__va(bank->start) >= vmalloc_min ||
__va(bank->start) < (void *)PAGE_OFFSET)
highmem = 1;
@@ -831,6 +826,9 @@ static void __init sanity_check_meminfo(void)
bank->size = newsize;
}
#endif
+ if (!bank->highmem && bank->start + bank->size > lowmem_limit)
+ lowmem_limit = bank->start + bank->size;
+
j++;
}
#ifdef CONFIG_HIGHMEM
@@ -854,6 +852,7 @@ static void __init sanity_check_meminfo(void)
}
#endif
meminfo.nr_banks = j;
+ memblock_set_current_limit(lowmem_limit);
}
static inline void prepare_page_table(void)
diff --git a/arch/arm/mm/proc-v6.S b/arch/arm/mm/proc-v6.S
index ab17cc0d3fa7..1d2b8451bf25 100644
--- a/arch/arm/mm/proc-v6.S
+++ b/arch/arm/mm/proc-v6.S
@@ -213,7 +213,9 @@ __v6_setup:
mcr p15, 0, r0, c2, c0, 2 @ TTB control register
ALT_SMP(orr r4, r4, #TTB_FLAGS_SMP)
ALT_UP(orr r4, r4, #TTB_FLAGS_UP)
- mcr p15, 0, r4, c2, c0, 1 @ load TTB1
+ ALT_SMP(orr r8, r8, #TTB_FLAGS_SMP)
+ ALT_UP(orr r8, r8, #TTB_FLAGS_UP)
+ mcr p15, 0, r8, c2, c0, 1 @ load TTB1
#endif /* CONFIG_MMU */
adr r5, v6_crval
ldmia r5, {r5, r6}
diff --git a/arch/arm/mm/proc-v7.S b/arch/arm/mm/proc-v7.S
index babfba09c89f..b3b566ec83d3 100644
--- a/arch/arm/mm/proc-v7.S
+++ b/arch/arm/mm/proc-v7.S
@@ -108,18 +108,16 @@ ENTRY(cpu_v7_switch_mm)
#ifdef CONFIG_ARM_ERRATA_430973
mcr p15, 0, r2, c7, c5, 6 @ flush BTAC/BTB
#endif
-#ifdef CONFIG_ARM_ERRATA_754322
- dsb
-#endif
- mcr p15, 0, r2, c13, c0, 1 @ set reserved context ID
- isb
-1: mcr p15, 0, r0, c2, c0, 0 @ set TTB 0
+ mrc p15, 0, r2, c2, c0, 1 @ load TTB 1
+ mcr p15, 0, r2, c2, c0, 0 @ into TTB 0
isb
#ifdef CONFIG_ARM_ERRATA_754322
dsb
#endif
mcr p15, 0, r1, c13, c0, 1 @ set context ID
isb
+ mcr p15, 0, r0, c2, c0, 0 @ set TTB 0
+ isb
#endif
mov pc, lr
ENDPROC(cpu_v7_switch_mm)
@@ -368,7 +366,9 @@ __v7_setup:
mcr p15, 0, r10, c2, c0, 2 @ TTB control register
ALT_SMP(orr r4, r4, #TTB_FLAGS_SMP)
ALT_UP(orr r4, r4, #TTB_FLAGS_UP)
- mcr p15, 0, r4, c2, c0, 1 @ load TTB1
+ ALT_SMP(orr r8, r8, #TTB_FLAGS_SMP)
+ ALT_UP(orr r8, r8, #TTB_FLAGS_UP)
+ mcr p15, 0, r8, c2, c0, 1 @ load TTB1
ldr r5, =PRRR @ PRRR
ldr r6, =NMRR @ NMRR
mcr p15, 0, r5, c10, c2, 0 @ write PRRR
diff --git a/arch/arm/plat-omap/include/plat/display.h b/arch/arm/plat-omap/include/plat/display.h
deleted file mode 100644
index 5e04ddc18fa8..000000000000
--- a/arch/arm/plat-omap/include/plat/display.h
+++ /dev/null
@@ -1,591 +0,0 @@
-/*
- * linux/include/asm-arm/arch-omap/display.h
- *
- * Copyright (C) 2008 Nokia Corporation
- * Author: Tomi Valkeinen <tomi.valkeinen@nokia.com>
- *
- * This program is free software; you can redistribute it and/or modify it
- * under the terms of the GNU General Public License version 2 as published by
- * the Free Software Foundation.
- *
- * This program is distributed in the hope that it will be useful, but WITHOUT
- * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
- * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
- * more details.
- *
- * You should have received a copy of the GNU General Public License along with
- * this program. If not, see <http://www.gnu.org/licenses/>.
- */
-
-#ifndef __ASM_ARCH_OMAP_DISPLAY_H
-#define __ASM_ARCH_OMAP_DISPLAY_H
-
-#include <linux/list.h>
-#include <linux/kobject.h>
-#include <linux/device.h>
-#include <linux/platform_device.h>
-#include <asm/atomic.h>
-
-#define DISPC_IRQ_FRAMEDONE (1 << 0)
-#define DISPC_IRQ_VSYNC (1 << 1)
-#define DISPC_IRQ_EVSYNC_EVEN (1 << 2)
-#define DISPC_IRQ_EVSYNC_ODD (1 << 3)
-#define DISPC_IRQ_ACBIAS_COUNT_STAT (1 << 4)
-#define DISPC_IRQ_PROG_LINE_NUM (1 << 5)
-#define DISPC_IRQ_GFX_FIFO_UNDERFLOW (1 << 6)
-#define DISPC_IRQ_GFX_END_WIN (1 << 7)
-#define DISPC_IRQ_PAL_GAMMA_MASK (1 << 8)
-#define DISPC_IRQ_OCP_ERR (1 << 9)
-#define DISPC_IRQ_VID1_FIFO_UNDERFLOW (1 << 10)
-#define DISPC_IRQ_VID1_END_WIN (1 << 11)
-#define DISPC_IRQ_VID2_FIFO_UNDERFLOW (1 << 12)
-#define DISPC_IRQ_VID2_END_WIN (1 << 13)
-#define DISPC_IRQ_SYNC_LOST (1 << 14)
-#define DISPC_IRQ_SYNC_LOST_DIGIT (1 << 15)
-#define DISPC_IRQ_WAKEUP (1 << 16)
-#define DISPC_IRQ_SYNC_LOST2 (1 << 17)
-#define DISPC_IRQ_VSYNC2 (1 << 18)
-#define DISPC_IRQ_ACBIAS_COUNT_STAT2 (1 << 21)
-#define DISPC_IRQ_FRAMEDONE2 (1 << 22)
-
-struct omap_dss_device;
-struct omap_overlay_manager;
-
-enum omap_display_type {
- OMAP_DISPLAY_TYPE_NONE = 0,
- OMAP_DISPLAY_TYPE_DPI = 1 << 0,
- OMAP_DISPLAY_TYPE_DBI = 1 << 1,
- OMAP_DISPLAY_TYPE_SDI = 1 << 2,
- OMAP_DISPLAY_TYPE_DSI = 1 << 3,
- OMAP_DISPLAY_TYPE_VENC = 1 << 4,
- OMAP_DISPLAY_TYPE_HDMI = 1 << 5,
-};
-
-enum omap_plane {
- OMAP_DSS_GFX = 0,
- OMAP_DSS_VIDEO1 = 1,
- OMAP_DSS_VIDEO2 = 2
-};
-
-enum omap_channel {
- OMAP_DSS_CHANNEL_LCD = 0,
- OMAP_DSS_CHANNEL_DIGIT = 1,
- OMAP_DSS_CHANNEL_LCD2 = 2,
-};
-
-enum omap_color_mode {
- OMAP_DSS_COLOR_CLUT1 = 1 << 0, /* BITMAP 1 */
- OMAP_DSS_COLOR_CLUT2 = 1 << 1, /* BITMAP 2 */
- OMAP_DSS_COLOR_CLUT4 = 1 << 2, /* BITMAP 4 */
- OMAP_DSS_COLOR_CLUT8 = 1 << 3, /* BITMAP 8 */
- OMAP_DSS_COLOR_RGB12U = 1 << 4, /* RGB12, 16-bit container */
- OMAP_DSS_COLOR_ARGB16 = 1 << 5, /* ARGB16 */
- OMAP_DSS_COLOR_RGB16 = 1 << 6, /* RGB16 */
- OMAP_DSS_COLOR_RGB24U = 1 << 7, /* RGB24, 32-bit container */
- OMAP_DSS_COLOR_RGB24P = 1 << 8, /* RGB24, 24-bit container */
- OMAP_DSS_COLOR_YUV2 = 1 << 9, /* YUV2 4:2:2 co-sited */
- OMAP_DSS_COLOR_UYVY = 1 << 10, /* UYVY 4:2:2 co-sited */
- OMAP_DSS_COLOR_ARGB32 = 1 << 11, /* ARGB32 */
- OMAP_DSS_COLOR_RGBA32 = 1 << 12, /* RGBA32 */
- OMAP_DSS_COLOR_RGBX32 = 1 << 13, /* RGBx32 */
-};
-
-enum omap_lcd_display_type {
- OMAP_DSS_LCD_DISPLAY_STN,
- OMAP_DSS_LCD_DISPLAY_TFT,
-};
-
-enum omap_dss_load_mode {
- OMAP_DSS_LOAD_CLUT_AND_FRAME = 0,
- OMAP_DSS_LOAD_CLUT_ONLY = 1,
- OMAP_DSS_LOAD_FRAME_ONLY = 2,
- OMAP_DSS_LOAD_CLUT_ONCE_FRAME = 3,
-};
-
-enum omap_dss_trans_key_type {
- OMAP_DSS_COLOR_KEY_GFX_DST = 0,
- OMAP_DSS_COLOR_KEY_VID_SRC = 1,
-};
-
-enum omap_rfbi_te_mode {
- OMAP_DSS_RFBI_TE_MODE_1 = 1,
- OMAP_DSS_RFBI_TE_MODE_2 = 2,
-};
-
-enum omap_panel_config {
- OMAP_DSS_LCD_IVS = 1<<0,
- OMAP_DSS_LCD_IHS = 1<<1,
- OMAP_DSS_LCD_IPC = 1<<2,
- OMAP_DSS_LCD_IEO = 1<<3,
- OMAP_DSS_LCD_RF = 1<<4,
- OMAP_DSS_LCD_ONOFF = 1<<5,
-
- OMAP_DSS_LCD_TFT = 1<<20,
-};
-
-enum omap_dss_venc_type {
- OMAP_DSS_VENC_TYPE_COMPOSITE,
- OMAP_DSS_VENC_TYPE_SVIDEO,
-};
-
-enum omap_display_caps {
- OMAP_DSS_DISPLAY_CAP_MANUAL_UPDATE = 1 << 0,
- OMAP_DSS_DISPLAY_CAP_TEAR_ELIM = 1 << 1,
-};
-
-enum omap_dss_update_mode {
- OMAP_DSS_UPDATE_DISABLED = 0,
- OMAP_DSS_UPDATE_AUTO,
- OMAP_DSS_UPDATE_MANUAL,
-};
-
-enum omap_dss_display_state {
- OMAP_DSS_DISPLAY_DISABLED = 0,
- OMAP_DSS_DISPLAY_ACTIVE,
- OMAP_DSS_DISPLAY_SUSPENDED,
-};
-
-/* XXX perhaps this should be removed */
-enum omap_dss_overlay_managers {
- OMAP_DSS_OVL_MGR_LCD,
- OMAP_DSS_OVL_MGR_TV,
- OMAP_DSS_OVL_MGR_LCD2,
-};
-
-enum omap_dss_rotation_type {
- OMAP_DSS_ROT_DMA = 0,
- OMAP_DSS_ROT_VRFB = 1,
-};
-
-/* clockwise rotation angle */
-enum omap_dss_rotation_angle {
- OMAP_DSS_ROT_0 = 0,
- OMAP_DSS_ROT_90 = 1,
- OMAP_DSS_ROT_180 = 2,
- OMAP_DSS_ROT_270 = 3,
-};
-
-enum omap_overlay_caps {
- OMAP_DSS_OVL_CAP_SCALE = 1 << 0,
- OMAP_DSS_OVL_CAP_DISPC = 1 << 1,
-};
-
-enum omap_overlay_manager_caps {
- OMAP_DSS_OVL_MGR_CAP_DISPC = 1 << 0,
-};
-
-/* RFBI */
-
-struct rfbi_timings {
- int cs_on_time;
- int cs_off_time;
- int we_on_time;
- int we_off_time;
- int re_on_time;
- int re_off_time;
- int we_cycle_time;
- int re_cycle_time;
- int cs_pulse_width;
- int access_time;
-
- int clk_div;
-
- u32 tim[5]; /* set by rfbi_convert_timings() */
-
- int converted;
-};
-
-void omap_rfbi_write_command(const void *buf, u32 len);
-void omap_rfbi_read_data(void *buf, u32 len);
-void omap_rfbi_write_data(const void *buf, u32 len);
-void omap_rfbi_write_pixels(const void __iomem *buf, int scr_width,
- u16 x, u16 y,
- u16 w, u16 h);
-int omap_rfbi_enable_te(bool enable, unsigned line);
-int omap_rfbi_setup_te(enum omap_rfbi_te_mode mode,
- unsigned hs_pulse_time, unsigned vs_pulse_time,
- int hs_pol_inv, int vs_pol_inv, int extif_div);
-
-/* DSI */
-void dsi_bus_lock(void);
-void dsi_bus_unlock(void);
-int dsi_vc_dcs_write(int channel, u8 *data, int len);
-int dsi_vc_dcs_write_0(int channel, u8 dcs_cmd);
-int dsi_vc_dcs_write_1(int channel, u8 dcs_cmd, u8 param);
-int dsi_vc_dcs_write_nosync(int channel, u8 *data, int len);
-int dsi_vc_dcs_read(int channel, u8 dcs_cmd, u8 *buf, int buflen);
-int dsi_vc_dcs_read_1(int channel, u8 dcs_cmd, u8 *data);
-int dsi_vc_dcs_read_2(int channel, u8 dcs_cmd, u8 *data1, u8 *data2);
-int dsi_vc_set_max_rx_packet_size(int channel, u16 len);
-int dsi_vc_send_null(int channel);
-int dsi_vc_send_bta_sync(int channel);
-
-/* Board specific data */
-struct omap_dss_board_info {
- int (*get_last_off_on_transaction_id)(struct device *dev);
- int num_devices;
- struct omap_dss_device **devices;
- struct omap_dss_device *default_device;
-};
-
-#if defined(CONFIG_OMAP2_DSS_MODULE) || defined(CONFIG_OMAP2_DSS)
-/* Init with the board info */
-extern int omap_display_init(struct omap_dss_board_info *board_data);
-#else
-static inline int omap_display_init(struct omap_dss_board_info *board_data)
-{
- return 0;
-}
-#endif
-
-struct omap_display_platform_data {
- struct omap_dss_board_info *board_data;
- /* TODO: Additional members to be added when PM is considered */
-
- bool (*opt_clock_available)(const char *clk_role);
-};
-
-struct omap_video_timings {
- /* Unit: pixels */
- u16 x_res;
- /* Unit: pixels */
- u16 y_res;
- /* Unit: KHz */
- u32 pixel_clock;
- /* Unit: pixel clocks */
- u16 hsw; /* Horizontal synchronization pulse width */
- /* Unit: pixel clocks */
- u16 hfp; /* Horizontal front porch */
- /* Unit: pixel clocks */
- u16 hbp; /* Horizontal back porch */
- /* Unit: line clocks */
- u16 vsw; /* Vertical synchronization pulse width */
- /* Unit: line clocks */
- u16 vfp; /* Vertical front porch */
- /* Unit: line clocks */
- u16 vbp; /* Vertical back porch */
-};
-
-#ifdef CONFIG_OMAP2_DSS_VENC
-/* Hardcoded timings for tv modes. Venc only uses these to
- * identify the mode, and does not actually use the configs
- * itself. However, the configs should be something that
- * a normal monitor can also show */
-extern const struct omap_video_timings omap_dss_pal_timings;
-extern const struct omap_video_timings omap_dss_ntsc_timings;
-#endif
-
-struct omap_overlay_info {
- bool enabled;
-
- u32 paddr;
- void __iomem *vaddr;
- u16 screen_width;
- u16 width;
- u16 height;
- enum omap_color_mode color_mode;
- u8 rotation;
- enum omap_dss_rotation_type rotation_type;
- bool mirror;
-
- u16 pos_x;
- u16 pos_y;
- u16 out_width; /* if 0, out_width == width */
- u16 out_height; /* if 0, out_height == height */
- u8 global_alpha;
- u8 pre_mult_alpha;
-};
-
-struct omap_overlay {
- struct kobject kobj;
- struct list_head list;
-
- /* static fields */
- const char *name;
- int id;
- enum omap_color_mode supported_modes;
- enum omap_overlay_caps caps;
-
- /* dynamic fields */
- struct omap_overlay_manager *manager;
- struct omap_overlay_info info;
-
- /* if true, info has been changed, but not applied() yet */
- bool info_dirty;
-
- int (*set_manager)(struct omap_overlay *ovl,
- struct omap_overlay_manager *mgr);
- int (*unset_manager)(struct omap_overlay *ovl);
-
- int (*set_overlay_info)(struct omap_overlay *ovl,
- struct omap_overlay_info *info);
- void (*get_overlay_info)(struct omap_overlay *ovl,
- struct omap_overlay_info *info);
-
- int (*wait_for_go)(struct omap_overlay *ovl);
-};
-
-struct omap_overlay_manager_info {
- u32 default_color;
-
- enum omap_dss_trans_key_type trans_key_type;
- u32 trans_key;
- bool trans_enabled;
-
- bool alpha_enabled;
-};
-
-struct omap_overlay_manager {
- struct kobject kobj;
- struct list_head list;
-
- /* static fields */
- const char *name;
- int id;
- enum omap_overlay_manager_caps caps;
- int num_overlays;
- struct omap_overlay **overlays;
- enum omap_display_type supported_displays;
-
- /* dynamic fields */
- struct omap_dss_device *device;
- struct omap_overlay_manager_info info;
-
- bool device_changed;
- /* if true, info has been changed but not applied() yet */
- bool info_dirty;
-
- int (*set_device)(struct omap_overlay_manager *mgr,
- struct omap_dss_device *dssdev);
- int (*unset_device)(struct omap_overlay_manager *mgr);
-
- int (*set_manager_info)(struct omap_overlay_manager *mgr,
- struct omap_overlay_manager_info *info);
- void (*get_manager_info)(struct omap_overlay_manager *mgr,
- struct omap_overlay_manager_info *info);
-
- int (*apply)(struct omap_overlay_manager *mgr);
- int (*wait_for_go)(struct omap_overlay_manager *mgr);
- int (*wait_for_vsync)(struct omap_overlay_manager *mgr);
-
- int (*enable)(struct omap_overlay_manager *mgr);
- int (*disable)(struct omap_overlay_manager *mgr);
-};
-
-struct omap_dss_device {
- struct device dev;
-
- enum omap_display_type type;
-
- enum omap_channel channel;
-
- union {
- struct {
- u8 data_lines;
- } dpi;
-
- struct {
- u8 channel;
- u8 data_lines;
- } rfbi;
-
- struct {
- u8 datapairs;
- } sdi;
-
- struct {
- u8 clk_lane;
- u8 clk_pol;
- u8 data1_lane;
- u8 data1_pol;
- u8 data2_lane;
- u8 data2_pol;
-
- struct {
- u16 regn;
- u16 regm;
- u16 regm_dispc;
- u16 regm_dsi;
-
- u16 lp_clk_div;
-
- u16 lck_div;
- u16 pck_div;
- } div;
-
- bool ext_te;
- u8 ext_te_gpio;
- } dsi;
-
- struct {
- enum omap_dss_venc_type type;
- bool invert_polarity;
- } venc;
- } phy;
-
- struct {
- struct omap_video_timings timings;
-
- int acbi; /* ac-bias pin transitions per interrupt */
- /* Unit: line clocks */
- int acb; /* ac-bias pin frequency */
-
- enum omap_panel_config config;
- } panel;
-
- struct {
- u8 pixel_size;
- struct rfbi_timings rfbi_timings;
- } ctrl;
-
- int reset_gpio;
-
- int max_backlight_level;
-
- const char *name;
-
- /* used to match device to driver */
- const char *driver_name;
-
- void *data;
-
- struct omap_dss_driver *driver;
-
- /* helper variable for driver suspend/resume */
- bool activate_after_resume;
-
- enum omap_display_caps caps;
-
- struct omap_overlay_manager *manager;
-
- enum omap_dss_display_state state;
-
- /* platform specific */
- int (*platform_enable)(struct omap_dss_device *dssdev);
- void (*platform_disable)(struct omap_dss_device *dssdev);
- int (*set_backlight)(struct omap_dss_device *dssdev, int level);
- int (*get_backlight)(struct omap_dss_device *dssdev);
-};
-
-struct omap_dss_driver {
- struct device_driver driver;
-
- int (*probe)(struct omap_dss_device *);
- void (*remove)(struct omap_dss_device *);
-
- int (*enable)(struct omap_dss_device *display);
- void (*disable)(struct omap_dss_device *display);
- int (*suspend)(struct omap_dss_device *display);
- int (*resume)(struct omap_dss_device *display);
- int (*run_test)(struct omap_dss_device *display, int test);
-
- int (*set_update_mode)(struct omap_dss_device *dssdev,
- enum omap_dss_update_mode);
- enum omap_dss_update_mode (*get_update_mode)(
- struct omap_dss_device *dssdev);
-
- int (*update)(struct omap_dss_device *dssdev,
- u16 x, u16 y, u16 w, u16 h);
- int (*sync)(struct omap_dss_device *dssdev);
-
- int (*enable_te)(struct omap_dss_device *dssdev, bool enable);
- int (*get_te)(struct omap_dss_device *dssdev);
-
- u8 (*get_rotate)(struct omap_dss_device *dssdev);
- int (*set_rotate)(struct omap_dss_device *dssdev, u8 rotate);
-
- bool (*get_mirror)(struct omap_dss_device *dssdev);
- int (*set_mirror)(struct omap_dss_device *dssdev, bool enable);
-
- int (*memory_read)(struct omap_dss_device *dssdev,
- void *buf, size_t size,
- u16 x, u16 y, u16 w, u16 h);
-
- void (*get_resolution)(struct omap_dss_device *dssdev,
- u16 *xres, u16 *yres);
- int (*get_recommended_bpp)(struct omap_dss_device *dssdev);
-
- int (*check_timings)(struct omap_dss_device *dssdev,
- struct omap_video_timings *timings);
- void (*set_timings)(struct omap_dss_device *dssdev,
- struct omap_video_timings *timings);
- void (*get_timings)(struct omap_dss_device *dssdev,
- struct omap_video_timings *timings);
-
- int (*set_wss)(struct omap_dss_device *dssdev, u32 wss);
- u32 (*get_wss)(struct omap_dss_device *dssdev);
-};
-
-int omap_dss_register_driver(struct omap_dss_driver *);
-void omap_dss_unregister_driver(struct omap_dss_driver *);
-
-int omap_dss_register_device(struct omap_dss_device *);
-void omap_dss_unregister_device(struct omap_dss_device *);
-
-void omap_dss_get_device(struct omap_dss_device *dssdev);
-void omap_dss_put_device(struct omap_dss_device *dssdev);
-#define for_each_dss_dev(d) while ((d = omap_dss_get_next_device(d)) != NULL)
-struct omap_dss_device *omap_dss_get_next_device(struct omap_dss_device *from);
-struct omap_dss_device *omap_dss_find_device(void *data,
- int (*match)(struct omap_dss_device *dssdev, void *data));
-
-int omap_dss_start_device(struct omap_dss_device *dssdev);
-void omap_dss_stop_device(struct omap_dss_device *dssdev);
-
-int omap_dss_get_num_overlay_managers(void);
-struct omap_overlay_manager *omap_dss_get_overlay_manager(int num);
-
-int omap_dss_get_num_overlays(void);
-struct omap_overlay *omap_dss_get_overlay(int num);
-
-void omapdss_default_get_resolution(struct omap_dss_device *dssdev,
- u16 *xres, u16 *yres);
-int omapdss_default_get_recommended_bpp(struct omap_dss_device *dssdev);
-
-typedef void (*omap_dispc_isr_t) (void *arg, u32 mask);
-int omap_dispc_register_isr(omap_dispc_isr_t isr, void *arg, u32 mask);
-int omap_dispc_unregister_isr(omap_dispc_isr_t isr, void *arg, u32 mask);
-
-int omap_dispc_wait_for_irq_timeout(u32 irqmask, unsigned long timeout);
-int omap_dispc_wait_for_irq_interruptible_timeout(u32 irqmask,
- unsigned long timeout);
-
-#define to_dss_driver(x) container_of((x), struct omap_dss_driver, driver)
-#define to_dss_device(x) container_of((x), struct omap_dss_device, dev)
-
-void omapdss_dsi_vc_enable_hs(int channel, bool enable);
-int omapdss_dsi_enable_te(struct omap_dss_device *dssdev, bool enable);
-
-int omap_dsi_prepare_update(struct omap_dss_device *dssdev,
- u16 *x, u16 *y, u16 *w, u16 *h,
- bool enlarge_update_area);
-int omap_dsi_update(struct omap_dss_device *dssdev,
- int channel,
- u16 x, u16 y, u16 w, u16 h,
- void (*callback)(int, void *), void *data);
-int omap_dsi_request_vc(struct omap_dss_device *dssdev, int *channel);
-int omap_dsi_set_vc_id(struct omap_dss_device *dssdev, int channel, int vc_id);
-void omap_dsi_release_vc(struct omap_dss_device *dssdev, int channel);
-
-int omapdss_dsi_display_enable(struct omap_dss_device *dssdev);
-void omapdss_dsi_display_disable(struct omap_dss_device *dssdev);
-
-int omapdss_dpi_display_enable(struct omap_dss_device *dssdev);
-void omapdss_dpi_display_disable(struct omap_dss_device *dssdev);
-void dpi_set_timings(struct omap_dss_device *dssdev,
- struct omap_video_timings *timings);
-int dpi_check_timings(struct omap_dss_device *dssdev,
- struct omap_video_timings *timings);
-
-int omapdss_sdi_display_enable(struct omap_dss_device *dssdev);
-void omapdss_sdi_display_disable(struct omap_dss_device *dssdev);
-
-int omapdss_rfbi_display_enable(struct omap_dss_device *dssdev);
-void omapdss_rfbi_display_disable(struct omap_dss_device *dssdev);
-int omap_rfbi_prepare_update(struct omap_dss_device *dssdev,
- u16 *x, u16 *y, u16 *w, u16 *h);
-int omap_rfbi_update(struct omap_dss_device *dssdev,
- u16 x, u16 y, u16 w, u16 h,
- void (*callback)(void *), void *data);
-
-#endif
diff --git a/arch/arm/plat-omap/include/plat/nokia-dsi-panel.h b/arch/arm/plat-omap/include/plat/nokia-dsi-panel.h
deleted file mode 100644
index 01ab6572ccbb..000000000000
--- a/arch/arm/plat-omap/include/plat/nokia-dsi-panel.h
+++ /dev/null
@@ -1,31 +0,0 @@
-#ifndef __ARCH_ARM_PLAT_OMAP_NOKIA_DSI_PANEL_H
-#define __ARCH_ARM_PLAT_OMAP_NOKIA_DSI_PANEL_H
-
-#include "display.h"
-
-/**
- * struct nokia_dsi_panel_data - Nokia DSI panel driver configuration
- * @name: panel name
- * @use_ext_te: use external TE
- * @ext_te_gpio: external TE GPIO
- * @use_esd_check: perform ESD checks
- * @max_backlight_level: maximum backlight level
- * @set_backlight: pointer to backlight set function
- * @get_backlight: pointer to backlight get function
- */
-struct nokia_dsi_panel_data {
- const char *name;
-
- int reset_gpio;
-
- bool use_ext_te;
- int ext_te_gpio;
-
- bool use_esd_check;
-
- int max_backlight_level;
- int (*set_backlight)(struct omap_dss_device *dssdev, int level);
- int (*get_backlight)(struct omap_dss_device *dssdev);
-};
-
-#endif /* __ARCH_ARM_PLAT_OMAP_NOKIA_DSI_PANEL_H */
diff --git a/arch/arm/plat-omap/include/plat/panel-generic-dpi.h b/arch/arm/plat-omap/include/plat/panel-generic-dpi.h
deleted file mode 100644
index 790619734bcd..000000000000
--- a/arch/arm/plat-omap/include/plat/panel-generic-dpi.h
+++ /dev/null
@@ -1,37 +0,0 @@
-/*
- * Header for generic DPI panel driver
- *
- * Copyright (C) 2010 Canonical Ltd.
- * Author: Bryan Wu <bryan.wu@canonical.com>
- *
- * This program is free software; you can redistribute it and/or modify it
- * under the terms of the GNU General Public License version 2 as published by
- * the Free Software Foundation.
- *
- * This program is distributed in the hope that it will be useful, but WITHOUT
- * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
- * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
- * more details.
- *
- * You should have received a copy of the GNU General Public License along with
- * this program. If not, see <http://www.gnu.org/licenses/>.
- */
-
-#ifndef __ARCH_ARM_PLAT_OMAP_PANEL_GENERIC_DPI_H
-#define __ARCH_ARM_PLAT_OMAP_PANEL_GENERIC_DPI_H
-
-#include "display.h"
-
-/**
- * struct panel_generic_dpi_data - panel driver configuration data
- * @name: panel name
- * @platform_enable: platform specific panel enable function
- * @platform_disable: platform specific panel disable function
- */
-struct panel_generic_dpi_data {
- const char *name;
- int (*platform_enable)(struct omap_dss_device *dssdev);
- void (*platform_disable)(struct omap_dss_device *dssdev);
-};
-
-#endif /* __ARCH_ARM_PLAT_OMAP_PANEL_GENERIC_DPI_H */