diff options
Diffstat (limited to 'arch/blackfin')
99 files changed, 2855 insertions, 1791 deletions
diff --git a/arch/blackfin/Kconfig b/arch/blackfin/Kconfig index 7faa2f554ab..9a01d445eca 100644 --- a/arch/blackfin/Kconfig +++ b/arch/blackfin/Kconfig @@ -342,8 +342,9 @@ config MEM_MT48LC64M4A2FB_7E config MEM_MT48LC16M16A2TG_75 bool depends on (BFIN533_EZKIT || BFIN561_EZKIT \ - || BFIN533_BLUETECHNIX_CM || BFIN537_BLUETECHNIX_CM \ - || H8606_HVSISTEMAS || BFIN527_BLUETECHNIX_CM) + || BFIN533_BLUETECHNIX_CM || BFIN537_BLUETECHNIX_CM_E \ + || BFIN537_BLUETECHNIX_CM_U || H8606_HVSISTEMAS \ + || BFIN527_BLUETECHNIX_CM) default y config MEM_MT48LC32M8A2_75 @@ -459,7 +460,7 @@ config VCO_MULT default "45" if BFIN533_STAMP default "20" if (BFIN537_STAMP || BFIN527_EZKIT || BFIN548_EZKIT || BFIN548_BLUETECHNIX_CM || BFIN538_EZKIT) default "22" if BFIN533_BLUETECHNIX_CM - default "20" if (BFIN537_BLUETECHNIX_CM || BFIN527_BLUETECHNIX_CM || BFIN561_BLUETECHNIX_CM) + default "20" if (BFIN537_BLUETECHNIX_CM_E || BFIN537_BLUETECHNIX_CM_U || BFIN527_BLUETECHNIX_CM || BFIN561_BLUETECHNIX_CM) default "20" if BFIN561_EZKIT default "16" if (H8606_HVSISTEMAS || BLACKSTAMP || BFIN526_EZBRD || BFIN518F_EZBRD) help @@ -574,8 +575,8 @@ config MAX_VCO_HZ default 400000000 if BF514 default 400000000 if BF516 default 400000000 if BF518 - default 600000000 if BF522 - default 400000000 if BF523 + default 400000000 if BF522 + default 600000000 if BF523 default 400000000 if BF524 default 600000000 if BF525 default 400000000 if BF526 @@ -647,7 +648,7 @@ config CYCLES_CLOCKSOURCE writing the registers will most likely crash the kernel. config GPTMR0_CLOCKSOURCE - bool "Use GPTimer0 as a clocksource (higher rating)" + bool "Use GPTimer0 as a clocksource" select BFIN_GPTIMERS depends on GENERIC_CLOCKEVENTS depends on !TICKSOURCE_GPTMR0 @@ -917,10 +918,6 @@ comment "Cache Support" config BFIN_ICACHE bool "Enable ICACHE" default y -config BFIN_ICACHE_LOCK - bool "Enable Instruction Cache Locking" - depends on BFIN_ICACHE - default n config BFIN_EXTMEM_ICACHEABLE bool "Enable ICACHE for external memory" depends on BFIN_ICACHE @@ -987,7 +984,7 @@ endchoice config BFIN_L2_DCACHEABLE bool "Enable DCACHE for L2 SRAM" depends on BFIN_DCACHE - depends on BF54x || BF561 + depends on (BF54x || BF561) && !SMP default n choice prompt "L2 SRAM DCACHE policy" @@ -995,11 +992,9 @@ choice default BFIN_L2_WRITEBACK config BFIN_L2_WRITEBACK bool "Write back" - depends on !SMP config BFIN_L2_WRITETHROUGH bool "Write through" - depends on !SMP endchoice @@ -1154,11 +1149,12 @@ source "fs/Kconfig.binfmt" endmenu menu "Power management options" + depends on !SMP + source "kernel/power/Kconfig" config ARCH_SUSPEND_POSSIBLE def_bool y - depends on !SMP choice prompt "Standby Power Saving Mode" @@ -1246,6 +1242,7 @@ config PM_BFIN_WAKE_GP endmenu menu "CPU Frequency scaling" + depends on !SMP source "drivers/cpufreq/Kconfig" diff --git a/arch/blackfin/Kconfig.debug b/arch/blackfin/Kconfig.debug index 1fc4981d486..87f195ee2e0 100644 --- a/arch/blackfin/Kconfig.debug +++ b/arch/blackfin/Kconfig.debug @@ -252,4 +252,10 @@ config ACCESS_CHECK Say N here to disable that check to improve the performance. +config BFIN_ISRAM_SELF_TEST + bool "isram boot self tests" + default n + help + Run some self tests of the isram driver code at boot. + endmenu diff --git a/arch/blackfin/Makefile b/arch/blackfin/Makefile index 6f9533c3d75..f063b772934 100644 --- a/arch/blackfin/Makefile +++ b/arch/blackfin/Makefile @@ -155,7 +155,7 @@ define archhelp echo '* vmImage.gz - Kernel-only image for U-Boot (arch/$(ARCH)/boot/vmImage.gz)' echo ' vmImage.lzma - Kernel-only image for U-Boot (arch/$(ARCH)/boot/vmImage.lzma)' echo ' install - Install kernel using' - echo ' (your) ~/bin/$(CROSS_COMPILE)installkernel or' - echo ' (distribution) PATH: $(CROSS_COMPILE)installkernel or' + echo ' (your) ~/bin/$(INSTALLKERNEL) or' + echo ' (distribution) PATH: $(INSTALLKERNEL) or' echo ' install to $$(INSTALL_PATH)' endef diff --git a/arch/blackfin/boot/install.sh b/arch/blackfin/boot/install.sh index 9560a6b2910..e2c6e40902b 100644 --- a/arch/blackfin/boot/install.sh +++ b/arch/blackfin/boot/install.sh @@ -36,9 +36,9 @@ verify "$3" # User may have a custom install script -if [ -x ~/bin/${CROSS_COMPILE}installkernel ]; then exec ~/bin/${CROSS_COMPILE}installkernel "$@"; fi -if which ${CROSS_COMPILE}installkernel >/dev/null 2>&1; then - exec ${CROSS_COMPILE}installkernel "$@" +if [ -x ~/bin/${INSTALLKERNEL} ]; then exec ~/bin/${INSTALLKERNEL} "$@"; fi +if which ${INSTALLKERNEL} >/dev/null 2>&1; then + exec ${INSTALLKERNEL} "$@" fi # Default install - same as make zlilo diff --git a/arch/blackfin/configs/BF518F-EZBRD_defconfig b/arch/blackfin/configs/BF518F-EZBRD_defconfig index dcfb4889559..9905b26009e 100644 --- a/arch/blackfin/configs/BF518F-EZBRD_defconfig +++ b/arch/blackfin/configs/BF518F-EZBRD_defconfig @@ -358,9 +358,9 @@ CONFIG_C_AMBEN_ALL=y # EBIU_AMBCTL Control # CONFIG_BANK_0=0x7BB0 -CONFIG_BANK_1=0x5554 +CONFIG_BANK_1=0x7BB0 CONFIG_BANK_2=0x7BB0 -CONFIG_BANK_3=0xFFC0 +CONFIG_BANK_3=0x99B2 # # Bus options (PCI, PCMCIA, EISA, MCA, ISA) diff --git a/arch/blackfin/configs/BF526-EZBRD_defconfig b/arch/blackfin/configs/BF526-EZBRD_defconfig index 48a3a7a9099..9dc68208802 100644 --- a/arch/blackfin/configs/BF526-EZBRD_defconfig +++ b/arch/blackfin/configs/BF526-EZBRD_defconfig @@ -359,9 +359,9 @@ CONFIG_C_AMBEN_ALL=y # EBIU_AMBCTL Control # CONFIG_BANK_0=0x7BB0 -CONFIG_BANK_1=0x5554 +CONFIG_BANK_1=0x7BB0 CONFIG_BANK_2=0x7BB0 -CONFIG_BANK_3=0xFFC0 +CONFIG_BANK_3=0x99B2 # # Bus options (PCI, PCMCIA, EISA, MCA, ISA) diff --git a/arch/blackfin/configs/BF527-EZKIT_defconfig b/arch/blackfin/configs/BF527-EZKIT_defconfig index dd8352791da..77e35d4baf5 100644 --- a/arch/blackfin/configs/BF527-EZKIT_defconfig +++ b/arch/blackfin/configs/BF527-EZKIT_defconfig @@ -363,9 +363,9 @@ CONFIG_C_AMBEN_ALL=y # EBIU_AMBCTL Control # CONFIG_BANK_0=0x7BB0 -CONFIG_BANK_1=0x5554 +CONFIG_BANK_1=0x7BB0 CONFIG_BANK_2=0x7BB0 -CONFIG_BANK_3=0xFFC0 +CONFIG_BANK_3=0x99B2 # # Bus options (PCI, PCMCIA, EISA, MCA, ISA) diff --git a/arch/blackfin/configs/BF548-EZKIT_defconfig b/arch/blackfin/configs/BF548-EZKIT_defconfig index b3d3cab81cf..f773ad1155d 100644 --- a/arch/blackfin/configs/BF548-EZKIT_defconfig +++ b/arch/blackfin/configs/BF548-EZKIT_defconfig @@ -400,7 +400,7 @@ CONFIG_C_AMBEN_ALL=y # EBIU_AMBCTL Control # CONFIG_BANK_0=0x7BB0 -CONFIG_BANK_1=0x5554 +CONFIG_BANK_1=0x7BB0 CONFIG_BANK_2=0x7BB0 CONFIG_BANK_3=0x99B2 CONFIG_EBIU_MBSCTLVAL=0x0 diff --git a/arch/blackfin/include/asm/bfin-global.h b/arch/blackfin/include/asm/bfin-global.h index e39277ea43e..aef0594e786 100644 --- a/arch/blackfin/include/asm/bfin-global.h +++ b/arch/blackfin/include/asm/bfin-global.h @@ -66,7 +66,6 @@ extern void program_IAR(void); extern asmlinkage void lower_to_irq14(void); extern asmlinkage void bfin_return_from_exception(void); -extern asmlinkage void evt14_softirq(void); extern asmlinkage void asm_do_IRQ(unsigned int irq, struct pt_regs *regs); extern int bfin_internal_set_wake(unsigned int irq, unsigned int state); @@ -100,11 +99,6 @@ extern unsigned long bfin_sic_iwr[]; extern unsigned vr_wakeup; extern u16 _bfin_swrst; /* shadow for Software Reset Register (SWRST) */ -#ifdef CONFIG_BFIN_ICACHE_LOCK -extern void cache_grab_lock(int way); -extern void bfin_cache_lock(int way); -#endif - #endif #endif /* _BLACKFIN_H_ */ diff --git a/arch/blackfin/include/asm/bfin5xx_spi.h b/arch/blackfin/include/asm/bfin5xx_spi.h index aaeb4df10d5..c281c632827 100644 --- a/arch/blackfin/include/asm/bfin5xx_spi.h +++ b/arch/blackfin/include/asm/bfin5xx_spi.h @@ -127,6 +127,7 @@ struct bfin5xx_spi_chip { u32 cs_gpio; /* Value to send if no TX value is supplied, usually 0x0 or 0xFFFF */ u16 idle_tx_val; + u8 pio_interrupt; /* Enable spi data irq */ }; #endif /* _SPI_CHANNEL_H_ */ diff --git a/arch/blackfin/include/asm/bfin_rotary.h b/arch/blackfin/include/asm/bfin_rotary.h new file mode 100644 index 00000000000..425ece64fd5 --- /dev/null +++ b/arch/blackfin/include/asm/bfin_rotary.h @@ -0,0 +1,39 @@ +/* + * board initialization should put one of these structures into platform_data + * and place the bfin-rotary onto platform_bus named "bfin-rotary". + */ + +#ifndef _BFIN_ROTARY_H +#define _BFIN_ROTARY_H + +/* mode bitmasks */ +#define ROT_QUAD_ENC CNTMODE_QUADENC /* quadrature/grey code encoder mode */ +#define ROT_BIN_ENC CNTMODE_BINENC /* binary encoder mode */ +#define ROT_UD_CNT CNTMODE_UDCNT /* rotary counter mode */ +#define ROT_DIR_CNT CNTMODE_DIRCNT /* direction counter mode */ + +#define ROT_DEBE DEBE /* Debounce Enable */ + +#define ROT_CDGINV CDGINV /* CDG Pin Polarity Invert */ +#define ROT_CUDINV CUDINV /* CUD Pin Polarity Invert */ +#define ROT_CZMINV CZMINV /* CZM Pin Polarity Invert */ + +struct bfin_rotary_platform_data { + /* set rotary UP KEY_### or BTN_### in case you prefer + * bfin-rotary to send EV_KEY otherwise set 0 + */ + unsigned int rotary_up_key; + /* set rotary DOWN KEY_### or BTN_### in case you prefer + * bfin-rotary to send EV_KEY otherwise set 0 + */ + unsigned int rotary_down_key; + /* set rotary BUTTON KEY_### or BTN_### */ + unsigned int rotary_button_key; + /* set rotary Relative Axis REL_### in case you prefer + * bfin-rotary to send EV_REL otherwise set 0 + */ + unsigned int rotary_rel_code; + unsigned short debounce; /* 0..17 */ + unsigned short mode; +}; +#endif diff --git a/arch/blackfin/include/asm/cplb.h b/arch/blackfin/include/asm/cplb.h index c5dacf8f8cf..d18d16837a6 100644 --- a/arch/blackfin/include/asm/cplb.h +++ b/arch/blackfin/include/asm/cplb.h @@ -125,4 +125,48 @@ #define FAULT_USERSUPV (1 << 17) #define FAULT_CPLBBITS 0x0000ffff -#endif /* _CPLB_H */ +#ifndef __ASSEMBLY__ + +static inline void _disable_cplb(u32 mmr, u32 mask) +{ + u32 ctrl = bfin_read32(mmr) & ~mask; + /* CSYNC to ensure load store ordering */ + __builtin_bfin_csync(); + bfin_write32(mmr, ctrl); + __builtin_bfin_ssync(); +} +static inline void disable_cplb(u32 mmr, u32 mask) +{ + u32 ctrl = bfin_read32(mmr) & ~mask; + CSYNC(); + bfin_write32(mmr, ctrl); + SSYNC(); +} +#define _disable_dcplb() _disable_cplb(DMEM_CONTROL, ENDCPLB) +#define disable_dcplb() disable_cplb(DMEM_CONTROL, ENDCPLB) +#define _disable_icplb() _disable_cplb(IMEM_CONTROL, ENICPLB) +#define disable_icplb() disable_cplb(IMEM_CONTROL, ENICPLB) + +static inline void _enable_cplb(u32 mmr, u32 mask) +{ + u32 ctrl = bfin_read32(mmr) | mask; + /* CSYNC to ensure load store ordering */ + __builtin_bfin_csync(); + bfin_write32(mmr, ctrl); + __builtin_bfin_ssync(); +} +static inline void enable_cplb(u32 mmr, u32 mask) +{ + u32 ctrl = bfin_read32(mmr) | mask; + CSYNC(); + bfin_write32(mmr, ctrl); + SSYNC(); +} +#define _enable_dcplb() _enable_cplb(DMEM_CONTROL, ENDCPLB) +#define enable_dcplb() enable_cplb(DMEM_CONTROL, ENDCPLB) +#define _enable_icplb() _enable_cplb(IMEM_CONTROL, ENICPLB) +#define enable_icplb() enable_cplb(IMEM_CONTROL, ENICPLB) + +#endif /* __ASSEMBLY__ */ + +#endif /* _CPLB_H */ diff --git a/arch/blackfin/include/asm/early_printk.h b/arch/blackfin/include/asm/early_printk.h index 110f1c1f845..53a762b6fcd 100644 --- a/arch/blackfin/include/asm/early_printk.h +++ b/arch/blackfin/include/asm/early_printk.h @@ -21,8 +21,32 @@ * GNU General Public License for more details. */ + +#ifndef __ASM_EARLY_PRINTK_H__ +#define __ASM_EARLY_PRINTK_H__ + #ifdef CONFIG_EARLY_PRINTK +/* For those that don't include it already */ +#include <linux/console.h> + extern int setup_early_printk(char *); +extern void enable_shadow_console(void); +extern int shadow_console_enabled(void); +extern void mark_shadow_error(void); +extern void early_shadow_reg(unsigned long reg, unsigned int n); +extern void early_shadow_write(struct console *con, const char *s, + unsigned int n) __attribute__((nonnull(2))); +#define early_shadow_puts(str) early_shadow_write(NULL, str, strlen(str)) +#define early_shadow_stamp() \ + do { \ + early_shadow_puts(__FILE__ " : " __stringify(__LINE__) " ["); \ + early_shadow_puts(__func__); \ + early_shadow_puts("]\n"); \ + } while (0) #else #define setup_early_printk(fmt) do { } while (0) +#define enable_shadow_console(fmt) do { } while (0) +#define early_shadow_stamp() do { } while (0) #endif /* CONFIG_EARLY_PRINTK */ + +#endif /* __ASM_EARLY_PRINTK_H__ */ diff --git a/arch/blackfin/include/asm/elf.h b/arch/blackfin/include/asm/elf.h index 5a87baf0659..c823e8ebbfa 100644 --- a/arch/blackfin/include/asm/elf.h +++ b/arch/blackfin/include/asm/elf.h @@ -23,7 +23,7 @@ typedef unsigned long elf_greg_t; #define ELF_NGREG 40 /* (sizeof(struct user_regs_struct) / sizeof(elf_greg_t)) */ typedef elf_greg_t elf_gregset_t[ELF_NGREG]; -typedef struct user_bfinfp_struct elf_fpregset_t; +typedef struct { } elf_fpregset_t; /* * This is used to ensure we don't load something for the wrong architecture. */ diff --git a/arch/blackfin/include/asm/entry.h b/arch/blackfin/include/asm/entry.h index ec58efc130e..55b808fced7 100644 --- a/arch/blackfin/include/asm/entry.h +++ b/arch/blackfin/include/asm/entry.h @@ -36,6 +36,21 @@ # define LOAD_IPIPE_IPEND #endif +/* + * Workaround for anomalies 05000283 and 05000315 + */ +#if ANOMALY_05000283 || ANOMALY_05000315 +# define ANOMALY_283_315_WORKAROUND(preg, dreg) \ + cc = dreg == dreg; \ + preg.h = HI(CHIPID); \ + preg.l = LO(CHIPID); \ + if cc jump 1f; \ + dreg.l = W[preg]; \ +1: +#else +# define ANOMALY_283_315_WORKAROUND(preg, dreg) +#endif /* ANOMALY_05000283 || ANOMALY_05000315 */ + #ifndef CONFIG_EXACT_HWERR /* As a debugging aid - we save IPEND when DEBUG_KERNEL is on, * otherwise it is a waste of cycles. @@ -88,17 +103,22 @@ * As you can see by the code - we actually need to do two SSYNCS - one to * make sure the read/writes complete, and another to make sure the hardware * error is recognized by the core. + * + * The extra nop before the SSYNC is to make sure we work around 05000244, + * since the 283/315 workaround includes a branch to the end */ #define INTERRUPT_ENTRY(N) \ - SSYNC; \ - SSYNC; \ [--sp] = SYSCFG; \ [--sp] = P0; /*orig_p0*/ \ [--sp] = R0; /*orig_r0*/ \ [--sp] = (R7:0,P5:0); \ R1 = ASTAT; \ + ANOMALY_283_315_WORKAROUND(p0, r0) \ P0.L = LO(ILAT); \ P0.H = HI(ILAT); \ + NOP; \ + SSYNC; \ + SSYNC; \ R0 = [P0]; \ CC = BITTST(R0, EVT_IVHW_P); \ IF CC JUMP 1f; \ @@ -118,15 +138,17 @@ RTI; #define TIMER_INTERRUPT_ENTRY(N) \ - SSYNC; \ - SSYNC; \ [--sp] = SYSCFG; \ [--sp] = P0; /*orig_p0*/ \ [--sp] = R0; /*orig_r0*/ \ [--sp] = (R7:0,P5:0); \ R1 = ASTAT; \ + ANOMALY_283_315_WORKAROUND(p0, r0) \ P0.L = LO(ILAT); \ P0.H = HI(ILAT); \ + NOP; \ + SSYNC; \ + SSYNC; \ R0 = [P0]; \ CC = BITTST(R0, EVT_IVHW_P); \ IF CC JUMP 1f; \ diff --git a/arch/blackfin/include/asm/ftrace.h b/arch/blackfin/include/asm/ftrace.h index 8643680f0f7..90c9b400ba6 100644 --- a/arch/blackfin/include/asm/ftrace.h +++ b/arch/blackfin/include/asm/ftrace.h @@ -8,6 +8,6 @@ #ifndef __ASM_BFIN_FTRACE_H__ #define __ASM_BFIN_FTRACE_H__ -#define MCOUNT_INSN_SIZE 8 /* sizeof mcount call: LINK + CALL */ +#define MCOUNT_INSN_SIZE 6 /* sizeof "[++sp] = rets; call __mcount;" */ #endif diff --git a/arch/blackfin/include/asm/ipipe.h b/arch/blackfin/include/asm/ipipe.h index 87ba9ad399c..4617ba66278 100644 --- a/arch/blackfin/include/asm/ipipe.h +++ b/arch/blackfin/include/asm/ipipe.h @@ -145,10 +145,6 @@ void __ipipe_handle_irq(unsigned irq, struct pt_regs *regs); int __ipipe_get_irq_priority(unsigned irq); -void __ipipe_stall_root_raw(void); - -void __ipipe_unstall_root_raw(void); - void __ipipe_serial_debug(const char *fmt, ...); asmlinkage void __ipipe_call_irqtail(unsigned long addr); @@ -234,9 +230,6 @@ int ipipe_start_irq_thread(unsigned irq, struct irq_desc *desc); #define task_hijacked(p) 0 #define ipipe_trap_notify(t, r) 0 -#define __ipipe_stall_root_raw() do { } while (0) -#define __ipipe_unstall_root_raw() do { } while (0) - #define ipipe_init_irq_threads() do { } while (0) #define ipipe_start_irq_thread(irq, desc) 0 diff --git a/arch/blackfin/include/asm/irq_handler.h b/arch/blackfin/include/asm/irq_handler.h index 139b5208f9d..7d9e2d3bbed 100644 --- a/arch/blackfin/include/asm/irq_handler.h +++ b/arch/blackfin/include/asm/irq_handler.h @@ -17,6 +17,7 @@ asmlinkage void evt_evt10(void); asmlinkage void evt_evt11(void); asmlinkage void evt_evt12(void); asmlinkage void evt_evt13(void); +asmlinkage void evt_evt14(void); asmlinkage void evt_soft_int1(void); asmlinkage void evt_system_call(void); asmlinkage void init_exception_buff(void); diff --git a/arch/blackfin/include/asm/mmu_context.h b/arch/blackfin/include/asm/mmu_context.h index 944e29faae4..040410bb07e 100644 --- a/arch/blackfin/include/asm/mmu_context.h +++ b/arch/blackfin/include/asm/mmu_context.h @@ -127,17 +127,17 @@ static inline void protect_page(struct mm_struct *mm, unsigned long addr, unsigned long idx = page >> 5; unsigned long bit = 1 << (page & 31); - if (flags & VM_MAYREAD) + if (flags & VM_READ) mask[idx] |= bit; else mask[idx] &= ~bit; mask += page_mask_nelts; - if (flags & VM_MAYWRITE) + if (flags & VM_WRITE) mask[idx] |= bit; else mask[idx] &= ~bit; mask += page_mask_nelts; - if (flags & VM_MAYEXEC) + if (flags & VM_EXEC) mask[idx] |= bit; else mask[idx] &= ~bit; diff --git a/arch/blackfin/include/asm/pda.h b/arch/blackfin/include/asm/pda.h index b42555c1431..a6f95695731 100644 --- a/arch/blackfin/include/asm/pda.h +++ b/arch/blackfin/include/asm/pda.h @@ -50,6 +50,7 @@ struct blackfin_pda { /* Per-processor Data Area */ unsigned long ex_optr; unsigned long ex_buf[4]; unsigned long ex_imask; /* Saved imask from exception */ + unsigned long ex_ipend; /* Saved IPEND from exception */ unsigned long *ex_stack; /* Exception stack space */ #ifdef ANOMALY_05000261 @@ -60,6 +61,12 @@ struct blackfin_pda { /* Per-processor Data Area */ unsigned long retx; unsigned long seqstat; unsigned int __nmi_count; /* number of times NMI asserted on this CPU */ +#ifdef CONFIG_DEBUG_DOUBLEFAULT + unsigned long dcplb_doublefault_addr; + unsigned long icplb_doublefault_addr; + unsigned long retx_doublefault; + unsigned long seqstat_doublefault; +#endif }; extern struct blackfin_pda cpu_pda[]; diff --git a/arch/blackfin/include/asm/sections.h b/arch/blackfin/include/asm/sections.h index e7fd0ecd73f..ae4dae1e370 100644 --- a/arch/blackfin/include/asm/sections.h +++ b/arch/blackfin/include/asm/sections.h @@ -1,9 +1,6 @@ #ifndef _BLACKFIN_SECTIONS_H #define _BLACKFIN_SECTIONS_H -/* nothing to see, move along */ -#include <asm-generic/sections.h> - /* only used when MTD_UCLINUX */ extern unsigned long memory_mtd_start, memory_mtd_end, mtd_size; @@ -15,4 +12,39 @@ extern char _stext_l1[], _etext_l1[], _sdata_l1[], _edata_l1[], _sbss_l1[], _stext_l2[], _etext_l2[], _sdata_l2[], _edata_l2[], _sbss_l2[], _ebss_l2[], _l2_lma_start[]; +#include <asm/mem_map.h> + +/* Blackfin systems have discontinuous memory map and no virtualized memory */ +static inline int arch_is_kernel_text(unsigned long addr) +{ + return + (L1_CODE_LENGTH && + addr >= (unsigned long)_stext_l1 && + addr < (unsigned long)_etext_l1) + || + (L2_LENGTH && + addr >= (unsigned long)_stext_l2 && + addr < (unsigned long)_etext_l2); +} +#define arch_is_kernel_text(addr) arch_is_kernel_text(addr) + +static inline int arch_is_kernel_data(unsigned long addr) +{ + return + (L1_DATA_A_LENGTH && + addr >= (unsigned long)_sdata_l1 && + addr < (unsigned long)_ebss_l1) + || + (L1_DATA_B_LENGTH && + addr >= (unsigned long)_sdata_b_l1 && + addr < (unsigned long)_ebss_b_l1) + || + (L2_LENGTH && + addr >= (unsigned long)_sdata_l2 && + addr < (unsigned long)_ebss_l2); +} +#define arch_is_kernel_data(addr) arch_is_kernel_data(addr) + +#include <asm-generic/sections.h> + #endif diff --git a/arch/blackfin/include/asm/unistd.h b/arch/blackfin/include/asm/unistd.h index c8e7ee4768c..02b1529dad5 100644 --- a/arch/blackfin/include/asm/unistd.h +++ b/arch/blackfin/include/asm/unistd.h @@ -381,7 +381,7 @@ #define __NR_preadv 366 #define __NR_pwritev 367 #define __NR_rt_tgsigqueueinfo 368 -#define __NR_perf_counter_open 369 +#define __NR_perf_event_open 369 #define __NR_syscall 370 #define NR_syscalls __NR_syscall diff --git a/arch/blackfin/kernel/Makefile b/arch/blackfin/kernel/Makefile index 141d9281e4b..a8ddbc8ed5a 100644 --- a/arch/blackfin/kernel/Makefile +++ b/arch/blackfin/kernel/Makefile @@ -26,6 +26,7 @@ obj-$(CONFIG_MODULES) += module.o obj-$(CONFIG_KGDB) += kgdb.o obj-$(CONFIG_KGDB_TESTS) += kgdb_test.o obj-$(CONFIG_EARLY_PRINTK) += early_printk.o +obj-$(CONFIG_EARLY_PRINTK) += shadow_console.o obj-$(CONFIG_STACKTRACE) += stacktrace.o # the kgdb test puts code into L2 and without linker diff --git a/arch/blackfin/kernel/asm-offsets.c b/arch/blackfin/kernel/asm-offsets.c index b5df9459d6d..f05d1b99b0e 100644 --- a/arch/blackfin/kernel/asm-offsets.c +++ b/arch/blackfin/kernel/asm-offsets.c @@ -145,6 +145,7 @@ int main(void) DEFINE(PDA_EXBUF, offsetof(struct blackfin_pda, ex_buf)); DEFINE(PDA_EXIMASK, offsetof(struct blackfin_pda, ex_imask)); DEFINE(PDA_EXSTACK, offsetof(struct blackfin_pda, ex_stack)); + DEFINE(PDA_EXIPEND, offsetof(struct blackfin_pda, ex_ipend)); #ifdef ANOMALY_05000261 DEFINE(PDA_LFRETX, offsetof(struct blackfin_pda, last_cplb_fault_retx)); #endif @@ -152,6 +153,12 @@ int main(void) DEFINE(PDA_ICPLB, offsetof(struct blackfin_pda, icplb_fault_addr)); DEFINE(PDA_RETX, offsetof(struct blackfin_pda, retx)); DEFINE(PDA_SEQSTAT, offsetof(struct blackfin_pda, seqstat)); +#ifdef CONFIG_DEBUG_DOUBLEFAULT + DEFINE(PDA_DF_DCPLB, offsetof(struct blackfin_pda, dcplb_doublefault_addr)); + DEFINE(PDA_DF_ICPLB, offsetof(struct blackfin_pda, icplb_doublefault_addr)); + DEFINE(PDA_DF_SEQSTAT, offsetof(struct blackfin_pda, seqstat_doublefault)); + DEFINE(PDA_DF_RETX, offsetof(struct blackfin_pda, retx_doublefault)); +#endif #ifdef CONFIG_SMP /* Inter-core lock (in L2 SRAM) */ DEFINE(SIZEOF_CORELOCK, sizeof(struct corelock_slot)); diff --git a/arch/blackfin/kernel/bfin_dma_5xx.c b/arch/blackfin/kernel/bfin_dma_5xx.c index 9f9b8281665..384868dedac 100644 --- a/arch/blackfin/kernel/bfin_dma_5xx.c +++ b/arch/blackfin/kernel/bfin_dma_5xx.c @@ -19,6 +19,7 @@ #include <asm/cacheflush.h> #include <asm/dma.h> #include <asm/uaccess.h> +#include <asm/early_printk.h> /* * To make sure we work around 05000119 - we always check DMA_DONE bit, @@ -146,8 +147,8 @@ EXPORT_SYMBOL(request_dma); int set_dma_callback(unsigned int channel, irq_handler_t callback, void *data) { - BUG_ON(!(dma_ch[channel].chan_status != DMA_CHANNEL_FREE - && channel < MAX_DMA_CHANNELS)); + BUG_ON(channel >= MAX_DMA_CHANNELS || + dma_ch[channel].chan_status == DMA_CHANNEL_FREE); if (callback != NULL) { int ret; @@ -181,8 +182,8 @@ static void clear_dma_buffer(unsigned int channel) void free_dma(unsigned int channel) { pr_debug("freedma() : BEGIN \n"); - BUG_ON(!(dma_ch[channel].chan_status != DMA_CHANNEL_FREE - && channel < MAX_DMA_CHANNELS)); + BUG_ON(channel >= MAX_DMA_CHANNELS || + dma_ch[channel].chan_status == DMA_CHANNEL_FREE); /* Halt the DMA */ disable_dma(channel); @@ -236,6 +237,7 @@ void blackfin_dma_resume(void) */ void __init blackfin_dma_early_init(void) { + early_shadow_stamp(); bfin_write_MDMA_S0_CONFIG(0); bfin_write_MDMA_S1_CONFIG(0); } @@ -246,6 +248,8 @@ void __init early_dma_memcpy(void *pdst, const void *psrc, size_t size) unsigned long src = (unsigned long)psrc; struct dma_register *dst_ch, *src_ch; + early_shadow_stamp(); + /* We assume that everything is 4 byte aligned, so include * a basic sanity check */ @@ -300,6 +304,8 @@ void __init early_dma_memcpy(void *pdst, const void *psrc, size_t size) void __init early_dma_memcpy_done(void) { + early_shadow_stamp(); + while ((bfin_read_MDMA_S0_CONFIG() && !(bfin_read_MDMA_D0_IRQ_STATUS() & DMA_DONE)) || (bfin_read_MDMA_S1_CONFIG() && !(bfin_read_MDMA_D1_IRQ_STATUS() & DMA_DONE))) continue; diff --git a/arch/blackfin/kernel/bfin_gpio.c b/arch/blackfin/kernel/bfin_gpio.c index 6b944627137..fc4681c0170 100644 --- a/arch/blackfin/kernel/bfin_gpio.c +++ b/arch/blackfin/kernel/bfin_gpio.c @@ -722,7 +722,6 @@ void bfin_gpio_pm_hibernate_suspend(void) gpio_bank_saved[bank].fer = gpio_array[bank]->port_fer; gpio_bank_saved[bank].mux = gpio_array[bank]->port_mux; gpio_bank_saved[bank].data = gpio_array[bank]->data; - gpio_bank_saved[bank].data = gpio_array[bank]->data; gpio_bank_saved[bank].inen = gpio_array[bank]->inen; gpio_bank_saved[bank].dir = gpio_array[bank]->dir_set; } diff --git a/arch/blackfin/kernel/cplb-mpu/Makefile b/arch/blackfin/kernel/cplb-mpu/Makefile index 7d70d3bf321..394d0b1b28f 100644 --- a/arch/blackfin/kernel/cplb-mpu/Makefile +++ b/arch/blackfin/kernel/cplb-mpu/Makefile @@ -2,7 +2,7 @@ # arch/blackfin/kernel/cplb-nompu/Makefile # -obj-y := cplbinit.o cacheinit.o cplbmgr.o +obj-y := cplbinit.o cplbmgr.o CFLAGS_cplbmgr.o := -ffixed-I0 -ffixed-I1 -ffixed-I2 -ffixed-I3 \ -ffixed-L0 -ffixed-L1 -ffixed-L2 -ffixed-L3 \ diff --git a/arch/blackfin/kernel/cplb-mpu/cacheinit.c b/arch/blackfin/kernel/cplb-mpu/cacheinit.c deleted file mode 100644 index d5a86c3017f..00000000000 --- a/arch/blackfin/kernel/cplb-mpu/cacheinit.c +++ /dev/null @@ -1,69 +0,0 @@ -/* - * Copyright 2004-2007 Analog Devices Inc. - * - * 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, see the file COPYING, or write - * to the Free Software Foundation, Inc., - * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA - */ - -#include <linux/cpu.h> - -#include <asm/cacheflush.h> -#include <asm/blackfin.h> -#include <asm/cplb.h> -#include <asm/cplbinit.h> - -#if defined(CONFIG_BFIN_ICACHE) -void __cpuinit bfin_icache_init(struct cplb_entry *icplb_tbl) -{ - unsigned long ctrl; - int i; - - SSYNC(); - for (i = 0; i < MAX_CPLBS; i++) { - bfin_write32(ICPLB_ADDR0 + i * 4, icplb_tbl[i].addr); - bfin_write32(ICPLB_DATA0 + i * 4, icplb_tbl[i].data); - } - ctrl = bfin_read_IMEM_CONTROL(); - ctrl |= IMC | ENICPLB; - bfin_write_IMEM_CONTROL(ctrl); - SSYNC(); -} -#endif - -#if defined(CONFIG_BFIN_DCACHE) -void __cpuinit bfin_dcache_init(struct cplb_entry *dcplb_tbl) -{ - unsigned long ctrl; - int i; - - SSYNC(); - for (i = 0; i < MAX_CPLBS; i++) { - bfin_write32(DCPLB_ADDR0 + i * 4, dcplb_tbl[i].addr); - bfin_write32(DCPLB_DATA0 + i * 4, dcplb_tbl[i].data); - } - - ctrl = bfin_read_DMEM_CONTROL(); - - /* - * Anomaly notes: - * 05000287 - We implement workaround #2 - Change the DMEM_CONTROL - * register, so that the port preferences for DAG0 and DAG1 are set - * to port B - */ - ctrl |= DMEM_CNTR | PORT_PREF0 | (ANOMALY_05000287 ? PORT_PREF1 : 0); - bfin_write_DMEM_CONTROL(ctrl); - SSYNC(); -} -#endif diff --git a/arch/blackfin/kernel/cplb-mpu/cplbmgr.c b/arch/blackfin/kernel/cplb-mpu/cplbmgr.c index bcdfe9b0b71..8e1e9e9e963 100644 --- a/arch/blackfin/kernel/cplb-mpu/cplbmgr.c +++ b/arch/blackfin/kernel/cplb-mpu/cplbmgr.c @@ -22,6 +22,7 @@ #include <asm/blackfin.h> #include <asm/cacheflush.h> +#include <asm/cplb.h> #include <asm/cplbinit.h> #include <asm/mmu_context.h> @@ -41,46 +42,6 @@ int nr_dcplb_miss[NR_CPUS], nr_icplb_miss[NR_CPUS]; int nr_icplb_supv_miss[NR_CPUS], nr_dcplb_prot[NR_CPUS]; int nr_cplb_flush[NR_CPUS]; -static inline void disable_dcplb(void) -{ - unsigned long ctrl; - SSYNC(); - ctrl = bfin_read_DMEM_CONTROL(); - ctrl &= ~ENDCPLB; - bfin_write_DMEM_CONTROL(ctrl); - SSYNC(); -} - -static inline void enable_dcplb(void) -{ - unsigned long ctrl; - SSYNC(); - ctrl = bfin_read_DMEM_CONTROL(); - ctrl |= ENDCPLB; - bfin_write_DMEM_CONTROL(ctrl); - SSYNC(); -} - -static inline void disable_icplb(void) -{ - unsigned long ctrl; - SSYNC(); - ctrl = bfin_read_IMEM_CONTROL(); - ctrl &= ~ENICPLB; - bfin_write_IMEM_CONTROL(ctrl); - SSYNC(); -} - -static inline void enable_icplb(void) -{ - unsigned long ctrl; - SSYNC(); - ctrl = bfin_read_IMEM_CONTROL(); - ctrl |= ENICPLB; - bfin_write_IMEM_CONTROL(ctrl); - SSYNC(); -} - /* * Given the contents of the status register, return the index of the * CPLB that caused the fault. @@ -198,10 +159,10 @@ static noinline int dcplb_miss(unsigned int cpu) dcplb_tbl[cpu][idx].addr = addr; dcplb_tbl[cpu][idx].data = d_data; - disable_dcplb(); + _disable_dcplb(); bfin_write32(DCPLB_DATA0 + idx * 4, d_data); bfin_write32(DCPLB_ADDR0 + idx * 4, addr); - enable_dcplb(); + _enable_dcplb(); return 0; } @@ -288,10 +249,10 @@ static noinline int icplb_miss(unsigned int cpu) icplb_tbl[cpu][idx].addr = addr; icplb_tbl[cpu][idx].data = i_data; - disable_icplb(); + _disable_icplb(); bfin_write32(ICPLB_DATA0 + idx * 4, i_data); bfin_write32(ICPLB_ADDR0 + idx * 4, addr); - enable_icplb(); + _enable_icplb(); return 0; } @@ -319,7 +280,7 @@ static noinline int dcplb_protection_fault(unsigned int cpu) int cplb_hdr(int seqstat, struct pt_regs *regs) { int cause = seqstat & 0x3f; - unsigned int cpu = smp_processor_id(); + unsigned int cpu = raw_smp_processor_id(); switch (cause) { case 0x23: return dcplb_protection_fault(cpu); @@ -340,19 +301,19 @@ void flush_switched_cplbs(unsigned int cpu) nr_cplb_flush[cpu]++; local_irq_save_hw(flags); - disable_icplb(); + _disable_icplb(); for (i = first_switched_icplb; i < MAX_CPLBS; i++) { icplb_tbl[cpu][i].data = 0; bfin_write32(ICPLB_DATA0 + i * 4, 0); } - enable_icplb(); + _enable_icplb(); - disable_dcplb(); + _disable_dcplb(); for (i = first_switched_dcplb; i < MAX_CPLBS; i++) { dcplb_tbl[cpu][i].data = 0; bfin_write32(DCPLB_DATA0 + i * 4, 0); } - enable_dcplb(); + _enable_dcplb(); local_irq_restore_hw(flags); } @@ -385,7 +346,7 @@ void set_mask_dcplbs(unsigned long *masks, unsigned int cpu) #endif } - disable_dcplb(); + _disable_dcplb(); for (i = first_mask_dcplb; i < first_switched_dcplb; i++) { dcplb_tbl[cpu][i].addr = addr; dcplb_tbl[cpu][i].data = d_data; @@ -393,6 +354,6 @@ void set_mask_dcplbs(unsigned long *masks, unsigned int cpu) bfin_write32(DCPLB_ADDR0 + i * 4, addr); addr += PAGE_SIZE; } - enable_dcplb(); + _enable_dcplb(); local_irq_restore_hw(flags); } diff --git a/arch/blackfin/kernel/cplb-nompu/Makefile b/arch/blackfin/kernel/cplb-nompu/Makefile index 7d70d3bf321..394d0b1b28f 100644 --- a/arch/blackfin/kernel/cplb-nompu/Makefile +++ b/arch/blackfin/kernel/cplb-nompu/Makefile @@ -2,7 +2,7 @@ # arch/blackfin/kernel/cplb-nompu/Makefile # -obj-y := cplbinit.o cacheinit.o cplbmgr.o +obj-y := cplbinit.o cplbmgr.o CFLAGS_cplbmgr.o := -ffixed-I0 -ffixed-I1 -ffixed-I2 -ffixed-I3 \ -ffixed-L0 -ffixed-L1 -ffixed-L2 -ffixed-L3 \ diff --git a/arch/blackfin/kernel/cplb-nompu/cacheinit.c b/arch/blackfin/kernel/cplb-nompu/cacheinit.c deleted file mode 100644 index d5a86c3017f..00000000000 --- a/arch/blackfin/kernel/cplb-nompu/cacheinit.c +++ /dev/null @@ -1,69 +0,0 @@ -/* - * Copyright 2004-2007 Analog Devices Inc. - * - * 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, see the file COPYING, or write - * to the Free Software Foundation, Inc., - * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA - */ - -#include <linux/cpu.h> - -#include <asm/cacheflush.h> -#include <asm/blackfin.h> -#include <asm/cplb.h> -#include <asm/cplbinit.h> - -#if defined(CONFIG_BFIN_ICACHE) -void __cpuinit bfin_icache_init(struct cplb_entry *icplb_tbl) -{ - unsigned long ctrl; - int i; - - SSYNC(); - for (i = 0; i < MAX_CPLBS; i++) { - bfin_write32(ICPLB_ADDR0 + i * 4, icplb_tbl[i].addr); - bfin_write32(ICPLB_DATA0 + i * 4, icplb_tbl[i].data); - } - ctrl = bfin_read_IMEM_CONTROL(); - ctrl |= IMC | ENICPLB; - bfin_write_IMEM_CONTROL(ctrl); - SSYNC(); -} -#endif - -#if defined(CONFIG_BFIN_DCACHE) -void __cpuinit bfin_dcache_init(struct cplb_entry *dcplb_tbl) -{ - unsigned long ctrl; - int i; - - SSYNC(); - for (i = 0; i < MAX_CPLBS; i++) { - bfin_write32(DCPLB_ADDR0 + i * 4, dcplb_tbl[i].addr); - bfin_write32(DCPLB_DATA0 + i * 4, dcplb_tbl[i].data); - } - - ctrl = bfin_read_DMEM_CONTROL(); - - /* - * Anomaly notes: - * 05000287 - We implement workaround #2 - Change the DMEM_CONTROL - * register, so that the port preferences for DAG0 and DAG1 are set - * to port B - */ - ctrl |= DMEM_CNTR | PORT_PREF0 | (ANOMALY_05000287 ? PORT_PREF1 : 0); - bfin_write_DMEM_CONTROL(ctrl); - SSYNC(); -} -#endif diff --git a/arch/blackfin/kernel/cplb-nompu/cplbinit.c b/arch/blackfin/kernel/cplb-nompu/cplbinit.c index 685f160a5a3..5d8ad503f82 100644 --- a/arch/blackfin/kernel/cplb-nompu/cplbinit.c +++ b/arch/blackfin/kernel/cplb-nompu/cplbinit.c @@ -36,7 +36,7 @@ int first_switched_icplb PDT_ATTR; int first_switched_dcplb PDT_ATTR; struct cplb_boundary dcplb_bounds[9] PDT_ATTR; -struct cplb_boundary icplb_bounds[7] PDT_ATTR; +struct cplb_boundary icplb_bounds[9] PDT_ATTR; int icplb_nr_bounds PDT_ATTR; int dcplb_nr_bounds PDT_ATTR; @@ -167,14 +167,21 @@ void __init generate_cplb_tables_all(void) icplb_bounds[i_i++].data = (reserved_mem_icache_on ? SDRAM_IGENERIC : SDRAM_INON_CHBL); } + /* Addressing hole up to the async bank. */ + icplb_bounds[i_i].eaddr = ASYNC_BANK0_BASE; + icplb_bounds[i_i++].data = 0; + /* ASYNC banks. */ + icplb_bounds[i_i].eaddr = ASYNC_BANK3_BASE + ASYNC_BANK3_SIZE; + icplb_bounds[i_i++].data = SDRAM_EBIU; /* Addressing hole up to BootROM. */ icplb_bounds[i_i].eaddr = BOOT_ROM_START; icplb_bounds[i_i++].data = 0; /* BootROM -- largest one should be less than 1 meg. */ icplb_bounds[i_i].eaddr = BOOT_ROM_START + (1 * 1024 * 1024); icplb_bounds[i_i++].data = SDRAM_IGENERIC; + if (L2_LENGTH) { - /* Addressing hole up to L2 SRAM, including the async bank. */ + /* Addressing hole up to L2 SRAM. */ icplb_bounds[i_i].eaddr = L2_START; icplb_bounds[i_i++].data = 0; /* L2 SRAM. */ diff --git a/arch/blackfin/kernel/cplb-nompu/cplbmgr.c b/arch/blackfin/kernel/cplb-nompu/cplbmgr.c index 12b030842fd..d9ea46c6e41 100644 --- a/arch/blackfin/kernel/cplb-nompu/cplbmgr.c +++ b/arch/blackfin/kernel/cplb-nompu/cplbmgr.c @@ -48,36 +48,13 @@ int nr_cplb_flush[NR_CPUS], nr_dcplb_prot[NR_CPUS]; #define MGR_ATTR #endif -/* - * We're in an exception handler. The normal cli nop nop workaround - * isn't going to do very much, as the only thing that can interrupt - * us is an NMI, and the cli isn't going to stop that. - */ -#define NOWA_SSYNC __asm__ __volatile__ ("ssync;") - -/* Anomaly handlers provide SSYNCs, so avoid extra if anomaly is present */ -#if ANOMALY_05000125 - -#define bfin_write_DMEM_CONTROL_SSYNC(v) bfin_write_DMEM_CONTROL(v) -#define bfin_write_IMEM_CONTROL_SSYNC(v) bfin_write_IMEM_CONTROL(v) - -#else - -#define bfin_write_DMEM_CONTROL_SSYNC(v) \ - do { NOWA_SSYNC; bfin_write_DMEM_CONTROL(v); NOWA_SSYNC; } while (0) -#define bfin_write_IMEM_CONTROL_SSYNC(v) \ - do { NOWA_SSYNC; bfin_write_IMEM_CONTROL(v); NOWA_SSYNC; } while (0) - -#endif - static inline void write_dcplb_data(int cpu, int idx, unsigned long data, unsigned long addr) { - unsigned long ctrl = bfin_read_DMEM_CONTROL(); - bfin_write_DMEM_CONTROL_SSYNC(ctrl & ~ENDCPLB); + _disable_dcplb(); bfin_write32(DCPLB_DATA0 + idx * 4, data); bfin_write32(DCPLB_ADDR0 + idx * 4, addr); - bfin_write_DMEM_CONTROL_SSYNC(ctrl); + _enable_dcplb(); #ifdef CONFIG_CPLB_INFO dcplb_tbl[cpu][idx].addr = addr; @@ -88,12 +65,10 @@ static inline void write_dcplb_data(int cpu, int idx, unsigned long data, static inline void write_icplb_data(int cpu, int idx, unsigned long data, unsigned long addr) { - unsigned long ctrl = bfin_read_IMEM_CONTROL(); - - bfin_write_IMEM_CONTROL_SSYNC(ctrl & ~ENICPLB); + _disable_icplb(); bfin_write32(ICPLB_DATA0 + idx * 4, data); bfin_write32(ICPLB_ADDR0 + idx * 4, addr); - bfin_write_IMEM_CONTROL_SSYNC(ctrl); + _enable_icplb(); #ifdef CONFIG_CPLB_INFO icplb_tbl[cpu][idx].addr = addr; @@ -227,7 +202,7 @@ MGR_ATTR static int dcplb_miss(int cpu) MGR_ATTR int cplb_hdr(int seqstat, struct pt_regs *regs) { int cause = seqstat & 0x3f; - unsigned int cpu = smp_processor_id(); + unsigned int cpu = raw_smp_processor_id(); switch (cause) { case VEC_CPLB_I_M: return icplb_miss(cpu); diff --git a/arch/blackfin/kernel/early_printk.c b/arch/blackfin/kernel/early_printk.c index 2ab56811841..931c78b5ea1 100644 --- a/arch/blackfin/kernel/early_printk.c +++ b/arch/blackfin/kernel/early_printk.c @@ -27,6 +27,7 @@ #include <linux/serial_core.h> #include <linux/console.h> #include <linux/string.h> +#include <linux/reboot.h> #include <asm/blackfin.h> #include <asm/irq_handler.h> #include <asm/early_printk.h> @@ -181,6 +182,22 @@ asmlinkage void __init init_early_exception_vectors(void) u32 evt; SSYNC(); + /* + * This starts up the shadow buffer, incase anything crashes before + * setup arch + */ + mark_shadow_error(); + early_shadow_puts(linux_banner); + early_shadow_stamp(); + + if (CPUID != bfin_cpuid()) { + early_shadow_puts("Running on wrong machine type, expected"); + early_shadow_reg(CPUID, 16); + early_shadow_puts(", but running on"); + early_shadow_reg(bfin_cpuid(), 16); + early_shadow_puts("\n"); + } + /* cannot program in software: * evt0 - emulation (jtag) * evt1 - reset @@ -199,6 +216,7 @@ asmlinkage void __init init_early_exception_vectors(void) } +__attribute__((__noreturn__)) asmlinkage void __init early_trap_c(struct pt_regs *fp, void *retaddr) { /* This can happen before the uart is initialized, so initialize @@ -210,10 +228,58 @@ asmlinkage void __init early_trap_c(struct pt_regs *fp, void *retaddr) if (likely(early_console == NULL) && CPUID == bfin_cpuid()) setup_early_printk(DEFAULT_EARLY_PORT); - printk(KERN_EMERG "Early panic\n"); - dump_bfin_mem(fp); - show_regs(fp); - dump_bfin_trace_buffer(); + if (!shadow_console_enabled()) { + /* crap - we crashed before setup_arch() */ + early_shadow_puts("panic before setup_arch\n"); + early_shadow_puts("IPEND:"); + early_shadow_reg(fp->ipend, 16); + if (fp->seqstat & SEQSTAT_EXCAUSE) { + early_shadow_puts("\nEXCAUSE:"); + early_shadow_reg(fp->seqstat & SEQSTAT_EXCAUSE, 8); + } + if (fp->seqstat & SEQSTAT_HWERRCAUSE) { + early_shadow_puts("\nHWERRCAUSE:"); + early_shadow_reg( + (fp->seqstat & SEQSTAT_HWERRCAUSE) >> 14, 8); + } + early_shadow_puts("\nErr @"); + if (fp->ipend & EVT_EVX) + early_shadow_reg(fp->retx, 32); + else + early_shadow_reg(fp->pc, 32); +#ifdef CONFIG_DEBUG_BFIN_HWTRACE_ON + early_shadow_puts("\nTrace:"); + if (likely(bfin_read_TBUFSTAT() & TBUFCNT)) { + while (bfin_read_TBUFSTAT() & TBUFCNT) { + early_shadow_puts("\nT :"); + early_shadow_reg(bfin_read_TBUF(), 32); + early_shadow_puts("\n S :"); + early_shadow_reg(bfin_read_TBUF(), 32); + } + } +#endif + early_shadow_puts("\nUse bfin-elf-addr2line to determine " + "function names\n"); + /* + * We should panic(), but we can't - since panic calls printk, + * and printk uses memcpy. + * we want to reboot, but if the machine type is different, + * can't due to machine specific reboot sequences + */ + if (CPUID == bfin_cpuid()) { + early_shadow_puts("Trying to restart\n"); + machine_restart(""); + } + + early_shadow_puts("Halting, since it is not safe to restart\n"); + while (1) + asm volatile ("EMUEXCPT; IDLE;\n"); + + } else { + printk(KERN_EMERG "Early panic\n"); + show_regs(fp); + dump_bfin_trace_buffer(); + } panic("Died early"); } diff --git a/arch/blackfin/kernel/entry.S b/arch/blackfin/kernel/entry.S index a9cfba9946b..3f8769b7db5 100644 --- a/arch/blackfin/kernel/entry.S +++ b/arch/blackfin/kernel/entry.S @@ -43,8 +43,28 @@ ENTRY(_ret_from_fork) #ifdef CONFIG_IPIPE - [--sp] = reti; /* IRQs on. */ - SP += 4; + /* + * Hw IRQs are off on entry, and we don't want the scheduling tail + * code to starve high priority domains from interrupts while it + * runs. Therefore we first stall the root stage to have the + * virtual interrupt state reflect IMASK. + */ + p0.l = ___ipipe_root_status; + p0.h = ___ipipe_root_status; + r4 = [p0]; + bitset(r4, 0); + [p0] = r4; + /* + * Then we may enable hw IRQs, allowing preemption from high + * priority domains. schedule_tail() will do local_irq_enable() + * since Blackfin does not define __ARCH_WANT_UNLOCKED_CTXSW, so + * there is no need to unstall the root domain by ourselves + * afterwards. + */ + p0.l = _bfin_irq_flags; + p0.h = _bfin_irq_flags; + r4 = [p0]; + sti r4; #endif /* CONFIG_IPIPE */ SP += -12; call _schedule_tail; diff --git a/arch/blackfin/kernel/ftrace-entry.S b/arch/blackfin/kernel/ftrace-entry.S index 6980b7a0615..76dd4fbcd17 100644 --- a/arch/blackfin/kernel/ftrace-entry.S +++ b/arch/blackfin/kernel/ftrace-entry.S @@ -17,8 +17,8 @@ * only one we can blow away. With pointer registers, we have P0-P2. * * Upon entry, the RETS will point to the top of the current profiled - * function. And since GCC setup the frame for us, the previous function - * will be waiting there. mmmm pie. + * function. And since GCC pushed the previous RETS for us, the previous + * function will be waiting there. mmmm pie. */ ENTRY(__mcount) /* save third function arg early so we can do testing below */ @@ -70,14 +70,14 @@ ENTRY(__mcount) /* setup the tracer function */ p0 = r3; - /* tracer(ulong frompc, ulong selfpc): - * frompc: the pc that did the call to ... - * selfpc: ... this location - * the selfpc itself will need adjusting for the mcount call + /* function_trace_call(unsigned long ip, unsigned long parent_ip): + * ip: this point was called by ... + * parent_ip: ... this function + * the ip itself will need adjusting for the mcount call */ - r1 = rets; - r0 = [fp + 4]; - r1 += -MCOUNT_INSN_SIZE; + r0 = rets; + r1 = [sp + 16]; /* skip the 4 local regs on stack */ + r0 += -MCOUNT_INSN_SIZE; /* call the tracer */ call (p0); @@ -106,9 +106,10 @@ ENTRY(_ftrace_graph_caller) [--sp] = r1; [--sp] = rets; - r0 = fp; + /* prepare_ftrace_return(unsigned long *parent, unsigned long self_addr) */ + r0 = sp; r1 = rets; - r0 += 4; + r0 += 16; /* skip the 4 local regs on stack */ r1 += -MCOUNT_INSN_SIZE; call _prepare_ftrace_return; diff --git a/arch/blackfin/kernel/ftrace.c b/arch/blackfin/kernel/ftrace.c index 905bfc40a00..f2c85ac6f2d 100644 --- a/arch/blackfin/kernel/ftrace.c +++ b/arch/blackfin/kernel/ftrace.c @@ -24,7 +24,7 @@ void prepare_ftrace_return(unsigned long *parent, unsigned long self_addr) if (unlikely(atomic_read(¤t->tracing_graph_pause))) return; - if (ftrace_push_return_trace(*parent, self_addr, &trace.depth) == -EBUSY) + if (ftrace_push_return_trace(*parent, self_addr, &trace.depth, 0) == -EBUSY) return; trace.func = self_addr; diff --git a/arch/blackfin/kernel/ipipe.c b/arch/blackfin/kernel/ipipe.c index b8d22034b9a..5d7382396dc 100644 --- a/arch/blackfin/kernel/ipipe.c +++ b/arch/blackfin/kernel/ipipe.c @@ -30,10 +30,10 @@ #include <linux/slab.h> #include <linux/errno.h> #include <linux/kthread.h> -#include <asm/unistd.h> +#include <linux/unistd.h> +#include <linux/io.h> #include <asm/system.h> #include <asm/atomic.h> -#include <asm/io.h> DEFINE_PER_CPU(struct pt_regs, __ipipe_tick_regs); @@ -90,6 +90,7 @@ void __ipipe_handle_irq(unsigned irq, struct pt_regs *regs) struct ipipe_percpu_domain_data *p = ipipe_root_cpudom_ptr(); struct ipipe_domain *this_domain, *next_domain; struct list_head *head, *pos; + struct ipipe_irqdesc *idesc; int m_ack, s = -1; /* @@ -100,17 +101,20 @@ void __ipipe_handle_irq(unsigned irq, struct pt_regs *regs) */ m_ack = (regs == NULL || irq == IRQ_SYSTMR || irq == IRQ_CORETMR); this_domain = __ipipe_current_domain; + idesc = &this_domain->irqs[irq]; - if (unlikely(test_bit(IPIPE_STICKY_FLAG, &this_domain->irqs[irq].control))) + if (unlikely(test_bit(IPIPE_STICKY_FLAG, &idesc->control))) head = &this_domain->p_link; else { head = __ipipe_pipeline.next; next_domain = list_entry(head, struct ipipe_domain, p_link); - if (likely(test_bit(IPIPE_WIRED_FLAG, &next_domain->irqs[irq].control))) { - if (!m_ack && next_domain->irqs[irq].acknowledge != NULL) - next_domain->irqs[irq].acknowledge(irq, irq_to_desc(irq)); + idesc = &next_domain->irqs[irq]; + if (likely(test_bit(IPIPE_WIRED_FLAG, &idesc->control))) { + if (!m_ack && idesc->acknowledge != NULL) + idesc->acknowledge(irq, irq_to_desc(irq)); if (test_bit(IPIPE_SYNCDEFER_FLAG, &p->status)) - s = __test_and_set_bit(IPIPE_STALL_FLAG, &p->status); + s = __test_and_set_bit(IPIPE_STALL_FLAG, + &p->status); __ipipe_dispatch_wired(next_domain, irq); goto out; } @@ -121,14 +125,15 @@ void __ipipe_handle_irq(unsigned irq, struct pt_regs *regs) pos = head; while (pos != &__ipipe_pipeline) { next_domain = list_entry(pos, struct ipipe_domain, p_link); - if (test_bit(IPIPE_HANDLE_FLAG, &next_domain->irqs[irq].control)) { + idesc = &next_domain->irqs[irq]; + if (test_bit(IPIPE_HANDLE_FLAG, &idesc->control)) { __ipipe_set_irq_pending(next_domain, irq); - if (!m_ack && next_domain->irqs[irq].acknowledge != NULL) { - next_domain->irqs[irq].acknowledge(irq, irq_to_desc(irq)); + if (!m_ack && idesc->acknowledge != NULL) { + idesc->acknowledge(irq, irq_to_desc(irq)); m_ack = 1; } } - if (!test_bit(IPIPE_PASS_FLAG, &next_domain->irqs[irq].control)) + if (!test_bit(IPIPE_PASS_FLAG, &idesc->control)) break; pos = next_domain->p_link.next; } @@ -159,11 +164,6 @@ out: __clear_bit(IPIPE_STALL_FLAG, &p->status); } -int __ipipe_check_root(void) -{ - return ipipe_root_domain_p; -} - void __ipipe_enable_irqdesc(struct ipipe_domain *ipd, unsigned irq) { struct irq_desc *desc = irq_to_desc(irq); @@ -186,30 +186,6 @@ void __ipipe_disable_irqdesc(struct ipipe_domain *ipd, unsigned irq) } EXPORT_SYMBOL(__ipipe_disable_irqdesc); -void __ipipe_stall_root_raw(void) -{ - /* - * This code is called by the ins{bwl} routines (see - * arch/blackfin/lib/ins.S), which are heavily used by the - * network stack. It masks all interrupts but those handled by - * non-root domains, so that we keep decent network transfer - * rates for Linux without inducing pathological jitter for - * the real-time domain. - */ - __asm__ __volatile__ ("sti %0;" : : "d"(__ipipe_irq_lvmask)); - - __set_bit(IPIPE_STALL_FLAG, - &ipipe_root_cpudom_var(status)); -} - -void __ipipe_unstall_root_raw(void) -{ - __clear_bit(IPIPE_STALL_FLAG, - &ipipe_root_cpudom_var(status)); - - __asm__ __volatile__ ("sti %0;" : : "d"(bfin_irq_flags)); -} - int __ipipe_syscall_root(struct pt_regs *regs) { struct ipipe_percpu_domain_data *p; @@ -333,12 +309,29 @@ asmlinkage void __ipipe_sync_root(void) void ___ipipe_sync_pipeline(unsigned long syncmask) { - if (__ipipe_root_domain_p) { - if (test_bit(IPIPE_SYNCDEFER_FLAG, &ipipe_root_cpudom_var(status))) - return; - } + if (__ipipe_root_domain_p && + test_bit(IPIPE_SYNCDEFER_FLAG, &ipipe_root_cpudom_var(status))) + return; __ipipe_sync_stage(syncmask); } -EXPORT_SYMBOL(show_stack); +void __ipipe_disable_root_irqs_hw(void) +{ + /* + * This code is called by the ins{bwl} routines (see + * arch/blackfin/lib/ins.S), which are heavily used by the + * network stack. It masks all interrupts but those handled by + * non-root domains, so that we keep decent network transfer + * rates for Linux without inducing pathological jitter for + * the real-time domain. + */ + bfin_sti(__ipipe_irq_lvmask); + __set_bit(IPIPE_STALL_FLAG, &ipipe_root_cpudom_var(status)); +} + +void __ipipe_enable_root_irqs_hw(void) +{ + __clear_bit(IPIPE_STALL_FLAG, &ipipe_root_cpudom_var(status)); + bfin_sti(bfin_irq_flags); +} diff --git a/arch/blackfin/kernel/kgdb_test.c b/arch/blackfin/kernel/kgdb_test.c index dbcf3e45cb0..59fc42dc5d6 100644 --- a/arch/blackfin/kernel/kgdb_test.c +++ b/arch/blackfin/kernel/kgdb_test.c @@ -54,7 +54,7 @@ void kgdb_l2_test(void) int kgdb_test(char *name, int len, int count, int z) { - printk(KERN_DEBUG "kgdb name(%d): %s, %d, %d\n", len, name, count, z); + printk(KERN_ALERT "kgdb name(%d): %s, %d, %d\n", len, name, count, z); count = z; return count; } diff --git a/arch/blackfin/kernel/module.c b/arch/blackfin/kernel/module.c index d5aee362668..67fc7a56c86 100644 --- a/arch/blackfin/kernel/module.c +++ b/arch/blackfin/kernel/module.c @@ -27,6 +27,7 @@ * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA */ +#define pr_fmt(fmt) "module %s: " fmt #include <linux/moduleloader.h> #include <linux/elf.h> @@ -36,6 +37,7 @@ #include <linux/kernel.h> #include <asm/dma.h> #include <asm/cacheflush.h> +#include <asm/uaccess.h> void *module_alloc(unsigned long size) { @@ -52,7 +54,7 @@ void module_free(struct module *mod, void *module_region) /* Transfer the section to the L1 memory */ int -module_frob_arch_sections(Elf_Ehdr * hdr, Elf_Shdr * sechdrs, +module_frob_arch_sections(Elf_Ehdr *hdr, Elf_Shdr *sechdrs, char *secstrings, struct module *mod) { /* @@ -63,126 +65,119 @@ module_frob_arch_sections(Elf_Ehdr * hdr, Elf_Shdr * sechdrs, * NOTE: this breaks the semantic of mod->arch structure. */ Elf_Shdr *s, *sechdrs_end = sechdrs + hdr->e_shnum; - void *dest = NULL; + void *dest; for (s = sechdrs; s < sechdrs_end; ++s) { - if ((strcmp(".l1.text", secstrings + s->sh_name) == 0) || - ((strcmp(".text", secstrings + s->sh_name) == 0) && - (hdr->e_flags & EF_BFIN_CODE_IN_L1) && (s->sh_size > 0))) { + const char *shname = secstrings + s->sh_name; + + if (s->sh_size == 0) + continue; + + if (!strcmp(".l1.text", shname) || + (!strcmp(".text", shname) && + (hdr->e_flags & EF_BFIN_CODE_IN_L1))) { + dest = l1_inst_sram_alloc(s->sh_size); mod->arch.text_l1 = dest; if (dest == NULL) { - printk(KERN_ERR - "module %s: L1 instruction memory allocation failed\n", - mod->name); + pr_err("L1 inst memory allocation failed\n", + mod->name); return -1; } dma_memcpy(dest, (void *)s->sh_addr, s->sh_size); - s->sh_flags &= ~SHF_ALLOC; - s->sh_addr = (unsigned long)dest; - } - if ((strcmp(".l1.data", secstrings + s->sh_name) == 0) || - ((strcmp(".data", secstrings + s->sh_name) == 0) && - (hdr->e_flags & EF_BFIN_DATA_IN_L1) && (s->sh_size > 0))) { + + } else if (!strcmp(".l1.data", shname) || + (!strcmp(".data", shname) && + (hdr->e_flags & EF_BFIN_DATA_IN_L1))) { + dest = l1_data_sram_alloc(s->sh_size); mod->arch.data_a_l1 = dest; if (dest == NULL) { - printk(KERN_ERR - "module %s: L1 data memory allocation failed\n", + pr_err("L1 data memory allocation failed\n", mod->name); return -1; } memcpy(dest, (void *)s->sh_addr, s->sh_size); - s->sh_flags &= ~SHF_ALLOC; - s->sh_addr = (unsigned long)dest; - } - if (strcmp(".l1.bss", secstrings + s->sh_name) == 0 || - ((strcmp(".bss", secstrings + s->sh_name) == 0) && - (hdr->e_flags & EF_BFIN_DATA_IN_L1) && (s->sh_size > 0))) { - dest = l1_data_sram_alloc(s->sh_size); + + } else if (!strcmp(".l1.bss", shname) || + (!strcmp(".bss", shname) && + (hdr->e_flags & EF_BFIN_DATA_IN_L1))) { + + dest = l1_data_sram_zalloc(s->sh_size); mod->arch.bss_a_l1 = dest; if (dest == NULL) { - printk(KERN_ERR - "module %s: L1 data memory allocation failed\n", + pr_err("L1 data memory allocation failed\n", mod->name); return -1; } - memset(dest, 0, s->sh_size); - s->sh_flags &= ~SHF_ALLOC; - s->sh_addr = (unsigned long)dest; - } - if (strcmp(".l1.data.B", secstrings + s->sh_name) == 0) { + + } else if (!strcmp(".l1.data.B", shname)) { + dest = l1_data_B_sram_alloc(s->sh_size); mod->arch.data_b_l1 = dest; if (dest == NULL) { - printk(KERN_ERR - "module %s: L1 data memory allocation failed\n", + pr_err("L1 data memory allocation failed\n", mod->name); return -1; } memcpy(dest, (void *)s->sh_addr, s->sh_size); - s->sh_flags &= ~SHF_ALLOC; - s->sh_addr = (unsigned long)dest; - } - if (strcmp(".l1.bss.B", secstrings + s->sh_name) == 0) { + + } else if (!strcmp(".l1.bss.B", shname)) { + dest = l1_data_B_sram_alloc(s->sh_size); mod->arch.bss_b_l1 = dest; if (dest == NULL) { - printk(KERN_ERR - "module %s: L1 data memory allocation failed\n", + pr_err("L1 data memory allocation failed\n", mod->name); return -1; } memset(dest, 0, s->sh_size); - s->sh_flags &= ~SHF_ALLOC; - s->sh_addr = (unsigned long)dest; - } - if ((strcmp(".l2.text", secstrings + s->sh_name) == 0) || - ((strcmp(".text", secstrings + s->sh_name) == 0) && - (hdr->e_flags & EF_BFIN_CODE_IN_L2) && (s->sh_size > 0))) { + + } else if (!strcmp(".l2.text", shname) || + (!strcmp(".text", shname) && + (hdr->e_flags & EF_BFIN_CODE_IN_L2))) { + dest = l2_sram_alloc(s->sh_size); mod->arch.text_l2 = dest; if (dest == NULL) { - printk(KERN_ERR - "module %s: L2 SRAM allocation failed\n", - mod->name); + pr_err("L2 SRAM allocation failed\n", + mod->name); return -1; } memcpy(dest, (void *)s->sh_addr, s->sh_size); - s->sh_flags &= ~SHF_ALLOC; - s->sh_addr = (unsigned long)dest; - } - if ((strcmp(".l2.data", secstrings + s->sh_name) == 0) || - ((strcmp(".data", secstrings + s->sh_name) == 0) && - (hdr->e_flags & EF_BFIN_DATA_IN_L2) && (s->sh_size > 0))) { + + } else if (!strcmp(".l2.data", shname) || + (!strcmp(".data", shname) && + (hdr->e_flags & EF_BFIN_DATA_IN_L2))) { + dest = l2_sram_alloc(s->sh_size); mod->arch.data_l2 = dest; if (dest == NULL) { - printk(KERN_ERR - "module %s: L2 SRAM allocation failed\n", + pr_err("L2 SRAM allocation failed\n", mod->name); return -1; } memcpy(dest, (void *)s->sh_addr, s->sh_size); - s->sh_flags &= ~SHF_ALLOC; - s->sh_addr = (unsigned long)dest; - } - if (strcmp(".l2.bss", secstrings + s->sh_name) == 0 || - ((strcmp(".bss", secstrings + s->sh_name) == 0) && - (hdr->e_flags & EF_BFIN_DATA_IN_L2) && (s->sh_size > 0))) { - dest = l2_sram_alloc(s->sh_size); + + } else if (!strcmp(".l2.bss", shname) || + (!strcmp(".bss", shname) && + (hdr->e_flags & EF_BFIN_DATA_IN_L2))) { + + dest = l2_sram_zalloc(s->sh_size); mod->arch.bss_l2 = dest; if (dest == NULL) { - printk(KERN_ERR - "module %s: L2 SRAM allocation failed\n", + pr_err("L2 SRAM allocation failed\n", mod->name); return -1; } - memset(dest, 0, s->sh_size); - s->sh_flags &= ~SHF_ALLOC; - s->sh_addr = (unsigned long)dest; - } + + } else + continue; + + s->sh_flags &= ~SHF_ALLOC; + s->sh_addr = (unsigned long)dest; } + return 0; } @@ -190,7 +185,7 @@ int apply_relocate(Elf_Shdr * sechdrs, const char *strtab, unsigned int symindex, unsigned int relsec, struct module *me) { - printk(KERN_ERR "module %s: .rel unsupported\n", me->name); + pr_err(".rel unsupported\n", me->name); return -ENOEXEC; } @@ -205,109 +200,86 @@ apply_relocate(Elf_Shdr * sechdrs, const char *strtab, /* gas does not generate it. */ /*************************************************************************/ int -apply_relocate_add(Elf_Shdr * sechdrs, const char *strtab, +apply_relocate_add(Elf_Shdr *sechdrs, const char *strtab, unsigned int symindex, unsigned int relsec, struct module *mod) { unsigned int i; - unsigned short tmp; Elf32_Rela *rel = (void *)sechdrs[relsec].sh_addr; Elf32_Sym *sym; - uint32_t *location32; - uint16_t *location16; - uint32_t value; + unsigned long location, value, size; + + pr_debug("applying relocate section %u to %u\n", mod->name, + relsec, sechdrs[relsec].sh_info); - pr_debug("Applying relocate section %u to %u\n", relsec, - sechdrs[relsec].sh_info); for (i = 0; i < sechdrs[relsec].sh_size / sizeof(*rel); i++) { /* This is where to make the change */ - location16 = - (uint16_t *) (sechdrs[sechdrs[relsec].sh_info].sh_addr + - rel[i].r_offset); - location32 = (uint32_t *) location16; + location = sechdrs[sechdrs[relsec].sh_info].sh_addr + + rel[i].r_offset; + /* This is the symbol it is referring to. Note that all undefined symbols have been resolved. */ sym = (Elf32_Sym *) sechdrs[symindex].sh_addr + ELF32_R_SYM(rel[i].r_info); value = sym->st_value; value += rel[i].r_addend; - pr_debug("location is %x, value is %x type is %d \n", - (unsigned int) location32, value, - ELF32_R_TYPE(rel[i].r_info)); + #ifdef CONFIG_SMP - if ((unsigned long)location16 >= COREB_L1_DATA_A_START) { - printk(KERN_ERR "module %s: cannot relocate in L1: %u (SMP kernel)", - mod->name, ELF32_R_TYPE(rel[i].r_info)); + if (location >= COREB_L1_DATA_A_START) { + pr_err("cannot relocate in L1: %u (SMP kernel)", + mod->name, ELF32_R_TYPE(rel[i].r_info)); return -ENOEXEC; } #endif + + pr_debug("location is %lx, value is %lx type is %d\n", + mod->name, location, value, ELF32_R_TYPE(rel[i].r_info)); + switch (ELF32_R_TYPE(rel[i].r_info)) { + case R_BFIN_HUIMM16: + value >>= 16; + case R_BFIN_LUIMM16: + case R_BFIN_RIMM16: + size = 2; + break; + case R_BFIN_BYTE4_DATA: + size = 4; + break; + case R_BFIN_PCREL24: case R_BFIN_PCREL24_JUMP_L: - /* Add the value, subtract its postition */ - location16 = - (uint16_t *) (sechdrs[sechdrs[relsec].sh_info]. - sh_addr + rel[i].r_offset - 2); - location32 = (uint32_t *) location16; - value -= (uint32_t) location32; - value >>= 1; - if ((value & 0xFF000000) != 0 && - (value & 0xFF000000) != 0xFF000000) { - printk(KERN_ERR "module %s: relocation overflow\n", - mod->name); - return -ENOEXEC; - } - pr_debug("value is %x, before %x-%x after %x-%x\n", value, - *location16, *(location16 + 1), - (*location16 & 0xff00) | (value >> 16 & 0x00ff), - value & 0xffff); - *location16 = - (*location16 & 0xff00) | (value >> 16 & 0x00ff); - *(location16 + 1) = value & 0xffff; - break; case R_BFIN_PCREL12_JUMP: case R_BFIN_PCREL12_JUMP_S: - value -= (uint32_t) location32; - value >>= 1; - *location16 = (value & 0xfff); - break; case R_BFIN_PCREL10: - value -= (uint32_t) location32; - value >>= 1; - *location16 = (value & 0x3ff); - break; - case R_BFIN_LUIMM16: - pr_debug("before %x after %x\n", *location16, - (value & 0xffff)); - tmp = (value & 0xffff); - if ((unsigned long)location16 >= L1_CODE_START) { - dma_memcpy(location16, &tmp, 2); - } else - *location16 = tmp; - break; - case R_BFIN_HUIMM16: - pr_debug("before %x after %x\n", *location16, - ((value >> 16) & 0xffff)); - tmp = ((value >> 16) & 0xffff); - if ((unsigned long)location16 >= L1_CODE_START) { - dma_memcpy(location16, &tmp, 2); - } else - *location16 = tmp; + pr_err("unsupported relocation: %u (no -mlong-calls?)\n", + mod->name, ELF32_R_TYPE(rel[i].r_info)); + return -ENOEXEC; + + default: + pr_err("unknown relocation: %u\n", mod->name, + ELF32_R_TYPE(rel[i].r_info)); + return -ENOEXEC; + } + + switch (bfin_mem_access_type(location, size)) { + case BFIN_MEM_ACCESS_CORE: + case BFIN_MEM_ACCESS_CORE_ONLY: + memcpy((void *)location, &value, size); break; - case R_BFIN_RIMM16: - *location16 = (value & 0xffff); + case BFIN_MEM_ACCESS_DMA: + dma_memcpy((void *)location, &value, size); break; - case R_BFIN_BYTE4_DATA: - pr_debug("before %x after %x\n", *location32, value); - *location32 = value; + case BFIN_MEM_ACCESS_ITEST: + isram_memcpy((void *)location, &value, size); break; default: - printk(KERN_ERR "module %s: Unknown relocation: %u\n", - mod->name, ELF32_R_TYPE(rel[i].r_info)); + pr_err("invalid relocation for %#lx\n", + mod->name, location); return -ENOEXEC; } } + return 0; } @@ -332,22 +304,28 @@ module_finalize(const Elf_Ehdr * hdr, for (i = 1; i < hdr->e_shnum; i++) { const char *strtab = (char *)sechdrs[strindex].sh_addr; unsigned int info = sechdrs[i].sh_info; + const char *shname = secstrings + sechdrs[i].sh_name; /* Not a valid relocation section? */ if (info >= hdr->e_shnum) continue; - if ((sechdrs[i].sh_type == SHT_RELA) && - ((strcmp(".rela.l2.text", secstrings + sechdrs[i].sh_name) == 0) || - (strcmp(".rela.l1.text", secstrings + sechdrs[i].sh_name) == 0) || - ((strcmp(".rela.text", secstrings + sechdrs[i].sh_name) == 0) && - (hdr->e_flags & (EF_BFIN_CODE_IN_L1|EF_BFIN_CODE_IN_L2))))) { + /* Only support RELA relocation types */ + if (sechdrs[i].sh_type != SHT_RELA) + continue; + + if (!strcmp(".rela.l2.text", shname) || + !strcmp(".rela.l1.text", shname) || + (!strcmp(".rela.text", shname) && + (hdr->e_flags & (EF_BFIN_CODE_IN_L1 | EF_BFIN_CODE_IN_L2)))) { + err = apply_relocate_add((Elf_Shdr *) sechdrs, strtab, symindex, i, mod); if (err < 0) return -ENOEXEC; } } + return 0; } diff --git a/arch/blackfin/kernel/process.c b/arch/blackfin/kernel/process.c index 9da36bab7cc..f5b28618964 100644 --- a/arch/blackfin/kernel/process.c +++ b/arch/blackfin/kernel/process.c @@ -282,25 +282,19 @@ void finish_atomic_sections (struct pt_regs *regs) { int __user *up0 = (int __user *)regs->p0; - if (regs->pc < ATOMIC_SEQS_START || regs->pc >= ATOMIC_SEQS_END) - return; - switch (regs->pc) { case ATOMIC_XCHG32 + 2: put_user(regs->r1, up0); - regs->pc += 2; + regs->pc = ATOMIC_XCHG32 + 4; break; case ATOMIC_CAS32 + 2: case ATOMIC_CAS32 + 4: if (regs->r0 == regs->r1) + case ATOMIC_CAS32 + 6: put_user(regs->r2, up0); regs->pc = ATOMIC_CAS32 + 8; break; - case ATOMIC_CAS32 + 6: - put_user(regs->r2, up0); - regs->pc += 2; - break; case ATOMIC_ADD32 + 2: regs->r0 = regs->r1 + regs->r0; diff --git a/arch/blackfin/kernel/ptrace.c b/arch/blackfin/kernel/ptrace.c index 6a387eec6b6..30f4828277a 100644 --- a/arch/blackfin/kernel/ptrace.c +++ b/arch/blackfin/kernel/ptrace.c @@ -206,6 +206,7 @@ long arch_ptrace(struct task_struct *child, long request, long addr, long data) { int ret; unsigned long __user *datap = (unsigned long __user *)data; + void *paddr = (void *)addr; switch (request) { /* when I and D space are separate, these will need to be fixed. */ @@ -215,42 +216,49 @@ long arch_ptrace(struct task_struct *child, long request, long addr, long data) case PTRACE_PEEKTEXT: /* read word at location addr. */ { unsigned long tmp = 0; - int copied; + int copied = 0, to_copy = sizeof(tmp); ret = -EIO; - pr_debug("ptrace: PEEKTEXT at addr 0x%08lx + %ld\n", addr, sizeof(data)); - if (is_user_addr_valid(child, addr, sizeof(tmp)) < 0) + pr_debug("ptrace: PEEKTEXT at addr 0x%08lx + %i\n", addr, to_copy); + if (is_user_addr_valid(child, addr, to_copy) < 0) break; pr_debug("ptrace: user address is valid\n"); - if (L1_CODE_LENGTH != 0 && addr >= get_l1_code_start() - && addr + sizeof(tmp) <= get_l1_code_start() + L1_CODE_LENGTH) { - safe_dma_memcpy (&tmp, (const void *)(addr), sizeof(tmp)); - copied = sizeof(tmp); - - } else if (L1_DATA_A_LENGTH != 0 && addr >= L1_DATA_A_START - && addr + sizeof(tmp) <= L1_DATA_A_START + L1_DATA_A_LENGTH) { - memcpy(&tmp, (const void *)(addr), sizeof(tmp)); - copied = sizeof(tmp); - - } else if (L1_DATA_B_LENGTH != 0 && addr >= L1_DATA_B_START - && addr + sizeof(tmp) <= L1_DATA_B_START + L1_DATA_B_LENGTH) { - memcpy(&tmp, (const void *)(addr), sizeof(tmp)); - copied = sizeof(tmp); - - } else if (addr >= FIXED_CODE_START - && addr + sizeof(tmp) <= FIXED_CODE_END) { - copy_from_user_page(0, 0, 0, &tmp, (const void *)(addr), sizeof(tmp)); - copied = sizeof(tmp); - - } else + switch (bfin_mem_access_type(addr, to_copy)) { + case BFIN_MEM_ACCESS_CORE: + case BFIN_MEM_ACCESS_CORE_ONLY: copied = access_process_vm(child, addr, &tmp, - sizeof(tmp), 0); + to_copy, 0); + if (copied) + break; + + /* hrm, why didn't that work ... maybe no mapping */ + if (addr >= FIXED_CODE_START && + addr + to_copy <= FIXED_CODE_END) { + copy_from_user_page(0, 0, 0, &tmp, paddr, to_copy); + copied = to_copy; + } else if (addr >= BOOT_ROM_START) { + memcpy(&tmp, paddr, to_copy); + copied = to_copy; + } - pr_debug("ptrace: copied size %d [0x%08lx]\n", copied, tmp); - if (copied != sizeof(tmp)) break; - ret = put_user(tmp, datap); + case BFIN_MEM_ACCESS_DMA: + if (safe_dma_memcpy(&tmp, paddr, to_copy)) + copied = to_copy; + break; + case BFIN_MEM_ACCESS_ITEST: + if (isram_memcpy(&tmp, paddr, to_copy)) + copied = to_copy; + break; + default: + copied = 0; + break; + } + + pr_debug("ptrace: copied size %d [0x%08lx]\n", copied, tmp); + if (copied == to_copy) + ret = put_user(tmp, datap); break; } @@ -277,9 +285,9 @@ long arch_ptrace(struct task_struct *child, long request, long addr, long data) tmp = child->mm->start_data; #ifdef CONFIG_BINFMT_ELF_FDPIC } else if (addr == (sizeof(struct pt_regs) + 12)) { - tmp = child->mm->context.exec_fdpic_loadmap; + goto case_PTRACE_GETFDPIC_EXEC; } else if (addr == (sizeof(struct pt_regs) + 16)) { - tmp = child->mm->context.interp_fdpic_loadmap; + goto case_PTRACE_GETFDPIC_INTERP; #endif } else { tmp = get_reg(child, addr); @@ -288,49 +296,78 @@ long arch_ptrace(struct task_struct *child, long request, long addr, long data) break; } +#ifdef CONFIG_BINFMT_ELF_FDPIC + case PTRACE_GETFDPIC: { + unsigned long tmp = 0; + + switch (addr) { + case_PTRACE_GETFDPIC_EXEC: + case PTRACE_GETFDPIC_EXEC: + tmp = child->mm->context.exec_fdpic_loadmap; + break; + case_PTRACE_GETFDPIC_INTERP: + case PTRACE_GETFDPIC_INTERP: + tmp = child->mm->context.interp_fdpic_loadmap; + break; + default: + break; + } + + ret = put_user(tmp, datap); + break; + } +#endif + /* when I and D space are separate, this will have to be fixed. */ case PTRACE_POKEDATA: pr_debug("ptrace: PTRACE_PEEKDATA\n"); /* fall through */ case PTRACE_POKETEXT: /* write the word at location addr. */ { - int copied; + int copied = 0, to_copy = sizeof(data); ret = -EIO; - pr_debug("ptrace: POKETEXT at addr 0x%08lx + %ld bytes %lx\n", - addr, sizeof(data), data); - if (is_user_addr_valid(child, addr, sizeof(data)) < 0) + pr_debug("ptrace: POKETEXT at addr 0x%08lx + %i bytes %lx\n", + addr, to_copy, data); + if (is_user_addr_valid(child, addr, to_copy) < 0) break; pr_debug("ptrace: user address is valid\n"); - if (L1_CODE_LENGTH != 0 && addr >= get_l1_code_start() - && addr + sizeof(data) <= get_l1_code_start() + L1_CODE_LENGTH) { - safe_dma_memcpy ((void *)(addr), &data, sizeof(data)); - copied = sizeof(data); - - } else if (L1_DATA_A_LENGTH != 0 && addr >= L1_DATA_A_START - && addr + sizeof(data) <= L1_DATA_A_START + L1_DATA_A_LENGTH) { - memcpy((void *)(addr), &data, sizeof(data)); - copied = sizeof(data); - - } else if (L1_DATA_B_LENGTH != 0 && addr >= L1_DATA_B_START - && addr + sizeof(data) <= L1_DATA_B_START + L1_DATA_B_LENGTH) { - memcpy((void *)(addr), &data, sizeof(data)); - copied = sizeof(data); - - } else if (addr >= FIXED_CODE_START - && addr + sizeof(data) <= FIXED_CODE_END) { - copy_to_user_page(0, 0, 0, (void *)(addr), &data, sizeof(data)); - copied = sizeof(data); - - } else + switch (bfin_mem_access_type(addr, to_copy)) { + case BFIN_MEM_ACCESS_CORE: + case BFIN_MEM_ACCESS_CORE_ONLY: copied = access_process_vm(child, addr, &data, - sizeof(data), 1); + to_copy, 0); + if (copied) + break; + + /* hrm, why didn't that work ... maybe no mapping */ + if (addr >= FIXED_CODE_START && + addr + to_copy <= FIXED_CODE_END) { + copy_to_user_page(0, 0, 0, paddr, &data, to_copy); + copied = to_copy; + } else if (addr >= BOOT_ROM_START) { + memcpy(paddr, &data, to_copy); + copied = to_copy; + } - pr_debug("ptrace: copied size %d\n", copied); - if (copied != sizeof(data)) break; - ret = 0; + case BFIN_MEM_ACCESS_DMA: + if (safe_dma_memcpy(paddr, &data, to_copy)) + copied = to_copy; + break; + case BFIN_MEM_ACCESS_ITEST: + if (isram_memcpy(paddr, &data, to_copy)) + copied = to_copy; + break; + default: + copied = 0; + break; + } + + pr_debug("ptrace: copied size %d\n", copied); + if (copied == to_copy) + ret = 0; break; } diff --git a/arch/blackfin/kernel/setup.c b/arch/blackfin/kernel/setup.c index 6225edae488..369535b61ed 100644 --- a/arch/blackfin/kernel/setup.c +++ b/arch/blackfin/kernel/setup.c @@ -112,7 +112,7 @@ void __cpuinit bfin_setup_caches(unsigned int cpu) /* * In cache coherence emulation mode, we need to have the * D-cache enabled before running any atomic operation which - * might invove cache invalidation (i.e. spinlock, rwlock). + * might involve cache invalidation (i.e. spinlock, rwlock). * So printk's are deferred until then. */ #ifdef CONFIG_BFIN_ICACHE @@ -187,6 +187,8 @@ void __init bfin_relocate_l1_mem(void) unsigned long l1_data_b_length; unsigned long l2_length; + early_shadow_stamp(); + /* * due to the ALIGN(4) in the arch/blackfin/kernel/vmlinux.lds.S * we know that everything about l1 text/data is nice and aligned, @@ -511,6 +513,7 @@ static __init void memory_setup(void) #ifdef CONFIG_MTD_UCLINUX unsigned long mtd_phys = 0; #endif + unsigned long max_mem; _rambase = (unsigned long)_stext; _ramstart = (unsigned long)_end; @@ -520,7 +523,22 @@ static __init void memory_setup(void) panic("DMA region exceeds memory limit: %lu.", _ramend - _ramstart); } - memory_end = _ramend - DMA_UNCACHED_REGION; + max_mem = memory_end = _ramend - DMA_UNCACHED_REGION; + +#if (defined(CONFIG_BFIN_EXTMEM_ICACHEABLE) && ANOMALY_05000263) + /* Due to a Hardware Anomaly we need to limit the size of usable + * instruction memory to max 60MB, 56 if HUNT_FOR_ZERO is on + * 05000263 - Hardware loop corrupted when taking an ICPLB exception + */ +# if (defined(CONFIG_DEBUG_HUNT_FOR_ZERO)) + if (max_mem >= 56 * 1024 * 1024) + max_mem = 56 * 1024 * 1024; +# else + if (max_mem >= 60 * 1024 * 1024) + max_mem = 60 * 1024 * 1024; +# endif /* CONFIG_DEBUG_HUNT_FOR_ZERO */ +#endif /* ANOMALY_05000263 */ + #ifdef CONFIG_MPU /* Round up to multiple of 4MB */ @@ -549,22 +567,16 @@ static __init void memory_setup(void) # if defined(CONFIG_ROMFS_FS) if (((unsigned long *)mtd_phys)[0] == ROMSB_WORD0 - && ((unsigned long *)mtd_phys)[1] == ROMSB_WORD1) + && ((unsigned long *)mtd_phys)[1] == ROMSB_WORD1) { mtd_size = PAGE_ALIGN(be32_to_cpu(((unsigned long *)mtd_phys)[2])); -# if (defined(CONFIG_BFIN_EXTMEM_ICACHEABLE) && ANOMALY_05000263) - /* Due to a Hardware Anomaly we need to limit the size of usable - * instruction memory to max 60MB, 56 if HUNT_FOR_ZERO is on - * 05000263 - Hardware loop corrupted when taking an ICPLB exception - */ -# if (defined(CONFIG_DEBUG_HUNT_FOR_ZERO)) - if (memory_end >= 56 * 1024 * 1024) - memory_end = 56 * 1024 * 1024; -# else - if (memory_end >= 60 * 1024 * 1024) - memory_end = 60 * 1024 * 1024; -# endif /* CONFIG_DEBUG_HUNT_FOR_ZERO */ -# endif /* ANOMALY_05000263 */ + + /* ROM_FS is XIP, so if we found it, we need to limit memory */ + if (memory_end > max_mem) { + pr_info("Limiting kernel memory to %liMB due to anomaly 05000263\n", max_mem >> 20); + memory_end = max_mem; + } + } # endif /* CONFIG_ROMFS_FS */ /* Since the default MTD_UCLINUX has no magic number, we just blindly @@ -586,20 +598,14 @@ static __init void memory_setup(void) } #endif /* CONFIG_MTD_UCLINUX */ -#if (defined(CONFIG_BFIN_EXTMEM_ICACHEABLE) && ANOMALY_05000263) - /* Due to a Hardware Anomaly we need to limit the size of usable - * instruction memory to max 60MB, 56 if HUNT_FOR_ZERO is on - * 05000263 - Hardware loop corrupted when taking an ICPLB exception + /* We need lo limit memory, since everything could have a text section + * of userspace in it, and expose anomaly 05000263. If the anomaly + * doesn't exist, or we don't need to - then dont. */ -#if (defined(CONFIG_DEBUG_HUNT_FOR_ZERO)) - if (memory_end >= 56 * 1024 * 1024) - memory_end = 56 * 1024 * 1024; -#else - if (memory_end >= 60 * 1024 * 1024) - memory_end = 60 * 1024 * 1024; -#endif /* CONFIG_DEBUG_HUNT_FOR_ZERO */ - printk(KERN_NOTICE "Warning: limiting memory to %liMB due to hardware anomaly 05000263\n", memory_end >> 20); -#endif /* ANOMALY_05000263 */ + if (memory_end > max_mem) { + pr_info("Limiting kernel memory to %liMB due to anomaly 05000263\n", max_mem >> 20); + memory_end = max_mem; + } #ifdef CONFIG_MPU page_mask_nelts = ((_ramend >> PAGE_SHIFT) + 31) / 32; @@ -693,7 +699,7 @@ static __init void setup_bootmem_allocator(void) sanitize_memmap(bfin_memmap.map, &bfin_memmap.nr_map); print_memory_map("boot memmap"); - /* intialize globals in linux/bootmem.h */ + /* initialize globals in linux/bootmem.h */ find_min_max_pfn(); /* pfn of the last usable page frame */ if (max_pfn > memory_end >> PAGE_SHIFT) @@ -806,6 +812,8 @@ void __init setup_arch(char **cmdline_p) { unsigned long sclk, cclk; + enable_shadow_console(); + /* Check to make sure we are running on the right processor */ if (unlikely(CPUID != bfin_cpuid())) printk(KERN_ERR "ERROR: Not running on ADSP-%s: unknown CPUID 0x%04x Rev 0.%d\n", @@ -1230,57 +1238,6 @@ static int show_cpuinfo(struct seq_file *m, void *v) #ifdef __ARCH_SYNC_CORE_ICACHE seq_printf(m, "SMP Icache Flushes\t: %lu\n\n", cpudata->icache_invld_count); #endif -#ifdef CONFIG_BFIN_ICACHE_LOCK - switch ((cpudata->imemctl >> 3) & WAYALL_L) { - case WAY0_L: - seq_printf(m, "Way0 Locked-Down\n"); - break; - case WAY1_L: - seq_printf(m, "Way1 Locked-Down\n"); - break; - case WAY01_L: - seq_printf(m, "Way0,Way1 Locked-Down\n"); - break; - case WAY2_L: - seq_printf(m, "Way2 Locked-Down\n"); - break; - case WAY02_L: - seq_printf(m, "Way0,Way2 Locked-Down\n"); - break; - case WAY12_L: - seq_printf(m, "Way1,Way2 Locked-Down\n"); - break; - case WAY012_L: - seq_printf(m, "Way0,Way1 & Way2 Locked-Down\n"); - break; - case WAY3_L: - seq_printf(m, "Way3 Locked-Down\n"); - break; - case WAY03_L: - seq_printf(m, "Way0,Way3 Locked-Down\n"); - break; - case WAY13_L: - seq_printf(m, "Way1,Way3 Locked-Down\n"); - break; - case WAY013_L: - seq_printf(m, "Way 0,Way1,Way3 Locked-Down\n"); - break; - case WAY32_L: - seq_printf(m, "Way3,Way2 Locked-Down\n"); - break; - case WAY320_L: - seq_printf(m, "Way3,Way2,Way0 Locked-Down\n"); - break; - case WAY321_L: - seq_printf(m, "Way3,Way2,Way1 Locked-Down\n"); - break; - case WAYALL_L: - seq_printf(m, "All Ways are locked\n"); - break; - default: - seq_printf(m, "No Ways are locked\n"); - } -#endif if (cpu_num != num_possible_cpus() - 1) return 0; @@ -1346,6 +1303,7 @@ const struct seq_operations cpuinfo_op = { void __init cmdline_init(const char *r0) { + early_shadow_stamp(); if (r0) strncpy(command_line, r0, COMMAND_LINE_SIZE); } diff --git a/arch/blackfin/kernel/shadow_console.c b/arch/blackfin/kernel/shadow_console.c new file mode 100644 index 00000000000..8b8c7107a16 --- /dev/null +++ b/arch/blackfin/kernel/shadow_console.c @@ -0,0 +1,113 @@ +/* + * manage a small early shadow of the log buffer which we can pass between the + * bootloader so early crash messages are communicated properly and easily + * + * Copyright 2009 Analog Devices Inc. + * + * Enter bugs at http://blackfin.uclinux.org/ + * + * Licensed under the GPL-2 or later. + */ + +#include <linux/kernel.h> +#include <linux/init.h> +#include <linux/console.h> +#include <linux/string.h> +#include <asm/blackfin.h> +#include <asm/irq_handler.h> +#include <asm/early_printk.h> + +#define SHADOW_CONSOLE_START (0x500) +#define SHADOW_CONSOLE_END (0x1000) +#define SHADOW_CONSOLE_MAGIC_LOC (0x4F0) +#define SHADOW_CONSOLE_MAGIC (0xDEADBEEF) + +static __initdata char *shadow_console_buffer = (char *)SHADOW_CONSOLE_START; + +__init void early_shadow_write(struct console *con, const char *s, + unsigned int n) +{ + unsigned int i; + /* + * save 2 bytes for the double null at the end + * once we fail on a long line, make sure we don't write a short line afterwards + */ + if ((shadow_console_buffer + n) <= (char *)(SHADOW_CONSOLE_END - 2)) { + /* can't use memcpy - it may not be relocated yet */ + for (i = 0; i <= n; i++) + shadow_console_buffer[i] = s[i]; + shadow_console_buffer += n; + shadow_console_buffer[0] = 0; + shadow_console_buffer[1] = 0; + } else + shadow_console_buffer = (char *)SHADOW_CONSOLE_END; +} + +static __initdata struct console early_shadow_console = { + .name = "early_shadow", + .write = early_shadow_write, + .flags = CON_BOOT | CON_PRINTBUFFER, + .index = -1, + .device = 0, +}; + +__init int shadow_console_enabled(void) +{ + return early_shadow_console.flags & CON_ENABLED; +} + +__init void mark_shadow_error(void) +{ + int *loc = (int *)SHADOW_CONSOLE_MAGIC_LOC; + loc[0] = SHADOW_CONSOLE_MAGIC; + loc[1] = SHADOW_CONSOLE_START; +} + +__init void enable_shadow_console(void) +{ + if (!shadow_console_enabled()) { + register_console(&early_shadow_console); + /* for now, assume things are going to fail */ + mark_shadow_error(); + } +} + +static __init int disable_shadow_console(void) +{ + /* + * by the time pure_initcall runs, the standard console is enabled, + * and the early_console is off, so unset the magic numbers + * unregistering the console is taken care of in common code (See + * ./kernel/printk:disable_boot_consoles() ) + */ + int *loc = (int *)SHADOW_CONSOLE_MAGIC_LOC; + + loc[0] = 0; + + return 0; +} +pure_initcall(disable_shadow_console); + +/* + * since we can't use printk, dump numbers (as hex), n = # bits + */ +__init void early_shadow_reg(unsigned long reg, unsigned int n) +{ + /* + * can't use any "normal" kernel features, since thay + * may not be relocated to their execute address yet + */ + int i; + char ascii[11] = " 0x"; + + n = n / 4; + reg = reg << ((8 - n) * 4); + n += 3; + + for (i = 3; i <= n ; i++) { + ascii[i] = hex_asc_lo(reg >> 28); + reg <<= 4; + } + early_shadow_write(NULL, ascii, n); + +} diff --git a/arch/blackfin/kernel/time-ts.c b/arch/blackfin/kernel/time-ts.c index 0791eba40d9..f9715764383 100644 --- a/arch/blackfin/kernel/time-ts.c +++ b/arch/blackfin/kernel/time-ts.c @@ -66,7 +66,7 @@ static cycle_t bfin_read_cycles(struct clocksource *cs) static struct clocksource bfin_cs_cycles = { .name = "bfin_cs_cycles", - .rating = 350, + .rating = 400, .read = bfin_read_cycles, .mask = CLOCKSOURCE_MASK(64), .shift = 22, @@ -115,7 +115,7 @@ static cycle_t bfin_read_gptimer0(void) static struct clocksource bfin_cs_gptimer0 = { .name = "bfin_cs_gptimer0", - .rating = 400, + .rating = 350, .read = bfin_read_gptimer0, .mask = CLOCKSOURCE_MASK(32), .shift = 22, diff --git a/arch/blackfin/kernel/traps.c b/arch/blackfin/kernel/traps.c index bf2b2d1f8ae..56464cb8edf 100644 --- a/arch/blackfin/kernel/traps.c +++ b/arch/blackfin/kernel/traps.c @@ -100,7 +100,11 @@ static void decode_address(char *buf, unsigned long address) char *modname; char *delim = ":"; char namebuf[128]; +#endif + + buf += sprintf(buf, "<0x%08lx> ", address); +#ifdef CONFIG_KALLSYMS /* look up the address and see if we are in kernel space */ symname = kallsyms_lookup(address, &symsize, &offset, &modname, namebuf); @@ -108,23 +112,33 @@ static void decode_address(char *buf, unsigned long address) /* yeah! kernel space! */ if (!modname) modname = delim = ""; - sprintf(buf, "<0x%p> { %s%s%s%s + 0x%lx }", - (void *)address, delim, modname, delim, symname, - (unsigned long)offset); + sprintf(buf, "{ %s%s%s%s + 0x%lx }", + delim, modname, delim, symname, + (unsigned long)offset); return; - } #endif - /* Problem in fixed code section? */ if (address >= FIXED_CODE_START && address < FIXED_CODE_END) { - sprintf(buf, "<0x%p> /* Maybe fixed code section */", (void *)address); + /* Problem in fixed code section? */ + strcat(buf, "/* Maybe fixed code section */"); + return; + + } else if (address < CONFIG_BOOT_LOAD) { + /* Problem somewhere before the kernel start address */ + strcat(buf, "/* Maybe null pointer? */"); + return; + + } else if (address >= COREMMR_BASE) { + strcat(buf, "/* core mmrs */"); return; - } - /* Problem somewhere before the kernel start address */ - if (address < CONFIG_BOOT_LOAD) { - sprintf(buf, "<0x%p> /* Maybe null pointer? */", (void *)address); + } else if (address >= SYSMMR_BASE) { + strcat(buf, "/* system mmrs */"); + return; + + } else if (address >= L1_ROM_START && address < L1_ROM_START + L1_ROM_LENGTH) { + strcat(buf, "/* on-chip L1 ROM */"); return; } @@ -172,18 +186,16 @@ static void decode_address(char *buf, unsigned long address) offset = (address - vma->vm_start) + (vma->vm_pgoff << PAGE_SHIFT); - sprintf(buf, "<0x%p> [ %s + 0x%lx ]", - (void *)address, name, offset); + sprintf(buf, "[ %s + 0x%lx ]", name, offset); } else - sprintf(buf, "<0x%p> [ %s vma:0x%lx-0x%lx]", - (void *)address, name, - vma->vm_start, vma->vm_end); + sprintf(buf, "[ %s vma:0x%lx-0x%lx]", + name, vma->vm_start, vma->vm_end); if (!in_atomic) mmput(mm); - if (!strlen(buf)) - sprintf(buf, "<0x%p> [ %s ] dynamic memory", (void *)address, name); + if (buf[0] == '\0') + sprintf(buf, "[ %s ] dynamic memory", name); goto done; } @@ -193,7 +205,7 @@ static void decode_address(char *buf, unsigned long address) } /* we were unable to find this address anywhere */ - sprintf(buf, "<0x%p> /* kernel dynamic memory */", (void *)address); + sprintf(buf, "/* kernel dynamic memory */"); done: write_unlock_irqrestore(&tasklist_lock, flags); @@ -215,14 +227,14 @@ asmlinkage void double_fault_c(struct pt_regs *fp) printk(KERN_EMERG "Double Fault\n"); #ifdef CONFIG_DEBUG_DOUBLEFAULT_PRINT if (((long)fp->seqstat & SEQSTAT_EXCAUSE) == VEC_UNCOV) { - unsigned int cpu = smp_processor_id(); + unsigned int cpu = raw_smp_processor_id(); char buf[150]; - decode_address(buf, cpu_pda[cpu].retx); + decode_address(buf, cpu_pda[cpu].retx_doublefault); printk(KERN_EMERG "While handling exception (EXCAUSE = 0x%x) at %s:\n", - (unsigned int)cpu_pda[cpu].seqstat & SEQSTAT_EXCAUSE, buf); - decode_address(buf, cpu_pda[cpu].dcplb_fault_addr); + (unsigned int)cpu_pda[cpu].seqstat_doublefault & SEQSTAT_EXCAUSE, buf); + decode_address(buf, cpu_pda[cpu].dcplb_doublefault_addr); printk(KERN_NOTICE " DCPLB_FAULT_ADDR: %s\n", buf); - decode_address(buf, cpu_pda[cpu].icplb_fault_addr); + decode_address(buf, cpu_pda[cpu].icplb_doublefault_addr); printk(KERN_NOTICE " ICPLB_FAULT_ADDR: %s\n", buf); decode_address(buf, fp->retx); @@ -245,13 +257,13 @@ static int kernel_mode_regs(struct pt_regs *regs) return regs->ipend & 0xffc0; } -asmlinkage void trap_c(struct pt_regs *fp) +asmlinkage notrace void trap_c(struct pt_regs *fp) { #ifdef CONFIG_DEBUG_BFIN_HWTRACE_ON int j; #endif #ifdef CONFIG_DEBUG_HUNT_FOR_ZERO - unsigned int cpu = smp_processor_id(); + unsigned int cpu = raw_smp_processor_id(); #endif const char *strerror = NULL; int sig = 0; @@ -267,11 +279,6 @@ asmlinkage void trap_c(struct pt_regs *fp) * double faults if the stack has become corrupt */ -#ifndef CONFIG_KGDB - /* IPEND is skipped if KGDB isn't enabled (see entry code) */ - fp->ipend = bfin_read_IPEND(); -#endif - /* trap_c() will be called for exceptions. During exceptions * processing, the pc value should be set with retx value. * With this change we can cleanup some code in signal.c- TODO @@ -404,7 +411,7 @@ asmlinkage void trap_c(struct pt_regs *fp) /* 0x23 - Data CPLB protection violation, handled here */ case VEC_CPLB_VL: info.si_code = ILL_CPLB_VI; - sig = SIGBUS; + sig = SIGSEGV; strerror = KERN_NOTICE EXC_0x23(KERN_NOTICE); CHK_DEBUGGER_TRAP_MAYBE(); break; @@ -904,7 +911,7 @@ void show_stack(struct task_struct *task, unsigned long *stack) frame_no = 0; for (addr = (unsigned int *)((unsigned int)stack & ~0xF), i = 0; - addr <= endstack; addr++, i++) { + addr < endstack; addr++, i++) { ret_addr = 0; if (!j && i % 8 == 0) @@ -949,6 +956,7 @@ void show_stack(struct task_struct *task, unsigned long *stack) } #endif } +EXPORT_SYMBOL(show_stack); void dump_stack(void) { @@ -1090,7 +1098,7 @@ void show_regs(struct pt_regs *fp) struct irqaction *action; unsigned int i; unsigned long flags = 0; - unsigned int cpu = smp_processor_id(); + unsigned int cpu = raw_smp_processor_id(); unsigned char in_atomic = (bfin_read_IPEND() & 0x10) || in_atomic(); verbose_printk(KERN_NOTICE "\n"); @@ -1116,10 +1124,16 @@ void show_regs(struct pt_regs *fp) verbose_printk(KERN_NOTICE "%s", linux_banner); - verbose_printk(KERN_NOTICE "\nSEQUENCER STATUS:\t\t%s\n", - print_tainted()); - verbose_printk(KERN_NOTICE " SEQSTAT: %08lx IPEND: %04lx SYSCFG: %04lx\n", - (long)fp->seqstat, fp->ipend, fp->syscfg); + verbose_printk(KERN_NOTICE "\nSEQUENCER STATUS:\t\t%s\n", print_tainted()); + verbose_printk(KERN_NOTICE " SEQSTAT: %08lx IPEND: %04lx IMASK: %04lx SYSCFG: %04lx\n", + (long)fp->seqstat, fp->ipend, cpu_pda[raw_smp_processor_id()].ex_imask, fp->syscfg); + if (fp->ipend & EVT_IRPTEN) + verbose_printk(KERN_NOTICE " Global Interrupts Disabled (IPEND[4])\n"); + if (!(cpu_pda[raw_smp_processor_id()].ex_imask & (EVT_IVG13 | EVT_IVG12 | EVT_IVG11 | + EVT_IVG10 | EVT_IVG9 | EVT_IVG8 | EVT_IVG7 | EVT_IVTMR))) + verbose_printk(KERN_NOTICE " Peripheral interrupts masked off\n"); + if (!(cpu_pda[raw_smp_processor_id()].ex_imask & (EVT_IVG15 | EVT_IVG14))) + verbose_printk(KERN_NOTICE " Kernel interrupts masked off\n"); if ((fp->seqstat & SEQSTAT_EXCAUSE) == VEC_HWERR) { verbose_printk(KERN_NOTICE " HWERRCAUSE: 0x%lx\n", (fp->seqstat & SEQSTAT_HWERRCAUSE) >> 14); diff --git a/arch/blackfin/kernel/vmlinux.lds.S b/arch/blackfin/kernel/vmlinux.lds.S index 6ac307ca0d8..21ac7c26079 100644 --- a/arch/blackfin/kernel/vmlinux.lds.S +++ b/arch/blackfin/kernel/vmlinux.lds.S @@ -221,7 +221,7 @@ SECTIONS . = ALIGN(4); __ebss_l1 = .; } - ASSERT (SIZEOF(.data_a_l1) <= L1_DATA_A_LENGTH, "L1 data A overflow!") + ASSERT (SIZEOF(.data_l1) <= L1_DATA_A_LENGTH, "L1 data A overflow!") .data_b_l1 L1_DATA_B_START : AT(LOADADDR(.data_l1) + SIZEOF(.data_l1)) { @@ -262,7 +262,7 @@ SECTIONS . = ALIGN(4); __ebss_l2 = .; } - ASSERT (SIZEOF(.text_data_l1) <= L2_LENGTH, "L2 overflow!") + ASSERT (SIZEOF(.text_data_l2) <= L2_LENGTH, "L2 overflow!") /* Force trailing alignment of our init section so that when we * free our init memory, we don't leave behind a partial page. @@ -277,8 +277,5 @@ SECTIONS DWARF_DEBUG - /DISCARD/ : - { - *(.exitcall.exit) - } + DISCARDS } diff --git a/arch/blackfin/lib/ins.S b/arch/blackfin/lib/ins.S index 1863a6ba507..3edbd8db659 100644 --- a/arch/blackfin/lib/ins.S +++ b/arch/blackfin/lib/ins.S @@ -16,7 +16,7 @@ [--sp] = rets; \ [--sp] = (P5:0); \ sp += -12; \ - call ___ipipe_stall_root_raw; \ + call ___ipipe_disable_root_irqs_hw; \ sp += 12; \ (P5:0) = [sp++]; # define CLI_INNER_NOP @@ -28,7 +28,7 @@ #ifdef CONFIG_IPIPE # define DO_STI \ sp += -12; \ - call ___ipipe_unstall_root_raw; \ + call ___ipipe_enable_root_irqs_hw; \ sp += 12; \ 2: rets = [sp++]; #else diff --git a/arch/blackfin/mach-bf518/boards/ezbrd.c b/arch/blackfin/mach-bf518/boards/ezbrd.c index 809be268e42..03e4a9941f0 100644 --- a/arch/blackfin/mach-bf518/boards/ezbrd.c +++ b/arch/blackfin/mach-bf518/boards/ezbrd.c @@ -199,15 +199,6 @@ static struct bfin5xx_spi_chip mmc_spi_chip_info = { }; #endif -#if defined(CONFIG_PBX) -static struct bfin5xx_spi_chip spi_si3xxx_chip_info = { - .ctl_reg = 0x4, /* send zero */ - .enable_dma = 0, - .bits_per_word = 8, - .cs_change_per_word = 1, -}; -#endif - #if defined(CONFIG_TOUCHSCREEN_AD7877) || defined(CONFIG_TOUCHSCREEN_AD7877_MODULE) static struct bfin5xx_spi_chip spi_ad7877_chip_info = { .enable_dma = 0, @@ -296,24 +287,6 @@ static struct spi_board_info bfin_spi_board_info[] __initdata = { .mode = SPI_MODE_3, }, #endif -#if defined(CONFIG_PBX) - { - .modalias = "fxs-spi", - .max_speed_hz = 12500000, /* max spi clock (SCK) speed in HZ */ - .bus_num = 0, - .chip_select = 8 - CONFIG_J11_JUMPER, - .controller_data = &spi_si3xxx_chip_info, - .mode = SPI_MODE_3, - }, - { - .modalias = "fxo-spi", - .max_speed_hz = 12500000, /* max spi clock (SCK) speed in HZ */ - .bus_num = 0, - .chip_select = 8 - CONFIG_J19_JUMPER, - .controller_data = &spi_si3xxx_chip_info, - .mode = SPI_MODE_3, - }, -#endif #if defined(CONFIG_TOUCHSCREEN_AD7877) || defined(CONFIG_TOUCHSCREEN_AD7877_MODULE) { .modalias = "ad7877", @@ -539,7 +512,7 @@ static struct i2c_board_info __initdata bfin_i2c_board_info[] = { I2C_BOARD_INFO("pcf8574_lcd", 0x22), }, #endif -#if defined(CONFIG_TWI_KEYPAD) || defined(CONFIG_TWI_KEYPAD_MODULE) +#if defined(CONFIG_INPUT_PCF8574) || defined(CONFIG_INPUT_PCF8574_MODULE) { I2C_BOARD_INFO("pcf8574_keypad", 0x27), .irq = IRQ_PF8, diff --git a/arch/blackfin/mach-bf518/include/mach/anomaly.h b/arch/blackfin/mach-bf518/include/mach/anomaly.h index 753ed810e1c..e9c65390edd 100644 --- a/arch/blackfin/mach-bf518/include/mach/anomaly.h +++ b/arch/blackfin/mach-bf518/include/mach/anomaly.h @@ -124,6 +124,7 @@ #define ANOMALY_05000386 (0) #define ANOMALY_05000389 (0) #define ANOMALY_05000400 (0) +#define ANOMALY_05000402 (0) #define ANOMALY_05000412 (0) #define ANOMALY_05000432 (0) #define ANOMALY_05000447 (0) diff --git a/arch/blackfin/mach-bf518/include/mach/blackfin.h b/arch/blackfin/mach-bf518/include/mach/blackfin.h index e8e14c2769e..83421d39314 100644 --- a/arch/blackfin/mach-bf518/include/mach/blackfin.h +++ b/arch/blackfin/mach-bf518/include/mach/blackfin.h @@ -68,11 +68,6 @@ #endif #endif -/* UART_IIR Register */ -#define STATUS(x) ((x << 1) & 0x06) -#define STATUS_P1 0x02 -#define STATUS_P0 0x01 - #define BFIN_UART_NR_PORTS 2 #define OFFSET_THR 0x00 /* Transmit Holding register */ @@ -88,11 +83,6 @@ #define OFFSET_SCR 0x1C /* SCR Scratch Register */ #define OFFSET_GCTL 0x24 /* Global Control Register */ -/* DPMC*/ -#define bfin_read_STOPCK_OFF() bfin_read_STOPCK() -#define bfin_write_STOPCK_OFF(val) bfin_write_STOPCK(val) -#define STOPCK_OFF STOPCK - /* PLL_DIV Masks */ #define CCLK_DIV1 CSEL_DIV1 /* CCLK = VCO / 1 */ #define CCLK_DIV2 CSEL_DIV2 /* CCLK = VCO / 2 */ diff --git a/arch/blackfin/mach-bf527/boards/cm_bf527.c b/arch/blackfin/mach-bf527/boards/cm_bf527.c index b09484f538f..08a3f01c988 100644 --- a/arch/blackfin/mach-bf527/boards/cm_bf527.c +++ b/arch/blackfin/mach-bf527/boards/cm_bf527.c @@ -151,46 +151,6 @@ static struct platform_device musb_device = { }; #endif -#if defined(CONFIG_MTD_PHYSMAP) || defined(CONFIG_MTD_PHYSMAP_MODULE) -static struct mtd_partition ezkit_partitions[] = { - { - .name = "bootloader(nor)", - .size = 0x40000, - .offset = 0, - }, { - .name = "linux kernel(nor)", - .size = 0x1C0000, - .offset = MTDPART_OFS_APPEND, - }, { - .name = "file system(nor)", - .size = MTDPART_SIZ_FULL, - .offset = MTDPART_OFS_APPEND, - } -}; - -static struct physmap_flash_data ezkit_flash_data = { - .width = 2, - .parts = ezkit_partitions, - .nr_parts = ARRAY_SIZE(ezkit_partitions), -}; - -static struct resource ezkit_flash_resource = { - .start = 0x20000000, - .end = 0x201fffff, - .flags = IORESOURCE_MEM, -}; - -static struct platform_device ezkit_flash_device = { - .name = "physmap-flash", - .id = 0, - .dev = { - .platform_data = &ezkit_flash_data, - }, - .num_resources = 1, - .resource = &ezkit_flash_resource, -}; -#endif - #if defined(CONFIG_MTD_NAND_BF5XX) || defined(CONFIG_MTD_NAND_BF5XX_MODULE) static struct mtd_partition partition_info[] = { { @@ -275,6 +235,14 @@ static struct platform_device rtc_device = { #endif #if defined(CONFIG_SMC91X) || defined(CONFIG_SMC91X_MODULE) +#include <linux/smc91x.h> + +static struct smc91x_platdata smc91x_info = { + .flags = SMC91X_USE_16BIT | SMC91X_NOWAIT, + .leda = RPC_LED_100_10, + .ledb = RPC_LED_TX_RX, +}; + static struct resource smc91x_resources[] = { { .name = "smc91x-regs", @@ -293,6 +261,9 @@ static struct platform_device smc91x_device = { .id = 0, .num_resources = ARRAY_SIZE(smc91x_resources), .resource = smc91x_resources, + .dev = { + .platform_data = &smc91x_info, + }, }; #endif @@ -300,10 +271,15 @@ static struct platform_device smc91x_device = { static struct resource dm9000_resources[] = { [0] = { .start = 0x203FB800, - .end = 0x203FB800 + 8, + .end = 0x203FB800 + 1, .flags = IORESOURCE_MEM, }, [1] = { + .start = 0x203FB804, + .end = 0x203FB804 + 1, + .flags = IORESOURCE_MEM, + }, + [2] = { .start = IRQ_PF9, .end = IRQ_PF9, .flags = (IORESOURCE_IRQ | IORESOURCE_IRQ_HIGHEDGE), @@ -479,13 +455,6 @@ static struct bfin5xx_spi_chip ad1836_spi_chip_info = { }; #endif -#if defined(CONFIG_AD9960) || defined(CONFIG_AD9960_MODULE) -static struct bfin5xx_spi_chip ad9960_spi_chip_info = { - .enable_dma = 0, - .bits_per_word = 16, -}; -#endif - #if defined(CONFIG_MMC_SPI) || defined(CONFIG_MMC_SPI_MODULE) static struct bfin5xx_spi_chip mmc_spi_chip_info = { .enable_dma = 0, @@ -493,15 +462,6 @@ static struct bfin5xx_spi_chip mmc_spi_chip_info = { }; #endif -#if defined(CONFIG_PBX) -static struct bfin5xx_spi_chip spi_si3xxx_chip_info = { - .ctl_reg = 0x4, /* send zero */ - .enable_dma = 0, - .bits_per_word = 8, - .cs_change_per_word = 1, -}; -#endif - #if defined(CONFIG_TOUCHSCREEN_AD7877) || defined(CONFIG_TOUCHSCREEN_AD7877_MODULE) static struct bfin5xx_spi_chip spi_ad7877_chip_info = { .enable_dma = 0, @@ -568,22 +528,13 @@ static struct spi_board_info bfin_spi_board_info[] __initdata = { #if defined(CONFIG_SND_BLACKFIN_AD1836) \ || defined(CONFIG_SND_BLACKFIN_AD1836_MODULE) { - .modalias = "ad1836-spi", + .modalias = "ad1836", .max_speed_hz = 3125000, /* max spi clock (SCK) speed in HZ */ .bus_num = 0, .chip_select = CONFIG_SND_BLACKFIN_SPI_PFBIT, .controller_data = &ad1836_spi_chip_info, }, #endif -#if defined(CONFIG_AD9960) || defined(CONFIG_AD9960_MODULE) - { - .modalias = "ad9960-spi", - .max_speed_hz = 10000000, /* max spi clock (SCK) speed in HZ */ - .bus_num = 0, - .chip_select = 1, - .controller_data = &ad9960_spi_chip_info, - }, -#endif #if defined(CONFIG_MMC_SPI) || defined(CONFIG_MMC_SPI_MODULE) { .modalias = "mmc_spi", @@ -594,24 +545,6 @@ static struct spi_board_info bfin_spi_board_info[] __initdata = { .mode = SPI_MODE_3, }, #endif -#if defined(CONFIG_PBX) - { - .modalias = "fxs-spi", - .max_speed_hz = 12500000, /* max spi clock (SCK) speed in HZ */ - .bus_num = 0, - .chip_select = 8 - CONFIG_J11_JUMPER, - .controller_data = &spi_si3xxx_chip_info, - .mode = SPI_MODE_3, - }, - { - .modalias = "fxo-spi", - .max_speed_hz = 12500000, /* max spi clock (SCK) speed in HZ */ - .bus_num = 0, - .chip_select = 8 - CONFIG_J19_JUMPER, - .controller_data = &spi_si3xxx_chip_info, - .mode = SPI_MODE_3, - }, -#endif #if defined(CONFIG_TOUCHSCREEN_AD7877) || defined(CONFIG_TOUCHSCREEN_AD7877_MODULE) { .modalias = "ad7877", @@ -689,6 +622,55 @@ static struct platform_device bfin_fb_adv7393_device = { }; #endif +#if defined(CONFIG_MTD_GPIO_ADDR) || defined(CONFIG_MTD_GPIO_ADDR_MODULE) +static struct mtd_partition cm_partitions[] = { + { + .name = "bootloader(nor)", + .size = 0x40000, + .offset = 0, + }, { + .name = "linux kernel(nor)", + .size = 0x100000, + .offset = MTDPART_OFS_APPEND, + }, { + .name = "file system(nor)", + .size = MTDPART_SIZ_FULL, + .offset = MTDPART_OFS_APPEND, + } +}; + +static struct physmap_flash_data cm_flash_data = { + .width = 2, + .parts = cm_partitions, + .nr_parts = ARRAY_SIZE(cm_partitions), +}; + +static unsigned cm_flash_gpios[] = { GPIO_PH9, GPIO_PG11 }; + +static struct resource cm_flash_resource[] = { + { + .name = "cfi_probe", + .start = 0x20000000, + .end = 0x201fffff, + .flags = IORESOURCE_MEM, + }, { + .start = (unsigned long)cm_flash_gpios, + .end = ARRAY_SIZE(cm_flash_gpios), + .flags = IORESOURCE_IRQ, + } +}; + +static struct platform_device cm_flash_device = { + .name = "gpio-addr-flash", + .id = 0, + .dev = { + .platform_data = &cm_flash_data, + }, + .num_resources = ARRAY_SIZE(cm_flash_resource), + .resource = cm_flash_resource, +}; +#endif + #if defined(CONFIG_SERIAL_BFIN) || defined(CONFIG_SERIAL_BFIN_MODULE) static struct resource bfin_uart_resources[] = { #ifdef CONFIG_SERIAL_BFIN_UART0 @@ -796,13 +778,11 @@ static struct i2c_board_info __initdata bfin_i2c_board_info[] = { #if defined(CONFIG_BFIN_TWI_LCD) || defined(CONFIG_BFIN_TWI_LCD_MODULE) { I2C_BOARD_INFO("pcf8574_lcd", 0x22), - .type = "pcf8574_lcd", }, #endif -#if defined(CONFIG_TWI_KEYPAD) || defined(CONFIG_TWI_KEYPAD_MODULE) +#if defined(CONFIG_INPUT_PCF8574) || defined(CONFIG_INPUT_PCF8574_MODULE) { I2C_BOARD_INFO("pcf8574_keypad", 0x27), - .type = "pcf8574_keypad", .irq = IRQ_PF8, }, #endif @@ -876,7 +856,7 @@ static struct platform_device bfin_dpmc = { }, }; -static struct platform_device *stamp_devices[] __initdata = { +static struct platform_device *cmbf527_devices[] __initdata = { &bfin_dpmc, @@ -959,8 +939,8 @@ static struct platform_device *stamp_devices[] __initdata = { &bfin_device_gpiokeys, #endif -#if defined(CONFIG_MTD_PHYSMAP) || defined(CONFIG_MTD_PHYSMAP_MODULE) - &ezkit_flash_device, +#if defined(CONFIG_MTD_GPIO_ADDR) || defined(CONFIG_MTD_GPIO_ADDR_MODULE) + &cm_flash_device, #endif &bfin_gpios_device, @@ -971,7 +951,7 @@ static int __init cm_init(void) printk(KERN_INFO "%s(): registering device resources\n", __func__); i2c_register_board_info(0, bfin_i2c_board_info, ARRAY_SIZE(bfin_i2c_board_info)); - platform_add_devices(stamp_devices, ARRAY_SIZE(stamp_devices)); + platform_add_devices(cmbf527_devices, ARRAY_SIZE(cmbf527_devices)); spi_register_board_info(bfin_spi_board_info, ARRAY_SIZE(bfin_spi_board_info)); return 0; } diff --git a/arch/blackfin/mach-bf527/boards/ezbrd.c b/arch/blackfin/mach-bf527/boards/ezbrd.c index 2ad68cd10ae..68b4c804364 100644 --- a/arch/blackfin/mach-bf527/boards/ezbrd.c +++ b/arch/blackfin/mach-bf527/boards/ezbrd.c @@ -263,15 +263,6 @@ static struct bfin5xx_spi_chip mmc_spi_chip_info = { }; #endif -#if defined(CONFIG_PBX) -static struct bfin5xx_spi_chip spi_si3xxx_chip_info = { - .ctl_reg = 0x4, /* send zero */ - .enable_dma = 0, - .bits_per_word = 8, - .cs_change_per_word = 1, -}; -#endif - #if defined(CONFIG_TOUCHSCREEN_AD7877) || defined(CONFIG_TOUCHSCREEN_AD7877_MODULE) static struct bfin5xx_spi_chip spi_ad7877_chip_info = { .enable_dma = 0, @@ -376,24 +367,6 @@ static struct spi_board_info bfin_spi_board_info[] __initdata = { .mode = SPI_MODE_3, }, #endif -#if defined(CONFIG_PBX) - { - .modalias = "fxs-spi", - .max_speed_hz = 12500000, /* max spi clock (SCK) speed in HZ */ - .bus_num = 0, - .chip_select = 8 - CONFIG_J11_JUMPER, - .controller_data = &spi_si3xxx_chip_info, - .mode = SPI_MODE_3, - }, - { - .modalias = "fxo-spi", - .max_speed_hz = 12500000, /* max spi clock (SCK) speed in HZ */ - .bus_num = 0, - .chip_select = 8 - CONFIG_J19_JUMPER, - .controller_data = &spi_si3xxx_chip_info, - .mode = SPI_MODE_3, - }, -#endif #if defined(CONFIG_TOUCHSCREEN_AD7877) || defined(CONFIG_TOUCHSCREEN_AD7877_MODULE) { .modalias = "ad7877", @@ -596,7 +569,7 @@ static struct i2c_board_info __initdata bfin_i2c_board_info[] = { I2C_BOARD_INFO("pcf8574_lcd", 0x22), }, #endif -#if defined(CONFIG_TWI_KEYPAD) || defined(CONFIG_TWI_KEYPAD_MODULE) +#if defined(CONFIG_INPUT_PCF8574) || defined(CONFIG_INPUT_PCF8574_MODULE) { I2C_BOARD_INFO("pcf8574_keypad", 0x27), .irq = IRQ_PF8, diff --git a/arch/blackfin/mach-bf527/boards/ezkit.c b/arch/blackfin/mach-bf527/boards/ezkit.c index 75e563d3f9d..2849b09abe9 100644 --- a/arch/blackfin/mach-bf527/boards/ezkit.c +++ b/arch/blackfin/mach-bf527/boards/ezkit.c @@ -292,6 +292,14 @@ static struct platform_device rtc_device = { #endif #if defined(CONFIG_SMC91X) || defined(CONFIG_SMC91X_MODULE) +#include <linux/smc91x.h> + +static struct smc91x_platdata smc91x_info = { + .flags = SMC91X_USE_16BIT | SMC91X_NOWAIT, + .leda = RPC_LED_100_10, + .ledb = RPC_LED_TX_RX, +}; + static struct resource smc91x_resources[] = { { .name = "smc91x-regs", @@ -310,6 +318,9 @@ static struct platform_device smc91x_device = { .id = 0, .num_resources = ARRAY_SIZE(smc91x_resources), .resource = smc91x_resources, + .dev = { + .platform_data = &smc91x_info, + }, }; #endif @@ -501,13 +512,6 @@ static struct bfin5xx_spi_chip ad1836_spi_chip_info = { }; #endif -#if defined(CONFIG_AD9960) || defined(CONFIG_AD9960_MODULE) -static struct bfin5xx_spi_chip ad9960_spi_chip_info = { - .enable_dma = 0, - .bits_per_word = 16, -}; -#endif - #if defined(CONFIG_MMC_SPI) || defined(CONFIG_MMC_SPI_MODULE) static struct bfin5xx_spi_chip mmc_spi_chip_info = { .enable_dma = 0, @@ -515,15 +519,6 @@ static struct bfin5xx_spi_chip mmc_spi_chip_info = { }; #endif -#if defined(CONFIG_PBX) -static struct bfin5xx_spi_chip spi_si3xxx_chip_info = { - .ctl_reg = 0x4, /* send zero */ - .enable_dma = 0, - .bits_per_word = 8, - .cs_change_per_word = 1, -}; -#endif - #if defined(CONFIG_TOUCHSCREEN_AD7877) || defined(CONFIG_TOUCHSCREEN_AD7877_MODULE) static struct bfin5xx_spi_chip spi_ad7877_chip_info = { .enable_dma = 0, @@ -614,22 +609,13 @@ static struct spi_board_info bfin_spi_board_info[] __initdata = { #if defined(CONFIG_SND_BLACKFIN_AD1836) \ || defined(CONFIG_SND_BLACKFIN_AD1836_MODULE) { - .modalias = "ad1836-spi", + .modalias = "ad1836", .max_speed_hz = 3125000, /* max spi clock (SCK) speed in HZ */ .bus_num = 0, .chip_select = CONFIG_SND_BLACKFIN_SPI_PFBIT, .controller_data = &ad1836_spi_chip_info, }, #endif -#if defined(CONFIG_AD9960) || defined(CONFIG_AD9960_MODULE) - { - .modalias = "ad9960-spi", - .max_speed_hz = 10000000, /* max spi clock (SCK) speed in HZ */ - .bus_num = 0, - .chip_select = 1, - .controller_data = &ad9960_spi_chip_info, - }, -#endif #if defined(CONFIG_MMC_SPI) || defined(CONFIG_MMC_SPI_MODULE) { .modalias = "mmc_spi", @@ -641,24 +627,6 @@ static struct spi_board_info bfin_spi_board_info[] __initdata = { }, #endif -#if defined(CONFIG_PBX) - { - .modalias = "fxs-spi", - .max_speed_hz = 12500000, /* max spi clock (SCK) speed in HZ */ - .bus_num = 0, - .chip_select = 8 - CONFIG_J11_JUMPER, - .controller_data = &spi_si3xxx_chip_info, - .mode = SPI_MODE_3, - }, - { - .modalias = "fxo-spi", - .max_speed_hz = 12500000, /* max spi clock (SCK) speed in HZ */ - .bus_num = 0, - .chip_select = 8 - CONFIG_J19_JUMPER, - .controller_data = &spi_si3xxx_chip_info, - .mode = SPI_MODE_3, - }, -#endif #if defined(CONFIG_TOUCHSCREEN_AD7877) || defined(CONFIG_TOUCHSCREEN_AD7877_MODULE) { .modalias = "ad7877", @@ -863,7 +831,7 @@ static struct i2c_board_info __initdata bfin_i2c_board_info[] = { I2C_BOARD_INFO("pcf8574_lcd", 0x22), }, #endif -#if defined(CONFIG_TWI_KEYPAD) || defined(CONFIG_TWI_KEYPAD_MODULE) +#if defined(CONFIG_INPUT_PCF8574) || defined(CONFIG_INPUT_PCF8574_MODULE) { I2C_BOARD_INFO("pcf8574_keypad", 0x27), .irq = IRQ_PF8, diff --git a/arch/blackfin/mach-bf527/include/mach/anomaly.h b/arch/blackfin/mach-bf527/include/mach/anomaly.h index c438ca89d8c..3f9052687fa 100644 --- a/arch/blackfin/mach-bf527/include/mach/anomaly.h +++ b/arch/blackfin/mach-bf527/include/mach/anomaly.h @@ -7,7 +7,7 @@ */ /* This file should be up to date with: - * - Revision C, 03/13/2009; ADSP-BF526 Blackfin Processor Anomaly List + * - Revision D, 08/14/2009; ADSP-BF526 Blackfin Processor Anomaly List * - Revision F, 03/03/2009; ADSP-BF527 Blackfin Processor Anomaly List */ @@ -176,7 +176,7 @@ #define ANOMALY_05000443 (1) /* The WURESET Bit in the SYSCR Register is not Functional */ #define ANOMALY_05000445 (1) -/* USB DMA Short Packet Data Corruption */ +/* USB DMA Mode 1 Short Packet Data Corruption */ #define ANOMALY_05000450 (1) /* BCODE_QUICKBOOT, BCODE_ALLBOOT, and BCODE_FULLBOOT Settings in SYSCR Register Not Functional */ #define ANOMALY_05000451 (1) @@ -186,12 +186,20 @@ #define ANOMALY_05000456 (1) /* Host DMA Port Responds to Certain Bus Activity Without HOST_CE Assertion */ #define ANOMALY_05000457 (1) +/* USB DMA Mode 1 Failure When Multiple USB DMA Channels Are Concurrently Enabled */ +#define ANOMALY_05000460 (1) /* False Hardware Error when RETI Points to Invalid Memory */ #define ANOMALY_05000461 (1) +/* Synchronization Problem at Startup May Cause SPORT Transmit Channels to Misalign */ +#define ANOMALY_05000462 (1) /* USB Rx DMA hang */ #define ANOMALY_05000465 (1) +/* TxPktRdy Bit Not Set for Transmit Endpoint When Core and DMA Access USB Endpoint FIFOs Simultaneously */ +#define ANOMALY_05000466 (1) /* Possible RX data corruption when control & data EP FIFOs are accessed via the core */ #define ANOMALY_05000467 (1) +/* PLL Latches Incorrect Settings During Reset */ +#define ANOMALY_05000469 (1) /* Anomalies that don't exist on this proc */ #define ANOMALY_05000099 (0) @@ -238,6 +246,7 @@ #define ANOMALY_05000362 (1) #define ANOMALY_05000363 (0) #define ANOMALY_05000400 (0) +#define ANOMALY_05000402 (0) #define ANOMALY_05000412 (0) #define ANOMALY_05000447 (0) #define ANOMALY_05000448 (0) diff --git a/arch/blackfin/mach-bf527/include/mach/blackfin.h b/arch/blackfin/mach-bf527/include/mach/blackfin.h index 03665a8e16b..ea9cb0fef8b 100644 --- a/arch/blackfin/mach-bf527/include/mach/blackfin.h +++ b/arch/blackfin/mach-bf527/include/mach/blackfin.h @@ -56,11 +56,6 @@ #endif #endif -/* UART_IIR Register */ -#define STATUS(x) ((x << 1) & 0x06) -#define STATUS_P1 0x02 -#define STATUS_P0 0x01 - #define BFIN_UART_NR_PORTS 2 #define OFFSET_THR 0x00 /* Transmit Holding register */ @@ -76,11 +71,6 @@ #define OFFSET_SCR 0x1C /* SCR Scratch Register */ #define OFFSET_GCTL 0x24 /* Global Control Register */ -/* DPMC*/ -#define bfin_read_STOPCK_OFF() bfin_read_STOPCK() -#define bfin_write_STOPCK_OFF(val) bfin_write_STOPCK(val) -#define STOPCK_OFF STOPCK - /* PLL_DIV Masks */ #define CCLK_DIV1 CSEL_DIV1 /* CCLK = VCO / 1 */ #define CCLK_DIV2 CSEL_DIV2 /* CCLK = VCO / 2 */ diff --git a/arch/blackfin/mach-bf533/boards/H8606.c b/arch/blackfin/mach-bf533/boards/H8606.c index 38cf8ffd6d7..6c2b47fe4fe 100644 --- a/arch/blackfin/mach-bf533/boards/H8606.c +++ b/arch/blackfin/mach-bf533/boards/H8606.c @@ -88,6 +88,14 @@ static struct platform_device dm9000_device = { #endif #if defined(CONFIG_SMC91X) || defined(CONFIG_SMC91X_MODULE) +#include <linux/smc91x.h> + +static struct smc91x_platdata smc91x_info = { + .flags = SMC91X_USE_16BIT | SMC91X_NOWAIT, + .leda = RPC_LED_100_10, + .ledb = RPC_LED_TX_RX, +}; + static struct resource smc91x_resources[] = { { .name = "smc91x-regs", @@ -110,6 +118,9 @@ static struct platform_device smc91x_device = { .id = 0, .num_resources = ARRAY_SIZE(smc91x_resources), .resource = smc91x_resources, + .dev = { + .platform_data = &smc91x_info, + }, }; #endif @@ -190,15 +201,6 @@ static struct bfin5xx_spi_chip ad1836_spi_chip_info = { }; #endif -#if defined(CONFIG_PBX) -static struct bfin5xx_spi_chip spi_si3xxx_chip_info = { - .ctl_reg = 0x1c04, - .enable_dma = 0, - .bits_per_word = 8, - .cs_change_per_word = 1, -}; -#endif - /* Notice: for blackfin, the speed_hz is the value of register * SPI_BAUD, not the real baudrate */ static struct spi_board_info bfin_spi_board_info[] __initdata = { @@ -229,7 +231,7 @@ static struct spi_board_info bfin_spi_board_info[] __initdata = { #if defined(CONFIG_SND_BLACKFIN_AD1836) || defined(CONFIG_SND_BLACKFIN_AD1836_MODULE) { - .modalias = "ad1836-spi", + .modalias = "ad1836", .max_speed_hz = 16, .bus_num = 1, .chip_select = CONFIG_SND_BLACKFIN_SPI_PFBIT, @@ -237,23 +239,6 @@ static struct spi_board_info bfin_spi_board_info[] __initdata = { }, #endif -#if defined(CONFIG_PBX) - { - .modalias = "fxs-spi", - .max_speed_hz = 4, - .bus_num = 1, - .chip_select = 3, - .controller_data = &spi_si3xxx_chip_info, - }, - - { - .modalias = "fxo-spi", - .max_speed_hz = 4, - .bus_num = 1, - .chip_select = 2, - .controller_data = &spi_si3xxx_chip_info, - }, -#endif }; /* SPI (0) */ diff --git a/arch/blackfin/mach-bf533/boards/blackstamp.c b/arch/blackfin/mach-bf533/boards/blackstamp.c index 9ecdc361fa6..8208d67e2c9 100644 --- a/arch/blackfin/mach-bf533/boards/blackstamp.c +++ b/arch/blackfin/mach-bf533/boards/blackstamp.c @@ -48,6 +48,14 @@ static struct platform_device rtc_device = { * Driver needs to know address, irq and flag pin. */ #if defined(CONFIG_SMC91X) || defined(CONFIG_SMC91X_MODULE) +#include <linux/smc91x.h> + +static struct smc91x_platdata smc91x_info = { + .flags = SMC91X_USE_16BIT | SMC91X_NOWAIT, + .leda = RPC_LED_100_10, + .ledb = RPC_LED_TX_RX, +}; + static struct resource smc91x_resources[] = { { .name = "smc91x-regs", @@ -66,6 +74,9 @@ static struct platform_device smc91x_device = { .id = 0, .num_resources = ARRAY_SIZE(smc91x_resources), .resource = smc91x_resources, + .dev = { + .platform_data = &smc91x_info, + }, }; #endif diff --git a/arch/blackfin/mach-bf533/boards/cm_bf533.c b/arch/blackfin/mach-bf533/boards/cm_bf533.c index 1443e92d8b6..7443b26c80c 100644 --- a/arch/blackfin/mach-bf533/boards/cm_bf533.c +++ b/arch/blackfin/mach-bf533/boards/cm_bf533.c @@ -31,8 +31,10 @@ #include <linux/platform_device.h> #include <linux/mtd/mtd.h> #include <linux/mtd/partitions.h> +#include <linux/mtd/physmap.h> #include <linux/spi/spi.h> #include <linux/spi/flash.h> +#include <linux/spi/mmc_spi.h> #if defined(CONFIG_USB_ISP1362_HCD) || defined(CONFIG_USB_ISP1362_HCD_MODULE) #include <linux/usb/isp1362.h> #endif @@ -130,7 +132,7 @@ static struct spi_board_info bfin_spi_board_info[] __initdata = { #if defined(CONFIG_SND_BLACKFIN_AD1836) || defined(CONFIG_SND_BLACKFIN_AD1836_MODULE) { - .modalias = "ad1836-spi", + .modalias = "ad1836", .max_speed_hz = 3125000, /* max spi clock (SCK) speed in HZ */ .bus_num = 0, .chip_select = CONFIG_SND_BLACKFIN_SPI_PFBIT, @@ -141,9 +143,9 @@ static struct spi_board_info bfin_spi_board_info[] __initdata = { #if defined(CONFIG_MMC_SPI) || defined(CONFIG_MMC_SPI_MODULE) { .modalias = "mmc_spi", - .max_speed_hz = 25000000, /* max spi clock (SCK) speed in HZ */ + .max_speed_hz = 20000000, /* max spi clock (SCK) speed in HZ */ .bus_num = 0, - .chip_select = 5, + .chip_select = 1, .controller_data = &mmc_spi_chip_info, .mode = SPI_MODE_3, }, @@ -195,6 +197,14 @@ static struct platform_device rtc_device = { #endif #if defined(CONFIG_SMC91X) || defined(CONFIG_SMC91X_MODULE) +#include <linux/smc91x.h> + +static struct smc91x_platdata smc91x_info = { + .flags = SMC91X_USE_16BIT | SMC91X_NOWAIT, + .leda = RPC_LED_100_10, + .ledb = RPC_LED_TX_RX, +}; + static struct resource smc91x_resources[] = { { .start = 0x20200300, @@ -211,6 +221,43 @@ static struct platform_device smc91x_device = { .id = 0, .num_resources = ARRAY_SIZE(smc91x_resources), .resource = smc91x_resources, + .dev = { + .platform_data = &smc91x_info, + }, +}; +#endif + +#if defined(CONFIG_SMSC911X) || defined(CONFIG_SMSC911X_MODULE) +#include <linux/smsc911x.h> + +static struct resource smsc911x_resources[] = { + { + .name = "smsc911x-memory", + .start = 0x20308000, + .end = 0x20308000 + 0xFF, + .flags = IORESOURCE_MEM, + }, { + .start = IRQ_PF8, + .end = IRQ_PF8, + .flags = IORESOURCE_IRQ | IORESOURCE_IRQ_LOWLEVEL, + }, +}; + +static struct smsc911x_platform_config smsc911x_config = { + .flags = SMSC911X_USE_16BIT, + .irq_polarity = SMSC911X_IRQ_POLARITY_ACTIVE_LOW, + .irq_type = SMSC911X_IRQ_TYPE_OPEN_DRAIN, + .phy_interface = PHY_INTERFACE_MODE_MII, +}; + +static struct platform_device smsc911x_device = { + .name = "smsc911x", + .id = 0, + .num_resources = ARRAY_SIZE(smsc911x_resources), + .resource = smsc911x_resources, + .dev = { + .platform_data = &smsc911x_config, + }, }; #endif @@ -324,6 +371,68 @@ static struct platform_device isp1362_hcd_device = { }; #endif + +#if defined(CONFIG_USB_NET2272) || defined(CONFIG_USB_NET2272_MODULE) +static struct resource net2272_bfin_resources[] = { + { + .start = 0x20300000, + .end = 0x20300000 + 0x100, + .flags = IORESOURCE_MEM, + }, { + .start = IRQ_PF6, + .end = IRQ_PF6, + .flags = IORESOURCE_IRQ | IORESOURCE_IRQ_HIGHLEVEL, + }, +}; + +static struct platform_device net2272_bfin_device = { + .name = "net2272", + .id = -1, + .num_resources = ARRAY_SIZE(net2272_bfin_resources), + .resource = net2272_bfin_resources, +}; +#endif + + + +#if defined(CONFIG_MTD_PHYSMAP) || defined(CONFIG_MTD_PHYSMAP_MODULE) +static struct mtd_partition para_partitions[] = { + { + .name = "bootloader(nor)", + .size = 0x40000, + .offset = 0, + }, { + .name = "linux+rootfs(nor)", + .size = MTDPART_SIZ_FULL, + .offset = MTDPART_OFS_APPEND, + }, +}; + +static struct physmap_flash_data para_flash_data = { + .width = 2, + .parts = para_partitions, + .nr_parts = ARRAY_SIZE(para_partitions), +}; + +static struct resource para_flash_resource = { + .start = 0x20000000, + .end = 0x201fffff, + .flags = IORESOURCE_MEM, +}; + +static struct platform_device para_flash_device = { + .name = "physmap-flash", + .id = 0, + .dev = { + .platform_data = ¶_flash_data, + }, + .num_resources = 1, + .resource = ¶_flash_resource, +}; +#endif + + + static const unsigned int cclk_vlev_datasheet[] = { VRPAIR(VLEV_085, 250000000), @@ -382,10 +491,22 @@ static struct platform_device *cm_bf533_devices[] __initdata = { &smc91x_device, #endif +#if defined(CONFIG_SMSC911X) || defined(CONFIG_SMSC911X_MODULE) + &smsc911x_device, +#endif + +#if defined(CONFIG_USB_NET2272) || defined(CONFIG_USB_NET2272_MODULE) + &net2272_bfin_device, +#endif + #if defined(CONFIG_SPI_BFIN) || defined(CONFIG_SPI_BFIN_MODULE) &bfin_spi0_device, #endif +#if defined(CONFIG_MTD_PHYSMAP) || defined(CONFIG_MTD_PHYSMAP_MODULE) + ¶_flash_device, +#endif + &bfin_gpios_device, }; diff --git a/arch/blackfin/mach-bf533/boards/ezkit.c b/arch/blackfin/mach-bf533/boards/ezkit.c index 4e3e511bf14..fd518e383b7 100644 --- a/arch/blackfin/mach-bf533/boards/ezkit.c +++ b/arch/blackfin/mach-bf533/boards/ezkit.c @@ -67,6 +67,14 @@ static struct platform_device bfin_fb_adv7393_device = { * Driver needs to know address, irq and flag pin. */ #if defined(CONFIG_SMC91X) || defined(CONFIG_SMC91X_MODULE) +#include <linux/smc91x.h> + +static struct smc91x_platdata smc91x_info = { + .flags = SMC91X_USE_16BIT | SMC91X_NOWAIT, + .leda = RPC_LED_100_10, + .ledb = RPC_LED_TX_RX, +}; + static struct resource smc91x_resources[] = { { .name = "smc91x-regs", @@ -84,6 +92,9 @@ static struct platform_device smc91x_device = { .id = 0, .num_resources = ARRAY_SIZE(smc91x_resources), .resource = smc91x_resources, + .dev = { + .platform_data = &smc91x_info, + }, }; #endif @@ -263,7 +274,7 @@ static struct spi_board_info bfin_spi_board_info[] __initdata = { #if defined(CONFIG_SND_BLACKFIN_AD1836) || defined(CONFIG_SND_BLACKFIN_AD1836_MODULE) { - .modalias = "ad1836-spi", + .modalias = "ad1836", .max_speed_hz = 3125000, /* max spi clock (SCK) speed in HZ */ .bus_num = 0, .chip_select = CONFIG_SND_BLACKFIN_SPI_PFBIT, diff --git a/arch/blackfin/mach-bf533/boards/stamp.c b/arch/blackfin/mach-bf533/boards/stamp.c index 3d743ccaff6..729fd7c2633 100644 --- a/arch/blackfin/mach-bf533/boards/stamp.c +++ b/arch/blackfin/mach-bf533/boards/stamp.c @@ -35,6 +35,7 @@ #include <linux/mtd/physmap.h> #include <linux/spi/spi.h> #include <linux/spi/flash.h> +#include <linux/spi/mmc_spi.h> #if defined(CONFIG_USB_ISP1362_HCD) || defined(CONFIG_USB_ISP1362_HCD_MODULE) #include <linux/usb/isp1362.h> #endif @@ -62,6 +63,14 @@ static struct platform_device rtc_device = { * Driver needs to know address, irq and flag pin. */ #if defined(CONFIG_SMC91X) || defined(CONFIG_SMC91X_MODULE) +#include <linux/smc91x.h> + +static struct smc91x_platdata smc91x_info = { + .flags = SMC91X_USE_16BIT | SMC91X_NOWAIT, + .leda = RPC_LED_100_10, + .ledb = RPC_LED_TX_RX, +}; + static struct resource smc91x_resources[] = { { .name = "smc91x-regs", @@ -80,6 +89,9 @@ static struct platform_device smc91x_device = { .id = 0, .num_resources = ARRAY_SIZE(smc91x_resources), .resource = smc91x_resources, + .dev = { + .platform_data = &smc91x_info, + }, }; #endif @@ -207,19 +219,38 @@ static struct bfin5xx_spi_chip ad1836_spi_chip_info = { }; #endif -#if defined(CONFIG_PBX) -static struct bfin5xx_spi_chip spi_si3xxx_chip_info = { - .ctl_reg = 0x4, /* send zero */ - .enable_dma = 0, - .bits_per_word = 8, - .cs_change_per_word = 1, +#if defined(CONFIG_SPI_SPIDEV) || defined(CONFIG_SPI_SPIDEV_MODULE) +static struct bfin5xx_spi_chip spidev_chip_info = { + .enable_dma = 0, + .bits_per_word = 8, }; #endif -#if defined(CONFIG_SPI_SPIDEV) || defined(CONFIG_SPI_SPIDEV_MODULE) -static struct bfin5xx_spi_chip spidev_chip_info = { +#if defined(CONFIG_MMC_SPI) || defined(CONFIG_MMC_SPI_MODULE) +#define MMC_SPI_CARD_DETECT_INT IRQ_PF5 +static int bfin_mmc_spi_init(struct device *dev, + irqreturn_t (*detect_int)(int, void *), void *data) +{ + return request_irq(MMC_SPI_CARD_DETECT_INT, detect_int, + IRQF_TRIGGER_FALLING | IRQF_TRIGGER_RISING, + "mmc-spi-detect", data); +} + +static void bfin_mmc_spi_exit(struct device *dev, void *data) +{ + free_irq(MMC_SPI_CARD_DETECT_INT, data); +} + +static struct mmc_spi_platform_data bfin_mmc_spi_pdata = { + .init = bfin_mmc_spi_init, + .exit = bfin_mmc_spi_exit, + .detect_delay = 100, /* msecs */ +}; + +static struct bfin5xx_spi_chip mmc_spi_chip_info = { .enable_dma = 0, .bits_per_word = 8, + .pio_interrupt = 0, }; #endif @@ -250,33 +281,14 @@ static struct spi_board_info bfin_spi_board_info[] __initdata = { #if defined(CONFIG_SND_BLACKFIN_AD1836) || defined(CONFIG_SND_BLACKFIN_AD1836_MODULE) { - .modalias = "ad1836-spi", - .max_speed_hz = 31250000, /* max spi clock (SCK) speed in HZ */ + .modalias = "ad1836", + .max_speed_hz = 3125000, /* max spi clock (SCK) speed in HZ */ .bus_num = 0, .chip_select = CONFIG_SND_BLACKFIN_SPI_PFBIT, .controller_data = &ad1836_spi_chip_info, }, #endif -#if defined(CONFIG_PBX) - { - .modalias = "fxs-spi", - .max_speed_hz = 12500000, /* max spi clock (SCK) speed in HZ */ - .bus_num = 0, - .chip_select = 8 - CONFIG_J11_JUMPER, - .controller_data = &spi_si3xxx_chip_info, - .mode = SPI_MODE_3, - }, - { - .modalias = "fxo-spi", - .max_speed_hz = 12500000, /* max spi clock (SCK) speed in HZ */ - .bus_num = 0, - .chip_select = 8 - CONFIG_J19_JUMPER, - .controller_data = &spi_si3xxx_chip_info, - .mode = SPI_MODE_3, - }, -#endif - #if defined(CONFIG_SPI_SPIDEV) || defined(CONFIG_SPI_SPIDEV_MODULE) { .modalias = "spidev", @@ -286,6 +298,17 @@ static struct spi_board_info bfin_spi_board_info[] __initdata = { .controller_data = &spidev_chip_info, }, #endif +#if defined(CONFIG_MMC_SPI) || defined(CONFIG_MMC_SPI_MODULE) + { + .modalias = "mmc_spi", + .max_speed_hz = 20000000, /* max spi clock (SCK) speed in HZ */ + .bus_num = 0, + .chip_select = 4, + .platform_data = &bfin_mmc_spi_pdata, + .controller_data = &mmc_spi_chip_info, + .mode = SPI_MODE_3, + }, +#endif }; #if defined(CONFIG_SPI_BFIN) || defined(CONFIG_SPI_BFIN_MODULE) @@ -458,7 +481,7 @@ static struct i2c_board_info __initdata bfin_i2c_board_info[] = { I2C_BOARD_INFO("pcf8574_lcd", 0x22), }, #endif -#if defined(CONFIG_TWI_KEYPAD) || defined(CONFIG_TWI_KEYPAD_MODULE) +#if defined(CONFIG_INPUT_PCF8574) || defined(CONFIG_INPUT_PCF8574_MODULE) { I2C_BOARD_INFO("pcf8574_keypad", 0x27), .irq = 39, diff --git a/arch/blackfin/mach-bf533/dma.c b/arch/blackfin/mach-bf533/dma.c index 0a6eb8f24d9..7a443c37fb9 100644 --- a/arch/blackfin/mach-bf533/dma.c +++ b/arch/blackfin/mach-bf533/dma.c @@ -76,12 +76,12 @@ int channel2irq(unsigned int channel) ret_irq = IRQ_SPI; break; - case CH_UART_RX: - ret_irq = IRQ_UART_RX; + case CH_UART0_RX: + ret_irq = IRQ_UART0_RX; break; - case CH_UART_TX: - ret_irq = IRQ_UART_TX; + case CH_UART0_TX: + ret_irq = IRQ_UART0_TX; break; case CH_MEM_STREAM0_SRC: diff --git a/arch/blackfin/mach-bf533/include/mach/bfin_serial_5xx.h b/arch/blackfin/mach-bf533/include/mach/bfin_serial_5xx.h index 4062e24e759..6965b4088c4 100644 --- a/arch/blackfin/mach-bf533/include/mach/bfin_serial_5xx.h +++ b/arch/blackfin/mach-bf533/include/mach/bfin_serial_5xx.h @@ -131,11 +131,11 @@ struct bfin_serial_res { struct bfin_serial_res bfin_serial_resource[] = { { 0xFFC00400, - IRQ_UART_RX, - IRQ_UART_ERROR, + IRQ_UART0_RX, + IRQ_UART0_ERROR, #ifdef CONFIG_SERIAL_BFIN_DMA - CH_UART_TX, - CH_UART_RX, + CH_UART0_TX, + CH_UART0_RX, #endif #ifdef CONFIG_SERIAL_BFIN_CTSRTS CONFIG_UART0_CTS_PIN, diff --git a/arch/blackfin/mach-bf533/include/mach/blackfin.h b/arch/blackfin/mach-bf533/include/mach/blackfin.h index 39aa175f19f..499e897a4f4 100644 --- a/arch/blackfin/mach-bf533/include/mach/blackfin.h +++ b/arch/blackfin/mach-bf533/include/mach/blackfin.h @@ -43,13 +43,6 @@ #define BFIN_UART_NR_PORTS 1 -#define CH_UART_RX CH_UART0_RX -#define CH_UART_TX CH_UART0_TX - -#define IRQ_UART_ERROR IRQ_UART0_ERROR -#define IRQ_UART_RX IRQ_UART0_RX -#define IRQ_UART_TX IRQ_UART0_TX - #define OFFSET_THR 0x00 /* Transmit Holding register */ #define OFFSET_RBR 0x00 /* Receive Buffer register */ #define OFFSET_DLL 0x00 /* Divisor Latch (Low-Byte) */ diff --git a/arch/blackfin/mach-bf537/boards/Kconfig b/arch/blackfin/mach-bf537/boards/Kconfig index 77c59da87e8..44132fda63b 100644 --- a/arch/blackfin/mach-bf537/boards/Kconfig +++ b/arch/blackfin/mach-bf537/boards/Kconfig @@ -9,11 +9,17 @@ config BFIN537_STAMP help BF537-STAMP board support. -config BFIN537_BLUETECHNIX_CM - bool "Bluetechnix CM-BF537" +config BFIN537_BLUETECHNIX_CM_E + bool "Bluetechnix CM-BF537E" depends on (BF537) help - CM-BF537 support for EVAL- and DEV-Board. + CM-BF537E support for EVAL- and DEV-Board. + +config BFIN537_BLUETECHNIX_CM_U + bool "Bluetechnix CM-BF537U" + depends on (BF537) + help + CM-BF537U support for EVAL- and DEV-Board. config BFIN537_BLUETECHNIX_TCM bool "Bluetechnix TCM-BF537" diff --git a/arch/blackfin/mach-bf537/boards/Makefile b/arch/blackfin/mach-bf537/boards/Makefile index 68b98a7af6a..7e6aa4e5b20 100644 --- a/arch/blackfin/mach-bf537/boards/Makefile +++ b/arch/blackfin/mach-bf537/boards/Makefile @@ -3,7 +3,8 @@ # obj-$(CONFIG_BFIN537_STAMP) += stamp.o -obj-$(CONFIG_BFIN537_BLUETECHNIX_CM) += cm_bf537.o +obj-$(CONFIG_BFIN537_BLUETECHNIX_CM_E) += cm_bf537e.o +obj-$(CONFIG_BFIN537_BLUETECHNIX_CM_U) += cm_bf537u.o obj-$(CONFIG_BFIN537_BLUETECHNIX_TCM) += tcm_bf537.o obj-$(CONFIG_PNAV10) += pnav10.o obj-$(CONFIG_CAMSIG_MINOTAUR) += minotaur.o diff --git a/arch/blackfin/mach-bf537/boards/cm_bf537e.c b/arch/blackfin/mach-bf537/boards/cm_bf537e.c new file mode 100644 index 00000000000..87acb7dd2df --- /dev/null +++ b/arch/blackfin/mach-bf537/boards/cm_bf537e.c @@ -0,0 +1,727 @@ +/* + * File: arch/blackfin/mach-bf537/boards/cm_bf537.c + * Based on: arch/blackfin/mach-bf533/boards/ezkit.c + * Author: Aidan Williams <aidan@nicta.com.au> + * + * Created: 2005 + * Description: Board description file + * + * Modified: + * Copyright 2005 National ICT Australia (NICTA) + * Copyright 2004-2006 Analog Devices Inc. + * + * Bugs: Enter bugs at http://blackfin.uclinux.org/ + * + * 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, see the file COPYING, or write + * to the Free Software Foundation, Inc., + * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + */ + +#include <linux/device.h> +#include <linux/etherdevice.h> +#include <linux/platform_device.h> +#include <linux/mtd/mtd.h> +#include <linux/mtd/partitions.h> +#include <linux/mtd/physmap.h> +#include <linux/spi/spi.h> +#include <linux/spi/flash.h> +#if defined(CONFIG_USB_ISP1362_HCD) || defined(CONFIG_USB_ISP1362_HCD_MODULE) +#include <linux/usb/isp1362.h> +#endif +#include <linux/ata_platform.h> +#include <linux/irq.h> +#include <asm/dma.h> +#include <asm/bfin5xx_spi.h> +#include <asm/portmux.h> +#include <asm/dpmc.h> + +/* + * Name the Board for the /proc/cpuinfo + */ +const char bfin_board_name[] = "Bluetechnix CM BF537E"; + +#if defined(CONFIG_SPI_BFIN) || defined(CONFIG_SPI_BFIN_MODULE) +/* all SPI peripherals info goes here */ + +#if defined(CONFIG_MTD_M25P80) || defined(CONFIG_MTD_M25P80_MODULE) +static struct mtd_partition bfin_spi_flash_partitions[] = { + { + .name = "bootloader(spi)", + .size = 0x00020000, + .offset = 0, + .mask_flags = MTD_CAP_ROM + }, { + .name = "linux kernel(spi)", + .size = 0xe0000, + .offset = 0x20000 + }, { + .name = "file system(spi)", + .size = 0x700000, + .offset = 0x00100000, + } +}; + +static struct flash_platform_data bfin_spi_flash_data = { + .name = "m25p80", + .parts = bfin_spi_flash_partitions, + .nr_parts = ARRAY_SIZE(bfin_spi_flash_partitions), + .type = "m25p64", +}; + +/* SPI flash chip (m25p64) */ +static struct bfin5xx_spi_chip spi_flash_chip_info = { + .enable_dma = 0, /* use dma transfer with this chip*/ + .bits_per_word = 8, +}; +#endif + +#if defined(CONFIG_BFIN_SPI_ADC) || defined(CONFIG_BFIN_SPI_ADC_MODULE) +/* SPI ADC chip */ +static struct bfin5xx_spi_chip spi_adc_chip_info = { + .enable_dma = 1, /* use dma transfer with this chip*/ + .bits_per_word = 16, +}; +#endif + +#if defined(CONFIG_SND_BLACKFIN_AD1836) || defined(CONFIG_SND_BLACKFIN_AD1836_MODULE) +static struct bfin5xx_spi_chip ad1836_spi_chip_info = { + .enable_dma = 0, + .bits_per_word = 16, +}; +#endif + +#if defined(CONFIG_MMC_SPI) || defined(CONFIG_MMC_SPI_MODULE) +static struct bfin5xx_spi_chip mmc_spi_chip_info = { + .enable_dma = 0, + .bits_per_word = 8, +}; +#endif + +static struct spi_board_info bfin_spi_board_info[] __initdata = { +#if defined(CONFIG_MTD_M25P80) || defined(CONFIG_MTD_M25P80_MODULE) + { + /* the modalias must be the same as spi device driver name */ + .modalias = "m25p80", /* Name of spi_driver for this device */ + .max_speed_hz = 25000000, /* max spi clock (SCK) speed in HZ */ + .bus_num = 0, /* Framework bus number */ + .chip_select = 1, /* Framework chip select. On STAMP537 it is SPISSEL1*/ + .platform_data = &bfin_spi_flash_data, + .controller_data = &spi_flash_chip_info, + .mode = SPI_MODE_3, + }, +#endif + +#if defined(CONFIG_BFIN_SPI_ADC) || defined(CONFIG_BFIN_SPI_ADC_MODULE) + { + .modalias = "bfin_spi_adc", /* Name of spi_driver for this device */ + .max_speed_hz = 6250000, /* max spi clock (SCK) speed in HZ */ + .bus_num = 0, /* Framework bus number */ + .chip_select = 1, /* Framework chip select. */ + .platform_data = NULL, /* No spi_driver specific config */ + .controller_data = &spi_adc_chip_info, + }, +#endif + +#if defined(CONFIG_SND_BLACKFIN_AD1836) || defined(CONFIG_SND_BLACKFIN_AD1836_MODULE) + { + .modalias = "ad1836", + .max_speed_hz = 3125000, /* max spi clock (SCK) speed in HZ */ + .bus_num = 0, + .chip_select = CONFIG_SND_BLACKFIN_SPI_PFBIT, + .controller_data = &ad1836_spi_chip_info, + }, +#endif + +#if defined(CONFIG_MMC_SPI) || defined(CONFIG_MMC_SPI_MODULE) + { + .modalias = "mmc_spi", + .max_speed_hz = 20000000, /* max spi clock (SCK) speed in HZ */ + .bus_num = 0, + .chip_select = 1, + .controller_data = &mmc_spi_chip_info, + .mode = SPI_MODE_3, + }, +#endif +}; + +/* SPI (0) */ +static struct resource bfin_spi0_resource[] = { + [0] = { + .start = SPI0_REGBASE, + .end = SPI0_REGBASE + 0xFF, + .flags = IORESOURCE_MEM, + }, + [1] = { + .start = CH_SPI, + .end = CH_SPI, + .flags = IORESOURCE_DMA, + }, + [2] = { + .start = IRQ_SPI, + .end = IRQ_SPI, + .flags = IORESOURCE_IRQ, + }, +}; + +/* SPI controller data */ +static struct bfin5xx_spi_master bfin_spi0_info = { + .num_chipselect = 8, + .enable_dma = 1, /* master has the ability to do dma transfer */ + .pin_req = {P_SPI0_SCK, P_SPI0_MISO, P_SPI0_MOSI, 0}, +}; + +static struct platform_device bfin_spi0_device = { + .name = "bfin-spi", + .id = 0, /* Bus number */ + .num_resources = ARRAY_SIZE(bfin_spi0_resource), + .resource = bfin_spi0_resource, + .dev = { + .platform_data = &bfin_spi0_info, /* Passed to driver */ + }, +}; +#endif /* spi master and devices */ + +#if defined(CONFIG_RTC_DRV_BFIN) || defined(CONFIG_RTC_DRV_BFIN_MODULE) +static struct platform_device rtc_device = { + .name = "rtc-bfin", + .id = -1, +}; +#endif + +#if defined(CONFIG_FB_HITACHI_TX09) || defined(CONFIG_FB_HITACHI_TX09_MODULE) +static struct platform_device hitachi_fb_device = { + .name = "hitachi-tx09", +}; +#endif + +#if defined(CONFIG_SMC91X) || defined(CONFIG_SMC91X_MODULE) +#include <linux/smc91x.h> + +static struct smc91x_platdata smc91x_info = { + .flags = SMC91X_USE_16BIT | SMC91X_NOWAIT, + .leda = RPC_LED_100_10, + .ledb = RPC_LED_TX_RX, +}; + +static struct resource smc91x_resources[] = { + { + .start = 0x20200300, + .end = 0x20200300 + 16, + .flags = IORESOURCE_MEM, + }, { + .start = IRQ_PF14, + .end = IRQ_PF14, + .flags = IORESOURCE_IRQ | IORESOURCE_IRQ_HIGHLEVEL, + }, +}; + +static struct platform_device smc91x_device = { + .name = "smc91x", + .id = 0, + .num_resources = ARRAY_SIZE(smc91x_resources), + .resource = smc91x_resources, + .dev = { + .platform_data = &smc91x_info, + }, +}; +#endif + +#if defined(CONFIG_USB_ISP1362_HCD) || defined(CONFIG_USB_ISP1362_HCD_MODULE) +static struct resource isp1362_hcd_resources[] = { + { + .start = 0x20308000, + .end = 0x20308000, + .flags = IORESOURCE_MEM, + }, { + .start = 0x20308004, + .end = 0x20308004, + .flags = IORESOURCE_MEM, + }, { + .start = IRQ_PG15, + .end = IRQ_PG15, + .flags = IORESOURCE_IRQ | IORESOURCE_IRQ_HIGHLEVEL, + }, +}; + +static struct isp1362_platform_data isp1362_priv = { + .sel15Kres = 1, + .clknotstop = 0, + .oc_enable = 0, + .int_act_high = 0, + .int_edge_triggered = 0, + .remote_wakeup_connected = 0, + .no_power_switching = 1, + .power_switching_mode = 0, +}; + +static struct platform_device isp1362_hcd_device = { + .name = "isp1362-hcd", + .id = 0, + .dev = { + .platform_data = &isp1362_priv, + }, + .num_resources = ARRAY_SIZE(isp1362_hcd_resources), + .resource = isp1362_hcd_resources, +}; +#endif + +#if defined(CONFIG_USB_NET2272) || defined(CONFIG_USB_NET2272_MODULE) +static struct resource net2272_bfin_resources[] = { + { + .start = 0x20300000, + .end = 0x20300000 + 0x100, + .flags = IORESOURCE_MEM, + }, { + .start = IRQ_PG13, + .end = IRQ_PG13, + .flags = IORESOURCE_IRQ | IORESOURCE_IRQ_HIGHLEVEL, + }, +}; + +static struct platform_device net2272_bfin_device = { + .name = "net2272", + .id = -1, + .num_resources = ARRAY_SIZE(net2272_bfin_resources), + .resource = net2272_bfin_resources, +}; +#endif + +static struct resource bfin_gpios_resources = { + .start = 0, + .end = MAX_BLACKFIN_GPIOS - 1, + .flags = IORESOURCE_IRQ, +}; + +static struct platform_device bfin_gpios_device = { + .name = "simple-gpio", + .id = -1, + .num_resources = 1, + .resource = &bfin_gpios_resources, +}; + +#if defined(CONFIG_MTD_GPIO_ADDR) || defined(CONFIG_MTD_GPIO_ADDR_MODULE) +static struct mtd_partition cm_partitions[] = { + { + .name = "bootloader(nor)", + .size = 0x40000, + .offset = 0, + }, { + .name = "linux kernel(nor)", + .size = 0x100000, + .offset = MTDPART_OFS_APPEND, + }, { + .name = "file system(nor)", + .size = MTDPART_SIZ_FULL, + .offset = MTDPART_OFS_APPEND, + } +}; + +static struct physmap_flash_data cm_flash_data = { + .width = 2, + .parts = cm_partitions, + .nr_parts = ARRAY_SIZE(cm_partitions), +}; + +static unsigned cm_flash_gpios[] = { GPIO_PF4 }; + +static struct resource cm_flash_resource[] = { + { + .name = "cfi_probe", + .start = 0x20000000, + .end = 0x201fffff, + .flags = IORESOURCE_MEM, + }, { + .start = (unsigned long)cm_flash_gpios, + .end = ARRAY_SIZE(cm_flash_gpios), + .flags = IORESOURCE_IRQ, + } +}; + +static struct platform_device cm_flash_device = { + .name = "gpio-addr-flash", + .id = 0, + .dev = { + .platform_data = &cm_flash_data, + }, + .num_resources = ARRAY_SIZE(cm_flash_resource), + .resource = cm_flash_resource, +}; +#endif + +#if defined(CONFIG_SERIAL_BFIN) || defined(CONFIG_SERIAL_BFIN_MODULE) +#ifdef CONFIG_SERIAL_BFIN_UART0 +static struct resource bfin_uart0_resources[] = { + { + .start = 0xFFC00400, + .end = 0xFFC004FF, + .flags = IORESOURCE_MEM, + }, + { + .start = IRQ_UART0_RX, + .end = IRQ_UART0_RX+1, + .flags = IORESOURCE_IRQ, + }, + { + .start = IRQ_UART0_ERROR, + .end = IRQ_UART0_ERROR, + .flags = IORESOURCE_IRQ, + }, + { + .start = CH_UART0_TX, + .end = CH_UART0_TX, + .flags = IORESOURCE_DMA, + }, + { + .start = CH_UART0_RX, + .end = CH_UART0_RX, + .flags = IORESOURCE_DMA, + }, +#ifdef CONFIG_BFIN_UART0_CTSRTS + { + /* + * Refer to arch/blackfin/mach-xxx/include/mach/gpio.h for the GPIO map. + */ + .start = -1, + .end = -1, + .flags = IORESOURCE_IO, + }, + { + /* + * Refer to arch/blackfin/mach-xxx/include/mach/gpio.h for the GPIO map. + */ + .start = -1, + .end = -1, + .flags = IORESOURCE_IO, + }, +#endif +}; + +static struct platform_device bfin_uart0_device = { + .name = "bfin-uart", + .id = 0, + .num_resources = ARRAY_SIZE(bfin_uart0_resources), + .resource = bfin_uart0_resources, +}; +#endif +#ifdef CONFIG_SERIAL_BFIN_UART1 +static struct resource bfin_uart1_resources[] = { + { + .start = 0xFFC02000, + .end = 0xFFC020FF, + .flags = IORESOURCE_MEM, + }, + { + .start = IRQ_UART1_RX, + .end = IRQ_UART1_RX+1, + .flags = IORESOURCE_IRQ, + }, + { + .start = IRQ_UART1_ERROR, + .end = IRQ_UART1_ERROR, + .flags = IORESOURCE_IRQ, + }, + { + .start = CH_UART1_TX, + .end = CH_UART1_TX, + .flags = IORESOURCE_DMA, + }, + { + .start = CH_UART1_RX, + .end = CH_UART1_RX, + .flags = IORESOURCE_DMA, + }, +#ifdef CONFIG_BFIN_UART1_CTSRTS + { + /* + * Refer to arch/blackfin/mach-xxx/include/mach/gpio.h for the GPIO map. + */ + .start = -1, + .end = -1, + .flags = IORESOURCE_IO, + }, + { + /* + * Refer to arch/blackfin/mach-xxx/include/mach/gpio.h for the GPIO map. + */ + .start = -1, + .end = -1, + .flags = IORESOURCE_IO, + }, +#endif +}; + +static struct platform_device bfin_uart1_device = { + .name = "bfin-uart", + .id = 1, + .num_resources = ARRAY_SIZE(bfin_uart1_resources), + .resource = bfin_uart1_resources, +}; +#endif +#endif + +#if defined(CONFIG_BFIN_SIR) || defined(CONFIG_BFIN_SIR_MODULE) +#ifdef CONFIG_BFIN_SIR0 +static struct resource bfin_sir0_resources[] = { + { + .start = 0xFFC00400, + .end = 0xFFC004FF, + .flags = IORESOURCE_MEM, + }, + { + .start = IRQ_UART0_RX, + .end = IRQ_UART0_RX+1, + .flags = IORESOURCE_IRQ, + }, + { + .start = CH_UART0_RX, + .end = CH_UART0_RX+1, + .flags = IORESOURCE_DMA, + }, +}; +static struct platform_device bfin_sir0_device = { + .name = "bfin_sir", + .id = 0, + .num_resources = ARRAY_SIZE(bfin_sir0_resources), + .resource = bfin_sir0_resources, +}; +#endif +#ifdef CONFIG_BFIN_SIR1 +static struct resource bfin_sir1_resources[] = { + { + .start = 0xFFC02000, + .end = 0xFFC020FF, + .flags = IORESOURCE_MEM, + }, + { + .start = IRQ_UART1_RX, + .end = IRQ_UART1_RX+1, + .flags = IORESOURCE_IRQ, + }, + { + .start = CH_UART1_RX, + .end = CH_UART1_RX+1, + .flags = IORESOURCE_DMA, + }, +}; +static struct platform_device bfin_sir1_device = { + .name = "bfin_sir", + .id = 1, + .num_resources = ARRAY_SIZE(bfin_sir1_resources), + .resource = bfin_sir1_resources, +}; +#endif +#endif + +#if defined(CONFIG_I2C_BLACKFIN_TWI) || defined(CONFIG_I2C_BLACKFIN_TWI_MODULE) +static struct resource bfin_twi0_resource[] = { + [0] = { + .start = TWI0_REGBASE, + .end = TWI0_REGBASE, + .flags = IORESOURCE_MEM, + }, + [1] = { + .start = IRQ_TWI, + .end = IRQ_TWI, + .flags = IORESOURCE_IRQ, + }, +}; + +static struct platform_device i2c_bfin_twi_device = { + .name = "i2c-bfin-twi", + .id = 0, + .num_resources = ARRAY_SIZE(bfin_twi0_resource), + .resource = bfin_twi0_resource, +}; +#endif + +#if defined(CONFIG_SERIAL_BFIN_SPORT) || defined(CONFIG_SERIAL_BFIN_SPORT_MODULE) +static struct platform_device bfin_sport0_uart_device = { + .name = "bfin-sport-uart", + .id = 0, +}; + +static struct platform_device bfin_sport1_uart_device = { + .name = "bfin-sport-uart", + .id = 1, +}; +#endif + +#if defined(CONFIG_BFIN_MAC) || defined(CONFIG_BFIN_MAC_MODULE) +static struct platform_device bfin_mii_bus = { + .name = "bfin_mii_bus", +}; + +static struct platform_device bfin_mac_device = { + .name = "bfin_mac", + .dev.platform_data = &bfin_mii_bus, +}; +#endif + +#if defined(CONFIG_PATA_PLATFORM) || defined(CONFIG_PATA_PLATFORM_MODULE) +#define PATA_INT IRQ_PF14 + +static struct pata_platform_info bfin_pata_platform_data = { + .ioport_shift = 2, + .irq_type = IRQF_TRIGGER_HIGH | IRQF_DISABLED, +}; + +static struct resource bfin_pata_resources[] = { + { + .start = 0x2030C000, + .end = 0x2030C01F, + .flags = IORESOURCE_MEM, + }, + { + .start = 0x2030D018, + .end = 0x2030D01B, + .flags = IORESOURCE_MEM, + }, + { + .start = PATA_INT, + .end = PATA_INT, + .flags = IORESOURCE_IRQ, + }, +}; + +static struct platform_device bfin_pata_device = { + .name = "pata_platform", + .id = -1, + .num_resources = ARRAY_SIZE(bfin_pata_resources), + .resource = bfin_pata_resources, + .dev = { + .platform_data = &bfin_pata_platform_data, + } +}; +#endif + +static const unsigned int cclk_vlev_datasheet[] = +{ + VRPAIR(VLEV_085, 250000000), + VRPAIR(VLEV_090, 376000000), + VRPAIR(VLEV_095, 426000000), + VRPAIR(VLEV_100, 426000000), + VRPAIR(VLEV_105, 476000000), + VRPAIR(VLEV_110, 476000000), + VRPAIR(VLEV_115, 476000000), + VRPAIR(VLEV_120, 500000000), + VRPAIR(VLEV_125, 533000000), + VRPAIR(VLEV_130, 600000000), +}; + +static struct bfin_dpmc_platform_data bfin_dmpc_vreg_data = { + .tuple_tab = cclk_vlev_datasheet, + .tabsize = ARRAY_SIZE(cclk_vlev_datasheet), + .vr_settling_time = 25 /* us */, +}; + +static struct platform_device bfin_dpmc = { + .name = "bfin dpmc", + .dev = { + .platform_data = &bfin_dmpc_vreg_data, + }, +}; + +static struct platform_device *cm_bf537e_devices[] __initdata = { + + &bfin_dpmc, + +#if defined(CONFIG_FB_HITACHI_TX09) || defined(CONFIG_FB_HITACHI_TX09_MODULE) + &hitachi_fb_device, +#endif + +#if defined(CONFIG_RTC_DRV_BFIN) || defined(CONFIG_RTC_DRV_BFIN_MODULE) + &rtc_device, +#endif + +#if defined(CONFIG_SERIAL_BFIN) || defined(CONFIG_SERIAL_BFIN_MODULE) +#ifdef CONFIG_SERIAL_BFIN_UART0 + &bfin_uart0_device, +#endif +#ifdef CONFIG_SERIAL_BFIN_UART1 + &bfin_uart1_device, +#endif +#endif + +#if defined(CONFIG_BFIN_SIR) || defined(CONFIG_BFIN_SIR_MODULE) +#ifdef CONFIG_BFIN_SIR0 + &bfin_sir0_device, +#endif +#ifdef CONFIG_BFIN_SIR1 + &bfin_sir1_device, +#endif +#endif + +#if defined(CONFIG_I2C_BLACKFIN_TWI) || defined(CONFIG_I2C_BLACKFIN_TWI_MODULE) + &i2c_bfin_twi_device, +#endif + +#if defined(CONFIG_SERIAL_BFIN_SPORT) || defined(CONFIG_SERIAL_BFIN_SPORT_MODULE) + &bfin_sport0_uart_device, + &bfin_sport1_uart_device, +#endif + +#if defined(CONFIG_USB_ISP1362_HCD) || defined(CONFIG_USB_ISP1362_HCD_MODULE) + &isp1362_hcd_device, +#endif + +#if defined(CONFIG_SMC91X) || defined(CONFIG_SMC91X_MODULE) + &smc91x_device, +#endif + +#if defined(CONFIG_BFIN_MAC) || defined(CONFIG_BFIN_MAC_MODULE) + &bfin_mii_bus, + &bfin_mac_device, +#endif + +#if defined(CONFIG_USB_NET2272) || defined(CONFIG_USB_NET2272_MODULE) + &net2272_bfin_device, +#endif + +#if defined(CONFIG_SPI_BFIN) || defined(CONFIG_SPI_BFIN_MODULE) + &bfin_spi0_device, +#endif + +#if defined(CONFIG_PATA_PLATFORM) || defined(CONFIG_PATA_PLATFORM_MODULE) + &bfin_pata_device, +#endif + +#if defined(CONFIG_MTD_GPIO_ADDR) || defined(CONFIG_MTD_GPIO_ADDR_MODULE) + &cm_flash_device, +#endif + + &bfin_gpios_device, +}; + +static int __init cm_bf537e_init(void) +{ + printk(KERN_INFO "%s(): registering device resources\n", __func__); + platform_add_devices(cm_bf537e_devices, ARRAY_SIZE(cm_bf537e_devices)); +#if defined(CONFIG_SPI_BFIN) || defined(CONFIG_SPI_BFIN_MODULE) + spi_register_board_info(bfin_spi_board_info, ARRAY_SIZE(bfin_spi_board_info)); +#endif + +#if defined(CONFIG_PATA_PLATFORM) || defined(CONFIG_PATA_PLATFORM_MODULE) + irq_desc[PATA_INT].status |= IRQ_NOAUTOEN; +#endif + return 0; +} + +arch_initcall(cm_bf537e_init); + +void bfin_get_ether_addr(char *addr) +{ + random_ether_addr(addr); + printk(KERN_WARNING "%s:%s: Setting Ethernet MAC to a random one\n", __FILE__, __func__); +} +EXPORT_SYMBOL(bfin_get_ether_addr); diff --git a/arch/blackfin/mach-bf537/boards/cm_bf537.c b/arch/blackfin/mach-bf537/boards/cm_bf537u.c index 2a87d1cfcd0..8219dc3d65b 100644 --- a/arch/blackfin/mach-bf537/boards/cm_bf537.c +++ b/arch/blackfin/mach-bf537/boards/cm_bf537u.c @@ -1,5 +1,5 @@ /* - * File: arch/blackfin/mach-bf537/boards/cm_bf537.c + * File: arch/blackfin/mach-bf537/boards/cm_bf537u.c * Based on: arch/blackfin/mach-bf533/boards/ezkit.c * Author: Aidan Williams <aidan@nicta.com.au> * @@ -45,11 +45,12 @@ #include <asm/bfin5xx_spi.h> #include <asm/portmux.h> #include <asm/dpmc.h> +#include <linux/spi/mmc_spi.h> /* * Name the Board for the /proc/cpuinfo */ -const char bfin_board_name[] = "Bluetechnix CM BF537"; +const char bfin_board_name[] = "Bluetechnix CM BF537U"; #if defined(CONFIG_SPI_BFIN) || defined(CONFIG_SPI_BFIN_MODULE) /* all SPI peripherals info goes here */ @@ -101,13 +102,6 @@ static struct bfin5xx_spi_chip ad1836_spi_chip_info = { }; #endif -#if defined(CONFIG_AD9960) || defined(CONFIG_AD9960_MODULE) -static struct bfin5xx_spi_chip ad9960_spi_chip_info = { - .enable_dma = 0, - .bits_per_word = 16, -}; -#endif - #if defined(CONFIG_MMC_SPI) || defined(CONFIG_MMC_SPI_MODULE) static struct bfin5xx_spi_chip mmc_spi_chip_info = { .enable_dma = 0, @@ -142,7 +136,7 @@ static struct spi_board_info bfin_spi_board_info[] __initdata = { #if defined(CONFIG_SND_BLACKFIN_AD1836) || defined(CONFIG_SND_BLACKFIN_AD1836_MODULE) { - .modalias = "ad1836-spi", + .modalias = "ad1836", .max_speed_hz = 3125000, /* max spi clock (SCK) speed in HZ */ .bus_num = 0, .chip_select = CONFIG_SND_BLACKFIN_SPI_PFBIT, @@ -150,16 +144,6 @@ static struct spi_board_info bfin_spi_board_info[] __initdata = { }, #endif -#if defined(CONFIG_AD9960) || defined(CONFIG_AD9960_MODULE) - { - .modalias = "ad9960-spi", - .max_speed_hz = 10000000, /* max spi clock (SCK) speed in HZ */ - .bus_num = 0, - .chip_select = 1, - .controller_data = &ad9960_spi_chip_info, - }, -#endif - #if defined(CONFIG_MMC_SPI) || defined(CONFIG_MMC_SPI_MODULE) { .modalias = "mmc_spi", @@ -223,6 +207,14 @@ static struct platform_device hitachi_fb_device = { #endif #if defined(CONFIG_SMC91X) || defined(CONFIG_SMC91X_MODULE) +#include <linux/smc91x.h> + +static struct smc91x_platdata smc91x_info = { + .flags = SMC91X_USE_16BIT | SMC91X_NOWAIT, + .leda = RPC_LED_100_10, + .ledb = RPC_LED_TX_RX, +}; + static struct resource smc91x_resources[] = { { .start = 0x20200300, @@ -240,6 +232,9 @@ static struct platform_device smc91x_device = { .id = 0, .num_resources = ARRAY_SIZE(smc91x_resources), .resource = smc91x_resources, + .dev = { + .platform_data = &smc91x_info, + }, }; #endif @@ -324,7 +319,7 @@ static struct mtd_partition cm_partitions[] = { .offset = 0, }, { .name = "linux kernel(nor)", - .size = 0xE0000, + .size = 0x100000, .offset = MTDPART_OFS_APPEND, }, { .name = "file system(nor)", @@ -339,7 +334,7 @@ static struct physmap_flash_data cm_flash_data = { .nr_parts = ARRAY_SIZE(cm_partitions), }; -static unsigned cm_flash_gpios[] = { GPIO_PF4 }; +static unsigned cm_flash_gpios[] = { GPIO_PH0 }; static struct resource cm_flash_resource[] = { { @@ -548,7 +543,7 @@ static struct platform_device bfin_dpmc = { }, }; -static struct platform_device *cm_bf537_devices[] __initdata = { +static struct platform_device *cm_bf537u_devices[] __initdata = { &bfin_dpmc, @@ -614,10 +609,10 @@ static struct platform_device *cm_bf537_devices[] __initdata = { &bfin_gpios_device, }; -static int __init cm_bf537_init(void) +static int __init cm_bf537u_init(void) { printk(KERN_INFO "%s(): registering device resources\n", __func__); - platform_add_devices(cm_bf537_devices, ARRAY_SIZE(cm_bf537_devices)); + platform_add_devices(cm_bf537u_devices, ARRAY_SIZE(cm_bf537u_devices)); #if defined(CONFIG_SPI_BFIN) || defined(CONFIG_SPI_BFIN_MODULE) spi_register_board_info(bfin_spi_board_info, ARRAY_SIZE(bfin_spi_board_info)); #endif @@ -628,7 +623,7 @@ static int __init cm_bf537_init(void) return 0; } -arch_initcall(cm_bf537_init); +arch_initcall(cm_bf537u_init); void bfin_get_ether_addr(char *addr) { diff --git a/arch/blackfin/mach-bf537/boards/pnav10.c b/arch/blackfin/mach-bf537/boards/pnav10.c index 838240f151f..10b35b838ba 100644 --- a/arch/blackfin/mach-bf537/boards/pnav10.c +++ b/arch/blackfin/mach-bf537/boards/pnav10.c @@ -92,6 +92,14 @@ static struct platform_device rtc_device = { #endif #if defined(CONFIG_SMC91X) || defined(CONFIG_SMC91X_MODULE) +#include <linux/smc91x.h> + +static struct smc91x_platdata smc91x_info = { + .flags = SMC91X_USE_16BIT | SMC91X_NOWAIT, + .leda = RPC_LED_100_10, + .ledb = RPC_LED_TX_RX, +}; + static struct resource smc91x_resources[] = { { .name = "smc91x-regs", @@ -110,6 +118,9 @@ static struct platform_device smc91x_device = { .id = 0, .num_resources = ARRAY_SIZE(smc91x_resources), .resource = smc91x_resources, + .dev = { + .platform_data = &smc91x_info, + }, }; #endif @@ -282,13 +293,6 @@ static struct bfin5xx_spi_chip ad1836_spi_chip_info = { }; #endif -#if defined(CONFIG_AD9960) || defined(CONFIG_AD9960_MODULE) -static struct bfin5xx_spi_chip ad9960_spi_chip_info = { - .enable_dma = 0, - .bits_per_word = 16, -}; -#endif - #if defined(CONFIG_MMC_SPI) || defined(CONFIG_MMC_SPI_MODULE) static struct bfin5xx_spi_chip mmc_spi_chip_info = { .enable_dma = 0, @@ -348,22 +352,13 @@ static struct spi_board_info bfin_spi_board_info[] __initdata = { #if defined(CONFIG_SND_BLACKFIN_AD1836) \ || defined(CONFIG_SND_BLACKFIN_AD1836_MODULE) { - .modalias = "ad1836-spi", + .modalias = "ad1836", .max_speed_hz = 3125000, /* max spi clock (SCK) speed in HZ */ .bus_num = 0, .chip_select = CONFIG_SND_BLACKFIN_SPI_PFBIT, .controller_data = &ad1836_spi_chip_info, }, #endif -#if defined(CONFIG_AD9960) || defined(CONFIG_AD9960_MODULE) - { - .modalias = "ad9960-spi", - .max_speed_hz = 10000000, /* max spi clock (SCK) speed in HZ */ - .bus_num = 0, - .chip_select = 1, - .controller_data = &ad9960_spi_chip_info, - }, -#endif #if defined(CONFIG_MMC_SPI) || defined(CONFIG_MMC_SPI_MODULE) { .modalias = "mmc_spi", diff --git a/arch/blackfin/mach-bf537/boards/stamp.c b/arch/blackfin/mach-bf537/boards/stamp.c index bd656907b8c..9db6b40743e 100644 --- a/arch/blackfin/mach-bf537/boards/stamp.c +++ b/arch/blackfin/mach-bf537/boards/stamp.c @@ -171,6 +171,14 @@ static struct platform_device rtc_device = { #endif #if defined(CONFIG_SMC91X) || defined(CONFIG_SMC91X_MODULE) +#include <linux/smc91x.h> + +static struct smc91x_platdata smc91x_info = { + .flags = SMC91X_USE_16BIT | SMC91X_NOWAIT, + .leda = RPC_LED_100_10, + .ledb = RPC_LED_TX_RX, +}; + static struct resource smc91x_resources[] = { { .name = "smc91x-regs", @@ -189,6 +197,9 @@ static struct platform_device smc91x_device = { .id = 0, .num_resources = ARRAY_SIZE(smc91x_resources), .resource = smc91x_resources, + .dev = { + .platform_data = &smc91x_info, + }, }; #endif @@ -196,10 +207,15 @@ static struct platform_device smc91x_device = { static struct resource dm9000_resources[] = { [0] = { .start = 0x203FB800, - .end = 0x203FB800 + 8, + .end = 0x203FB800 + 1, .flags = IORESOURCE_MEM, }, [1] = { + .start = 0x203FB804, + .end = 0x203FB804 + 1, + .flags = IORESOURCE_MEM, + }, + [2] = { .start = IRQ_PF9, .end = IRQ_PF9, .flags = (IORESOURCE_IRQ | IORESOURCE_IRQ_HIGHEDGE), @@ -516,19 +532,135 @@ static struct bfin5xx_spi_chip spi_adc_chip_info = { }; #endif -#if defined(CONFIG_SND_BLACKFIN_AD1836) \ - || defined(CONFIG_SND_BLACKFIN_AD1836_MODULE) +#if defined(CONFIG_SND_BF5XX_SOC_AD1836) \ + || defined(CONFIG_SND_BF5XX_SOC_AD1836_MODULE) static struct bfin5xx_spi_chip ad1836_spi_chip_info = { .enable_dma = 0, .bits_per_word = 16, }; #endif -#if defined(CONFIG_AD9960) || defined(CONFIG_AD9960_MODULE) -static struct bfin5xx_spi_chip ad9960_spi_chip_info = { +#if defined(CONFIG_SND_BF5XX_SOC_AD1938) \ + || defined(CONFIG_SND_BF5XX_SOC_AD1938_MODULE) +static struct bfin5xx_spi_chip ad1938_spi_chip_info = { + .enable_dma = 0, + .bits_per_word = 8, + .cs_gpio = GPIO_PF5, +}; +#endif + +#if defined(CONFIG_INPUT_EVAL_AD7147EBZ) +#include <linux/input.h> +#include <linux/input/ad714x.h> +static struct bfin5xx_spi_chip ad7147_spi_chip_info = { .enable_dma = 0, .bits_per_word = 16, }; + +static struct ad714x_slider_plat slider_plat[] = { + { + .start_stage = 0, + .end_stage = 7, + .max_coord = 128, + }, +}; + +static struct ad714x_button_plat button_plat[] = { + { + .keycode = BTN_FORWARD, + .l_mask = 0, + .h_mask = 0x600, + }, + { + .keycode = BTN_LEFT, + .l_mask = 0, + .h_mask = 0x500, + }, + { + .keycode = BTN_MIDDLE, + .l_mask = 0, + .h_mask = 0x800, + }, + { + .keycode = BTN_RIGHT, + .l_mask = 0x100, + .h_mask = 0x400, + }, + { + .keycode = BTN_BACK, + .l_mask = 0x200, + .h_mask = 0x400, + }, +}; +static struct ad714x_platform_data ad7147_platfrom_data = { + .slider_num = 1, + .button_num = 5, + .slider = slider_plat, + .button = button_plat, + .stage_cfg_reg = { + {0xFBFF, 0x1FFF, 0, 0x2626, 1600, 1600, 1600, 1600}, + {0xEFFF, 0x1FFF, 0, 0x2626, 1650, 1650, 1650, 1650}, + {0xFFFF, 0x1FFE, 0, 0x2626, 1650, 1650, 1650, 1650}, + {0xFFFF, 0x1FFB, 0, 0x2626, 1650, 1650, 1650, 1650}, + {0xFFFF, 0x1FEF, 0, 0x2626, 1650, 1650, 1650, 1650}, + {0xFFFF, 0x1FBF, 0, 0x2626, 1650, 1650, 1650, 1650}, + {0xFFFF, 0x1EFF, 0, 0x2626, 1650, 1650, 1650, 1650}, + {0xFFFF, 0x1BFF, 0, 0x2626, 1600, 1600, 1600, 1600}, + {0xFF7B, 0x3FFF, 0x506, 0x2626, 1100, 1100, 1150, 1150}, + {0xFDFE, 0x3FFF, 0x606, 0x2626, 1100, 1100, 1150, 1150}, + {0xFEBA, 0x1FFF, 0x1400, 0x2626, 1200, 1200, 1300, 1300}, + {0xFFEF, 0x1FFF, 0x0, 0x2626, 1100, 1100, 1150, 1150}, + }, + .sys_cfg_reg = {0x2B2, 0x0, 0x3233, 0x819, 0x832, 0xCFF, 0xCFF, 0x0}, +}; +#endif + +#if defined(CONFIG_INPUT_EVAL_AD7142EB) +#include <linux/input.h> +#include <linux/input/ad714x.h> +static struct ad714x_button_plat button_plat[] = { + { + .keycode = BTN_1, + .l_mask = 0, + .h_mask = 0x1, + }, + { + .keycode = BTN_2, + .l_mask = 0, + .h_mask = 0x2, + }, + { + .keycode = BTN_3, + .l_mask = 0, + .h_mask = 0x4, + }, + { + .keycode = BTN_4, + .l_mask = 0x0, + .h_mask = 0x8, + }, +}; +static struct ad714x_platform_data ad7142_platfrom_data = { + .button_num = 4, + .button = button_plat, + .stage_cfg_reg = { + /* fixme: figure out right setting for all comoponent according + * to hardware feature of EVAL-AD7142EB board */ + {0xE7FF, 0x3FFF, 0x0005, 0x2626, 0x01F4, 0x01F4, 0x028A, 0x028A}, + {0xFDBF, 0x3FFF, 0x0001, 0x2626, 0x01F4, 0x01F4, 0x028A, 0x028A}, + {0xFFFF, 0x2DFF, 0x0001, 0x2626, 0x01F4, 0x01F4, 0x028A, 0x028A}, + {0xFFFF, 0x37BF, 0x0001, 0x2626, 0x01F4, 0x01F4, 0x028A, 0x028A}, + {0xFFFF, 0x3FFF, 0x0000, 0x0606, 0x01F4, 0x01F4, 0x0320, 0x0320}, + {0xFFFF, 0x3FFF, 0x0000, 0x0606, 0x01F4, 0x01F4, 0x0320, 0x0320}, + {0xFFFF, 0x3FFF, 0x0000, 0x0606, 0x01F4, 0x01F4, 0x0320, 0x0320}, + {0xFFFF, 0x3FFF, 0x0000, 0x0606, 0x01F4, 0x01F4, 0x0320, 0x0320}, + {0xFFFF, 0x3FFF, 0x0000, 0x0606, 0x01F4, 0x01F4, 0x0320, 0x0320}, + {0xFFFF, 0x3FFF, 0x0000, 0x0606, 0x01F4, 0x01F4, 0x0320, 0x0320}, + {0xFFFF, 0x3FFF, 0x0000, 0x0606, 0x01F4, 0x01F4, 0x0320, 0x0320}, + {0xFFFF, 0x3FFF, 0x0000, 0x0606, 0x01F4, 0x01F4, 0x0320, 0x0320}, + }, + .sys_cfg_reg = {0x0B2, 0x0, 0x690, 0x664, 0x290F, 0xF, 0xF, 0x0}, +}; #endif #if defined(CONFIG_MMC_SPI) || defined(CONFIG_MMC_SPI_MODULE) @@ -555,15 +687,7 @@ static struct mmc_spi_platform_data bfin_mmc_spi_pdata = { static struct bfin5xx_spi_chip mmc_spi_chip_info = { .enable_dma = 0, .bits_per_word = 8, -}; -#endif - -#if defined(CONFIG_PBX) -static struct bfin5xx_spi_chip spi_si3xxx_chip_info = { - .ctl_reg = 0x4, /* send zero */ - .enable_dma = 0, - .bits_per_word = 8, - .cs_change_per_word = 1, + .pio_interrupt = 0, }; #endif @@ -743,25 +867,42 @@ static struct spi_board_info bfin_spi_board_info[] __initdata = { }, #endif -#if defined(CONFIG_SND_BLACKFIN_AD1836) \ - || defined(CONFIG_SND_BLACKFIN_AD1836_MODULE) +#if defined(CONFIG_SND_BF5XX_SOC_AD1836) \ + || defined(CONFIG_SND_BF5XX_SOC_AD1836_MODULE) { - .modalias = "ad1836-spi", + .modalias = "ad1836", .max_speed_hz = 3125000, /* max spi clock (SCK) speed in HZ */ .bus_num = 0, - .chip_select = CONFIG_SND_BLACKFIN_SPI_PFBIT, + .chip_select = 4,/* CONFIG_SND_BLACKFIN_SPI_PFBIT */ .controller_data = &ad1836_spi_chip_info, + .mode = SPI_MODE_3, }, #endif -#if defined(CONFIG_AD9960) || defined(CONFIG_AD9960_MODULE) + +#if defined(CONFIG_SND_BF5XX_SOC_AD1938) || defined(CONFIG_SND_BF5XX_SOC_AD1938_MODULE) { - .modalias = "ad9960-spi", - .max_speed_hz = 10000000, /* max spi clock (SCK) speed in HZ */ + .modalias = "ad1938", + .max_speed_hz = 3125000, /* max spi clock (SCK) speed in HZ */ .bus_num = 0, - .chip_select = 1, - .controller_data = &ad9960_spi_chip_info, + .chip_select = 0,/* CONFIG_SND_BLACKFIN_SPI_PFBIT */ + .controller_data = &ad1938_spi_chip_info, + .mode = SPI_MODE_3, }, #endif + +#if defined(CONFIG_INPUT_EVAL_AD7147EBZ) + { + .modalias = "ad714x_captouch", + .max_speed_hz = 1000000, /* max spi clock (SCK) speed in HZ */ + .irq = IRQ_PF4, + .bus_num = 0, + .chip_select = 5, + .mode = SPI_MODE_3, + .platform_data = &ad7147_platfrom_data, + .controller_data = &ad7147_spi_chip_info, + }, +#endif + #if defined(CONFIG_MMC_SPI) || defined(CONFIG_MMC_SPI_MODULE) { .modalias = "mmc_spi", @@ -773,24 +914,6 @@ static struct spi_board_info bfin_spi_board_info[] __initdata = { .mode = SPI_MODE_3, }, #endif -#if defined(CONFIG_PBX) - { - .modalias = "fxs-spi", - .max_speed_hz = 12500000, /* max spi clock (SCK) speed in HZ */ - .bus_num = 0, - .chip_select = 8 - CONFIG_J11_JUMPER, - .controller_data = &spi_si3xxx_chip_info, - .mode = SPI_MODE_3, - }, - { - .modalias = "fxo-spi", - .max_speed_hz = 12500000, /* max spi clock (SCK) speed in HZ */ - .bus_num = 0, - .chip_select = 8 - CONFIG_J19_JUMPER, - .controller_data = &spi_si3xxx_chip_info, - .mode = SPI_MODE_3, - }, -#endif #if defined(CONFIG_TOUCHSCREEN_AD7877) || defined(CONFIG_TOUCHSCREEN_AD7877_MODULE) { .modalias = "ad7877", @@ -864,6 +987,11 @@ static struct resource bfin_spi0_resource[] = { [1] = { .start = CH_SPI, .end = CH_SPI, + .flags = IORESOURCE_DMA, + }, + [2] = { + .start = IRQ_SPI, + .end = IRQ_SPI, .flags = IORESOURCE_IRQ, }, }; @@ -1089,7 +1217,7 @@ static struct platform_device i2c_bfin_twi_device = { #if defined(CONFIG_KEYBOARD_ADP5588) || defined(CONFIG_KEYBOARD_ADP5588_MODULE) #include <linux/input.h> -#include <linux/i2c/adp5588_keys.h> +#include <linux/i2c/adp5588.h> static const unsigned short adp5588_keymap[ADP5588_KEYMAPSIZE] = { [0] = KEY_GRAVE, [1] = KEY_1, @@ -1309,11 +1437,20 @@ static struct adp5520_platform_data adp5520_pdev_data = { #endif +#if defined(CONFIG_GPIO_ADP5588) || defined(CONFIG_GPIO_ADP5588_MODULE) +#include <linux/i2c/adp5588.h> +static struct adp5588_gpio_platfrom_data adp5588_gpio_data = { + .gpio_start = 50, + .pullup_dis_mask = 0, +}; +#endif + static struct i2c_board_info __initdata bfin_i2c_board_info[] = { -#if defined(CONFIG_JOYSTICK_AD7142) || defined(CONFIG_JOYSTICK_AD7142_MODULE) +#if defined(CONFIG_INPUT_EVAL_AD7142EB) { - I2C_BOARD_INFO("ad7142_joystick", 0x2C), + I2C_BOARD_INFO("ad7142_captouch", 0x2C), .irq = IRQ_PG5, + .platform_data = (void *)&ad7142_platfrom_data, }, #endif #if defined(CONFIG_BFIN_TWI_LCD) || defined(CONFIG_BFIN_TWI_LCD_MODULE) @@ -1321,7 +1458,7 @@ static struct i2c_board_info __initdata bfin_i2c_board_info[] = { I2C_BOARD_INFO("pcf8574_lcd", 0x22), }, #endif -#if defined(CONFIG_TWI_KEYPAD) || defined(CONFIG_TWI_KEYPAD_MODULE) +#if defined(CONFIG_INPUT_PCF8574) || defined(CONFIG_INPUT_PCF8574_MODULE) { I2C_BOARD_INFO("pcf8574_keypad", 0x27), .irq = IRQ_PG6, @@ -1355,6 +1492,12 @@ static struct i2c_board_info __initdata bfin_i2c_board_info[] = { .platform_data = (void *)&adxl34x_info, }, #endif +#if defined(CONFIG_GPIO_ADP5588) || defined(CONFIG_GPIO_ADP5588_MODULE) + { + I2C_BOARD_INFO("adp5588-gpio", 0x34), + .platform_data = (void *)&adp5588_gpio_data, + }, +#endif }; #if defined(CONFIG_SERIAL_BFIN_SPORT) || defined(CONFIG_SERIAL_BFIN_SPORT_MODULE) @@ -1456,6 +1599,13 @@ static struct platform_device bfin_dpmc = { }, }; +#if defined(CONFIG_SND_BF5XX_TDM) || defined(CONFIG_SND_BF5XX_TDM_MODULE) +static struct platform_device bfin_tdm = { + .name = "bfin-tdm", + /* TODO: add platform data here */ +}; +#endif + static struct platform_device *stamp_devices[] __initdata = { &bfin_dpmc, @@ -1561,6 +1711,10 @@ static struct platform_device *stamp_devices[] __initdata = { #if defined(CONFIG_MTD_PHYSMAP) || defined(CONFIG_MTD_PHYSMAP_MODULE) &stamp_flash_device, #endif + +#if defined(CONFIG_SND_BF5XX_TDM) || defined(CONFIG_SND_BF5XX_TDM_MODULE) + &bfin_tdm, +#endif }; static int __init stamp_init(void) @@ -1572,11 +1726,6 @@ static int __init stamp_init(void) platform_add_devices(stamp_devices, ARRAY_SIZE(stamp_devices)); spi_register_board_info(bfin_spi_board_info, ARRAY_SIZE(bfin_spi_board_info)); -#if (defined(CONFIG_PATA_PLATFORM) || defined(CONFIG_PATA_PLATFORM_MODULE)) \ - && defined(PATA_INT) - irq_desc[PATA_INT].status |= IRQ_NOAUTOEN; -#endif - return 0; } diff --git a/arch/blackfin/mach-bf537/boards/tcm_bf537.c b/arch/blackfin/mach-bf537/boards/tcm_bf537.c index e523e6e610d..61353f7bcb9 100644 --- a/arch/blackfin/mach-bf537/boards/tcm_bf537.c +++ b/arch/blackfin/mach-bf537/boards/tcm_bf537.c @@ -45,6 +45,7 @@ #include <asm/bfin5xx_spi.h> #include <asm/portmux.h> #include <asm/dpmc.h> +#include <linux/spi/mmc_spi.h> /* * Name the Board for the /proc/cpuinfo @@ -101,13 +102,6 @@ static struct bfin5xx_spi_chip ad1836_spi_chip_info = { }; #endif -#if defined(CONFIG_AD9960) || defined(CONFIG_AD9960_MODULE) -static struct bfin5xx_spi_chip ad9960_spi_chip_info = { - .enable_dma = 0, - .bits_per_word = 16, -}; -#endif - #if defined(CONFIG_MMC_SPI) || defined(CONFIG_MMC_SPI_MODULE) static struct bfin5xx_spi_chip mmc_spi_chip_info = { .enable_dma = 0, @@ -142,7 +136,7 @@ static struct spi_board_info bfin_spi_board_info[] __initdata = { #if defined(CONFIG_SND_BLACKFIN_AD1836) || defined(CONFIG_SND_BLACKFIN_AD1836_MODULE) { - .modalias = "ad1836-spi", + .modalias = "ad1836", .max_speed_hz = 3125000, /* max spi clock (SCK) speed in HZ */ .bus_num = 0, .chip_select = CONFIG_SND_BLACKFIN_SPI_PFBIT, @@ -150,22 +144,12 @@ static struct spi_board_info bfin_spi_board_info[] __initdata = { }, #endif -#if defined(CONFIG_AD9960) || defined(CONFIG_AD9960_MODULE) - { - .modalias = "ad9960-spi", - .max_speed_hz = 10000000, /* max spi clock (SCK) speed in HZ */ - .bus_num = 0, - .chip_select = 1, - .controller_data = &ad9960_spi_chip_info, - }, -#endif - #if defined(CONFIG_MMC_SPI) || defined(CONFIG_MMC_SPI_MODULE) { .modalias = "mmc_spi", .max_speed_hz = 25000000, /* max spi clock (SCK) speed in HZ */ .bus_num = 0, - .chip_select = 5, + .chip_select = 1, .controller_data = &mmc_spi_chip_info, .mode = SPI_MODE_3, }, @@ -223,6 +207,14 @@ static struct platform_device hitachi_fb_device = { #endif #if defined(CONFIG_SMC91X) || defined(CONFIG_SMC91X_MODULE) +#include <linux/smc91x.h> + +static struct smc91x_platdata smc91x_info = { + .flags = SMC91X_USE_16BIT | SMC91X_NOWAIT, + .leda = RPC_LED_100_10, + .ledb = RPC_LED_TX_RX, +}; + static struct resource smc91x_resources[] = { { .start = 0x20200300, @@ -240,6 +232,9 @@ static struct platform_device smc91x_device = { .id = 0, .num_resources = ARRAY_SIZE(smc91x_resources), .resource = smc91x_resources, + .dev = { + .platform_data = &smc91x_info, + }, }; #endif @@ -285,12 +280,12 @@ static struct platform_device isp1362_hcd_device = { #if defined(CONFIG_USB_NET2272) || defined(CONFIG_USB_NET2272_MODULE) static struct resource net2272_bfin_resources[] = { { - .start = 0x20200000, - .end = 0x20200000 + 0x100, + .start = 0x20300000, + .end = 0x20300000 + 0x100, .flags = IORESOURCE_MEM, }, { - .start = IRQ_PH14, - .end = IRQ_PH14, + .start = IRQ_PG13, + .end = IRQ_PG13, .flags = IORESOURCE_IRQ | IORESOURCE_IRQ_HIGHLEVEL, }, }; @@ -324,7 +319,7 @@ static struct mtd_partition cm_partitions[] = { .offset = 0, }, { .name = "linux kernel(nor)", - .size = 0xE0000, + .size = 0x100000, .offset = MTDPART_OFS_APPEND, }, { .name = "file system(nor)", diff --git a/arch/blackfin/mach-bf537/dma.c b/arch/blackfin/mach-bf537/dma.c index 81185051de9..d23fc0edf2b 100644 --- a/arch/blackfin/mach-bf537/dma.c +++ b/arch/blackfin/mach-bf537/dma.c @@ -96,12 +96,12 @@ int channel2irq(unsigned int channel) ret_irq = IRQ_SPI; break; - case CH_UART_RX: - ret_irq = IRQ_UART_RX; + case CH_UART0_RX: + ret_irq = IRQ_UART0_RX; break; - case CH_UART_TX: - ret_irq = IRQ_UART_TX; + case CH_UART0_TX: + ret_irq = IRQ_UART0_TX; break; case CH_MEM_STREAM0_SRC: diff --git a/arch/blackfin/mach-bf537/include/mach/anomaly.h b/arch/blackfin/mach-bf537/include/mach/anomaly.h index e66aa131f51..f091ad2d8ea 100644 --- a/arch/blackfin/mach-bf537/include/mach/anomaly.h +++ b/arch/blackfin/mach-bf537/include/mach/anomaly.h @@ -143,7 +143,7 @@ /* Possible RETS Register Corruption when Subroutine Is under 5 Cycles in Duration */ #define ANOMALY_05000371 (1) /* SSYNC Stalls Processor when Executed from Non-Cacheable Memory */ -#define ANOMALY_05000402 (__SILICON_REVISION__ >= 5) +#define ANOMALY_05000402 (__SILICON_REVISION__ == 2) /* Level-Sensitive External GPIO Wakeups May Cause Indefinite Stall */ #define ANOMALY_05000403 (1) /* Speculative Fetches Can Cause Undesired External FIFO Operations */ diff --git a/arch/blackfin/mach-bf537/include/mach/blackfin.h b/arch/blackfin/mach-bf537/include/mach/blackfin.h index f5e5015ad83..9ee8834c8f1 100644 --- a/arch/blackfin/mach-bf537/include/mach/blackfin.h +++ b/arch/blackfin/mach-bf537/include/mach/blackfin.h @@ -45,96 +45,11 @@ #if !defined(__ASSEMBLY__) #include "cdefBF534.h" -/* UART 0*/ -#define bfin_read_UART_THR() bfin_read_UART0_THR() -#define bfin_write_UART_THR(val) bfin_write_UART0_THR(val) -#define bfin_read_UART_RBR() bfin_read_UART0_RBR() -#define bfin_write_UART_RBR(val) bfin_write_UART0_RBR(val) -#define bfin_read_UART_DLL() bfin_read_UART0_DLL() -#define bfin_write_UART_DLL(val) bfin_write_UART0_DLL(val) -#define bfin_read_UART_IER() bfin_read_UART0_IER() -#define bfin_write_UART_IER(val) bfin_write_UART0_IER(val) -#define bfin_read_UART_DLH() bfin_read_UART0_DLH() -#define bfin_write_UART_DLH(val) bfin_write_UART0_DLH(val) -#define bfin_read_UART_IIR() bfin_read_UART0_IIR() -#define bfin_write_UART_IIR(val) bfin_write_UART0_IIR(val) -#define bfin_read_UART_LCR() bfin_read_UART0_LCR() -#define bfin_write_UART_LCR(val) bfin_write_UART0_LCR(val) -#define bfin_read_UART_MCR() bfin_read_UART0_MCR() -#define bfin_write_UART_MCR(val) bfin_write_UART0_MCR(val) -#define bfin_read_UART_LSR() bfin_read_UART0_LSR() -#define bfin_write_UART_LSR(val) bfin_write_UART0_LSR(val) -#define bfin_read_UART_SCR() bfin_read_UART0_SCR() -#define bfin_write_UART_SCR(val) bfin_write_UART0_SCR(val) -#define bfin_read_UART_GCTL() bfin_read_UART0_GCTL() -#define bfin_write_UART_GCTL(val) bfin_write_UART0_GCTL(val) - #if defined(CONFIG_BF537) || defined(CONFIG_BF536) #include "cdefBF537.h" #endif #endif -/* MAP used DEFINES from BF533 to BF537 - so we don't need to change them in the driver, kernel, etc. */ - -/* UART_IIR Register */ -#define STATUS(x) ((x << 1) & 0x06) -#define STATUS_P1 0x02 -#define STATUS_P0 0x01 - -/* DMA Channel */ -#define bfin_read_CH_UART_RX() bfin_read_CH_UART0_RX() -#define bfin_write_CH_UART_RX(val) bfin_write_CH_UART0_RX(val) -#define CH_UART_RX CH_UART0_RX -#define bfin_read_CH_UART_TX() bfin_read_CH_UART0_TX() -#define bfin_write_CH_UART_TX(val) bfin_write_CH_UART0_TX(val) -#define CH_UART_TX CH_UART0_TX - -/* System Interrupt Controller */ -#define bfin_read_IRQ_UART_RX() bfin_read_IRQ_UART0_RX() -#define bfin_write_IRQ_UART_RX(val) bfin_write_IRQ_UART0_RX(val) -#define IRQ_UART_RX IRQ_UART0_RX -#define bfin_read_IRQ_UART_TX() bfin_read_IRQ_UART0_TX() -#define bfin_write_IRQ_UART_TX(val) bfin_write_IRQ_UART0_TX(val) -#define IRQ_UART_TX IRQ_UART0_TX -#define bfin_read_IRQ_UART_ERROR() bfin_read_IRQ_UART0_ERROR() -#define bfin_write_IRQ_UART_ERROR(val) bfin_write_IRQ_UART0_ERROR(val) -#define IRQ_UART_ERROR IRQ_UART0_ERROR - -/* MMR Registers*/ -#define bfin_read_UART_THR() bfin_read_UART0_THR() -#define bfin_write_UART_THR(val) bfin_write_UART0_THR(val) -#define BFIN_UART_THR UART0_THR -#define bfin_read_UART_RBR() bfin_read_UART0_RBR() -#define bfin_write_UART_RBR(val) bfin_write_UART0_RBR(val) -#define BFIN_UART_RBR UART0_RBR -#define bfin_read_UART_DLL() bfin_read_UART0_DLL() -#define bfin_write_UART_DLL(val) bfin_write_UART0_DLL(val) -#define BFIN_UART_DLL UART0_DLL -#define bfin_read_UART_IER() bfin_read_UART0_IER() -#define bfin_write_UART_IER(val) bfin_write_UART0_IER(val) -#define BFIN_UART_IER UART0_IER -#define bfin_read_UART_DLH() bfin_read_UART0_DLH() -#define bfin_write_UART_DLH(val) bfin_write_UART0_DLH(val) -#define BFIN_UART_DLH UART0_DLH -#define bfin_read_UART_IIR() bfin_read_UART0_IIR() -#define bfin_write_UART_IIR(val) bfin_write_UART0_IIR(val) -#define BFIN_UART_IIR UART0_IIR -#define bfin_read_UART_LCR() bfin_read_UART0_LCR() -#define bfin_write_UART_LCR(val) bfin_write_UART0_LCR(val) -#define BFIN_UART_LCR UART0_LCR -#define bfin_read_UART_MCR() bfin_read_UART0_MCR() -#define bfin_write_UART_MCR(val) bfin_write_UART0_MCR(val) -#define BFIN_UART_MCR UART0_MCR -#define bfin_read_UART_LSR() bfin_read_UART0_LSR() -#define bfin_write_UART_LSR(val) bfin_write_UART0_LSR(val) -#define BFIN_UART_LSR UART0_LSR -#define bfin_read_UART_SCR() bfin_read_UART0_SCR() -#define bfin_write_UART_SCR(val) bfin_write_UART0_SCR(val) -#define BFIN_UART_SCR UART0_SCR -#define bfin_read_UART_GCTL() bfin_read_UART0_GCTL() -#define bfin_write_UART_GCTL(val) bfin_write_UART0_GCTL(val) -#define BFIN_UART_GCTL UART0_GCTL - #define BFIN_UART_NR_PORTS 2 #define OFFSET_THR 0x00 /* Transmit Holding register */ @@ -150,11 +65,6 @@ #define OFFSET_SCR 0x1C /* SCR Scratch Register */ #define OFFSET_GCTL 0x24 /* Global Control Register */ -/* DPMC*/ -#define bfin_read_STOPCK_OFF() bfin_read_STOPCK() -#define bfin_write_STOPCK_OFF(val) bfin_write_STOPCK(val) -#define STOPCK_OFF STOPCK - /* PLL_DIV Masks */ #define CCLK_DIV1 CSEL_DIV1 /* CCLK = VCO / 1 */ #define CCLK_DIV2 CSEL_DIV2 /* CCLK = VCO / 2 */ diff --git a/arch/blackfin/mach-bf538/boards/ezkit.c b/arch/blackfin/mach-bf538/boards/ezkit.c index 57695b4c3c0..f2ac3b0ebf2 100644 --- a/arch/blackfin/mach-bf538/boards/ezkit.c +++ b/arch/blackfin/mach-bf538/boards/ezkit.c @@ -31,6 +31,7 @@ #include <linux/device.h> #include <linux/platform_device.h> #include <linux/mtd/mtd.h> +#include <linux/mtd/physmap.h> #include <linux/mtd/partitions.h> #include <linux/spi/spi.h> #include <linux/spi/flash.h> @@ -177,6 +178,14 @@ static struct platform_device bfin_sir2_device = { * Driver needs to know address, irq and flag pin. */ #if defined(CONFIG_SMC91X) || defined(CONFIG_SMC91X_MODULE) +#include <linux/smc91x.h> + +static struct smc91x_platdata smc91x_info = { + .flags = SMC91X_USE_16BIT | SMC91X_NOWAIT, + .leda = RPC_LED_100_10, + .ledb = RPC_LED_TX_RX, +}; + static struct resource smc91x_resources[] = { { .name = "smc91x-regs", @@ -194,6 +203,9 @@ static struct platform_device smc91x_device = { .id = 0, .num_resources = ARRAY_SIZE(smc91x_resources), .resource = smc91x_resources, + .dev = { + .platform_data = &smc91x_info, + }, }; #endif @@ -390,6 +402,11 @@ static struct resource bfin_spi2_resource[] = { [1] = { .start = CH_SPI2, .end = CH_SPI2, + .flags = IORESOURCE_DMA, + }, + [2] = { + .start = IRQ_SPI2, + .end = IRQ_SPI2, .flags = IORESOURCE_IRQ, } }; @@ -550,6 +567,50 @@ static struct platform_device bfin_dpmc = { }, }; +#if defined(CONFIG_MTD_PHYSMAP) || defined(CONFIG_MTD_PHYSMAP_MODULE) +static struct mtd_partition ezkit_partitions[] = { + { + .name = "bootloader(nor)", + .size = 0x40000, + .offset = 0, + }, { + .name = "linux kernel(nor)", + .size = 0x180000, + .offset = MTDPART_OFS_APPEND, + }, { + .name = "file system(nor)", + .size = MTDPART_SIZ_FULL, + .offset = MTDPART_OFS_APPEND, + } +}; + +static struct physmap_flash_data ezkit_flash_data = { + .width = 2, + .parts = ezkit_partitions, + .nr_parts = ARRAY_SIZE(ezkit_partitions), +}; + +static struct resource ezkit_flash_resource = { + .start = 0x20000000, +#if defined(CONFIG_SMC91X) || defined(CONFIG_SMC91X_MODULE) + .end = 0x202fffff, +#else + .end = 0x203fffff, +#endif + .flags = IORESOURCE_MEM, +}; + +static struct platform_device ezkit_flash_device = { + .name = "physmap-flash", + .id = 0, + .dev = { + .platform_data = &ezkit_flash_data, + }, + .num_resources = 1, + .resource = &ezkit_flash_resource, +}; +#endif + static struct platform_device *cm_bf538_devices[] __initdata = { &bfin_dpmc, @@ -598,6 +659,10 @@ static struct platform_device *cm_bf538_devices[] __initdata = { #endif &bfin_gpios_device, + +#if defined(CONFIG_MTD_PHYSMAP) || defined(CONFIG_MTD_PHYSMAP_MODULE) + &ezkit_flash_device, +#endif }; static int __init ezkit_init(void) diff --git a/arch/blackfin/mach-bf538/include/mach/anomaly.h b/arch/blackfin/mach-bf538/include/mach/anomaly.h index 451cf8a82a4..26b76083e14 100644 --- a/arch/blackfin/mach-bf538/include/mach/anomaly.h +++ b/arch/blackfin/mach-bf538/include/mach/anomaly.h @@ -113,7 +113,7 @@ /* GPIO Pins PC1 and PC4 Can Function as Normal Outputs */ #define ANOMALY_05000375 (__SILICON_REVISION__ < 4) /* SSYNC Stalls Processor when Executed from Non-Cacheable Memory */ -#define ANOMALY_05000402 (__SILICON_REVISION__ < 4) +#define ANOMALY_05000402 (__SILICON_REVISION__ == 3) /* Level-Sensitive External GPIO Wakeups May Cause Indefinite Stall */ #define ANOMALY_05000403 (1) /* Speculative Fetches Can Cause Undesired External FIFO Operations */ diff --git a/arch/blackfin/mach-bf538/include/mach/blackfin.h b/arch/blackfin/mach-bf538/include/mach/blackfin.h index 9496196ac16..5ecee169095 100644 --- a/arch/blackfin/mach-bf538/include/mach/blackfin.h +++ b/arch/blackfin/mach-bf538/include/mach/blackfin.h @@ -47,11 +47,6 @@ #endif #endif -/* UART_IIR Register */ -#define STATUS(x) ((x << 1) & 0x06) -#define STATUS_P1 0x02 -#define STATUS_P0 0x01 - #define BFIN_UART_NR_PORTS 3 #define OFFSET_THR 0x00 /* Transmit Holding register */ @@ -67,11 +62,6 @@ #define OFFSET_SCR 0x1C /* SCR Scratch Register */ #define OFFSET_GCTL 0x24 /* Global Control Register */ -/* DPMC*/ -#define bfin_read_STOPCK_OFF() bfin_read_STOPCK() -#define bfin_write_STOPCK_OFF(val) bfin_write_STOPCK(val) -#define STOPCK_OFF STOPCK - /* PLL_DIV Masks */ #define CCLK_DIV1 CSEL_DIV1 /* CCLK = VCO / 1 */ #define CCLK_DIV2 CSEL_DIV2 /* CCLK = VCO / 2 */ diff --git a/arch/blackfin/mach-bf538/include/mach/cdefBF538.h b/arch/blackfin/mach-bf538/include/mach/cdefBF538.h index 99ca3f4305e..1de67515dc9 100644 --- a/arch/blackfin/mach-bf538/include/mach/cdefBF538.h +++ b/arch/blackfin/mach-bf538/include/mach/cdefBF538.h @@ -1310,6 +1310,7 @@ #define bfin_write_PPI_CONTROL(val) bfin_write16(PPI_CONTROL, val) #define bfin_read_PPI_STATUS() bfin_read16(PPI_STATUS) #define bfin_write_PPI_STATUS(val) bfin_write16(PPI_STATUS, val) +#define bfin_clear_PPI_STATUS() bfin_read_PPI_STATUS() #define bfin_read_PPI_DELAY() bfin_read16(PPI_DELAY) #define bfin_write_PPI_DELAY(val) bfin_write16(PPI_DELAY, val) #define bfin_read_PPI_COUNT() bfin_read16(PPI_COUNT) diff --git a/arch/blackfin/mach-bf538/include/mach/defBF539.h b/arch/blackfin/mach-bf538/include/mach/defBF539.h index bdc330cd0e1..1c58914a874 100644 --- a/arch/blackfin/mach-bf538/include/mach/defBF539.h +++ b/arch/blackfin/mach-bf538/include/mach/defBF539.h @@ -2325,7 +2325,7 @@ #define AMBEN_B0_B1 0x0004 /* Enable Asynchronous Memory Banks 0 & 1 only */ #define AMBEN_B0_B1_B2 0x0006 /* Enable Asynchronous Memory Banks 0, 1, and 2 */ #define AMBEN_ALL 0x0008 /* Enable Asynchronous Memory Banks (all) 0, 1, 2, and 3 */ -#define CDPRIO 0x0100 /* DMA has priority over core for for external accesses */ +#define CDPRIO 0x0100 /* DMA has priority over core for external accesses */ /* EBIU_AMGCTL Bit Positions */ #define AMCKEN_P 0x0000 /* Enable CLKOUT */ diff --git a/arch/blackfin/mach-bf548/boards/cm_bf548.c b/arch/blackfin/mach-bf548/boards/cm_bf548.c index f5a3c30a41b..e565aae11d7 100644 --- a/arch/blackfin/mach-bf548/boards/cm_bf548.c +++ b/arch/blackfin/mach-bf548/boards/cm_bf548.c @@ -291,6 +291,8 @@ static struct platform_device bfin_sir3_device = { #endif #if defined(CONFIG_SMSC911X) || defined(CONFIG_SMSC911X_MODULE) +#include <linux/smsc911x.h> + static struct resource smsc911x_resources[] = { { .name = "smsc911x-memory", @@ -304,11 +306,22 @@ static struct resource smsc911x_resources[] = { .flags = IORESOURCE_IRQ | IORESOURCE_IRQ_LOWLEVEL, }, }; + +static struct smsc911x_platform_config smsc911x_config = { + .flags = SMSC911X_USE_16BIT, + .irq_polarity = SMSC911X_IRQ_POLARITY_ACTIVE_LOW, + .irq_type = SMSC911X_IRQ_TYPE_OPEN_DRAIN, + .phy_interface = PHY_INTERFACE_MODE_MII, +}; + static struct platform_device smsc911x_device = { .name = "smsc911x", .id = 0, .num_resources = ARRAY_SIZE(smsc911x_resources), .resource = smsc911x_resources, + .dev = { + .platform_data = &smsc911x_config, + }, }; #endif @@ -473,7 +486,7 @@ static struct mtd_partition para_partitions[] = { .offset = 0, }, { .name = "linux kernel(nor)", - .size = 0x400000, + .size = 0x100000, .offset = MTDPART_OFS_APPEND, }, { .name = "file system(nor)", @@ -642,7 +655,7 @@ static struct resource bfin_spi1_resource[] = { /* SPI controller data */ static struct bfin5xx_spi_master bf54x_spi_master_info0 = { - .num_chipselect = 8, + .num_chipselect = 3, .enable_dma = 1, /* master has the ability to do dma transfer */ .pin_req = {P_SPI0_SCK, P_SPI0_MISO, P_SPI0_MOSI, 0}, }; @@ -658,7 +671,7 @@ static struct platform_device bf54x_spi_master0 = { }; static struct bfin5xx_spi_master bf54x_spi_master_info1 = { - .num_chipselect = 8, + .num_chipselect = 3, .enable_dma = 1, /* master has the ability to do dma transfer */ .pin_req = {P_SPI1_SCK, P_SPI1_MISO, P_SPI1_MOSI, 0}, }; diff --git a/arch/blackfin/mach-bf548/boards/ezkit.c b/arch/blackfin/mach-bf548/boards/ezkit.c index dc0dd9b2bce..c66f3801274 100644 --- a/arch/blackfin/mach-bf548/boards/ezkit.c +++ b/arch/blackfin/mach-bf548/boards/ezkit.c @@ -99,8 +99,8 @@ static struct platform_device bfin_isp1760_device = { #include <mach/bf54x-lq043.h> static struct bfin_bf54xfb_mach_info bf54x_lq043_data = { - .width = 480, - .height = 272, + .width = 95, + .height = 54, .xres = {480, 480, 480}, .yres = {272, 272, 272}, .bpp = {24, 24, 24}, @@ -702,7 +702,7 @@ static struct spi_board_info bfin_spi_board_info[] __initdata = { #if defined(CONFIG_SND_BLACKFIN_AD1836) \ || defined(CONFIG_SND_BLACKFIN_AD1836_MODULE) { - .modalias = "ad1836-spi", + .modalias = "ad1836", .max_speed_hz = 3125000, /* max spi clock (SCK) speed in HZ */ .bus_num = 1, .chip_select = CONFIG_SND_BLACKFIN_SPI_PFBIT, @@ -783,7 +783,7 @@ static struct resource bfin_spi1_resource[] = { /* SPI controller data */ static struct bfin5xx_spi_master bf54x_spi_master_info0 = { - .num_chipselect = 8, + .num_chipselect = 3, .enable_dma = 1, /* master has the ability to do dma transfer */ .pin_req = {P_SPI0_SCK, P_SPI0_MISO, P_SPI0_MOSI, 0}, }; @@ -799,7 +799,7 @@ static struct platform_device bf54x_spi_master0 = { }; static struct bfin5xx_spi_master bf54x_spi_master_info1 = { - .num_chipselect = 8, + .num_chipselect = 3, .enable_dma = 1, /* master has the ability to do dma transfer */ .pin_req = {P_SPI1_SCK, P_SPI1_MISO, P_SPI1_MOSI, 0}, }; @@ -869,7 +869,7 @@ static struct i2c_board_info __initdata bfin_i2c_board_info1[] = { I2C_BOARD_INFO("pcf8574_lcd", 0x22), }, #endif -#if defined(CONFIG_TWI_KEYPAD) || defined(CONFIG_TWI_KEYPAD_MODULE) +#if defined(CONFIG_INPUT_PCF8574) || defined(CONFIG_INPUT_PCF8574_MODULE) { I2C_BOARD_INFO("pcf8574_keypad", 0x27), .irq = 212, diff --git a/arch/blackfin/mach-bf548/dma.c b/arch/blackfin/mach-bf548/dma.c index 535980652bf..d9239bc05dd 100644 --- a/arch/blackfin/mach-bf548/dma.c +++ b/arch/blackfin/mach-bf548/dma.c @@ -91,16 +91,16 @@ int channel2irq(unsigned int channel) ret_irq = IRQ_SPI1; break; case CH_UART0_RX: - ret_irq = IRQ_UART_RX; + ret_irq = IRQ_UART0_RX; break; case CH_UART0_TX: - ret_irq = IRQ_UART_TX; + ret_irq = IRQ_UART0_TX; break; case CH_UART1_RX: - ret_irq = IRQ_UART_RX; + ret_irq = IRQ_UART1_RX; break; case CH_UART1_TX: - ret_irq = IRQ_UART_TX; + ret_irq = IRQ_UART1_TX; break; case CH_EPPI0: ret_irq = IRQ_EPPI0; diff --git a/arch/blackfin/mach-bf548/include/mach/anomaly.h b/arch/blackfin/mach-bf548/include/mach/anomaly.h index cd040fe0bc5..52b116ae522 100644 --- a/arch/blackfin/mach-bf548/include/mach/anomaly.h +++ b/arch/blackfin/mach-bf548/include/mach/anomaly.h @@ -7,7 +7,7 @@ */ /* This file should be up to date with: - * - Revision H, 01/16/2009; ADSP-BF542/BF544/BF547/BF548/BF549 Blackfin Processor Anomaly List + * - Revision I, 07/23/2009; ADSP-BF542/BF544/BF547/BF548/BF549 Blackfin Processor Anomaly List */ #ifndef _MACH_ANOMALY_H_ @@ -162,6 +162,8 @@ #define ANOMALY_05000430 (__SILICON_REVISION__ >= 2) /* Incorrect Use of Stack in Lockbox Firmware During Authentication */ #define ANOMALY_05000431 (__SILICON_REVISION__ < 3) +/* SW Breakpoints Ignored Upon Return From Lockbox Authentication */ +#define ANOMALY_05000434 (1) /* OTP Write Accesses Not Supported */ #define ANOMALY_05000442 (__SILICON_REVISION__ < 1) /* IFLUSH Instruction at End of Hardware Loop Causes Infinite Stall */ @@ -176,12 +178,26 @@ #define ANOMALY_05000449 (__SILICON_REVISION__ == 1) /* USB DMA Mode 1 Short Packet Data Corruption */ #define ANOMALY_05000450 (1) +/* Incorrect Default Hysteresis Setting for RESET, NMI, and BMODE Signals */ +#define ANOMALY_05000452 (__SILICON_REVISION__ < 1) /* USB Receive Interrupt Is Not Generated in DMA Mode 1 */ -#define ANOMALY_05000456 (__SILICON_REVISION__ < 3) +#define ANOMALY_05000456 (1) +/* Host DMA Port Responds to Certain Bus Activity Without HOST_CE Assertion */ +#define ANOMALY_05000457 (1) +/* USB DMA Mode 1 Failure When Multiple USB DMA Channels Are Concurrently Enabled */ +#define ANOMALY_05000460 (1) /* False Hardware Error when RETI Points to Invalid Memory */ #define ANOMALY_05000461 (1) +/* Synchronization Problem at Startup May Cause SPORT Transmit Channels to Misalign */ +#define ANOMALY_05000462 (1) +/* USB DMA RX Data Corruption */ +#define ANOMALY_05000463 (1) +/* USB TX DMA Hang */ +#define ANOMALY_05000464 (1) /* USB Rx DMA hang */ #define ANOMALY_05000465 (1) +/* TxPktRdy Bit Not Set for Transmit Endpoint When Core and DMA Access USB Endpoint FIFOs Simultaneously */ +#define ANOMALY_05000466 (1) /* Possible RX data corruption when control & data EP FIFOs are accessed via the core */ #define ANOMALY_05000467 (1) @@ -230,6 +246,7 @@ #define ANOMALY_05000364 (0) #define ANOMALY_05000380 (0) #define ANOMALY_05000400 (0) +#define ANOMALY_05000402 (0) #define ANOMALY_05000412 (0) #define ANOMALY_05000432 (0) #define ANOMALY_05000435 (0) diff --git a/arch/blackfin/mach-bf548/include/mach/blackfin.h b/arch/blackfin/mach-bf548/include/mach/blackfin.h index 6b97396d817..318667b2f03 100644 --- a/arch/blackfin/mach-bf548/include/mach/blackfin.h +++ b/arch/blackfin/mach-bf548/include/mach/blackfin.h @@ -72,97 +72,8 @@ #include "cdefBF549.h" #endif -/* UART 1*/ -#define bfin_read_UART_THR() bfin_read_UART1_THR() -#define bfin_write_UART_THR(val) bfin_write_UART1_THR(val) -#define bfin_read_UART_RBR() bfin_read_UART1_RBR() -#define bfin_write_UART_RBR(val) bfin_write_UART1_RBR(val) -#define bfin_read_UART_DLL() bfin_read_UART1_DLL() -#define bfin_write_UART_DLL(val) bfin_write_UART1_DLL(val) -#define bfin_read_UART_IER() bfin_read_UART1_IER() -#define bfin_write_UART_IER(val) bfin_write_UART1_IER(val) -#define bfin_read_UART_DLH() bfin_read_UART1_DLH() -#define bfin_write_UART_DLH(val) bfin_write_UART1_DLH(val) -#define bfin_read_UART_IIR() bfin_read_UART1_IIR() -#define bfin_write_UART_IIR(val) bfin_write_UART1_IIR(val) -#define bfin_read_UART_LCR() bfin_read_UART1_LCR() -#define bfin_write_UART_LCR(val) bfin_write_UART1_LCR(val) -#define bfin_read_UART_MCR() bfin_read_UART1_MCR() -#define bfin_write_UART_MCR(val) bfin_write_UART1_MCR(val) -#define bfin_read_UART_LSR() bfin_read_UART1_LSR() -#define bfin_write_UART_LSR(val) bfin_write_UART1_LSR(val) -#define bfin_read_UART_SCR() bfin_read_UART1_SCR() -#define bfin_write_UART_SCR(val) bfin_write_UART1_SCR(val) -#define bfin_read_UART_GCTL() bfin_read_UART1_GCTL() -#define bfin_write_UART_GCTL(val) bfin_write_UART1_GCTL(val) - #endif -/* MAP used DEFINES from BF533 to BF54x - so we don't need to change - * them in the driver, kernel, etc. */ - -/* UART_IIR Register */ -#define STATUS(x) ((x << 1) & 0x06) -#define STATUS_P1 0x02 -#define STATUS_P0 0x01 - -/* UART 0*/ - -/* DMA Channel */ -#define bfin_read_CH_UART_RX() bfin_read_CH_UART1_RX() -#define bfin_write_CH_UART_RX(val) bfin_write_CH_UART1_RX(val) -#define bfin_read_CH_UART_TX() bfin_read_CH_UART1_TX() -#define bfin_write_CH_UART_TX(val) bfin_write_CH_UART1_TX(val) -#define CH_UART_RX CH_UART1_RX -#define CH_UART_TX CH_UART1_TX - -/* System Interrupt Controller */ -#define bfin_read_IRQ_UART_RX() bfin_read_IRQ_UART1_RX() -#define bfin_write_IRQ_UART_RX(val) bfin_write_IRQ_UART1_RX(val) -#define bfin_read_IRQ_UART_TX() bfin_read_IRQ_UART1_TX() -#define bfin_write_IRQ_UART_TX(val) bfin_write_IRQ_UART1_TX(val) -#define bfin_read_IRQ_UART_ERROR() bfin_read_IRQ_UART1_ERROR() -#define bfin_write_IRQ_UART_ERROR(val) bfin_write_IRQ_UART1_ERROR(val) -#define IRQ_UART_RX IRQ_UART1_RX -#define IRQ_UART_TX IRQ_UART1_TX -#define IRQ_UART_ERROR IRQ_UART1_ERROR - -/* MMR Registers*/ -#define bfin_read_UART_THR() bfin_read_UART1_THR() -#define bfin_write_UART_THR(val) bfin_write_UART1_THR(val) -#define bfin_read_UART_RBR() bfin_read_UART1_RBR() -#define bfin_write_UART_RBR(val) bfin_write_UART1_RBR(val) -#define bfin_read_UART_DLL() bfin_read_UART1_DLL() -#define bfin_write_UART_DLL(val) bfin_write_UART1_DLL(val) -#define bfin_read_UART_IER() bfin_read_UART1_IER() -#define bfin_write_UART_IER(val) bfin_write_UART1_IER(val) -#define bfin_read_UART_DLH() bfin_read_UART1_DLH() -#define bfin_write_UART_DLH(val) bfin_write_UART1_DLH(val) -#define bfin_read_UART_IIR() bfin_read_UART1_IIR() -#define bfin_write_UART_IIR(val) bfin_write_UART1_IIR(val) -#define bfin_read_UART_LCR() bfin_read_UART1_LCR() -#define bfin_write_UART_LCR(val) bfin_write_UART1_LCR(val) -#define bfin_read_UART_MCR() bfin_read_UART1_MCR() -#define bfin_write_UART_MCR(val) bfin_write_UART1_MCR(val) -#define bfin_read_UART_LSR() bfin_read_UART1_LSR() -#define bfin_write_UART_LSR(val) bfin_write_UART1_LSR(val) -#define bfin_read_UART_SCR() bfin_read_UART1_SCR() -#define bfin_write_UART_SCR(val) bfin_write_UART1_SCR(val) -#define bfin_read_UART_GCTL() bfin_read_UART1_GCTL() -#define bfin_write_UART_GCTL(val) bfin_write_UART1_GCTL(val) - -#define BFIN_UART_THR UART1_THR -#define BFIN_UART_RBR UART1_RBR -#define BFIN_UART_DLL UART1_DLL -#define BFIN_UART_IER UART1_IER -#define BFIN_UART_DLH UART1_DLH -#define BFIN_UART_IIR UART1_IIR -#define BFIN_UART_LCR UART1_LCR -#define BFIN_UART_MCR UART1_MCR -#define BFIN_UART_LSR UART1_LSR -#define BFIN_UART_SCR UART1_SCR -#define BFIN_UART_GCTL UART1_GCTL - #define BFIN_UART_NR_PORTS 4 #define OFFSET_DLL 0x00 /* Divisor Latch (Low-Byte) */ diff --git a/arch/blackfin/mach-bf561/boards/cm_bf561.c b/arch/blackfin/mach-bf561/boards/cm_bf561.c index 0c9d72c5f5b..6577ecfcf11 100644 --- a/arch/blackfin/mach-bf561/boards/cm_bf561.c +++ b/arch/blackfin/mach-bf561/boards/cm_bf561.c @@ -42,6 +42,7 @@ #include <asm/bfin5xx_spi.h> #include <asm/portmux.h> #include <asm/dpmc.h> +#include <linux/mtd/physmap.h> /* * Name the Board for the /proc/cpuinfo @@ -98,13 +99,6 @@ static struct bfin5xx_spi_chip ad1836_spi_chip_info = { }; #endif -#if defined(CONFIG_AD9960) || defined(CONFIG_AD9960_MODULE) -static struct bfin5xx_spi_chip ad9960_spi_chip_info = { - .enable_dma = 0, - .bits_per_word = 16, -}; -#endif - #if defined(CONFIG_MMC_SPI) || defined(CONFIG_MMC_SPI_MODULE) static struct bfin5xx_spi_chip mmc_spi_chip_info = { .enable_dma = 0, @@ -139,28 +133,19 @@ static struct spi_board_info bfin_spi_board_info[] __initdata = { #if defined(CONFIG_SND_BLACKFIN_AD1836) || defined(CONFIG_SND_BLACKFIN_AD1836_MODULE) { - .modalias = "ad1836-spi", + .modalias = "ad1836", .max_speed_hz = 3125000, /* max spi clock (SCK) speed in HZ */ .bus_num = 0, .chip_select = CONFIG_SND_BLACKFIN_SPI_PFBIT, .controller_data = &ad1836_spi_chip_info, }, #endif -#if defined(CONFIG_AD9960) || defined(CONFIG_AD9960_MODULE) - { - .modalias = "ad9960-spi", - .max_speed_hz = 10000000, /* max spi clock (SCK) speed in HZ */ - .bus_num = 0, - .chip_select = 1, - .controller_data = &ad9960_spi_chip_info, - }, -#endif #if defined(CONFIG_MMC_SPI) || defined(CONFIG_MMC_SPI_MODULE) { .modalias = "mmc_spi", - .max_speed_hz = 25000000, /* max spi clock (SCK) speed in HZ */ + .max_speed_hz = 20000000, /* max spi clock (SCK) speed in HZ */ .bus_num = 0, - .chip_select = 5, + .chip_select = 1, .controller_data = &mmc_spi_chip_info, .mode = SPI_MODE_3, }, @@ -213,6 +198,13 @@ static struct platform_device hitachi_fb_device = { #if defined(CONFIG_SMC91X) || defined(CONFIG_SMC91X_MODULE) +#include <linux/smc91x.h> + +static struct smc91x_platdata smc91x_info = { + .flags = SMC91X_USE_32BIT | SMC91X_NOWAIT, + .leda = RPC_LED_100_10, + .ledb = RPC_LED_TX_RX, +}; static struct resource smc91x_resources[] = { { @@ -231,6 +223,65 @@ static struct platform_device smc91x_device = { .id = 0, .num_resources = ARRAY_SIZE(smc91x_resources), .resource = smc91x_resources, + .dev = { + .platform_data = &smc91x_info, + }, +}; +#endif + +#if defined(CONFIG_SMSC911X) || defined(CONFIG_SMSC911X_MODULE) +#include <linux/smsc911x.h> + +static struct resource smsc911x_resources[] = { + { + .name = "smsc911x-memory", + .start = 0x24008000, + .end = 0x24008000 + 0xFF, + .flags = IORESOURCE_MEM, + }, + { + .start = IRQ_PF43, + .end = IRQ_PF43, + .flags = IORESOURCE_IRQ | IORESOURCE_IRQ_LOWLEVEL, + }, +}; + +static struct smsc911x_platform_config smsc911x_config = { + .flags = SMSC911X_USE_16BIT, + .irq_polarity = SMSC911X_IRQ_POLARITY_ACTIVE_LOW, + .irq_type = SMSC911X_IRQ_TYPE_OPEN_DRAIN, + .phy_interface = PHY_INTERFACE_MODE_MII, +}; + +static struct platform_device smsc911x_device = { + .name = "smsc911x", + .id = 0, + .num_resources = ARRAY_SIZE(smsc911x_resources), + .resource = smsc911x_resources, + .dev = { + .platform_data = &smsc911x_config, + }, +}; +#endif + +#if defined(CONFIG_USB_NET2272) || defined(CONFIG_USB_NET2272_MODULE) +static struct resource net2272_bfin_resources[] = { + { + .start = 0x24000000, + .end = 0x24000000 + 0x100, + .flags = IORESOURCE_MEM, + }, { + .start = IRQ_PF45, + .end = IRQ_PF45, + .flags = IORESOURCE_IRQ | IORESOURCE_IRQ_HIGHLEVEL, + }, +}; + +static struct platform_device net2272_bfin_device = { + .name = "net2272", + .id = -1, + .num_resources = ARRAY_SIZE(net2272_bfin_resources), + .resource = net2272_bfin_resources, }; #endif @@ -369,6 +420,46 @@ static struct platform_device bfin_pata_device = { }; #endif +#if defined(CONFIG_MTD_PHYSMAP) || defined(CONFIG_MTD_PHYSMAP_MODULE) +static struct mtd_partition para_partitions[] = { + { + .name = "bootloader(nor)", + .size = 0x40000, + .offset = 0, + }, { + .name = "linux kernel(nor)", + .size = 0x100000, + .offset = MTDPART_OFS_APPEND, + }, { + .name = "file system(nor)", + .size = MTDPART_SIZ_FULL, + .offset = MTDPART_OFS_APPEND, + } +}; + +static struct physmap_flash_data para_flash_data = { + .width = 2, + .parts = para_partitions, + .nr_parts = ARRAY_SIZE(para_partitions), +}; + +static struct resource para_flash_resource = { + .start = 0x20000000, + .end = 0x207fffff, + .flags = IORESOURCE_MEM, +}; + +static struct platform_device para_flash_device = { + .name = "physmap-flash", + .id = 0, + .dev = { + .platform_data = ¶_flash_data, + }, + .num_resources = 1, + .resource = ¶_flash_resource, +}; +#endif + static const unsigned int cclk_vlev_datasheet[] = { VRPAIR(VLEV_085, 250000000), @@ -422,6 +513,14 @@ static struct platform_device *cm_bf561_devices[] __initdata = { &smc91x_device, #endif +#if defined(CONFIG_SMSC911X) || defined(CONFIG_SMSC911X_MODULE) + &smsc911x_device, +#endif + +#if defined(CONFIG_USB_NET2272) || defined(CONFIG_USB_NET2272_MODULE) + &net2272_bfin_device, +#endif + #if defined(CONFIG_SPI_BFIN) || defined(CONFIG_SPI_BFIN_MODULE) &bfin_spi0_device, #endif @@ -430,6 +529,10 @@ static struct platform_device *cm_bf561_devices[] __initdata = { &bfin_pata_device, #endif +#if defined(CONFIG_MTD_PHYSMAP) || defined(CONFIG_MTD_PHYSMAP_MODULE) + ¶_flash_device, +#endif + &bfin_gpios_device, }; diff --git a/arch/blackfin/mach-bf561/boards/ezkit.c b/arch/blackfin/mach-bf561/boards/ezkit.c index 4df904f9e90..caed96bb957 100644 --- a/arch/blackfin/mach-bf561/boards/ezkit.c +++ b/arch/blackfin/mach-bf561/boards/ezkit.c @@ -147,6 +147,14 @@ static struct platform_device net2272_bfin_device = { * Driver needs to know address, irq and flag pin. */ #if defined(CONFIG_SMC91X) || defined(CONFIG_SMC91X_MODULE) +#include <linux/smc91x.h> + +static struct smc91x_platdata smc91x_info = { + .flags = SMC91X_USE_32BIT | SMC91X_NOWAIT, + .leda = RPC_LED_100_10, + .ledb = RPC_LED_TX_RX, +}; + static struct resource smc91x_resources[] = { { .name = "smc91x-regs", @@ -166,6 +174,9 @@ static struct platform_device smc91x_device = { .id = 0, .num_resources = ARRAY_SIZE(smc91x_resources), .resource = smc91x_resources, + .dev = { + .platform_data = &smc91x_info, + }, }; #endif @@ -334,7 +345,7 @@ static struct spi_board_info bfin_spi_board_info[] __initdata = { #if defined(CONFIG_SND_BLACKFIN_AD1836) \ || defined(CONFIG_SND_BLACKFIN_AD1836_MODULE) { - .modalias = "ad1836-spi", + .modalias = "ad1836", .max_speed_hz = 3125000, /* max spi clock (SCK) speed in HZ */ .bus_num = 0, .chip_select = CONFIG_SND_BLACKFIN_SPI_PFBIT, diff --git a/arch/blackfin/mach-bf561/include/mach/anomaly.h b/arch/blackfin/mach-bf561/include/mach/anomaly.h index a5312b2d267..70da495c966 100644 --- a/arch/blackfin/mach-bf561/include/mach/anomaly.h +++ b/arch/blackfin/mach-bf561/include/mach/anomaly.h @@ -262,6 +262,8 @@ #define ANOMALY_05000366 (1) /* Possible RETS Register Corruption when Subroutine Is under 5 Cycles in Duration */ #define ANOMALY_05000371 (1) +/* SSYNC Stalls Processor when Executed from Non-Cacheable Memory */ +#define ANOMALY_05000402 (__SILICON_REVISION__ == 4) /* Level-Sensitive External GPIO Wakeups May Cause Indefinite Stall */ #define ANOMALY_05000403 (1) /* TESTSET Instruction Causes Data Corruption with Writeback Data Cache Enabled */ diff --git a/arch/blackfin/mach-bf561/secondary.S b/arch/blackfin/mach-bf561/secondary.S index 35280f06b7b..f72a6af20c4 100644 --- a/arch/blackfin/mach-bf561/secondary.S +++ b/arch/blackfin/mach-bf561/secondary.S @@ -85,16 +85,10 @@ ENTRY(_coreb_trampoline_start) R0 = ~ENICPLB; R0 = R0 & R1; - /* Anomaly 05000125 */ -#ifdef ANOMALY_05000125 - CLI R2; - SSYNC; -#endif + /* Disabling of CPLBs should be proceeded by a CSYNC */ + CSYNC; [p0] = R0; SSYNC; -#ifdef ANOMALY_05000125 - STI R2; -#endif /* Turn off the dcache */ p0.l = LO(DMEM_CONTROL); @@ -103,16 +97,10 @@ ENTRY(_coreb_trampoline_start) R0 = ~ENDCPLB; R0 = R0 & R1; - /* Anomaly 05000125 */ -#ifdef ANOMALY_05000125 - CLI R2; - SSYNC; -#endif + /* Disabling of CPLBs should be proceeded by a CSYNC */ + CSYNC; [p0] = R0; SSYNC; -#ifdef ANOMALY_05000125 - STI R2; -#endif /* in case of double faults, save a few things */ p0.l = _init_retx_coreb; @@ -126,22 +114,22 @@ ENTRY(_coreb_trampoline_start) * below */ GET_PDA(p0, r0); - r7 = [p0 + PDA_RETX]; + r7 = [p0 + PDA_DF_RETX]; p1.l = _init_saved_retx_coreb; p1.h = _init_saved_retx_coreb; [p1] = r7; - r7 = [p0 + PDA_DCPLB]; + r7 = [p0 + PDA_DF_DCPLB]; p1.l = _init_saved_dcplb_fault_addr_coreb; p1.h = _init_saved_dcplb_fault_addr_coreb; [p1] = r7; - r7 = [p0 + PDA_ICPLB]; + r7 = [p0 + PDA_DF_ICPLB]; p1.l = _init_saved_icplb_fault_addr_coreb; p1.h = _init_saved_icplb_fault_addr_coreb; [p1] = r7; - r7 = [p0 + PDA_SEQSTAT]; + r7 = [p0 + PDA_DF_SEQSTAT]; p1.l = _init_saved_seqstat_coreb; p1.h = _init_saved_seqstat_coreb; [p1] = r7; diff --git a/arch/blackfin/mach-common/Makefile b/arch/blackfin/mach-common/Makefile index dd8b2dc97f5..814cb483853 100644 --- a/arch/blackfin/mach-common/Makefile +++ b/arch/blackfin/mach-common/Makefile @@ -6,7 +6,6 @@ obj-y := \ cache.o cache-c.o entry.o head.o \ interrupt.o arch_checks.o ints-priority.o -obj-$(CONFIG_BFIN_ICACHE_LOCK) += lock.o obj-$(CONFIG_PM) += pm.o dpmc_modes.o obj-$(CONFIG_CPU_FREQ) += cpufreq.o obj-$(CONFIG_CPU_VOLTAGE) += dpmc.o diff --git a/arch/blackfin/mach-common/cache-c.c b/arch/blackfin/mach-common/cache-c.c index b59ce3cb380..4ebbd78db3a 100644 --- a/arch/blackfin/mach-common/cache-c.c +++ b/arch/blackfin/mach-common/cache-c.c @@ -1,14 +1,16 @@ /* * Blackfin cache control code (simpler control-style functions) * - * Copyright 2004-2008 Analog Devices Inc. + * Copyright 2004-2009 Analog Devices Inc. * * Enter bugs at http://blackfin.uclinux.org/ * * Licensed under the GPL-2 or later. */ +#include <linux/init.h> #include <asm/blackfin.h> +#include <asm/cplbinit.h> /* Invalidate the Entire Data cache by * clearing DMC[1:0] bits @@ -34,3 +36,43 @@ void blackfin_invalidate_entire_icache(void) SSYNC(); } +#if defined(CONFIG_BFIN_ICACHE) || defined(CONFIG_BFIN_DCACHE) + +static void +bfin_cache_init(struct cplb_entry *cplb_tbl, unsigned long cplb_addr, + unsigned long cplb_data, unsigned long mem_control, + unsigned long mem_mask) +{ + int i; + + for (i = 0; i < MAX_CPLBS; i++) { + bfin_write32(cplb_addr + i * 4, cplb_tbl[i].addr); + bfin_write32(cplb_data + i * 4, cplb_tbl[i].data); + } + + _enable_cplb(mem_control, mem_mask); +} + +#ifdef CONFIG_BFIN_ICACHE +void __cpuinit bfin_icache_init(struct cplb_entry *icplb_tbl) +{ + bfin_cache_init(icplb_tbl, ICPLB_ADDR0, ICPLB_DATA0, IMEM_CONTROL, + (IMC | ENICPLB)); +} +#endif + +#ifdef CONFIG_BFIN_DCACHE +void __cpuinit bfin_dcache_init(struct cplb_entry *dcplb_tbl) +{ + /* + * Anomaly notes: + * 05000287 - We implement workaround #2 - Change the DMEM_CONTROL + * register, so that the port preferences for DAG0 and DAG1 are set + * to port B + */ + bfin_cache_init(dcplb_tbl, DCPLB_ADDR0, DCPLB_DATA0, DMEM_CONTROL, + (DMEM_CNTR | PORT_PREF0 | (ANOMALY_05000287 ? PORT_PREF1 : 0))); +} +#endif + +#endif diff --git a/arch/blackfin/mach-common/entry.S b/arch/blackfin/mach-common/entry.S index fb1795d5be2..1e7cac23e25 100644 --- a/arch/blackfin/mach-common/entry.S +++ b/arch/blackfin/mach-common/entry.S @@ -301,27 +301,31 @@ ENTRY(_ex_replaceable) nop; ENTRY(_ex_trap_c) + /* The only thing that has been saved in this context is + * (R7:6,P5:4), ASTAT & SP - don't use anything else + */ + + GET_PDA(p5, r6); + /* Make sure we are not in a double fault */ p4.l = lo(IPEND); p4.h = hi(IPEND); r7 = [p4]; CC = BITTST (r7, 5); if CC jump _double_fault; + [p5 + PDA_EXIPEND] = r7; /* Call C code (trap_c) to handle the exception, which most * likely involves sending a signal to the current process. * To avoid double faults, lower our priority to IRQ5 first. */ - P5.h = _exception_to_level5; - P5.l = _exception_to_level5; + r7.h = _exception_to_level5; + r7.l = _exception_to_level5; p4.l = lo(EVT5); p4.h = hi(EVT5); - [p4] = p5; + [p4] = r7; csync; - GET_PDA(p5, r6); -#ifndef CONFIG_DEBUG_DOUBLEFAULT - /* * Save these registers, as they are only valid in exception context * (where we are now - as soon as we defer to IRQ5, they can change) @@ -341,7 +345,10 @@ ENTRY(_ex_trap_c) r6 = retx; [p5 + PDA_RETX] = r6; -#endif + + r6 = SEQSTAT; + [p5 + PDA_SEQSTAT] = r6; + /* Save the state of single stepping */ r6 = SYSCFG; [p5 + PDA_SYSCFG] = r6; @@ -349,8 +356,7 @@ ENTRY(_ex_trap_c) BITCLR(r6, SYSCFG_SSSTEP_P); SYSCFG = r6; - /* Disable all interrupts, but make sure level 5 is enabled so - * we can switch to that level. Save the old mask. */ + /* Save the current IMASK, since we change in order to jump to level 5 */ cli r6; [p5 + PDA_EXIMASK] = r6; @@ -358,9 +364,21 @@ ENTRY(_ex_trap_c) p4.h = hi(SAFE_USER_INSTRUCTION); retx = p4; + /* Disable all interrupts, but make sure level 5 is enabled so + * we can switch to that level. + */ r6 = 0x3f; sti r6; + /* In case interrupts are disabled IPEND[4] (global interrupt disable bit) + * clear it (re-enabling interrupts again) by the special sequence of pushing + * RETI onto the stack. This way we can lower ourselves to IVG5 even if the + * exception was taken after the interrupt handler was called but before it + * got a chance to enable global interrupts itself. + */ + [--sp] = reti; + sp += 4; + raise 5; jump.s _bfin_return_from_exception; ENDPROC(_ex_trap_c) @@ -379,8 +397,7 @@ ENTRY(_double_fault) R5 = [P4]; /* Control Register*/ BITCLR(R5,ENICPLB_P); - SSYNC; /* SSYNC required before writing to IMEM_CONTROL. */ - .align 8; + CSYNC; /* Disabling of CPLBs should be proceeded by a CSYNC */ [P4] = R5; SSYNC; @@ -388,8 +405,7 @@ ENTRY(_double_fault) P4.H = HI(DMEM_CONTROL); R5 = [P4]; BITCLR(R5,ENDCPLB_P); - SSYNC; /* SSYNC required before writing to DMEM_CONTROL. */ - .align 8; + CSYNC; /* Disabling of CPLBs should be proceeded by a CSYNC */ [P4] = R5; SSYNC; @@ -420,47 +436,55 @@ ENDPROC(_double_fault) ENTRY(_exception_to_level5) SAVE_ALL_SYS - GET_PDA(p4, r7); /* Fetch current PDA */ - r6 = [p4 + PDA_RETX]; + GET_PDA(p5, r7); /* Fetch current PDA */ + r6 = [p5 + PDA_RETX]; [sp + PT_PC] = r6; - r6 = [p4 + PDA_SYSCFG]; + r6 = [p5 + PDA_SYSCFG]; [sp + PT_SYSCFG] = r6; - /* Restore interrupt mask. We haven't pushed RETI, so this - * doesn't enable interrupts until we return from this handler. */ - r6 = [p4 + PDA_EXIMASK]; - sti r6; + r6 = [p5 + PDA_SEQSTAT]; /* Read back seqstat */ + [sp + PT_SEQSTAT] = r6; /* Restore the hardware error vector. */ - P5.h = _evt_ivhw; - P5.l = _evt_ivhw; + r7.h = _evt_ivhw; + r7.l = _evt_ivhw; p4.l = lo(EVT5); p4.h = hi(EVT5); - [p4] = p5; + [p4] = r7; csync; - p2.l = lo(IPEND); - p2.h = hi(IPEND); - csync; - r0 = [p2]; /* Read current IPEND */ - [sp + PT_IPEND] = r0; /* Store IPEND */ +#ifdef CONFIG_DEBUG_DOUBLEFAULT + /* Now that we have the hardware error vector programmed properly + * we can re-enable interrupts (IPEND[4]), so if the _trap_c causes + * another hardware error, we can catch it (self-nesting). + */ + [--sp] = reti; + sp += 4; +#endif + + r7 = [p5 + PDA_EXIPEND] /* Read the IPEND from the Exception state */ + [sp + PT_IPEND] = r7; /* Store IPEND onto the stack */ r0 = sp; /* stack frame pt_regs pointer argument ==> r0 */ SP += -12; call _trap_c; SP += 12; -#ifdef CONFIG_DEBUG_DOUBLEFAULT - /* Grab ILAT */ - p2.l = lo(ILAT); - p2.h = hi(ILAT); - r0 = [p2]; - r1 = 0x20; /* Did I just cause anther HW error? */ - r0 = r0 & r1; - CC = R0 == R1; - if CC JUMP _double_fault; -#endif + /* If interrupts were off during the exception (IPEND[4] = 1), turn them off + * before we return. + */ + CC = BITTST(r7, EVT_IRPTEN_P) + if !CC jump 1f; + /* this will load a random value into the reti register - but that is OK, + * since we do restore it to the correct value in the 'RESTORE_ALL_SYS' macro + */ + sp += -4; + reti = [sp++]; +1: + /* restore the interrupt mask (IMASK) */ + r6 = [p5 + PDA_EXIMASK]; + sti r6; call _ret_from_exception; RESTORE_ALL_SYS @@ -474,7 +498,7 @@ ENTRY(_trap) /* Exception: 4th entry into system event table(supervisor mode)*/ */ EX_SCRATCH_REG = sp; GET_PDA_SAFE(sp); - sp = [sp + PDA_EXSTACK] + sp = [sp + PDA_EXSTACK]; /* Try to deal with syscalls quickly. */ [--sp] = ASTAT; [--sp] = (R7:6,P5:4); @@ -489,14 +513,7 @@ ENTRY(_trap) /* Exception: 4th entry into system event table(supervisor mode)*/ ssync; #endif -#if ANOMALY_05000283 || ANOMALY_05000315 - cc = r7 == r7; - p5.h = HI(CHIPID); - p5.l = LO(CHIPID); - if cc jump 1f; - r7.l = W[p5]; -1: -#endif + ANOMALY_283_315_WORKAROUND(p5, r7) #ifdef CONFIG_DEBUG_DOUBLEFAULT /* @@ -510,18 +527,18 @@ ENTRY(_trap) /* Exception: 4th entry into system event table(supervisor mode)*/ p4.l = lo(DCPLB_FAULT_ADDR); p4.h = hi(DCPLB_FAULT_ADDR); r7 = [p4]; - [p5 + PDA_DCPLB] = r7; + [p5 + PDA_DF_DCPLB] = r7; p4.l = lo(ICPLB_FAULT_ADDR); p4.h = hi(ICPLB_FAULT_ADDR); r7 = [p4]; - [p5 + PDA_ICPLB] = r7; + [p5 + PDA_DF_ICPLB] = r7; - r6 = retx; - [p5 + PDA_RETX] = r6; + r7 = retx; + [p5 + PDA_DF_RETX] = r7; r7 = SEQSTAT; /* reason code is in bit 5:0 */ - [p5 + PDA_SEQSTAT] = r7; + [p5 + PDA_DF_SEQSTAT] = r7; #else r7 = SEQSTAT; /* reason code is in bit 5:0 */ #endif @@ -686,8 +703,14 @@ ENTRY(_system_call) #ifdef CONFIG_IPIPE cc = BITTST(r7, TIF_IRQ_SYNC); if !cc jump .Lsyscall_no_irqsync; + /* + * Clear IPEND[4] manually to undo what resume_userspace_1 just did; + * we need this so that high priority domain interrupts may still + * preempt the current domain while the pipeline log is being played + * back. + */ [--sp] = reti; - r0 = [sp++]; + SP += 4; /* don't merge with next insn to keep the pattern obvious */ SP += -12; call ___ipipe_sync_root; SP += 12; @@ -699,7 +722,7 @@ ENTRY(_system_call) /* Reenable interrupts. */ [--sp] = reti; - r0 = [sp++]; + sp += 4; SP += -12; call _schedule; @@ -715,7 +738,7 @@ ENTRY(_system_call) .Lsyscall_do_signals: /* Reenable interrupts. */ [--sp] = reti; - r0 = [sp++]; + sp += 4; r0 = sp; SP += -12; @@ -725,10 +748,6 @@ ENTRY(_system_call) .Lsyscall_really_exit: r5 = [sp + PT_RESERVED]; rets = r5; -#ifdef CONFIG_IPIPE - [--sp] = reti; - r5 = [sp++]; -#endif /* CONFIG_IPIPE */ rts; ENDPROC(_system_call) @@ -816,13 +835,13 @@ ENDPROC(_resume) ENTRY(_ret_from_exception) #ifdef CONFIG_IPIPE - [--sp] = rets; - SP += -12; - call ___ipipe_check_root - SP += 12 - rets = [sp++]; - cc = r0 == 0; - if cc jump 4f; /* not on behalf of Linux, get out */ + p2.l = _per_cpu__ipipe_percpu_domain; + p2.h = _per_cpu__ipipe_percpu_domain; + r0.l = _ipipe_root; + r0.h = _ipipe_root; + r2 = [p2]; + cc = r0 == r2; + if !cc jump 4f; /* not on behalf of the root domain, get out */ #endif /* CONFIG_IPIPE */ p2.l = lo(IPEND); p2.h = hi(IPEND); @@ -882,14 +901,9 @@ ENDPROC(_ret_from_exception) #ifdef CONFIG_IPIPE -_sync_root_irqs: - [--sp] = reti; /* Reenable interrupts */ - r0 = [sp++]; - jump.l ___ipipe_sync_root - _resume_kernel_from_int: - r0.l = _sync_root_irqs - r0.h = _sync_root_irqs + r0.l = ___ipipe_sync_root; + r0.h = ___ipipe_sync_root; [--sp] = rets; [--sp] = ( r7:4, p5:3 ); SP += -12; @@ -953,10 +967,10 @@ ENTRY(_lower_to_irq14) #endif #ifdef CONFIG_DEBUG_HWERR - /* enable irq14 & hwerr interrupt, until we transition to _evt14_softirq */ + /* enable irq14 & hwerr interrupt, until we transition to _evt_evt14 */ r0 = (EVT_IVG14 | EVT_IVHW | EVT_IRPTEN | EVT_EVX | EVT_NMI | EVT_RST | EVT_EMU); #else - /* Only enable irq14 interrupt, until we transition to _evt14_softirq */ + /* Only enable irq14 interrupt, until we transition to _evt_evt14 */ r0 = (EVT_IVG14 | EVT_IRPTEN | EVT_EVX | EVT_NMI | EVT_RST | EVT_EMU); #endif sti r0; @@ -964,7 +978,7 @@ ENTRY(_lower_to_irq14) rti; ENDPROC(_lower_to_irq14) -ENTRY(_evt14_softirq) +ENTRY(_evt_evt14) #ifdef CONFIG_DEBUG_HWERR r0 = (EVT_IVHW | EVT_IRPTEN | EVT_EVX | EVT_NMI | EVT_RST | EVT_EMU); sti r0; @@ -974,7 +988,7 @@ ENTRY(_evt14_softirq) [--sp] = RETI; SP += 4; rts; -ENDPROC(_evt14_softirq) +ENDPROC(_evt_evt14) ENTRY(_schedule_and_signal_from_int) /* To end up here, vector 15 was changed - so we have to change it @@ -1004,6 +1018,12 @@ ENTRY(_schedule_and_signal_from_int) #endif sti r0; + /* finish the userspace "atomic" functions for it */ + r1 = FIXED_CODE_END; + r2 = [sp + PT_PC]; + cc = r1 <= r2; + if cc jump .Lresume_userspace (bp); + r0 = sp; sp += -12; call _finish_atomic_sections; @@ -1107,14 +1127,7 @@ ENTRY(_early_trap) SAVE_ALL_SYS trace_buffer_stop(p0,r0); -#if ANOMALY_05000283 || ANOMALY_05000315 - cc = r5 == r5; - p4.h = HI(CHIPID); - p4.l = LO(CHIPID); - if cc jump 1f; - r5.l = W[p4]; -1: -#endif + ANOMALY_283_315_WORKAROUND(p4, r5) /* Turn caches off, to ensure we don't get double exceptions */ @@ -1123,9 +1136,7 @@ ENTRY(_early_trap) R5 = [P4]; /* Control Register*/ BITCLR(R5,ENICPLB_P); - CLI R1; - SSYNC; /* SSYNC required before writing to IMEM_CONTROL. */ - .align 8; + CSYNC; /* Disabling of CPLBs should be proceeded by a CSYNC */ [P4] = R5; SSYNC; @@ -1133,11 +1144,9 @@ ENTRY(_early_trap) P4.H = HI(DMEM_CONTROL); R5 = [P4]; BITCLR(R5,ENDCPLB_P); - SSYNC; /* SSYNC required before writing to DMEM_CONTROL. */ - .align 8; + CSYNC; /* Disabling of CPLBs should be proceeded by a CSYNC */ [P4] = R5; SSYNC; - STI R1; r0 = sp; /* stack frame pt_regs pointer argument ==> r0 */ r1 = RETX; @@ -1611,7 +1620,7 @@ ENTRY(_sys_call_table) .long _sys_preadv .long _sys_pwritev .long _sys_rt_tgsigqueueinfo - .long _sys_perf_counter_open + .long _sys_perf_event_open .rept NR_syscalls-(.-_sys_call_table)/4 .long _sys_ni_syscall diff --git a/arch/blackfin/mach-common/head.S b/arch/blackfin/mach-common/head.S index f826f6b9f91..9c79dfea2a5 100644 --- a/arch/blackfin/mach-common/head.S +++ b/arch/blackfin/mach-common/head.S @@ -124,22 +124,22 @@ ENTRY(__start) * below */ GET_PDA(p0, r0); - r6 = [p0 + PDA_RETX]; + r6 = [p0 + PDA_DF_RETX]; p1.l = _init_saved_retx; p1.h = _init_saved_retx; [p1] = r6; - r6 = [p0 + PDA_DCPLB]; + r6 = [p0 + PDA_DF_DCPLB]; p1.l = _init_saved_dcplb_fault_addr; p1.h = _init_saved_dcplb_fault_addr; [p1] = r6; - r6 = [p0 + PDA_ICPLB]; + r6 = [p0 + PDA_DF_ICPLB]; p1.l = _init_saved_icplb_fault_addr; p1.h = _init_saved_icplb_fault_addr; [p1] = r6; - r6 = [p0 + PDA_SEQSTAT]; + r6 = [p0 + PDA_DF_SEQSTAT]; p1.l = _init_saved_seqstat; p1.h = _init_saved_seqstat; [p1] = r6; @@ -153,6 +153,8 @@ ENTRY(__start) #ifdef CONFIG_EARLY_PRINTK call _init_early_exception_vectors; + r0 = (EVT_IVHW | EVT_IRPTEN | EVT_EVX | EVT_NMI | EVT_RST | EVT_EMU); + sti r0; #endif r0 = 0 (x); @@ -212,12 +214,21 @@ ENTRY(__start) [p0] = p1; csync; +#ifdef CONFIG_EARLY_PRINTK + r0 = (EVT_IVG15 | EVT_IVHW | EVT_IRPTEN | EVT_EVX | EVT_NMI | EVT_RST | EVT_EMU) (z); +#else r0 = EVT_IVG15 (z); +#endif sti r0; raise 15; +#ifdef CONFIG_EARLY_PRINTK + p0.l = _early_trap; + p0.h = _early_trap; +#else p0.l = .LWAIT_HERE; p0.h = .LWAIT_HERE; +#endif reti = p0; #if ANOMALY_05000281 nop; nop; nop; diff --git a/arch/blackfin/mach-common/interrupt.S b/arch/blackfin/mach-common/interrupt.S index 9c46680186e..82d417ef4b5 100644 --- a/arch/blackfin/mach-common/interrupt.S +++ b/arch/blackfin/mach-common/interrupt.S @@ -119,14 +119,8 @@ __common_int_entry: fp = 0; #endif -#if ANOMALY_05000283 || ANOMALY_05000315 - cc = r7 == r7; - p5.h = HI(CHIPID); - p5.l = LO(CHIPID); - if cc jump 1f; - r7.l = W[p5]; -1: -#endif + ANOMALY_283_315_WORKAROUND(p5, r7) + r1 = sp; SP += -12; #ifdef CONFIG_IPIPE @@ -158,14 +152,7 @@ ENTRY(_evt_ivhw) fp = 0; #endif -#if ANOMALY_05000283 || ANOMALY_05000315 - cc = r7 == r7; - p5.h = HI(CHIPID); - p5.l = LO(CHIPID); - if cc jump 1f; - r7.l = W[p5]; -1: -#endif + ANOMALY_283_315_WORKAROUND(p5, r7) /* Handle all stacked hardware errors * To make sure we don't hang forever, only do it 10 times @@ -261,6 +248,31 @@ ENTRY(_evt_system_call) ENDPROC(_evt_system_call) #ifdef CONFIG_IPIPE +/* + * __ipipe_call_irqtail: lowers the current priority level to EVT15 + * before running a user-defined routine, then raises the priority + * level to EVT14 to prepare the caller for a normal interrupt + * return through RTI. + * + * We currently use this facility in two occasions: + * + * - to branch to __ipipe_irq_tail_hook as requested by a high + * priority domain after the pipeline delivered an interrupt, + * e.g. such as Xenomai, in order to start its rescheduling + * procedure, since we may not switch tasks when IRQ levels are + * nested on the Blackfin, so we have to fake an interrupt return + * so that we may reschedule immediately. + * + * - to branch to sync_root_irqs, in order to play any interrupt + * pending for the root domain (i.e. the Linux kernel). This lowers + * the core priority level enough so that Linux IRQ handlers may + * never delay interrupts handled by high priority domains; we defer + * those handlers until this point instead. This is a substitute + * to using a threaded interrupt model for the Linux kernel. + * + * r0: address of user-defined routine + * context: caller must have preempted EVT15, hw interrupts must be off. + */ ENTRY(___ipipe_call_irqtail) p0 = r0; r0.l = 1f; @@ -276,33 +288,19 @@ ENTRY(___ipipe_call_irqtail) ( r7:4, p5:3 ) = [sp++]; rets = [sp++]; - [--sp] = reti; - reti = [sp++]; /* IRQs are off. */ - r0.h = 3f; - r0.l = 3f; - p0.l = lo(EVT14); - p0.h = hi(EVT14); - [p0] = r0; - csync; - r0 = 0x401f (z); +#ifdef CONFIG_DEBUG_HWERR + /* enable irq14 & hwerr interrupt, until we transition to _evt_evt14 */ + r0 = (EVT_IVG14 | EVT_IVHW | \ + EVT_IRPTEN | EVT_EVX | EVT_NMI | EVT_RST | EVT_EMU); +#else + /* Only enable irq14 interrupt, until we transition to _evt_evt14 */ + r0 = (EVT_IVG14 | \ + EVT_IRPTEN | EVT_EVX | EVT_NMI | EVT_RST | EVT_EMU); +#endif sti r0; - raise 14; - [--sp] = reti; /* IRQs on. */ + raise 14; /* Branches to _evt_evt14 */ 2: jump 2b; /* Likely paranoid. */ -3: - sp += 4; /* Discard saved RETI */ - r0.h = _evt14_softirq; - r0.l = _evt14_softirq; - p0.l = lo(EVT14); - p0.h = hi(EVT14); - [p0] = r0; - csync; - p0.l = _bfin_irq_flags; - p0.h = _bfin_irq_flags; - r0 = [p0]; - sti r0; - rts; ENDPROC(___ipipe_call_irqtail) #endif /* CONFIG_IPIPE */ diff --git a/arch/blackfin/mach-common/ints-priority.c b/arch/blackfin/mach-common/ints-priority.c index b42150190d0..6ffda78aaf9 100644 --- a/arch/blackfin/mach-common/ints-priority.c +++ b/arch/blackfin/mach-common/ints-priority.c @@ -967,7 +967,7 @@ void __cpuinit init_exception_vectors(void) bfin_write_EVT11(evt_evt11); bfin_write_EVT12(evt_evt12); bfin_write_EVT13(evt_evt13); - bfin_write_EVT14(evt14_softirq); + bfin_write_EVT14(evt_evt14); bfin_write_EVT15(evt_system_call); CSYNC(); } @@ -1052,18 +1052,26 @@ int __init init_arch_irq(void) set_irq_chained_handler(irq, bfin_demux_error_irq); break; #endif + #ifdef CONFIG_SMP +#ifdef CONFIG_TICKSOURCE_GPTMR0 + case IRQ_TIMER0: +#endif +#ifdef CONFIG_TICKSOURCE_CORETMR + case IRQ_CORETMR: +#endif case IRQ_SUPPLE_0: case IRQ_SUPPLE_1: set_irq_handler(irq, handle_percpu_irq); break; #endif + #ifdef CONFIG_IPIPE #ifndef CONFIG_TICKSOURCE_CORETMR case IRQ_TIMER0: set_irq_handler(irq, handle_simple_irq); break; -#endif /* !CONFIG_TICKSOURCE_CORETMR */ +#endif case IRQ_CORETMR: set_irq_handler(irq, handle_simple_irq); break; @@ -1071,15 +1079,10 @@ int __init init_arch_irq(void) set_irq_handler(irq, handle_level_irq); break; #else /* !CONFIG_IPIPE */ -#ifdef CONFIG_TICKSOURCE_GPTMR0 - case IRQ_TIMER0: - set_irq_handler(irq, handle_percpu_irq); - break; -#endif /* CONFIG_TICKSOURCE_GPTMR0 */ default: set_irq_handler(irq, handle_simple_irq); break; -#endif /* !CONFIG_IPIPE */ +#endif /* !CONFIG_IPIPE */ } } diff --git a/arch/blackfin/mach-common/lock.S b/arch/blackfin/mach-common/lock.S deleted file mode 100644 index 6c5f5f0ea7f..00000000000 --- a/arch/blackfin/mach-common/lock.S +++ /dev/null @@ -1,223 +0,0 @@ -/* - * File: arch/blackfin/mach-common/lock.S - * Based on: - * Author: LG Soft India - * - * Created: ? - * Description: kernel locks - * - * Modified: - * Copyright 2004-2006 Analog Devices Inc. - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * 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, see the file COPYING, or write - * to the Free Software Foundation, Inc., - * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA - */ - -#include <linux/linkage.h> -#include <asm/blackfin.h> - -.text - -/* When you come here, it is assumed that - * R0 - Which way to be locked - */ - -ENTRY(_cache_grab_lock) - - [--SP]=( R7:0,P5:0 ); - - P1.H = HI(IMEM_CONTROL); - P1.L = LO(IMEM_CONTROL); - P5.H = HI(ICPLB_ADDR0); - P5.L = LO(ICPLB_ADDR0); - P4.H = HI(ICPLB_DATA0); - P4.L = LO(ICPLB_DATA0); - R7 = R0; - - /* If the code of interest already resides in the cache - * invalidate the entire cache itself. - * invalidate_entire_icache; - */ - - SP += -12; - [--SP] = RETS; - CALL _invalidate_entire_icache; - RETS = [SP++]; - SP += 12; - - /* Disable the Interrupts*/ - - CLI R3; - -.LLOCK_WAY: - - /* Way0 - 0xFFA133E0 - * Way1 - 0xFFA137E0 - * Way2 - 0xFFA13BE0 Total Way Size = 4K - * Way3 - 0xFFA13FE0 - */ - - /* Procedure Ex. -Set the locks for other ways by setting ILOC[3:1] - * Only Way0 of the instruction cache can now be - * replaced by a new code - */ - - R5 = R7; - CC = BITTST(R7,0); - IF CC JUMP .LCLEAR1; - R7 = 0; - BITSET(R7,0); - JUMP .LDONE1; - -.LCLEAR1: - R7 = 0; - BITCLR(R7,0); -.LDONE1: R4 = R7 << 3; - R7 = [P1]; - R7 = R7 | R4; - SSYNC; /* SSYNC required writing to IMEM_CONTROL. */ - .align 8; - [P1] = R7; - SSYNC; - - R7 = R5; - CC = BITTST(R7,1); - IF CC JUMP .LCLEAR2; - R7 = 0; - BITSET(R7,1); - JUMP .LDONE2; - -.LCLEAR2: - R7 = 0; - BITCLR(R7,1); -.LDONE2: R4 = R7 << 3; - R7 = [P1]; - R7 = R7 | R4; - SSYNC; /* SSYNC required writing to IMEM_CONTROL. */ - .align 8; - [P1] = R7; - SSYNC; - - R7 = R5; - CC = BITTST(R7,2); - IF CC JUMP .LCLEAR3; - R7 = 0; - BITSET(R7,2); - JUMP .LDONE3; -.LCLEAR3: - R7 = 0; - BITCLR(R7,2); -.LDONE3: R4 = R7 << 3; - R7 = [P1]; - R7 = R7 | R4; - SSYNC; /* SSYNC required writing to IMEM_CONTROL. */ - .align 8; - [P1] = R7; - SSYNC; - - - R7 = R5; - CC = BITTST(R7,3); - IF CC JUMP .LCLEAR4; - R7 = 0; - BITSET(R7,3); - JUMP .LDONE4; -.LCLEAR4: - R7 = 0; - BITCLR(R7,3); -.LDONE4: R4 = R7 << 3; - R7 = [P1]; - R7 = R7 | R4; - SSYNC; /* SSYNC required writing to IMEM_CONTROL. */ - .align 8; - [P1] = R7; - SSYNC; - - STI R3; - - ( R7:0,P5:0 ) = [SP++]; - - RTS; -ENDPROC(_cache_grab_lock) - -/* After the execution of critical code, the code is now locked into - * the cache way. Now we need to set ILOC. - * - * R0 - Which way to be locked - */ - -ENTRY(_bfin_cache_lock) - - [--SP]=( R7:0,P5:0 ); - - P1.H = HI(IMEM_CONTROL); - P1.L = LO(IMEM_CONTROL); - - /* Disable the Interrupts*/ - CLI R3; - - R7 = [P1]; - R2 = ~(0x78) (X); /* mask out ILOC */ - R7 = R7 & R2; - R0 = R0 << 3; - R7 = R0 | R7; - SSYNC; /* SSYNC required writing to IMEM_CONTROL. */ - .align 8; - [P1] = R7; - SSYNC; - /* Renable the Interrupts */ - STI R3; - - ( R7:0,P5:0 ) = [SP++]; - RTS; -ENDPROC(_bfin_cache_lock) - -/* Invalidate the Entire Instruction cache by - * disabling IMC bit - */ -ENTRY(_invalidate_entire_icache) - [--SP] = ( R7:5); - - P0.L = LO(IMEM_CONTROL); - P0.H = HI(IMEM_CONTROL); - R7 = [P0]; - - /* Clear the IMC bit , All valid bits in the instruction - * cache are set to the invalid state - */ - BITCLR(R7,IMC_P); - CLI R6; - SSYNC; /* SSYNC required before invalidating cache. */ - .align 8; - [P0] = R7; - SSYNC; - STI R6; - - /* Configures the instruction cache agian */ - R6 = (IMC | ENICPLB); - R7 = R7 | R6; - - CLI R6; - SSYNC; /* SSYNC required before writing to IMEM_CONTROL. */ - .align 8; - [P0] = R7; - SSYNC; - STI R6; - - ( R7:5) = [SP++]; - RTS; -ENDPROC(_invalidate_entire_icache) diff --git a/arch/blackfin/mach-common/pm.c b/arch/blackfin/mach-common/pm.c index 9e7e27b7fc8..0e3d4ff9d8b 100644 --- a/arch/blackfin/mach-common/pm.c +++ b/arch/blackfin/mach-common/pm.c @@ -38,6 +38,7 @@ #include <linux/io.h> #include <linux/irq.h> +#include <asm/cplb.h> #include <asm/gpio.h> #include <asm/dma.h> #include <asm/dpmc.h> @@ -170,58 +171,6 @@ static void flushinv_all_dcache(void) } #endif -static inline void dcache_disable(void) -{ -#ifdef CONFIG_BFIN_DCACHE - unsigned long ctrl; - -#if defined(CONFIG_BFIN_EXTMEM_WRITEBACK) || defined(CONFIG_BFIN_L2_WRITEBACK) - flushinv_all_dcache(); -#endif - SSYNC(); - ctrl = bfin_read_DMEM_CONTROL(); - ctrl &= ~ENDCPLB; - bfin_write_DMEM_CONTROL(ctrl); - SSYNC(); -#endif -} - -static inline void dcache_enable(void) -{ -#ifdef CONFIG_BFIN_DCACHE - unsigned long ctrl; - SSYNC(); - ctrl = bfin_read_DMEM_CONTROL(); - ctrl |= ENDCPLB; - bfin_write_DMEM_CONTROL(ctrl); - SSYNC(); -#endif -} - -static inline void icache_disable(void) -{ -#ifdef CONFIG_BFIN_ICACHE - unsigned long ctrl; - SSYNC(); - ctrl = bfin_read_IMEM_CONTROL(); - ctrl &= ~ENICPLB; - bfin_write_IMEM_CONTROL(ctrl); - SSYNC(); -#endif -} - -static inline void icache_enable(void) -{ -#ifdef CONFIG_BFIN_ICACHE - unsigned long ctrl; - SSYNC(); - ctrl = bfin_read_IMEM_CONTROL(); - ctrl |= ENICPLB; - bfin_write_IMEM_CONTROL(ctrl); - SSYNC(); -#endif -} - int bfin_pm_suspend_mem_enter(void) { unsigned long flags; @@ -258,16 +207,19 @@ int bfin_pm_suspend_mem_enter(void) bfin_gpio_pm_hibernate_suspend(); - dcache_disable(); - icache_disable(); +#if defined(CONFIG_BFIN_EXTMEM_WRITEBACK) || defined(CONFIG_BFIN_L2_WRITEBACK) + flushinv_all_dcache(); +#endif + _disable_dcplb(); + _disable_icplb(); bf53x_suspend_l1_mem(memptr); do_hibernate(wakeup | vr_wakeup); /* Goodbye */ bf53x_resume_l1_mem(memptr); - icache_enable(); - dcache_enable(); + _enable_icplb(); + _enable_dcplb(); bfin_gpio_pm_hibernate_restore(); blackfin_dma_resume(); diff --git a/arch/blackfin/mm/init.c b/arch/blackfin/mm/init.c index 68bd0bd680c..b88ce7fda54 100644 --- a/arch/blackfin/mm/init.c +++ b/arch/blackfin/mm/init.c @@ -33,6 +33,7 @@ #include <asm/bfin-global.h> #include <asm/pda.h> #include <asm/cplbinit.h> +#include <asm/early_printk.h> #include "blackfin_sram.h" /* @@ -113,6 +114,8 @@ asmlinkage void __init init_pda(void) { unsigned int cpu = raw_smp_processor_id(); + early_shadow_stamp(); + /* Initialize the PDA fields holding references to other parts of the memory. The content of such memory is still undefined at the time of the call, we are only setting up diff --git a/arch/blackfin/mm/isram-driver.c b/arch/blackfin/mm/isram-driver.c index c080e70f98b..beb1a608824 100644 --- a/arch/blackfin/mm/isram-driver.c +++ b/arch/blackfin/mm/isram-driver.c @@ -16,6 +16,8 @@ * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA */ +#define pr_fmt(fmt) "isram: " fmt + #include <linux/module.h> #include <linux/kernel.h> #include <linux/types.h> @@ -23,6 +25,7 @@ #include <linux/sched.h> #include <asm/blackfin.h> +#include <asm/dma.h> /* * IMPORTANT WARNING ABOUT THESE FUNCTIONS @@ -50,10 +53,12 @@ static DEFINE_SPINLOCK(dtest_lock); #define IADDR2DTEST(x) \ ({ unsigned long __addr = (unsigned long)(x); \ (__addr & 0x47F8) | /* address bits 14 & 10:3 */ \ + (__addr & 0x8000) << 23 | /* Bank A/B */ \ (__addr & 0x0800) << 15 | /* address bit 11 */ \ - (__addr & 0x3000) << 4 | /* address bits 13:12 */ \ - (__addr & 0x8000) << 8 | /* address bit 15 */ \ - (0x1000004); /* isram access */ \ + (__addr & 0x3000) << 4 | /* address bits 13:12 */ \ + (__addr & 0x8000) << 8 | /* address bit 15 */ \ + (0x1000000) | /* instruction access = 1 */ \ + (0x4); /* data array = 1 */ \ }) /* Takes a pointer, and returns the offset (in bits) which things should be shifted */ @@ -70,7 +75,7 @@ static void isram_write(const void *addr, uint64_t data) if (addr >= (void *)(L1_CODE_START + L1_CODE_LENGTH)) return; - cmd = IADDR2DTEST(addr) | 1; /* write */ + cmd = IADDR2DTEST(addr) | 2; /* write */ /* * Writes to DTEST_DATA[0:1] need to be atomic with write to DTEST_COMMAND @@ -127,8 +132,7 @@ static bool isram_check_addr(const void *addr, size_t n) (addr < (void *)(L1_CODE_START + L1_CODE_LENGTH))) { if ((addr + n) > (void *)(L1_CODE_START + L1_CODE_LENGTH)) { show_stack(NULL, NULL); - printk(KERN_ERR "isram_memcpy: copy involving %p length " - "(%zu) too long\n", addr, n); + pr_err("copy involving %p length (%zu) too long\n", addr, n); } return true; } @@ -199,3 +203,209 @@ void *isram_memcpy(void *dest, const void *src, size_t n) } EXPORT_SYMBOL(isram_memcpy); +#ifdef CONFIG_BFIN_ISRAM_SELF_TEST + +#define TEST_LEN 0x100 + +static __init void hex_dump(unsigned char *buf, int len) +{ + while (len--) + pr_cont("%02x", *buf++); +} + +static __init int isram_read_test(char *sdram, void *l1inst) +{ + int i, ret = 0; + uint64_t data1, data2; + + pr_info("INFO: running isram_read tests\n"); + + /* setup some different data to play with */ + for (i = 0; i < TEST_LEN; ++i) + sdram[i] = i; + dma_memcpy(l1inst, sdram, TEST_LEN); + + /* make sure we can read the L1 inst */ + for (i = 0; i < TEST_LEN; i += sizeof(uint64_t)) { + data1 = isram_read(l1inst + i); + memcpy(&data2, sdram + i, sizeof(data2)); + if (memcmp(&data1, &data2, sizeof(uint64_t))) { + pr_err("FAIL: isram_read(%p) returned %#llx but wanted %#llx\n", + l1inst + i, data1, data2); + ++ret; + } + } + + return ret; +} + +static __init int isram_write_test(char *sdram, void *l1inst) +{ + int i, ret = 0; + uint64_t data1, data2; + + pr_info("INFO: running isram_write tests\n"); + + /* setup some different data to play with */ + memset(sdram, 0, TEST_LEN * 2); + dma_memcpy(l1inst, sdram, TEST_LEN); + for (i = 0; i < TEST_LEN; ++i) + sdram[i] = i; + + /* make sure we can write the L1 inst */ + for (i = 0; i < TEST_LEN; i += sizeof(uint64_t)) { + memcpy(&data1, sdram + i, sizeof(data1)); + isram_write(l1inst + i, data1); + data2 = isram_read(l1inst + i); + if (memcmp(&data1, &data2, sizeof(uint64_t))) { + pr_err("FAIL: isram_write(%p, %#llx) != %#llx\n", + l1inst + i, data1, data2); + ++ret; + } + } + + dma_memcpy(sdram + TEST_LEN, l1inst, TEST_LEN); + if (memcmp(sdram, sdram + TEST_LEN, TEST_LEN)) { + pr_err("FAIL: isram_write() did not work properly\n"); + ++ret; + } + + return ret; +} + +static __init int +_isram_memcpy_test(char pattern, void *sdram, void *l1inst, const char *smemcpy, + void *(*fmemcpy)(void *, const void *, size_t)) +{ + memset(sdram, pattern, TEST_LEN); + fmemcpy(l1inst, sdram, TEST_LEN); + fmemcpy(sdram + TEST_LEN, l1inst, TEST_LEN); + if (memcmp(sdram, sdram + TEST_LEN, TEST_LEN)) { + pr_err("FAIL: %s(%p <=> %p, %#x) failed (data is %#x)\n", + smemcpy, l1inst, sdram, TEST_LEN, pattern); + return 1; + } + return 0; +} +#define _isram_memcpy_test(a, b, c, d) _isram_memcpy_test(a, b, c, #d, d) + +static __init int isram_memcpy_test(char *sdram, void *l1inst) +{ + int i, j, thisret, ret = 0; + + /* check broad isram_memcpy() */ + pr_info("INFO: running broad isram_memcpy tests\n"); + for (i = 0xf; i >= 0; --i) + ret += _isram_memcpy_test(i, sdram, l1inst, isram_memcpy); + + /* check read of small, unaligned, and hardware 64bit limits */ + pr_info("INFO: running isram_memcpy (read) tests\n"); + + for (i = 0; i < TEST_LEN; ++i) + sdram[i] = i; + dma_memcpy(l1inst, sdram, TEST_LEN); + + thisret = 0; + for (i = 0; i < TEST_LEN - 32; ++i) { + unsigned char cmp[32]; + for (j = 1; j <= 32; ++j) { + memset(cmp, 0, sizeof(cmp)); + isram_memcpy(cmp, l1inst + i, j); + if (memcmp(cmp, sdram + i, j)) { + pr_err("FAIL: %p:", l1inst + 1); + hex_dump(cmp, j); + pr_cont(" SDRAM:"); + hex_dump(sdram + i, j); + pr_cont("\n"); + if (++thisret > 20) { + pr_err("FAIL: skipping remaining series\n"); + i = TEST_LEN; + break; + } + } + } + } + ret += thisret; + + /* check write of small, unaligned, and hardware 64bit limits */ + pr_info("INFO: running isram_memcpy (write) tests\n"); + + memset(sdram + TEST_LEN, 0, TEST_LEN); + dma_memcpy(l1inst, sdram + TEST_LEN, TEST_LEN); + + thisret = 0; + for (i = 0; i < TEST_LEN - 32; ++i) { + unsigned char cmp[32]; + for (j = 1; j <= 32; ++j) { + isram_memcpy(l1inst + i, sdram + i, j); + dma_memcpy(cmp, l1inst + i, j); + if (memcmp(cmp, sdram + i, j)) { + pr_err("FAIL: %p:", l1inst + i); + hex_dump(cmp, j); + pr_cont(" SDRAM:"); + hex_dump(sdram + i, j); + pr_cont("\n"); + if (++thisret > 20) { + pr_err("FAIL: skipping remaining series\n"); + i = TEST_LEN; + break; + } + } + } + } + ret += thisret; + + return ret; +} + +static __init int isram_test_init(void) +{ + int ret; + char *sdram; + void *l1inst; + + sdram = kmalloc(TEST_LEN * 2, GFP_KERNEL); + if (!sdram) { + pr_warning("SKIP: could not allocate sdram\n"); + return 0; + } + + l1inst = l1_inst_sram_alloc(TEST_LEN); + if (!l1inst) { + kfree(sdram); + pr_warning("SKIP: could not allocate L1 inst\n"); + return 0; + } + + /* sanity check initial L1 inst state */ + ret = 1; + pr_info("INFO: running initial dma_memcpy checks\n"); + if (_isram_memcpy_test(0xa, sdram, l1inst, dma_memcpy)) + goto abort; + if (_isram_memcpy_test(0x5, sdram, l1inst, dma_memcpy)) + goto abort; + + ret = 0; + ret += isram_read_test(sdram, l1inst); + ret += isram_write_test(sdram, l1inst); + ret += isram_memcpy_test(sdram, l1inst); + + abort: + sram_free(l1inst); + kfree(sdram); + + if (ret) + return -EIO; + + pr_info("PASS: all tests worked !\n"); + return 0; +} +late_initcall(isram_test_init); + +static __exit void isram_test_exit(void) +{ + /* stub to allow unloading */ +} +module_exit(isram_test_exit); + +#endif diff --git a/arch/blackfin/mm/sram-alloc.c b/arch/blackfin/mm/sram-alloc.c index 0bc3c4ef0aa..eb63ab353e5 100644 --- a/arch/blackfin/mm/sram-alloc.c +++ b/arch/blackfin/mm/sram-alloc.c @@ -42,11 +42,6 @@ #include <asm/mem_map.h> #include "blackfin_sram.h" -static DEFINE_PER_CPU(spinlock_t, l1sram_lock) ____cacheline_aligned_in_smp; -static DEFINE_PER_CPU(spinlock_t, l1_data_sram_lock) ____cacheline_aligned_in_smp; -static DEFINE_PER_CPU(spinlock_t, l1_inst_sram_lock) ____cacheline_aligned_in_smp; -static spinlock_t l2_sram_lock ____cacheline_aligned_in_smp; - /* the data structure for L1 scratchpad and DATA SRAM */ struct sram_piece { void *paddr; @@ -55,6 +50,7 @@ struct sram_piece { struct sram_piece *next; }; +static DEFINE_PER_CPU_SHARED_ALIGNED(spinlock_t, l1sram_lock); static DEFINE_PER_CPU(struct sram_piece, free_l1_ssram_head); static DEFINE_PER_CPU(struct sram_piece, used_l1_ssram_head); @@ -68,12 +64,18 @@ static DEFINE_PER_CPU(struct sram_piece, free_l1_data_B_sram_head); static DEFINE_PER_CPU(struct sram_piece, used_l1_data_B_sram_head); #endif +#if L1_DATA_A_LENGTH || L1_DATA_B_LENGTH +static DEFINE_PER_CPU_SHARED_ALIGNED(spinlock_t, l1_data_sram_lock); +#endif + #if L1_CODE_LENGTH != 0 +static DEFINE_PER_CPU_SHARED_ALIGNED(spinlock_t, l1_inst_sram_lock); static DEFINE_PER_CPU(struct sram_piece, free_l1_inst_sram_head); static DEFINE_PER_CPU(struct sram_piece, used_l1_inst_sram_head); #endif #if L2_LENGTH != 0 +static spinlock_t l2_sram_lock ____cacheline_aligned_in_smp; static struct sram_piece free_l2_sram_head, used_l2_sram_head; #endif @@ -225,10 +227,10 @@ static void __init l2_sram_init(void) printk(KERN_INFO "Blackfin L2 SRAM: %d KB (%d KB free)\n", L2_LENGTH >> 10, free_l2_sram_head.next->size >> 10); -#endif /* mutex initialize */ spin_lock_init(&l2_sram_lock); +#endif } static int __init bfin_sram_init(void) @@ -416,18 +418,17 @@ EXPORT_SYMBOL(sram_free); void *l1_data_A_sram_alloc(size_t size) { +#if L1_DATA_A_LENGTH != 0 unsigned long flags; - void *addr = NULL; + void *addr; unsigned int cpu; cpu = get_cpu(); /* add mutex operation */ spin_lock_irqsave(&per_cpu(l1_data_sram_lock, cpu), flags); -#if L1_DATA_A_LENGTH != 0 addr = _sram_alloc(size, &per_cpu(free_l1_data_A_sram_head, cpu), &per_cpu(used_l1_data_A_sram_head, cpu)); -#endif /* add mutex operation */ spin_unlock_irqrestore(&per_cpu(l1_data_sram_lock, cpu), flags); @@ -437,11 +438,15 @@ void *l1_data_A_sram_alloc(size_t size) (long unsigned int)addr, size); return addr; +#else + return NULL; +#endif } EXPORT_SYMBOL(l1_data_A_sram_alloc); int l1_data_A_sram_free(const void *addr) { +#if L1_DATA_A_LENGTH != 0 unsigned long flags; int ret; unsigned int cpu; @@ -450,18 +455,17 @@ int l1_data_A_sram_free(const void *addr) /* add mutex operation */ spin_lock_irqsave(&per_cpu(l1_data_sram_lock, cpu), flags); -#if L1_DATA_A_LENGTH != 0 ret = _sram_free(addr, &per_cpu(free_l1_data_A_sram_head, cpu), &per_cpu(used_l1_data_A_sram_head, cpu)); -#else - ret = -1; -#endif /* add mutex operation */ spin_unlock_irqrestore(&per_cpu(l1_data_sram_lock, cpu), flags); put_cpu(); return ret; +#else + return -1; +#endif } EXPORT_SYMBOL(l1_data_A_sram_free); |