aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorThomas White <taw@bitwiz.org.uk>2009-09-11 12:49:39 +0100
committerThomas White <taw@bitwiz.org.uk>2009-09-11 12:49:39 +0100
commitcd38bcdac64aec45575ed58de66db4a2fbf1914d (patch)
tree450333c7a1c67685db627edda3e1376a5bd46a2e
parent166226209d59b1210cadfdec6b31e7d633100d9d (diff)
parenta3587e4ed77974adfb057af261aaeea4022018e8 (diff)
Merge commit 'remotes/openmoko/andy-tracking' into drm-tracking
-rw-r--r--arch/arm/configs/gta01_moredrivers_defconfig4
-rw-r--r--arch/arm/configs/gta02_moredrivers_defconfig2
-rw-r--r--arch/arm/configs/gta02_packaging_defconfig6
-rw-r--r--arch/arm/mach-s3c2410/mach-gta01.c6
-rw-r--r--arch/arm/mach-s3c2442/mach-gta02.c38
-rw-r--r--arch/arm/plat-s3c24xx/neo1973_pm_gps.c3
-rw-r--r--drivers/ar6000/ar6000/ar6000_drv.c150
-rw-r--r--drivers/input/keyboard/neo1973kbd.c6
-rw-r--r--drivers/mfd/glamo/glamo-fb.c4
-rw-r--r--drivers/mfd/glamo/glamo-mci.c2
-rw-r--r--drivers/mfd/pcf50606-core.c6
-rw-r--r--drivers/mfd/pcf50633-adc.c32
-rw-r--r--drivers/mfd/pcf50633-core.c9
-rw-r--r--drivers/power/Kconfig1
-rw-r--r--drivers/power/bq27000_battery.c3
-rw-r--r--drivers/power/gta01_battery.c71
-rw-r--r--drivers/power/pcf50633-charger.c101
-rw-r--r--drivers/rtc/rtc-pcf50606.c9
-rw-r--r--drivers/usb/gadget/rndis.c19
-rw-r--r--include/linux/mfd/pcf50633/adc.h3
-rw-r--r--include/linux/mfd/pcf50633/core.h3
-rw-r--r--include/linux/mfd/pcf50633/mbc.h1
-rw-r--r--include/linux/resume-dependency.h2
-rw-r--r--sound/soc/codecs/wm8753.c6
-rw-r--r--sound/soc/s3c24xx/neo1973_wm8753.c16
25 files changed, 294 insertions, 209 deletions
diff --git a/arch/arm/configs/gta01_moredrivers_defconfig b/arch/arm/configs/gta01_moredrivers_defconfig
index 1f5883729dc..36d2b170b52 100644
--- a/arch/arm/configs/gta01_moredrivers_defconfig
+++ b/arch/arm/configs/gta01_moredrivers_defconfig
@@ -1839,7 +1839,7 @@ CONFIG_NLS_CODEPAGE_850=m
# CONFIG_NLS_CODEPAGE_863 is not set
# CONFIG_NLS_CODEPAGE_864 is not set
# CONFIG_NLS_CODEPAGE_865 is not set
-# CONFIG_NLS_CODEPAGE_866 is not set
+CONFIG_NLS_CODEPAGE_866=m
# CONFIG_NLS_CODEPAGE_869 is not set
CONFIG_NLS_CODEPAGE_936=m
CONFIG_NLS_CODEPAGE_950=m
@@ -1848,7 +1848,7 @@ CONFIG_NLS_CODEPAGE_950=m
# CONFIG_NLS_CODEPAGE_874 is not set
# CONFIG_NLS_ISO8859_8 is not set
# CONFIG_NLS_CODEPAGE_1250 is not set
-# CONFIG_NLS_CODEPAGE_1251 is not set
+CONFIG_NLS_CODEPAGE_1251=m
# CONFIG_NLS_ASCII is not set
CONFIG_NLS_ISO8859_1=y
# CONFIG_NLS_ISO8859_2 is not set
diff --git a/arch/arm/configs/gta02_moredrivers_defconfig b/arch/arm/configs/gta02_moredrivers_defconfig
index 8d06cd6c70b..bd66869f74a 100644
--- a/arch/arm/configs/gta02_moredrivers_defconfig
+++ b/arch/arm/configs/gta02_moredrivers_defconfig
@@ -1177,7 +1177,7 @@ CONFIG_APM_POWER=y
CONFIG_CHARGER_PCF50633=y
CONFIG_BATTERY_BQ27000_HDQ=y
CONFIG_HDQ_GPIO_BITBANG=y
-# CONFIG_BATTERY_GTA01 is not set
+CONFIG_BATTERY_GTA01=m
CONFIG_HWMON=y
# CONFIG_HWMON_VID is not set
# CONFIG_SENSORS_AD7414 is not set
diff --git a/arch/arm/configs/gta02_packaging_defconfig b/arch/arm/configs/gta02_packaging_defconfig
index dfdfb19a2f1..15defd28841 100644
--- a/arch/arm/configs/gta02_packaging_defconfig
+++ b/arch/arm/configs/gta02_packaging_defconfig
@@ -1180,7 +1180,7 @@ CONFIG_APM_POWER=y
CONFIG_CHARGER_PCF50633=y
CONFIG_BATTERY_BQ27000_HDQ=y
CONFIG_HDQ_GPIO_BITBANG=y
-# CONFIG_BATTERY_GTA01 is not set
+CONFIG_BATTERY_GTA01=m
CONFIG_HWMON=y
# CONFIG_HWMON_VID is not set
# CONFIG_SENSORS_AD7414 is not set
@@ -1953,7 +1953,7 @@ CONFIG_NLS_CODEPAGE_850=m
# CONFIG_NLS_CODEPAGE_863 is not set
# CONFIG_NLS_CODEPAGE_864 is not set
# CONFIG_NLS_CODEPAGE_865 is not set
-# CONFIG_NLS_CODEPAGE_866 is not set
+CONFIG_NLS_CODEPAGE_866=m
# CONFIG_NLS_CODEPAGE_869 is not set
CONFIG_NLS_CODEPAGE_936=m
CONFIG_NLS_CODEPAGE_950=m
@@ -1962,7 +1962,7 @@ CONFIG_NLS_CODEPAGE_950=m
# CONFIG_NLS_CODEPAGE_874 is not set
# CONFIG_NLS_ISO8859_8 is not set
# CONFIG_NLS_CODEPAGE_1250 is not set
-# CONFIG_NLS_CODEPAGE_1251 is not set
+CONFIG_NLS_CODEPAGE_1251=m
# CONFIG_NLS_ASCII is not set
CONFIG_NLS_ISO8859_1=y
# CONFIG_NLS_ISO8859_2 is not set
diff --git a/arch/arm/mach-s3c2410/mach-gta01.c b/arch/arm/mach-s3c2410/mach-gta01.c
index 1fe3eef2257..8a13a4adcfd 100644
--- a/arch/arm/mach-s3c2410/mach-gta01.c
+++ b/arch/arm/mach-s3c2410/mach-gta01.c
@@ -237,7 +237,7 @@ static int gta01_bat_get_voltage(void)
adc = pcf50606_adc_sync_read(pcf, PCF50606_ADCMUX_BATVOLT_RES);
mv = (adc * 6000) / 1024;
- return mv;
+ return mv * 1000;
}
static int gta01_bat_get_current(void)
@@ -248,10 +248,10 @@ static int gta01_bat_get_current(void)
adc_battvolt = pcf50606_adc_sync_read(pcf, PCF50606_ADCMUX_BATVOLT_SUBTR);
adc_adcin1 = pcf50606_adc_sync_read(pcf, PCF50606_ADCMUX_ADCIN1_SUBTR);
- res = (adc_adcin1 - adc_battvolt) * 2400;
+ res = (adc_battvolt - adc_adcin1) * 2400;
/*rsense is 220 milli */
- return (res * 1000) / (220 * 1024);
+ return (res * 1000) / (220 * 1024) * 1000;
}
static struct gta01_bat_platform_data gta01_bat_pdata = {
diff --git a/arch/arm/mach-s3c2442/mach-gta02.c b/arch/arm/mach-s3c2442/mach-gta02.c
index e7a5f0a55a1..0a93749ef8c 100644
--- a/arch/arm/mach-s3c2442/mach-gta02.c
+++ b/arch/arm/mach-s3c2442/mach-gta02.c
@@ -100,6 +100,7 @@
#include <linux/hdq.h>
#include <linux/bq27000_battery.h>
+#include <linux/gta01_battery.h>
#include "../plat-s3c24xx/neo1973_pm_gps.h"
@@ -391,7 +392,7 @@ static int gta02_get_charger_online_status(void)
{
struct pcf50633 *pcf = gta02_pcf;
- return pcf50633_mbc_get_status(pcf) & PCF50633_MBC_USB_ONLINE;
+ return pcf50633_mbc_get_usb_online_status(pcf);
}
static int gta02_get_charger_active_status(void)
@@ -484,12 +485,13 @@ static int gta02_udc_vbus_status(void)
if (!gta02_pcf)
return -ENODEV;
- return !!(pcf50633_mbc_get_status(pcf) & PCF50633_MBC_USB_ONLINE);
+ return pcf50633_mbc_get_usb_online_status(pcf);
}
#else /* !CONFIG_CHARGER_PCF50633 */
#define gta02_get_charger_online_status NULL
#define gta02_get_charger_active_status NULL
#define gta02_pmu_event_callback NULL
+#define gta02_pmu_force_shutdown NULL
#define gta02_udc_vbus_draw NULL
#define gta02_udc_vbus_status NULL
#endif
@@ -569,7 +571,6 @@ struct pcf50633_platform_data gta02_pcf_pdata = {
.batteries = gta02_batteries,
.num_batteries = ARRAY_SIZE(gta02_batteries),
- .charging_restart_interval = (900 * HZ),
.chg_ref_current_ma = 1000,
.reg_init_data = {
@@ -726,7 +727,7 @@ static void mangle_pmu_pdata_by_system_rev(void)
reg_init_data[PCF50633_REGULATOR_LDO1]
.constraints.min_uV = 3300000;
reg_init_data[PCF50633_REGULATOR_LDO1]
- .constraints.min_uV = 3300000;
+ .constraints.max_uV = 3300000;
reg_init_data[PCF50633_REGULATOR_LDO1]
.constraints.state_mem.enabled = 0;
@@ -747,6 +748,34 @@ static void mangle_pmu_pdata_by_system_rev(void)
}
}
+static int gta02_bat_get_voltage(void)
+{
+ struct pcf50633 *pcf = gta02_pcf;
+ u16 adc, mv = 0;
+ adc = pcf50633_adc_sync_read(pcf,
+ PCF50633_ADCC1_MUX_BATSNS_RES,
+ PCF50633_ADCC1_AVERAGE_16);
+ /* The formula from DS is for divide-by-two mode, current driver uses
+ divide-by-three */
+ mv = (adc * 6000) / 1023;
+ return mv * 1000;
+}
+
+static struct gta01_bat_platform_data gta01_bat_pdata = {
+#ifdef CONFIG_CHARGER_PCF50633
+ .get_charging_status = gta02_get_charger_active_status,
+#endif
+ .get_voltage = gta02_bat_get_voltage,
+};
+
+struct platform_device gta01_bat = {
+ .name = "gta01_battery",
+ .id = -1,
+ .dev = {
+ .platform_data = &gta01_bat_pdata,
+ }
+};
+
#ifdef CONFIG_HDQ_GPIO_BITBANG
/* BQ27000 Battery */
@@ -1551,6 +1580,7 @@ static struct platform_device *gta02_devices_pmu_children[] = {
&gta02_spi_gpio_dev, /* input 2 and 3 */
&gta02_button_dev, /* input 4 */
&gta02_resume_reason_device,
+ &gta01_bat,
};
static void gta02_pmu_regulator_registered(struct pcf50633 *pcf, int id)
diff --git a/arch/arm/plat-s3c24xx/neo1973_pm_gps.c b/arch/arm/plat-s3c24xx/neo1973_pm_gps.c
index 93b491137e7..b59d4959257 100644
--- a/arch/arm/plat-s3c24xx/neo1973_pm_gps.c
+++ b/arch/arm/plat-s3c24xx/neo1973_pm_gps.c
@@ -305,7 +305,8 @@ static void gps_pwron_set(int on)
/* remove pulldown now it won't be floating any more */
s3c2410_gpio_pullup(S3C2410_GPH5, 0);
- if (!neo1973_gps.power_was_on)
+ if (!regulator_is_enabled(neo1973_gps.regulator[
+ GTA02_GPS_REG_RF_3V]))
regulator_enable(neo1973_gps.regulator[
GTA02_GPS_REG_RF_3V]);
return;
diff --git a/drivers/ar6000/ar6000/ar6000_drv.c b/drivers/ar6000/ar6000/ar6000_drv.c
index b790670ece8..21504f221dd 100644
--- a/drivers/ar6000/ar6000/ar6000_drv.c
+++ b/drivers/ar6000/ar6000/ar6000_drv.c
@@ -974,17 +974,86 @@ ar6000_destroy(struct net_device *dev, unsigned int unregister)
return;
}
+ /* Stop the transmit queues */
+ netif_stop_queue(dev);
+
+ /* Disable the target and the interrupts associated with it */
+ if (ar->arWmiReady == TRUE)
+ {
+ if (!bypasswmi)
+ {
+ if (ar->arConnected == TRUE || ar->arConnectPending == TRUE)
+ {
+ AR_DEBUG_PRINTF("%s(): Disconnect\n", __func__);
+ AR6000_SPIN_LOCK(&ar->arLock, 0);
+ ar6000_init_profile_info(ar);
+ AR6000_SPIN_UNLOCK(&ar->arLock, 0);
+ wmi_disconnect_cmd(ar->arWmi);
+ }
+
+ ar6000_dbglog_get_debug_logs(ar);
+ ar->arWmiReady = FALSE;
+ ar->arConnected = FALSE;
+ ar->arConnectPending = FALSE;
+ wmi_shutdown(ar->arWmi);
+ ar->arWmiEnabled = FALSE;
+ ar->arWmi = NULL;
+ ar->arWlanState = WLAN_ENABLED;
+#ifdef USER_KEYS
+ ar->user_savedkeys_stat = USER_SAVEDKEYS_STAT_INIT;
+ ar->user_key_ctrl = 0;
+#endif
+ }
+
+ AR_DEBUG_PRINTF("%s(): WMI stopped\n", __func__);
+ }
+ else
+ {
+ AR_DEBUG_PRINTF("%s(): WMI not ready 0x%08x 0x%08x\n",
+ __func__, (unsigned int) ar, (unsigned int) ar->arWmi);
+
+ /* Shut down WMI if we have started it */
+ if(ar->arWmiEnabled == TRUE)
+ {
+ AR_DEBUG_PRINTF("%s(): Shut down WMI\n", __func__);
+ wmi_shutdown(ar->arWmi);
+ ar->arWmiEnabled = FALSE;
+ ar->arWmi = NULL;
+ }
+ }
+
+ /* stop HTC */
+ HTCStop(ar->arHtcTarget);
+
+ /* set the instance to NULL so we do not get called back on remove incase we
+ * we're explicity destroyed by module unload */
+ HTCSetInstance(ar->arHtcTarget, NULL);
+
+ if (resetok) {
+ /* try to reset the device if we can
+ * The driver may have been configure NOT to reset the target during
+ * a debug session */
+ AR_DEBUG_PRINTF(" Attempting to reset target on instance destroy.... \n");
+ ar6000_reset_device(ar->arHifDevice, ar->arTargetType);
+ } else {
+ AR_DEBUG_PRINTF(" Host does not want target reset. \n");
+ }
+
+ /* Done with cookies */
+ ar6000_cookie_cleanup(ar);
+
+ /* Cleanup BMI */
+ BMIInit();
+
/* Clear the tx counters */
memset(tx_attempt, 0, sizeof(tx_attempt));
memset(tx_post, 0, sizeof(tx_post));
memset(tx_complete, 0, sizeof(tx_complete));
+
/* Free up the device data structure */
- if (unregister) {
- unregister_netdev(dev);
- } else {
- ar6000_close(dev);
- }
+ if (unregister)
+ unregister_netdev(dev);
free_raw_buffers(ar);
@@ -1090,79 +1159,8 @@ ar6000_open(struct net_device *dev)
static int
ar6000_close(struct net_device *dev)
{
- AR_SOFTC_T *ar = netdev_priv(dev);
-
- /* Stop the transmit queues */
netif_stop_queue(dev);
- /* Disable the target and the interrupts associated with it */
- if (ar->arWmiReady == TRUE)
- {
- if (!bypasswmi)
- {
- if (ar->arConnected == TRUE || ar->arConnectPending == TRUE)
- {
- AR_DEBUG_PRINTF("%s(): Disconnect\n", __func__);
- AR6000_SPIN_LOCK(&ar->arLock, 0);
- ar6000_init_profile_info(ar);
- AR6000_SPIN_UNLOCK(&ar->arLock, 0);
- wmi_disconnect_cmd(ar->arWmi);
- }
-
- ar6000_dbglog_get_debug_logs(ar);
- ar->arWmiReady = FALSE;
- ar->arConnected = FALSE;
- ar->arConnectPending = FALSE;
- wmi_shutdown(ar->arWmi);
- ar->arWmiEnabled = FALSE;
- ar->arWmi = NULL;
- ar->arWlanState = WLAN_ENABLED;
-#ifdef USER_KEYS
- ar->user_savedkeys_stat = USER_SAVEDKEYS_STAT_INIT;
- ar->user_key_ctrl = 0;
-#endif
- }
-
- AR_DEBUG_PRINTF("%s(): WMI stopped\n", __func__);
- }
- else
- {
- AR_DEBUG_PRINTF("%s(): WMI not ready 0x%08x 0x%08x\n",
- __func__, (unsigned int) ar, (unsigned int) ar->arWmi);
-
- /* Shut down WMI if we have started it */
- if(ar->arWmiEnabled == TRUE)
- {
- AR_DEBUG_PRINTF("%s(): Shut down WMI\n", __func__);
- wmi_shutdown(ar->arWmi);
- ar->arWmiEnabled = FALSE;
- ar->arWmi = NULL;
- }
- }
-
- /* stop HTC */
- HTCStop(ar->arHtcTarget);
-
- /* set the instance to NULL so we do not get called back on remove incase we
- * we're explicity destroyed by module unload */
- HTCSetInstance(ar->arHtcTarget, NULL);
-
- if (resetok) {
- /* try to reset the device if we can
- * The driver may have been configure NOT to reset the target during
- * a debug session */
- AR_DEBUG_PRINTF(" Attempting to reset target on instance destroy.... \n");
- ar6000_reset_device(ar->arHifDevice, ar->arTargetType);
- } else {
- AR_DEBUG_PRINTF(" Host does not want target reset. \n");
- }
-
- /* Done with cookies */
- ar6000_cookie_cleanup(ar);
-
- /* Cleanup BMI */
- BMIInit();
-
return 0;
}
diff --git a/drivers/input/keyboard/neo1973kbd.c b/drivers/input/keyboard/neo1973kbd.c
index a95dd5806d2..8756ae60910 100644
--- a/drivers/input/keyboard/neo1973kbd.c
+++ b/drivers/input/keyboard/neo1973kbd.c
@@ -75,7 +75,7 @@ static struct neo1973kbd_key keys[] = {
[NEO1973_KEY_HOLD] = {
.name = "Neo1973 HOLD button",
.isr = neo1973kbd_default_key_irq,
- .input_key = KEY_PAUSE,
+ .input_key = KEY_PLAY,
},
[NEO1973_KEY_JACK] = {
.name = "Neo1973 Headphone jack",
@@ -161,7 +161,7 @@ static irqreturn_t neo1973kbd_default_key_irq(int irq, void *dev_id)
continue;
input_report_key(kbd->input, keys[n].input_key,
- gpio_get_value(kbd->pdev->resource[n].start));
+ !gpio_get_value(kbd->pdev->resource[n].start));
input_sync(kbd->input);
}
@@ -346,7 +346,7 @@ static int neo1973kbd_probe(struct platform_device *pdev)
input_dev->evbit[0] = BIT(EV_KEY) | BIT(EV_SW);
set_bit(SW_HEADPHONE_INSERT, input_dev->swbit);
set_bit(KEY_PHONE, input_dev->keybit);
- set_bit(KEY_PAUSE, input_dev->keybit);
+ set_bit(KEY_PLAY, input_dev->keybit);
rc = input_register_device(neo1973kbd->input);
if (rc)
diff --git a/drivers/mfd/glamo/glamo-fb.c b/drivers/mfd/glamo/glamo-fb.c
index 95d40d25cf7..06bbe8a505f 100644
--- a/drivers/mfd/glamo/glamo-fb.c
+++ b/drivers/mfd/glamo/glamo-fb.c
@@ -1067,7 +1067,7 @@ static int __init glamofb_probe(struct platform_device *pdev)
glamo_engine_enable(mach_info->glamo, GLAMO_ENGINE_LCD);
glamo_engine_reset(mach_info->glamo, GLAMO_ENGINE_LCD);
- dev_info(&pdev->dev, "spin_lock_init\n");
+ dev_dbg(&pdev->dev, "spin_lock_init\n");
spin_lock_init(&glamofb->lock_cmd);
glamofb_init_regs(glamofb);
#ifdef CONFIG_MFD_GLAMO_HWACCEL
@@ -1154,7 +1154,7 @@ static int glamofb_resume(struct platform_device *pdev)
glamo_engine_enable(mach_info->glamo, GLAMO_ENGINE_LCD);
glamo_engine_reset(mach_info->glamo, GLAMO_ENGINE_LCD);
- printk(KERN_ERR"spin_lock_init\n");
+ dev_dbg(&pdev->dev, "spin_lock_init\n");
spin_lock_init(&gfb->lock_cmd);
glamofb_init_regs(gfb);
#ifdef CONFIG_MFD_GLAMO_HWACCEL
diff --git a/drivers/mfd/glamo/glamo-mci.c b/drivers/mfd/glamo/glamo-mci.c
index 398f8634a9b..a3b4c5e4962 100644
--- a/drivers/mfd/glamo/glamo-mci.c
+++ b/drivers/mfd/glamo/glamo-mci.c
@@ -616,7 +616,7 @@ static void glamo_mci_send_request(struct mmc_host *mmc)
int insanity_timeout = 1000000;
if (host->suspending) {
- dev_err(&host->pdev->dev, "IGNORING glamo_mci_send_request while "
+ dev_dbg(&host->pdev->dev, "REFUSING glamo_mci_send_request while "
"suspended\n");
cmd->error = -EIO;
if (cmd->data)
diff --git a/drivers/mfd/pcf50606-core.c b/drivers/mfd/pcf50606-core.c
index 7c4fb42b460..09ce70b9b79 100644
--- a/drivers/mfd/pcf50606-core.c
+++ b/drivers/mfd/pcf50606-core.c
@@ -282,7 +282,7 @@ out:
int pcf50606_irq_mask(struct pcf50606 *pcf, int irq)
{
- dev_info(pcf->dev, "Masking IRQ %d\n", irq);
+ dev_dbg(pcf->dev, "Masking IRQ %d\n", irq);
return __pcf50606_irq_mask_set(pcf, irq, 1);
}
@@ -290,7 +290,7 @@ EXPORT_SYMBOL_GPL(pcf50606_irq_mask);
int pcf50606_irq_unmask(struct pcf50606 *pcf, int irq)
{
- dev_info(pcf->dev, "Unmasking IRQ %d\n", irq);
+ dev_dbg(pcf->dev, "Unmasking IRQ %d\n", irq);
return __pcf50606_irq_mask_set(pcf, irq, 0);
}
@@ -330,7 +330,7 @@ static void pcf50606_irq_worker(struct work_struct *work)
ret = pcf50606_read_block(pcf, PCF50606_REG_INT1,
ARRAY_SIZE(pcf_int), pcf_int);
if (ret != ARRAY_SIZE(pcf_int)) {
- dev_info(pcf->dev, "Error reading INT registers\n");
+ dev_err(pcf->dev, "Error reading INT registers\n");
/*
* If this doesn't ACK the interrupt to the chip, we'll be
diff --git a/drivers/mfd/pcf50633-adc.c b/drivers/mfd/pcf50633-adc.c
index c2d05becfa9..3d31e97d6a4 100644
--- a/drivers/mfd/pcf50633-adc.c
+++ b/drivers/mfd/pcf50633-adc.c
@@ -73,15 +73,10 @@ static void trigger_next_adc_job_if_any(struct pcf50633 *pcf)
struct pcf50633_adc *adc = __to_adc(pcf);
int head;
- mutex_lock(&adc->queue_mutex);
-
head = adc->queue_head;
- if (!adc->queue[head]) {
- mutex_unlock(&adc->queue_mutex);
+ if (!adc->queue[head])
return;
- }
- mutex_unlock(&adc->queue_mutex);
adc_setup(pcf, adc->queue[head]->mux, adc->queue[head]->avg);
}
@@ -99,16 +94,17 @@ adc_enqueue_request(struct pcf50633 *pcf, struct pcf50633_adc_request *req)
if (adc->queue[tail]) {
mutex_unlock(&adc->queue_mutex);
+ dev_err(pcf->dev, "ADC queue is full, dropping request\n");
return -EBUSY;
}
adc->queue[tail] = req;
+ if (head == tail)
+ trigger_next_adc_job_if_any(pcf);
adc->queue_tail = (tail + 1) & (PCF50633_MAX_ADC_FIFO_DEPTH - 1);
mutex_unlock(&adc->queue_mutex);
- trigger_next_adc_job_if_any(pcf);
-
return 0;
}
@@ -124,6 +120,7 @@ pcf50633_adc_sync_read_callback(struct pcf50633 *pcf, void *param, int result)
int pcf50633_adc_sync_read(struct pcf50633 *pcf, int mux, int avg)
{
struct pcf50633_adc_request *req;
+ int err;
/* req is freed when the result is ready, in interrupt handler */
req = kzalloc(sizeof(*req), GFP_KERNEL);
@@ -136,9 +133,13 @@ int pcf50633_adc_sync_read(struct pcf50633 *pcf, int mux, int avg)
req->callback_param = req;
init_completion(&req->completion);
- adc_enqueue_request(pcf, req);
+ err = adc_enqueue_request(pcf, req);
+ if (err)
+ return err;
+
wait_for_completion(&req->completion);
+ /* FIXME by this time req might be already freed */
return req->result;
}
EXPORT_SYMBOL_GPL(pcf50633_adc_sync_read);
@@ -159,9 +160,7 @@ int pcf50633_adc_async_read(struct pcf50633 *pcf, int mux, int avg,
req->callback = callback;
req->callback_param = callback_param;
- adc_enqueue_request(pcf, req);
-
- return 0;
+ return adc_enqueue_request(pcf, req);
}
EXPORT_SYMBOL_GPL(pcf50633_adc_async_read);
@@ -184,7 +183,7 @@ static void pcf50633_adc_irq(int irq, void *data)
struct pcf50633_adc *adc = data;
struct pcf50633 *pcf = adc->pcf;
struct pcf50633_adc_request *req;
- int head;
+ int head, res;
mutex_lock(&adc->queue_mutex);
head = adc->queue_head;
@@ -199,12 +198,13 @@ static void pcf50633_adc_irq(int irq, void *data)
adc->queue_head = (head + 1) &
(PCF50633_MAX_ADC_FIFO_DEPTH - 1);
+ res = adc_result(pcf);
+ trigger_next_adc_job_if_any(pcf);
+
mutex_unlock(&adc->queue_mutex);
- req->callback(pcf, req->callback_param, adc_result(pcf));
+ req->callback(pcf, req->callback_param, res);
kfree(req);
-
- trigger_next_adc_job_if_any(pcf);
}
static int __devinit pcf50633_adc_probe(struct platform_device *pdev)
diff --git a/drivers/mfd/pcf50633-core.c b/drivers/mfd/pcf50633-core.c
index 29c9395d65f..b3c96015600 100644
--- a/drivers/mfd/pcf50633-core.c
+++ b/drivers/mfd/pcf50633-core.c
@@ -291,7 +291,7 @@ out:
int pcf50633_irq_mask(struct pcf50633 *pcf, int irq)
{
- dev_info(pcf->dev, "Masking IRQ %d\n", irq);
+ dev_dbg(pcf->dev, "Masking IRQ %d\n", irq);
return __pcf50633_irq_mask_set(pcf, irq, 1);
}
@@ -299,7 +299,7 @@ EXPORT_SYMBOL_GPL(pcf50633_irq_mask);
int pcf50633_irq_unmask(struct pcf50633 *pcf, int irq)
{
- dev_info(pcf->dev, "Unmasking IRQ %d\n", irq);
+ dev_dbg(pcf->dev, "Unmasking IRQ %d\n", irq);
return __pcf50633_irq_mask_set(pcf, irq, 0);
}
@@ -448,7 +448,7 @@ static irqreturn_t pcf50633_irq(int irq, void *data)
get_device(pcf->dev);
disable_irq(pcf->irq);
- schedule_work(&pcf->irq_work);
+ queue_work(pcf->work_queue, &pcf->irq_work);
return IRQ_HANDLED;
}
@@ -579,6 +579,7 @@ static int __devinit pcf50633_probe(struct i2c_client *client,
pcf->dev = &client->dev;
pcf->i2c_client = client;
pcf->irq = client->irq;
+ pcf->work_queue = create_singlethread_workqueue("pcf50633");
INIT_WORK(&pcf->irq_work, pcf50633_irq_worker);
@@ -656,6 +657,7 @@ static int __devinit pcf50633_probe(struct i2c_client *client,
return 0;
err:
+ destroy_workqueue(pcf->work_queue);
kfree(pcf);
return ret;
}
@@ -666,6 +668,7 @@ static int __devexit pcf50633_remove(struct i2c_client *client)
int i;
free_irq(pcf->irq, pcf);
+ destroy_workqueue(pcf->work_queue);
platform_device_unregister(pcf->input_pdev);
platform_device_unregister(pcf->rtc_pdev);
diff --git a/drivers/power/Kconfig b/drivers/power/Kconfig
index b5332f714cd..f88c5aab640 100644
--- a/drivers/power/Kconfig
+++ b/drivers/power/Kconfig
@@ -90,6 +90,7 @@ config CHARGER_PCF50633
config BATTERY_BQ27000_HDQ
tristate "BQ27000 HDQ battery monitor driver"
+ select HDQ_GPIO_BITBANG
help
Say Y to enable support for the battery on the Neo Freerunner
diff --git a/drivers/power/bq27000_battery.c b/drivers/power/bq27000_battery.c
index 593cbe6f752..f1dcda3297d 100644
--- a/drivers/power/bq27000_battery.c
+++ b/drivers/power/bq27000_battery.c
@@ -186,6 +186,9 @@ static int bq27000_battery_get_property(struct power_supply *psy,
int n;
struct bq27000_device_info *di = container_of(psy, struct bq27000_device_info, bat);
+ if (di->regs.rsoc < 0 && psp != POWER_SUPPLY_PROP_PRESENT)
+ return -ENODEV;
+
switch (psp) {
case POWER_SUPPLY_PROP_STATUS:
val->intval = POWER_SUPPLY_STATUS_UNKNOWN;
diff --git a/drivers/power/gta01_battery.c b/drivers/power/gta01_battery.c
index 81a0fe7387e..2078b071b06 100644
--- a/drivers/power/gta01_battery.c
+++ b/drivers/power/gta01_battery.c
@@ -23,8 +23,40 @@ static enum power_supply_property gta01_bat_props[] = {
POWER_SUPPLY_PROP_STATUS,
POWER_SUPPLY_PROP_VOLTAGE_NOW,
POWER_SUPPLY_PROP_CURRENT_NOW,
+ POWER_SUPPLY_PROP_CAPACITY,
+ POWER_SUPPLY_PROP_CHARGE_FULL,
+ POWER_SUPPLY_PROP_CHARGE_NOW,
};
+/* Capacity of typical BL-5C dumb battery */
+#define GTA01_BAT_CHARGE_FULL 850000
+
+static int gta01_bat_voltscale(int volt)
+{
+ /* This table is suggested by SpeedEvil based on analysis of
+ * experimental data */
+ static const int lut[][2] = {
+ { 4120, 100 },
+ { 3900, 60 },
+ { 3740, 25 },
+ { 3600, 5 },
+ { 3000, 0 } };
+ int i, res = 0;
+
+ if (volt > lut[0][0])
+ res = lut[0][1];
+ else
+ for (i = 0; lut[i][1]; i++) {
+ if (volt <= lut[i][0] && volt >= lut[i+1][0]) {
+ res = lut[i][1] - (lut[i][0]-volt)*
+ (lut[i][1]-lut[i+1][1])/
+ (lut[i][0]-lut[i+1][0]);
+ break;
+ }
+ }
+ return res;
+}
+
static int gta01_bat_get_property(struct power_supply *psy,
enum power_supply_property psp,
union power_supply_propval *val)
@@ -33,20 +65,48 @@ static int gta01_bat_get_property(struct power_supply *psy,
switch(psp) {
case POWER_SUPPLY_PROP_STATUS:
- if (bat->pdata->get_charging_status())
- val->intval = POWER_SUPPLY_STATUS_CHARGING;
+ if (bat->pdata->get_charging_status)
+ if (bat->pdata->get_charging_status())
+ val->intval = POWER_SUPPLY_STATUS_CHARGING;
+ else
+ val->intval = POWER_SUPPLY_STATUS_DISCHARGING;
else
- val->intval = POWER_SUPPLY_STATUS_DISCHARGING;
+ val->intval = POWER_SUPPLY_STATUS_UNKNOWN;
break;
case POWER_SUPPLY_PROP_VOLTAGE_NOW:
- val->intval = bat->pdata->get_voltage();
+ if (bat->pdata->get_voltage)
+ val->intval = bat->pdata->get_voltage();
+ else
+ val->intval = 0;
break;
case POWER_SUPPLY_PROP_CURRENT_NOW:
- val->intval = bat->pdata->get_current();
+ if (bat->pdata->get_current)
+ val->intval = bat->pdata->get_current();
+ else
+ val->intval = 0;
break;
case POWER_SUPPLY_PROP_PRESENT:
val->intval = 1; /* You must never run GTA01 without battery. */
break;
+ case POWER_SUPPLY_PROP_CHARGE_NOW:
+ if (bat->pdata->get_voltage) {
+ int perc = gta01_bat_voltscale(
+ bat->pdata->get_voltage()/1000);
+ val->intval = perc * GTA01_BAT_CHARGE_FULL / 100;
+ } else
+ val->intval = 0;
+ break;
+ case POWER_SUPPLY_PROP_CAPACITY:
+ if (bat->pdata->get_voltage)
+ val->intval = gta01_bat_voltscale(
+ bat->pdata->get_voltage()/1000);
+ else
+ val->intval = 0;
+ break;
+ case POWER_SUPPLY_PROP_CHARGE_FULL:
+ val->intval = GTA01_BAT_CHARGE_FULL;
+ break;
+
default:
return -EINVAL;
}
@@ -76,6 +136,7 @@ static int gta01_battery_probe(struct platform_device *pdev)
gta01_bat->psy.external_power_changed = gta01_bat_ext_changed;
gta01_bat->pdata = pdev->dev.platform_data;
+ platform_set_drvdata(pdev, gta01_bat);
power_supply_register(&pdev->dev, &gta01_bat->psy);
return 0;
diff --git a/drivers/power/pcf50633-charger.c b/drivers/power/pcf50633-charger.c
index 1bdb9906201..6fbe26eb756 100644
--- a/drivers/power/pcf50633-charger.c
+++ b/drivers/power/pcf50633-charger.c
@@ -29,16 +29,12 @@
struct pcf50633_mbc {
struct pcf50633 *pcf;
- int adapter_active;
int adapter_online;
- int usb_active;
int usb_online;
struct power_supply usb;
struct power_supply adapter;
struct power_supply ac;
-
- struct delayed_work charging_restart_work;
};
int pcf50633_mbc_usb_curlim_set(struct pcf50633 *pcf, int ma)
@@ -92,17 +88,19 @@ int pcf50633_mbc_usb_curlim_set(struct pcf50633 *pcf, int ma)
chgmod = (mbcs2 & PCF50633_MBCS2_MBC_MASK);
/* If chgmod == BATFULL, setting chgena has no effect.
- * We need to set resume instead.
+ * Datasheet says we need to set resume instead but when autoresume is
+ * used resume doesn't work. Clear and set chgena instead.
*/
if (chgmod != PCF50633_MBCS2_MBC_BAT_FULL)
pcf50633_reg_set_bit_mask(pcf, PCF50633_REG_MBCC1,
PCF50633_MBCC1_CHGENA, PCF50633_MBCC1_CHGENA);
- else
+ else {
+ pcf50633_reg_clear_bits(pcf, PCF50633_REG_MBCC1,
+ PCF50633_MBCC1_CHGENA);
pcf50633_reg_set_bit_mask(pcf, PCF50633_REG_MBCC1,
- PCF50633_MBCC1_RESUME, PCF50633_MBCC1_RESUME);
+ PCF50633_MBCC1_CHGENA, PCF50633_MBCC1_CHGENA);
+ }
- mbc->usb_active = charging_start;
-
power_supply_changed(&mbc->usb);
return ret;
@@ -113,23 +111,44 @@ int pcf50633_mbc_get_status(struct pcf50633 *pcf)
{
struct pcf50633_mbc *mbc = platform_get_drvdata(pcf->mbc_pdev);
int status = 0;
+ u8 chgmod;
if (!mbc)
return 0;
+ chgmod = pcf50633_reg_read(pcf, PCF50633_REG_MBCS2)
+ & PCF50633_MBCS2_MBC_MASK;
+
if (mbc->usb_online)
status |= PCF50633_MBC_USB_ONLINE;
- if (mbc->usb_active)
+ if (chgmod == PCF50633_MBCS2_MBC_USB_PRE ||
+ chgmod == PCF50633_MBCS2_MBC_USB_PRE_WAIT ||
+ chgmod == PCF50633_MBCS2_MBC_USB_FAST ||
+ chgmod == PCF50633_MBCS2_MBC_USB_FAST_WAIT)
status |= PCF50633_MBC_USB_ACTIVE;
if (mbc->adapter_online)
status |= PCF50633_MBC_ADAPTER_ONLINE;
- if (mbc->adapter_active)
+ if (chgmod == PCF50633_MBCS2_MBC_ADP_PRE ||
+ chgmod == PCF50633_MBCS2_MBC_ADP_PRE_WAIT ||
+ chgmod == PCF50633_MBCS2_MBC_ADP_FAST ||
+ chgmod == PCF50633_MBCS2_MBC_ADP_FAST_WAIT)
status |= PCF50633_MBC_ADAPTER_ACTIVE;
return status;
}
EXPORT_SYMBOL_GPL(pcf50633_mbc_get_status);
+int pcf50633_mbc_get_usb_online_status(struct pcf50633 *pcf)
+{
+ struct pcf50633_mbc *mbc = platform_get_drvdata(pcf->mbc_pdev);
+
+ if (!mbc)
+ return 0;
+
+ return mbc->usb_online;
+}
+EXPORT_SYMBOL_GPL(pcf50633_mbc_get_usb_online_status);
+
static ssize_t
show_chgmode(struct device *dev, struct device_attribute *attr, char *buf)
{
@@ -226,75 +245,24 @@ static struct attribute_group mbc_attr_group = {
.attrs = pcf50633_mbc_sysfs_entries,
};
-/* MBC state machine switches into charging mode when the battery voltage
- * falls below 96% of a battery float voltage. But the voltage drop in Li-ion
- * batteries is marginal(1~2 %) till about 80% of its capacity - which means,
- * after a BATFULL, charging won't be restarted until 80%.
- *
- * This work_struct function restarts charging every few seconds and makes
- * sure we don't discharge too much
- */
-
-static void pcf50633_mbc_charging_restart(struct work_struct *work)
-{
- struct pcf50633_mbc *mbc;
- u8 mbcs2, chgmod;
-
- mbc = container_of(work, struct pcf50633_mbc,
- charging_restart_work.work);
-
- mbcs2 = pcf50633_reg_read(mbc->pcf, PCF50633_REG_MBCS2);
- chgmod = (mbcs2 & PCF50633_MBCS2_MBC_MASK);
-
- if (chgmod != PCF50633_MBCS2_MBC_BAT_FULL)
- return;
-
- /* Restart charging */
- pcf50633_reg_set_bit_mask(mbc->pcf, PCF50633_REG_MBCC1,
- PCF50633_MBCC1_RESUME, PCF50633_MBCC1_RESUME);
- mbc->usb_active = 1;
- power_supply_changed(&mbc->usb);
-
- dev_info(mbc->pcf->dev, "Charging restarted\n");
-}
-
static void
pcf50633_mbc_irq_handler(int irq, void *data)
{
struct pcf50633_mbc *mbc = data;
- int chg_restart_interval =
- mbc->pcf->pdata->charging_restart_interval;
/* USB */
if (irq == PCF50633_IRQ_USBINS) {
mbc->usb_online = 1;
} else if (irq == PCF50633_IRQ_USBREM) {
mbc->usb_online = 0;
- mbc->usb_active = 0;
pcf50633_mbc_usb_curlim_set(mbc->pcf, 0);
- cancel_delayed_work_sync(&mbc->charging_restart_work);
}
/* Adapter */
- if (irq == PCF50633_IRQ_ADPINS) {
+ if (irq == PCF50633_IRQ_ADPINS)
mbc->adapter_online = 1;
- mbc->adapter_active = 1;
- } else if (irq == PCF50633_IRQ_ADPREM) {
+ else if (irq == PCF50633_IRQ_ADPREM)
mbc->adapter_online = 0;
- mbc->adapter_active = 0;
- }
-
- if (irq == PCF50633_IRQ_BATFULL) {
- mbc->usb_active = 0;
- mbc->adapter_active = 0;
-
- if (chg_restart_interval > 0)
- schedule_delayed_work(&mbc->charging_restart_work,
- chg_restart_interval);
- } else if (irq == PCF50633_IRQ_USBLIMON)
- mbc->usb_active = 0;
- else if (irq == PCF50633_IRQ_USBLIMOFF)
- mbc->usb_active = 1;
power_supply_changed(&mbc->usb);
power_supply_changed(&mbc->adapter);
@@ -428,9 +396,6 @@ static int __devinit pcf50633_mbc_probe(struct platform_device *pdev)
mbc->ac.supplied_to = mbc->pcf->pdata->batteries;
mbc->ac.num_supplicants = mbc->pcf->pdata->num_batteries;
- INIT_DELAYED_WORK(&mbc->charging_restart_work,
- pcf50633_mbc_charging_restart);
-
ret = power_supply_register(&pdev->dev, &mbc->adapter);
if (ret) {
dev_err(mbc->pcf->dev, "failed to register adapter\n");
@@ -480,8 +445,6 @@ static int __devexit pcf50633_mbc_remove(struct platform_device *pdev)
power_supply_unregister(&mbc->usb);
power_supply_unregister(&mbc->adapter);
- cancel_delayed_work_sync(&mbc->charging_restart_work);
-
kfree(mbc);
return 0;
diff --git a/drivers/rtc/rtc-pcf50606.c b/drivers/rtc/rtc-pcf50606.c
index 434cfc1dca4..6bd93b0b672 100644
--- a/drivers/rtc/rtc-pcf50606.c
+++ b/drivers/rtc/rtc-pcf50606.c
@@ -58,6 +58,7 @@ struct pcf50606_time {
struct pcf50606_rtc {
int alarm_enabled;
int second_enabled;
+ int alarm_pending;
struct pcf50606 *pcf;
struct rtc_device *rtc_dev;
@@ -198,6 +199,7 @@ static int pcf50606_rtc_read_alarm(struct device *dev, struct rtc_wkalrm *alrm)
rtc = dev_get_drvdata(dev);
alrm->enabled = rtc->alarm_enabled;
+ alrm->pending = rtc->alarm_pending;
ret = pcf50606_read_block(rtc->pcf, PCF50606_REG_RTCSCA,
PCF50606_TI_EXTENT, &pcf_tm.time[0]);
@@ -234,8 +236,12 @@ static int pcf50606_rtc_set_alarm(struct device *dev, struct rtc_wkalrm *alrm)
ret = pcf50606_write_block(rtc->pcf, PCF50606_REG_RTCSCA,
PCF50606_TI_EXTENT, &pcf_tm.time[0]);
- if (!alarm_masked)
+ if (!alrm->enabled)
+ rtc->alarm_pending = 0;
+
+ if (!alarm_masked || alrm->enabled)
pcf50606_irq_unmask(rtc->pcf, PCF50606_IRQ_ALARM);
+ rtc->alarm_enabled = alrm->enabled;
return ret;
}
@@ -255,6 +261,7 @@ static void pcf50606_rtc_irq(int irq, void *data)
switch (irq) {
case PCF50606_IRQ_ALARM:
rtc_update_irq(rtc->rtc_dev, 1, RTC_AF | RTC_IRQF);
+ rtc->alarm_pending = 1;
break;
case PCF50606_IRQ_SECOND:
rtc_update_irq(rtc->rtc_dev, 1, RTC_UF | RTC_IRQF);
diff --git a/drivers/usb/gadget/rndis.c b/drivers/usb/gadget/rndis.c
index 8c26f5ea2b8..c719b1efcbc 100644
--- a/drivers/usb/gadget/rndis.c
+++ b/drivers/usb/gadget/rndis.c
@@ -294,9 +294,22 @@ gen_ndis_query_resp (int configNr, u32 OID, u8 *buf, unsigned buf_len,
/* mandatory */
case OID_GEN_VENDOR_DESCRIPTION:
pr_debug("%s: OID_GEN_VENDOR_DESCRIPTION\n", __func__);
- length = strlen (rndis_per_dev_params [configNr].vendorDescr);
- memcpy (outbuf,
- rndis_per_dev_params [configNr].vendorDescr, length);
+
+ if (rndis_per_dev_params[configNr].vendorDescr) {
+ length = strlen(
+ rndis_per_dev_params[configNr].vendorDescr);
+ memcpy(outbuf,
+ rndis_per_dev_params[configNr].vendorDescr,
+ length);
+ } else {
+ /*
+ * FIXME: Openmoko hack by Paul Fertser to avoid
+ * panic with Win XP SP2 when vendorDescr is NULL
+ * (always ATM).
+ */
+ length = 5;
+ memcpy(outbuf, "dummy", length);
+ }
retval = 0;
break;
diff --git a/include/linux/mfd/pcf50633/adc.h b/include/linux/mfd/pcf50633/adc.h
index 56669b4183a..b35e62801ff 100644
--- a/include/linux/mfd/pcf50633/adc.h
+++ b/include/linux/mfd/pcf50633/adc.h
@@ -25,7 +25,8 @@
#define PCF50633_REG_ADCS3 0x57
#define PCF50633_ADCC1_ADCSTART 0x01
-#define PCF50633_ADCC1_RES_10BIT 0x02
+#define PCF50633_ADCC1_RES_8BIT 0x02
+#define PCF50633_ADCC1_RES_10BIT 0x00
#define PCF50633_ADCC1_AVERAGE_NO 0x00
#define PCF50633_ADCC1_AVERAGE_4 0x04
#define PCF50633_ADCC1_AVERAGE_8 0x08
diff --git a/include/linux/mfd/pcf50633/core.h b/include/linux/mfd/pcf50633/core.h
index af67b4e3ec6..c8125f2e99e 100644
--- a/include/linux/mfd/pcf50633/core.h
+++ b/include/linux/mfd/pcf50633/core.h
@@ -29,8 +29,6 @@ struct pcf50633_platform_data {
char **batteries;
int num_batteries;
- int charging_restart_interval;
-
int chg_ref_current_ma;
/* Callbacks */
@@ -138,6 +136,7 @@ struct pcf50633 {
int irq;
struct pcf50633_irq irq_handler[PCF50633_NUM_IRQ];
struct work_struct irq_work;
+ struct workqueue_struct *work_queue;
struct mutex lock;
u8 mask_regs[5];
diff --git a/include/linux/mfd/pcf50633/mbc.h b/include/linux/mfd/pcf50633/mbc.h
index 747725b0cd0..e6328a664b3 100644
--- a/include/linux/mfd/pcf50633/mbc.h
+++ b/include/linux/mfd/pcf50633/mbc.h
@@ -128,5 +128,6 @@ enum pcf50633_reg_mbcs3 {
int pcf50633_mbc_usb_curlim_set(struct pcf50633 *pcf, int ma);
int pcf50633_mbc_get_status(struct pcf50633 *);
+int pcf50633_mbc_get_usb_online_status(struct pcf50633 *);
#endif
diff --git a/include/linux/resume-dependency.h b/include/linux/resume-dependency.h
index 2b87af8cac7..f84bf618205 100644
--- a/include/linux/resume-dependency.h
+++ b/include/linux/resume-dependency.h
@@ -38,7 +38,7 @@ struct resume_dependency {
*/
#define init_resume_dependency_list(_head) \
- printk(KERN_INFO "##### init_resume_dependency_list(head=%p)\n", (_head)); \
+ printk(KERN_DEBUG "##### init_resume_dependency_list(head=%p)\n", (_head)); \
INIT_LIST_HEAD(&(_head)->list);
diff --git a/sound/soc/codecs/wm8753.c b/sound/soc/codecs/wm8753.c
index e8f0da02677..f753bc16da2 100644
--- a/sound/soc/codecs/wm8753.c
+++ b/sound/soc/codecs/wm8753.c
@@ -79,7 +79,7 @@ static const u16 wm8753_reg[] = {
0x0097, 0x0097, 0x0000, 0x0004,
0x0000, 0x0083, 0x0024, 0x01ba,
0x0000, 0x0083, 0x0024, 0x01ba,
- 0x0000, 0x0000
+ 0x0000, 0x0000, 0x0000
};
/* codec private data */
@@ -1665,11 +1665,11 @@ static int wm8753_register(struct wm8753_priv *wm8753)
codec->set_bias_level = wm8753_set_bias_level;
codec->dai = wm8753_dai;
codec->num_dai = 2;
- codec->reg_cache_size = ARRAY_SIZE(wm8753->reg_cache);
+ codec->reg_cache_size = ARRAY_SIZE(wm8753->reg_cache) + 1;
codec->reg_cache = &wm8753->reg_cache;
codec->private_data = wm8753;
- memcpy(codec->reg_cache, wm8753_reg, sizeof(codec->reg_cache));
+ memcpy(codec->reg_cache, wm8753_reg, sizeof(wm8753->reg_cache));
INIT_DELAYED_WORK(&codec->delayed_work, wm8753_work);
ret = wm8753_reset(codec);
diff --git a/sound/soc/s3c24xx/neo1973_wm8753.c b/sound/soc/s3c24xx/neo1973_wm8753.c
index 2970305990f..3f170cb53d3 100644
--- a/sound/soc/s3c24xx/neo1973_wm8753.c
+++ b/sound/soc/s3c24xx/neo1973_wm8753.c
@@ -353,9 +353,11 @@ static void lm4857_write_regs(void)
static int lm4857_get_reg(struct snd_kcontrol *kcontrol,
struct snd_ctl_elem_value *ucontrol)
{
- int reg = kcontrol->private_value & 0xFF;
- int shift = (kcontrol->private_value >> 8) & 0x0F;
- int mask = (kcontrol->private_value >> 16) & 0xFF;
+ struct soc_mixer_control *mc =
+ (struct soc_mixer_control *)kcontrol->private_value;
+ int reg = mc->reg;
+ int shift = mc->shift;
+ int mask = mc->max;
DBG("Entered %s\n", __func__);
@@ -366,9 +368,11 @@ static int lm4857_get_reg(struct snd_kcontrol *kcontrol,
static int lm4857_set_reg(struct snd_kcontrol *kcontrol,
struct snd_ctl_elem_value *ucontrol)
{
- int reg = kcontrol->private_value & 0xFF;
- int shift = (kcontrol->private_value >> 8) & 0x0F;
- int mask = (kcontrol->private_value >> 16) & 0xFF;
+ struct soc_mixer_control *mc =
+ (struct soc_mixer_control *)kcontrol->private_value;
+ int reg = mc->reg;
+ int shift = mc->shift;
+ int mask = mc->max;
if (((lm4857_regs[reg] >> shift) & mask) ==
ucontrol->value.integer.value[0])