config.c revision 2424f549020b6f87ea3b6e89fd7bd26ddf1f717b
1/***************************************************************************/ 2 3/* 4 * linux/arch/m68knommu/platform/5249/config.c 5 * 6 * Copyright (C) 2002, Greg Ungerer (gerg@snapgear.com) 7 */ 8 9/***************************************************************************/ 10 11#include <linux/kernel.h> 12#include <linux/param.h> 13#include <linux/init.h> 14#include <linux/io.h> 15#include <linux/spi/spi.h> 16#include <linux/gpio.h> 17#include <asm/machdep.h> 18#include <asm/coldfire.h> 19#include <asm/mcfsim.h> 20#include <asm/mcfqspi.h> 21 22/***************************************************************************/ 23 24#ifdef CONFIG_M5249C3 25 26static struct resource m5249_smc91x_resources[] = { 27 { 28 .start = 0xe0000300, 29 .end = 0xe0000300 + 0x100, 30 .flags = IORESOURCE_MEM, 31 }, 32 { 33 .start = MCFINTC2_GPIOIRQ6, 34 .end = MCFINTC2_GPIOIRQ6, 35 .flags = IORESOURCE_IRQ, 36 }, 37}; 38 39static struct platform_device m5249_smc91x = { 40 .name = "smc91x", 41 .id = 0, 42 .num_resources = ARRAY_SIZE(m5249_smc91x_resources), 43 .resource = m5249_smc91x_resources, 44}; 45 46#endif /* CONFIG_M5249C3 */ 47 48#if defined(CONFIG_SPI_COLDFIRE_QSPI) || defined(CONFIG_SPI_COLDFIRE_QSPI_MODULE) 49static struct resource m5249_qspi_resources[] = { 50 { 51 .start = MCFQSPI_BASE, 52 .end = MCFQSPI_BASE + MCFQSPI_SIZE - 1, 53 .flags = IORESOURCE_MEM, 54 }, 55 { 56 .start = MCF_IRQ_QSPI, 57 .end = MCF_IRQ_QSPI, 58 .flags = IORESOURCE_IRQ, 59 }, 60}; 61 62static int m5249_cs_setup(struct mcfqspi_cs_control *cs_control) 63{ 64 int status; 65 66 status = gpio_request(MCFQSPI_CS0, "MCFQSPI_CS0"); 67 if (status) { 68 pr_debug("gpio_request for MCFQSPI_CS0 failed\n"); 69 goto fail0; 70 } 71 status = gpio_direction_output(MCFQSPI_CS0, 1); 72 if (status) { 73 pr_debug("gpio_direction_output for MCFQSPI_CS0 failed\n"); 74 goto fail1; 75 } 76 77 status = gpio_request(MCFQSPI_CS1, "MCFQSPI_CS1"); 78 if (status) { 79 pr_debug("gpio_request for MCFQSPI_CS1 failed\n"); 80 goto fail1; 81 } 82 status = gpio_direction_output(MCFQSPI_CS1, 1); 83 if (status) { 84 pr_debug("gpio_direction_output for MCFQSPI_CS1 failed\n"); 85 goto fail2; 86 } 87 88 status = gpio_request(MCFQSPI_CS2, "MCFQSPI_CS2"); 89 if (status) { 90 pr_debug("gpio_request for MCFQSPI_CS2 failed\n"); 91 goto fail2; 92 } 93 status = gpio_direction_output(MCFQSPI_CS2, 1); 94 if (status) { 95 pr_debug("gpio_direction_output for MCFQSPI_CS2 failed\n"); 96 goto fail3; 97 } 98 99 status = gpio_request(MCFQSPI_CS3, "MCFQSPI_CS3"); 100 if (status) { 101 pr_debug("gpio_request for MCFQSPI_CS3 failed\n"); 102 goto fail3; 103 } 104 status = gpio_direction_output(MCFQSPI_CS3, 1); 105 if (status) { 106 pr_debug("gpio_direction_output for MCFQSPI_CS3 failed\n"); 107 goto fail4; 108 } 109 110 return 0; 111 112fail4: 113 gpio_free(MCFQSPI_CS3); 114fail3: 115 gpio_free(MCFQSPI_CS2); 116fail2: 117 gpio_free(MCFQSPI_CS1); 118fail1: 119 gpio_free(MCFQSPI_CS0); 120fail0: 121 return status; 122} 123 124static void m5249_cs_teardown(struct mcfqspi_cs_control *cs_control) 125{ 126 gpio_free(MCFQSPI_CS3); 127 gpio_free(MCFQSPI_CS2); 128 gpio_free(MCFQSPI_CS1); 129 gpio_free(MCFQSPI_CS0); 130} 131 132static void m5249_cs_select(struct mcfqspi_cs_control *cs_control, 133 u8 chip_select, bool cs_high) 134{ 135 switch (chip_select) { 136 case 0: 137 gpio_set_value(MCFQSPI_CS0, cs_high); 138 break; 139 case 1: 140 gpio_set_value(MCFQSPI_CS1, cs_high); 141 break; 142 case 2: 143 gpio_set_value(MCFQSPI_CS2, cs_high); 144 break; 145 case 3: 146 gpio_set_value(MCFQSPI_CS3, cs_high); 147 break; 148 } 149} 150 151static void m5249_cs_deselect(struct mcfqspi_cs_control *cs_control, 152 u8 chip_select, bool cs_high) 153{ 154 switch (chip_select) { 155 case 0: 156 gpio_set_value(MCFQSPI_CS0, !cs_high); 157 break; 158 case 1: 159 gpio_set_value(MCFQSPI_CS1, !cs_high); 160 break; 161 case 2: 162 gpio_set_value(MCFQSPI_CS2, !cs_high); 163 break; 164 case 3: 165 gpio_set_value(MCFQSPI_CS3, !cs_high); 166 break; 167 } 168} 169 170static struct mcfqspi_cs_control m5249_cs_control = { 171 .setup = m5249_cs_setup, 172 .teardown = m5249_cs_teardown, 173 .select = m5249_cs_select, 174 .deselect = m5249_cs_deselect, 175}; 176 177static struct mcfqspi_platform_data m5249_qspi_data = { 178 .bus_num = 0, 179 .num_chipselect = 4, 180 .cs_control = &m5249_cs_control, 181}; 182 183static struct platform_device m5249_qspi = { 184 .name = "mcfqspi", 185 .id = 0, 186 .num_resources = ARRAY_SIZE(m5249_qspi_resources), 187 .resource = m5249_qspi_resources, 188 .dev.platform_data = &m5249_qspi_data, 189}; 190 191static void __init m5249_qspi_init(void) 192{ 193 /* QSPI irq setup */ 194 writeb(MCFSIM_ICR_AUTOVEC | MCFSIM_ICR_LEVEL4 | MCFSIM_ICR_PRI0, 195 MCF_MBAR + MCFSIM_QSPIICR); 196 mcf_mapirq2imr(MCF_IRQ_QSPI, MCFINTC_QSPI); 197} 198#endif /* defined(CONFIG_SPI_COLDFIRE_QSPI) || defined(CONFIG_SPI_COLDFIRE_QSPI_MODULE) */ 199 200 201static struct platform_device *m5249_devices[] __initdata = { 202#ifdef CONFIG_M5249C3 203 &m5249_smc91x, 204#endif 205#if defined(CONFIG_SPI_COLDFIRE_QSPI) || defined(CONFIG_SPI_COLDFIRE_QSPI_MODULE) 206 &m5249_qspi, 207#endif 208}; 209 210/***************************************************************************/ 211 212#ifdef CONFIG_M5249C3 213 214static void __init m5249_smc91x_init(void) 215{ 216 u32 gpio; 217 218 /* Set the GPIO line as interrupt source for smc91x device */ 219 gpio = readl(MCF_MBAR2 + MCFSIM2_GPIOINTENABLE); 220 writel(gpio | 0x40, MCF_MBAR2 + MCFSIM2_GPIOINTENABLE); 221 222 gpio = readl(MCF_MBAR2 + MCFSIM2_INTLEVEL5); 223 writel(gpio | 0x04000000, MCF_MBAR2 + MCFSIM2_INTLEVEL5); 224} 225 226#endif /* CONFIG_M5249C3 */ 227 228/***************************************************************************/ 229 230static void __init m5249_timers_init(void) 231{ 232 /* Timer1 is always used as system timer */ 233 writeb(MCFSIM_ICR_AUTOVEC | MCFSIM_ICR_LEVEL6 | MCFSIM_ICR_PRI3, 234 MCF_MBAR + MCFSIM_TIMER1ICR); 235 mcf_mapirq2imr(MCF_IRQ_TIMER, MCFINTC_TIMER1); 236 237#ifdef CONFIG_HIGHPROFILE 238 /* Timer2 is to be used as a high speed profile timer */ 239 writeb(MCFSIM_ICR_AUTOVEC | MCFSIM_ICR_LEVEL7 | MCFSIM_ICR_PRI3, 240 MCF_MBAR + MCFSIM_TIMER2ICR); 241 mcf_mapirq2imr(MCF_IRQ_PROFILER, MCFINTC_TIMER2); 242#endif 243} 244 245/***************************************************************************/ 246 247void m5249_cpu_reset(void) 248{ 249 local_irq_disable(); 250 /* Set watchdog to soft reset, and enabled */ 251 __raw_writeb(0xc0, MCF_MBAR + MCFSIM_SYPCR); 252 for (;;) 253 /* wait for watchdog to timeout */; 254} 255 256/***************************************************************************/ 257 258void __init config_BSP(char *commandp, int size) 259{ 260 mach_reset = m5249_cpu_reset; 261 mach_sched_init = hw_timer_init; 262 m5249_timers_init(); 263#ifdef CONFIG_M5249C3 264 m5249_smc91x_init(); 265#endif 266#if defined(CONFIG_SPI_COLDFIRE_QSPI) || defined(CONFIG_SPI_COLDFIRE_QSPI_MODULE) 267 m5249_qspi_init(); 268#endif 269} 270 271/***************************************************************************/ 272 273static int __init init_BSP(void) 274{ 275 platform_add_devices(m5249_devices, ARRAY_SIZE(m5249_devices)); 276 return 0; 277} 278 279arch_initcall(init_BSP); 280 281/***************************************************************************/ 282