diff options
author | Andy Green <andy@openmoko.com> | 2008-11-26 15:22:52 +0000 |
---|---|---|
committer | Andy Green <agreen@pads.home.warmcat.com> | 2008-11-26 15:22:52 +0000 |
commit | 524f4a1dfe71a8b353a244140164e09828abb68c (patch) | |
tree | 06ac52aeb7a73d92f896a9eca262251f6036a24b /arch/arm/mach-s3c6410 | |
parent | b06c3045f1f8ab65d645f57f79ea9589cde2d09c (diff) |
clean-gta03-features.patch
Signed-off-by: Andy Green <andy@openmoko.com>
Diffstat (limited to 'arch/arm/mach-s3c6410')
-rw-r--r-- | arch/arm/mach-s3c6410/mach-om-gta03.c | 4 | ||||
-rw-r--r-- | arch/arm/mach-s3c6410/om-gta03-features.c | 309 |
2 files changed, 159 insertions, 154 deletions
diff --git a/arch/arm/mach-s3c6410/mach-om-gta03.c b/arch/arm/mach-s3c6410/mach-om-gta03.c index 0bc05f1e336..a1c39a3b0d4 100644 --- a/arch/arm/mach-s3c6410/mach-om-gta03.c +++ b/arch/arm/mach-s3c6410/mach-om-gta03.c @@ -558,6 +558,9 @@ static void om_gta03_pmu_regulator_registered(struct pcf50633 *pcf, int id) case PCF50633_REGULATOR_LDO4: pdev = &s3c_device_hsmmc0; break; + case PCF50633_REGULATOR_LDO5: /* GPS regulator */ + pdev = &om_gta03_features_dev; + break; case PCF50633_REGULATOR_LDO6: pdev = &om_gta03_lcd_powerdev; break; @@ -572,7 +575,6 @@ static void om_gta03_pmu_regulator_registered(struct pcf50633 *pcf, int id) static struct platform_device *om_gta03_devices_pmu_children[] = { &om_gta03_button_dev, &s3c_device_spi_acc1, /* relies on PMU reg for power */ - &om_gta03_features_dev, }; /* this is called when pc50633 is probed, unfortunately quite late in the diff --git a/arch/arm/mach-s3c6410/om-gta03-features.c b/arch/arm/mach-s3c6410/om-gta03-features.c index 0fc59c9b0b5..32ea4a3b0f9 100644 --- a/arch/arm/mach-s3c6410/om-gta03-features.c +++ b/arch/arm/mach-s3c6410/om-gta03-features.c @@ -29,190 +29,192 @@ #include <plat/gpio-cfg.h> -struct om_gta03_features_data { - int gps_power_was_on; - struct regulator *gps_regulator; - - int wlan_bt_power_was_on; +enum feature { + OM_GTA03_GPS, /* power to GPS section and LNA */ + OM_GTA03_WLAN_BT, /* WLAN and BT Module */ + OM_GTA03_GSM, /* GSM module */ + OM_GTA03_USBHOST, /* USB Host power generation */ + OM_GTA03_VIB, /* Vibrator */ + + OM_GTA03_FEATURE_COUNT /* always last */ +}; - int gsm_power_was_on; - int usbhost_power_was_on; +struct om_gta03_feature_info { + const char * name; + int depower_on_suspend; + int on; +}; +static struct om_gta03_feature_info feature_info[OM_GTA03_FEATURE_COUNT] = { + [OM_GTA03_GPS] = { "gps_power", 1, 0 }, + [OM_GTA03_WLAN_BT] = { "wlan_bt_power", 1, 1 }, + [OM_GTA03_GSM] = { "gsm_power", 0, 0 }, + [OM_GTA03_USBHOST] = { "usbhost_power", 1, 0 }, + [OM_GTA03_VIB] = { "vibrator_power", 1, 0 }, }; -static struct om_gta03_features_data om_gta03_features; +static struct regulator *gps_regulator; -/* GPS power */ -static void om_gta03_gps_pwron_set(int on) + +static void om_gta03_features_pwron_set_on(enum feature feature) { - if ((on) && (!om_gta03_features.gps_power_was_on)) { - regulator_enable(om_gta03_features.gps_regulator); + switch (feature) { + case OM_GTA03_GPS: + regulator_enable(gps_regulator); /* enable LNA */ gpio_direction_output(GTA03_GPIO_GPS_LNA_EN, 1); + break; + case OM_GTA03_WLAN_BT: + /* give power to WLAN / BT module */ + s3c_gpio_setpull(GTA03_GPIO_WLAN_RESET, S3C_GPIO_PULL_NONE); + s3c_gpio_cfgpin(GTA03_GPIO_WLAN_RESET, S3C_GPIO_SFN(1)); + gpio_direction_output(GTA03_GPIO_WLAN_RESET, 0); + + gpio_direction_output(GTA03_GPIO_NWLAN_POWER, 0); + s3c_gpio_setpull(GTA03_GPIO_NWLAN_POWER, S3C_GPIO_PULL_NONE); + s3c_gpio_cfgpin(GTA03_GPIO_NWLAN_POWER, S3C_GPIO_SFN(1)); + msleep(1); + gpio_direction_output(GTA03_GPIO_WLAN_RESET, 1); + break; + case OM_GTA03_GSM: + /* give power to GSM module */ + s3c_gpio_setpull(GTA03_GPIO_N_MODEM_RESET, S3C_GPIO_PULL_NONE); + s3c_gpio_cfgpin(GTA03_GPIO_N_MODEM_RESET, S3C_GPIO_SFN(1)); + gpio_direction_output(GTA03_GPIO_N_MODEM_RESET, 0); + + gpio_direction_output(GTA03_GPIO_MODEN_ON, 1); + s3c_gpio_setpull(GTA03_GPIO_MODEN_ON, S3C_GPIO_PULL_NONE); + s3c_gpio_cfgpin(GTA03_GPIO_MODEN_ON, S3C_GPIO_SFN(1)); + msleep(1); + gpio_direction_output(GTA03_GPIO_N_MODEM_RESET, 1); + break; + case OM_GTA03_USBHOST: + pcf50633_gpio_set(om_gta03_pcf_pdata.pcf, PCF50633_GPO, 1); + break; + case OM_GTA03_VIB: + gpio_direction_output(GTA03_GPIO_VIBRATOR_ON, 1); + break; + default: + break; } - - if ((!on) && (om_gta03_features.gps_power_was_on)) { - /* disable LNA */ - gpio_direction_output(GTA03_GPIO_GPS_LNA_EN, 0); - regulator_disable(om_gta03_features.gps_regulator); - } -} - -static ssize_t om_gta03_gps_power_read(struct device *dev, - struct device_attribute *attr, char *buf) -{ - if (regulator_is_enabled(om_gta03_features.gps_regulator)) - return strlcpy(buf, "1\n", 3); - else - return strlcpy(buf, "0\n", 3); } -static ssize_t om_gta03_gps_power_write(struct device *dev, - struct device_attribute *attr, - const char *buf, size_t count) +static void om_gta03_features_pwron_set_off(enum feature feature) { - int on = !!simple_strtoul(buf, NULL, 10); - - om_gta03_gps_pwron_set(on); - om_gta03_features.gps_power_was_on = on; - - return count; -} - -static DEVICE_ATTR(gps_power, 0644, om_gta03_gps_power_read, - om_gta03_gps_power_write); - -/* WLAN / BT power */ - -static void om_gta03_wlan_bt_pwron_set(int on) -{ - if (!on) { + switch (feature) { + case OM_GTA03_GPS: + /* disable LNA */ + gpio_direction_output(GTA03_GPIO_GPS_LNA_EN, 0); + regulator_disable(gps_regulator); + break; + case OM_GTA03_WLAN_BT: /* remove power from WLAN / BT module */ gpio_direction_output(GTA03_GPIO_NWLAN_POWER, 1); s3c_gpio_setpull(GTA03_GPIO_NWLAN_POWER, S3C_GPIO_PULL_NONE); s3c_gpio_cfgpin(GTA03_GPIO_NWLAN_POWER, S3C_GPIO_SFN(1)); - - return; - } - - /* give power to WLAN / BT module */ - s3c_gpio_setpull(GTA03_GPIO_WLAN_RESET, S3C_GPIO_PULL_NONE); - s3c_gpio_cfgpin(GTA03_GPIO_WLAN_RESET, S3C_GPIO_SFN(1)); - gpio_direction_output(GTA03_GPIO_WLAN_RESET, 0); - - gpio_direction_output(GTA03_GPIO_NWLAN_POWER, 0); - s3c_gpio_setpull(GTA03_GPIO_NWLAN_POWER, S3C_GPIO_PULL_NONE); - s3c_gpio_cfgpin(GTA03_GPIO_NWLAN_POWER, S3C_GPIO_SFN(1)); - msleep(1); - gpio_direction_output(GTA03_GPIO_WLAN_RESET, 1); -} - -static ssize_t om_gta03_wlan_bt_power_read(struct device *dev, - struct device_attribute *attr, char *buf) -{ - if (om_gta03_features.wlan_bt_power_was_on) - return strlcpy(buf, "1\n", 3); - else - return strlcpy(buf, "0\n", 3); -} - -static ssize_t om_gta03_wlan_bt_power_write(struct device *dev, - struct device_attribute *attr, - const char *buf, size_t count) -{ - om_gta03_wlan_bt_pwron_set(simple_strtoul(buf, NULL, 10)); - - return count; -} - -static DEVICE_ATTR(wlan_bt_power, 0644, om_gta03_wlan_bt_power_read, - om_gta03_wlan_bt_power_write); - - -/* GSM Module on / off */ - -static void om_gta03_gsm_pwron_set(int on) -{ - if (!on) { + break; + case OM_GTA03_GSM: /* remove power from WLAN / BT module */ gpio_direction_output(GTA03_GPIO_MODEN_ON, 0); s3c_gpio_setpull(GTA03_GPIO_MODEN_ON, S3C_GPIO_PULL_NONE); s3c_gpio_cfgpin(GTA03_GPIO_MODEN_ON, S3C_GPIO_SFN(1)); - - return; + break; + case OM_GTA03_USBHOST: + pcf50633_gpio_set(om_gta03_pcf_pdata.pcf, PCF50633_GPO, 0); + break; + case OM_GTA03_VIB: + gpio_direction_output(GTA03_GPIO_VIBRATOR_ON, 0); + break; + default: + break; } - - /* give power to GSM module */ - s3c_gpio_setpull(GTA03_GPIO_N_MODEM_RESET, S3C_GPIO_PULL_NONE); - s3c_gpio_cfgpin(GTA03_GPIO_N_MODEM_RESET, S3C_GPIO_SFN(1)); - gpio_direction_output(GTA03_GPIO_N_MODEM_RESET, 0); - - gpio_direction_output(GTA03_GPIO_MODEN_ON, 1); - s3c_gpio_setpull(GTA03_GPIO_MODEN_ON, S3C_GPIO_PULL_NONE); - s3c_gpio_cfgpin(GTA03_GPIO_MODEN_ON, S3C_GPIO_SFN(1)); - msleep(1); - gpio_direction_output(GTA03_GPIO_N_MODEM_RESET, 1); } -static ssize_t om_gta03_gsm_power_read(struct device *dev, - struct device_attribute *attr, char *buf) +static void om_gta03_features_pwron_set(enum feature feature, int on) { - if (om_gta03_features.gsm_power_was_on) - return strlcpy(buf, "1\n", 3); + if ((on) && (!feature_info[feature].on)) + om_gta03_features_pwron_set_on(feature); else - return strlcpy(buf, "0\n", 3); + if ((!on) && (feature_info[feature].on)) + om_gta03_features_pwron_set_off(feature); } -static ssize_t om_gta03_gsm_power_write(struct device *dev, - struct device_attribute *attr, - const char *buf, size_t count) +static ssize_t om_gta03_feature_read(struct device *dev, + struct device_attribute *attr, char *buf) { - int on = !!simple_strtoul(buf, NULL, 10); - - om_gta03_gsm_pwron_set(on); - om_gta03_features.gsm_power_was_on = on; - - return count; -} - -static DEVICE_ATTR(gsm_power, 0644, om_gta03_gsm_power_read, - om_gta03_gsm_power_write); - + int on; + int feature = 0; + int hit = 0; + + while (!hit && feature < OM_GTA03_FEATURE_COUNT) { + if (!strcmp(attr->attr.name, feature_info[feature].name)) + hit = 1; + else + feature++; + } -/* USB host power on / off */ + if (!hit) + return -EINVAL; + + switch (feature) { + case OM_GTA03_GPS: + on = regulator_is_enabled(gps_regulator); + break; + case OM_GTA03_USBHOST: + on = pcf50633_gpio_get(om_gta03_pcf_pdata.pcf, PCF50633_GPO); + break; + default: + on = feature_info[feature].on; + } -static void om_gta03_usbhost_pwron_set(int on) -{ - pcf50633_gpio_set(om_gta03_pcf_pdata.pcf, PCF50633_GPO, on); -} + *buf++ = '0' + on; + *buf++='\n'; + *buf = '\0'; -static ssize_t om_gta03_usbhost_power_read(struct device *dev, - struct device_attribute *attr, char *buf) -{ - if (pcf50633_gpio_get(om_gta03_pcf_pdata.pcf, PCF50633_GPO)) - return strlcpy(buf, "1\n", 3); - else - return strlcpy(buf, "0\n", 3); + return 3; } -static ssize_t om_gta03_usbhost_power_write(struct device *dev, +static ssize_t om_gta03_feature_write(struct device *dev, struct device_attribute *attr, const char *buf, size_t count) { int on = !!simple_strtoul(buf, NULL, 10); + int feature = 0; + int hit = 0; + + while (!hit && feature < OM_GTA03_FEATURE_COUNT) { + if (!strcmp(attr->attr.name, feature_info[feature].name)) + hit = 1; + else + feature++; + } + + if (!hit) + return -EINVAL; - om_gta03_usbhost_pwron_set(on); - om_gta03_features.usbhost_power_was_on = on; + om_gta03_features_pwron_set(feature, on); + feature_info[feature].on = on; return count; } -static DEVICE_ATTR(usbhost_power, 0644, om_gta03_usbhost_power_read, - om_gta03_usbhost_power_write); +static DEVICE_ATTR(gps_power, 0644, om_gta03_feature_read, + om_gta03_feature_write); + +static DEVICE_ATTR(wlan_bt_power, 0644, om_gta03_feature_read, + om_gta03_feature_write); + +static DEVICE_ATTR(gsm_power, 0644, om_gta03_feature_read, + om_gta03_feature_write); +static DEVICE_ATTR(usbhost_power, 0644, om_gta03_feature_read, + om_gta03_feature_write); + +static DEVICE_ATTR(vibrator_power, 0644, om_gta03_feature_read, + om_gta03_feature_write); static struct attribute *om_gta03_features_sysfs_entries[] = { @@ -220,9 +222,11 @@ static struct attribute *om_gta03_features_sysfs_entries[] = { &dev_attr_wlan_bt_power.attr, &dev_attr_gsm_power.attr, &dev_attr_usbhost_power.attr, + &dev_attr_vibrator_power.attr, NULL }; + static struct attribute_group om_gta03_features_attr_group = { .name = NULL, .attrs = om_gta03_features_sysfs_entries, @@ -230,18 +234,17 @@ static struct attribute_group om_gta03_features_attr_group = { static int __init om_gta03_features_probe(struct platform_device *pdev) { - om_gta03_features.gps_regulator = regulator_get(&pdev->dev, "RF_3V"); + gps_regulator = regulator_get(&pdev->dev, "RF_3V"); dev_info(&pdev->dev, "starting\n"); - om_gta03_features.wlan_bt_power_was_on = 1; /* defaults to on */ - - return sysfs_create_group(&pdev->dev.kobj, &om_gta03_features_attr_group); + return sysfs_create_group(&pdev->dev.kobj, + &om_gta03_features_attr_group); } static int om_gta03_features_remove(struct platform_device *pdev) { - regulator_put(om_gta03_features.gps_regulator); + regulator_put(gps_regulator); sysfs_remove_group(&pdev->dev.kobj, &om_gta03_features_attr_group); return 0; @@ -252,23 +255,23 @@ static int om_gta03_features_remove(struct platform_device *pdev) static int om_gta03_features_suspend(struct platform_device *pdev, pm_message_t state) { - om_gta03_gps_pwron_set(0); - om_gta03_wlan_bt_pwron_set(0); - om_gta03_usbhost_pwron_set(0); + int feature; + + for (feature = 0; feature < OM_GTA03_FEATURE_COUNT; feature++) + if (feature_info[feature].depower_on_suspend) + om_gta03_features_pwron_set_off(feature); return 0; } static int om_gta03_features_resume(struct platform_device *pdev) { - if (om_gta03_features.gps_power_was_on) - om_gta03_gps_pwron_set(1); - - if (om_gta03_features.wlan_bt_power_was_on) - om_gta03_wlan_bt_pwron_set(1); + int feature; - if (om_gta03_features.usbhost_power_was_on) - om_gta03_usbhost_pwron_set(1); + for (feature = 0; feature < OM_GTA03_FEATURE_COUNT; feature++) + if (feature_info[feature].depower_on_suspend) + if (feature_info[feature].on) + om_gta03_features_pwron_set_on(feature); return 0; } |