diff options
57 files changed, 2985 insertions, 1126 deletions
diff --git a/arch/m68k/Kconfig.bus b/arch/m68k/Kconfig.bus index 3adb499..ffc0601 100644 --- a/arch/m68k/Kconfig.bus +++ b/arch/m68k/Kconfig.bus @@ -48,6 +48,13 @@ config ISA config GENERIC_ISA_DMA def_bool ISA +config PCI + bool "PCI support" + depends on M54xx + help + Enable the PCI bus. Support for the PCI bus hardware built into the + ColdFire 547x and 548x processors. + source "drivers/pci/Kconfig" source "drivers/zorro/Kconfig" diff --git a/arch/m68k/Kconfig.cpu b/arch/m68k/Kconfig.cpu index 2b53254..43a9f8f 100644 --- a/arch/m68k/Kconfig.cpu +++ b/arch/m68k/Kconfig.cpu @@ -23,7 +23,7 @@ config M68KCLASSIC config COLDFIRE bool "Coldfire CPU family support" select GENERIC_GPIO - select ARCH_REQUIRE_GPIOLIB + select ARCH_WANT_OPTIONAL_GPIOLIB select ARCH_HAVE_CUSTOM_GPIO_H select CPU_HAS_NO_BITFIELDS select CPU_HAS_NO_MULDIV64 @@ -167,6 +167,14 @@ config M5249 help Motorola ColdFire 5249 processor support. +config M525x + bool "MCF525x" + depends on !MMU + select COLDFIRE_SW_A7 + select HAVE_MBAR + help + Freescale (Motorola) Coldfire 5251/5253 processor support. + config M527x bool @@ -253,6 +261,14 @@ config M548x help Freescale ColdFire 5480/5481/5482/5483/5484/5485 processor support. +config M5441x + bool "MCF5441x" + depends on !MMU + select GENERIC_CLOCKEVENTS + select HAVE_CACHE_CB + help + Freescale Coldfire 54410/54415/54416/54417/54418 processor support. + endif # COLDFIRE diff --git a/arch/m68k/Makefile b/arch/m68k/Makefile index b7f2e2d..7636751 100644 --- a/arch/m68k/Makefile +++ b/arch/m68k/Makefile @@ -41,6 +41,7 @@ cpuflags-$(CONFIG_M68030) := cpuflags-$(CONFIG_M68020) := cpuflags-$(CONFIG_M68360) := -m68332 cpuflags-$(CONFIG_M68000) := -m68000 +cpuflags-$(CONFIG_M5441x) := $(call cc-option,-mcpu=54455,-mcfv4e) cpuflags-$(CONFIG_M54xx) := $(call cc-option,-mcpu=5475,-m5200) cpuflags-$(CONFIG_M5407) := $(call cc-option,-mcpu=5407,-m5200) cpuflags-$(CONFIG_M532x) := $(call cc-option,-mcpu=532x,-m5307) @@ -50,6 +51,7 @@ cpuflags-$(CONFIG_M5275) := $(call cc-option,-mcpu=5275,-m5307) cpuflags-$(CONFIG_M5272) := $(call cc-option,-mcpu=5272,-m5307) cpuflags-$(CONFIG_M5271) := $(call cc-option,-mcpu=5271,-m5307) cpuflags-$(CONFIG_M523x) := $(call cc-option,-mcpu=523x,-m5307) +cpuflags-$(CONFIG_M525x) := $(call cc-option,-mcpu=5253,-m5200) cpuflags-$(CONFIG_M5249) := $(call cc-option,-mcpu=5249,-m5200) cpuflags-$(CONFIG_M520x) := $(call cc-option,-mcpu=5208,-m5200) cpuflags-$(CONFIG_M5206e) := $(call cc-option,-mcpu=5206e,-m5200) diff --git a/arch/m68k/include/asm/cacheflush_mm.h b/arch/m68k/include/asm/cacheflush_mm.h index 8104bd8..fa2c3d6 100644 --- a/arch/m68k/include/asm/cacheflush_mm.h +++ b/arch/m68k/include/asm/cacheflush_mm.h @@ -16,7 +16,48 @@ #define DCACHE_MAX_ADDR 0 #define DCACHE_SETMASK 0 #endif +#ifndef CACHE_MODE +#define CACHE_MODE 0 +#define CACR_ICINVA 0 +#define CACR_DCINVA 0 +#define CACR_BCINVA 0 +#endif + +/* + * ColdFire architecture has no way to clear individual cache lines, so we + * are stuck invalidating all the cache entries when we want a clear operation. + */ +static inline void clear_cf_icache(unsigned long start, unsigned long end) +{ + __asm__ __volatile__ ( + "movec %0,%%cacr\n\t" + "nop" + : + : "r" (CACHE_MODE | CACR_ICINVA | CACR_BCINVA)); +} + +static inline void clear_cf_dcache(unsigned long start, unsigned long end) +{ + __asm__ __volatile__ ( + "movec %0,%%cacr\n\t" + "nop" + : + : "r" (CACHE_MODE | CACR_DCINVA)); +} +static inline void clear_cf_bcache(unsigned long start, unsigned long end) +{ + __asm__ __volatile__ ( + "movec %0,%%cacr\n\t" + "nop" + : + : "r" (CACHE_MODE | CACR_ICINVA | CACR_BCINVA | CACR_DCINVA)); +} + +/* + * Use the ColdFire cpushl instruction to push (and invalidate) cache lines. + * The start and end addresses are cache line numbers not memory addresses. + */ static inline void flush_cf_icache(unsigned long start, unsigned long end) { unsigned long set; diff --git a/arch/m68k/include/asm/dma.h b/arch/m68k/include/asm/dma.h index 6fbdfe8..0ff3fc6 100644 --- a/arch/m68k/include/asm/dma.h +++ b/arch/m68k/include/asm/dma.h @@ -33,7 +33,9 @@ * Set number of channels of DMA on ColdFire for different implementations. */ #if defined(CONFIG_M5249) || defined(CONFIG_M5307) || defined(CONFIG_M5407) || \ - defined(CONFIG_M523x) || defined(CONFIG_M527x) || defined(CONFIG_M528x) + defined(CONFIG_M523x) || defined(CONFIG_M527x) || \ + defined(CONFIG_M528x) || defined(CONFIG_M525x) + #define MAX_M68K_DMA_CHANNELS 4 #elif defined(CONFIG_M5272) #define MAX_M68K_DMA_CHANNELS 1 @@ -486,6 +488,10 @@ static __inline__ int get_dma_residue(unsigned int dmanr) extern int request_dma(unsigned int dmanr, const char * device_id); /* reserve a DMA channel */ extern void free_dma(unsigned int dmanr); /* release it again */ +#ifdef CONFIG_PCI +extern int isa_dma_bridge_buggy; +#else #define isa_dma_bridge_buggy (0) +#endif #endif /* _M68K_DMA_H */ diff --git a/arch/m68k/include/asm/gpio.h b/arch/m68k/include/asm/gpio.h index 00d0071..4395ffc 100644 --- a/arch/m68k/include/asm/gpio.h +++ b/arch/m68k/include/asm/gpio.h @@ -17,170 +17,9 @@ #define coldfire_gpio_h #include <linux/io.h> -#include <asm-generic/gpio.h> #include <asm/coldfire.h> #include <asm/mcfsim.h> - -/* - * The Freescale Coldfire family is quite varied in how they implement GPIO. - * Some parts have 8 bit ports, some have 16bit and some have 32bit; some have - * only one port, others have multiple ports; some have a single data latch - * for both input and output, others have a separate pin data register to read - * input; some require a read-modify-write access to change an output, others - * have set and clear registers for some of the outputs; Some have all the - * GPIOs in a single control area, others have some GPIOs implemented in - * different modules. - * - * This implementation attempts accommodate the differences while presenting - * a generic interface that will optimize to as few instructions as possible. - */ -#if defined(CONFIG_M5206) || defined(CONFIG_M5206e) || \ - defined(CONFIG_M520x) || defined(CONFIG_M523x) || \ - defined(CONFIG_M527x) || defined(CONFIG_M528x) || \ - defined(CONFIG_M532x) || defined(CONFIG_M54xx) - -/* These parts have GPIO organized by 8 bit ports */ - -#define MCFGPIO_PORTTYPE u8 -#define MCFGPIO_PORTSIZE 8 -#define mcfgpio_read(port) __raw_readb(port) -#define mcfgpio_write(data, port) __raw_writeb(data, port) - -#elif defined(CONFIG_M5307) || defined(CONFIG_M5407) || defined(CONFIG_M5272) - -/* These parts have GPIO organized by 16 bit ports */ - -#define MCFGPIO_PORTTYPE u16 -#define MCFGPIO_PORTSIZE 16 -#define mcfgpio_read(port) __raw_readw(port) -#define mcfgpio_write(data, port) __raw_writew(data, port) - -#elif defined(CONFIG_M5249) - -/* These parts have GPIO organized by 32 bit ports */ - -#define MCFGPIO_PORTTYPE u32 -#define MCFGPIO_PORTSIZE 32 -#define mcfgpio_read(port) __raw_readl(port) -#define mcfgpio_write(data, port) __raw_writel(data, port) - -#endif - -#define mcfgpio_bit(gpio) (1 << ((gpio) % MCFGPIO_PORTSIZE)) -#define mcfgpio_port(gpio) ((gpio) / MCFGPIO_PORTSIZE) - -#if defined(CONFIG_M520x) || defined(CONFIG_M523x) || \ - defined(CONFIG_M527x) || defined(CONFIG_M528x) || defined(CONFIG_M532x) -/* - * These parts have an 'Edge' Port module (external interrupt/GPIO) which uses - * read-modify-write to change an output and a GPIO module which has separate - * set/clr registers to directly change outputs with a single write access. - */ -#if defined(CONFIG_M528x) -/* - * The 528x also has GPIOs in other modules (GPT, QADC) which use - * read-modify-write as well as those controlled by the EPORT and GPIO modules. - */ -#define MCFGPIO_SCR_START 40 -#else -#define MCFGPIO_SCR_START 8 -#endif - -#define MCFGPIO_SETR_PORT(gpio) (MCFGPIO_SETR + \ - mcfgpio_port(gpio - MCFGPIO_SCR_START)) - -#define MCFGPIO_CLRR_PORT(gpio) (MCFGPIO_CLRR + \ - mcfgpio_port(gpio - MCFGPIO_SCR_START)) -#else - -#define MCFGPIO_SCR_START MCFGPIO_PIN_MAX -/* with MCFGPIO_SCR == MCFGPIO_PIN_MAX, these will be optimized away */ -#define MCFGPIO_SETR_PORT(gpio) 0 -#define MCFGPIO_CLRR_PORT(gpio) 0 - -#endif -/* - * Coldfire specific helper functions - */ - -/* return the port pin data register for a gpio */ -static inline u32 __mcf_gpio_ppdr(unsigned gpio) -{ -#if defined(CONFIG_M5206) || defined(CONFIG_M5206e) || \ - defined(CONFIG_M5307) || defined(CONFIG_M5407) - return MCFSIM_PADAT; -#elif defined(CONFIG_M5272) - if (gpio < 16) - return MCFSIM_PADAT; - else if (gpio < 32) - return MCFSIM_PBDAT; - else - return MCFSIM_PCDAT; -#elif defined(CONFIG_M5249) - if (gpio < 32) - return MCFSIM2_GPIOREAD; - else - return MCFSIM2_GPIO1READ; -#elif defined(CONFIG_M520x) || defined(CONFIG_M523x) || \ - defined(CONFIG_M527x) || defined(CONFIG_M528x) || defined(CONFIG_M532x) - if (gpio < 8) - return MCFEPORT_EPPDR; -#if defined(CONFIG_M528x) - else if (gpio < 16) - return MCFGPTA_GPTPORT; - else if (gpio < 24) - return MCFGPTB_GPTPORT; - else if (gpio < 32) - return MCFQADC_PORTQA; - else if (gpio < 40) - return MCFQADC_PORTQB; -#endif - else - return MCFGPIO_PPDR + mcfgpio_port(gpio - MCFGPIO_SCR_START); -#else - return 0; -#endif -} - -/* return the port output data register for a gpio */ -static inline u32 __mcf_gpio_podr(unsigned gpio) -{ -#if defined(CONFIG_M5206) || defined(CONFIG_M5206e) || \ - defined(CONFIG_M5307) || defined(CONFIG_M5407) - return MCFSIM_PADAT; -#elif defined(CONFIG_M5272) - if (gpio < 16) - return MCFSIM_PADAT; - else if (gpio < 32) - return MCFSIM_PBDAT; - else - return MCFSIM_PCDAT; -#elif defined(CONFIG_M5249) - if (gpio < 32) - return MCFSIM2_GPIOWRITE; - else - return MCFSIM2_GPIO1WRITE; -#elif defined(CONFIG_M520x) || defined(CONFIG_M523x) || \ - defined(CONFIG_M527x) || defined(CONFIG_M528x) || defined(CONFIG_M532x) - if (gpio < 8) - return MCFEPORT_EPDR; -#if defined(CONFIG_M528x) - else if (gpio < 16) - return MCFGPTA_GPTPORT; - else if (gpio < 24) - return MCFGPTB_GPTPORT; - else if (gpio < 32) - return MCFQADC_PORTQA; - else if (gpio < 40) - return MCFQADC_PORTQB; -#endif - else - return MCFGPIO_PODR + mcfgpio_port(gpio - MCFGPIO_SCR_START); -#else - return 0; -#endif -} - +#include <asm/mcfgpio.h> /* * The Generic GPIO functions * @@ -191,7 +30,7 @@ static inline u32 __mcf_gpio_podr(unsigned gpio) static inline int gpio_get_value(unsigned gpio) { if (__builtin_constant_p(gpio) && gpio < MCFGPIO_PIN_MAX) - return mcfgpio_read(__mcf_gpio_ppdr(gpio)) & mcfgpio_bit(gpio); + return mcfgpio_read(__mcfgpio_ppdr(gpio)) & mcfgpio_bit(gpio); else return __gpio_get_value(gpio); } @@ -204,12 +43,12 @@ static inline void gpio_set_value(unsigned gpio, int value) MCFGPIO_PORTTYPE data; local_irq_save(flags); - data = mcfgpio_read(__mcf_gpio_podr(gpio)); + data = mcfgpio_read(__mcfgpio_podr(gpio)); if (value) data |= mcfgpio_bit(gpio); else data &= ~mcfgpio_bit(gpio); - mcfgpio_write(data, __mcf_gpio_podr(gpio)); + mcfgpio_write(data, __mcfgpio_podr(gpio)); local_irq_restore(flags); } else { if (value) @@ -225,8 +64,14 @@ static inline void gpio_set_value(unsigned gpio, int value) static inline int gpio_to_irq(unsigned gpio) { - return (gpio < MCFGPIO_IRQ_MAX) ? gpio + MCFGPIO_IRQ_VECBASE - : __gpio_to_irq(gpio); +#if defined(MCFGPIO_IRQ_MIN) + if ((gpio >= MCFGPIO_IRQ_MIN) && (gpio < MCFGPIO_IRQ_MAX)) +#else + if (gpio < MCFGPIO_IRQ_MAX) +#endif + return gpio + MCFGPIO_IRQ_VECBASE; + else + return __gpio_to_irq(gpio); } static inline int irq_to_gpio(unsigned irq) diff --git a/arch/m68k/include/asm/io_mm.h b/arch/m68k/include/asm/io_mm.h index fa4324b..a6686d2 100644 --- a/arch/m68k/include/asm/io_mm.h +++ b/arch/m68k/include/asm/io_mm.h @@ -65,7 +65,53 @@ -#ifdef CONFIG_ISA +#if defined(CONFIG_PCI) && defined(CONFIG_COLDFIRE) + +#define HAVE_ARCH_PIO_SIZE +#define PIO_OFFSET 0 +#define PIO_MASK 0xffff +#define PIO_RESERVED 0x10000 + +u8 mcf_pci_inb(u32 addr); +u16 mcf_pci_inw(u32 addr); +u32 mcf_pci_inl(u32 addr); +void mcf_pci_insb(u32 addr, u8 *buf, u32 len); +void mcf_pci_insw(u32 addr, u16 *buf, u32 len); +void mcf_pci_insl(u32 addr, u32 *buf, u32 len); + +void mcf_pci_outb(u8 v, u32 addr); +void mcf_pci_outw(u16 v, u32 addr); +void mcf_pci_outl(u32 v, u32 addr); +void mcf_pci_outsb(u32 addr, const u8 *buf, u32 len); +void mcf_pci_outsw(u32 addr, const u16 *buf, u32 len); +void mcf_pci_outsl(u32 addr, const u32 *buf, u32 len); + +#define inb mcf_pci_inb +#define inb_p mcf_pci_inb +#define inw mcf_pci_inw +#define inw_p mcf_pci_inw +#define inl mcf_pci_inl +#define inl_p mcf_pci_inl +#define insb mcf_pci_insb +#define insw mcf_pci_insw +#define insl mcf_pci_insl + +#define outb mcf_pci_outb +#define outb_p mcf_pci_outb +#define outw mcf_pci_outw +#define outw_p mcf_pci_outw +#define outl mcf_pci_outl +#define outl_p mcf_pci_outl +#define outsb mcf_pci_outsb +#define outsw mcf_pci_outsw +#define outsl mcf_pci_outsl + +#define readb(addr) in_8(addr) +#define writeb(v, addr) out_8((addr), (v)) +#define readw(addr) in_le16(addr) +#define writew(v, addr) out_le16((addr), (v)) + +#elif defined(CONFIG_ISA) #if MULTI_ISA == 0 #undef MULTI_ISA @@ -340,4 +386,6 @@ static inline void memcpy_toio(volatile void __iomem *dst, const void *src, int */ #define xlate_dev_kmem_ptr(p) p +#define ioport_map(port, nr) ((void __iomem *)(port)) + #endif /* _IO_H */ diff --git a/arch/m68k/include/asm/m520xsim.h b/arch/m68k/include/asm/m520xsim.h index 17f2aab..db3f8ee 100644 --- a/arch/m68k/include/asm/m520xsim.h +++ b/arch/m68k/include/asm/m520xsim.h @@ -42,6 +42,9 @@ #define MCFINTC1_SIMR (0) #define MCFINTC1_CIMR (0) #define MCFINTC1_ICR0 (0) +#define MCFINTC2_SIMR (0) +#define MCFINTC2_CIMR (0) +#define MCFINTC2_ICR0 (0) #define MCFINT_VECBASE 64 #define MCFINT_UART0 26 /* Interrupt number for UART0 */ @@ -62,6 +65,7 @@ #define MCF_IRQ_FECENTC0 (MCFINT_VECBASE + MCFINT_FECENTC0) #define MCF_IRQ_QSPI (MCFINT_VECBASE + MCFINT_QSPI) +#define MCF_IRQ_PIT1 (MCFINT_VECBASE + MCFINT_PIT1) /* * SDRAM configuration registers. @@ -186,5 +190,15 @@ #define MCF_RCR_SWRESET 0x80 /* Software reset bit */ #define MCF_RCR_FRCSTOUT 0x40 /* Force external reset */ +/* + * Power Management. + */ +#define MCFPM_WCR 0xfc040013 +#define MCFPM_PPMSR0 0xfc04002c +#define MCFPM_PPMCR0 0xfc04002d +#define MCFPM_PPMHR0 0xfc040030 +#define MCFPM_PPMLR0 0xfc040034 +#define MCFPM_LPCR 0xfc0a0007 + /****************************************************************************/ #endif /* m520xsim_h */ diff --git a/arch/m68k/include/asm/m523xsim.h b/arch/m68k/include/asm/m523xsim.h index 075062d..91d3abc 100644 --- a/arch/m68k/include/asm/m523xsim.h +++ b/arch/m68k/include/asm/m523xsim.h @@ -52,6 +52,7 @@ #define MCF_IRQ_FECENTC0 (MCFINT_VECBASE + MCFINT_FECENTC0) #define MCF_IRQ_QSPI (MCFINT_VECBASE + MCFINT_QSPI) +#define MCF_IRQ_PIT1 (MCFINT_VECBASE + MCFINT_PIT1) /* * SDRAM configuration registers. diff --git a/arch/m68k/include/asm/m525xsim.h b/arch/m68k/include/asm/m525xsim.h new file mode 100644 index 0000000..6da24f6 --- /dev/null +++ b/arch/m68k/include/asm/m525xsim.h @@ -0,0 +1,194 @@ +/****************************************************************************/ + +/* + * m525xsim.h -- ColdFire 525x System Integration Module support. + * + * (C) Copyright 2012, Steven king <sfking@fdwdc.com> + * (C) Copyright 2002, Greg Ungerer (gerg@snapgear.com) + */ + +/****************************************************************************/ +#ifndef m525xsim_h +#define m525xsim_h +/****************************************************************************/ + +#define CPU_NAME "COLDFIRE(m525x)" +#define CPU_INSTR_PER_JIFFY 3 +#define MCF_BUSCLK (MCF_CLK / 2) + +#include <asm/m52xxacr.h> + +/* + * The 525x has a second MBAR region, define its address. + */ +#define MCF_MBAR2 0x80000000 + +/* + * Define the 525x SIM register set addresses. + */ +#define MCFSIM_RSR 0x00 /* Reset Status reg (r/w) */ +#define MCFSIM_SYPCR 0x01 /* System Protection reg (r/w)*/ +#define MCFSIM_SWIVR 0x02 /* SW Watchdog intr reg (r/w) */ +#define MCFSIM_SWSR 0x03 /* SW Watchdog service (r/w) */ +#define MCFSIM_MPARK 0x0C /* BUS Master Control Reg*/ +#define MCFSIM_IPR 0x40 /* Interrupt Pend reg (r/w) */ +#define MCFSIM_IMR 0x44 /* Interrupt Mask reg (r/w) */ +#define MCFSIM_ICR0 0x4c /* Intr Ctrl reg 0 (r/w) */ +#define MCFSIM_ICR1 0x4d /* Intr Ctrl reg 1 (r/w) */ +#define MCFSIM_ICR2 0x4e /* Intr Ctrl reg 2 (r/w) */ +#define MCFSIM_ICR3 0x4f /* Intr Ctrl reg 3 (r/w) */ +#define MCFSIM_ICR4 0x50 /* Intr Ctrl reg 4 (r/w) */ +#define MCFSIM_ICR5 0x51 /* Intr Ctrl reg 5 (r/w) */ +#define MCFSIM_ICR6 0x52 /* Intr Ctrl reg 6 (r/w) */ +#define MCFSIM_ICR7 0x53 /* Intr Ctrl reg 7 (r/w) */ +#define MCFSIM_ICR8 0x54 /* Intr Ctrl reg 8 (r/w) */ +#define MCFSIM_ICR9 0x55 /* Intr Ctrl reg 9 (r/w) */ +#define MCFSIM_ICR10 0x56 /* Intr Ctrl reg 10 (r/w) */ +#define MCFSIM_ICR11 0x57 /* Intr Ctrl reg 11 (r/w) */ + +#define MCFSIM_CSAR0 0x80 /* CS 0 Address 0 reg (r/w) */ +#define MCFSIM_CSMR0 0x84 /* CS 0 Mask 0 reg (r/w) */ +#define MCFSIM_CSCR0 0x8a /* CS 0 Control reg (r/w) */ +#define MCFSIM_CSAR1 0x8c /* CS 1 Address reg (r/w) */ +#define MCFSIM_CSMR1 0x90 /* CS 1 Mask reg (r/w) */ +#define MCFSIM_CSCR1 0x96 /* CS 1 Control reg (r/w) */ +#define MCFSIM_CSAR2 0x98 /* CS 2 Address reg (r/w) */ +#define MCFSIM_CSMR2 0x9c /* CS 2 Mask reg (r/w) */ +#define MCFSIM_CSCR2 0xa2 /* CS 2 Control reg (r/w) */ +#define MCFSIM_CSAR3 0xa4 /* CS 3 Address reg (r/w) */ +#define MCFSIM_CSMR3 0xa8 /* CS 3 Mask reg (r/w) */ +#define MCFSIM_CSCR3 0xae /* CS 3 Control reg (r/w) */ +#define MCFSIM_CSAR4 0xb0 /* CS 4 Address reg (r/w) */ +#define MCFSIM_CSMR4 0xb4 /* CS 4 Mask reg (r/w) */ +#define MCFSIM_CSCR4 0xba /* CS 4 Control reg (r/w) */ + +#define MCFSIM_DCR (MCF_MBAR + 0x100) /* DRAM Control */ +#define MCFSIM_DACR0 (MCF_MBAR + 0x108) /* DRAM 0 Addr/Ctrl */ +#define MCFSIM_DMR0 (MCF_MBAR + 0x10c) /* DRAM 0 Mask */ + +/* + * Secondary Interrupt Controller (in MBAR2) +*/ +#define MCFINTC2_INTBASE (MCF_MBAR2 + 0x168) /* Base Vector Reg */ +#define MCFINTC2_INTPRI1 (MCF_MBAR2 + 0x140) /* 0-7 priority */ +#define MCFINTC2_INTPRI2 (MCF_MBAR2 + 0x144) /* 8-15 priority */ +#define MCFINTC2_INTPRI3 (MCF_MBAR2 + 0x148) /* 16-23 priority */ +#define MCFINTC2_INTPRI4 (MCF_MBAR2 + 0x14c) /* 24-31 priority */ +#define MCFINTC2_INTPRI5 (MCF_MBAR2 + 0x150) /* 32-39 priority */ +#define MCFINTC2_INTPRI6 (MCF_MBAR2 + 0x154) /* 40-47 priority */ +#define MCFINTC2_INTPRI7 (MCF_MBAR2 + 0x158) /* 48-55 priority */ +#define MCFINTC2_INTPRI8 (MCF_MBAR2 + 0x15c) /* 56-63 priority */ + +#define MCFINTC2_INTPRI_REG(i) (MCFINTC2_INTPRI1 + \ + ((((i) - MCFINTC2_VECBASE) / 8) * 4)) +#define MCFINTC2_INTPRI_BITS(b, i) ((b) << (((i) % 8) * 4)) + +/* + * Timer module. + */ +#define MCFTIMER_BASE1 (MCF_MBAR + 0x140) /* Base of TIMER1 */ +#define MCFTIMER_BASE2 (MCF_MBAR + 0x180) /* Base of TIMER2 */ + +/* + * UART module. + */ +#define MCFUART_BASE0 (MCF_MBAR + 0x1c0) /* Base address UART0 */ +#define MCFUART_BASE1 (MCF_MBAR + 0x200) /* Base address UART1 */ + +/* + * QSPI module. + */ +#define MCFQSPI_BASE (MCF_MBAR + 0x300) /* Base address QSPI */ +#define MCFQSPI_SIZE 0x40 /* Register set size */ + + +#define MCFQSPI_CS0 15 +#define MCFQSPI_CS1 16 +#define MCFQSPI_CS2 24 +#define MCFQSPI_CS3 28 + +/* + * I2C module. + */ +#define MCFI2C_BASE0 (MCF_MBAR + 0x280) /* Base addreess I2C0 */ +#define MCFI2C_SIZE0 0x20 /* Register set size */ + +#define MCFI2C_BASE1 (MCF_MBAR2 + 0x440) /* Base addreess I2C1 */ +#define MCFI2C_SIZE1 0x20 /* Register set size */ +/* + * DMA unit base addresses. + */ +#define MCFDMA_BASE0 (MCF_MBAR + 0x300) /* Base address DMA 0 */ +#define MCFDMA_BASE1 (MCF_MBAR + 0x340) /* Base address DMA 1 */ +#define MCFDMA_BASE2 (MCF_MBAR + 0x380) /* Base address DMA 2 */ +#define MCFDMA_BASE3 (MCF_MBAR + 0x3C0) /* Base address DMA 3 */ + +/* + * Some symbol defines for the above... + */ +#define MCFSIM_SWDICR MCFSIM_ICR0 /* Watchdog timer ICR */ +#define MCFSIM_TIMER1ICR MCFSIM_ICR1 /* Timer 1 ICR */ +#define MCFSIM_TIMER2ICR MCFSIM_ICR2 /* Timer 2 ICR */ +#define MCFSIM_I2CICR MCFSIM_ICR3 /* I2C ICR */ +#define MCFSIM_UART1ICR MCFSIM_ICR4 /* UART 1 ICR */ +#define MCFSIM_UART2ICR MCFSIM_ICR5 /* UART 2 ICR */ +#define MCFSIM_DMA0ICR MCFSIM_ICR6 /* DMA 0 ICR */ +#define MCFSIM_DMA1ICR MCFSIM_ICR7 /* DMA 1 ICR */ +#define MCFSIM_DMA2ICR MCFSIM_ICR8 /* DMA 2 ICR */ +#define MCFSIM_DMA3ICR MCFSIM_ICR9 /* DMA 3 ICR */ +#define MCFSIM_QSPIICR MCFSIM_ICR10 /* QSPI ICR */ + +/* + * Define system peripheral IRQ usage. + */ +#define MCF_IRQ_QSPI 28 /* QSPI, Level 4 */ +#define MCF_IRQ_I2C0 29 +#define MCF_IRQ_TIMER 30 /* Timer0, Level 6 */ +#define MCF_IRQ_PROFILER 31 /* Timer1, Level 7 */ + +#define MCF_IRQ_UART0 73 /* UART0 */ +#define MCF_IRQ_UART1 74 /* UART1 */ + +/* + * Define the base interrupt for the second interrupt controller. + * We set it to 128, out of the way of the base interrupts, and plenty + * of room for its 64 interrupts. + */ +#define MCFINTC2_VECBASE 128 + +#define MCF_IRQ_GPIO0 (MCFINTC2_VECBASE + 32) +#define MCF_IRQ_GPIO1 (MCFINTC2_VECBASE + 33) +#define MCF_IRQ_GPIO2 (MCFINTC2_VECBASE + 34) +#define MCF_IRQ_GPIO3 (MCFINTC2_VECBASE + 35) +#define MCF_IRQ_GPIO4 (MCFINTC2_VECBASE + 36) +#define MCF_IRQ_GPIO5 (MCFINTC2_VECBASE + 37) +#define MCF_IRQ_GPIO6 (MCFINTC2_VECBASE + 38) + +#define MCF_IRQ_USBWUP (MCFINTC2_VECBASE + 40) +#define MCF_IRQ_I2C1 (MCFINTC2_VECBASE + 62) + +/* + * General purpose IO registers (in MBAR2). + */ +#define MCFSIM2_GPIOREAD (MCF_MBAR2 + 0x000) /* GPIO read values */ +#define MCFSIM2_GPIOWRITE (MCF_MBAR2 + 0x004) /* GPIO write values */ +#define MCFSIM2_GPIOENABLE (MCF_MBAR2 + 0x008) /* GPIO enabled */ +#define MCFSIM2_GPIOFUNC (MCF_MBAR2 + 0x00C) /* GPIO function */ +#define MCFSIM2_GPIO1READ (MCF_MBAR2 + 0x0B0) /* GPIO1 read values */ +#define MCFSIM2_GPIO1WRITE (MCF_MBAR2 + 0x0B4) /* GPIO1 write values */ +#define MCFSIM2_GPIO1ENABLE (MCF_MBAR2 + 0x0B8) /* GPIO1 enabled */ +#define MCFSIM2_GPIO1FUNC (MCF_MBAR2 + 0x0BC) /* GPIO1 function */ + +#define MCFSIM2_GPIOINTSTAT (MCF_MBAR2 + 0xc0) /* GPIO intr status */ +#define MCFSIM2_GPIOINTCLEAR (MCF_MBAR2 + 0xc0) /* GPIO intr clear */ +#define MCFSIM2_GPIOINTENABLE (MCF_MBAR2 + 0xc4) /* GPIO intr enable */ + +/* + * Generic GPIO support + */ +#define MCFGPIO_PIN_MAX 64 +#define MCFGPIO_IRQ_MAX 7 +#define MCFGPIO_IRQ_VECBASE MCF_IRQ_GPIO0 + +/****************************************************************************/ +#endif /* m525xsim_h */ diff --git a/arch/m68k/include/asm/m527xsim.h b/arch/m68k/include/asm/m527xsim.h index 83db810..71aa510 100644 --- a/arch/m68k/include/asm/m527xsim.h +++ b/arch/m68k/include/asm/m527xsim.h @@ -60,6 +60,7 @@ #define MCF_IRQ_FECENTC1 (MCFINT2_VECBASE + MCFINT2_FECENTC1) #define MCF_IRQ_QSPI (MCFINT_VECBASE + MCFINT_QSPI) +#define MCF_IRQ_PIT1 (MCFINT_VECBASE + MCFINT_PIT1) /* * SDRAM configuration registers. diff --git a/arch/m68k/include/asm/m528xsim.h b/arch/m68k/include/asm/m528xsim.h index 497c31c..4acb3c0 100644 --- a/arch/m68k/include/asm/m528xsim.h +++ b/arch/m68k/include/asm/m528xsim.h @@ -52,7 +52,7 @@ #define MCF_IRQ_FECENTC0 (MCFINT_VECBASE + MCFINT_FECENTC0) #define MCF_IRQ_QSPI (MCFINT_VECBASE + MCFINT_QSPI) - +#define MCF_IRQ_PIT1 (MCFINT_VECBASE + MCFINT_PIT1) /* * SDRAM configuration registers. */ diff --git a/arch/m68k/include/asm/m532xsim.h b/arch/m68k/include/asm/m532xsim.h index 29b66e2..5ca7b29 100644 --- a/arch/m68k/include/asm/m532xsim.h +++ b/arch/m68k/include/asm/m532xsim.h @@ -82,6 +82,9 @@ #define MCFINTC1_SIMR 0xFC04C01C #define MCFINTC1_CIMR 0xFC04C01D #define MCFINTC1_ICR0 0xFC04C040 +#define MCFINTC2_SIMR (0) +#define MCFINTC2_CIMR (0) +#define MCFINTC2_ICR0 (0) #define MCFSIM_ICR_TIMER1 (0xFC048040+32) #define MCFSIM_ICR_TIMER2 (0xFC048040+33) @@ -135,6 +138,20 @@ #define MCF_RCR_SWRESET 0x80 /* Software reset bit */ #define MCF_RCR_FRCSTOUT 0x40 /* Force external reset */ + +/* + * Power Management + */ +#define MCFPM_WCR 0xfc040013 +#define MCFPM_PPMSR0 0xfc04002c +#define MCFPM_PPMCR0 0xfc04002d +#define MCFPM_PPMSR1 0xfc04002e +#define MCFPM_PPMCR1 0xfc04002f +#define MCFPM_PPMHR0 0xfc040030 +#define MCFPM_PPMLR0 0xfc040034 +#define MCFPM_PPMHR1 0xfc040038 +#define MCFPM_LPCR 0xec090007 + /********************************************************************* * * Inter-IC (I2C) Module diff --git a/arch/m68k/include/asm/m5441xsim.h b/arch/m68k/include/asm/m5441xsim.h new file mode 100644 index 0000000..cc798ab --- /dev/null +++ b/arch/m68k/include/asm/m5441xsim.h @@ -0,0 +1,276 @@ +/* + * m5441xsim.h -- Coldfire 5441x register definitions + * + * (C) Copyright 2012, Steven King <sfking@fdwdc.com> +*/ + +#ifndef m5441xsim_h +#define m5441xsim_h + +#define CPU_NAME "COLDFIRE(m5441x)" +#define CPU_INSTR_PER_JIFFY 2 +#define MCF_BUSCLK (MCF_CLK / 2) + +#include <asm/m54xxacr.h> + +/* + * Reset Controller Module. + */ + +#define MCF_RCR 0xec090000 +#define MCF_RSR 0xec090001 + +#define MCF_RCR_SWRESET 0x80 /* Software reset bit */ +#define MCF_RCR_FRCSTOUT 0x40 /* Force external reset */ + +/* + * Interrupt Controller Modules. + */ +/* the 5441x have 3 interrupt controllers, each control 64 interrupts */ +#define MCFINT_VECBASE 64 +#define MCFINT0_VECBASE MCFINT_VECBASE +#define MCFINT1_VECBASE (MCFINT0_VECBASE + 64) +#define MCFINT2_VECBASE (MCFINT1_VECBASE + 64) + +/* interrupt controller 0 */ +#define MCFINTC0_SIMR 0xfc04801c +#define MCFINTC0_CIMR 0xfc04801d +#define MCFINTC0_ICR0 0xfc048040 +/* interrupt controller 1 */ +#define MCFINTC1_SIMR 0xfc04c01c +#define MCFINTC1_CIMR 0xfc04c01d +#define MCFINTC1_ICR0 0xfc04c040 +/* interrupt controller 2 */ +#define MCFINTC2_SIMR 0xfc05001c +#define MCFINTC2_CIMR 0xfc05001d +#define MCFINTC2_ICR0 0xfc050040 + +/* on interrupt controller 0 */ +#define MCFINT0_EPORT0 1 +#define MCFINT0_UART0 26 +#define MCFINT0_UART1 27 +#define MCFINT0_UART2 28 +#define MCFINT0_UART3 29 +#define MCFINT0_I2C0 30 +#define MCFINT0_DSPI0 31 + +#define MCFINT0_TIMER0 32 +#define MCFINT0_TIMER1 33 +#define MCFINT0_TIMER2 34 +#define MCFINT0_TIMER3 35 + +#define MCFINT0_FECRX0 36 +#define MCFINT0_FECTX0 40 +#define MCFINT0_FECENTC0 42 + +#define MCFINT0_FECRX1 49 +#define MCFINT0_FECTX1 53 +#define MCFINT0_FECENTC1 55 + +/* on interrupt controller 1 */ +#define MCFINT1_UART4 48 +#define MCFINT1_UART5 49 +#define MCFINT1_UART6 50 +#define MCFINT1_UART7 51 +#define MCFINT1_UART8 52 +#define MCFINT1_UART9 53 +#define MCFINT1_DSPI1 54 +#define MCFINT1_DSPI2 55 +#define MCFINT1_DSPI3 56 +#define MCFINT1_I2C1 57 +#define MCFINT1_I2C2 58 +#define MCFINT1_I2C3 59 +#define MCFINT1_I2C4 60 +#define MCFINT1_I2C5 61 + +/* on interrupt controller 2 */ +#define MCFINT2_PIT0 13 +#define MCFINT2_PIT1 14 +#define MCFINT2_PIT2 15 +#define MCFINT2_PIT3 16 +#define MCFINT2_RTC 26 + +/* + * PIT timer module. + */ +#define MCFPIT_BASE0 0xFC080000 /* Base address of TIMER0 */ +#define MCFPIT_BASE1 0xFC084000 /* Base address of TIMER1 */ +#define MCFPIT_BASE2 0xFC088000 /* Base address of TIMER2 */ +#define MCFPIT_BASE3 0xFC08C000 /* Base address of TIMER3 */ + + +#define MCF_IRQ_PIT1 (MCFINT2_VECBASE + MCFINT2_PIT1) + +/* + * Power Management + */ +#define MCFPM_WCR 0xfc040013 +#define MCFPM_PPMSR0 0xfc04002c +#define MCFPM_PPMCR0 0xfc04002d +#define MCFPM_PPMSR1 0xfc04002e +#define MCFPM_PPMCR1 0xfc04002f +#define MCFPM_PPMHR0 0xfc040030 +#define MCFPM_PPMLR0 0xfc040034 +#define MCFPM_PPMHR1 0xfc040038 +#define MCFPM_PPMLR1 0xfc04003c +#define MCFPM_LPCR 0xec090007 +/* + * UART module. + */ +#define MCFUART_BASE0 0xfc060000 /* Base address of UART0 */ +#define MCFUART_BASE1 0xfc064000 /* Base address of UART1 */ +#define MCFUART_BASE2 0xfc068000 /* Base address of UART2 */ +#define MCFUART_BASE3 0xfc06c000 /* Base address of UART3 */ +#define MCFUART_BASE4 0xec060000 /* Base address of UART4 */ +#define MCFUART_BASE5 0xec064000 /* Base address of UART5 */ +#define MCFUART_BASE6 0xec068000 /* Base address of UART6 */ +#define MCFUART_BASE7 0xec06c000 /* Base address of UART7 */ +#define MCFUART_BASE8 0xec070000 /* Base address of UART8 */ +#define MCFUART_BASE9 0xec074000 /* Base address of UART9 */ + +#define MCF_IRQ_UART0 (MCFINT0_VECBASE + MCFINT0_UART0) +#define MCF_IRQ_UART1 (MCFINT0_VECBASE + MCFINT0_UART1) +#define MCF_IRQ_UART2 (MCFINT0_VECBASE + MCFINT0_UART2) +#define MCF_IRQ_UART3 (MCFINT0_VECBASE + MCFINT0_UART3) +#define MCF_IRQ_UART4 (MCFINT1_VECBASE + MCFINT1_UART4) +#define MCF_IRQ_UART5 (MCFINT1_VECBASE + MCFINT1_UART5) +#define MCF_IRQ_UART6 (MCFINT1_VECBASE + MCFINT1_UART6) +#define MCF_IRQ_UART7 (MCFINT1_VECBASE + MCFINT1_UART7) +#define MCF_IRQ_UART8 (MCFINT1_VECBASE + MCFINT1_UART8) +#define MCF_IRQ_UART9 (MCFINT1_VECBASE + MCFINT1_UART9) +/* + * FEC modules. + */ +#define MCFFEC_BASE0 0xfc0d4000 +#define MCFFEC_SIZE0 0x800 +#define MCF_IRQ_FECRX0 (MCFINT0_VECBASE + MCFINT0_FECRX0) +#define MCF_IRQ_FECTX0 (MCFINT0_VECBASE + MCFINT0_FECTX0) +#define MCF_IRQ_FECENTC0 (MCFINT0_VECBASE + MCFINT0_FECENTC0) + +#define MCFFEC_BASE1 0xfc0d8000 +#define MCFFEC_SIZE1 0x800 +#define MCF_IRQ_FECRX1 (MCFINT0_VECBASE + MCFINT0_FECRX1) +#define MCF_IRQ_FECTX1 (MCFINT0_VECBASE + MCFINT0_FECTX1) +#define MCF_IRQ_FECENTC1 (MCFINT0_VECBASE + MCFINT0_FECENTC1) +/* + * I2C modules. + */ +#define MCFI2C_BASE0 0xfc058000 +#define MCFI2C_SIZE0 0x20 +#define MCFI2C_BASE1 0xfc038000 +#define MCFI2C_SIZE1 0x20 +#define MCFI2C_BASE2 0xec010000 +#define MCFI2C_SIZE2 0x20 +#define MCFI2C_BASE3 0xec014000 +#define MCFI2C_SIZE3 0x20 +#define MCFI2C_BASE4 0xec018000 +#define MCFI2C_SIZE4 0x20 +#define MCFI2C_BASE5 0xec01c000 +#define MCFI2C_SIZE5 0x20 + +#define MCF_IRQ_I2C0 (MCFINT0_VECBASE + MCFINT0_I2C0) +#define MCF_IRQ_I2C1 (MCFINT1_VECBASE + MCFINT1_I2C1) +#define MCF_IRQ_I2C2 (MCFINT1_VECBASE + MCFINT1_I2C2) +#define MCF_IRQ_I2C3 (MCFINT1_VECBASE + MCFINT1_I2C3) +#define MCF_IRQ_I2C4 (MCFINT1_VECBASE + MCFINT1_I2C4) +#define MCF_IRQ_I2C5 (MCFINT1_VECBASE + MCFINT1_I2C5) +/* + * EPORT Module. + */ +#define MCFEPORT_EPPAR 0xfc090000 +#define MCFEPORT_EPIER 0xfc090003 +#define MCFEPORT_EPFR 0xfc090006 +/* + * RTC Module. + */ +#define MCFRTC_BASE 0xfc0a8000 +#define MCFRTC_SIZE (0xfc0a8840 - 0xfc0a8000) +#define MCF_IRQ_RTC (MCFINT2_VECBASE + MCFINT2_RTC) + +/* + * GPIO Module. + */ +#define MCFGPIO_PODR_A 0xec094000 +#define MCFGPIO_PODR_B 0xec094001 +#define MCFGPIO_PODR_C 0xec094002 +#define MCFGPIO_PODR_D 0xec094003 +#define MCFGPIO_PODR_E 0xec094004 +#define MCFGPIO_PODR_F 0xec094005 +#define MCFGPIO_PODR_G 0xec094006 +#define MCFGPIO_PODR_H 0xec094007 +#define MCFGPIO_PODR_I 0xec094008 +#define MCFGPIO_PODR_J 0xec094009 +#define MCFGPIO_PODR_K 0xec09400a + +#define MCFGPIO_PDDR_A 0xec09400c +#define MCFGPIO_PDDR_B 0xec09400d +#define MCFGPIO_PDDR_C 0xec09400e +#define MCFGPIO_PDDR_D 0xec09400f +#define MCFGPIO_PDDR_E 0xec094010 +#define MCFGPIO_PDDR_F 0xec094011 +#define MCFGPIO_PDDR_G 0xec094012 +#define MCFGPIO_PDDR_H 0xec094013 +#define MCFGPIO_PDDR_I 0xec094014 +#define MCFGPIO_PDDR_J 0xec094015 +#define MCFGPIO_PDDR_K 0xec094016 + +#define MCFGPIO_PPDSDR_A 0xec094018 +#define MCFGPIO_PPDSDR_B 0xec094019 +#define MCFGPIO_PPDSDR_C 0xec09401a +#define MCFGPIO_PPDSDR_D 0xec09401b +#define MCFGPIO_PPDSDR_E 0xec09401c +#define MCFGPIO_PPDSDR_F 0xec09401d +#define MCFGPIO_PPDSDR_G 0xec09401e +#define MCFGPIO_PPDSDR_H 0xec09401f +#define MCFGPIO_PPDSDR_I 0xec094020 +#define MCFGPIO_PPDSDR_J 0xec094021 +#define MCFGPIO_PPDSDR_K 0xec094022 + +#define MCFGPIO_PCLRR_A 0xec094024 +#define MCFGPIO_PCLRR_B 0xec094025 +#define MCFGPIO_PCLRR_C 0xec094026 +#define MCFGPIO_PCLRR_D 0xec094027 +#define MCFGPIO_PCLRR_E 0xec094028 +#define MCFGPIO_PCLRR_F 0xec094029 +#define MCFGPIO_PCLRR_G 0xec09402a +#define MCFGPIO_PCLRR_H 0xec09402b +#define MCFGPIO_PCLRR_I 0xec09402c +#define MCFGPIO_PCLRR_J 0xec09402d +#define MCFGPIO_PCLRR_K 0xec09402e + +#define MCFGPIO_PAR_FBCTL 0xec094048 +#define MCFGPIO_PAR_BE 0xec094049 +#define MCFGPIO_PAR_CS 0xec09404a +#define MCFGPIO_PAR_CANI2C 0xec09404b +#define MCFGPIO_PAR_IRQ0H 0xec09404c +#define MCFGPIO_PAR_IRQ0L 0xec09404d +#define MCFGPIO_PAR_DSPIOWH 0xec09404e +#define MCFGPIO_PAR_DSPIOWL 0xec09404f +#define MCFGPIO_PAR_TIMER 0xec094050 +#define MCFGPIO_PAR_UART2 0xec094051 +#define MCFGPIO_PAR_UART1 0xec094052 +#define MCFGPIO_PAR_UART0 0xec094053 +#define MCFGPIO_PAR_SDHCH 0xec094054 +#define MCFGPIO_PAR_SDHCL 0xec094055 +#define MCFGPIO_PAR_SIMP0H 0xec094056 +#define MCFGPIO_PAR_SIMP0L 0xec094057 +#define MCFGPIO_PAR_SSI0H 0xec094058 +#define MCFGPIO_PAR_SSI0L 0xec094059 +#define MCFGPIO_PAR_DEBUGH1 0xec09405a +#define MCFGPIO_PAR_DEBUGH0 0xec09405b +#define MCFGPIO_PAR_DEBUGl 0xec09405c +#define MCFGPIO_PAR_FEC 0xec09405e + +/* generalization for generic gpio support */ +#define MCFGPIO_PODR MCFGPIO_PODR_A +#define MCFGPIO_PDDR MCFGPIO_PDDR_A +#define MCFGPIO_PPDR MCFGPIO_PPDSDR_A +#define MCFGPIO_SETR MCFGPIO_PPDSDR_A +#define MCFGPIO_CLRR MCFGPIO_PCLRR_A + +#define MCFGPIO_IRQ_MIN 17 +#define MCFGPIO_IRQ_MAX 24 +#define MCFGPIO_IRQ_VECBASE (MCFINT_VECBASE - MCFGPIO_IRQ_MIN) +#define MCFGPIO_PIN_MAX 87 + +#endif /* m5441xsim_h */ diff --git a/arch/m68k/include/asm/m54xxacr.h b/arch/m68k/include/asm/m54xxacr.h index 47906aa..192bbfe 100644 --- a/arch/m68k/include/asm/m54xxacr.h +++ b/arch/m68k/include/asm/m54xxacr.h @@ -55,6 +55,10 @@ #define ICACHE_SIZE 0x8000 /* instruction - 32k */ #define DCACHE_SIZE 0x8000 /* data - 32k */ +#elif defined(CONFIG_M5441x) + +#define ICACHE_SIZE 0x2000 /* instruction - 8k */ +#define DCACHE_SIZE 0x2000 /* data - 8k */ #endif #define CACHE_LINE_SIZE 0x0010 /* 16 bytes */ diff --git a/arch/m68k/include/asm/m54xxpci.h b/arch/m68k/include/asm/m54xxpci.h new file mode 100644 index 0000000..6fbf54f --- /dev/null +++ b/arch/m68k/include/asm/m54xxpci.h @@ -0,0 +1,138 @@ +/****************************************************************************/ + +/* + * m54xxpci.h -- ColdFire 547x and 548x PCI bus support + * + * (C) Copyright 2011, Greg Ungerer <gerg@uclinux.org> + * + * This file is subject to the terms and conditions of the GNU General Public + * License. See the file COPYING in the main directory of this archive + * for more details. + */ + +/****************************************************************************/ +#ifndef M54XXPCI_H +#define M54XXPCI_H +/****************************************************************************/ + +/* + * The core set of PCI support registers are mapped into the MBAR region. + */ +#define PCIIDR (CONFIG_MBAR + 0xb00) /* PCI device/vendor ID */ +#define PCISCR (CONFIG_MBAR + 0xb04) /* PCI status/command */ +#define PCICCRIR (CONFIG_MBAR + 0xb08) /* PCI class/revision */ +#define PCICR1 (CONFIG_MBAR + 0xb0c) /* PCI configuration 1 */ +#define PCIBAR0 (CONFIG_MBAR + 0xb10) /* PCI base address 0 */ +#define PCIBAR1 (CONFIG_MBAR + 0xb14) /* PCI base address 1 */ +#define PCICCPR (CONFIG_MBAR + 0xb28) /* PCI cardbus CIS pointer */ +#define PCISID (CONFIG_MBAR + 0xb2c) /* PCI subsystem IDs */ +#define PCIERBAR (CONFIG_MBAR + 0xb30) /* PCI expansion ROM */ +#define PCICPR (CONFIG_MBAR + 0xb34) /* PCI capabilities pointer */ +#define PCICR2 (CONFIG_MBAR + 0xb3c) /* PCI configuration 2 */ + +#define PCIGSCR (CONFIG_MBAR + 0xb60) /* Global status/control */ +#define PCITBATR0 (CONFIG_MBAR + 0xb64) /* Target base translation 0 */ +#define PCITBATR1 (CONFIG_MBAR + 0xb68) /* Target base translation 1 */ +#define PCITCR (CONFIG_MBAR + 0xb6c) /* Target control */ +#define PCIIW0BTAR (CONFIG_MBAR + 0xb70) /* Initiator window 0 */ +#define PCIIW1BTAR (CONFIG_MBAR + 0xb74) /* Initiator window 1 */ +#define PCIIW2BTAR (CONFIG_MBAR + 0xb78) /* Initiator window 2 */ +#define PCIIWCR (CONFIG_MBAR + 0xb80) /* Initiator window config */ +#define PCIICR (CONFIG_MBAR + 0xb84) /* Initiator control */ +#define PCIISR (CONFIG_MBAR + 0xb88) /* Initiator status */ +#define PCICAR (CONFIG_MBAR + 0xbf8) /* Configuration address */ + +#define PCITPSR (CONFIG_MBAR + 0x8400) /* TX packet size */ +#define PCITSAR (CONFIG_MBAR + 0x8404) /* TX start address */ +#define PCITTCR (CONFIG_MBAR + 0x8408) /* TX transaction control */ +#define PCITER (CONFIG_MBAR + 0x840c) /* TX enables */ +#define PCITNAR (CONFIG_MBAR + 0x8410) /* TX next address */ +#define PCITLWR (CONFIG_MBAR + 0x8414) /* TX last word */ +#define PCITDCR (CONFIG_MBAR + 0x8418) /* TX done counts */ +#define PCITSR (CONFIG_MBAR + 0x841c) /* TX status */ +#define PCITFDR (CONFIG_MBAR + 0x8440) /* TX FIFO data */ +#define PCITFSR (CONFIG_MBAR + 0x8444) /* TX FIFO status */ +#define PCITFCR (CONFIG_MBAR + 0x8448) /* TX FIFO control */ +#define PCITFAR (CONFIG_MBAR + 0x844c) /* TX FIFO alarm */ +#define PCITFRPR (CONFIG_MBAR + 0x8450) /* TX FIFO read pointer */ +#define PCITFWPR (CONFIG_MBAR + 0x8454) /* TX FIFO write pointer */ + +#define PCIRPSR (CONFIG_MBAR + 0x8480) /* RX packet size */ +#define PCIRSAR (CONFIG_MBAR + 0x8484) /* RX start address */ +#define PCIRTCR (CONFIG_MBAR + 0x8488) /* RX transaction control */ +#define PCIRER (CONFIG_MBAR + 0x848c) /* RX enables */ +#define PCIRNAR (CONFIG_MBAR + 0x8490) /* RX next address */ +#define PCIRDCR (CONFIG_MBAR + 0x8498) /* RX done counts */ +#define PCIRSR (CONFIG_MBAR + 0x849c) /* RX status */ +#define PCIRFDR (CONFIG_MBAR + 0x84c0) /* RX FIFO data */ +#define PCIRFSR (CONFIG_MBAR + 0x84c4) /* RX FIFO status */ +#define PCIRFCR (CONFIG_MBAR + 0x84c8) /* RX FIFO control */ +#define PCIRFAR (CONFIG_MBAR + 0x84cc) /* RX FIFO alarm */ +#define PCIRFRPR (CONFIG_MBAR + 0x84d0) /* RX FIFO read pointer */ +#define PCIRFWPR (CONFIG_MBAR + 0x84d4) /* RX FIFO write pointer */ + +#define PACR (CONFIG_MBAR + 0xc00) /* PCI arbiter control */ +#define PASR (COFNIG_MBAR + 0xc04) /* PCI arbiter status */ + +/* + * Definitions for the Global status and control register. + */ +#define PCIGSCR_PE 0x20000000 /* Parity error detected */ +#define PCIGSCR_SE 0x10000000 /* System error detected */ +#define PCIGSCR_XCLKBIN 0x07000000 /* XLB2CLKIN mask */ +#define PCIGSCR_PEE 0x00002000 /* Parity error intr enable */ +#define PCIGSCR_SEE 0x00001000 /* System error intr enable */ +#define PCIGSCR_RESET 0x00000001 /* Reset bit */ + +/* + * Bit definitions for the PCICAR configuration address register. + */ +#define PCICAR_E 0x80000000 /* Enable config space */ +#define PCICAR_BUSN 16 /* Move bus bits */ +#define PCICAR_DEVFNN 8 /* Move devfn bits */ +#define PCICAR_DWORDN 0 /* Move dword bits */ + +/* + * The initiator windows hold the memory and IO mapping information. + * This macro creates the register values from the desired addresses. + */ +#define WXBTAR(hostaddr, pciaddr, size) \ + (((hostaddr) & 0xff000000) | \ + ((((size) - 1) & 0xff000000) >> 8) | \ + (((pciaddr) & 0xff000000) >> 16)) + +#define PCIIWCR_W0_MEM 0x00000000 /* Window 0 is memory */ +#define PCIIWCR_W0_IO 0x08000000 /* Window 0 is IO */ +#define PCIIWCR_W0_MRD 0x00000000 /* Window 0 memory read */ +#define PCIIWCR_W0_MRDL 0x02000000 /* Window 0 memory read line */ +#define PCIIWCR_W0_MRDM 0x04000000 /* Window 0 memory read mult */ +#define PCIIWCR_W0_E 0x01000000 /* Window 0 enable */ + +#define PCIIWCR_W1_MEM 0x00000000 /* Window 0 is memory */ +#define PCIIWCR_W1_IO 0x00080000 /* Window 0 is IO */ +#define PCIIWCR_W1_MRD 0x00000000 /* Window 0 memory read */ +#define PCIIWCR_W1_MRDL 0x00020000 /* Window 0 memory read line */ +#define PCIIWCR_W1_MRDM 0x00040000 /* Window 0 memory read mult */ +#define PCIIWCR_W1_E 0x00010000 /* Window 0 enable */ + +/* + * Bit definitions for the PCIBATR registers. + */ +#define PCITBATR0_E 0x00000001 /* Enable window 0 */ +#define PCITBATR1_E 0x00000001 /* Enable window 1 */ + +/* + * PCI arbiter support definitions and macros. + */ +#define PACR_INTMPRI 0x00000001 +#define PACR_EXTMPRI(x) (((x) & 0x1f) << 1) +#define PACR_INTMINTE 0x00010000 +#define PACR_EXTMINTE(x) (((x) & 0x1f) << 17) +#define PACR_PKMD 0x40000000 +#define PACR_DS 0x80000000 + +#define PCICR1_CL(x) ((x) & 0xf) /* Cacheline size field */ +#define PCICR1_LT(x) (((x) & 0xff) << 8) /* Latency timer field */ + +/****************************************************************************/ +#endif /* M54XXPCI_H */ diff --git a/arch/m68k/include/asm/m54xxsim.h b/arch/m68k/include/asm/m54xxsim.h index ae56b88..d3c5e0d 100644 --- a/arch/m68k/include/asm/m54xxsim.h +++ b/arch/m68k/include/asm/m54xxsim.h @@ -81,4 +81,7 @@ #define MCF_PAR_PSC_RTS_RTS (0x30) #define MCF_PAR_PSC_CANRX (0x40) +#define MCF_PAR_PCIBG (CONFIG_MBAR + 0xa48) /* PCI bus grant */ +#define MCF_PAR_PCIBR (CONFIG_MBAR + 0xa4a) /* PCI */ + #endif /* m54xxsim_h */ diff --git a/arch/m68k/include/asm/mcfclk.h b/arch/m68k/include/asm/mcfclk.h new file mode 100644 index 0000000..b676a02 --- /dev/null +++ b/arch/m68k/include/asm/mcfclk.h @@ -0,0 +1,43 @@ +/* + * mcfclk.h -- coldfire specific clock structure + */ + + +#ifndef mcfclk_h +#define mcfclk_h + +struct clk; + +#ifdef MCFPM_PPMCR0 +struct clk_ops { + void (*enable)(struct clk *); + void (*disable)(struct clk *); +}; + +struct clk { + const char *name; + struct clk_ops *clk_ops; + unsigned long rate; + unsigned long enabled; + u8 slot; +}; + +extern struct clk *mcf_clks[]; +extern struct clk_ops clk_ops0; +#ifdef MCFPM_PPMCR1 +extern struct clk_ops clk_ops1; +#endif /* MCFPM_PPMCR1 */ + +#define DEFINE_CLK(clk_bank, clk_name, clk_slot, clk_rate) \ +static struct clk __clk_##clk_bank##_##clk_slot = { \ + .name = clk_name, \ + .clk_ops = &clk_ops##clk_bank, \ + .rate = clk_rate, \ + .slot = clk_slot, \ +} + +void __clk_init_enabled(struct clk *); +void __clk_init_disabled(struct clk *); +#endif /* MCFPM_PPMCR0 */ + +#endif /* mcfclk_h */ diff --git a/arch/m68k/include/asm/mcfgpio.h b/arch/m68k/include/asm/mcfgpio.h index fe468ea..fa1059f 100644 --- a/arch/m68k/include/asm/mcfgpio.h +++ b/arch/m68k/include/asm/mcfgpio.h @@ -16,82 +16,289 @@ #ifndef mcfgpio_h #define mcfgpio_h -#include <linux/io.h> +#ifdef CONFIG_GPIOLIB #include <asm-generic/gpio.h> +#else + +int __mcfgpio_get_value(unsigned gpio); +void __mcfgpio_set_value(unsigned gpio, int value); +int __mcfgpio_direction_input(unsigned gpio); +int __mcfgpio_direction_output(unsigned gpio, int value); +int __mcfgpio_request(unsigned gpio); +void __mcfgpio_free(unsigned gpio); + +/* our alternate 'gpiolib' functions */ +static inline int __gpio_get_value(unsigned gpio) +{ + if (gpio < MCFGPIO_PIN_MAX) + return __mcfgpio_get_value(gpio); + else + return -EINVAL; +} + +static inline void __gpio_set_value(unsigned gpio, int value) +{ + if (gpio < MCFGPIO_PIN_MAX) + __mcfgpio_set_value(gpio, value); +} + +static inline int __gpio_cansleep(unsigned gpio) +{ + if (gpio < MCFGPIO_PIN_MAX) + return 0; + else + return -EINVAL; +} + +static inline int __gpio_to_irq(unsigned gpio) +{ + return -EINVAL; +} + +static inline int gpio_direction_input(unsigned gpio) +{ + if (gpio < MCFGPIO_PIN_MAX) + return __mcfgpio_direction_input(gpio); + else + return -EINVAL; +} + +static inline int gpio_direction_output(unsigned gpio, int value) +{ + if (gpio < MCFGPIO_PIN_MAX) + return __mcfgpio_direction_output(gpio, value); + else + return -EINVAL; +} + +static inline int gpio_request(unsigned gpio, const char *label) +{ + if (gpio < MCFGPIO_PIN_MAX) + return __mcfgpio_request(gpio); + else + return -EINVAL; +} + +static inline void gpio_free(unsigned gpio) +{ + if (gpio < MCFGPIO_PIN_MAX) + __mcfgpio_free(gpio); +} + +#endif /* CONFIG_GPIOLIB */ -struct mcf_gpio_chip { - struct gpio_chip gpio_chip; - void __iomem *pddr; - void __iomem *podr; - void __iomem *ppdr; - void __iomem *setr; - void __iomem *clrr; - const u8 *gpio_to_pinmux; -}; - -extern struct mcf_gpio_chip mcf_gpio_chips[]; -extern unsigned int mcf_gpio_chips_size; - -int mcf_gpio_direction_input(struct gpio_chip *, unsigned); -int mcf_gpio_get_value(struct gpio_chip *, unsigned); -int mcf_gpio_direction_output(struct gpio_chip *, unsigned, int); -void mcf_gpio_set_value(struct gpio_chip *, unsigned, int); -void mcf_gpio_set_value_fast(struct gpio_chip *, unsigned, int); -int mcf_gpio_request(struct gpio_chip *, unsigned); -void mcf_gpio_free(struct gpio_chip *, unsigned); /* - * Define macros to ease the pain of setting up the GPIO tables. There - * are two cases we need to deal with here, they cover all currently - * available ColdFire GPIO hardware. There are of course minor differences - * in the layout and number of bits in each ColdFire part, but the macros - * take all that in. + * The Freescale Coldfire family is quite varied in how they implement GPIO. + * Some parts have 8 bit ports, some have 16bit and some have 32bit; some have + * only one port, others have multiple ports; some have a single data latch + * for both input and output, others have a separate pin data register to read + * input; some require a read-modify-write access to change an output, others + * have set and clear registers for some of the outputs; Some have all the + * GPIOs in a single control area, others have some GPIOs implemented in + * different modules. * - * Firstly is the conventional GPIO registers where we toggle individual - * bits in a register, preserving the other bits in the register. For - * lack of a better term I have called this the slow method. + * This implementation attempts accommodate the differences while presenting + * a generic interface that will optimize to as few instructions as possible. + */ +#if defined(CONFIG_M5206) || defined(CONFIG_M5206e) || \ + defined(CONFIG_M520x) || defined(CONFIG_M523x) || \ + defined(CONFIG_M527x) || defined(CONFIG_M528x) || \ + defined(CONFIG_M532x) || defined(CONFIG_M54xx) || \ + defined(CONFIG_M5441x) + +/* These parts have GPIO organized by 8 bit ports */ + +#define MCFGPIO_PORTTYPE u8 +#define MCFGPIO_PORTSIZE 8 +#define mcfgpio_read(port) __raw_readb(port) +#define mcfgpio_write(data, port) __raw_writeb(data, port) + +#elif defined(CONFIG_M5307) || defined(CONFIG_M5407) || defined(CONFIG_M5272) + +/* These parts have GPIO organized by 16 bit ports */ + +#define MCFGPIO_PORTTYPE u16 +#define MCFGPIO_PORTSIZE 16 +#define mcfgpio_read(port) __raw_readw(port) +#define mcfgpio_write(data, port) __raw_writew(data, port) + +#elif defined(CONFIG_M5249) || defined(CONFIG_M525x) + +/* These parts have GPIO organized by 32 bit ports */ + +#define MCFGPIO_PORTTYPE u32 +#define MCFGPIO_PORTSIZE 32 +#define mcfgpio_read(port) __raw_readl(port) +#define mcfgpio_write(data, port) __raw_writel(data, port) + +#endif + +#define mcfgpio_bit(gpio) (1 << ((gpio) % MCFGPIO_PORTSIZE)) +#define mcfgpio_port(gpio) ((gpio) / MCFGPIO_PORTSIZE) + +#if defined(CONFIG_M520x) || defined(CONFIG_M523x) || \ + defined(CONFIG_M527x) || defined(CONFIG_M528x) || \ + defined(CONFIG_M532x) || defined(CONFIG_M5441x) +/* + * These parts have an 'Edge' Port module (external interrupt/GPIO) which uses + * read-modify-write to change an output and a GPIO module which has separate + * set/clr registers to directly change outputs with a single write access. + */ +#if defined(CONFIG_M528x) +/* + * The 528x also has GPIOs in other modules (GPT, QADC) which use + * read-modify-write as well as those controlled by the EPORT and GPIO modules. */ -#define MCFGPS(mlabel, mbase, mngpio, mpddr, mpodr, mppdr) \ - { \ - .gpio_chip = { \ - .label = #mlabel, \ - .request = mcf_gpio_request, \ - .free = mcf_gpio_free, \ - .direction_input = mcf_gpio_direction_input, \ - .direction_output = mcf_gpio_direction_output,\ - .get = mcf_gpio_get_value, \ - .set = mcf_gpio_set_value, \ - .base = mbase, \ - .ngpio = mngpio, \ - }, \ - .pddr = (void __iomem *) mpddr, \ - .podr = (void __iomem *) mpodr, \ - .ppdr = (void __iomem *) mppdr, \ - } +#define MCFGPIO_SCR_START 40 +#elif defined(CONFIGM5441x) +/* The m5441x EPORT doesn't have its own GPIO port, uses PORT C */ +#define MCFGPIO_SCR_START 0 +#else +#define MCFGPIO_SCR_START 8 +#endif +#define MCFGPIO_SETR_PORT(gpio) (MCFGPIO_SETR + \ + mcfgpio_port(gpio - MCFGPIO_SCR_START)) + +#define MCFGPIO_CLRR_PORT(gpio) (MCFGPIO_CLRR + \ + mcfgpio_port(gpio - MCFGPIO_SCR_START)) +#else + +#define MCFGPIO_SCR_START MCFGPIO_PIN_MAX +/* with MCFGPIO_SCR == MCFGPIO_PIN_MAX, these will be optimized away */ +#define MCFGPIO_SETR_PORT(gpio) 0 +#define MCFGPIO_CLRR_PORT(gpio) 0 + +#endif /* - * Secondly is the faster case, where we have set and clear registers - * that allow us to set or clear a bit with a single write, not having - * to worry about preserving other bits. + * Coldfire specific helper functions */ -#define MCFGPF(mlabel, mbase, mngpio) \ - { \ - .gpio_chip = { \ - .label = #mlabel, \ - .request = mcf_gpio_request, \ - .free = mcf_gpio_free, \ - .direction_input = mcf_gpio_direction_input, \ - .direction_output = mcf_gpio_direction_output,\ - .get = mcf_gpio_get_value, \ - .set = mcf_gpio_set_value_fast, \ - .base = mbase, \ - .ngpio = mngpio, \ - }, \ - .pddr = (void __iomem *) MCFGPIO_PDDR_##mlabel, \ - .podr = (void __iomem *) MCFGPIO_PODR_##mlabel, \ - .ppdr = (void __iomem *) MCFGPIO_PPDSDR_##mlabel, \ - .setr = (void __iomem *) MCFGPIO_PPDSDR_##mlabel, \ - .clrr = (void __iomem *) MCFGPIO_PCLRR_##mlabel, \ - } +/* return the port pin data register for a gpio */ +static inline u32 __mcfgpio_ppdr(unsigned gpio) +{ +#if defined(CONFIG_M5206) || defined(CONFIG_M5206e) || \ + defined(CONFIG_M5307) || defined(CONFIG_M5407) + return MCFSIM_PADAT; +#elif defined(CONFIG_M5272) + if (gpio < 16) + return MCFSIM_PADAT; + else if (gpio < 32) + return MCFSIM_PBDAT; + else + return MCFSIM_PCDAT; +#elif defined(CONFIG_M5249) || defined(CONFIG_M525x) + if (gpio < 32) + return MCFSIM2_GPIOREAD; + else + return MCFSIM2_GPIO1READ; +#elif defined(CONFIG_M520x) || defined(CONFIG_M523x) || \ + defined(CONFIG_M527x) || defined(CONFIG_M528x) || \ + defined(CONFIG_M532x) || defined(CONFIG_M5441x) +#if !defined(CONFIG_M5441x) + if (gpio < 8) + return MCFEPORT_EPPDR; +#if defined(CONFIG_M528x) + else if (gpio < 16) + return MCFGPTA_GPTPORT; + else if (gpio < 24) + return MCFGPTB_GPTPORT; + else if (gpio < 32) + return MCFQADC_PORTQA; + else if (gpio < 40) + return MCFQADC_PORTQB; +#endif /* defined(CONFIG_M528x) */ + else +#endif /* !defined(CONFIG_M5441x) */ + return MCFGPIO_PPDR + mcfgpio_port(gpio - MCFGPIO_SCR_START); +#else + return 0; #endif +} + +/* return the port output data register for a gpio */ +static inline u32 __mcfgpio_podr(unsigned gpio) +{ +#if defined(CONFIG_M5206) || defined(CONFIG_M5206e) || \ + defined(CONFIG_M5307) || defined(CONFIG_M5407) + return MCFSIM_PADAT; +#elif defined(CONFIG_M5272) + if (gpio < 16) + return MCFSIM_PADAT; + else if (gpio < 32) + return MCFSIM_PBDAT; + else + return MCFSIM_PCDAT; +#elif defined(CONFIG_M5249) || defined(CONFIG_M525x) + if (gpio < 32) + return MCFSIM2_GPIOWRITE; + else + return MCFSIM2_GPIO1WRITE; +#elif defined(CONFIG_M520x) || defined(CONFIG_M523x) || \ + defined(CONFIG_M527x) || defined(CONFIG_M528x) || \ + defined(CONFIG_M532x) || defined(CONFIG_M5441x) +#if !defined(CONFIG_M5441x) + if (gpio < 8) + return MCFEPORT_EPDR; +#if defined(CONFIG_M528x) + else if (gpio < 16) + return MCFGPTA_GPTPORT; + else if (gpio < 24) + return MCFGPTB_GPTPORT; + else if (gpio < 32) + return MCFQADC_PORTQA; + else if (gpio < 40) + return MCFQADC_PORTQB; +#endif /* defined(CONFIG_M528x) */ + else +#endif /* !defined(CONFIG_M5441x) */ + return MCFGPIO_PODR + mcfgpio_port(gpio - MCFGPIO_SCR_START); +#else + return 0; +#endif +} + +/* return the port direction data register for a gpio */ +static inline u32 __mcfgpio_pddr(unsigned gpio) +{ +#if defined(CONFIG_M5206) || defined(CONFIG_M5206e) || \ + defined(CONFIG_M5307) || defined(CONFIG_M5407) + return MCFSIM_PADDR; +#elif defined(CONFIG_M5272) + if (gpio < 16) + return MCFSIM_PADDR; + else if (gpio < 32) + return MCFSIM_PBDDR; + else + return MCFSIM_PCDDR; +#elif defined(CONFIG_M5249) || defined(CONFIG_M525x) + if (gpio < 32) + return MCFSIM2_GPIOENABLE; + else + return MCFSIM2_GPIO1ENABLE; +#elif defined(CONFIG_M520x) || defined(CONFIG_M523x) || \ + defined(CONFIG_M527x) || defined(CONFIG_M528x) || \ + defined(CONFIG_M532x) || defined(CONFIG_M5441x) +#if !defined(CONFIG_M5441x) + if (gpio < 8) + return MCFEPORT_EPDDR; +#if defined(CONFIG_M528x) + else if (gpio < 16) + return MCFGPTA_GPTDDR; + else if (gpio < 24) + return MCFGPTB_GPTDDR; + else if (gpio < 32) + return MCFQADC_DDRQA; + else if (gpio < 40) + return MCFQADC_DDRQB; +#endif /* defined(CONFIG_M528x) */ + else +#endif /* !defined(CONFIG_M5441x) */ + return MCFGPIO_PDDR + mcfgpio_port(gpio - MCFGPIO_SCR_START); +#else + return 0; +#endif +} + +#endif /* mcfgpio_h */ diff --git a/arch/m68k/include/asm/mcfsim.h b/arch/m68k/include/asm/mcfsim.h index ebd0304..7a83e61 100644 --- a/arch/m68k/include/asm/mcfsim.h +++ b/arch/m68k/include/asm/mcfsim.h @@ -27,6 +27,9 @@ #elif defined(CONFIG_M5249) #include <asm/m5249sim.h> #include <asm/mcfintc.h> +#elif defined(CONFIG_M525x) +#include <asm/m525xsim.h> +#include <asm/mcfintc.h> #elif defined(CONFIG_M527x) #include <asm/m527xsim.h> #elif defined(CONFIG_M5272) @@ -43,6 +46,8 @@ #include <asm/mcfintc.h> #elif defined(CONFIG_M54xx) #include <asm/m54xxsim.h> +#elif defined(CONFIG_M5441x) +#include <asm/m5441xsim.h> #endif /****************************************************************************/ diff --git a/arch/m68k/include/asm/mcftimer.h b/arch/m68k/include/asm/mcftimer.h index 351c272..da2fa43 100644 --- a/arch/m68k/include/asm/mcftimer.h +++ b/arch/m68k/include/asm/mcftimer.h @@ -19,7 +19,7 @@ #define MCFTIMER_TRR 0x04 /* Timer Reference (r/w) */ #define MCFTIMER_TCR 0x08 /* Timer Capture reg (r/w) */ #define MCFTIMER_TCN 0x0C /* Timer Counter reg (r/w) */ -#if defined(CONFIG_M532x) +#if defined(CONFIG_M532x) || defined(CONFIG_M5441x) #define MCFTIMER_TER 0x03 /* Timer Event reg (r/w) */ #else #define MCFTIMER_TER 0x11 /* Timer Event reg (r/w) */ diff --git a/arch/m68k/include/asm/mcfuart.h b/arch/m68k/include/asm/mcfuart.h index 2d3bc77..b40c20f 100644 --- a/arch/m68k/include/asm/mcfuart.h +++ b/arch/m68k/include/asm/mcfuart.h @@ -43,8 +43,8 @@ struct mcf_platform_uart { #define MCFUART_UFPD 0x30 /* Frac Prec. Divider (r/w) */ #endif #if defined(CONFIG_M5206) || defined(CONFIG_M5206e) || \ - defined(CONFIG_M5249) || defined(CONFIG_M5307) || \ - defined(CONFIG_M5407) + defined(CONFIG_M5249) || defined(CONFIG_M525x) || \ + defined(CONFIG_M5307) || defined(CONFIG_M5407) #define MCFUART_UIVR 0x30 /* Interrupt Vector (r/w) */ #endif #define MCFUART_UIPR 0x34 /* Input Port (r) */ diff --git a/arch/m68k/include/asm/pci.h b/arch/m68k/include/asm/pci.h index 4ad0aea..848c3df 100644 --- a/arch/m68k/include/asm/pci.h +++ b/arch/m68k/include/asm/pci.h @@ -2,6 +2,7 @@ #define _ASM_M68K_PCI_H #include <asm-generic/pci-dma-compat.h> +#include <asm-generic/pci.h> /* The PCI address space does equal the physical memory * address space. The networking and block device layers use @@ -9,4 +10,9 @@ */ #define PCI_DMA_BUS_IS_PHYS (1) +#define pcibios_assign_all_busses() 1 + +#define PCIBIOS_MIN_IO 0x00000100 +#define PCIBIOS_MIN_MEM 0x02000000 + #endif /* _ASM_M68K_PCI_H */ diff --git a/arch/m68k/include/asm/pinmux.h b/arch/m68k/include/asm/pinmux.h deleted file mode 100644 index 119ee68..0000000 --- a/arch/m68k/include/asm/pinmux.h +++ /dev/null @@ -1,30 +0,0 @@ -/* - * Coldfire generic GPIO pinmux support. - * - * (C) Copyright 2009, Steven King <sfking@fdwdc.com> - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; version 2 of the License. - * - * 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. - */ - -#ifndef pinmux_h -#define pinmux_h - -#define MCFPINMUX_NONE -1 - -extern int mcf_pinmux_request(unsigned, unsigned); -extern void mcf_pinmux_release(unsigned, unsigned); - -static inline int mcf_pinmux_is_valid(unsigned pinmux) -{ - return pinmux != MCFPINMUX_NONE; -} - -#endif - diff --git a/arch/m68k/kernel/Makefile b/arch/m68k/kernel/Makefile index 5c7070e..068ad49 100644 --- a/arch/m68k/kernel/Makefile +++ b/arch/m68k/kernel/Makefile @@ -18,6 +18,7 @@ obj-y += setup.o signal.o sys_m68k.o syscalltable.o time.o traps.o obj-$(CONFIG_MMU_MOTOROLA) += ints.o vectors.o obj-$(CONFIG_MMU_SUN3) += ints.o vectors.o +obj-$(CONFIG_PCI) += pcibios.o ifndef CONFIG_MMU_SUN3 obj-y += dma.o diff --git a/arch/m68k/kernel/dma.c b/arch/m68k/kernel/dma.c index f6daf6e..e546a55 100644 --- a/arch/m68k/kernel/dma.c +++ b/arch/m68k/kernel/dma.c @@ -16,7 +16,7 @@ #include <asm/pgalloc.h> -#ifdef CONFIG_MMU +#if defined(CONFIG_MMU) && !defined(CONFIG_COLDFIRE) void *dma_alloc_coherent(struct device *dev, size_t size, dma_addr_t *handle, gfp_t flag) @@ -96,7 +96,7 @@ void dma_free_coherent(struct device *dev, size_t size, free_pages((unsigned long)vaddr, get_order(size)); } -#endif /* CONFIG_MMU */ +#endif /* CONFIG_MMU && !CONFIG_COLDFIRE */ EXPORT_SYMBOL(dma_alloc_coherent); EXPORT_SYMBOL(dma_free_coherent); @@ -105,6 +105,7 @@ void dma_sync_single_for_device(struct device *dev, dma_addr_t handle, size_t size, enum dma_data_direction dir) { switch (dir) { + case DMA_BIDIRECTIONAL: case DMA_TO_DEVICE: cache_push(handle, size); break; diff --git a/arch/m68k/kernel/entry.S b/arch/m68k/kernel/entry.S index b8daf64..165ee9f 100644 --- a/arch/m68k/kernel/entry.S +++ b/arch/m68k/kernel/entry.S @@ -1,5 +1,451 @@ -#if defined(CONFIG_MMU) && !defined(CONFIG_COLDFIRE) -#include "entry_mm.S" +/* -*- mode: asm -*- + * + * linux/arch/m68k/kernel/entry.S + * + * Copyright (C) 1991, 1992 Linus Torvalds + * + * This file is subject to the terms and conditions of the GNU General Public + * License. See the file README.legal in the main directory of this archive + * for more details. + * + * Linux/m68k support by Hamish Macdonald + * + * 68060 fixes by Jesper Skov + * + */ + +/* + * entry.S contains the system-call and fault low-level handling routines. + * This also contains the timer-interrupt handler, as well as all interrupts + * and faults that can result in a task-switch. + * + * NOTE: This code handles signal-recognition, which happens every time + * after a timer-interrupt and after each system call. + * + */ + +/* + * 12/03/96 Jes: Currently we only support m68k single-cpu systems, so + * all pointers that used to be 'current' are now entry + * number 0 in the 'current_set' list. + * + * 6/05/00 RZ: addedd writeback completion after return from sighandler + * for 68040 + */ + +#include <linux/linkage.h> +#include <asm/errno.h> +#include <asm/setup.h> +#include <asm/segment.h> +#include <asm/traps.h> +#include <asm/unistd.h> +#include <asm/asm-offsets.h> +#include <asm/entry.h> + +.globl system_call, buserr, trap, resume +.globl sys_call_table +.globl sys_fork, sys_clone, sys_vfork +.globl ret_from_interrupt, bad_interrupt +.globl auto_irqhandler_fixup +.globl user_irqvec_fixup + +.text +ENTRY(sys_fork) + SAVE_SWITCH_STACK + pea %sp@(SWITCH_STACK_SIZE) + jbsr m68k_fork + addql #4,%sp + RESTORE_SWITCH_STACK + rts + +ENTRY(sys_clone) + SAVE_SWITCH_STACK + pea %sp@(SWITCH_STACK_SIZE) + jbsr m68k_clone + addql #4,%sp + RESTORE_SWITCH_STACK + rts + +ENTRY(sys_vfork) + SAVE_SWITCH_STACK + pea %sp@(SWITCH_STACK_SIZE) + jbsr m68k_vfork + addql #4,%sp + RESTORE_SWITCH_STACK + rts + +ENTRY(sys_sigreturn) + SAVE_SWITCH_STACK + jbsr do_sigreturn + RESTORE_SWITCH_STACK + rts + +ENTRY(sys_rt_sigreturn) + SAVE_SWITCH_STACK + jbsr do_rt_sigreturn + RESTORE_SWITCH_STACK + rts + +ENTRY(buserr) + SAVE_ALL_INT + GET_CURRENT(%d0) + movel %sp,%sp@- | stack frame pointer argument + jbsr buserr_c + addql #4,%sp + jra ret_from_exception + +ENTRY(trap) + SAVE_ALL_INT + GET_CURRENT(%d0) + movel %sp,%sp@- | stack frame pointer argument + jbsr trap_c + addql #4,%sp + jra ret_from_exception + + | After a fork we jump here directly from resume, + | so that %d1 contains the previous task + | schedule_tail now used regardless of CONFIG_SMP +ENTRY(ret_from_fork) + movel %d1,%sp@- + jsr schedule_tail + addql #4,%sp + jra ret_from_exception + +#if defined(CONFIG_COLDFIRE) || !defined(CONFIG_MMU) + +#ifdef TRAP_DBG_INTERRUPT + +.globl dbginterrupt +ENTRY(dbginterrupt) + SAVE_ALL_INT + GET_CURRENT(%d0) + movel %sp,%sp@- /* stack frame pointer argument */ + jsr dbginterrupt_c + addql #4,%sp + jra ret_from_exception +#endif + +ENTRY(reschedule) + /* save top of frame */ + pea %sp@ + jbsr set_esp0 + addql #4,%sp + pea ret_from_exception + jmp schedule + +ENTRY(ret_from_user_signal) + moveq #__NR_sigreturn,%d0 + trap #0 + +ENTRY(ret_from_user_rt_signal) + movel #__NR_rt_sigreturn,%d0 + trap #0 + #else -#include "entry_no.S" + +do_trace_entry: + movel #-ENOSYS,%sp@(PT_OFF_D0)| needed for strace + subql #4,%sp + SAVE_SWITCH_STACK + jbsr syscall_trace + RESTORE_SWITCH_STACK + addql #4,%sp + movel %sp@(PT_OFF_ORIG_D0),%d0 + cmpl #NR_syscalls,%d0 + jcs syscall +badsys: + movel #-ENOSYS,%sp@(PT_OFF_D0) + jra ret_from_syscall + +do_trace_exit: + subql #4,%sp + SAVE_SWITCH_STACK + jbsr syscall_trace + RESTORE_SWITCH_STACK + addql #4,%sp + jra .Lret_from_exception + +ENTRY(ret_from_signal) + movel %curptr@(TASK_STACK),%a1 + tstb %a1@(TINFO_FLAGS+2) + jge 1f + jbsr syscall_trace +1: RESTORE_SWITCH_STACK + addql #4,%sp +/* on 68040 complete pending writebacks if any */ +#ifdef CONFIG_M68040 + bfextu %sp@(PT_OFF_FORMATVEC){#0,#4},%d0 + subql #7,%d0 | bus error frame ? + jbne 1f + movel %sp,%sp@- + jbsr berr_040cleanup + addql #4,%sp +1: +#endif + jra .Lret_from_exception + +ENTRY(system_call) + SAVE_ALL_SYS + + GET_CURRENT(%d1) + movel %d1,%a1 + + | save top of frame + movel %sp,%curptr@(TASK_THREAD+THREAD_ESP0) + + | syscall trace? + tstb %a1@(TINFO_FLAGS+2) + jmi do_trace_entry + cmpl #NR_syscalls,%d0 + jcc badsys +syscall: + jbsr @(sys_call_table,%d0:l:4)@(0) + movel %d0,%sp@(PT_OFF_D0) | save the return value +ret_from_syscall: + |oriw #0x0700,%sr + movel %curptr@(TASK_STACK),%a1 + movew %a1@(TINFO_FLAGS+2),%d0 + jne syscall_exit_work +1: RESTORE_ALL + +syscall_exit_work: + btst #5,%sp@(PT_OFF_SR) | check if returning to kernel + bnes 1b | if so, skip resched, signals + lslw #1,%d0 + jcs do_trace_exit + jmi do_delayed_trace + lslw #8,%d0 + jne do_signal_return + pea resume_userspace + jra schedule + + +ENTRY(ret_from_exception) +.Lret_from_exception: + btst #5,%sp@(PT_OFF_SR) | check if returning to kernel + bnes 1f | if so, skip resched, signals + | only allow interrupts when we are really the last one on the + | kernel stack, otherwise stack overflow can occur during + | heavy interrupt load + andw #ALLOWINT,%sr + +resume_userspace: + movel %curptr@(TASK_STACK),%a1 + moveb %a1@(TINFO_FLAGS+3),%d0 + jne exit_work +1: RESTORE_ALL + +exit_work: + | save top of frame + movel %sp,%curptr@(TASK_THREAD+THREAD_ESP0) + lslb #1,%d0 + jne do_signal_return + pea resume_userspace + jra schedule + + +do_signal_return: + |andw #ALLOWINT,%sr + subql #4,%sp | dummy return address + SAVE_SWITCH_STACK + pea %sp@(SWITCH_STACK_SIZE) + bsrl do_notify_resume + addql #4,%sp + RESTORE_SWITCH_STACK + addql #4,%sp + jbra resume_userspace + +do_delayed_trace: + bclr #7,%sp@(PT_OFF_SR) | clear trace bit in SR + pea 1 | send SIGTRAP + movel %curptr,%sp@- + pea LSIGTRAP + jbsr send_sig + addql #8,%sp + addql #4,%sp + jbra resume_userspace + + +/* This is the main interrupt handler for autovector interrupts */ + +ENTRY(auto_inthandler) + SAVE_ALL_INT + GET_CURRENT(%d0) + movel %d0,%a1 + addqb #1,%a1@(TINFO_PREEMPT+1) + | put exception # in d0 + bfextu %sp@(PT_OFF_FORMATVEC){#4,#10},%d0 + subw #VEC_SPUR,%d0 + + movel %sp,%sp@- + movel %d0,%sp@- | put vector # on stack +auto_irqhandler_fixup = . + 2 + jsr do_IRQ | process the IRQ + addql #8,%sp | pop parameters off stack + +ret_from_interrupt: + movel %curptr@(TASK_STACK),%a1 + subqb #1,%a1@(TINFO_PREEMPT+1) + jeq ret_from_last_interrupt +2: RESTORE_ALL + + ALIGN +ret_from_last_interrupt: + moveq #(~ALLOWINT>>8)&0xff,%d0 + andb %sp@(PT_OFF_SR),%d0 + jne 2b + + /* check if we need to do software interrupts */ + tstl irq_stat+CPUSTAT_SOFTIRQ_PENDING + jeq .Lret_from_exception + pea ret_from_exception + jra do_softirq + +/* Handler for user defined interrupt vectors */ + +ENTRY(user_inthandler) + SAVE_ALL_INT + GET_CURRENT(%d0) + movel %d0,%a1 + addqb #1,%a1@(TINFO_PREEMPT+1) + | put exception # in d0 + bfextu %sp@(PT_OFF_FORMATVEC){#4,#10},%d0 +user_irqvec_fixup = . + 2 + subw #VEC_USER,%d0 + + movel %sp,%sp@- + movel %d0,%sp@- | put vector # on stack + jsr do_IRQ | process the IRQ + addql #8,%sp | pop parameters off stack + + movel %curptr@(TASK_STACK),%a1 + subqb #1,%a1@(TINFO_PREEMPT+1) + jeq ret_from_last_interrupt + RESTORE_ALL + +/* Handler for uninitialized and spurious interrupts */ + +ENTRY(bad_inthandler) + SAVE_ALL_INT + GET_CURRENT(%d0) + movel %d0,%a1 + addqb #1,%a1@(TINFO_PREEMPT+1) + + movel %sp,%sp@- + jsr handle_badint + addql #4,%sp + + movel %curptr@(TASK_STACK),%a1 + subqb #1,%a1@(TINFO_PREEMPT+1) + jeq ret_from_last_interrupt + RESTORE_ALL + + +resume: + /* + * Beware - when entering resume, prev (the current task) is + * in a0, next (the new task) is in a1,so don't change these + * registers until their contents are no longer needed. + */ + + /* save sr */ + movew %sr,%a0@(TASK_THREAD+THREAD_SR) + + /* save fs (sfc,%dfc) (may be pointing to kernel memory) */ + movec %sfc,%d0 + movew %d0,%a0@(TASK_THREAD+THREAD_FS) + + /* save usp */ + /* it is better to use a movel here instead of a movew 8*) */ + movec %usp,%d0 + movel %d0,%a0@(TASK_THREAD+THREAD_USP) + + /* save non-scratch registers on stack */ + SAVE_SWITCH_STACK + + /* save current kernel stack pointer */ + movel %sp,%a0@(TASK_THREAD+THREAD_KSP) + + /* save floating point context */ +#ifndef CONFIG_M68KFPU_EMU_ONLY +#ifdef CONFIG_M68KFPU_EMU + tstl m68k_fputype + jeq 3f +#endif + fsave %a0@(TASK_THREAD+THREAD_FPSTATE) + +#if defined(CONFIG_M68060) +#if !defined(CPU_M68060_ONLY) + btst #3,m68k_cputype+3 + beqs 1f +#endif + /* The 060 FPU keeps status in bits 15-8 of the first longword */ + tstb %a0@(TASK_THREAD+THREAD_FPSTATE+2) + jeq 3f +#if !defined(CPU_M68060_ONLY) + jra 2f +#endif +#endif /* CONFIG_M68060 */ +#if !defined(CPU_M68060_ONLY) +1: tstb %a0@(TASK_THREAD+THREAD_FPSTATE) + jeq 3f +#endif +2: fmovemx %fp0-%fp7,%a0@(TASK_THREAD+THREAD_FPREG) + fmoveml %fpcr/%fpsr/%fpiar,%a0@(TASK_THREAD+THREAD_FPCNTL) +3: +#endif /* CONFIG_M68KFPU_EMU_ONLY */ + /* Return previous task in %d1 */ + movel %curptr,%d1 + + /* switch to new task (a1 contains new task) */ + movel %a1,%curptr + + /* restore floating point context */ +#ifndef CONFIG_M68KFPU_EMU_ONLY +#ifdef CONFIG_M68KFPU_EMU + tstl m68k_fputype + jeq 4f +#endif +#if defined(CONFIG_M68060) +#if !defined(CPU_M68060_ONLY) + btst #3,m68k_cputype+3 + beqs 1f +#endif + /* The 060 FPU keeps status in bits 15-8 of the first longword */ + tstb %a1@(TASK_THREAD+THREAD_FPSTATE+2) + jeq 3f +#if !defined(CPU_M68060_ONLY) + jra 2f +#endif +#endif /* CONFIG_M68060 */ +#if !defined(CPU_M68060_ONLY) +1: tstb %a1@(TASK_THREAD+THREAD_FPSTATE) + jeq 3f #endif +2: fmovemx %a1@(TASK_THREAD+THREAD_FPREG),%fp0-%fp7 + fmoveml %a1@(TASK_THREAD+THREAD_FPCNTL),%fpcr/%fpsr/%fpiar +3: frestore %a1@(TASK_THREAD+THREAD_FPSTATE) +4: +#endif /* CONFIG_M68KFPU_EMU_ONLY */ + + /* restore the kernel stack pointer */ + movel %a1@(TASK_THREAD+THREAD_KSP),%sp + + /* restore non-scratch registers */ + RESTORE_SWITCH_STACK + + /* restore user stack pointer */ + movel %a1@(TASK_THREAD+THREAD_USP),%a0 + movel %a0,%usp + + /* restore fs (sfc,%dfc) */ + movew %a1@(TASK_THREAD+THREAD_FS),%a0 + movec %a0,%sfc + movec %a0,%dfc + + /* restore status register */ + movew %a1@(TASK_THREAD+THREAD_SR),%sr + + rts + +#endif /* CONFIG_MMU && !CONFIG_COLDFIRE */ diff --git a/arch/m68k/kernel/entry_mm.S b/arch/m68k/kernel/entry_mm.S deleted file mode 100644 index f29e73c..0000000 --- a/arch/m68k/kernel/entry_mm.S +++ /dev/null @@ -1,419 +0,0 @@ -/* -*- mode: asm -*- - * - * linux/arch/m68k/kernel/entry.S - * - * Copyright (C) 1991, 1992 Linus Torvalds - * - * This file is subject to the terms and conditions of the GNU General Public - * License. See the file README.legal in the main directory of this archive - * for more details. - * - * Linux/m68k support by Hamish Macdonald - * - * 68060 fixes by Jesper Skov - * - */ - -/* - * entry.S contains the system-call and fault low-level handling routines. - * This also contains the timer-interrupt handler, as well as all interrupts - * and faults that can result in a task-switch. - * - * NOTE: This code handles signal-recognition, which happens every time - * after a timer-interrupt and after each system call. - * - */ - -/* - * 12/03/96 Jes: Currently we only support m68k single-cpu systems, so - * all pointers that used to be 'current' are now entry - * number 0 in the 'current_set' list. - * - * 6/05/00 RZ: addedd writeback completion after return from sighandler - * for 68040 - */ - -#include <linux/linkage.h> -#include <asm/entry.h> -#include <asm/errno.h> -#include <asm/setup.h> -#include <asm/segment.h> -#include <asm/traps.h> -#include <asm/unistd.h> - -#include <asm/asm-offsets.h> - -.globl system_call, buserr, trap, resume -.globl sys_call_table -.globl sys_fork, sys_clone, sys_vfork -.globl ret_from_interrupt, bad_interrupt -.globl auto_irqhandler_fixup -.globl user_irqvec_fixup - -.text -ENTRY(buserr) - SAVE_ALL_INT - GET_CURRENT(%d0) - movel %sp,%sp@- | stack frame pointer argument - bsrl buserr_c - addql #4,%sp - jra .Lret_from_exception - -ENTRY(trap) - SAVE_ALL_INT - GET_CURRENT(%d0) - movel %sp,%sp@- | stack frame pointer argument - bsrl trap_c - addql #4,%sp - jra .Lret_from_exception - - | After a fork we jump here directly from resume, - | so that %d1 contains the previous task - | schedule_tail now used regardless of CONFIG_SMP -ENTRY(ret_from_fork) - movel %d1,%sp@- - jsr schedule_tail - addql #4,%sp - jra .Lret_from_exception - -do_trace_entry: - movel #-ENOSYS,%sp@(PT_OFF_D0)| needed for strace - subql #4,%sp - SAVE_SWITCH_STACK - jbsr syscall_trace - RESTORE_SWITCH_STACK - addql #4,%sp - movel %sp@(PT_OFF_ORIG_D0),%d0 - cmpl #NR_syscalls,%d0 - jcs syscall -badsys: - movel #-ENOSYS,%sp@(PT_OFF_D0) - jra ret_from_syscall - -do_trace_exit: - subql #4,%sp - SAVE_SWITCH_STACK - jbsr syscall_trace - RESTORE_SWITCH_STACK - addql #4,%sp - jra .Lret_from_exception - -ENTRY(ret_from_signal) - movel %curptr@(TASK_STACK),%a1 - tstb %a1@(TINFO_FLAGS+2) - jge 1f - jbsr syscall_trace -1: RESTORE_SWITCH_STACK - addql #4,%sp -/* on 68040 complete pending writebacks if any */ -#ifdef CONFIG_M68040 - bfextu %sp@(PT_OFF_FORMATVEC){#0,#4},%d0 - subql #7,%d0 | bus error frame ? - jbne 1f - movel %sp,%sp@- - jbsr berr_040cleanup - addql #4,%sp -1: -#endif - jra .Lret_from_exception - -ENTRY(system_call) - SAVE_ALL_SYS - - GET_CURRENT(%d1) - movel %d1,%a1 - - | save top of frame - movel %sp,%curptr@(TASK_THREAD+THREAD_ESP0) - - | syscall trace? - tstb %a1@(TINFO_FLAGS+2) - jmi do_trace_entry - cmpl #NR_syscalls,%d0 - jcc badsys -syscall: - jbsr @(sys_call_table,%d0:l:4)@(0) - movel %d0,%sp@(PT_OFF_D0) | save the return value -ret_from_syscall: - |oriw #0x0700,%sr - movel %curptr@(TASK_STACK),%a1 - movew %a1@(TINFO_FLAGS+2),%d0 - jne syscall_exit_work -1: RESTORE_ALL - -syscall_exit_work: - btst #5,%sp@(PT_OFF_SR) | check if returning to kernel - bnes 1b | if so, skip resched, signals - lslw #1,%d0 - jcs do_trace_exit - jmi do_delayed_trace - lslw #8,%d0 - jne do_signal_return - pea resume_userspace - jra schedule - - -ENTRY(ret_from_exception) -.Lret_from_exception: - btst #5,%sp@(PT_OFF_SR) | check if returning to kernel - bnes 1f | if so, skip resched, signals - | only allow interrupts when we are really the last one on the - | kernel stack, otherwise stack overflow can occur during - | heavy interrupt load - andw #ALLOWINT,%sr - -resume_userspace: - movel %curptr@(TASK_STACK),%a1 - moveb %a1@(TINFO_FLAGS+3),%d0 - jne exit_work -1: RESTORE_ALL - -exit_work: - | save top of frame - movel %sp,%curptr@(TASK_THREAD+THREAD_ESP0) - lslb #1,%d0 - jne do_signal_return - pea resume_userspace - jra schedule - - -do_signal_return: - |andw #ALLOWINT,%sr - subql #4,%sp | dummy return address - SAVE_SWITCH_STACK - pea %sp@(SWITCH_STACK_SIZE) - bsrl do_notify_resume - addql #4,%sp - RESTORE_SWITCH_STACK - addql #4,%sp - jbra resume_userspace - -do_delayed_trace: - bclr #7,%sp@(PT_OFF_SR) | clear trace bit in SR - pea 1 | send SIGTRAP - movel %curptr,%sp@- - pea LSIGTRAP - jbsr send_sig - addql #8,%sp - addql #4,%sp - jbra resume_userspace - - -/* This is the main interrupt handler for autovector interrupts */ - -ENTRY(auto_inthandler) - SAVE_ALL_INT - GET_CURRENT(%d0) - movel %d0,%a1 - addqb #1,%a1@(TINFO_PREEMPT+1) - | put exception # in d0 - bfextu %sp@(PT_OFF_FORMATVEC){#4,#10},%d0 - subw #VEC_SPUR,%d0 - - movel %sp,%sp@- - movel %d0,%sp@- | put vector # on stack -auto_irqhandler_fixup = . + 2 - jsr do_IRQ | process the IRQ - addql #8,%sp | pop parameters off stack - -ret_from_interrupt: - movel %curptr@(TASK_STACK),%a1 - subqb #1,%a1@(TINFO_PREEMPT+1) - jeq ret_from_last_interrupt -2: RESTORE_ALL - - ALIGN -ret_from_last_interrupt: - moveq #(~ALLOWINT>>8)&0xff,%d0 - andb %sp@(PT_OFF_SR),%d0 - jne 2b - - /* check if we need to do software interrupts */ - tstl irq_stat+CPUSTAT_SOFTIRQ_PENDING - jeq .Lret_from_exception - pea ret_from_exception - jra do_softirq - -/* Handler for user defined interrupt vectors */ - -ENTRY(user_inthandler) - SAVE_ALL_INT - GET_CURRENT(%d0) - movel %d0,%a1 - addqb #1,%a1@(TINFO_PREEMPT+1) - | put exception # in d0 - bfextu %sp@(PT_OFF_FORMATVEC){#4,#10},%d0 -user_irqvec_fixup = . + 2 - subw #VEC_USER,%d0 - - movel %sp,%sp@- - movel %d0,%sp@- | put vector # on stack - jsr do_IRQ | process the IRQ - addql #8,%sp | pop parameters off stack - - movel %curptr@(TASK_STACK),%a1 - subqb #1,%a1@(TINFO_PREEMPT+1) - jeq ret_from_last_interrupt - RESTORE_ALL - -/* Handler for uninitialized and spurious interrupts */ - -ENTRY(bad_inthandler) - SAVE_ALL_INT - GET_CURRENT(%d0) - movel %d0,%a1 - addqb #1,%a1@(TINFO_PREEMPT+1) - - movel %sp,%sp@- - jsr handle_badint - addql #4,%sp - - movel %curptr@(TASK_STACK),%a1 - subqb #1,%a1@(TINFO_PREEMPT+1) - jeq ret_from_last_interrupt - RESTORE_ALL - - -ENTRY(sys_fork) - SAVE_SWITCH_STACK - pea %sp@(SWITCH_STACK_SIZE) - jbsr m68k_fork - addql #4,%sp - RESTORE_SWITCH_STACK - rts - -ENTRY(sys_clone) - SAVE_SWITCH_STACK - pea %sp@(SWITCH_STACK_SIZE) - jbsr m68k_clone - addql #4,%sp - RESTORE_SWITCH_STACK - rts - -ENTRY(sys_vfork) - SAVE_SWITCH_STACK - pea %sp@(SWITCH_STACK_SIZE) - jbsr m68k_vfork - addql #4,%sp - RESTORE_SWITCH_STACK - rts - -ENTRY(sys_sigreturn) - SAVE_SWITCH_STACK - jbsr do_sigreturn - RESTORE_SWITCH_STACK - rts - -ENTRY(sys_rt_sigreturn) - SAVE_SWITCH_STACK - jbsr do_rt_sigreturn - RESTORE_SWITCH_STACK - rts - -resume: - /* - * Beware - when entering resume, prev (the current task) is - * in a0, next (the new task) is in a1,so don't change these - * registers until their contents are no longer needed. - */ - - /* save sr */ - movew %sr,%a0@(TASK_THREAD+THREAD_SR) - - /* save fs (sfc,%dfc) (may be pointing to kernel memory) */ - movec %sfc,%d0 - movew %d0,%a0@(TASK_THREAD+THREAD_FS) - - /* save usp */ - /* it is better to use a movel here instead of a movew 8*) */ - movec %usp,%d0 - movel %d0,%a0@(TASK_THREAD+THREAD_USP) - - /* save non-scratch registers on stack */ - SAVE_SWITCH_STACK - - /* save current kernel stack pointer */ - movel %sp,%a0@(TASK_THREAD+THREAD_KSP) - - /* save floating point context */ -#ifndef CONFIG_M68KFPU_EMU_ONLY -#ifdef CONFIG_M68KFPU_EMU - tstl m68k_fputype - jeq 3f -#endif - fsave %a0@(TASK_THREAD+THREAD_FPSTATE) - -#if defined(CONFIG_M68060) -#if !defined(CPU_M68060_ONLY) - btst #3,m68k_cputype+3 - beqs 1f -#endif - /* The 060 FPU keeps status in bits 15-8 of the first longword */ - tstb %a0@(TASK_THREAD+THREAD_FPSTATE+2) - jeq 3f -#if !defined(CPU_M68060_ONLY) - jra 2f -#endif -#endif /* CONFIG_M68060 */ -#if !defined(CPU_M68060_ONLY) -1: tstb %a0@(TASK_THREAD+THREAD_FPSTATE) - jeq 3f -#endif -2: fmovemx %fp0-%fp7,%a0@(TASK_THREAD+THREAD_FPREG) - fmoveml %fpcr/%fpsr/%fpiar,%a0@(TASK_THREAD+THREAD_FPCNTL) -3: -#endif /* CONFIG_M68KFPU_EMU_ONLY */ - /* Return previous task in %d1 */ - movel %curptr,%d1 - - /* switch to new task (a1 contains new task) */ - movel %a1,%curptr - - /* restore floating point context */ -#ifndef CONFIG_M68KFPU_EMU_ONLY -#ifdef CONFIG_M68KFPU_EMU - tstl m68k_fputype - jeq 4f -#endif -#if defined(CONFIG_M68060) -#if !defined(CPU_M68060_ONLY) - btst #3,m68k_cputype+3 - beqs 1f -#endif - /* The 060 FPU keeps status in bits 15-8 of the first longword */ - tstb %a1@(TASK_THREAD+THREAD_FPSTATE+2) - jeq 3f -#if !defined(CPU_M68060_ONLY) - jra 2f -#endif -#endif /* CONFIG_M68060 */ -#if !defined(CPU_M68060_ONLY) -1: tstb %a1@(TASK_THREAD+THREAD_FPSTATE) - jeq 3f -#endif -2: fmovemx %a1@(TASK_THREAD+THREAD_FPREG),%fp0-%fp7 - fmoveml %a1@(TASK_THREAD+THREAD_FPCNTL),%fpcr/%fpsr/%fpiar -3: frestore %a1@(TASK_THREAD+THREAD_FPSTATE) -4: -#endif /* CONFIG_M68KFPU_EMU_ONLY */ - - /* restore the kernel stack pointer */ - movel %a1@(TASK_THREAD+THREAD_KSP),%sp - - /* restore non-scratch registers */ - RESTORE_SWITCH_STACK - - /* restore user stack pointer */ - movel %a1@(TASK_THREAD+THREAD_USP),%a0 - movel %a0,%usp - - /* restore fs (sfc,%dfc) */ - movew %a1@(TASK_THREAD+THREAD_FS),%a0 - movec %a0,%sfc - movec %a0,%dfc - - /* restore status register */ - movew %a1@(TASK_THREAD+THREAD_SR),%sr - - rts - diff --git a/arch/m68k/kernel/entry_no.S b/arch/m68k/kernel/entry_no.S deleted file mode 100644 index d80cba4..0000000 --- a/arch/m68k/kernel/entry_no.S +++ /dev/null @@ -1,130 +0,0 @@ -/* - * linux/arch/m68knommu/kernel/entry.S - * - * Copyright (C) 1999-2002, Greg Ungerer (gerg@snapgear.com) - * Copyright (C) 1998 D. Jeff Dionne <jeff@lineo.ca>, - * Kenneth Albanowski <kjahds@kjahds.com>, - * Copyright (C) 2000 Lineo Inc. (www.lineo.com) - * - * Based on: - * - * linux/arch/m68k/kernel/entry.S - * - * Copyright (C) 1991, 1992 Linus Torvalds - * - * This file is subject to the terms and conditions of the GNU General Public - * License. See the file README.legal in the main directory of this archive - * for more details. - * - * Linux/m68k support by Hamish Macdonald - * - * 68060 fixes by Jesper Skov - * ColdFire support by Greg Ungerer (gerg@snapgear.com) - * 5307 fixes by David W. Miller - * linux 2.4 support David McCullough <davidm@snapgear.com> - */ - -#include <linux/linkage.h> -#include <asm/errno.h> -#include <asm/setup.h> -#include <asm/segment.h> -#include <asm/asm-offsets.h> -#include <asm/entry.h> -#include <asm/unistd.h> - -.text - -.globl buserr -.globl trap -.globl ret_from_exception -.globl ret_from_signal -.globl sys_fork -.globl sys_clone -.globl sys_vfork - -ENTRY(buserr) - SAVE_ALL_INT - GET_CURRENT(%d0) - movel %sp,%sp@- /* stack frame pointer argument */ - jsr buserr_c - addql #4,%sp - jra ret_from_exception - -ENTRY(trap) - SAVE_ALL_INT - GET_CURRENT(%d0) - movel %sp,%sp@- /* stack frame pointer argument */ - jsr trap_c - addql #4,%sp - jra ret_from_exception - -#ifdef TRAP_DBG_INTERRUPT - -.globl dbginterrupt -ENTRY(dbginterrupt) - SAVE_ALL_INT - GET_CURRENT(%d0) - movel %sp,%sp@- /* stack frame pointer argument */ - jsr dbginterrupt_c - addql #4,%sp - jra ret_from_exception -#endif - -ENTRY(reschedule) - /* save top of frame */ - pea %sp@ - jbsr set_esp0 - addql #4,%sp - pea ret_from_exception - jmp schedule - -ENTRY(ret_from_fork) - movel %d1,%sp@- - jsr schedule_tail - addql #4,%sp - jra ret_from_exception - -ENTRY(sys_fork) - SAVE_SWITCH_STACK - pea %sp@(SWITCH_STACK_SIZE) - jbsr m68k_fork - addql #4,%sp - RESTORE_SWITCH_STACK - rts - -ENTRY(sys_vfork) - SAVE_SWITCH_STACK - pea %sp@(SWITCH_STACK_SIZE) - jbsr m68k_vfork - addql #4,%sp - RESTORE_SWITCH_STACK - rts - -ENTRY(sys_clone) - SAVE_SWITCH_STACK - pea %sp@(SWITCH_STACK_SIZE) - jbsr m68k_clone - addql #4,%sp - RESTORE_SWITCH_STACK - rts - -ENTRY(sys_sigreturn) - SAVE_SWITCH_STACK - jbsr do_sigreturn - RESTORE_SWITCH_STACK - rts - -ENTRY(sys_rt_sigreturn) - SAVE_SWITCH_STACK - jbsr do_rt_sigreturn - RESTORE_SWITCH_STACK - rts - -ENTRY(ret_from_user_signal) - moveq #__NR_sigreturn,%d0 - trap #0 - -ENTRY(ret_from_user_rt_signal) - movel #__NR_rt_sigreturn,%d0 - trap #0 - diff --git a/arch/m68k/kernel/pcibios.c b/arch/m68k/kernel/pcibios.c new file mode 100644 index 0000000..b2988aa --- /dev/null +++ b/arch/m68k/kernel/pcibios.c @@ -0,0 +1,109 @@ +/* + * pci.c -- basic PCI support code + * + * 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. + * + * (C) Copyright 2011, Greg Ungerer <gerg@uclinux.org> + */ + +#include <linux/kernel.h> +#include <linux/types.h> +#include <linux/mm.h> +#include <linux/init.h> +#include <linux/pci.h> + +/* + * From arch/i386/kernel/pci-i386.c: + * + * We need to avoid collisions with `mirrored' VGA ports + * and other strange ISA hardware, so we always want the + * addresses to be allocated in the 0x000-0x0ff region + * modulo 0x400. + * + * Why? Because some silly external IO cards only decode + * the low 10 bits of the IO address. The 0x00-0xff region + * is reserved for motherboard devices that decode all 16 + * bits, so it's ok to allocate at, say, 0x2800-0x28ff, + * but we want to try to avoid allocating at 0x2900-0x2bff + * which might be mirrored at 0x0100-0x03ff.. + */ +resource_size_t pcibios_align_resource(void *data, const struct resource *res, + resource_size_t size, resource_size_t align) +{ + resource_size_t start = res->start; + + if ((res->flags & IORESOURCE_IO) && (start & 0x300)) + start = (start + 0x3ff) & ~0x3ff; + + start = (start + align - 1) & ~(align - 1); + + return start; +} + +/* + * This is taken from the ARM code for this. + */ +int pcibios_enable_device(struct pci_dev *dev, int mask) +{ + struct resource *r; + u16 cmd, newcmd; + int idx; + + pci_read_config_word(dev, PCI_COMMAND, &cmd); + newcmd = cmd; + + for (idx = 0; idx < 6; idx++) { + /* Only set up the requested stuff */ + if (!(mask & (1 << idx))) + continue; + + r = dev->resource + idx; + if (!r->start && r->end) { + pr_err(KERN_ERR "PCI: Device %s not available because of resource collisions\n", + pci_name(dev)); + return -EINVAL; + } + if (r->flags & IORESOURCE_IO) + newcmd |= PCI_COMMAND_IO; + if (r->flags & IORESOURCE_MEM) + newcmd |= PCI_COMMAND_MEMORY; + } + + /* + * Bridges (eg, cardbus bridges) need to be fully enabled + */ + if ((dev->class >> 16) == PCI_BASE_CLASS_BRIDGE) + newcmd |= PCI_COMMAND_IO | PCI_COMMAND_MEMORY; + + + if (newcmd != cmd) { + pr_info("PCI: enabling device %s (0x%04x -> 0x%04x)\n", + pci_name(dev), cmd, newcmd); + pci_write_config_word(dev, PCI_COMMAND, newcmd); + } + return 0; +} + +void pcibios_update_irq(struct pci_dev *dev, int irq) +{ + pci_write_config_byte(dev, PCI_INTERRUPT_LINE, irq); +} + +void __devinit pcibios_fixup_bus(struct pci_bus *bus) +{ + struct pci_dev *dev; + + list_for_each_entry(dev, &bus->devices, bus_list) { + pci_write_config_byte(dev, PCI_CACHE_LINE_SIZE, 8); + pci_write_config_byte(dev, PCI_LATENCY_TIMER, 32); + } +} + +char __devinit *pcibios_setup(char *str) +{ + return str; +} + diff --git a/arch/m68k/mm/memory.c b/arch/m68k/mm/memory.c index 250b8b7..51bc9d25 100644 --- a/arch/m68k/mm/memory.c +++ b/arch/m68k/mm/memory.c @@ -203,7 +203,7 @@ static inline void pushcl040(unsigned long paddr) void cache_clear (unsigned long paddr, int len) { if (CPU_IS_COLDFIRE) { - flush_cf_bcache(0, DCACHE_MAX_ADDR); + clear_cf_bcache(0, DCACHE_MAX_ADDR); } else if (CPU_IS_040_OR_060) { int tmp; diff --git a/arch/m68k/platform/coldfire/Makefile b/arch/m68k/platform/coldfire/Makefile index 76d389d..02591a10 100644 --- a/arch/m68k/platform/coldfire/Makefile +++ b/arch/m68k/platform/coldfire/Makefile @@ -20,6 +20,7 @@ obj-$(CONFIG_M5206e) += m5206.o timers.o intc.o reset.o obj-$(CONFIG_M520x) += m520x.o pit.o intc-simr.o reset.o obj-$(CONFIG_M523x) += m523x.o pit.o dma_timer.o intc-2.o reset.o obj-$(CONFIG_M5249) += m5249.o timers.o intc.o intc-5249.o reset.o +obj-$(CONFIG_M525x) += m525x.o timers.o intc.o intc-525x.o reset.o obj-$(CONFIG_M527x) += m527x.o pit.o intc-2.o reset.o obj-$(CONFIG_M5272) += m5272.o intc-5272.o timers.o obj-$(CONFIG_M528x) += m528x.o pit.o intc-2.o reset.o @@ -27,10 +28,14 @@ obj-$(CONFIG_M5307) += m5307.o timers.o intc.o reset.o obj-$(CONFIG_M532x) += m532x.o timers.o intc-simr.o reset.o obj-$(CONFIG_M5407) += m5407.o timers.o intc.o reset.o obj-$(CONFIG_M54xx) += m54xx.o sltimers.o intc-2.o +obj-$(CONFIG_M5441x) += m5441x.o pit.o intc-simr.o reset.o obj-$(CONFIG_NETtel) += nettel.o obj-$(CONFIG_CLEOPATRA) += nettel.o obj-$(CONFIG_FIREBEE) += firebee.o +obj-$(CONFIG_MCF8390) += mcf8390.o -obj-y += pinmux.o gpio.o +obj-$(CONFIG_PCI) += pci.o + +obj-y += gpio.o extra-y := head.o diff --git a/arch/m68k/platform/coldfire/clk.c b/arch/m68k/platform/coldfire/clk.c index 44da406..75f9ee9 100644 --- a/arch/m68k/platform/coldfire/clk.c +++ b/arch/m68k/platform/coldfire/clk.c @@ -10,11 +10,17 @@ #include <linux/kernel.h> #include <linux/module.h> +#include <linux/platform_device.h> +#include <linux/mutex.h> #include <linux/clk.h> +#include <linux/io.h> +#include <linux/err.h> #include <asm/coldfire.h> +#include <asm/mcfsim.h> +#include <asm/mcfclk.h> /***************************************************************************/ - +#ifndef MCFPM_PPMCR0 struct clk *clk_get(struct device *dev, const char *id) { return NULL; @@ -42,11 +48,107 @@ unsigned long clk_get_rate(struct clk *clk) return MCF_CLK; } EXPORT_SYMBOL(clk_get_rate); +#else +static DEFINE_SPINLOCK(clk_lock); + +struct clk *clk_get(struct device *dev, const char *id) +{ + const char *clk_name = dev ? dev_name(dev) : id ? id : NULL; + struct clk *clk; + unsigned i; + + for (i = 0; (clk = mcf_clks[i]) != NULL; ++i) + if (!strcmp(clk->name, clk_name)) + return clk; + pr_warn("clk_get: didn't find clock %s\n", clk_name); + return ERR_PTR(-ENOENT); +} +EXPORT_SYMBOL(clk_get); + +int clk_enable(struct clk *clk) +{ + unsigned long flags; + spin_lock_irqsave(&clk_lock, flags); + if ((clk->enabled++ == 0) && clk->clk_ops) + clk->clk_ops->enable(clk); + spin_unlock_irqrestore(&clk_lock, flags); + + return 0; +} +EXPORT_SYMBOL(clk_enable); + +void clk_disable(struct clk *clk) +{ + unsigned long flags; + spin_lock_irqsave(&clk_lock, flags); + if ((--clk->enabled == 0) && clk->clk_ops) + clk->clk_ops->disable(clk); + spin_unlock_irqrestore(&clk_lock, flags); +} +EXPORT_SYMBOL(clk_disable); + +void clk_put(struct clk *clk) +{ + if (clk->enabled != 0) + pr_warn("clk_put %s still enabled\n", clk->name); +} +EXPORT_SYMBOL(clk_put); + +unsigned long clk_get_rate(struct clk *clk) +{ + return clk->rate; +} +EXPORT_SYMBOL(clk_get_rate); + +/***************************************************************************/ + +void __clk_init_enabled(struct clk *clk) +{ + clk->enabled = 1; + clk->clk_ops->enable(clk); +} + +void __clk_init_disabled(struct clk *clk) +{ + clk->enabled = 0; + clk->clk_ops->disable(clk); +} + +static void __clk_enable0(struct clk *clk) +{ + __raw_writeb(clk->slot, MCFPM_PPMCR0); +} + +static void __clk_disable0(struct clk *clk) +{ + __raw_writeb(clk->slot, MCFPM_PPMSR0); +} + +struct clk_ops clk_ops0 = { + .enable = __clk_enable0, + .disable = __clk_disable0, +}; + +#ifdef MCFPM_PPMCR1 +static void __clk_enable1(struct clk *clk) +{ + __raw_writeb(clk->slot, MCFPM_PPMCR1); +} + +static void __clk_disable1(struct clk *clk) +{ + __raw_writeb(clk->slot, MCFPM_PPMSR1); +} + +struct clk_ops clk_ops1 = { + .enable = __clk_enable1, + .disable = __clk_disable1, +}; +#endif /* MCFPM_PPMCR1 */ +#endif /* MCFPM_PPMCR0 */ struct clk *devm_clk_get(struct device *dev, const char *id) { return NULL; } EXPORT_SYMBOL(devm_clk_get); - -/***************************************************************************/ diff --git a/arch/m68k/platform/coldfire/device.c b/arch/m68k/platform/coldfire/device.c index 3aa77dd..81f0fb5 100644 --- a/arch/m68k/platform/coldfire/device.c +++ b/arch/m68k/platform/coldfire/device.c @@ -13,6 +13,7 @@ #include <linux/io.h> #include <linux/spi/spi.h> #include <linux/gpio.h> +#include <linux/fec.h> #include <asm/traps.h> #include <asm/coldfire.h> #include <asm/mcfsim.h> @@ -20,7 +21,7 @@ #include <asm/mcfqspi.h> /* - * All current ColdFire parts contain from 2, 3 or 4 UARTS. + * All current ColdFire parts contain from 2, 3, 4 or 10 UARTS. */ static struct mcf_platform_uart mcf_uart_platform_data[] = { { @@ -43,6 +44,42 @@ static struct mcf_platform_uart mcf_uart_platform_data[] = { .irq = MCF_IRQ_UART3, }, #endif +#ifdef MCFUART_BASE4 + { + .mapbase = MCFUART_BASE4, + .irq = MCF_IRQ_UART4, + }, +#endif +#ifdef MCFUART_BASE5 + { + .mapbase = MCFUART_BASE5, + .irq = MCF_IRQ_UART5, + }, +#endif +#ifdef MCFUART_BASE6 + { + .mapbase = MCFUART_BASE6, + .irq = MCF_IRQ_UART6, + }, +#endif +#ifdef MCFUART_BASE7 + { + .mapbase = MCFUART_BASE7, + .irq = MCF_IRQ_UART7, + }, +#endif +#ifdef MCFUART_BASE8 + { + .mapbase = MCFUART_BASE8, + .irq = MCF_IRQ_UART8, + }, +#endif +#ifdef MCFUART_BASE9 + { + .mapbase = MCFUART_BASE9, + .irq = MCF_IRQ_UART9, + }, +#endif { }, }; @@ -53,6 +90,18 @@ static struct platform_device mcf_uart = { }; #ifdef CONFIG_FEC + +#ifdef CONFIG_M5441x +#define FEC_NAME "enet-fec" +static struct fec_platform_data fec_pdata = { + .phy = PHY_INTERFACE_MODE_RMII, +}; +#define FEC_PDATA (&fec_pdata) +#else +#define FEC_NAME "fec" +#define FEC_PDATA NULL +#endif + /* * Some ColdFire cores contain the Fast Ethernet Controller (FEC) * block. It is Freescale's own hardware block. Some ColdFires @@ -82,10 +131,11 @@ static struct resource mcf_fec0_resources[] = { }; static struct platform_device mcf_fec0 = { - .name = "fec", + .name = FEC_NAME, .id = 0, .num_resources = ARRAY_SIZE(mcf_fec0_resources), .resource = mcf_fec0_resources, + .dev.platform_data = FEC_PDATA, }; #ifdef MCFFEC_BASE1 @@ -113,10 +163,11 @@ static struct resource mcf_fec1_resources[] = { }; static struct platform_device mcf_fec1 = { - .name = "fec", + .name = FEC_NAME, .id = 1, .num_resources = ARRAY_SIZE(mcf_fec1_resources), .resource = mcf_fec1_resources, + .dev.platform_data = FEC_PDATA, }; #endif /* MCFFEC_BASE1 */ #endif /* CONFIG_FEC */ diff --git a/arch/m68k/platform/coldfire/gpio.c b/arch/m68k/platform/coldfire/gpio.c index 4c8c424..9cd2b5c 100644 --- a/arch/m68k/platform/coldfire/gpio.c +++ b/arch/m68k/platform/coldfire/gpio.c @@ -14,119 +14,161 @@ */ #include <linux/kernel.h> +#include <linux/module.h> #include <linux/init.h> #include <linux/device.h> -#include <asm/gpio.h> -#include <asm/pinmux.h> +#include <linux/io.h> +#include <asm/coldfire.h> +#include <asm/mcfsim.h> #include <asm/mcfgpio.h> -#define MCF_CHIP(chip) container_of(chip, struct mcf_gpio_chip, gpio_chip) +int __mcfgpio_get_value(unsigned gpio) +{ + return mcfgpio_read(__mcfgpio_ppdr(gpio)) & mcfgpio_bit(gpio); +} +EXPORT_SYMBOL(__mcfgpio_get_value); + +void __mcfgpio_set_value(unsigned gpio, int value) +{ + if (gpio < MCFGPIO_SCR_START) { + unsigned long flags; + MCFGPIO_PORTTYPE data; + + local_irq_save(flags); + data = mcfgpio_read(__mcfgpio_podr(gpio)); + if (value) + data |= mcfgpio_bit(gpio); + else + data &= ~mcfgpio_bit(gpio); + mcfgpio_write(data, __mcfgpio_podr(gpio)); + local_irq_restore(flags); + } else { + if (value) + mcfgpio_write(mcfgpio_bit(gpio), + MCFGPIO_SETR_PORT(gpio)); + else + mcfgpio_write(~mcfgpio_bit(gpio), + MCFGPIO_CLRR_PORT(gpio)); + } +} +EXPORT_SYMBOL(__mcfgpio_set_value); -int mcf_gpio_direction_input(struct gpio_chip *chip, unsigned offset) +int __mcfgpio_direction_input(unsigned gpio) { unsigned long flags; MCFGPIO_PORTTYPE dir; - struct mcf_gpio_chip *mcf_chip = MCF_CHIP(chip); local_irq_save(flags); - dir = mcfgpio_read(mcf_chip->pddr); - dir &= ~mcfgpio_bit(chip->base + offset); - mcfgpio_write(dir, mcf_chip->pddr); + dir = mcfgpio_read(__mcfgpio_pddr(gpio)); + dir &= ~mcfgpio_bit(gpio); + mcfgpio_write(dir, __mcfgpio_pddr(gpio)); local_irq_restore(flags); return 0; } +EXPORT_SYMBOL(__mcfgpio_direction_input); -int mcf_gpio_get_value(struct gpio_chip *chip, unsigned offset) -{ - struct mcf_gpio_chip *mcf_chip = MCF_CHIP(chip); - - return mcfgpio_read(mcf_chip->ppdr) & mcfgpio_bit(chip->base + offset); -} - -int mcf_gpio_direction_output(struct gpio_chip *chip, unsigned offset, - int value) +int __mcfgpio_direction_output(unsigned gpio, int value) { unsigned long flags; MCFGPIO_PORTTYPE data; - struct mcf_gpio_chip *mcf_chip = MCF_CHIP(chip); local_irq_save(flags); - /* write the value to the output latch */ - data = mcfgpio_read(mcf_chip->podr); + data = mcfgpio_read(__mcfgpio_pddr(gpio)); if (value) - data |= mcfgpio_bit(chip->base + offset); + data |= mcfgpio_bit(gpio); else - data &= ~mcfgpio_bit(chip->base + offset); - mcfgpio_write(data, mcf_chip->podr); - - /* now set the direction to output */ - data = mcfgpio_read(mcf_chip->pddr); - data |= mcfgpio_bit(chip->base + offset); - mcfgpio_write(data, mcf_chip->pddr); + data &= mcfgpio_bit(gpio); + mcfgpio_write(data, __mcfgpio_pddr(gpio)); + + /* now set the data to output */ + if (gpio < MCFGPIO_SCR_START) { + data = mcfgpio_read(__mcfgpio_podr(gpio)); + if (value) + data |= mcfgpio_bit(gpio); + else + data &= ~mcfgpio_bit(gpio); + mcfgpio_write(data, __mcfgpio_podr(gpio)); + } else { + if (value) + mcfgpio_write(mcfgpio_bit(gpio), + MCFGPIO_SETR_PORT(gpio)); + else + mcfgpio_write(~mcfgpio_bit(gpio), + MCFGPIO_CLRR_PORT(gpio)); + } local_irq_restore(flags); + return 0; +} +EXPORT_SYMBOL(__mcfgpio_direction_output); +int __mcfgpio_request(unsigned gpio) +{ return 0; } +EXPORT_SYMBOL(__mcfgpio_request); -void mcf_gpio_set_value(struct gpio_chip *chip, unsigned offset, int value) +void __mcfgpio_free(unsigned gpio) { - struct mcf_gpio_chip *mcf_chip = MCF_CHIP(chip); + __mcfgpio_direction_input(gpio); +} +EXPORT_SYMBOL(__mcfgpio_free); - unsigned long flags; - MCFGPIO_PORTTYPE data; +#ifdef CONFIG_GPIOLIB - local_irq_save(flags); - data = mcfgpio_read(mcf_chip->podr); - if (value) - data |= mcfgpio_bit(chip->base + offset); - else - data &= ~mcfgpio_bit(chip->base + offset); - mcfgpio_write(data, mcf_chip->podr); - local_irq_restore(flags); +int mcfgpio_direction_input(struct gpio_chip *chip, unsigned offset) +{ + return __mcfgpio_direction_input(offset); } -void mcf_gpio_set_value_fast(struct gpio_chip *chip, unsigned offset, int value) +int mcfgpio_get_value(struct gpio_chip *chip, unsigned offset) { - struct mcf_gpio_chip *mcf_chip = MCF_CHIP(chip); - - if (value) - mcfgpio_write(mcfgpio_bit(chip->base + offset), mcf_chip->setr); - else - mcfgpio_write(~mcfgpio_bit(chip->base + offset), mcf_chip->clrr); + return __mcfgpio_get_value(offset); } -int mcf_gpio_request(struct gpio_chip *chip, unsigned offset) +int mcfgpio_direction_output(struct gpio_chip *chip, unsigned offset, int value) { - struct mcf_gpio_chip *mcf_chip = MCF_CHIP(chip); - - return mcf_chip->gpio_to_pinmux ? - mcf_pinmux_request(mcf_chip->gpio_to_pinmux[offset], 0) : 0; + return __mcfgpio_direction_output(offset, value); } -void mcf_gpio_free(struct gpio_chip *chip, unsigned offset) +void mcfgpio_set_value(struct gpio_chip *chip, unsigned offset, int value) { - struct mcf_gpio_chip *mcf_chip = MCF_CHIP(chip); + __mcfgpio_set_value(offset, value); +} - mcf_gpio_direction_input(chip, offset); +int mcfgpio_request(struct gpio_chip *chip, unsigned offset) +{ + return __mcfgpio_request(offset); +} - if (mcf_chip->gpio_to_pinmux) - mcf_pinmux_release(mcf_chip->gpio_to_pinmux[offset], 0); +void mcfgpio_free(struct gpio_chip *chip, unsigned offset) +{ + __mcfgpio_free(offset); } -struct bus_type mcf_gpio_subsys = { +struct bus_type mcfgpio_subsys = { .name = "gpio", .dev_name = "gpio", }; -static int __init mcf_gpio_sysinit(void) -{ - unsigned int i = 0; +static struct gpio_chip mcfgpio_chip = { + .label = "mcfgpio", + .request = mcfgpio_request, + .free = mcfgpio_free, + .direction_input = mcfgpio_direction_input, + .direction_output = mcfgpio_direction_output, + .get = mcfgpio_get_value, + .set = mcfgpio_set_value, + .base = 0, + .ngpio = MCFGPIO_PIN_MAX, +}; - while (i < mcf_gpio_chips_size) - gpiochip_add((struct gpio_chip *)&mcf_gpio_chips[i++]); - return subsys_system_register(&mcf_gpio_subsys, NULL); +static int __init mcfgpio_sysinit(void) +{ + gpiochip_add(&mcfgpio_chip); + return subsys_system_register(&mcfgpio_subsys, NULL); } -core_initcall(mcf_gpio_sysinit); +core_initcall(mcfgpio_sysinit); +#endif diff --git a/arch/m68k/platform/coldfire/head.S b/arch/m68k/platform/coldfire/head.S index c3db70e..4e0c9eb 100644 --- a/arch/m68k/platform/coldfire/head.S +++ b/arch/m68k/platform/coldfire/head.S @@ -31,9 +31,9 @@ .endm #elif defined(CONFIG_M5206) || defined(CONFIG_M5206e) || \ - defined(CONFIG_M5249) || defined(CONFIG_M527x) || \ - defined(CONFIG_M528x) || defined(CONFIG_M5307) || \ - defined(CONFIG_M5407) + defined(CONFIG_M5249) || defined(CONFIG_M525x) || \ + defined(CONFIG_M527x) || defined(CONFIG_M528x) || \ + defined(CONFIG_M5307) || defined(CONFIG_M5407) /* * Not all these devices have exactly the same DRAM controller, * but the DCMR register is virtually identical - give or take diff --git a/arch/m68k/platform/coldfire/intc-525x.c b/arch/m68k/platform/coldfire/intc-525x.c new file mode 100644 index 0000000..b23204d --- /dev/null +++ b/arch/m68k/platform/coldfire/intc-525x.c @@ -0,0 +1,91 @@ +/* + * intc2.c -- support for the 2nd INTC controller of the 525x + * + * (C) Copyright 2012, Steven King <sfking@fdwdc.com> + * (C) Copyright 2009, Greg Ungerer <gerg@snapgear.com> + * + * This file is subject to the terms and conditions of the GNU General Public + * License. See the file COPYING in the main directory of this archive + * for more details. + */ + +#include <linux/types.h> +#include <linux/init.h> +#include <linux/kernel.h> +#include <linux/interrupt.h> +#include <linux/irq.h> +#include <linux/io.h> +#include <asm/coldfire.h> +#include <asm/mcfsim.h> + +static void intc2_irq_gpio_mask(struct irq_data *d) +{ + u32 imr = readl(MCFSIM2_GPIOINTENABLE); + u32 type = irqd_get_trigger_type(d); + int irq = d->irq - MCF_IRQ_GPIO0; + + if (type & IRQ_TYPE_EDGE_RISING) + imr &= ~(0x001 << irq); + if (type & IRQ_TYPE_EDGE_FALLING) + imr &= ~(0x100 << irq); + writel(imr, MCFSIM2_GPIOINTENABLE); +} + +static void intc2_irq_gpio_unmask(struct irq_data *d) +{ + u32 imr = readl(MCFSIM2_GPIOINTENABLE); + u32 type = irqd_get_trigger_type(d); + int irq = d->irq - MCF_IRQ_GPIO0; + + if (type & IRQ_TYPE_EDGE_RISING) + imr |= (0x001 << irq); + if (type & IRQ_TYPE_EDGE_FALLING) + imr |= (0x100 << irq); + writel(imr, MCFSIM2_GPIOINTENABLE); +} + +static void intc2_irq_gpio_ack(struct irq_data *d) +{ + u32 imr = 0; + u32 type = irqd_get_trigger_type(d); + int irq = d->irq - MCF_IRQ_GPIO0; + + if (type & IRQ_TYPE_EDGE_RISING) + imr |= (0x001 << irq); + if (type & IRQ_TYPE_EDGE_FALLING) + imr |= (0x100 << irq); + writel(imr, MCFSIM2_GPIOINTCLEAR); +} + +static int intc2_irq_gpio_set_type(struct irq_data *d, unsigned int f) +{ + if (f & ~IRQ_TYPE_EDGE_BOTH) + return -EINVAL; + return 0; +} + +static struct irq_chip intc2_irq_gpio_chip = { + .name = "CF-INTC2", + .irq_mask = intc2_irq_gpio_mask, + .irq_unmask = intc2_irq_gpio_unmask, + .irq_ack = intc2_irq_gpio_ack, + .irq_set_type = intc2_irq_gpio_set_type, +}; + +static int __init mcf_intc2_init(void) +{ + int irq; + + /* set the interrupt base for the second interrupt controller */ + writel(MCFINTC2_VECBASE, MCFINTC2_INTBASE); + + /* GPIO interrupt sources */ + for (irq = MCF_IRQ_GPIO0; (irq <= MCF_IRQ_GPIO6); irq++) { + irq_set_chip(irq, &intc2_irq_gpio_chip); + irq_set_handler(irq, handle_edge_irq); + } + + return 0; +} + +arch_initcall(mcf_intc2_init); diff --git a/arch/m68k/platform/coldfire/intc-simr.c b/arch/m68k/platform/coldfire/intc-simr.c index 650d52e..7cf2c15 100644 --- a/arch/m68k/platform/coldfire/intc-simr.c +++ b/arch/m68k/platform/coldfire/intc-simr.c @@ -59,16 +59,18 @@ static unsigned int inline irq2ebit(unsigned int irq) #endif /* - * There maybe one or two interrupt control units, each has 64 - * interrupts. If there is no second unit then MCFINTC1_* defines - * will be 0 (and code for them optimized away). + * There maybe one, two or three interrupt control units, each has 64 + * interrupts. If there is no second or third unit then MCFINTC1_* or + * MCFINTC2_* defines will be 0 (and code for them optimized away). */ static void intc_irq_mask(struct irq_data *d) { unsigned int irq = d->irq - MCFINT_VECBASE; - if (MCFINTC1_SIMR && (irq > 64)) + if (MCFINTC2_SIMR && (irq > 128)) + __raw_writeb(irq - 128, MCFINTC2_SIMR); + else if (MCFINTC1_SIMR && (irq > 64)) __raw_writeb(irq - 64, MCFINTC1_SIMR); else __raw_writeb(irq, MCFINTC0_SIMR); @@ -78,7 +80,9 @@ static void intc_irq_unmask(struct irq_data *d) { unsigned int irq = d->irq - MCFINT_VECBASE; - if (MCFINTC1_CIMR && (irq > 64)) + if (MCFINTC2_CIMR && (irq > 128)) + __raw_writeb(irq - 128, MCFINTC2_CIMR); + else if (MCFINTC1_CIMR && (irq > 64)) __raw_writeb(irq - 64, MCFINTC1_CIMR); else __raw_writeb(irq, MCFINTC0_CIMR); @@ -99,9 +103,11 @@ static unsigned int intc_irq_startup(struct irq_data *d) unsigned int ebit = irq2ebit(irq); u8 v; +#if defined(MCFEPORT_EPDDR) /* Set EPORT line as input */ v = __raw_readb(MCFEPORT_EPDDR); __raw_writeb(v & ~(0x1 << ebit), MCFEPORT_EPDDR); +#endif /* Set EPORT line as interrupt source */ v = __raw_readb(MCFEPORT_EPIER); @@ -109,12 +115,13 @@ static unsigned int intc_irq_startup(struct irq_data *d) } irq -= MCFINT_VECBASE; - if (MCFINTC1_ICR0 && (irq > 64)) + if (MCFINTC2_ICR0 && (irq > 128)) + __raw_writeb(5, MCFINTC2_ICR0 + irq - 128); + else if (MCFINTC1_ICR0 && (irq > 64)) __raw_writeb(5, MCFINTC1_ICR0 + irq - 64); else __raw_writeb(5, MCFINTC0_ICR0 + irq); - intc_irq_unmask(d); return 0; } @@ -175,8 +182,11 @@ void __init init_IRQ(void) __raw_writeb(0xff, MCFINTC0_SIMR); if (MCFINTC1_SIMR) __raw_writeb(0xff, MCFINTC1_SIMR); + if (MCFINTC2_SIMR) + __raw_writeb(0xff, MCFINTC2_SIMR); - eirq = MCFINT_VECBASE + 64 + (MCFINTC1_ICR0 ? 64 : 0); + eirq = MCFINT_VECBASE + 64 + (MCFINTC1_ICR0 ? 64 : 0) + + (MCFINTC2_ICR0 ? 64 : 0); for (irq = MCFINT_VECBASE; (irq < eirq); irq++) { if ((irq >= EINT1) && (irq <= EINT7)) irq_set_chip(irq, &intc_irq_chip_edge_port); diff --git a/arch/m68k/platform/coldfire/m5206.c b/arch/m68k/platform/coldfire/m5206.c index a8b81df..6bfbeeb 100644 --- a/arch/m68k/platform/coldfire/m5206.c +++ b/arch/m68k/platform/coldfire/m5206.c @@ -16,15 +16,6 @@ #include <asm/machdep.h> #include <asm/coldfire.h> #include <asm/mcfsim.h> -#include <asm/mcfgpio.h> - -/***************************************************************************/ - -struct mcf_gpio_chip mcf_gpio_chips[] = { - MCFGPS(PP, 0, 8, MCFSIM_PADDR, MCFSIM_PADAT, MCFSIM_PADAT), -}; - -unsigned int mcf_gpio_chips_size = ARRAY_SIZE(mcf_gpio_chips); /***************************************************************************/ diff --git a/arch/m68k/platform/coldfire/m520x.c b/arch/m68k/platform/coldfire/m520x.c index 3264b88..ea1be0e 100644 --- a/arch/m68k/platform/coldfire/m520x.c +++ b/arch/m68k/platform/coldfire/m520x.c @@ -19,22 +19,102 @@ #include <asm/coldfire.h> #include <asm/mcfsim.h> #include <asm/mcfuart.h> -#include <asm/mcfgpio.h> +#include <asm/mcfclk.h> /***************************************************************************/ -struct mcf_gpio_chip mcf_gpio_chips[] = { - MCFGPS(PIRQ, 0, 8, MCFEPORT_EPDDR, MCFEPORT_EPDR, MCFEPORT_EPPDR), - MCFGPF(CS, 9, 3), - MCFGPF(FECI2C, 16, 4), - MCFGPF(QSPI, 24, 4), - MCFGPF(TIMER, 32, 4), - MCFGPF(UART, 40, 8), - MCFGPF(FECH, 48, 8), - MCFGPF(FECL, 56, 8), +DEFINE_CLK(0, "flexbus", 2, MCF_CLK); +DEFINE_CLK(0, "fec.0", 12, MCF_CLK); +DEFINE_CLK(0, "edma", 17, MCF_CLK); +DEFINE_CLK(0, "intc.0", 18, MCF_CLK); +DEFINE_CLK(0, "iack.0", 21, MCF_CLK); +DEFINE_CLK(0, "mcfi2c.0", 22, MCF_CLK); +DEFINE_CLK(0, "mcfqspi.0", 23, MCF_CLK); +DEFINE_CLK(0, "mcfuart.0", 24, MCF_BUSCLK); +DEFINE_CLK(0, "mcfuart.1", 25, MCF_BUSCLK); +DEFINE_CLK(0, "mcfuart.2", 26, MCF_BUSCLK); +DEFINE_CLK(0, "mcftmr.0", 28, MCF_CLK); +DEFINE_CLK(0, "mcftmr.1", 29, MCF_CLK); +DEFINE_CLK(0, "mcftmr.2", 30, MCF_CLK); +DEFINE_CLK(0, "mcftmr.3", 31, MCF_CLK); + +DEFINE_CLK(0, "mcfpit.0", 32, MCF_CLK); +DEFINE_CLK(0, "mcfpit.1", 33, MCF_CLK); +DEFINE_CLK(0, "mcfeport.0", 34, MCF_CLK); +DEFINE_CLK(0, "mcfwdt.0", 35, MCF_CLK); +DEFINE_CLK(0, "pll.0", 36, MCF_CLK); +DEFINE_CLK(0, "sys.0", 40, MCF_BUSCLK); +DEFINE_CLK(0, "gpio.0", 41, MCF_BUSCLK); +DEFINE_CLK(0, "sdram.0", 42, MCF_CLK); + +struct clk *mcf_clks[] = { + &__clk_0_2, /* flexbus */ + &__clk_0_12, /* fec.0 */ + &__clk_0_17, /* edma */ + &__clk_0_18, /* intc.0 */ + &__clk_0_21, /* iack.0 */ + &__clk_0_22, /* mcfi2c.0 */ + &__clk_0_23, /* mcfqspi.0 */ + &__clk_0_24, /* mcfuart.0 */ + &__clk_0_25, /* mcfuart.1 */ + &__clk_0_26, /* mcfuart.2 */ + &__clk_0_28, /* mcftmr.0 */ + &__clk_0_29, /* mcftmr.1 */ + &__clk_0_30, /* mcftmr.2 */ + &__clk_0_31, /* mcftmr.3 */ + + &__clk_0_32, /* mcfpit.0 */ + &__clk_0_33, /* mcfpit.1 */ + &__clk_0_34, /* mcfeport.0 */ + &__clk_0_35, /* mcfwdt.0 */ + &__clk_0_36, /* pll.0 */ + &__clk_0_40, /* sys.0 */ + &__clk_0_41, /* gpio.0 */ + &__clk_0_42, /* sdram.0 */ +NULL, }; -unsigned int mcf_gpio_chips_size = ARRAY_SIZE(mcf_gpio_chips); +static struct clk * const enable_clks[] __initconst = { + &__clk_0_2, /* flexbus */ + &__clk_0_18, /* intc.0 */ + &__clk_0_21, /* iack.0 */ + &__clk_0_24, /* mcfuart.0 */ + &__clk_0_25, /* mcfuart.1 */ + &__clk_0_26, /* mcfuart.2 */ + + &__clk_0_32, /* mcfpit.0 */ + &__clk_0_33, /* mcfpit.1 */ + &__clk_0_34, /* mcfeport.0 */ + &__clk_0_36, /* pll.0 */ + &__clk_0_40, /* sys.0 */ + &__clk_0_41, /* gpio.0 */ + &__clk_0_42, /* sdram.0 */ +}; + +static struct clk * const disable_clks[] __initconst = { + &__clk_0_12, /* fec.0 */ + &__clk_0_17, /* edma */ + &__clk_0_22, /* mcfi2c.0 */ + &__clk_0_23, /* mcfqspi.0 */ + &__clk_0_28, /* mcftmr.0 */ + &__clk_0_29, /* mcftmr.1 */ + &__clk_0_30, /* mcftmr.2 */ + &__clk_0_31, /* mcftmr.3 */ + &__clk_0_35, /* mcfwdt.0 */ +}; + + +static void __init m520x_clk_init(void) +{ + unsigned i; + + /* make sure these clocks are enabled */ + for (i = 0; i < ARRAY_SIZE(enable_clks); ++i) + __clk_init_enabled(enable_clks[i]); + /* make sure these clocks are disabled */ + for (i = 0; i < ARRAY_SIZE(disable_clks); ++i) + __clk_init_disabled(disable_clks[i]); +} /***************************************************************************/ @@ -93,6 +173,7 @@ static void __init m520x_fec_init(void) void __init config_BSP(char *commandp, int size) { mach_sched_init = hw_timer_init; + m520x_clk_init(); m520x_uarts_init(); m520x_fec_init(); #if IS_ENABLED(CONFIG_SPI_COLDFIRE_QSPI) diff --git a/arch/m68k/platform/coldfire/m523x.c b/arch/m68k/platform/coldfire/m523x.c index 5d57a42..d47dfd8 100644 --- a/arch/m68k/platform/coldfire/m523x.c +++ b/arch/m68k/platform/coldfire/m523x.c @@ -19,28 +19,6 @@ #include <asm/machdep.h> #include <asm/coldfire.h> #include <asm/mcfsim.h> -#include <asm/mcfgpio.h> - -/***************************************************************************/ - -struct mcf_gpio_chip mcf_gpio_chips[] = { - MCFGPS(PIRQ, 1, 7, MCFEPORT_EPDDR, MCFEPORT_EPDR, MCFEPORT_EPPDR), - MCFGPF(ADDR, 13, 3), - MCFGPF(DATAH, 16, 8), - MCFGPF(DATAL, 24, 8), - MCFGPF(BUSCTL, 32, 8), - MCFGPF(BS, 40, 4), - MCFGPF(CS, 49, 7), - MCFGPF(SDRAM, 56, 6), - MCFGPF(FECI2C, 64, 4), - MCFGPF(UARTH, 72, 2), - MCFGPF(UARTL, 80, 8), - MCFGPF(QSPI, 88, 5), - MCFGPF(TIMER, 96, 8), - MCFGPF(ETPU, 104, 3), -}; - -unsigned int mcf_gpio_chips_size = ARRAY_SIZE(mcf_gpio_chips); /***************************************************************************/ diff --git a/arch/m68k/platform/coldfire/m5249.c b/arch/m68k/platform/coldfire/m5249.c index fdfa1ed..300e729 100644 --- a/arch/m68k/platform/coldfire/m5249.c +++ b/arch/m68k/platform/coldfire/m5249.c @@ -16,16 +16,6 @@ #include <asm/machdep.h> #include <asm/coldfire.h> #include <asm/mcfsim.h> -#include <asm/mcfgpio.h> - -/***************************************************************************/ - -struct mcf_gpio_chip mcf_gpio_chips[] = { - MCFGPS(GPIO0, 0, 32, MCFSIM2_GPIOENABLE, MCFSIM2_GPIOWRITE, MCFSIM2_GPIOREAD), - MCFGPS(GPIO1, 32, 32, MCFSIM2_GPIO1ENABLE, MCFSIM2_GPIO1WRITE, MCFSIM2_GPIO1READ), -}; - -unsigned int mcf_gpio_chips_size = ARRAY_SIZE(mcf_gpio_chips); /***************************************************************************/ diff --git a/arch/m68k/platform/coldfire/m525x.c b/arch/m68k/platform/coldfire/m525x.c new file mode 100644 index 0000000..8ce905f --- /dev/null +++ b/arch/m68k/platform/coldfire/m525x.c @@ -0,0 +1,66 @@ +/***************************************************************************/ + +/* + * 525x.c + * + * Copyright (C) 2012, Steven King <sfking@fdwdc.com> + */ + +/***************************************************************************/ + +#include <linux/kernel.h> +#include <linux/param.h> +#include <linux/init.h> +#include <linux/io.h> +#include <linux/platform_device.h> +#include <asm/machdep.h> +#include <asm/coldfire.h> +#include <asm/mcfsim.h> + +/***************************************************************************/ + +static void __init m525x_qspi_init(void) +{ +#if IS_ENABLED(CONFIG_SPI_COLDFIRE_QSPI) + /* set the GPIO function for the qspi cs gpios */ + /* FIXME: replace with pinmux/pinctl support */ + u32 f = readl(MCFSIM2_GPIOFUNC); + f |= (1 << MCFQSPI_CS2) | (1 << MCFQSPI_CS1) | (1 << MCFQSPI_CS0); + writel(f, MCFSIM2_GPIOFUNC); + + /* QSPI irq setup */ + writeb(MCFSIM_ICR_AUTOVEC | MCFSIM_ICR_LEVEL4 | MCFSIM_ICR_PRI0, + MCF_MBAR + MCFSIM_QSPIICR); + mcf_mapirq2imr(MCF_IRQ_QSPI, MCFINTC_QSPI); +#endif /* IS_ENABLED(CONFIG_SPI_COLDFIRE_QSPI) */ +} + +static void __init m525x_i2c_init(void) +{ +#if IS_ENABLED(CONFIG_I2C_COLDFIRE) + u32 r; + + /* first I2C controller uses regular irq setup */ + writeb(MCFSIM_ICR_AUTOVEC | MCFSIM_ICR_LEVEL5 | MCFSIM_ICR_PRI0, + MCF_MBAR + MCFSIM_I2CICR); + mcf_mapirq2imr(MCF_IRQ_I2C0, MCFINTC_I2C); + + /* second I2C controller is completely different */ + r = readl(MCFINTC2_INTPRI_REG(MCF_IRQ_I2C1)); + r &= ~MCFINTC2_INTPRI_BITS(0xf, MCF_IRQ_I2C1); + r |= MCFINTC2_INTPRI_BITS(0x5, MCF_IRQ_I2C1); + writel(r, MCFINTC2_INTPRI_REG(MCF_IRQ_I2C1)); +#endif /* IS_ENABLED(CONFIG_I2C_COLDFIRE) */ +} + +/***************************************************************************/ + +void __init config_BSP(char *commandp, int size) +{ + mach_sched_init = hw_timer_init; + + m525x_qspi_init(); + m525x_i2c_init(); +} + +/***************************************************************************/ diff --git a/arch/m68k/platform/coldfire/m5272.c b/arch/m68k/platform/coldfire/m5272.c index 43e3606..e68bc7a 100644 --- a/arch/m68k/platform/coldfire/m5272.c +++ b/arch/m68k/platform/coldfire/m5272.c @@ -19,7 +19,6 @@ #include <asm/coldfire.h> #include <asm/mcfsim.h> #include <asm/mcfuart.h> -#include <asm/mcfgpio.h> /***************************************************************************/ @@ -31,16 +30,6 @@ unsigned char ledbank = 0xff; /***************************************************************************/ -struct mcf_gpio_chip mcf_gpio_chips[] = { - MCFGPS(PA, 0, 16, MCFSIM_PADDR, MCFSIM_PADAT, MCFSIM_PADAT), - MCFGPS(PB, 16, 16, MCFSIM_PBDDR, MCFSIM_PBDAT, MCFSIM_PBDAT), - MCFGPS(Pc, 32, 16, MCFSIM_PCDDR, MCFSIM_PCDAT, MCFSIM_PCDAT), -}; - -unsigned int mcf_gpio_chips_size = ARRAY_SIZE(mcf_gpio_chips); - -/***************************************************************************/ - static void __init m5272_uarts_init(void) { u32 v; diff --git a/arch/m68k/platform/coldfire/m527x.c b/arch/m68k/platform/coldfire/m527x.c index 9b0b66a..b3cb378 100644 --- a/arch/m68k/platform/coldfire/m527x.c +++ b/arch/m68k/platform/coldfire/m527x.c @@ -20,49 +20,6 @@ #include <asm/coldfire.h> #include <asm/mcfsim.h> #include <asm/mcfuart.h> -#include <asm/mcfgpio.h> - -/***************************************************************************/ - -struct mcf_gpio_chip mcf_gpio_chips[] = { -#if defined(CONFIG_M5271) - MCFGPS(PIRQ, 1, 7, MCFEPORT_EPDDR, MCFEPORT_EPDR, MCFEPORT_EPPDR), - MCFGPF(ADDR, 13, 3), - MCFGPF(DATAH, 16, 8), - MCFGPF(DATAL, 24, 8), - MCFGPF(BUSCTL, 32, 8), - MCFGPF(BS, 40, 4), - MCFGPF(CS, 49, 7), - MCFGPF(SDRAM, 56, 6), - MCFGPF(FECI2C, 64, 4), - MCFGPF(UARTH, 72, 2), - MCFGPF(UARTL, 80, 8), - MCFGPF(QSPI, 88, 5), - MCFGPF(TIMER, 96, 8), -#elif defined(CONFIG_M5275) - MCFGPS(PIRQ, 1, 7, MCFEPORT_EPDDR, MCFEPORT_EPDR, MCFEPORT_EPPDR), - MCFGPF(BUSCTL, 8, 8), - MCFGPF(ADDR, 21, 3), - MCFGPF(CS, 25, 7), - MCFGPF(FEC0H, 32, 8), - MCFGPF(FEC0L, 40, 8), - MCFGPF(FECI2C, 48, 6), - MCFGPF(QSPI, 56, 7), - MCFGPF(SDRAM, 64, 8), - MCFGPF(TIMERH, 72, 4), - MCFGPF(TIMERL, 80, 4), - MCFGPF(UARTL, 88, 8), - MCFGPF(FEC1H, 96, 8), - MCFGPF(FEC1L, 104, 8), - MCFGPF(BS, 114, 2), - MCFGPF(IRQ, 121, 7), - MCFGPF(USBH, 128, 1), - MCFGPF(USBL, 136, 8), - MCFGPF(UARTH, 144, 4), -#endif -}; - -unsigned int mcf_gpio_chips_size = ARRAY_SIZE(mcf_gpio_chips); /***************************************************************************/ diff --git a/arch/m68k/platform/coldfire/m528x.c b/arch/m68k/platform/coldfire/m528x.c index 7ed1276b..f1319e5 100644 --- a/arch/m68k/platform/coldfire/m528x.c +++ b/arch/m68k/platform/coldfire/m528x.c @@ -21,37 +21,6 @@ #include <asm/coldfire.h> #include <asm/mcfsim.h> #include <asm/mcfuart.h> -#include <asm/mcfgpio.h> - -/***************************************************************************/ - -struct mcf_gpio_chip mcf_gpio_chips[] = { - MCFGPS(NQ, 1, 7, MCFEPORT_EPDDR, MCFEPORT_EPDR, MCFEPORT_EPPDR), - MCFGPS(TA, 8, 4, MCFGPTA_GPTDDR, MCFGPTA_GPTPORT, MCFGPTB_GPTPORT), - MCFGPS(TB, 16, 4, MCFGPTB_GPTDDR, MCFGPTB_GPTPORT, MCFGPTB_GPTPORT), - MCFGPS(QA, 24, 4, MCFQADC_DDRQA, MCFQADC_PORTQA, MCFQADC_PORTQA), - MCFGPS(QB, 32, 4, MCFQADC_DDRQB, MCFQADC_PORTQB, MCFQADC_PORTQB), - MCFGPF(A, 40, 8), - MCFGPF(B, 48, 8), - MCFGPF(C, 56, 8), - MCFGPF(D, 64, 8), - MCFGPF(E, 72, 8), - MCFGPF(F, 80, 8), - MCFGPF(G, 88, 8), - MCFGPF(H, 96, 8), - MCFGPF(J, 104, 8), - MCFGPF(DD, 112, 8), - MCFGPF(EH, 120, 8), - MCFGPF(EL, 128, 8), - MCFGPF(AS, 136, 6), - MCFGPF(QS, 144, 7), - MCFGPF(SD, 152, 6), - MCFGPF(TC, 160, 4), - MCFGPF(TD, 168, 4), - MCFGPF(UA, 176, 4), -}; - -unsigned int mcf_gpio_chips_size = ARRAY_SIZE(mcf_gpio_chips); /***************************************************************************/ @@ -74,7 +43,7 @@ static void __init m528x_uarts_init(void) /* make sure PUAPAR is set for UART0 and UART1 */ port = readb(MCF5282_GPIO_PUAPAR); port |= 0x03 | (0x03 << 2); - writeb(port, MCF5282_GPIO_PUAPAR); + writeb(port, MCFGPIO_PUAPAR); } /***************************************************************************/ diff --git a/arch/m68k/platform/coldfire/m5307.c b/arch/m68k/platform/coldfire/m5307.c index 93b4849..a568d28 100644 --- a/arch/m68k/platform/coldfire/m5307.c +++ b/arch/m68k/platform/coldfire/m5307.c @@ -16,7 +16,6 @@ #include <asm/machdep.h> #include <asm/coldfire.h> #include <asm/mcfsim.h> -#include <asm/mcfgpio.h> #include <asm/mcfwdebug.h> /***************************************************************************/ @@ -29,14 +28,6 @@ unsigned char ledbank = 0xff; /***************************************************************************/ -struct mcf_gpio_chip mcf_gpio_chips[] = { - MCFGPS(PP, 0, 16, MCFSIM_PADDR, MCFSIM_PADAT, MCFSIM_PADAT), -}; - -unsigned int mcf_gpio_chips_size = ARRAY_SIZE(mcf_gpio_chips); - -/***************************************************************************/ - void __init config_BSP(char *commandp, int size) { #if defined(CONFIG_NETtel) || \ diff --git a/arch/m68k/platform/coldfire/m532x.c b/arch/m68k/platform/coldfire/m532x.c index 53942236..4819a44 100644 --- a/arch/m68k/platform/coldfire/m532x.c +++ b/arch/m68k/platform/coldfire/m532x.c @@ -26,32 +26,144 @@ #include <asm/mcfsim.h> #include <asm/mcfuart.h> #include <asm/mcfdma.h> -#include <asm/mcfgpio.h> #include <asm/mcfwdebug.h> +#include <asm/mcfclk.h> /***************************************************************************/ -struct mcf_gpio_chip mcf_gpio_chips[] = { - MCFGPS(PIRQ, 0, 8, MCFEPORT_EPDDR, MCFEPORT_EPDR, MCFEPORT_EPPDR), - MCFGPF(FECH, 8, 8), - MCFGPF(FECL, 16, 8), - MCFGPF(SSI, 24, 5), - MCFGPF(BUSCTL, 32, 4), - MCFGPF(BE, 40, 4), - MCFGPF(CS, 49, 5), - MCFGPF(PWM, 58, 4), - MCFGPF(FECI2C, 64, 4), - MCFGPF(UART, 72, 8), - MCFGPF(QSPI, 80, 6), - MCFGPF(TIMER, 88, 4), - MCFGPF(LCDDATAH, 96, 2), - MCFGPF(LCDDATAM, 104, 8), - MCFGPF(LCDDATAL, 112, 8), - MCFGPF(LCDCTLH, 120, 1), - MCFGPF(LCDCTLL, 128, 8), +DEFINE_CLK(0, "flexbus", 2, MCF_CLK); +DEFINE_CLK(0, "mcfcan.0", 8, MCF_CLK); +DEFINE_CLK(0, "fec.0", 12, MCF_CLK); +DEFINE_CLK(0, "edma", 17, MCF_CLK); +DEFINE_CLK(0, "intc.0", 18, MCF_CLK); +DEFINE_CLK(0, "intc.1", 19, MCF_CLK); +DEFINE_CLK(0, "iack.0", 21, MCF_CLK); +DEFINE_CLK(0, "mcfi2c.0", 22, MCF_CLK); +DEFINE_CLK(0, "mcfqspi.0", 23, MCF_CLK); +DEFINE_CLK(0, "mcfuart.0", 24, MCF_BUSCLK); +DEFINE_CLK(0, "mcfuart.1", 25, MCF_BUSCLK); +DEFINE_CLK(0, "mcfuart.2", 26, MCF_BUSCLK); +DEFINE_CLK(0, "mcftmr.0", 28, MCF_CLK); +DEFINE_CLK(0, "mcftmr.1", 29, MCF_CLK); +DEFINE_CLK(0, "mcftmr.2", 30, MCF_CLK); +DEFINE_CLK(0, "mcftmr.3", 31, MCF_CLK); + +DEFINE_CLK(0, "mcfpit.0", 32, MCF_CLK); +DEFINE_CLK(0, "mcfpit.1", 33, MCF_CLK); +DEFINE_CLK(0, "mcfpit.2", 34, MCF_CLK); +DEFINE_CLK(0, "mcfpit.3", 35, MCF_CLK); +DEFINE_CLK(0, "mcfpwm.0", 36, MCF_CLK); +DEFINE_CLK(0, "mcfeport.0", 37, MCF_CLK); +DEFINE_CLK(0, "mcfwdt.0", 38, MCF_CLK); +DEFINE_CLK(0, "sys.0", 40, MCF_BUSCLK); +DEFINE_CLK(0, "gpio.0", 41, MCF_BUSCLK); +DEFINE_CLK(0, "mcfrtc.0", 42, MCF_CLK); +DEFINE_CLK(0, "mcflcd.0", 43, MCF_CLK); +DEFINE_CLK(0, "mcfusb-otg.0", 44, MCF_CLK); +DEFINE_CLK(0, "mcfusb-host.0", 45, MCF_CLK); +DEFINE_CLK(0, "sdram.0", 46, MCF_CLK); +DEFINE_CLK(0, "ssi.0", 47, MCF_CLK); +DEFINE_CLK(0, "pll.0", 48, MCF_CLK); + +DEFINE_CLK(1, "mdha.0", 32, MCF_CLK); +DEFINE_CLK(1, "skha.0", 33, MCF_CLK); +DEFINE_CLK(1, "rng.0", 34, MCF_CLK); + +struct clk *mcf_clks[] = { + &__clk_0_2, /* flexbus */ + &__clk_0_8, /* mcfcan.0 */ + &__clk_0_12, /* fec.0 */ + &__clk_0_17, /* edma */ + &__clk_0_18, /* intc.0 */ + &__clk_0_19, /* intc.1 */ + &__clk_0_21, /* iack.0 */ + &__clk_0_22, /* mcfi2c.0 */ + &__clk_0_23, /* mcfqspi.0 */ + &__clk_0_24, /* mcfuart.0 */ + &__clk_0_25, /* mcfuart.1 */ + &__clk_0_26, /* mcfuart.2 */ + &__clk_0_28, /* mcftmr.0 */ + &__clk_0_29, /* mcftmr.1 */ + &__clk_0_30, /* mcftmr.2 */ + &__clk_0_31, /* mcftmr.3 */ + + &__clk_0_32, /* mcfpit.0 */ + &__clk_0_33, /* mcfpit.1 */ + &__clk_0_34, /* mcfpit.2 */ + &__clk_0_35, /* mcfpit.3 */ + &__clk_0_36, /* mcfpwm.0 */ + &__clk_0_37, /* mcfeport.0 */ + &__clk_0_38, /* mcfwdt.0 */ + &__clk_0_40, /* sys.0 */ + &__clk_0_41, /* gpio.0 */ + &__clk_0_42, /* mcfrtc.0 */ + &__clk_0_43, /* mcflcd.0 */ + &__clk_0_44, /* mcfusb-otg.0 */ + &__clk_0_45, /* mcfusb-host.0 */ + &__clk_0_46, /* sdram.0 */ + &__clk_0_47, /* ssi.0 */ + &__clk_0_48, /* pll.0 */ + + &__clk_1_32, /* mdha.0 */ + &__clk_1_33, /* skha.0 */ + &__clk_1_34, /* rng.0 */ + NULL, +}; + +static struct clk * const enable_clks[] __initconst = { + &__clk_0_2, /* flexbus */ + &__clk_0_18, /* intc.0 */ + &__clk_0_19, /* intc.1 */ + &__clk_0_21, /* iack.0 */ + &__clk_0_24, /* mcfuart.0 */ + &__clk_0_25, /* mcfuart.1 */ + &__clk_0_26, /* mcfuart.2 */ + + &__clk_0_32, /* mcfpit.0 */ + &__clk_0_33, /* mcfpit.1 */ + &__clk_0_37, /* mcfeport.0 */ + &__clk_0_40, /* sys.0 */ + &__clk_0_41, /* gpio.0 */ + &__clk_0_46, /* sdram.0 */ + &__clk_0_48, /* pll.0 */ +}; + +static struct clk * const disable_clks[] __initconst = { + &__clk_0_8, /* mcfcan.0 */ + &__clk_0_12, /* fec.0 */ + &__clk_0_17, /* edma */ + &__clk_0_22, /* mcfi2c.0 */ + &__clk_0_23, /* mcfqspi.0 */ + &__clk_0_28, /* mcftmr.0 */ + &__clk_0_29, /* mcftmr.1 */ + &__clk_0_30, /* mcftmr.2 */ + &__clk_0_31, /* mcftmr.3 */ + &__clk_0_34, /* mcfpit.2 */ + &__clk_0_35, /* mcfpit.3 */ + &__clk_0_36, /* mcfpwm.0 */ + &__clk_0_38, /* mcfwdt.0 */ + &__clk_0_42, /* mcfrtc.0 */ + &__clk_0_43, /* mcflcd.0 */ + &__clk_0_44, /* mcfusb-otg.0 */ + &__clk_0_45, /* mcfusb-host.0 */ + &__clk_0_47, /* ssi.0 */ + &__clk_1_32, /* mdha.0 */ + &__clk_1_33, /* skha.0 */ + &__clk_1_34, /* rng.0 */ }; -unsigned int mcf_gpio_chips_size = ARRAY_SIZE(mcf_gpio_chips); + +static void __init m532x_clk_init(void) +{ + unsigned i; + + /* make sure these clocks are enabled */ + for (i = 0; i < ARRAY_SIZE(enable_clks); ++i) + __clk_init_enabled(enable_clks[i]); + /* make sure these clocks are disabled */ + for (i = 0; i < ARRAY_SIZE(disable_clks); ++i) + __clk_init_disabled(disable_clks[i]); +} /***************************************************************************/ @@ -98,8 +210,8 @@ void __init config_BSP(char *commandp, int size) memset(commandp, 0, size); } #endif - mach_sched_init = hw_timer_init; + m532x_clk_init(); m532x_uarts_init(); m532x_fec_init(); #if IS_ENABLED(CONFIG_SPI_COLDFIRE_QSPI) diff --git a/arch/m68k/platform/coldfire/m5407.c b/arch/m68k/platform/coldfire/m5407.c index faa6680..bb6c746 100644 --- a/arch/m68k/platform/coldfire/m5407.c +++ b/arch/m68k/platform/coldfire/m5407.c @@ -16,15 +16,6 @@ #include <asm/machdep.h> #include <asm/coldfire.h> #include <asm/mcfsim.h> -#include <asm/mcfgpio.h> - -/***************************************************************************/ - -struct mcf_gpio_chip mcf_gpio_chips[] = { - MCFGPS(PP, 0, 16, MCFSIM_PADDR, MCFSIM_PADAT, MCFSIM_PADAT), -}; - -unsigned int mcf_gpio_chips_size = ARRAY_SIZE(mcf_gpio_chips); /***************************************************************************/ diff --git a/arch/m68k/platform/coldfire/m5441x.c b/arch/m68k/platform/coldfire/m5441x.c new file mode 100644 index 0000000..98a13cc --- /dev/null +++ b/arch/m68k/platform/coldfire/m5441x.c @@ -0,0 +1,261 @@ +/* + * m5441x.c -- support for Coldfire m5441x processors + * + * (C) Copyright Steven King <sfking@fdwdc.com> + */ + +#include <linux/kernel.h> +#include <linux/param.h> +#include <linux/init.h> +#include <linux/io.h> +#include <linux/clk.h> +#include <asm/machdep.h> +#include <asm/coldfire.h> +#include <asm/mcfsim.h> +#include <asm/mcfuart.h> +#include <asm/mcfdma.h> +#include <asm/mcfclk.h> + +DEFINE_CLK(0, "flexbus", 2, MCF_CLK); +DEFINE_CLK(0, "mcfcan.0", 8, MCF_CLK); +DEFINE_CLK(0, "mcfcan.1", 9, MCF_CLK); +DEFINE_CLK(0, "mcfi2c.1", 14, MCF_CLK); +DEFINE_CLK(0, "mcfdspi.1", 15, MCF_CLK); +DEFINE_CLK(0, "edma", 17, MCF_CLK); +DEFINE_CLK(0, "intc.0", 18, MCF_CLK); +DEFINE_CLK(0, "intc.1", 19, MCF_CLK); +DEFINE_CLK(0, "intc.2", 20, MCF_CLK); +DEFINE_CLK(0, "mcfi2c.0", 22, MCF_CLK); +DEFINE_CLK(0, "mcfdspi.0", 23, MCF_CLK); +DEFINE_CLK(0, "mcfuart.0", 24, MCF_BUSCLK); +DEFINE_CLK(0, "mcfuart.1", 25, MCF_BUSCLK); +DEFINE_CLK(0, "mcfuart.2", 26, MCF_BUSCLK); +DEFINE_CLK(0, "mcfuart.3", 27, MCF_BUSCLK); +DEFINE_CLK(0, "mcftmr.0", 28, MCF_CLK); +DEFINE_CLK(0, "mcftmr.1", 29, MCF_CLK); +DEFINE_CLK(0, "mcftmr.2", 30, MCF_CLK); +DEFINE_CLK(0, "mcftmr.3", 31, MCF_CLK); +DEFINE_CLK(0, "mcfpit.0", 32, MCF_CLK); +DEFINE_CLK(0, "mcfpit.1", 33, MCF_CLK); +DEFINE_CLK(0, "mcfpit.2", 34, MCF_CLK); +DEFINE_CLK(0, "mcfpit.3", 35, MCF_CLK); +DEFINE_CLK(0, "mcfeport.0", 37, MCF_CLK); +DEFINE_CLK(0, "mcfadc.0", 38, MCF_CLK); +DEFINE_CLK(0, "mcfdac.0", 39, MCF_CLK); +DEFINE_CLK(0, "mcfrtc.0", 42, MCF_CLK); +DEFINE_CLK(0, "mcfsim.0", 43, MCF_CLK); +DEFINE_CLK(0, "mcfusb-otg.0", 44, MCF_CLK); +DEFINE_CLK(0, "mcfusb-host.0", 45, MCF_CLK); +DEFINE_CLK(0, "mcfddr-sram.0", 46, MCF_CLK); +DEFINE_CLK(0, "mcfssi.0", 47, MCF_CLK); +DEFINE_CLK(0, "pll.0", 48, MCF_CLK); +DEFINE_CLK(0, "mcfrng.0", 49, MCF_CLK); +DEFINE_CLK(0, "mcfssi.1", 50, MCF_CLK); +DEFINE_CLK(0, "mcfsdhc.0", 51, MCF_CLK); +DEFINE_CLK(0, "enet-fec.0", 53, MCF_CLK); +DEFINE_CLK(0, "enet-fec.1", 54, MCF_CLK); +DEFINE_CLK(0, "switch.0", 55, MCF_CLK); +DEFINE_CLK(0, "switch.1", 56, MCF_CLK); +DEFINE_CLK(0, "nand.0", 63, MCF_CLK); + +DEFINE_CLK(1, "mcfow.0", 2, MCF_CLK); +DEFINE_CLK(1, "mcfi2c.2", 4, MCF_CLK); +DEFINE_CLK(1, "mcfi2c.3", 5, MCF_CLK); +DEFINE_CLK(1, "mcfi2c.4", 6, MCF_CLK); +DEFINE_CLK(1, "mcfi2c.5", 7, MCF_CLK); +DEFINE_CLK(1, "mcfuart.4", 24, MCF_BUSCLK); +DEFINE_CLK(1, "mcfuart.5", 25, MCF_BUSCLK); +DEFINE_CLK(1, "mcfuart.6", 26, MCF_BUSCLK); +DEFINE_CLK(1, "mcfuart.7", 27, MCF_BUSCLK); +DEFINE_CLK(1, "mcfuart.8", 28, MCF_BUSCLK); +DEFINE_CLK(1, "mcfuart.9", 29, MCF_BUSCLK); +DEFINE_CLK(1, "mcfpwm.0", 34, MCF_BUSCLK); +DEFINE_CLK(1, "sys.0", 36, MCF_BUSCLK); +DEFINE_CLK(1, "gpio.0", 37, MCF_BUSCLK); + +struct clk *mcf_clks[] = { + &__clk_0_2, + &__clk_0_8, + &__clk_0_9, + &__clk_0_14, + &__clk_0_15, + &__clk_0_17, + &__clk_0_18, + &__clk_0_19, + &__clk_0_20, + &__clk_0_22, + &__clk_0_23, + &__clk_0_24, + &__clk_0_25, + &__clk_0_26, + &__clk_0_27, + &__clk_0_28, + &__clk_0_29, + &__clk_0_30, + &__clk_0_31, + &__clk_0_32, + &__clk_0_33, + &__clk_0_34, + &__clk_0_35, + &__clk_0_37, + &__clk_0_38, + &__clk_0_39, + &__clk_0_42, + &__clk_0_43, + &__clk_0_44, + &__clk_0_45, + &__clk_0_46, + &__clk_0_47, + &__clk_0_48, + &__clk_0_49, + &__clk_0_50, + &__clk_0_51, + &__clk_0_53, + &__clk_0_54, + &__clk_0_55, + &__clk_0_56, + &__clk_0_63, + + &__clk_1_2, + &__clk_1_4, + &__clk_1_5, + &__clk_1_6, + &__clk_1_7, + &__clk_1_24, + &__clk_1_25, + &__clk_1_26, + &__clk_1_27, + &__clk_1_28, + &__clk_1_29, + &__clk_1_34, + &__clk_1_36, + &__clk_1_37, + NULL, +}; + + +static struct clk * const enable_clks[] __initconst = { + /* make sure these clocks are enabled */ + &__clk_0_18, /* intc0 */ + &__clk_0_19, /* intc0 */ + &__clk_0_20, /* intc0 */ + &__clk_0_24, /* uart0 */ + &__clk_0_25, /* uart1 */ + &__clk_0_26, /* uart2 */ + &__clk_0_27, /* uart3 */ + + &__clk_0_33, /* pit.1 */ + &__clk_0_37, /* eport */ + &__clk_0_48, /* pll */ + + &__clk_1_36, /* CCM/reset module/Power management */ + &__clk_1_37, /* gpio */ +}; +static struct clk * const disable_clks[] __initconst = { + &__clk_0_8, /* can.0 */ + &__clk_0_9, /* can.1 */ + &__clk_0_14, /* i2c.1 */ + &__clk_0_15, /* dspi.1 */ + &__clk_0_17, /* eDMA */ + &__clk_0_22, /* i2c.0 */ + &__clk_0_23, /* dspi.0 */ + &__clk_0_28, /* tmr.1 */ + &__clk_0_29, /* tmr.2 */ + &__clk_0_30, /* tmr.2 */ + &__clk_0_31, /* tmr.3 */ + &__clk_0_32, /* pit.0 */ + &__clk_0_34, /* pit.2 */ + &__clk_0_35, /* pit.3 */ + &__clk_0_38, /* adc */ + &__clk_0_39, /* dac */ + &__clk_0_44, /* usb otg */ + &__clk_0_45, /* usb host */ + &__clk_0_47, /* ssi.0 */ + &__clk_0_49, /* rng */ + &__clk_0_50, /* ssi.1 */ + &__clk_0_51, /* eSDHC */ + &__clk_0_53, /* enet-fec */ + &__clk_0_54, /* enet-fec */ + &__clk_0_55, /* switch.0 */ + &__clk_0_56, /* switch.1 */ + + &__clk_1_2, /* 1-wire */ + &__clk_1_4, /* i2c.2 */ + &__clk_1_5, /* i2c.3 */ + &__clk_1_6, /* i2c.4 */ + &__clk_1_7, /* i2c.5 */ + &__clk_1_24, /* uart 4 */ + &__clk_1_25, /* uart 5 */ + &__clk_1_26, /* uart 6 */ + &__clk_1_27, /* uart 7 */ + &__clk_1_28, /* uart 8 */ + &__clk_1_29, /* uart 9 */ +}; + +static void __init m5441x_clk_init(void) +{ + unsigned i; + + for (i = 0; i < ARRAY_SIZE(enable_clks); ++i) + __clk_init_enabled(enable_clks[i]); + /* make sure these clocks are disabled */ + for (i = 0; i < ARRAY_SIZE(disable_clks); ++i) + __clk_init_disabled(disable_clks[i]); +} + +static void __init m5441x_uarts_init(void) +{ + __raw_writeb(0x0f, MCFGPIO_PAR_UART0); + __raw_writeb(0x00, MCFGPIO_PAR_UART1); + __raw_writeb(0x00, MCFGPIO_PAR_UART2); +} + +static void __init m5441x_fec_init(void) +{ + __raw_writeb(0x03, MCFGPIO_PAR_FEC); +} + +void __init config_BSP(char *commandp, int size) +{ + m5441x_clk_init(); + mach_sched_init = hw_timer_init; + m5441x_uarts_init(); + m5441x_fec_init(); +} + + +#if IS_ENABLED(CONFIG_RTC_DRV_M5441x) +static struct resource m5441x_rtc_resources[] = { + { + .start = MCFRTC_BASE, + .end = MCFRTC_BASE + MCFRTC_SIZE - 1, + .flags = IORESOURCE_MEM, + }, + { + .start = MCF_IRQ_RTC, + .end = MCF_IRQ_RTC, + .flags = IORESOURCE_IRQ, + }, +}; + +static struct platform_device m5441x_rtc = { + .name = "mcfrtc", + .id = 0, + .resource = m5441x_rtc_resources, + .num_resources = ARRAY_SIZE(m5441x_rtc_resources), +}; +#endif + +static struct platform_device *m5441x_devices[] __initdata = { +#if IS_ENABLED(CONFIG_RTC_DRV_M5441x) + &m5441x_rtc, +#endif +}; + +static int __init init_BSP(void) +{ + platform_add_devices(m5441x_devices, ARRAY_SIZE(m5441x_devices)); + return 0; +} + +arch_initcall(init_BSP); diff --git a/arch/m68k/platform/coldfire/m54xx.c b/arch/m68k/platform/coldfire/m54xx.c index 20672da..2081c6c 100644 --- a/arch/m68k/platform/coldfire/m54xx.c +++ b/arch/m68k/platform/coldfire/m54xx.c @@ -21,19 +21,12 @@ #include <asm/m54xxsim.h> #include <asm/mcfuart.h> #include <asm/m54xxgpt.h> -#include <asm/mcfgpio.h> #ifdef CONFIG_MMU #include <asm/mmu_context.h> #endif /***************************************************************************/ -struct mcf_gpio_chip mcf_gpio_chips[] = { }; - -unsigned int mcf_gpio_chips_size = ARRAY_SIZE(mcf_gpio_chips); - -/***************************************************************************/ - static void __init m54xx_uarts_init(void) { /* enable io pins */ diff --git a/arch/m68k/platform/coldfire/mcf8390.c b/arch/m68k/platform/coldfire/mcf8390.c new file mode 100644 index 0000000..23a6874 --- /dev/null +++ b/arch/m68k/platform/coldfire/mcf8390.c @@ -0,0 +1,38 @@ +/* + * mcf8390.c -- platform support for 8390 ethernet on many boards + * + * (C) Copyright 2012, Greg Ungerer <gerg@uclinux.org> + * + * This file is subject to the terms and conditions of the GNU General Public + * License. See the file COPYING in the main directory of this archive + * for more details. + */ + +#include <linux/kernel.h> +#include <linux/module.h> +#include <linux/init.h> +#include <linux/resource.h> +#include <linux/platform_device.h> +#include <asm/mcf8390.h> + +static struct resource mcf8390_resources[] = { + { + .start = NE2000_ADDR, + .end = NE2000_ADDR + NE2000_ADDRSIZE - 1, + .flags = IORESOURCE_MEM, + }, + { + .start = NE2000_IRQ_VECTOR, + .end = NE2000_IRQ_VECTOR, + .flags = IORESOURCE_IRQ, + }, +}; + +static int __init mcf8390_platform_init(void) +{ + platform_device_register_simple("mcf8390", -1, mcf8390_resources, + ARRAY_SIZE(mcf8390_resources)); + return 0; +} + +arch_initcall(mcf8390_platform_init); diff --git a/arch/m68k/platform/coldfire/pci.c b/arch/m68k/platform/coldfire/pci.c new file mode 100644 index 0000000..553210d --- /dev/null +++ b/arch/m68k/platform/coldfire/pci.c @@ -0,0 +1,327 @@ +/* + * pci.c -- PCI bus support for ColdFire processors + * + * (C) Copyright 2012, Greg Ungerer <gerg@uclinux.com> + * + * This file is subject to the terms and conditions of the GNU General Public + * License. See the file COPYING in the main directory of this archive + * for more details. + */ + +#include <linux/types.h> +#include <linux/module.h> +#include <linux/init.h> +#include <linux/kernel.h> +#include <linux/interrupt.h> +#include <linux/irq.h> +#include <linux/io.h> +#include <linux/pci.h> +#include <linux/delay.h> +#include <asm/coldfire.h> +#include <asm/mcfsim.h> +#include <asm/m54xxpci.h> + +/* + * Memory and IO mappings. We use a 1:1 mapping for local host memory to + * PCI bus memory (no reason not to really). IO space doesn't matter, we + * always use access functions for that. The device configuration space is + * mapped over the IO map space when we enable it in the PCICAR register. + */ +#define PCI_MEM_PA 0xf0000000 /* Host physical address */ +#define PCI_MEM_BA 0xf0000000 /* Bus physical address */ +#define PCI_MEM_SIZE 0x08000000 /* 128 MB */ +#define PCI_MEM_MASK (PCI_MEM_SIZE - 1) + +#define PCI_IO_PA 0xf8000000 /* Host physical address */ +#define PCI_IO_BA 0x00000000 /* Bus physical address */ +#define PCI_IO_SIZE 0x00010000 /* 64k */ +#define PCI_IO_MASK (PCI_IO_SIZE - 1) + +static struct pci_bus *rootbus; +static unsigned long iospace; + +/* + * We need to be carefull probing on bus 0 (directly connected to host + * bridge). We should only acccess the well defined possible devices in + * use, ignore aliases and the like. + */ +static unsigned char mcf_host_slot2sid[32] = { + 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, 1, 2, 0, 3, 4, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, +}; + +static unsigned char mcf_host_irq[] = { + 0, 69, 69, 71, 71, +}; + + +static inline void syncio(void) +{ + /* The ColdFire "nop" instruction waits for all bus IO to complete */ + __asm__ __volatile__ ("nop"); +} + +/* + * Configuration space access functions. Configuration space access is + * through the IO mapping window, enabling it via the PCICAR register. + */ +static unsigned long mcf_mk_pcicar(int bus, unsigned int devfn, int where) +{ + return (bus << PCICAR_BUSN) | (devfn << PCICAR_DEVFNN) | (where & 0xfc); +} + +static int mcf_pci_readconfig(struct pci_bus *bus, unsigned int devfn, + int where, int size, u32 *value) +{ + unsigned long addr; + + *value = 0xffffffff; + + if (bus->number == 0) { + if (mcf_host_slot2sid[PCI_SLOT(devfn)] == 0) + return PCIBIOS_SUCCESSFUL; + } + + syncio(); + addr = mcf_mk_pcicar(bus->number, devfn, where); + __raw_writel(PCICAR_E | addr, PCICAR); + addr = iospace + (where & 0x3); + + switch (size) { + case 1: + *value = __raw_readb(addr); + break; + case 2: + *value = le16_to_cpu(__raw_readw(addr)); + break; + default: + *value = le32_to_cpu(__raw_readl(addr)); + break; + } + + syncio(); + __raw_writel(0, PCICAR); + return PCIBIOS_SUCCESSFUL; +} + +static int mcf_pci_writeconfig(struct pci_bus *bus, unsigned int devfn, + int where, int size, u32 value) +{ + unsigned long addr; + + if (bus->number == 0) { + if (mcf_host_slot2sid[PCI_SLOT(devfn)] == 0) + return PCIBIOS_SUCCESSFUL; + } + + syncio(); + addr = mcf_mk_pcicar(bus->number, devfn, where); + __raw_writel(PCICAR_E | addr, PCICAR); + addr = iospace + (where & 0x3); + + switch (size) { + case 1: + __raw_writeb(value, addr); + break; + case 2: + __raw_writew(cpu_to_le16(value), addr); + break; + default: + __raw_writel(cpu_to_le32(value), addr); + break; + } + + syncio(); + __raw_writel(0, PCICAR); + return PCIBIOS_SUCCESSFUL; +} + +static struct pci_ops mcf_pci_ops = { + .read = mcf_pci_readconfig, + .write = mcf_pci_writeconfig, +}; + +/* + * IO address space access functions. Pretty strait forward, these are + * directly mapped in to the IO mapping window. And that is mapped into + * virtual address space. + */ +u8 mcf_pci_inb(u32 addr) +{ + return __raw_readb(iospace + (addr & PCI_IO_MASK)); +} +EXPORT_SYMBOL(mcf_pci_inb); + +u16 mcf_pci_inw(u32 addr) +{ + return le16_to_cpu(__raw_readw(iospace + (addr & PCI_IO_MASK))); +} +EXPORT_SYMBOL(mcf_pci_inw); + +u32 mcf_pci_inl(u32 addr) +{ + return le32_to_cpu(__raw_readl(iospace + (addr & PCI_IO_MASK))); +} +EXPORT_SYMBOL(mcf_pci_inl); + +void mcf_pci_insb(u32 addr, u8 *buf, u32 len) +{ + for (; len; len--) + *buf++ = mcf_pci_inb(addr); +} +EXPORT_SYMBOL(mcf_pci_insb); + +void mcf_pci_insw(u32 addr, u16 *buf, u32 len) +{ + for (; len; len--) + *buf++ = mcf_pci_inw(addr); +} +EXPORT_SYMBOL(mcf_pci_insw); + +void mcf_pci_insl(u32 addr, u32 *buf, u32 len) +{ + for (; len; len--) + *buf++ = mcf_pci_inl(addr); +} +EXPORT_SYMBOL(mcf_pci_insl); + +void mcf_pci_outb(u8 v, u32 addr) +{ + __raw_writeb(v, iospace + (addr & PCI_IO_MASK)); +} +EXPORT_SYMBOL(mcf_pci_outb); + +void mcf_pci_outw(u16 v, u32 addr) +{ + __raw_writew(cpu_to_le16(v), iospace + (addr & PCI_IO_MASK)); +} +EXPORT_SYMBOL(mcf_pci_outw); + +void mcf_pci_outl(u32 v, u32 addr) +{ + __raw_writel(cpu_to_le32(v), iospace + (addr & PCI_IO_MASK)); +} +EXPORT_SYMBOL(mcf_pci_outl); + +void mcf_pci_outsb(u32 addr, const u8 *buf, u32 len) +{ + for (; len; len--) + mcf_pci_outb(*buf++, addr); +} +EXPORT_SYMBOL(mcf_pci_outsb); + +void mcf_pci_outsw(u32 addr, const u16 *buf, u32 len) +{ + for (; len; len--) + mcf_pci_outw(*buf++, addr); +} +EXPORT_SYMBOL(mcf_pci_outsw); + +void mcf_pci_outsl(u32 addr, const u32 *buf, u32 len) +{ + for (; len; len--) + mcf_pci_outl(*buf++, addr); +} +EXPORT_SYMBOL(mcf_pci_outsl); + +/* + * Initialize the PCI bus registers, and scan the bus. + */ +static struct resource mcf_pci_mem = { + .name = "PCI Memory space", + .start = PCI_MEM_PA, + .end = PCI_MEM_PA + PCI_MEM_SIZE - 1, + .flags = IORESOURCE_MEM, +}; + +static struct resource mcf_pci_io = { + .name = "PCI IO space", + .start = 0x400, + .end = 0x10000 - 1, + .flags = IORESOURCE_IO, +}; + +/* + * Interrupt mapping and setting. + */ +static int mcf_pci_map_irq(const struct pci_dev *dev, u8 slot, u8 pin) +{ + int sid; + + sid = mcf_host_slot2sid[slot]; + if (sid) + return mcf_host_irq[sid]; + return 0; +} + +static int __init mcf_pci_init(void) +{ + pr_info("ColdFire: PCI bus initialization...\n"); + + /* Reset the external PCI bus */ + __raw_writel(PCIGSCR_RESET, PCIGSCR); + __raw_writel(0, PCITCR); + + request_resource(&iomem_resource, &mcf_pci_mem); + request_resource(&iomem_resource, &mcf_pci_io); + + /* Configure PCI arbiter */ + __raw_writel(PACR_INTMPRI | PACR_INTMINTE | PACR_EXTMPRI(0x1f) | + PACR_EXTMINTE(0x1f), PACR); + + /* Set required multi-function pins for PCI bus use */ + __raw_writew(0x3ff, MCF_PAR_PCIBG); + __raw_writew(0x3ff, MCF_PAR_PCIBR); + + /* Set up config space for local host bus controller */ + __raw_writel(PCI_COMMAND_MEMORY | PCI_COMMAND_MASTER | + PCI_COMMAND_INVALIDATE, PCISCR); + __raw_writel(PCICR1_LT(32) | PCICR1_CL(8), PCICR1); + __raw_writel(0, PCICR2); + + /* + * Set up the initiator windows for memory and IO mapping. + * These give the CPU bus access onto the PCI bus. One for each of + * PCI memory and IO address spaces. + */ + __raw_writel(WXBTAR(PCI_MEM_PA, PCI_MEM_BA, PCI_MEM_SIZE), + PCIIW0BTAR); + __raw_writel(WXBTAR(PCI_IO_PA, PCI_IO_BA, PCI_IO_SIZE), + PCIIW1BTAR); + __raw_writel(PCIIWCR_W0_MEM /*| PCIIWCR_W0_MRDL*/ | PCIIWCR_W0_E | + PCIIWCR_W1_IO | PCIIWCR_W1_E, PCIIWCR); + + /* + * Set up the target windows for access from the PCI bus back to the + * CPU bus. All we need is access to system RAM (for mastering). + */ + __raw_writel(CONFIG_RAMBASE, PCIBAR1); + __raw_writel(CONFIG_RAMBASE | PCITBATR1_E, PCITBATR1); + + /* Keep a virtual mapping to IO/config space active */ + iospace = (unsigned long) ioremap(PCI_IO_PA, PCI_IO_SIZE); + if (iospace == 0) + return -ENODEV; + pr_info("Coldfire: PCI IO/config window mapped to 0x%x\n", + (u32) iospace); + + /* Turn of PCI reset, and wait for devices to settle */ + __raw_writel(0, PCIGSCR); + set_current_state(TASK_UNINTERRUPTIBLE); + schedule_timeout(msecs_to_jiffies(200)); + + rootbus = pci_scan_bus(0, &mcf_pci_ops, NULL); + rootbus->resource[0] = &mcf_pci_io; + rootbus->resource[1] = &mcf_pci_mem; + + pci_fixup_irqs(pci_common_swizzle, mcf_pci_map_irq); + pci_bus_size_bridges(rootbus); + pci_bus_assign_resources(rootbus); + pci_enable_bridges(rootbus); + pci_bus_add_devices(rootbus); + return 0; +} + +subsys_initcall(mcf_pci_init); diff --git a/arch/m68k/platform/coldfire/pinmux.c b/arch/m68k/platform/coldfire/pinmux.c deleted file mode 100644 index 8c62b82..0000000 --- a/arch/m68k/platform/coldfire/pinmux.c +++ /dev/null @@ -1,28 +0,0 @@ -/* - * Coldfire generic GPIO pinmux support. - * - * (C) Copyright 2009, Steven King <sfking@fdwdc.com> - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; version 2 of the License. - * - * 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. - * - */ - -#include <linux/kernel.h> - -#include <asm/pinmux.h> - -int mcf_pinmux_request(unsigned pinmux, unsigned func) -{ - return 0; -} - -void mcf_pinmux_release(unsigned pinmux, unsigned func) -{ -} diff --git a/arch/m68k/platform/coldfire/pit.c b/arch/m68k/platform/coldfire/pit.c index e62dbbc..e8f3b97 100644 --- a/arch/m68k/platform/coldfire/pit.c +++ b/arch/m68k/platform/coldfire/pit.c @@ -93,7 +93,7 @@ struct clock_event_device cf_pit_clockevent = { .set_mode = init_cf_pit_timer, .set_next_event = cf_pit_next_event, .shift = 32, - .irq = MCFINT_VECBASE + MCFINT_PIT1, + .irq = MCF_IRQ_PIT1, }; @@ -159,7 +159,7 @@ void hw_timer_init(irq_handler_t handler) clockevent_delta2ns(0x3f, &cf_pit_clockevent); clockevents_register_device(&cf_pit_clockevent); - setup_irq(MCFINT_VECBASE + MCFINT_PIT1, &pit_irq); + setup_irq(MCF_IRQ_PIT1, &pit_irq); clocksource_register_hz(&pit_clk, FREQ); } diff --git a/arch/m68k/platform/coldfire/timers.c b/arch/m68k/platform/coldfire/timers.c index ed96ce5..0a273e7 100644 --- a/arch/m68k/platform/coldfire/timers.c +++ b/arch/m68k/platform/coldfire/timers.c @@ -36,7 +36,7 @@ */ void coldfire_profile_init(void); -#if defined(CONFIG_M532x) +#if defined(CONFIG_M532x) || defined(CONFIG_M5441x) #define __raw_readtrr __raw_readl #define __raw_writetrr __raw_writel #else diff --git a/drivers/spi/Kconfig b/drivers/spi/Kconfig index cd2fe35..cb90bc6 100644 --- a/drivers/spi/Kconfig +++ b/drivers/spi/Kconfig @@ -125,7 +125,7 @@ config SPI_BUTTERFLY config SPI_COLDFIRE_QSPI tristate "Freescale Coldfire QSPI controller" - depends on (M520x || M523x || M5249 || M527x || M528x || M532x) + depends on (M520x || M523x || M5249 || M525x || M527x || M528x || M532x) help This enables support for the Coldfire QSPI controller in master mode. |