1 /* drivers/input/misc/gpio_event.c
3 * Copyright (C) 2007 Google, Inc.
5 * This software is licensed under the terms of the GNU General Public
6 * License version 2, as published by the Free Software Foundation, and
7 * may be copied, distributed, and modified under those terms.
9 * This program is distributed in the hope that it will be useful,
10 * but WITHOUT ANY WARRANTY; without even the implied warranty of
11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12 * GNU General Public License for more details.
17 #include <linux/module.h>
18 #include <linux/input.h>
19 #include <linux/gpio_event.h>
20 #include <linux/hrtimer.h>
21 #include <linux/platform_device.h>
24 struct input_dev *input_dev;
25 const struct gpio_event_platform_data *info;
29 static int gpio_input_event(
30 struct input_dev *dev, unsigned int type, unsigned int code, int value)
35 struct gpio_event_info **ii;
36 struct gpio_event *ip = input_get_drvdata(dev);
38 for (i = 0, ii = ip->info->info; i < ip->info->info_count; i++, ii++) {
40 tmp_ret = (*ii)->event(ip->input_dev, *ii,
41 &ip->state[i], type, code, value);
49 static int gpio_event_call_all_func(struct gpio_event *ip, int func)
53 struct gpio_event_info **ii;
55 if (func == GPIO_EVENT_FUNC_INIT || func == GPIO_EVENT_FUNC_RESUME) {
57 for (i = 0; i < ip->info->info_count; i++, ii++) {
58 if ((*ii)->func == NULL) {
60 pr_err("gpio_event_probe: Incomplete pdata, "
64 ret = (*ii)->func(ip->input_dev, *ii, &ip->state[i],
67 pr_err("gpio_event_probe: function failed\n");
75 i = ip->info->info_count;
76 ii = ip->info->info + i;
80 (*ii)->func(ip->input_dev, *ii, &ip->state[i], func & ~1);
88 #ifdef CONFIG_HAS_EARLYSUSPEND
89 void gpio_event_suspend(struct early_suspend *h)
91 struct gpio_event *ip;
92 ip = container_of(h, struct gpio_event, early_suspend);
93 gpio_event_call_all_func(ip, GPIO_EVENT_FUNC_SUSPEND);
94 ip->info->power(ip->info, 0);
97 void gpio_event_resume(struct early_suspend *h)
99 struct gpio_event *ip;
100 ip = container_of(h, struct gpio_event, early_suspend);
101 ip->info->power(ip->info, 1);
102 gpio_event_call_all_func(ip, GPIO_EVENT_FUNC_RESUME);
106 static int __init gpio_event_probe(struct platform_device *pdev)
109 struct gpio_event *ip;
110 struct input_dev *input_dev;
111 struct gpio_event_platform_data *event_info;
113 event_info = pdev->dev.platform_data;
114 if (event_info == NULL) {
115 pr_err("gpio_event_probe: No pdata\n");
118 if (event_info->name == NULL ||
119 event_info->info == NULL ||
120 event_info->info_count == 0) {
121 pr_err("gpio_event_probe: Incomplete pdata\n");
124 ip = kzalloc(sizeof(*ip) +
125 sizeof(ip->state[0]) * event_info->info_count, GFP_KERNEL);
128 pr_err("gpio_event_probe: Failed to allocate private data\n");
129 goto err_kp_alloc_failed;
131 platform_set_drvdata(pdev, ip);
133 input_dev = input_allocate_device();
134 if (input_dev == NULL) {
136 pr_err("gpio_event_probe: Failed to allocate input device\n");
137 goto err_input_dev_alloc_failed;
139 input_set_drvdata(input_dev, ip);
140 ip->input_dev = input_dev;
141 ip->info = event_info;
142 if (event_info->power) {
143 #ifdef CONFIG_HAS_EARLYSUSPEND
144 ip->early_suspend.level = EARLY_SUSPEND_LEVEL_BLANK_SCREEN + 1;
145 ip->early_suspend.suspend = gpio_event_suspend;
146 ip->early_suspend.resume = gpio_event_resume;
147 register_early_suspend(&ip->early_suspend);
149 ip->info->power(ip->info, 1);
152 input_dev->name = ip->info->name;
153 input_dev->event = gpio_input_event;
155 err = gpio_event_call_all_func(ip, GPIO_EVENT_FUNC_INIT);
157 goto err_call_all_func_failed;
159 err = input_register_device(input_dev);
161 pr_err("gpio_event_probe: Unable to register %s input device\n",
163 goto err_input_register_device_failed;
168 err_input_register_device_failed:
169 gpio_event_call_all_func(ip, GPIO_EVENT_FUNC_UNINIT);
170 err_call_all_func_failed:
171 if (event_info->power) {
172 #ifdef CONFIG_HAS_EARLYSUSPEND
173 unregister_early_suspend(&ip->early_suspend);
175 ip->info->power(ip->info, 0);
177 input_free_device(input_dev);
178 err_input_dev_alloc_failed:
184 static int gpio_event_remove(struct platform_device *pdev)
186 struct gpio_event *ip = platform_get_drvdata(pdev);
188 gpio_event_call_all_func(ip, GPIO_EVENT_FUNC_UNINIT);
189 if (ip->info->power) {
190 #ifdef CONFIG_HAS_EARLYSUSPEND
191 unregister_early_suspend(&ip->early_suspend);
193 ip->info->power(ip->info, 0);
195 input_unregister_device(ip->input_dev);
200 static struct platform_driver gpio_event_driver = {
201 .probe = gpio_event_probe,
202 .remove = gpio_event_remove,
204 .name = GPIO_EVENT_DEV_NAME,
208 static int __devinit gpio_event_init(void)
210 return platform_driver_register(&gpio_event_driver);
213 static void __exit gpio_event_exit(void)
215 platform_driver_unregister(&gpio_event_driver);
218 module_init(gpio_event_init);
219 module_exit(gpio_event_exit);
221 MODULE_DESCRIPTION("GPIO Event Driver");
222 MODULE_LICENSE("GPL");