ARM: Merge for-2637/s3c24xx/h1940
authorBen Dooks <ben-linux@fluff.org>
Fri, 29 Oct 2010 23:46:49 +0000 (00:46 +0100)
committerBen Dooks <ben-linux@fluff.org>
Fri, 29 Oct 2010 23:46:49 +0000 (00:46 +0100)
1  2 
arch/arm/mach-s3c2410/mach-h1940.c

@@@ -24,6 -24,7 +24,7 @@@
  #include <linux/io.h>
  #include <linux/gpio.h>
  #include <linux/pwm_backlight.h>
+ #include <linux/i2c.h>
  #include <video/platform_lcd.h>
  
  #include <linux/mmc/host.h>
  #include <plat/mci.h>
  #include <plat/ts.h>
  
+ #include <sound/uda1380.h>
+ #define H1940_LATCH           ((void __force __iomem *)0xF8000000)
+ #define H1940_PA_LATCH                S3C2410_CS2
+ #define H1940_LATCH_BIT(x)    (1 << ((x) + 16 - S3C_GPIO_END))
  static struct map_desc h1940_iodesc[] __initdata = {
        [0] = {
                .virtual        = (unsigned long)H1940_LATCH,
@@@ -100,9 -109,9 +109,9 @@@ static struct s3c2410_uartcfg h1940_uar
  
  /* Board control latch control */
  
- static unsigned int latch_state = H1940_LATCH_DEFAULT;
+ static unsigned int latch_state;
  
- void h1940_latch_control(unsigned int clear, unsigned int set)
static void h1940_latch_control(unsigned int clear, unsigned int set)
  {
        unsigned long flags;
  
        local_irq_restore(flags);
  }
  
- EXPORT_SYMBOL_GPL(h1940_latch_control);
+ static inline int h1940_gpiolib_to_latch(int offset)
+ {
+       return 1 << (offset + 16);
+ }
+ static void h1940_gpiolib_latch_set(struct gpio_chip *chip,
+                                       unsigned offset, int value)
+ {
+       int latch_bit = h1940_gpiolib_to_latch(offset);
+       h1940_latch_control(value ? 0 : latch_bit,
+               value ? latch_bit : 0);
+ }
+ static int h1940_gpiolib_latch_output(struct gpio_chip *chip,
+                                       unsigned offset, int value)
+ {
+       h1940_gpiolib_latch_set(chip, offset, value);
+       return 0;
+ }
+ static int h1940_gpiolib_latch_get(struct gpio_chip *chip,
+                                       unsigned offset)
+ {
+       return (latch_state >> (offset + 16)) & 1;
+ }
+ struct gpio_chip h1940_latch_gpiochip = {
+       .base                   = H1940_LATCH_GPIO(0),
+       .owner                  = THIS_MODULE,
+       .label                  = "H1940_LATCH",
+       .ngpio                  = 16,
+       .direction_output       = h1940_gpiolib_latch_output,
+       .set                    = h1940_gpiolib_latch_set,
+       .get                    = h1940_gpiolib_latch_get,
+ };
  
  static void h1940_udc_pullup(enum s3c2410_udc_cmd_e cmd)
  {
        switch (cmd)
        {
                case S3C2410_UDC_P_ENABLE :
-                       h1940_latch_control(0, H1940_LATCH_USB_DP);
+                       gpio_set_value(H1940_LATCH_USB_DP, 1);
                        break;
                case S3C2410_UDC_P_DISABLE :
-                       h1940_latch_control(H1940_LATCH_USB_DP, 0);
+                       gpio_set_value(H1940_LATCH_USB_DP, 0);
                        break;
                case S3C2410_UDC_P_RESET :
                        break;
@@@ -199,10 -243,25 +243,25 @@@ static struct platform_device h1940_dev
        .id               = -1,
  };
  
+ static void h1940_set_mmc_power(unsigned char power_mode, unsigned short vdd)
+ {
+       switch (power_mode) {
+       case MMC_POWER_OFF:
+               gpio_set_value(H1940_LATCH_SD_POWER, 0);
+               break;
+       case MMC_POWER_UP:
+       case MMC_POWER_ON:
+               gpio_set_value(H1940_LATCH_SD_POWER, 1);
+               break;
+       default:
+               break;
+       };
+ }
  static struct s3c24xx_mci_pdata h1940_mmc_cfg __initdata = {
        .gpio_detect   = S3C2410_GPF(5),
        .gpio_wprotect = S3C2410_GPH(8),
-       .set_power     = NULL,
+       .set_power     = h1940_set_mmc_power,
        .ocr_avail     = MMC_VDD_32_33,
  };
  
@@@ -213,15 -272,32 +272,32 @@@ static int h1940_backlight_init(struct 
        gpio_direction_output(S3C2410_GPB(0), 0);
        s3c_gpio_setpull(S3C2410_GPB(0), S3C_GPIO_PULL_NONE);
        s3c_gpio_cfgpin(S3C2410_GPB(0), S3C2410_GPB0_TOUT0);
+       gpio_set_value(H1940_LATCH_MAX1698_nSHUTDOWN, 1);
  
        return 0;
  }
  
+ static int h1940_backlight_notify(struct device *dev, int brightness)
+ {
+       if (!brightness) {
+               gpio_direction_output(S3C2410_GPB(0), 1);
+               gpio_set_value(H1940_LATCH_MAX1698_nSHUTDOWN, 0);
+       } else {
+               gpio_direction_output(S3C2410_GPB(0), 0);
+               s3c_gpio_setpull(S3C2410_GPB(0), S3C_GPIO_PULL_NONE);
+               s3c_gpio_cfgpin(S3C2410_GPB(0), S3C2410_GPB0_TOUT0);
+               gpio_set_value(H1940_LATCH_MAX1698_nSHUTDOWN, 1);
+       }
+       return brightness;
+ }
  static void h1940_backlight_exit(struct device *dev)
  {
        gpio_direction_output(S3C2410_GPB(0), 1);
+       gpio_set_value(H1940_LATCH_MAX1698_nSHUTDOWN, 0);
  }
  
  static struct platform_pwm_backlight_data backlight_data = {
        .pwm_id         = 0,
        .max_brightness = 100,
        /* tcnt = 0x31 */
        .pwm_period_ns  = 36296,
        .init           = h1940_backlight_init,
+       .notify         = h1940_backlight_notify,
        .exit           = h1940_backlight_exit,
  };
  
@@@ -247,19 -324,37 +324,37 @@@ static void h1940_lcd_power_set(struct 
        int value;
  
        if (!power) {
-               /* set to 3ec */
-               gpio_direction_output(S3C2410_GPC(0), 0);
+               gpio_set_value(S3C2410_GPC(0), 0);
                /* wait for 3ac */
                do {
                        value = gpio_get_value(S3C2410_GPC(6));
                } while (value);
-               /* set to 38c */
-               gpio_direction_output(S3C2410_GPC(5), 0);
+               gpio_set_value(H1940_LATCH_LCD_P2, 0);
+               gpio_set_value(H1940_LATCH_LCD_P3, 0);
+               gpio_set_value(H1940_LATCH_LCD_P4, 0);
+               gpio_direction_output(S3C2410_GPC(1), 0);
+               gpio_direction_output(S3C2410_GPC(4), 0);
+               gpio_set_value(H1940_LATCH_LCD_P1, 0);
+               gpio_set_value(H1940_LATCH_LCD_P0, 0);
+               gpio_set_value(S3C2410_GPC(5), 0);
        } else {
-               /* Set to 3ac */
-               gpio_direction_output(S3C2410_GPC(5), 1);
-               /* Set to 3ad */
-               gpio_direction_output(S3C2410_GPC(0), 1);
+               gpio_set_value(H1940_LATCH_LCD_P0, 1);
+               gpio_set_value(H1940_LATCH_LCD_P1, 1);
+               s3c_gpio_cfgpin(S3C2410_GPC(1), S3C_GPIO_SFN(2));
+               s3c_gpio_cfgpin(S3C2410_GPC(4), S3C_GPIO_SFN(2));
+               gpio_set_value(S3C2410_GPC(5), 1);
+               gpio_set_value(S3C2410_GPC(0), 1);
+               gpio_set_value(H1940_LATCH_LCD_P3, 1);
+               gpio_set_value(H1940_LATCH_LCD_P2, 1);
+               gpio_set_value(H1940_LATCH_LCD_P4, 1);
        }
  }
  
@@@ -273,12 -368,26 +368,26 @@@ static struct platform_device h1940_lcd
        .dev.platform_data      = &h1940_lcd_power_data,
  };
  
+ static struct uda1380_platform_data uda1380_info = {
+       .gpio_power     = H1940_LATCH_UDA_POWER,
+       .gpio_reset     = S3C2410_GPA(12),
+       .dac_clk        = UDA1380_DAC_CLK_SYSCLK,
+ };
+ static struct i2c_board_info h1940_i2c_devices[] = {
+       {
+               I2C_BOARD_INFO("uda1380", 0x1a),
+               .platform_data = &uda1380_info,
+       },
+ };
  static struct platform_device *h1940_devices[] __initdata = {
        &s3c_device_ohci,
        &s3c_device_lcd,
        &s3c_device_wdt,
        &s3c_device_i2c0,
        &s3c_device_iis,
+       &s3c_device_pcm,
        &s3c_device_usbgadget,
        &h1940_device_leds,
        &h1940_device_bluetooth,
@@@ -303,6 -412,10 +412,10 @@@ static void __init h1940_map_io(void
        memcpy(phys_to_virt(H1940_SUSPEND_RESUMEAT), h1940_pm_return, 1024);
  #endif
        s3c_pm_init();
+       /* Add latch gpio chip, set latch initial value */
+       h1940_latch_control(0, 0);
+       WARN_ON(gpiochip_add(&h1940_latch_gpiochip));
  }
  
  /* H1940 and RX3715 need to reserve this for suspend */
@@@ -340,16 -453,44 +453,42 @@@ static void __init h1940_init(void
        writel(tmp, S3C2410_UPLLCON);
  
        gpio_request(S3C2410_GPC(0), "LCD power");
+       gpio_request(S3C2410_GPC(1), "LCD power");
+       gpio_request(S3C2410_GPC(4), "LCD power");
        gpio_request(S3C2410_GPC(5), "LCD power");
        gpio_request(S3C2410_GPC(6), "LCD power");
+       gpio_request(H1940_LATCH_LCD_P0, "LCD power");
+       gpio_request(H1940_LATCH_LCD_P1, "LCD power");
+       gpio_request(H1940_LATCH_LCD_P2, "LCD power");
+       gpio_request(H1940_LATCH_LCD_P3, "LCD power");
+       gpio_request(H1940_LATCH_LCD_P4, "LCD power");
+       gpio_request(H1940_LATCH_MAX1698_nSHUTDOWN, "LCD power");
+       gpio_direction_output(S3C2410_GPC(0), 0);
+       gpio_direction_output(S3C2410_GPC(1), 0);
+       gpio_direction_output(S3C2410_GPC(4), 0);
+       gpio_direction_output(S3C2410_GPC(5), 0);
        gpio_direction_input(S3C2410_GPC(6));
+       gpio_direction_output(H1940_LATCH_LCD_P0, 0);
+       gpio_direction_output(H1940_LATCH_LCD_P1, 0);
+       gpio_direction_output(H1940_LATCH_LCD_P2, 0);
+       gpio_direction_output(H1940_LATCH_LCD_P3, 0);
+       gpio_direction_output(H1940_LATCH_LCD_P4, 0);
+       gpio_direction_output(H1940_LATCH_MAX1698_nSHUTDOWN, 0);
+       gpio_request(H1940_LATCH_USB_DP, "USB pullup");
+       gpio_direction_output(H1940_LATCH_USB_DP, 0);
+       gpio_request(H1940_LATCH_SD_POWER, "SD power");
+       gpio_direction_output(H1940_LATCH_SD_POWER, 0);
  
        platform_add_devices(h1940_devices, ARRAY_SIZE(h1940_devices));
+       i2c_register_board_info(0, h1940_i2c_devices,
+               ARRAY_SIZE(h1940_i2c_devices));
  }
  
  MACHINE_START(H1940, "IPAQ-H1940")
        /* Maintainer: Ben Dooks <ben-linux@fluff.org> */
 -      .phys_io        = S3C2410_PA_UART,
 -      .io_pg_offst    = (((u32)S3C24XX_VA_UART) >> 18) & 0xfffc,
        .boot_params    = S3C2410_SDRAM_PA + 0x100,
        .map_io         = h1940_map_io,
        .reserve        = h1940_reserve,