0001
0002
0003
0004
0005
0006 #include <linux/module.h>
0007 #include <linux/gpio/machine.h>
0008 #include <linux/init.h>
0009 #include <linux/kernel.h>
0010 #include <linux/tty.h>
0011 #include <linux/proc_fs.h>
0012 #include <linux/string.h>
0013 #include <linux/pm.h>
0014 #include <linux/platform_data/sa11x0-serial.h>
0015 #include <linux/platform_device.h>
0016 #include <linux/mfd/ucb1x00.h>
0017 #include <linux/mtd/mtd.h>
0018 #include <linux/mtd/partitions.h>
0019 #include <linux/io.h>
0020 #include <linux/gpio/driver.h>
0021
0022 #include <mach/hardware.h>
0023 #include <asm/setup.h>
0024 #include <asm/irq.h>
0025
0026 #include <asm/mach-types.h>
0027 #include <asm/mach/arch.h>
0028 #include <asm/mach/flash.h>
0029 #include <asm/mach/map.h>
0030 #include <linux/platform_data/mfd-mcp-sa11x0.h>
0031 #include <mach/simpad.h>
0032 #include <mach/irqs.h>
0033
0034 #include <linux/serial_core.h>
0035 #include <linux/ioport.h>
0036 #include <linux/input.h>
0037 #include <linux/gpio_keys.h>
0038 #include <linux/leds.h>
0039 #include <linux/platform_data/i2c-gpio.h>
0040
0041 #include "generic.h"
0042
0043
0044
0045
0046
0047 static long cs3_shadow;
0048 static spinlock_t cs3_lock;
0049 static struct gpio_chip cs3_gpio;
0050
0051 long simpad_get_cs3_ro(void)
0052 {
0053 return readl(CS3_BASE);
0054 }
0055 EXPORT_SYMBOL(simpad_get_cs3_ro);
0056
0057 long simpad_get_cs3_shadow(void)
0058 {
0059 return cs3_shadow;
0060 }
0061 EXPORT_SYMBOL(simpad_get_cs3_shadow);
0062
0063 static void __simpad_write_cs3(void)
0064 {
0065 writel(cs3_shadow, CS3_BASE);
0066 }
0067
0068 void simpad_set_cs3_bit(int value)
0069 {
0070 unsigned long flags;
0071
0072 spin_lock_irqsave(&cs3_lock, flags);
0073 cs3_shadow |= value;
0074 __simpad_write_cs3();
0075 spin_unlock_irqrestore(&cs3_lock, flags);
0076 }
0077 EXPORT_SYMBOL(simpad_set_cs3_bit);
0078
0079 void simpad_clear_cs3_bit(int value)
0080 {
0081 unsigned long flags;
0082
0083 spin_lock_irqsave(&cs3_lock, flags);
0084 cs3_shadow &= ~value;
0085 __simpad_write_cs3();
0086 spin_unlock_irqrestore(&cs3_lock, flags);
0087 }
0088 EXPORT_SYMBOL(simpad_clear_cs3_bit);
0089
0090 static void cs3_gpio_set(struct gpio_chip *chip, unsigned offset, int value)
0091 {
0092 if (offset > 15)
0093 return;
0094 if (value)
0095 simpad_set_cs3_bit(1 << offset);
0096 else
0097 simpad_clear_cs3_bit(1 << offset);
0098 };
0099
0100 static int cs3_gpio_get(struct gpio_chip *chip, unsigned offset)
0101 {
0102 if (offset > 15)
0103 return !!(simpad_get_cs3_ro() & (1 << (offset - 16)));
0104 return !!(simpad_get_cs3_shadow() & (1 << offset));
0105 };
0106
0107 static int cs3_gpio_direction_input(struct gpio_chip *chip, unsigned offset)
0108 {
0109 if (offset > 15)
0110 return 0;
0111 return -EINVAL;
0112 };
0113
0114 static int cs3_gpio_direction_output(struct gpio_chip *chip, unsigned offset,
0115 int value)
0116 {
0117 if (offset > 15)
0118 return -EINVAL;
0119 cs3_gpio_set(chip, offset, value);
0120 return 0;
0121 };
0122
0123 static struct map_desc simpad_io_desc[] __initdata = {
0124 {
0125 .virtual = 0xf2800000,
0126 .pfn = __phys_to_pfn(0x4b800000),
0127 .length = 0x00800000,
0128 .type = MT_DEVICE
0129 }, {
0130 .virtual = (unsigned long)CS3_BASE,
0131 .pfn = __phys_to_pfn(SA1100_CS3_PHYS),
0132 .length = 0x00100000,
0133 .type = MT_DEVICE
0134 },
0135 };
0136
0137
0138 static void simpad_uart_pm(struct uart_port *port, u_int state, u_int oldstate)
0139 {
0140 if (port->mapbase == (u_int)&Ser1UTCR0) {
0141 if (state)
0142 {
0143 simpad_clear_cs3_bit(RS232_ON);
0144 simpad_clear_cs3_bit(DECT_POWER_ON);
0145 }else
0146 {
0147 simpad_set_cs3_bit(RS232_ON);
0148 simpad_set_cs3_bit(DECT_POWER_ON);
0149 }
0150 }
0151 }
0152
0153 static struct sa1100_port_fns simpad_port_fns __initdata = {
0154 .pm = simpad_uart_pm,
0155 };
0156
0157
0158 static struct mtd_partition simpad_partitions[] = {
0159 {
0160 .name = "SIMpad boot firmware",
0161 .size = 0x00080000,
0162 .offset = 0,
0163 .mask_flags = MTD_WRITEABLE,
0164 }, {
0165 .name = "SIMpad kernel",
0166 .size = 0x0010000,
0167 .offset = MTDPART_OFS_APPEND,
0168 }, {
0169 .name = "SIMpad root jffs2",
0170 .size = MTDPART_SIZ_FULL,
0171 .offset = MTDPART_OFS_APPEND,
0172 }
0173 };
0174
0175 static struct flash_platform_data simpad_flash_data = {
0176 .map_name = "cfi_probe",
0177 .parts = simpad_partitions,
0178 .nr_parts = ARRAY_SIZE(simpad_partitions),
0179 };
0180
0181
0182 static struct resource simpad_flash_resources [] = {
0183 DEFINE_RES_MEM(SA1100_CS0_PHYS, SZ_16M),
0184 DEFINE_RES_MEM(SA1100_CS1_PHYS, SZ_16M),
0185 };
0186
0187 static struct ucb1x00_plat_data simpad_ucb1x00_data = {
0188 .gpio_base = SIMPAD_UCB1X00_GPIO_BASE,
0189 };
0190
0191 static struct mcp_plat_data simpad_mcp_data = {
0192 .mccr0 = MCCR0_ADM,
0193 .sclk_rate = 11981000,
0194 .codec_pdata = &simpad_ucb1x00_data,
0195 };
0196
0197
0198
0199 static void __init simpad_map_io(void)
0200 {
0201 sa1100_map_io();
0202
0203 iotable_init(simpad_io_desc, ARRAY_SIZE(simpad_io_desc));
0204
0205
0206 cs3_shadow = (EN1 | EN0 | LED2_ON | DISPLAY_ON |
0207 RS232_ON | ENABLE_5V | RESET_SIMCARD | DECT_POWER_ON);
0208 __simpad_write_cs3();
0209
0210 sa1100_register_uart_fns(&simpad_port_fns);
0211 sa1100_register_uart(0, 3);
0212 sa1100_register_uart(1, 1);
0213
0214
0215 GAFR |= GPIO_UART_TXD | GPIO_UART_RXD;
0216 GPDR |= GPIO_UART_TXD | GPIO_LDD13 | GPIO_LDD15;
0217 GPDR &= ~GPIO_UART_RXD;
0218 PPAR |= PPAR_UPR;
0219
0220
0221
0222
0223
0224
0225 PWER = PWER_GPIO0| PWER_RTC;
0226 PGSR = 0x818;
0227 PCFR = 0;
0228 PSDR = 0;
0229
0230 }
0231
0232 static void simpad_power_off(void)
0233 {
0234 local_irq_disable();
0235 cs3_shadow = SD_MEDIAQ;
0236 __simpad_write_cs3();
0237
0238
0239 PCFR = (PCFR_OPDE | PCFR_FP | PCFR_FS);
0240
0241 PWER = GFER = GRER = PWER_GPIO0;
0242
0243
0244
0245
0246 PSPR = 0;
0247 PGSR = 0;
0248
0249 PMCR = PMCR_SF;
0250 while(1);
0251
0252 local_irq_enable();
0253
0254
0255 }
0256
0257
0258
0259
0260
0261 static struct gpio_keys_button simpad_button_table[] = {
0262 { KEY_POWER, IRQ_GPIO_POWER_BUTTON, 1, "power button" },
0263 };
0264
0265 static struct gpio_keys_platform_data simpad_keys_data = {
0266 .buttons = simpad_button_table,
0267 .nbuttons = ARRAY_SIZE(simpad_button_table),
0268 };
0269
0270 static struct platform_device simpad_keys = {
0271 .name = "gpio-keys",
0272 .dev = {
0273 .platform_data = &simpad_keys_data,
0274 },
0275 };
0276
0277 static struct gpio_keys_button simpad_polled_button_table[] = {
0278 { KEY_PROG1, SIMPAD_UCB1X00_GPIO_PROG1, 1, "prog1 button" },
0279 { KEY_PROG2, SIMPAD_UCB1X00_GPIO_PROG2, 1, "prog2 button" },
0280 { KEY_UP, SIMPAD_UCB1X00_GPIO_UP, 1, "up button" },
0281 { KEY_DOWN, SIMPAD_UCB1X00_GPIO_DOWN, 1, "down button" },
0282 { KEY_LEFT, SIMPAD_UCB1X00_GPIO_LEFT, 1, "left button" },
0283 { KEY_RIGHT, SIMPAD_UCB1X00_GPIO_RIGHT, 1, "right button" },
0284 };
0285
0286 static struct gpio_keys_platform_data simpad_polled_keys_data = {
0287 .buttons = simpad_polled_button_table,
0288 .nbuttons = ARRAY_SIZE(simpad_polled_button_table),
0289 .poll_interval = 50,
0290 };
0291
0292 static struct platform_device simpad_polled_keys = {
0293 .name = "gpio-keys-polled",
0294 .dev = {
0295 .platform_data = &simpad_polled_keys_data,
0296 },
0297 };
0298
0299
0300
0301
0302
0303 static struct gpio_led simpad_leds[] = {
0304 {
0305 .name = "simpad:power",
0306 .gpio = SIMPAD_CS3_LED2_ON,
0307 .active_low = 0,
0308 .default_trigger = "default-on",
0309 },
0310 };
0311
0312 static struct gpio_led_platform_data simpad_led_data = {
0313 .num_leds = ARRAY_SIZE(simpad_leds),
0314 .leds = simpad_leds,
0315 };
0316
0317 static struct platform_device simpad_gpio_leds = {
0318 .name = "leds-gpio",
0319 .id = 0,
0320 .dev = {
0321 .platform_data = &simpad_led_data,
0322 },
0323 };
0324
0325
0326
0327
0328 static struct gpiod_lookup_table simpad_i2c_gpiod_table = {
0329 .dev_id = "i2c-gpio.0",
0330 .table = {
0331 GPIO_LOOKUP_IDX("gpio", 21, NULL, 0,
0332 GPIO_ACTIVE_HIGH | GPIO_OPEN_DRAIN),
0333 GPIO_LOOKUP_IDX("gpio", 25, NULL, 1,
0334 GPIO_ACTIVE_HIGH | GPIO_OPEN_DRAIN),
0335 },
0336 };
0337
0338 static struct i2c_gpio_platform_data simpad_i2c_data = {
0339 .udelay = 10,
0340 .timeout = HZ,
0341 };
0342
0343 static struct platform_device simpad_i2c = {
0344 .name = "i2c-gpio",
0345 .id = 0,
0346 .dev = {
0347 .platform_data = &simpad_i2c_data,
0348 },
0349 };
0350
0351
0352
0353
0354 static struct platform_device simpad_mq200fb = {
0355 .name = "simpad-mq200",
0356 .id = 0,
0357 };
0358
0359 static struct platform_device *devices[] __initdata = {
0360 &simpad_keys,
0361 &simpad_polled_keys,
0362 &simpad_mq200fb,
0363 &simpad_gpio_leds,
0364 &simpad_i2c,
0365 };
0366
0367
0368 static struct gpiod_lookup_table simpad_cf_gpio_table = {
0369 .dev_id = "sa11x0-pcmcia",
0370 .table = {
0371 GPIO_LOOKUP("gpio", GPIO_CF_IRQ, "cf-ready", GPIO_ACTIVE_HIGH),
0372 GPIO_LOOKUP("gpio", GPIO_CF_CD, "cf-detect", GPIO_ACTIVE_HIGH),
0373 { },
0374 },
0375 };
0376
0377
0378 static int __init simpad_init(void)
0379 {
0380 int ret;
0381
0382 spin_lock_init(&cs3_lock);
0383
0384 cs3_gpio.label = "simpad_cs3";
0385 cs3_gpio.base = SIMPAD_CS3_GPIO_BASE;
0386 cs3_gpio.ngpio = 24;
0387 cs3_gpio.set = cs3_gpio_set;
0388 cs3_gpio.get = cs3_gpio_get;
0389 cs3_gpio.direction_input = cs3_gpio_direction_input;
0390 cs3_gpio.direction_output = cs3_gpio_direction_output;
0391 ret = gpiochip_add_data(&cs3_gpio, NULL);
0392 if (ret)
0393 printk(KERN_WARNING "simpad: Unable to register cs3 GPIO device");
0394
0395 pm_power_off = simpad_power_off;
0396
0397 sa11x0_register_pcmcia(-1, &simpad_cf_gpio_table);
0398 sa11x0_ppc_configure_mcp();
0399 sa11x0_register_mtd(&simpad_flash_data, simpad_flash_resources,
0400 ARRAY_SIZE(simpad_flash_resources));
0401 sa11x0_register_mcp(&simpad_mcp_data);
0402
0403 gpiod_add_lookup_table(&simpad_i2c_gpiod_table);
0404 ret = platform_add_devices(devices, ARRAY_SIZE(devices));
0405 if(ret)
0406 printk(KERN_WARNING "simpad: Unable to register mq200 framebuffer device");
0407
0408 return 0;
0409 }
0410
0411 arch_initcall(simpad_init);
0412
0413
0414 MACHINE_START(SIMPAD, "Simpad")
0415
0416 .atag_offset = 0x100,
0417 .map_io = simpad_map_io,
0418 .nr_irqs = SA1100_NR_IRQS,
0419 .init_irq = sa1100_init_irq,
0420 .init_late = sa11x0_init_late,
0421 .init_time = sa1100_timer_init,
0422 .restart = sa11x0_restart,
0423 MACHINE_END