0001
0002
0003
0004
0005
0006
0007
0008 #include <linux/kernel.h>
0009 #include <linux/types.h>
0010 #include <linux/interrupt.h>
0011 #include <linux/list.h>
0012 #include <linux/memblock.h>
0013 #include <linux/delay.h>
0014 #include <linux/timer.h>
0015 #include <linux/init.h>
0016 #include <linux/gpio.h>
0017 #include <linux/gpio/machine.h>
0018 #include <linux/platform_device.h>
0019 #include <linux/serial_core.h>
0020 #include <linux/serial_s3c.h>
0021 #include <linux/input.h>
0022 #include <linux/gpio_keys.h>
0023 #include <linux/device.h>
0024 #include <linux/pda_power.h>
0025 #include <linux/pwm_backlight.h>
0026 #include <linux/pwm.h>
0027 #include <linux/s3c_adc_battery.h>
0028 #include <linux/leds.h>
0029 #include <linux/i2c.h>
0030
0031 #include <linux/mtd/mtd.h>
0032 #include <linux/mtd/partitions.h>
0033
0034 #include <linux/mmc/host.h>
0035
0036 #include <asm/mach-types.h>
0037 #include <asm/mach/arch.h>
0038 #include <asm/mach/map.h>
0039
0040 #include <linux/platform_data/i2c-s3c2410.h>
0041 #include <linux/platform_data/mmc-s3cmci.h>
0042 #include <linux/platform_data/mtd-nand-s3c2410.h>
0043 #include <linux/platform_data/touchscreen-s3c2410.h>
0044 #include <linux/platform_data/usb-s3c2410_udc.h>
0045 #include <linux/platform_data/fb-s3c2410.h>
0046
0047 #include <sound/uda1380.h>
0048
0049 #include "hardware-s3c24xx.h"
0050 #include "regs-gpio.h"
0051 #include "gpio-samsung.h"
0052
0053 #include "cpu.h"
0054 #include "devs.h"
0055 #include "pm.h"
0056 #include "gpio-cfg.h"
0057
0058 #include "s3c24xx.h"
0059 #include "h1940.h"
0060
0061 #define LCD_PWM_PERIOD 192960
0062 #define LCD_PWM_DUTY 127353
0063
0064 static struct map_desc rx1950_iodesc[] __initdata = {
0065 };
0066
0067 static struct s3c2410_uartcfg rx1950_uartcfgs[] __initdata = {
0068 [0] = {
0069 .hwport = 0,
0070 .flags = 0,
0071 .ucon = 0x3c5,
0072 .ulcon = 0x03,
0073 .ufcon = 0x51,
0074 .clk_sel = S3C2410_UCON_CLKSEL3,
0075 },
0076 [1] = {
0077 .hwport = 1,
0078 .flags = 0,
0079 .ucon = 0x3c5,
0080 .ulcon = 0x03,
0081 .ufcon = 0x51,
0082 .clk_sel = S3C2410_UCON_CLKSEL3,
0083 },
0084
0085 [2] = {
0086 .hwport = 2,
0087 .flags = 0,
0088 .ucon = 0x3c5,
0089 .ulcon = 0x43,
0090 .ufcon = 0xf1,
0091 .clk_sel = S3C2410_UCON_CLKSEL3,
0092 },
0093 };
0094
0095 static struct s3c2410fb_display rx1950_display = {
0096 .type = S3C2410_LCDCON1_TFT,
0097 .width = 240,
0098 .height = 320,
0099 .xres = 240,
0100 .yres = 320,
0101 .bpp = 16,
0102
0103 .pixclock = 260000,
0104 .left_margin = 10,
0105 .right_margin = 20,
0106 .hsync_len = 10,
0107 .upper_margin = 2,
0108 .lower_margin = 2,
0109 .vsync_len = 2,
0110
0111 .lcdcon5 = S3C2410_LCDCON5_FRM565 |
0112 S3C2410_LCDCON5_INVVCLK |
0113 S3C2410_LCDCON5_INVVLINE |
0114 S3C2410_LCDCON5_INVVFRAME |
0115 S3C2410_LCDCON5_HWSWP |
0116 (0x02 << 13) |
0117 (0x02 << 15),
0118
0119 };
0120
0121 static int power_supply_init(struct device *dev)
0122 {
0123 return gpio_request(S3C2410_GPF(2), "cable plugged");
0124 }
0125
0126 static int rx1950_is_ac_online(void)
0127 {
0128 return !gpio_get_value(S3C2410_GPF(2));
0129 }
0130
0131 static void power_supply_exit(struct device *dev)
0132 {
0133 gpio_free(S3C2410_GPF(2));
0134 }
0135
0136 static char *rx1950_supplicants[] = {
0137 "main-battery"
0138 };
0139
0140 static struct pda_power_pdata power_supply_info = {
0141 .init = power_supply_init,
0142 .is_ac_online = rx1950_is_ac_online,
0143 .exit = power_supply_exit,
0144 .supplied_to = rx1950_supplicants,
0145 .num_supplicants = ARRAY_SIZE(rx1950_supplicants),
0146 };
0147
0148 static struct resource power_supply_resources[] = {
0149 [0] = DEFINE_RES_NAMED(IRQ_EINT2, 1, "ac", IORESOURCE_IRQ \
0150 | IORESOURCE_IRQ_LOWEDGE | IORESOURCE_IRQ_HIGHEDGE),
0151 };
0152
0153 static struct platform_device power_supply = {
0154 .name = "pda-power",
0155 .id = -1,
0156 .dev = {
0157 .platform_data =
0158 &power_supply_info,
0159 },
0160 .resource = power_supply_resources,
0161 .num_resources = ARRAY_SIZE(power_supply_resources),
0162 };
0163
0164 static const struct s3c_adc_bat_thresh bat_lut_noac[] = {
0165 { .volt = 4100, .cur = 156, .level = 100},
0166 { .volt = 4050, .cur = 156, .level = 95},
0167 { .volt = 4025, .cur = 141, .level = 90},
0168 { .volt = 3995, .cur = 144, .level = 85},
0169 { .volt = 3957, .cur = 162, .level = 80},
0170 { .volt = 3931, .cur = 147, .level = 75},
0171 { .volt = 3902, .cur = 147, .level = 70},
0172 { .volt = 3863, .cur = 153, .level = 65},
0173 { .volt = 3838, .cur = 150, .level = 60},
0174 { .volt = 3800, .cur = 153, .level = 55},
0175 { .volt = 3765, .cur = 153, .level = 50},
0176 { .volt = 3748, .cur = 172, .level = 45},
0177 { .volt = 3740, .cur = 153, .level = 40},
0178 { .volt = 3714, .cur = 175, .level = 35},
0179 { .volt = 3710, .cur = 156, .level = 30},
0180 { .volt = 3963, .cur = 156, .level = 25},
0181 { .volt = 3672, .cur = 178, .level = 20},
0182 { .volt = 3651, .cur = 178, .level = 15},
0183 { .volt = 3629, .cur = 178, .level = 10},
0184 { .volt = 3612, .cur = 162, .level = 5},
0185 { .volt = 3605, .cur = 162, .level = 0},
0186 };
0187
0188 static const struct s3c_adc_bat_thresh bat_lut_acin[] = {
0189 { .volt = 4200, .cur = 0, .level = 100},
0190 { .volt = 4190, .cur = 0, .level = 99},
0191 { .volt = 4178, .cur = 0, .level = 95},
0192 { .volt = 4110, .cur = 0, .level = 70},
0193 { .volt = 4076, .cur = 0, .level = 65},
0194 { .volt = 4046, .cur = 0, .level = 60},
0195 { .volt = 4021, .cur = 0, .level = 55},
0196 { .volt = 3999, .cur = 0, .level = 50},
0197 { .volt = 3982, .cur = 0, .level = 45},
0198 { .volt = 3965, .cur = 0, .level = 40},
0199 { .volt = 3957, .cur = 0, .level = 35},
0200 { .volt = 3948, .cur = 0, .level = 30},
0201 { .volt = 3936, .cur = 0, .level = 25},
0202 { .volt = 3927, .cur = 0, .level = 20},
0203 { .volt = 3906, .cur = 0, .level = 15},
0204 { .volt = 3880, .cur = 0, .level = 10},
0205 { .volt = 3829, .cur = 0, .level = 5},
0206 { .volt = 3820, .cur = 0, .level = 0},
0207 };
0208
0209 static struct gpiod_lookup_table rx1950_bat_gpio_table = {
0210 .dev_id = "s3c-adc-battery",
0211 .table = {
0212
0213 GPIO_LOOKUP("GPIOF", 3, "charge-status", GPIO_ACTIVE_HIGH),
0214 { },
0215 },
0216 };
0217
0218 static int rx1950_bat_init(void)
0219 {
0220 int ret;
0221
0222 ret = gpio_request(S3C2410_GPJ(2), "rx1950-charger-enable-1");
0223 if (ret)
0224 goto err_gpio1;
0225 ret = gpio_request(S3C2410_GPJ(3), "rx1950-charger-enable-2");
0226 if (ret)
0227 goto err_gpio2;
0228
0229 return 0;
0230
0231 err_gpio2:
0232 gpio_free(S3C2410_GPJ(2));
0233 err_gpio1:
0234 return ret;
0235 }
0236
0237 static void rx1950_bat_exit(void)
0238 {
0239 gpio_free(S3C2410_GPJ(2));
0240 gpio_free(S3C2410_GPJ(3));
0241 }
0242
0243 static void rx1950_enable_charger(void)
0244 {
0245 gpio_direction_output(S3C2410_GPJ(2), 1);
0246 gpio_direction_output(S3C2410_GPJ(3), 1);
0247 }
0248
0249 static void rx1950_disable_charger(void)
0250 {
0251 gpio_direction_output(S3C2410_GPJ(2), 0);
0252 gpio_direction_output(S3C2410_GPJ(3), 0);
0253 }
0254
0255 static DEFINE_SPINLOCK(rx1950_blink_spin);
0256
0257 static int rx1950_led_blink_set(struct gpio_desc *desc, int state,
0258 unsigned long *delay_on, unsigned long *delay_off)
0259 {
0260 int gpio = desc_to_gpio(desc);
0261 int blink_gpio, check_gpio;
0262
0263 switch (gpio) {
0264 case S3C2410_GPA(6):
0265 blink_gpio = S3C2410_GPA(4);
0266 check_gpio = S3C2410_GPA(3);
0267 break;
0268 case S3C2410_GPA(7):
0269 blink_gpio = S3C2410_GPA(3);
0270 check_gpio = S3C2410_GPA(4);
0271 break;
0272 default:
0273 return -EINVAL;
0274 }
0275
0276 if (delay_on && delay_off && !*delay_on && !*delay_off)
0277 *delay_on = *delay_off = 500;
0278
0279 spin_lock(&rx1950_blink_spin);
0280
0281 switch (state) {
0282 case GPIO_LED_NO_BLINK_LOW:
0283 case GPIO_LED_NO_BLINK_HIGH:
0284 if (!gpio_get_value(check_gpio))
0285 gpio_set_value(S3C2410_GPJ(6), 0);
0286 gpio_set_value(blink_gpio, 0);
0287 gpio_set_value(gpio, state);
0288 break;
0289 case GPIO_LED_BLINK:
0290 gpio_set_value(gpio, 0);
0291 gpio_set_value(S3C2410_GPJ(6), 1);
0292 gpio_set_value(blink_gpio, 1);
0293 break;
0294 }
0295
0296 spin_unlock(&rx1950_blink_spin);
0297
0298 return 0;
0299 }
0300
0301 static struct gpio_led rx1950_leds_desc[] = {
0302 {
0303 .name = "Green",
0304 .default_trigger = "main-battery-full",
0305 .gpio = S3C2410_GPA(6),
0306 .retain_state_suspended = 1,
0307 },
0308 {
0309 .name = "Red",
0310 .default_trigger
0311 = "main-battery-charging-blink-full-solid",
0312 .gpio = S3C2410_GPA(7),
0313 .retain_state_suspended = 1,
0314 },
0315 {
0316 .name = "Blue",
0317 .default_trigger = "rx1950-acx-mem",
0318 .gpio = S3C2410_GPA(11),
0319 .retain_state_suspended = 1,
0320 },
0321 };
0322
0323 static struct gpio_led_platform_data rx1950_leds_pdata = {
0324 .num_leds = ARRAY_SIZE(rx1950_leds_desc),
0325 .leds = rx1950_leds_desc,
0326 .gpio_blink_set = rx1950_led_blink_set,
0327 };
0328
0329 static struct platform_device rx1950_leds = {
0330 .name = "leds-gpio",
0331 .id = -1,
0332 .dev = {
0333 .platform_data = &rx1950_leds_pdata,
0334 },
0335 };
0336
0337 static struct s3c_adc_bat_pdata rx1950_bat_cfg = {
0338 .init = rx1950_bat_init,
0339 .exit = rx1950_bat_exit,
0340 .enable_charger = rx1950_enable_charger,
0341 .disable_charger = rx1950_disable_charger,
0342 .lut_noac = bat_lut_noac,
0343 .lut_noac_cnt = ARRAY_SIZE(bat_lut_noac),
0344 .lut_acin = bat_lut_acin,
0345 .lut_acin_cnt = ARRAY_SIZE(bat_lut_acin),
0346 .volt_channel = 0,
0347 .current_channel = 1,
0348 .volt_mult = 4235,
0349 .current_mult = 2900,
0350 .internal_impedance = 200,
0351 };
0352
0353 static struct platform_device rx1950_battery = {
0354 .name = "s3c-adc-battery",
0355 .id = -1,
0356 .dev = {
0357 .parent = &s3c_device_adc.dev,
0358 .platform_data = &rx1950_bat_cfg,
0359 },
0360 };
0361
0362 static struct s3c2410fb_mach_info rx1950_lcd_cfg = {
0363 .displays = &rx1950_display,
0364 .num_displays = 1,
0365 .default_display = 0,
0366
0367 .lpcsel = 0x02,
0368 .gpccon = 0xaa9556a9,
0369 .gpccon_mask = 0xffc003fc,
0370 .gpccon_reg = S3C2410_GPCCON,
0371 .gpcup = 0x0000ffff,
0372 .gpcup_mask = 0xffffffff,
0373 .gpcup_reg = S3C2410_GPCUP,
0374
0375 .gpdcon = 0xaa90aaa1,
0376 .gpdcon_mask = 0xffc0fff0,
0377 .gpdcon_reg = S3C2410_GPDCON,
0378 .gpdup = 0x0000fcfd,
0379 .gpdup_mask = 0xffffffff,
0380 .gpdup_reg = S3C2410_GPDUP,
0381 };
0382
0383 static struct pwm_lookup rx1950_pwm_lookup[] = {
0384 PWM_LOOKUP("samsung-pwm", 0, "pwm-backlight.0", NULL, 48000,
0385 PWM_POLARITY_NORMAL),
0386 PWM_LOOKUP("samsung-pwm", 1, "pwm-backlight.0", "RX1950 LCD", LCD_PWM_PERIOD,
0387 PWM_POLARITY_NORMAL),
0388 };
0389
0390 static struct pwm_device *lcd_pwm;
0391 static struct pwm_state lcd_pwm_state;
0392
0393 static void rx1950_lcd_power(int enable)
0394 {
0395 int i;
0396 static int enabled;
0397 if (enabled == enable)
0398 return;
0399 if (!enable) {
0400
0401
0402 for (i = 11; i < 16; i++)
0403 gpio_direction_output(S3C2410_GPC(i), 1);
0404
0405
0406 mdelay(100);
0407
0408
0409
0410
0411 for (i = 2; i < 8; i++)
0412 gpio_direction_output(S3C2410_GPD(i), 1);
0413 for (i = 11; i < 16; i++)
0414 gpio_direction_output(S3C2410_GPD(i), 1);
0415
0416
0417 mdelay(100);
0418
0419
0420 gpio_direction_output(S3C2410_GPB(0), 0);
0421
0422
0423 for (i = 1; i < 5; i++)
0424 gpio_direction_output(S3C2410_GPC(i), 0);
0425
0426
0427 for (i = 11; i < 16; i++)
0428 gpio_direction_output(S3C2410_GPC(i), 0);
0429
0430
0431 for (i = 11; i < 16; i++)
0432 gpio_direction_output(S3C2410_GPD(i), 0);
0433
0434 for (i = 2; i < 8; i++)
0435 gpio_direction_output(S3C2410_GPD(i), 0);
0436
0437
0438 gpio_direction_output(S3C2410_GPC(6), 0);
0439 gpio_direction_output(S3C2410_GPC(7), 0);
0440 gpio_direction_output(S3C2410_GPC(5), 0);
0441
0442
0443 gpio_direction_output(S3C2410_GPB(1), 0);
0444
0445 lcd_pwm_state.enabled = false;
0446 pwm_apply_state(lcd_pwm, &lcd_pwm_state);
0447
0448
0449 gpio_direction_output(S3C2410_GPC(0), 0);
0450 gpio_direction_output(S3C2410_GPC(10), 0);
0451 } else {
0452 lcd_pwm_state.enabled = true;
0453 pwm_apply_state(lcd_pwm, &lcd_pwm_state);
0454
0455 gpio_direction_output(S3C2410_GPC(0), 1);
0456 gpio_direction_output(S3C2410_GPC(5), 1);
0457
0458 s3c_gpio_cfgpin(S3C2410_GPB(1), S3C2410_GPB1_TOUT1);
0459 gpio_direction_output(S3C2410_GPC(7), 1);
0460
0461 for (i = 1; i < 5; i++)
0462 s3c_gpio_cfgpin(S3C2410_GPC(i), S3C_GPIO_SFN(2));
0463
0464 for (i = 11; i < 16; i++)
0465 s3c_gpio_cfgpin(S3C2410_GPC(i), S3C_GPIO_SFN(2));
0466
0467 for (i = 2; i < 8; i++)
0468 s3c_gpio_cfgpin(S3C2410_GPD(i), S3C_GPIO_SFN(2));
0469
0470 for (i = 11; i < 16; i++)
0471 s3c_gpio_cfgpin(S3C2410_GPD(i), S3C_GPIO_SFN(2));
0472
0473 gpio_direction_output(S3C2410_GPC(10), 1);
0474 gpio_direction_output(S3C2410_GPC(6), 1);
0475 }
0476 enabled = enable;
0477 }
0478
0479 static void rx1950_bl_power(int enable)
0480 {
0481 static int enabled;
0482 if (enabled == enable)
0483 return;
0484 if (!enable) {
0485 gpio_direction_output(S3C2410_GPB(0), 0);
0486 } else {
0487
0488 gpio_direction_output(S3C2410_GPB(0), 1);
0489
0490
0491
0492
0493 ndelay(48000);
0494 s3c_gpio_cfgpin(S3C2410_GPB(0), S3C2410_GPB0_TOUT0);
0495 }
0496 enabled = enable;
0497 }
0498
0499 static int rx1950_backlight_init(struct device *dev)
0500 {
0501 WARN_ON(gpio_request(S3C2410_GPB(0), "Backlight"));
0502 lcd_pwm = pwm_get(dev, "RX1950 LCD");
0503 if (IS_ERR(lcd_pwm)) {
0504 dev_err(dev, "Unable to request PWM for LCD power!\n");
0505 return PTR_ERR(lcd_pwm);
0506 }
0507
0508
0509
0510
0511
0512 pwm_init_state(lcd_pwm, &lcd_pwm_state);
0513
0514 lcd_pwm_state.duty_cycle = LCD_PWM_DUTY;
0515
0516 rx1950_lcd_power(1);
0517 rx1950_bl_power(1);
0518
0519 return 0;
0520 }
0521
0522 static void rx1950_backlight_exit(struct device *dev)
0523 {
0524 rx1950_bl_power(0);
0525 rx1950_lcd_power(0);
0526
0527 pwm_put(lcd_pwm);
0528 gpio_free(S3C2410_GPB(0));
0529 }
0530
0531
0532 static int rx1950_backlight_notify(struct device *dev, int brightness)
0533 {
0534 if (!brightness) {
0535 rx1950_bl_power(0);
0536 rx1950_lcd_power(0);
0537 } else {
0538 rx1950_lcd_power(1);
0539 rx1950_bl_power(1);
0540 }
0541 return brightness;
0542 }
0543
0544 static struct platform_pwm_backlight_data rx1950_backlight_data = {
0545 .max_brightness = 24,
0546 .dft_brightness = 4,
0547 .init = rx1950_backlight_init,
0548 .notify = rx1950_backlight_notify,
0549 .exit = rx1950_backlight_exit,
0550 };
0551
0552 static struct platform_device rx1950_backlight = {
0553 .name = "pwm-backlight",
0554 .dev = {
0555 .parent = &samsung_device_pwm.dev,
0556 .platform_data = &rx1950_backlight_data,
0557 },
0558 };
0559
0560 static void rx1950_set_mmc_power(unsigned char power_mode, unsigned short vdd)
0561 {
0562 s3c24xx_mci_def_set_power(power_mode, vdd);
0563
0564 switch (power_mode) {
0565 case MMC_POWER_OFF:
0566 gpio_direction_output(S3C2410_GPJ(1), 0);
0567 break;
0568 case MMC_POWER_UP:
0569 case MMC_POWER_ON:
0570 gpio_direction_output(S3C2410_GPJ(1), 1);
0571 break;
0572 default:
0573 break;
0574 }
0575 }
0576
0577 static struct s3c24xx_mci_pdata rx1950_mmc_cfg __initdata = {
0578 .set_power = rx1950_set_mmc_power,
0579 .ocr_avail = MMC_VDD_32_33,
0580 };
0581
0582 static struct gpiod_lookup_table rx1950_mmc_gpio_table = {
0583 .dev_id = "s3c2410-sdi",
0584 .table = {
0585
0586 GPIO_LOOKUP("GPIOF", 5, "cd", GPIO_ACTIVE_LOW),
0587
0588 GPIO_LOOKUP("GPIOH", 8, "wp", GPIO_ACTIVE_LOW),
0589
0590 GPIO_LOOKUP_IDX("GPIOE", 5, "bus", 0, GPIO_ACTIVE_HIGH),
0591 GPIO_LOOKUP_IDX("GPIOE", 6, "bus", 1, GPIO_ACTIVE_HIGH),
0592 GPIO_LOOKUP_IDX("GPIOE", 7, "bus", 2, GPIO_ACTIVE_HIGH),
0593 GPIO_LOOKUP_IDX("GPIOE", 8, "bus", 3, GPIO_ACTIVE_HIGH),
0594 GPIO_LOOKUP_IDX("GPIOE", 9, "bus", 4, GPIO_ACTIVE_HIGH),
0595 GPIO_LOOKUP_IDX("GPIOE", 10, "bus", 5, GPIO_ACTIVE_HIGH),
0596 { },
0597 },
0598 };
0599
0600 static struct mtd_partition rx1950_nand_part[] = {
0601 [0] = {
0602 .name = "Boot0",
0603 .offset = 0,
0604 .size = 0x4000,
0605 .mask_flags = MTD_WRITEABLE,
0606 },
0607 [1] = {
0608 .name = "Boot1",
0609 .offset = MTDPART_OFS_APPEND,
0610 .size = 0x40000,
0611 .mask_flags = MTD_WRITEABLE,
0612 },
0613 [2] = {
0614 .name = "Kernel",
0615 .offset = MTDPART_OFS_APPEND,
0616 .size = 0x300000,
0617 .mask_flags = 0,
0618 },
0619 [3] = {
0620 .name = "Filesystem",
0621 .offset = MTDPART_OFS_APPEND,
0622 .size = MTDPART_SIZ_FULL,
0623 .mask_flags = 0,
0624 },
0625 };
0626
0627 static struct s3c2410_nand_set rx1950_nand_sets[] = {
0628 [0] = {
0629 .name = "Internal",
0630 .nr_chips = 1,
0631 .nr_partitions = ARRAY_SIZE(rx1950_nand_part),
0632 .partitions = rx1950_nand_part,
0633 },
0634 };
0635
0636 static struct s3c2410_platform_nand rx1950_nand_info = {
0637 .tacls = 25,
0638 .twrph0 = 50,
0639 .twrph1 = 15,
0640 .nr_sets = ARRAY_SIZE(rx1950_nand_sets),
0641 .sets = rx1950_nand_sets,
0642 .engine_type = NAND_ECC_ENGINE_TYPE_SOFT,
0643 };
0644
0645 static struct s3c2410_udc_mach_info rx1950_udc_cfg __initdata = {
0646 .vbus_pin = S3C2410_GPG(5),
0647 .vbus_pin_inverted = 1,
0648 .pullup_pin = S3C2410_GPJ(5),
0649 };
0650
0651 static struct s3c2410_ts_mach_info rx1950_ts_cfg __initdata = {
0652 .delay = 10000,
0653 .presc = 49,
0654 .oversampling_shift = 3,
0655 };
0656
0657 static struct gpio_keys_button rx1950_gpio_keys_table[] = {
0658 {
0659 .code = KEY_POWER,
0660 .gpio = S3C2410_GPF(0),
0661 .active_low = 1,
0662 .desc = "Power button",
0663 .wakeup = 1,
0664 },
0665 {
0666 .code = KEY_F5,
0667 .gpio = S3C2410_GPF(7),
0668 .active_low = 1,
0669 .desc = "Record button",
0670 },
0671 {
0672 .code = KEY_F1,
0673 .gpio = S3C2410_GPG(0),
0674 .active_low = 1,
0675 .desc = "Calendar button",
0676 },
0677 {
0678 .code = KEY_F2,
0679 .gpio = S3C2410_GPG(2),
0680 .active_low = 1,
0681 .desc = "Contacts button",
0682 },
0683 {
0684 .code = KEY_F3,
0685 .gpio = S3C2410_GPG(3),
0686 .active_low = 1,
0687 .desc = "Mail button",
0688 },
0689 {
0690 .code = KEY_F4,
0691 .gpio = S3C2410_GPG(7),
0692 .active_low = 1,
0693 .desc = "WLAN button",
0694 },
0695 {
0696 .code = KEY_LEFT,
0697 .gpio = S3C2410_GPG(10),
0698 .active_low = 1,
0699 .desc = "Left button",
0700 },
0701 {
0702 .code = KEY_RIGHT,
0703 .gpio = S3C2410_GPG(11),
0704 .active_low = 1,
0705 .desc = "Right button",
0706 },
0707 {
0708 .code = KEY_UP,
0709 .gpio = S3C2410_GPG(4),
0710 .active_low = 1,
0711 .desc = "Up button",
0712 },
0713 {
0714 .code = KEY_DOWN,
0715 .gpio = S3C2410_GPG(6),
0716 .active_low = 1,
0717 .desc = "Down button",
0718 },
0719 {
0720 .code = KEY_ENTER,
0721 .gpio = S3C2410_GPG(9),
0722 .active_low = 1,
0723 .desc = "Ok button"
0724 },
0725 };
0726
0727 static struct gpio_keys_platform_data rx1950_gpio_keys_data = {
0728 .buttons = rx1950_gpio_keys_table,
0729 .nbuttons = ARRAY_SIZE(rx1950_gpio_keys_table),
0730 };
0731
0732 static struct platform_device rx1950_device_gpiokeys = {
0733 .name = "gpio-keys",
0734 .dev.platform_data = &rx1950_gpio_keys_data,
0735 };
0736
0737 static struct uda1380_platform_data uda1380_info = {
0738 .gpio_power = S3C2410_GPJ(0),
0739 .gpio_reset = S3C2410_GPD(0),
0740 .dac_clk = UDA1380_DAC_CLK_SYSCLK,
0741 };
0742
0743 static struct i2c_board_info rx1950_i2c_devices[] = {
0744 {
0745 I2C_BOARD_INFO("uda1380", 0x1a),
0746 .platform_data = &uda1380_info,
0747 },
0748 };
0749
0750 static struct gpiod_lookup_table rx1950_audio_gpio_table = {
0751 .dev_id = "rx1950-audio",
0752 .table = {
0753 GPIO_LOOKUP("GPIOG", 12, "hp-gpio", GPIO_ACTIVE_HIGH),
0754 GPIO_LOOKUP("GPIOA", 1, "speaker-power", GPIO_ACTIVE_HIGH),
0755 { },
0756 },
0757 };
0758
0759 static struct platform_device rx1950_audio = {
0760 .name = "rx1950-audio",
0761 .id = -1,
0762 };
0763
0764 static struct platform_device *rx1950_devices[] __initdata = {
0765 &s3c2410_device_dclk,
0766 &s3c_device_lcd,
0767 &s3c_device_wdt,
0768 &s3c_device_i2c0,
0769 &s3c_device_iis,
0770 &s3c_device_usbgadget,
0771 &s3c_device_rtc,
0772 &s3c_device_nand,
0773 &s3c_device_sdi,
0774 &s3c_device_adc,
0775 &s3c_device_ts,
0776 &samsung_device_pwm,
0777 &rx1950_backlight,
0778 &rx1950_device_gpiokeys,
0779 &power_supply,
0780 &rx1950_battery,
0781 &rx1950_leds,
0782 &rx1950_audio,
0783 };
0784
0785 static void __init rx1950_map_io(void)
0786 {
0787 s3c24xx_init_io(rx1950_iodesc, ARRAY_SIZE(rx1950_iodesc));
0788 s3c24xx_init_uarts(rx1950_uartcfgs, ARRAY_SIZE(rx1950_uartcfgs));
0789 s3c24xx_set_timer_source(S3C24XX_PWM3, S3C24XX_PWM4);
0790
0791
0792
0793 #ifdef CONFIG_PM_H1940
0794 memcpy(phys_to_virt(H1940_SUSPEND_RESUMEAT), h1940_pm_return, 8);
0795 #endif
0796
0797 s3c_pm_init();
0798 }
0799
0800 static void __init rx1950_init_time(void)
0801 {
0802 s3c2442_init_clocks(16934000);
0803 s3c24xx_timer_init();
0804 }
0805
0806 static void __init rx1950_init_machine(void)
0807 {
0808 int i;
0809
0810 s3c24xx_fb_set_platdata(&rx1950_lcd_cfg);
0811 s3c24xx_udc_set_platdata(&rx1950_udc_cfg);
0812 s3c24xx_ts_set_platdata(&rx1950_ts_cfg);
0813 gpiod_add_lookup_table(&rx1950_mmc_gpio_table);
0814 s3c24xx_mci_set_platdata(&rx1950_mmc_cfg);
0815 s3c_i2c0_set_platdata(NULL);
0816 s3c_nand_set_platdata(&rx1950_nand_info);
0817
0818
0819
0820 s3c2410_modify_misccr(S3C2410_MISCCR_USBHOST |
0821 S3C2410_MISCCR_USBSUSPND0 |
0822 S3C2410_MISCCR_USBSUSPND1, 0x0);
0823
0824
0825 WARN_ON(gpio_request(S3C2410_GPJ(1), "MMC power"));
0826 gpio_direction_output(S3C2410_GPJ(1), 0);
0827
0828 for (i = 0; i < 8; i++)
0829 WARN_ON(gpio_request(S3C2410_GPC(i), "LCD power"));
0830
0831 for (i = 10; i < 16; i++)
0832 WARN_ON(gpio_request(S3C2410_GPC(i), "LCD power"));
0833
0834 for (i = 2; i < 8; i++)
0835 WARN_ON(gpio_request(S3C2410_GPD(i), "LCD power"));
0836
0837 for (i = 11; i < 16; i++)
0838 WARN_ON(gpio_request(S3C2410_GPD(i), "LCD power"));
0839
0840 WARN_ON(gpio_request(S3C2410_GPB(1), "LCD power"));
0841
0842 WARN_ON(gpio_request(S3C2410_GPA(3), "Red blink"));
0843 WARN_ON(gpio_request(S3C2410_GPA(4), "Green blink"));
0844 WARN_ON(gpio_request(S3C2410_GPJ(6), "LED blink"));
0845 gpio_direction_output(S3C2410_GPA(3), 0);
0846 gpio_direction_output(S3C2410_GPA(4), 0);
0847 gpio_direction_output(S3C2410_GPJ(6), 0);
0848
0849 pwm_add_table(rx1950_pwm_lookup, ARRAY_SIZE(rx1950_pwm_lookup));
0850 gpiod_add_lookup_table(&rx1950_audio_gpio_table);
0851 gpiod_add_lookup_table(&rx1950_bat_gpio_table);
0852
0853 s3c_gpio_cfgall_range(S3C2410_GPE(0), 5, S3C_GPIO_SFN(2),
0854 S3C_GPIO_PULL_NONE);
0855 platform_add_devices(rx1950_devices, ARRAY_SIZE(rx1950_devices));
0856
0857 i2c_register_board_info(0, rx1950_i2c_devices,
0858 ARRAY_SIZE(rx1950_i2c_devices));
0859 }
0860
0861
0862 static void __init rx1950_reserve(void)
0863 {
0864 memblock_reserve(0x30003000, 0x1000);
0865 memblock_reserve(0x30081000, 0x1000);
0866 }
0867
0868 MACHINE_START(RX1950, "HP iPAQ RX1950")
0869
0870 .atag_offset = 0x100,
0871 .nr_irqs = NR_IRQS_S3C2442,
0872 .map_io = rx1950_map_io,
0873 .reserve = rx1950_reserve,
0874 .init_irq = s3c2442_init_irq,
0875 .init_machine = rx1950_init_machine,
0876 .init_time = rx1950_init_time,
0877 MACHINE_END