2 +++ b/arch/arm/mach-cns3xxx/laguna.c
5 + * Gateworks Corporation Laguna Platform
7 + * Copyright 2000 Deep Blue Solutions Ltd
8 + * Copyright 2008 ARM Limited
9 + * Copyright 2008 Cavium Networks
11 + * Copyright 2010 MontaVista Software, LLC.
12 + * Anton Vorontsov <avorontsov@mvista.com>
13 + * Copyright 2011 Gateworks Corporation
14 + * Chris Lang <clang@gateworks.com>
16 + * This file is free software; you can redistribute it and/or modify
17 + * it under the terms of the GNU General Public License, Version 2, as
18 + * published by the Free Software Foundation.
21 +#include <linux/init.h>
22 +#include <linux/kernel.h>
23 +#include <linux/compiler.h>
24 +#include <linux/io.h>
25 +#include <linux/dma-mapping.h>
26 +#include <linux/serial_core.h>
27 +#include <linux/serial_8250.h>
28 +#include <linux/platform_device.h>
29 +#include <linux/mtd/mtd.h>
30 +#include <linux/mtd/physmap.h>
31 +#include <linux/mtd/partitions.h>
32 +#include <linux/leds.h>
33 +#include <linux/i2c.h>
34 +#include <linux/i2c/at24.h>
35 +#include <linux/i2c/pca953x.h>
36 +#include <linux/spi/spi.h>
37 +#include <linux/spi/flash.h>
38 +#include <linux/if_ether.h>
39 +#include <asm/setup.h>
40 +#include <asm/mach-types.h>
41 +#include <asm/mach/arch.h>
42 +#include <asm/mach/map.h>
43 +#include <asm/mach/time.h>
44 +#include <mach/hardware.h>
45 +#include <mach/cns3xxx.h>
46 +#include <mach/irqs.h>
52 +#define ETH0_LOAD BIT(0)
53 +#define ETH1_LOAD BIT(1)
54 +#define ETH2_LOAD BIT(2)
55 +#define SATA0_LOAD BIT(3)
56 +#define SATA1_LOAD BIT(4)
57 +#define PCM_LOAD BIT(5)
58 +#define I2S_LOAD BIT(6)
59 +#define SPI0_LOAD BIT(7)
60 +#define SPI1_LOAD BIT(8)
61 +#define PCIE0_LOAD BIT(9)
62 +#define PCIE1_LOAD BIT(10)
63 +#define USB0_LOAD BIT(11)
64 +#define USB1_LOAD BIT(12)
65 +#define USB1_ROUTE BIT(13)
66 +#define SD_LOAD BIT(14)
67 +#define UART0_LOAD BIT(15)
68 +#define UART1_LOAD BIT(16)
69 +#define UART2_LOAD BIT(17)
70 +#define MPCI0_LOAD BIT(18)
71 +#define MPCI1_LOAD BIT(19)
72 +#define MPCI2_LOAD BIT(20)
73 +#define MPCI3_LOAD BIT(21)
74 +#define FP_BUT_LOAD BIT(22)
75 +#define FP_BUT_HEADER_LOAD BIT(23)
76 +#define FP_LED_LOAD BIT(24)
77 +#define FP_LED_HEADER_LOAD BIT(25)
78 +#define FP_TAMPER_LOAD BIT(26)
79 +#define HEADER_33V_LOAD BIT(27)
80 +#define SATA_POWER_LOAD BIT(28)
81 +#define FP_POWER_LOAD BIT(29)
82 +#define GPIO_HEADER_LOAD BIT(30)
83 +#define GSP_BAT_LOAD BIT(31)
86 +#define FAN_LOAD BIT(0)
87 +#define SPI_FLASH_LOAD BIT(1)
88 +#define NOR_FLASH_LOAD BIT(2)
89 +#define GPS_LOAD BIT(3)
90 +#define SUPPLY_5V_LOAD BIT(6)
91 +#define SUPPLY_33V_LOAD BIT(7)
93 +struct laguna_board_info {
101 +static struct laguna_board_info laguna_info __initdata;
106 +static struct mtd_partition laguna_nor_partitions[] = {
111 + .mask_flags = MTD_WRITEABLE,
119 + .offset = SZ_256K + SZ_128K,
122 + .size = SZ_16M - SZ_256K - SZ_128K - SZ_2M,
123 + .offset = SZ_256K + SZ_128K + SZ_2M,
127 +static struct physmap_flash_data laguna_nor_pdata = {
129 + .parts = laguna_nor_partitions,
130 + .nr_parts = ARRAY_SIZE(laguna_nor_partitions),
133 +static struct resource laguna_nor_res = {
134 + .start = CNS3XXX_FLASH_BASE,
135 + .end = CNS3XXX_FLASH_BASE + SZ_128M - 1,
136 + .flags = IORESOURCE_MEM | IORESOURCE_MEM_32BIT,
139 +static struct platform_device laguna_nor_pdev = {
140 + .name = "physmap-flash",
142 + .resource = &laguna_nor_res,
143 + .num_resources = 1,
145 + .platform_data = &laguna_nor_pdata,
152 +static struct mtd_partition laguna_spi_partitions[] = {
157 + .mask_flags = MTD_WRITEABLE,
164 + .size = SZ_1M + SZ_512K,
168 + .size = SZ_16M - SZ_2M,
173 +static struct flash_platform_data laguna_spi_pdata = {
174 + .parts = laguna_spi_partitions,
175 + .nr_parts = ARRAY_SIZE(laguna_spi_partitions),
178 +static struct spi_board_info __initdata laguna_spi_devices[] = {
180 + .modalias = "m25p80",
181 + .platform_data = &laguna_spi_pdata,
182 + .max_speed_hz = 50000000,
188 +static struct platform_device laguna_spi_controller = {
189 + .name = "cns3xxx_spi",
195 +static struct gpio_led laguna_gpio_leds[] = {
197 + .name = "user1", /* Green Led */
201 + .name = "user2", /* Red Led */
207 +static struct gpio_led_platform_data laguna_gpio_leds_data = {
209 + .leds = laguna_gpio_leds,
212 +static struct platform_device laguna_gpio_leds_device = {
213 + .name = "leds-gpio",
215 + .dev.platform_data = &laguna_gpio_leds_data,
221 +static struct cns3xxx_plat_info laguna_net_data = {
230 +static struct platform_device laguna_net_device = {
231 + .name = "cns3xxx_eth",
233 + .dev.platform_data = &laguna_net_data,
239 +static void __init laguna_early_serial_setup(void)
241 +#ifdef CONFIG_SERIAL_8250_CONSOLE
242 + static struct uart_port laguna_serial_port = {
243 + .membase = (void __iomem *)CNS3XXX_UART0_BASE_VIRT,
244 + .mapbase = CNS3XXX_UART0_BASE,
245 + .irq = IRQ_CNS3XXX_UART0,
246 + .iotype = UPIO_MEM,
247 + .flags = UPF_BOOT_AUTOCONF | UPF_FIXED_TYPE,
249 + .uartclk = 24000000,
251 + .type = PORT_16550A,
255 + early_serial_setup(&laguna_serial_port);
259 +static struct resource laguna_uart_resources[] = {
261 + .start = CNS3XXX_UART0_BASE,
262 + .end = CNS3XXX_UART0_BASE + SZ_4K - 1,
263 + .flags = IORESOURCE_MEM
265 + .start = CNS3XXX_UART2_BASE,
266 + .end = CNS3XXX_UART2_BASE + SZ_4K - 1,
267 + .flags = IORESOURCE_MEM
269 + .start = CNS3XXX_UART2_BASE,
270 + .end = CNS3XXX_UART2_BASE + SZ_4K - 1,
271 + .flags = IORESOURCE_MEM
275 +static struct plat_serial8250_port laguna_uart_data[] = {
277 + .membase = (char*) (CNS3XXX_UART0_BASE_VIRT),
278 + .mapbase = (CNS3XXX_UART0_BASE),
279 + .irq = IRQ_CNS3XXX_UART0,
280 + .iotype = UPIO_MEM,
281 + .flags = UPF_BOOT_AUTOCONF | UPF_FIXED_TYPE | UPF_NO_TXEN_TEST,
283 + .uartclk = 24000000,
284 + .type = PORT_16550A,
286 + .membase = (char*) (CNS3XXX_UART1_BASE_VIRT),
287 + .mapbase = (CNS3XXX_UART1_BASE),
288 + .irq = IRQ_CNS3XXX_UART1,
289 + .iotype = UPIO_MEM,
290 + .flags = UPF_BOOT_AUTOCONF | UPF_FIXED_TYPE | UPF_NO_TXEN_TEST,
292 + .uartclk = 24000000,
293 + .type = PORT_16550A,
295 + .membase = (char*) (CNS3XXX_UART2_BASE_VIRT),
296 + .mapbase = (CNS3XXX_UART2_BASE),
297 + .irq = IRQ_CNS3XXX_UART2,
298 + .iotype = UPIO_MEM,
299 + .flags = UPF_BOOT_AUTOCONF | UPF_FIXED_TYPE | UPF_NO_TXEN_TEST,
301 + .uartclk = 24000000,
302 + .type = PORT_16550A,
306 +static struct platform_device laguna_uart = {
307 + .name = "serial8250",
308 + .id = PLAT8250_DEV_PLATFORM,
309 + .dev.platform_data = laguna_uart_data,
310 + .num_resources = 3,
311 + .resource = laguna_uart_resources
317 +static struct resource cns3xxx_usb_ehci_resources[] = {
319 + .start = CNS3XXX_USB_BASE,
320 + .end = CNS3XXX_USB_BASE + SZ_16M - 1,
321 + .flags = IORESOURCE_MEM,
324 + .start = IRQ_CNS3XXX_USB_EHCI,
325 + .flags = IORESOURCE_IRQ,
329 +static u64 cns3xxx_usb_ehci_dma_mask = DMA_BIT_MASK(32);
331 +static struct platform_device cns3xxx_usb_ehci_device = {
332 + .name = "cns3xxx-ehci",
333 + .num_resources = ARRAY_SIZE(cns3xxx_usb_ehci_resources),
334 + .resource = cns3xxx_usb_ehci_resources,
336 + .dma_mask = &cns3xxx_usb_ehci_dma_mask,
337 + .coherent_dma_mask = DMA_BIT_MASK(32),
341 +static struct resource cns3xxx_usb_ohci_resources[] = {
343 + .start = CNS3XXX_USB_OHCI_BASE,
344 + .end = CNS3XXX_USB_OHCI_BASE + SZ_16M - 1,
345 + .flags = IORESOURCE_MEM,
348 + .start = IRQ_CNS3XXX_USB_OHCI,
349 + .flags = IORESOURCE_IRQ,
353 +static u64 cns3xxx_usb_ohci_dma_mask = DMA_BIT_MASK(32);
355 +static struct platform_device cns3xxx_usb_ohci_device = {
356 + .name = "cns3xxx-ohci",
357 + .num_resources = ARRAY_SIZE(cns3xxx_usb_ohci_resources),
358 + .resource = cns3xxx_usb_ohci_resources,
360 + .dma_mask = &cns3xxx_usb_ohci_dma_mask,
361 + .coherent_dma_mask = DMA_BIT_MASK(32),
365 +static struct resource cns3xxx_usb_otg_resources[] = {
367 + .start = CNS3XXX_USBOTG_BASE,
368 + .end = CNS3XXX_USBOTG_BASE + SZ_16M - 1,
369 + .flags = IORESOURCE_MEM,
372 + .start = IRQ_CNS3XXX_USB_OTG,
373 + .flags = IORESOURCE_IRQ,
377 +static u64 cns3xxx_usb_otg_dma_mask = DMA_BIT_MASK(32);
379 +static struct platform_device cns3xxx_usb_otg_device = {
381 + .num_resources = ARRAY_SIZE(cns3xxx_usb_otg_resources),
382 + .resource = cns3xxx_usb_otg_resources,
384 + .dma_mask = &cns3xxx_usb_otg_dma_mask,
385 + .coherent_dma_mask = DMA_BIT_MASK(32),
392 +static struct resource laguna_i2c_resource[] = {
394 + .start = CNS3XXX_SSP_BASE + 0x20,
396 + .flags = IORESOURCE_MEM,
398 + .start = IRQ_CNS3XXX_I2C,
399 + .flags = IORESOURCE_IRQ,
403 +static struct platform_device laguna_i2c_controller = {
404 + .name = "cns3xxx-i2c",
405 + .num_resources = 2,
406 + .resource = laguna_i2c_resource,
409 +static struct memory_accessor *at24_mem_acc;
411 +static void at24_setup(struct memory_accessor *mem_acc, void *context)
415 + at24_mem_acc = mem_acc;
417 + /* Read MAC addresses */
418 + if (at24_mem_acc->read(at24_mem_acc, buf, 0x100, 6) == 6)
419 + memcpy(&laguna_net_data.hwaddr[0], buf, ETH_ALEN);
420 + if (at24_mem_acc->read(at24_mem_acc, buf, 0x106, 6) == 6)
421 + memcpy(&laguna_net_data.hwaddr[1], buf, ETH_ALEN);
422 + if (at24_mem_acc->read(at24_mem_acc, buf, 0x10C, 6) == 6)
423 + memcpy(&laguna_net_data.hwaddr[2], buf, ETH_ALEN);
424 + if (at24_mem_acc->read(at24_mem_acc, buf, 0x112, 6) == 6)
425 + memcpy(&laguna_net_data.hwaddr[3], buf, ETH_ALEN);
427 + /* Read out Model Information */
428 + if (at24_mem_acc->read(at24_mem_acc, buf, 0x130, 16) == 16)
429 + memcpy(&laguna_info.model, buf, 16);
430 + if (at24_mem_acc->read(at24_mem_acc, buf, 0x140, 1) == 1)
431 + memcpy(&laguna_info.nor_flash_size, buf, 1);
432 + if (at24_mem_acc->read(at24_mem_acc, buf, 0x141, 1) == 1)
433 + memcpy(&laguna_info.spi_flash_size, buf, 1);
434 + if (at24_mem_acc->read(at24_mem_acc, buf, 0x142, 4) == 4)
435 + memcpy(&laguna_info.config_bitmap, buf, 4);
436 + if (at24_mem_acc->read(at24_mem_acc, buf, 0x146, 4) == 4)
437 + memcpy(&laguna_info.config2_bitmap, buf, 4);
440 +static struct at24_platform_data laguna_eeprom_info = {
443 + .flags = AT24_FLAG_READONLY,
444 + .setup = at24_setup,
447 +static struct pca953x_platform_data laguna_pca_data = {
451 +static struct i2c_board_info __initdata laguna_i2c_devices[] = {
453 + I2C_BOARD_INFO("pca9555", 0x23),
454 + .platform_data = &laguna_pca_data,
456 + I2C_BOARD_INFO("gsp", 0x29),
458 + I2C_BOARD_INFO ("24c08",0x50),
459 + .platform_data = &laguna_eeprom_info,
461 + I2C_BOARD_INFO("ds1672", 0x68),
469 +static struct resource laguna_watchdog_resource[] = {
471 + .start = CNS3XXX_TC11MP_TWD_BASE,
472 + .end = CNS3XXX_TC11MP_TWD_BASE + SZ_4K - 1,
473 + .flags = IORESOURCE_MEM,
475 + .start = IRQ_LOCALWDOG,
476 + .end = IRQ_LOCALWDOG,
477 + .flags = IORESOURCE_IRQ,
481 +static struct platform_device laguna_watchdog = {
482 + .name = "mpcore_wdt",
484 + .num_resources = ARRAY_SIZE(laguna_watchdog_resource),
485 + .resource = laguna_watchdog_resource,
492 +static void __init laguna_init(void)
494 + platform_device_register(&laguna_watchdog);
496 + platform_device_register(&laguna_i2c_controller);
498 + i2c_register_board_info(0, laguna_i2c_devices,
499 + ARRAY_SIZE(laguna_i2c_devices));
502 + pm_power_off = cns3xxx_power_off;
505 +static struct map_desc laguna_io_desc[] __initdata = {
507 + .virtual = CNS3XXX_UART0_BASE_VIRT,
508 + .pfn = __phys_to_pfn(CNS3XXX_UART0_BASE),
512 + .virtual = CNS3XXX_UART1_BASE_VIRT,
513 + .pfn = __phys_to_pfn(CNS3XXX_UART1_BASE),
517 + .virtual = CNS3XXX_UART2_BASE_VIRT,
518 + .pfn = __phys_to_pfn(CNS3XXX_UART2_BASE),
524 +static void __init laguna_map_io(void)
527 + iotable_init(laguna_io_desc, ARRAY_SIZE(laguna_io_desc));
529 + laguna_early_serial_setup();
533 +static int __init laguna_model_setup(void)
537 + u8 pcie_bitmap = 0;
539 + printk("Running on Gateworks Laguna %s\n", laguna_info.model);
541 + if (strncmp(laguna_info.model, "GW", 2) == 0) {
542 + if (laguna_info.config_bitmap & ETH0_LOAD)
543 + laguna_net_data.ports |= BIT(0);
544 + if (laguna_info.config_bitmap & ETH1_LOAD)
545 + laguna_net_data.ports |= BIT(1);
546 + if (laguna_info.config_bitmap & ETH2_LOAD)
547 + laguna_net_data.ports |= BIT(2);
548 + if (laguna_net_data.ports)
549 + platform_device_register(&laguna_net_device);
551 + if (laguna_info.config_bitmap & (SATA0_LOAD | SATA1_LOAD))
552 + cns3xxx_ahci_init();
554 + if (laguna_info.config_bitmap & (PCIE0_LOAD))
555 + pcie_bitmap |= 0x1;
557 + if (laguna_info.config_bitmap & (PCIE1_LOAD))
558 + pcie_bitmap |= 0x2;
560 + cns3xxx_pcie_init(pcie_bitmap);
562 + if (laguna_info.config_bitmap & (USB0_LOAD)) {
563 + cns3xxx_pwr_power_up(1 << PM_PLL_HM_PD_CTRL_REG_OFFSET_PLL_USB);
565 + /* DRVVBUS pins share with GPIOA */
566 + mem = (void __iomem *)(CNS3XXX_MISC_BASE_VIRT + 0x0014);
567 + reg = __raw_readl(mem);
569 + __raw_writel(reg, mem);
572 + mem = (void __iomem *)(CNS3XXX_MISC_BASE_VIRT + 0x0808);
573 + reg = __raw_readl(mem);
575 + __raw_writel(reg, mem);
577 + platform_device_register(&cns3xxx_usb_otg_device);
580 + if (laguna_info.config_bitmap & (USB1_LOAD)) {
581 + platform_device_register(&cns3xxx_usb_ehci_device);
582 + platform_device_register(&cns3xxx_usb_ohci_device);
585 + if (laguna_info.config_bitmap & (SD_LOAD))
586 + cns3xxx_sdhci_init();
588 + if (laguna_info.config_bitmap & (UART0_LOAD))
589 + laguna_uart.num_resources = 1;
590 + if (laguna_info.config_bitmap & (UART1_LOAD))
591 + laguna_uart.num_resources = 2;
592 + if (laguna_info.config_bitmap & (UART2_LOAD))
593 + laguna_uart.num_resources = 3;
594 + platform_device_register(&laguna_uart);
596 + if (laguna_info.config2_bitmap & (NOR_FLASH_LOAD)) {
597 + switch (laguna_info.nor_flash_size) {
599 + laguna_nor_partitions[3].size = SZ_8M - SZ_256K - SZ_128K - SZ_2M;
600 + laguna_nor_res.end = CNS3XXX_FLASH_BASE + SZ_8M - 1;
603 + laguna_nor_partitions[3].size = SZ_16M - SZ_256K - SZ_128K - SZ_2M;
604 + laguna_nor_res.end = CNS3XXX_FLASH_BASE + SZ_16M - 1;
607 + laguna_nor_partitions[3].size = SZ_32M - SZ_256K - SZ_128K - SZ_2M;
608 + laguna_nor_res.end = CNS3XXX_FLASH_BASE + SZ_32M - 1;
611 + laguna_nor_partitions[3].size = SZ_64M - SZ_256K - SZ_128K - SZ_2M;
612 + laguna_nor_res.end = CNS3XXX_FLASH_BASE + SZ_64M - 1;
615 + laguna_nor_partitions[3].size = SZ_128M - SZ_256K - SZ_128K - SZ_2M;
616 + laguna_nor_res.end = CNS3XXX_FLASH_BASE + SZ_128M - 1;
619 + platform_device_register(&laguna_nor_pdev);
622 + if (laguna_info.config2_bitmap & (SPI_FLASH_LOAD)) {
623 + switch (laguna_info.spi_flash_size) {
625 + laguna_spi_partitions[3].size = SZ_4M - SZ_2M;
628 + laguna_spi_partitions[3].size = SZ_8M - SZ_2M;
631 + laguna_spi_partitions[3].size = SZ_16M - SZ_2M;
634 + laguna_spi_partitions[3].size = SZ_32M - SZ_2M;
637 + laguna_spi_partitions[3].size = SZ_64M - SZ_2M;
640 + spi_register_board_info(laguna_spi_devices, ARRAY_SIZE(laguna_spi_devices));
643 + if (laguna_info.config_bitmap & (SPI0_LOAD | SPI1_LOAD)) {
644 + platform_device_register(&laguna_spi_controller);
648 + * Do any model specific setup not known by the bitmap by matching
649 + * the first 6 characters of the model name
652 + if (strncmp(laguna_info.model, "GW2388", 6) == 0) {
653 + platform_device_register(&laguna_gpio_leds_device);
654 + } else if (strncmp(laguna_info.model, "GW2380", 6) == 0) {
655 + laguna_gpio_leds[0].gpio = 107;
656 + laguna_gpio_leds[1].gpio = 106;
657 + laguna_gpio_leds_data.num_leds = 2;
658 + platform_device_register(&laguna_gpio_leds_device);
661 + // Do some defaults here, not sure what yet
666 +late_initcall(laguna_model_setup);
668 +MACHINE_START(GW2388, "Gateworks Corporation Laguna Platform")
669 + .boot_params = 0x00000100,
670 + .map_io = laguna_map_io,
671 + .init_irq = cns3xxx_init_irq,
672 + .timer = &cns3xxx_timer,
673 + .init_machine = laguna_init,
675 --- a/arch/arm/mach-cns3xxx/Kconfig
676 +++ b/arch/arm/mach-cns3xxx/Kconfig
677 @@ -10,4 +10,13 @@ config MACH_CNS3420VB
678 This is a platform with an on-board ARM11 MPCore and has support
679 for USB, USB-OTG, MMC/SD/SDIO, SATA, PCI-E, etc.
682 + bool "Support for Gateworks Laguna Platform"
683 + select MIGHT_HAVE_PCI
685 + Include support for the Gateworks Laguna Platform
687 + This is a platform with an on-board ARM11 MPCore and has support
688 + for USB, USB-OTG, MMC/SD/SDIO, SATA, PCI-E, I2C, GIG, etc.
691 --- a/arch/arm/mach-cns3xxx/core.c
692 +++ b/arch/arm/mach-cns3xxx/core.c
694 #include <asm/mach/time.h>
695 #include <asm/mach/irq.h>
696 #include <asm/hardware/gic.h>
697 +#include <asm/smp_twd.h>
698 #include <mach/cns3xxx.h>
701 @@ -60,11 +61,24 @@ static struct map_desc cns3xxx_io_desc[]
702 .pfn = __phys_to_pfn(CNS3XXX_PM_BASE),
706 + .virtual = CNS3XXX_SWITCH_BASE_VIRT,
707 + .pfn = __phys_to_pfn(CNS3XXX_SWITCH_BASE),
711 + .virtual = CNS3XXX_SSP_BASE_VIRT,
712 + .pfn = __phys_to_pfn(CNS3XXX_SSP_BASE),
718 void __init cns3xxx_map_io(void)
720 +#ifdef CONFIG_LOCAL_TIMERS
721 + twd_base = (void __iomem *) CNS3XXX_TC11MP_TWD_BASE_VIRT;
723 iotable_init(cns3xxx_io_desc, ARRAY_SIZE(cns3xxx_io_desc));
726 --- a/arch/arm/Kconfig
727 +++ b/arch/arm/Kconfig
728 @@ -313,6 +313,7 @@ config ARCH_CLPS711X
730 bool "Cavium Networks CNS3XXX family"
732 + select ARCH_WANT_OPTIONAL_GPIOLIB
733 select GENERIC_CLOCKEVENTS
735 select MIGHT_HAVE_PCI
737 +++ b/arch/arm/mach-cns3xxx/include/mach/gpio.h
740 + * arch/arm/mach-cns3xxx/include/mach/gpio.h
742 + * CNS3xxx GPIO wrappers for arch-neutral GPIO calls
744 + * Copyright 2011 Gateworks Corporation
745 + * Chris Lang <clang@gateworks.com>
747 + * Based on IXP implementation by Milan Svoboda <msvoboda@ra.rockwell.com>
748 + * Based on PXA implementation by Philipp Zabel <philipp.zabel@gmail.com>
750 + * This program is free software; you can redistribute it and/or modify
751 + * it under the terms of the GNU General Public License as published by
752 + * the Free Software Foundation; either version 2 of the License, or
753 + * (at your option) any later version.
755 + * This program is distributed in the hope that it will be useful,
756 + * but WITHOUT ANY WARRANTY; without even the implied warranty of
757 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
758 + * GNU General Public License for more details.
760 + * You should have received a copy of the GNU General Public License
761 + * along with this program; if not, write to the Free Software
762 + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
766 +#ifndef __ASM_ARCH_CNS3XXX_GPIO_H
767 +#define __ASM_ARCH_CNS3XXX_GPIO_H
769 +#include <linux/kernel.h>
770 +#include <linux/io.h>
771 +#include <mach/hardware.h>
772 +#include <asm-generic/gpio.h> /* cansleep wrappers */
774 +#define NR_BUILTIN_GPIO 64
776 +#define CNS3XXX_GPIO_IN 0x0
777 +#define CNS3XXX_GPIO_OUT 0x1
779 +#define CNS3XXX_GPIO_LO 0
780 +#define CNS3XXX_GPIO_HI 1
782 +#define CNS3XXX_GPIO_OUTPUT 0x00
783 +#define CNS3XXX_GPIO_INPUT 0x04
784 +#define CNS3XXX_GPIO_DIR 0x08
785 +#define CNS3XXX_GPIO_SET 0x10
786 +#define CNS3XXX_GPIO_CLEAR 0x14
788 +static inline void gpio_line_get(u8 line, int *value)
791 + *value = ((__raw_readl(CNS3XXX_GPIOA_BASE_VIRT + CNS3XXX_GPIO_INPUT) >> line) & 0x1);
793 + *value = ((__raw_readl(CNS3XXX_GPIOB_BASE_VIRT + CNS3XXX_GPIO_INPUT) >> (line - 32)) & 0x1);
796 +static inline void gpio_line_set(u8 line, int value)
800 + __raw_writel((1 << line), CNS3XXX_GPIOA_BASE_VIRT + CNS3XXX_GPIO_SET);
802 + __raw_writel((1 << line), CNS3XXX_GPIOA_BASE_VIRT + CNS3XXX_GPIO_CLEAR);
805 + __raw_writel((1 << line), CNS3XXX_GPIOB_BASE_VIRT + CNS3XXX_GPIO_SET);
807 + __raw_writel((1 << line), CNS3XXX_GPIOB_BASE_VIRT + CNS3XXX_GPIO_CLEAR);
811 +static inline int gpio_get_value(unsigned gpio)
813 + if (gpio < NR_BUILTIN_GPIO)
816 + gpio_line_get(gpio, &value);
820 + return __gpio_get_value(gpio);
823 +static inline void gpio_set_value(unsigned gpio, int value)
825 + if (gpio < NR_BUILTIN_GPIO)
826 + gpio_line_set(gpio, value);
828 + __gpio_set_value(gpio, value);
831 +#define gpio_cansleep __gpio_cansleep
833 +extern int gpio_to_irq(int gpio);
834 +extern int irq_to_gpio(int gpio);
837 --- a/arch/arm/mach-cns3xxx/Makefile
838 +++ b/arch/arm/mach-cns3xxx/Makefile
840 obj-$(CONFIG_ARCH_CNS3XXX) += core.o pm.o devices.o
841 obj-$(CONFIG_PCI) += pcie.o
842 obj-$(CONFIG_MACH_CNS3420VB) += cns3420vb.o
843 +obj-$(CONFIG_MACH_GW2388) += laguna.o
844 obj-$(CONFIG_SMP) += platsmp.o headsmp.o
845 obj-$(CONFIG_HOTPLUG_CPU) += hotplug.o
846 obj-$(CONFIG_LOCAL_TIMERS) += localtimer.o
847 --- a/arch/arm/tools/mach-types
848 +++ b/arch/arm/tools/mach-types
849 @@ -438,6 +438,7 @@ icontrol MACH_ICONTROL ICONTROL 2624
850 qsd8x50a_st1_5 MACH_QSD8X50A_ST1_5 QSD8X50A_ST1_5 2627
851 mx23evk MACH_MX23EVK MX23EVK 2629
852 ap4evb MACH_AP4EVB AP4EVB 2630
853 +gw2388 MACH_GW2388 GW2388 2635
854 mityomapl138 MACH_MITYOMAPL138 MITYOMAPL138 2650
855 guruplug MACH_GURUPLUG GURUPLUG 2659
856 spear310 MACH_SPEAR310 SPEAR310 2660
857 --- a/arch/arm/mach-cns3xxx/pcie.c
858 +++ b/arch/arm/mach-cns3xxx/pcie.c
859 @@ -365,7 +365,7 @@ static int cns3xxx_pcie_abort_handler(un
863 -static int __init cns3xxx_pcie_init(void)
864 +int cns3xxx_pcie_init(u8 bitmap)
868 @@ -373,6 +373,9 @@ static int __init cns3xxx_pcie_init(void
869 "imprecise external abort");
871 for (i = 0; i < ARRAY_SIZE(cns3xxx_pcie); i++) {
872 + if (!(bitmap & (1 << i)))
875 iotable_init(cns3xxx_pcie[i].cfg_bases,
876 ARRAY_SIZE(cns3xxx_pcie[i].cfg_bases));
877 cns3xxx_pwr_clk_en(0x1 << PM_CLK_GATE_REG_OFFSET_PCIE(i));
878 @@ -386,4 +389,3 @@ static int __init cns3xxx_pcie_init(void
882 -device_initcall(cns3xxx_pcie_init);
883 --- a/arch/arm/mach-cns3xxx/cns3420vb.c
884 +++ b/arch/arm/mach-cns3xxx/cns3420vb.c
885 @@ -175,6 +175,8 @@ static void __init cns3420_init(void)
887 cns3xxx_sdhci_init();
889 + cns3xxx_pcie_init(0x3);
891 pm_power_off = cns3xxx_power_off;
894 --- a/arch/arm/mach-cns3xxx/include/mach/platform.h
895 +++ b/arch/arm/mach-cns3xxx/include/mach/platform.h
896 @@ -22,5 +22,7 @@ struct cns3xxx_plat_info {
900 +extern int cns3xxx_pcie_init(u8 bitmap);
902 #endif /* __ASM_ARCH_PLATFORM_H */