diff options
Diffstat (limited to 'drivers/input/keyboard/sh_keysc.c')
| -rw-r--r-- | drivers/input/keyboard/sh_keysc.c | 82 | 
1 files changed, 29 insertions, 53 deletions
diff --git a/drivers/input/keyboard/sh_keysc.c b/drivers/input/keyboard/sh_keysc.c index d7dafd9425b..7abf03b4cc9 100644 --- a/drivers/input/keyboard/sh_keysc.c +++ b/drivers/input/keyboard/sh_keysc.c @@ -12,7 +12,6 @@  #include <linux/kernel.h>  #include <linux/module.h> -#include <linux/init.h>  #include <linux/interrupt.h>  #include <linux/irq.h>  #include <linux/delay.h> @@ -20,7 +19,7 @@  #include <linux/input.h>  #include <linux/input/sh_keysc.h>  #include <linux/bitmap.h> -#include <linux/clk.h> +#include <linux/pm_runtime.h>  #include <linux/io.h>  #include <linux/slab.h> @@ -32,12 +31,11 @@ static const struct {  	[SH_KEYSC_MODE_3] = { 2, 4, 7 },  	[SH_KEYSC_MODE_4] = { 3, 6, 6 },  	[SH_KEYSC_MODE_5] = { 4, 6, 7 }, -	[SH_KEYSC_MODE_6] = { 5, 7, 7 }, +	[SH_KEYSC_MODE_6] = { 5, 8, 8 },  };  struct sh_keysc_priv {  	void __iomem *iomem_base; -	struct clk *clk;  	DECLARE_BITMAP(last_keys, SH_KEYSC_MAXKEYS);  	struct input_dev *input;  	struct sh_keysc_info pdata; @@ -163,17 +161,16 @@ static irqreturn_t sh_keysc_isr(int irq, void *dev_id)  	return IRQ_HANDLED;  } -static int __devinit sh_keysc_probe(struct platform_device *pdev) +static int sh_keysc_probe(struct platform_device *pdev)  {  	struct sh_keysc_priv *priv;  	struct sh_keysc_info *pdata;  	struct resource *res;  	struct input_dev *input; -	char clk_name[8];  	int i;  	int irq, error; -	if (!pdev->dev.platform_data) { +	if (!dev_get_platdata(&pdev->dev)) {  		dev_err(&pdev->dev, "no platform data defined\n");  		error = -EINVAL;  		goto err0; @@ -200,7 +197,7 @@ static int __devinit sh_keysc_probe(struct platform_device *pdev)  	}  	platform_set_drvdata(pdev, priv); -	memcpy(&priv->pdata, pdev->dev.platform_data, sizeof(priv->pdata)); +	memcpy(&priv->pdata, dev_get_platdata(&pdev->dev), sizeof(priv->pdata));  	pdata = &priv->pdata;  	priv->iomem_base = ioremap_nocache(res->start, resource_size(res)); @@ -210,19 +207,11 @@ static int __devinit sh_keysc_probe(struct platform_device *pdev)  		goto err1;  	} -	snprintf(clk_name, sizeof(clk_name), "keysc%d", pdev->id); -	priv->clk = clk_get(&pdev->dev, clk_name); -	if (IS_ERR(priv->clk)) { -		dev_err(&pdev->dev, "cannot get clock \"%s\"\n", clk_name); -		error = PTR_ERR(priv->clk); -		goto err2; -	} -  	priv->input = input_allocate_device();  	if (!priv->input) {  		dev_err(&pdev->dev, "failed to allocate input device\n");  		error = -ENOMEM; -		goto err3; +		goto err2;  	}  	input = priv->input; @@ -241,10 +230,11 @@ static int __devinit sh_keysc_probe(struct platform_device *pdev)  	input->keycodesize = sizeof(pdata->keycodes[0]);  	input->keycodemax = ARRAY_SIZE(pdata->keycodes); -	error = request_irq(irq, sh_keysc_isr, 0, pdev->name, pdev); +	error = request_threaded_irq(irq, NULL, sh_keysc_isr, IRQF_ONESHOT, +				     dev_name(&pdev->dev), pdev);  	if (error) {  		dev_err(&pdev->dev, "failed to request IRQ\n"); -		goto err4; +		goto err3;  	}  	for (i = 0; i < SH_KEYSC_MAXKEYS; i++) @@ -254,10 +244,11 @@ static int __devinit sh_keysc_probe(struct platform_device *pdev)  	error = input_register_device(input);  	if (error) {  		dev_err(&pdev->dev, "failed to register input device\n"); -		goto err5; +		goto err4;  	} -	clk_enable(priv->clk); +	pm_runtime_enable(&pdev->dev); +	pm_runtime_get_sync(&pdev->dev);  	sh_keysc_write(priv, KYCR1, (sh_keysc_mode[pdata->mode].kymd << 8) |  		       pdata->scan_timing); @@ -267,22 +258,19 @@ static int __devinit sh_keysc_probe(struct platform_device *pdev)  	return 0; - err5: -	free_irq(irq, pdev);   err4: -	input_free_device(input); +	free_irq(irq, pdev);   err3: -	clk_put(priv->clk); +	input_free_device(input);   err2:  	iounmap(priv->iomem_base);   err1: -	platform_set_drvdata(pdev, NULL);  	kfree(priv);   err0:  	return error;  } -static int __devexit sh_keysc_remove(struct platform_device *pdev) +static int sh_keysc_remove(struct platform_device *pdev)  {  	struct sh_keysc_priv *priv = platform_get_drvdata(pdev); @@ -292,15 +280,15 @@ static int __devexit sh_keysc_remove(struct platform_device *pdev)  	free_irq(platform_get_irq(pdev, 0), pdev);  	iounmap(priv->iomem_base); -	clk_disable(priv->clk); -	clk_put(priv->clk); +	pm_runtime_put_sync(&pdev->dev); +	pm_runtime_disable(&pdev->dev); -	platform_set_drvdata(pdev, NULL);  	kfree(priv);  	return 0;  } +#ifdef CONFIG_PM_SLEEP  static int sh_keysc_suspend(struct device *dev)  {  	struct platform_device *pdev = to_platform_device(dev); @@ -311,14 +299,13 @@ static int sh_keysc_suspend(struct device *dev)  	value = sh_keysc_read(priv, KYCR1);  	if (device_may_wakeup(dev)) { -		value |= 0x80; +		sh_keysc_write(priv, KYCR1, value | 0x80);  		enable_irq_wake(irq);  	} else { -		value &= ~0x80; +		sh_keysc_write(priv, KYCR1, value & ~0x80); +		pm_runtime_put_sync(dev);  	} -	sh_keysc_write(priv, KYCR1, value); -  	return 0;  } @@ -329,36 +316,25 @@ static int sh_keysc_resume(struct device *dev)  	if (device_may_wakeup(dev))  		disable_irq_wake(irq); +	else +		pm_runtime_get_sync(dev);  	return 0;  } +#endif -static const struct dev_pm_ops sh_keysc_dev_pm_ops = { -	.suspend = sh_keysc_suspend, -	.resume = sh_keysc_resume, -}; +static SIMPLE_DEV_PM_OPS(sh_keysc_dev_pm_ops, +			 sh_keysc_suspend, sh_keysc_resume); -struct platform_driver sh_keysc_device_driver = { +static struct platform_driver sh_keysc_device_driver = {  	.probe		= sh_keysc_probe, -	.remove		= __devexit_p(sh_keysc_remove), +	.remove		= sh_keysc_remove,  	.driver		= {  		.name	= "sh_keysc",  		.pm	= &sh_keysc_dev_pm_ops,  	}  }; - -static int __init sh_keysc_init(void) -{ -	return platform_driver_register(&sh_keysc_device_driver); -} - -static void __exit sh_keysc_exit(void) -{ -	platform_driver_unregister(&sh_keysc_device_driver); -} - -module_init(sh_keysc_init); -module_exit(sh_keysc_exit); +module_platform_driver(sh_keysc_device_driver);  MODULE_AUTHOR("Magnus Damm");  MODULE_DESCRIPTION("SuperH KEYSC Keypad Driver");  | 
