• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright 2004-2009 Analog Devices Inc.
3  *           2007-2008 HV Sistemas S.L.
4  *                      Javier Herrero <jherrero@hvsistemas.es>
5  *                2005 National ICT Australia (NICTA)
6  *                      Aidan Williams <aidan@nicta.com.au>
7  *
8  * Licensed under the GPL-2 or later.
9  */
10 
11 #include <linux/device.h>
12 #include <linux/platform_device.h>
13 #include <linux/mtd/mtd.h>
14 #include <linux/mtd/partitions.h>
15 #include <linux/spi/spi.h>
16 #include <linux/spi/flash.h>
17 #if IS_ENABLED(CONFIG_USB_ISP1362_HCD)
18 #include <linux/usb/isp1362.h>
19 #endif
20 #include <linux/irq.h>
21 
22 #include <asm/dma.h>
23 #include <asm/bfin5xx_spi.h>
24 #include <asm/reboot.h>
25 #include <asm/portmux.h>
26 
27 /*
28  * Name the Board for the /proc/cpuinfo
29  */
30 const char bfin_board_name[] = "HV Sistemas H8606";
31 
32 #if IS_ENABLED(CONFIG_RTC_DRV_BFIN)
33 static struct platform_device rtc_device = {
34 	.name = "rtc-bfin",
35 	.id   = -1,
36 };
37 #endif
38 
39 /*
40 *  Driver needs to know address, irq and flag pin.
41  */
42 #if IS_ENABLED(CONFIG_DM9000)
43 static struct resource dm9000_resources[] = {
44 	[0] = {
45 		.start	= 0x20300000,
46 		.end	= 0x20300002,
47 		.flags	= IORESOURCE_MEM,
48 	},
49 	[1] = {
50 		.start	= 0x20300004,
51 		.end	= 0x20300006,
52 		.flags	= IORESOURCE_MEM,
53 	},
54 	[2] = {
55 		.start	= IRQ_PF10,
56 		.end	= IRQ_PF10,
57 		.flags	= (IORESOURCE_IRQ | IORESOURCE_IRQ_HIGHEDGE |
58 		           IORESOURCE_IRQ_SHAREABLE),
59 	},
60 };
61 
62 static struct platform_device dm9000_device = {
63     .id			= 0,
64     .name		= "dm9000",
65     .resource		= dm9000_resources,
66     .num_resources	= ARRAY_SIZE(dm9000_resources),
67 };
68 #endif
69 
70 #if IS_ENABLED(CONFIG_SMC91X)
71 #include <linux/smc91x.h>
72 
73 static struct smc91x_platdata smc91x_info = {
74 	.flags = SMC91X_USE_16BIT | SMC91X_NOWAIT,
75 	.leda = RPC_LED_100_10,
76 	.ledb = RPC_LED_TX_RX,
77 };
78 
79 static struct resource smc91x_resources[] = {
80 	{
81 		.name = "smc91x-regs",
82 		.start = 0x20300300,
83 		.end = 0x20300300 + 16,
84 		.flags = IORESOURCE_MEM,
85 	}, {
86 		.start = IRQ_PROG_INTB,
87 		.end = IRQ_PROG_INTB,
88 		.flags = IORESOURCE_IRQ | IORESOURCE_IRQ_HIGHLEVEL,
89 	}, {
90 		.start = IRQ_PF7,
91 		.end = IRQ_PF7,
92 		.flags = IORESOURCE_IRQ | IORESOURCE_IRQ_HIGHLEVEL,
93 	},
94 };
95 
96 static struct platform_device smc91x_device = {
97 	.name = "smc91x",
98 	.id = 0,
99 	.num_resources = ARRAY_SIZE(smc91x_resources),
100 	.resource = smc91x_resources,
101 	.dev	= {
102 		.platform_data	= &smc91x_info,
103 	},
104 };
105 #endif
106 
107 #if IS_ENABLED(CONFIG_USB_NET2272)
108 static struct resource net2272_bfin_resources[] = {
109 	{
110 		.start = 0x20300000,
111 		.end = 0x20300000 + 0x100,
112 		.flags = IORESOURCE_MEM,
113 	}, {
114 		.start = IRQ_PF10,
115 		.end = IRQ_PF10,
116 		.flags = IORESOURCE_IRQ | IORESOURCE_IRQ_HIGHLEVEL,
117 	},
118 };
119 
120 static struct platform_device net2272_bfin_device = {
121 	.name = "net2272",
122 	.id = -1,
123 	.num_resources = ARRAY_SIZE(net2272_bfin_resources),
124 	.resource = net2272_bfin_resources,
125 };
126 #endif
127 
128 #if IS_ENABLED(CONFIG_SPI_BFIN5XX)
129 /* all SPI peripherals info goes here */
130 
131 #if IS_ENABLED(CONFIG_MTD_M25P80)
132 static struct mtd_partition bfin_spi_flash_partitions[] = {
133 	{
134 		.name = "bootloader (spi)",
135 		.size = 0x40000,
136 		.offset = 0,
137 		.mask_flags = MTD_CAP_ROM
138 	}, {
139 		.name = "fpga (spi)",
140 		.size =   0x30000,
141 		.offset = 0x40000
142 	}, {
143 		.name = "linux kernel (spi)",
144 		.size =   0x150000,
145 		.offset =  0x70000
146 	}, {
147 		.name = "jffs2 root file system (spi)",
148 		.size =   0x640000,
149 		.offset = 0x1c0000,
150 	}
151 };
152 
153 static struct flash_platform_data bfin_spi_flash_data = {
154 	.name = "m25p80",
155 	.parts = bfin_spi_flash_partitions,
156 	.nr_parts = ARRAY_SIZE(bfin_spi_flash_partitions),
157 	.type = "m25p64",
158 };
159 
160 /* SPI flash chip (m25p64) */
161 static struct bfin5xx_spi_chip spi_flash_chip_info = {
162 	.enable_dma = 0,         /* use dma transfer with this chip*/
163 };
164 #endif
165 
166 /* Notice: for blackfin, the speed_hz is the value of register
167  * SPI_BAUD, not the real baudrate */
168 static struct spi_board_info bfin_spi_board_info[] __initdata = {
169 #if IS_ENABLED(CONFIG_MTD_M25P80)
170 	{
171 		/* the modalias must be the same as spi device driver name */
172 		.modalias = "m25p80", /* Name of spi_driver for this device */
173 		/* this value is the baudrate divisor */
174 		.max_speed_hz = 50000000, /* actual baudrate is SCLK/(2xspeed_hz) */
175 		.bus_num = 0, /* Framework bus number */
176 		.chip_select = 2, /* Framework chip select. On STAMP537 it is SPISSEL2*/
177 		.platform_data = &bfin_spi_flash_data,
178 		.controller_data = &spi_flash_chip_info,
179 		.mode = SPI_MODE_3,
180 	},
181 #endif
182 
183 #if IS_ENABLED(CONFIG_SND_BF5XX_SOC_AD183X)
184 	{
185 		.modalias = "ad183x",
186 		.max_speed_hz = 16,
187 		.bus_num = 1,
188 		.chip_select = 4,
189 	},
190 #endif
191 
192 };
193 
194 /* SPI (0) */
195 static struct resource bfin_spi0_resource[] = {
196 	[0] = {
197 		.start = SPI0_REGBASE,
198 		.end   = SPI0_REGBASE + 0xFF,
199 		.flags = IORESOURCE_MEM,
200 	},
201 	[1] = {
202 		.start = CH_SPI,
203 		.end   = CH_SPI,
204 		.flags = IORESOURCE_DMA,
205 	},
206 	[2] = {
207 		.start = IRQ_SPI,
208 		.end   = IRQ_SPI,
209 		.flags = IORESOURCE_IRQ,
210 	}
211 };
212 
213 
214 /* SPI controller data */
215 static struct bfin5xx_spi_master bfin_spi0_info = {
216 	.num_chipselect = 8,
217 	.enable_dma = 1,  /* master has the ability to do dma transfer */
218 	.pin_req = {P_SPI0_SCK, P_SPI0_MISO, P_SPI0_MOSI, 0},
219 };
220 
221 static struct platform_device bfin_spi0_device = {
222 	.name = "bfin-spi",
223 	.id = 0, /* Bus number */
224 	.num_resources = ARRAY_SIZE(bfin_spi0_resource),
225 	.resource = bfin_spi0_resource,
226 	.dev = {
227 		.platform_data = &bfin_spi0_info, /* Passed to driver */
228 	},
229 };
230 #endif  /* spi master and devices */
231 
232 #if IS_ENABLED(CONFIG_SERIAL_BFIN)
233 #ifdef CONFIG_SERIAL_BFIN_UART0
234 static struct resource bfin_uart0_resources[] = {
235 	{
236 		.start = BFIN_UART_THR,
237 		.end = BFIN_UART_GCTL+2,
238 		.flags = IORESOURCE_MEM,
239 	},
240 	{
241 		.start = IRQ_UART0_TX,
242 		.end = IRQ_UART0_TX,
243 		.flags = IORESOURCE_IRQ,
244 	},
245 	{
246 		.start = IRQ_UART0_RX,
247 		.end = IRQ_UART0_RX,
248 		.flags = IORESOURCE_IRQ,
249 	},
250 	{
251 		.start = IRQ_UART0_ERROR,
252 		.end = IRQ_UART0_ERROR,
253 		.flags = IORESOURCE_IRQ,
254 	},
255 	{
256 		.start = CH_UART0_TX,
257 		.end = CH_UART0_TX,
258 		.flags = IORESOURCE_DMA,
259 	},
260 	{
261 		.start = CH_UART0_RX,
262 		.end = CH_UART0_RX,
263 		.flags = IORESOURCE_DMA,
264 	},
265 };
266 
267 static unsigned short bfin_uart0_peripherals[] = {
268 	P_UART0_TX, P_UART0_RX, 0
269 };
270 
271 static struct platform_device bfin_uart0_device = {
272 	.name = "bfin-uart",
273 	.id = 0,
274 	.num_resources = ARRAY_SIZE(bfin_uart0_resources),
275 	.resource = bfin_uart0_resources,
276 	.dev = {
277 		.platform_data = &bfin_uart0_peripherals, /* Passed to driver */
278 	},
279 };
280 #endif
281 #endif
282 
283 #if IS_ENABLED(CONFIG_BFIN_SIR)
284 #ifdef CONFIG_BFIN_SIR0
285 static struct resource bfin_sir0_resources[] = {
286 	{
287 		.start = 0xFFC00400,
288 		.end = 0xFFC004FF,
289 		.flags = IORESOURCE_MEM,
290 	},
291 	{
292 		.start = IRQ_UART0_RX,
293 		.end = IRQ_UART0_RX+1,
294 		.flags = IORESOURCE_IRQ,
295 	},
296 	{
297 		.start = CH_UART0_RX,
298 		.end = CH_UART0_RX+1,
299 		.flags = IORESOURCE_DMA,
300 	},
301 };
302 
303 static struct platform_device bfin_sir0_device = {
304 	.name = "bfin_sir",
305 	.id = 0,
306 	.num_resources = ARRAY_SIZE(bfin_sir0_resources),
307 	.resource = bfin_sir0_resources,
308 };
309 #endif
310 #endif
311 
312 #if IS_ENABLED(CONFIG_SERIAL_8250)
313 
314 #include <linux/serial_8250.h>
315 #include <linux/serial.h>
316 
317 /*
318  * Configuration for two 16550 UARTS in FPGA at addresses 0x20200000 and 0x202000010.
319  * running at half system clock, both with interrupt output or-ed to PF8. Change to
320  * suit different FPGA configuration, or to suit real 16550 UARTS connected to the bus
321  */
322 
323 static struct plat_serial8250_port serial8250_platform_data [] = {
324 	{
325 		.membase = (void *)0x20200000,
326 		.mapbase = 0x20200000,
327 		.irq = IRQ_PF8,
328 		.irqflags = IRQF_TRIGGER_HIGH,
329 		.flags = UPF_BOOT_AUTOCONF | UART_CONFIG_TYPE,
330 		.iotype = UPIO_MEM,
331 		.regshift = 1,
332 		.uartclk = 66666667,
333 	}, {
334 		.membase = (void *)0x20200010,
335 		.mapbase = 0x20200010,
336 		.irq = IRQ_PF8,
337 		.irqflags = IRQF_TRIGGER_HIGH,
338 		.flags = UPF_BOOT_AUTOCONF | UART_CONFIG_TYPE,
339 		.iotype = UPIO_MEM,
340 		.regshift = 1,
341 		.uartclk = 66666667,
342 	}, {
343 	}
344 };
345 
346 static struct platform_device serial8250_device = {
347 	.id		= PLAT8250_DEV_PLATFORM,
348 	.name		= "serial8250",
349 	.dev		= {
350 		.platform_data = serial8250_platform_data,
351 	},
352 };
353 
354 #endif
355 
356 #if IS_ENABLED(CONFIG_KEYBOARD_OPENCORES)
357 
358 /*
359  * Configuration for one OpenCores keyboard controller in FPGA at address 0x20200030,
360  * interrupt output wired to PF9. Change to suit different FPGA configuration
361  */
362 
363 static struct resource opencores_kbd_resources[] = {
364 	[0] = {
365 		.start	= 0x20200030,
366 		.end	= 0x20300030 + 2,
367 		.flags	= IORESOURCE_MEM,
368 	},
369 	[1] = {
370 		.start	= IRQ_PF9,
371 		.end	= IRQ_PF9,
372 		.flags	= IORESOURCE_IRQ | IORESOURCE_IRQ_HIGHEDGE,
373 	},
374 };
375 
376 static struct platform_device opencores_kbd_device = {
377 	.id		= -1,
378 	.name		= "opencores-kbd",
379 	.resource	= opencores_kbd_resources,
380 	.num_resources	= ARRAY_SIZE(opencores_kbd_resources),
381 };
382 #endif
383 
384 static struct platform_device *h8606_devices[] __initdata = {
385 #if IS_ENABLED(CONFIG_RTC_DRV_BFIN)
386 	&rtc_device,
387 #endif
388 
389 #if IS_ENABLED(CONFIG_DM9000)
390 	&dm9000_device,
391 #endif
392 
393 #if IS_ENABLED(CONFIG_SMC91X)
394 	&smc91x_device,
395 #endif
396 
397 #if IS_ENABLED(CONFIG_USB_NET2272)
398 	&net2272_bfin_device,
399 #endif
400 
401 #if IS_ENABLED(CONFIG_SPI_BFIN5XX)
402 	&bfin_spi0_device,
403 #endif
404 
405 #if IS_ENABLED(CONFIG_SERIAL_BFIN)
406 #ifdef CONFIG_SERIAL_BFIN_UART0
407 	&bfin_uart0_device,
408 #endif
409 #endif
410 
411 #if IS_ENABLED(CONFIG_SERIAL_8250)
412 	&serial8250_device,
413 #endif
414 
415 #if IS_ENABLED(CONFIG_BFIN_SIR)
416 #ifdef CONFIG_BFIN_SIR0
417 	&bfin_sir0_device,
418 #endif
419 #endif
420 
421 #if IS_ENABLED(CONFIG_KEYBOARD_OPENCORES)
422 	&opencores_kbd_device,
423 #endif
424 };
425 
H8606_init(void)426 static int __init H8606_init(void)
427 {
428 	printk(KERN_INFO "HV Sistemas H8606 board support by http://www.hvsistemas.com\n");
429 	printk(KERN_INFO "%s(): registering device resources\n", __func__);
430 	platform_add_devices(h8606_devices, ARRAY_SIZE(h8606_devices));
431 #if IS_ENABLED(CONFIG_SPI_BFIN5XX)
432 	spi_register_board_info(bfin_spi_board_info, ARRAY_SIZE(bfin_spi_board_info));
433 #endif
434 	return 0;
435 }
436 
437 arch_initcall(H8606_init);
438 
439 static struct platform_device *H8606_early_devices[] __initdata = {
440 #if defined(CONFIG_SERIAL_BFIN_CONSOLE) || defined(CONFIG_EARLY_PRINTK)
441 #ifdef CONFIG_SERIAL_BFIN_UART0
442 	&bfin_uart0_device,
443 #endif
444 #endif
445 };
446 
native_machine_early_platform_add_devices(void)447 void __init native_machine_early_platform_add_devices(void)
448 {
449 	printk(KERN_INFO "register early platform devices\n");
450 	early_platform_add_devices(H8606_early_devices,
451 		ARRAY_SIZE(H8606_early_devices));
452 }
453