/**
 * wm831x-on.c - WM831X ON pin driver
 *
 * Copyright (C) 2009 Wolfson Microelectronics plc
 *
 * This file is subject to the terms and conditions of the GNU General
 * Public License. See the file "COPYING" in the main directory of this
 * archive for more details.
 *
 * This program is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 * GNU General Public License for more details.
 *
 * You should have received a copy of the GNU General Public License
 * along with this program; if not, write to the Free Software
 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
 */

#include <linux/module.h>
#include <linux/init.h>
#include <linux/kernel.h>
#include <linux/errno.h>
#include <linux/input.h>
#include <linux/interrupt.h>
#include <linux/platform_device.h>
#include <linux/workqueue.h>
#include <linux/mfd/wm831x/core.h>

struct wm831x_on {
	struct input_dev *dev;
	struct delayed_work work;
	struct wm831x *wm831x;
};

/*
 * The chip gives us an interrupt when the ON pin is asserted but we
 * then need to poll to see when the pin is deasserted.
 */
static void wm831x_poll_on(struct work_struct *work)
{
	struct wm831x_on *wm831x_on = container_of(work, struct wm831x_on,
						   work.work);
	struct wm831x *wm831x = wm831x_on->wm831x;
	int poll, ret;

	ret = wm831x_reg_read(wm831x, WM831X_ON_PIN_CONTROL);
	if (ret >= 0) {
		poll = !(ret & WM831X_ON_PIN_STS);

		input_report_key(wm831x_on->dev, KEY_POWER, poll);
		input_sync(wm831x_on->dev);
	} else {
		dev_err(wm831x->dev, "Failed to read ON status: %d\n", ret);
		poll = 1;
	}

	if (poll)
		schedule_delayed_work(&wm831x_on->work, 100);
}

static irqreturn_t wm831x_on_irq(int irq, void *data)
{
	struct wm831x_on *wm831x_on = data;

	schedule_delayed_work(&wm831x_on->work, 0);

	return IRQ_HANDLED;
}

static int __devinit wm831x_on_probe(struct platform_device *pdev)
{
	struct wm831x *wm831x = dev_get_drvdata(pdev->dev.parent);
	struct wm831x_on *wm831x_on;
	int irq = platform_get_irq(pdev, 0);
	int ret;

	wm831x_on = kzalloc(sizeof(struct wm831x_on), GFP_KERNEL);
	if (!wm831x_on) {
		dev_err(&pdev->dev, "Can't allocate data\n");
		return -ENOMEM;
	}

	wm831x_on->wm831x = wm831x;
	INIT_DELAYED_WORK(&wm831x_on->work, wm831x_poll_on);

	wm831x_on->dev = input_allocate_device();
	if (!wm831x_on->dev) {
		dev_err(&pdev->dev, "Can't allocate input dev\n");
		ret = -ENOMEM;
		goto err;
	}

	wm831x_on->dev->evbit[0] = BIT_MASK(EV_KEY);
	wm831x_on->dev->keybit[BIT_WORD(KEY_POWER)] = BIT_MASK(KEY_POWER);
	wm831x_on->dev->name = "wm831x_on";
	wm831x_on->dev->phys = "wm831x_on/input0";
	wm831x_on->dev->dev.parent = &pdev->dev;

	ret = wm831x_request_irq(wm831x, irq, wm831x_on_irq,
				 IRQF_TRIGGER_RISING, "wm831x_on", wm831x_on);
	if (ret < 0) {
		dev_err(&pdev->dev, "Unable to request IRQ: %d\n", ret);
		goto err_input_dev;
	}
	ret = input_register_device(wm831x_on->dev);
	if (ret) {
		dev_dbg(&pdev->dev, "Can't register input device: %d\n", ret);
		goto err_irq;
	}

	platform_set_drvdata(pdev, wm831x_on);

	return 0;

err_irq:
	wm831x_free_irq(wm831x, irq, NULL);
err_input_dev:
	input_free_device(wm831x_on->dev);
err:
	kfree(wm831x_on);
	return ret;
}

static int __devexit wm831x_on_remove(struct platform_device *pdev)
{
	struct wm831x_on *wm831x_on = platform_get_drvdata(pdev);
	int irq = platform_get_irq(pdev, 0);

	wm831x_free_irq(wm831x_on->wm831x, irq, wm831x_on);
	cancel_delayed_work_sync(&wm831x_on->work);
	input_unregister_device(wm831x_on->dev);
	kfree(wm831x_on);

	return 0;
}

static struct platform_driver wm831x_on_driver = {
	.probe		= wm831x_on_probe,
	.remove		= __devexit_p(wm831x_on_remove),
	.driver		= {
		.name	= "wm831x-on",
		.owner	= THIS_MODULE,
	},
};

static int __init wm831x_on_init(void)
{
	return platform_driver_register(&wm831x_on_driver);
}
module_init(wm831x_on_init);

static void __exit wm831x_on_exit(void)
{
	platform_driver_unregister(&wm831x_on_driver);
}
module_exit(wm831x_on_exit);

MODULE_ALIAS("platform:wm831x-on");
MODULE_DESCRIPTION("WM831x ON pin");
MODULE_LICENSE("GPL");
MODULE_AUTHOR("Mark Brown <broonie@opensource.wolfsonmicro.com>");

