diff options
author | Mark Brown <broonie@opensource.wolfsonmicro.com> | 2008-04-17 09:24:58 -0400 |
---|---|---|
committer | Dmitry Torokhov <dmitry.torokhov@gmail.com> | 2008-04-17 09:24:58 -0400 |
commit | 34d278534db050b93d79175d59a32a70ac25f9b5 (patch) | |
tree | b3624684b7b8036979b9422ca98f39b75cabe23f /drivers/input | |
parent | db7c10e708b9bdd1618c034591d27c33cb341222 (diff) |
Input: wm97xx-core - support use as a wakeup source
The WM97xx touch screen controllers can be used to generate a wakeup
event when the system is suspended. Provide a new core API call
wm97xx_set_suspend_mode() allowing machine drivers to enable this. If no
suspend_mode is provided then the touch panel will be powered down when
the system is suspended.
Signed-off-by: Mark Brown <broonie@opensource.wolfsonmicro.com>
Signed-off-by: Dmitry Torokhov <dtor@mail.ru>
Diffstat (limited to 'drivers/input')
-rw-r--r-- | drivers/input/touchscreen/wm97xx-core.c | 39 |
1 files changed, 39 insertions, 0 deletions
diff --git a/drivers/input/touchscreen/wm97xx-core.c b/drivers/input/touchscreen/wm97xx-core.c index fec07c28281a..e9c7ea46b6e3 100644 --- a/drivers/input/touchscreen/wm97xx-core.c +++ b/drivers/input/touchscreen/wm97xx-core.c | |||
@@ -262,6 +262,23 @@ void wm97xx_config_gpio(struct wm97xx *wm, u32 gpio, enum wm97xx_gpio_dir dir, | |||
262 | EXPORT_SYMBOL_GPL(wm97xx_config_gpio); | 262 | EXPORT_SYMBOL_GPL(wm97xx_config_gpio); |
263 | 263 | ||
264 | /* | 264 | /* |
265 | * Configure the WM97XX_PRP value to use while system is suspended. | ||
266 | * If a value other than 0 is set then WM97xx pen detection will be | ||
267 | * left enabled in the configured mode while the system is in suspend, | ||
268 | * the device has users and suspend has not been disabled via the | ||
269 | * wakeup sysfs entries. | ||
270 | * | ||
271 | * @wm: WM97xx device to configure | ||
272 | * @mode: WM97XX_PRP value to configure while suspended | ||
273 | */ | ||
274 | void wm97xx_set_suspend_mode(struct wm97xx *wm, u16 mode) | ||
275 | { | ||
276 | wm->suspend_mode = mode; | ||
277 | device_init_wakeup(&wm->input_dev->dev, mode != 0); | ||
278 | } | ||
279 | EXPORT_SYMBOL_GPL(wm97xx_set_suspend_mode); | ||
280 | |||
281 | /* | ||
265 | * Handle a pen down interrupt. | 282 | * Handle a pen down interrupt. |
266 | */ | 283 | */ |
267 | static void wm97xx_pen_irq_worker(struct work_struct *work) | 284 | static void wm97xx_pen_irq_worker(struct work_struct *work) |
@@ -689,10 +706,32 @@ static int wm97xx_remove(struct device *dev) | |||
689 | static int wm97xx_suspend(struct device *dev, pm_message_t state) | 706 | static int wm97xx_suspend(struct device *dev, pm_message_t state) |
690 | { | 707 | { |
691 | struct wm97xx *wm = dev_get_drvdata(dev); | 708 | struct wm97xx *wm = dev_get_drvdata(dev); |
709 | u16 reg; | ||
710 | int suspend_mode; | ||
711 | |||
712 | if (device_may_wakeup(&wm->input_dev->dev)) | ||
713 | suspend_mode = wm->suspend_mode; | ||
714 | else | ||
715 | suspend_mode = 0; | ||
692 | 716 | ||
693 | if (wm->input_dev->users) | 717 | if (wm->input_dev->users) |
694 | cancel_delayed_work_sync(&wm->ts_reader); | 718 | cancel_delayed_work_sync(&wm->ts_reader); |
695 | 719 | ||
720 | /* Power down the digitiser (bypassing the cache for resume) */ | ||
721 | reg = wm97xx_reg_read(wm, AC97_WM97XX_DIGITISER2); | ||
722 | reg &= ~WM97XX_PRP_DET_DIG; | ||
723 | if (wm->input_dev->users) | ||
724 | reg |= suspend_mode; | ||
725 | wm->ac97->bus->ops->write(wm->ac97, AC97_WM97XX_DIGITISER2, reg); | ||
726 | |||
727 | /* WM9713 has an additional power bit - turn it off if there | ||
728 | * are no users or if suspend mode is zero. */ | ||
729 | if (wm->id == WM9713_ID2 && | ||
730 | (!wm->input_dev->users || !suspend_mode)) { | ||
731 | reg = wm97xx_reg_read(wm, AC97_EXTENDED_MID) | 0x8000; | ||
732 | wm97xx_reg_write(wm, AC97_EXTENDED_MID, reg); | ||
733 | } | ||
734 | |||
696 | return 0; | 735 | return 0; |
697 | } | 736 | } |
698 | 737 | ||