2 * arch/ubicom32/mach-common/ubicom32input.c
3 * Ubicom32 Input driver
7 * (C) Copyright 2009, Ubicom, Inc.
9 * This file is part of the Ubicom32 Linux Kernel Port.
11 * The Ubicom32 Linux Kernel Port is free software: you can redistribute
12 * it and/or modify it under the terms of the GNU General Public License
13 * as published by the Free Software Foundation, either version 2 of the
14 * License, or (at your option) any later version.
16 * The Ubicom32 Linux Kernel Port is distributed in the hope that it
17 * will be useful, but WITHOUT ANY WARRANTY; without even the implied
18 * warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See
19 * the GNU General Public License for more details.
21 * You should have received a copy of the GNU General Public License
22 * along with the Ubicom32 Linux Kernel Port. If not,
23 * see <http://www.gnu.org/licenses/>.
25 * Ubicom32 implementation derived from (with many thanks):
31 * TODO: add groups for inputs which can be sampled together (i.e. I2C)
34 #include <linux/kernel.h>
35 #include <linux/module.h>
36 #include <linux/platform_device.h>
37 #include <linux/input.h>
38 #include <linux/input-polldev.h>
39 #include <linux/delay.h>
40 #include <linux/gpio.h>
42 #include <asm/ubicom32input.h>
44 struct ubicom32input_data
{
45 struct ubicom32input_platform_data
*pdata
;
47 struct input_polled_dev
*poll_dev
;
50 * collection of previous states for buttons
58 static void ubicom32input_poll(struct input_polled_dev
*dev
)
60 struct ubicom32input_data
*ud
=
61 (struct ubicom32input_data
*)dev
->private;
62 struct ubicom32input_platform_data
*pdata
= ud
->pdata
;
63 struct input_dev
*id
= dev
->input
;
67 for (i
= 0; i
< pdata
->nbuttons
; i
++) {
68 const struct ubicom32input_button
*ub
= &pdata
->buttons
[i
];
71 int val
= gpio_get_value(ub
->gpio
);
74 * Check to see if the state changed from the last time we
77 if (val
== ud
->prev_state
[i
]) {
82 * The state has changed, determine if we are "up" or "down"
84 ud
->prev_state
[i
] = val
;
86 if ((!val
&& ub
->active_low
) || (val
&& !ub
->active_low
)) {
90 input_event(id
, ub
->type
, ub
->code
, state
);
100 * ubicom32input_probe
102 static int __devinit
ubicom32input_probe(struct platform_device
*pdev
)
105 struct ubicom32input_data
*ud
;
106 struct input_polled_dev
*poll_dev
;
107 struct input_dev
*input_dev
;
108 struct ubicom32input_platform_data
*pdata
;
111 pdata
= pdev
->dev
.platform_data
;
116 ud
= kzalloc(sizeof(struct ubicom32input_data
) +
117 pdata
->nbuttons
, GFP_KERNEL
);
123 poll_dev
= input_allocate_polled_device();
129 platform_set_drvdata(pdev
, ud
);
131 ud
->poll_dev
= poll_dev
;
132 poll_dev
->private = ud
;
133 poll_dev
->poll
= ubicom32input_poll
;
136 * Set the poll interval requested, default to 50 msec
138 if (pdata
->poll_interval
) {
139 poll_dev
->poll_interval
= pdata
->poll_interval
;
141 poll_dev
->poll_interval
= 50;
145 * Setup the input device
147 input_dev
= poll_dev
->input
;
148 input_dev
->name
= pdata
->name
? pdata
->name
: "Ubicom32 Input";
149 input_dev
->phys
= "ubicom32input/input0";
150 input_dev
->dev
.parent
= &pdev
->dev
;
151 input_dev
->id
.bustype
= BUS_HOST
;
156 for (i
= 0; i
< pdata
->nbuttons
; i
++) {
157 const struct ubicom32input_button
*ub
= &pdata
->buttons
[i
];
159 ret
= gpio_request(ub
->gpio
,
160 ub
->desc
? ub
->desc
: "ubicom32input");
162 pr_err("ubicom32input: failed to request "
163 "GPIO %d ret=%d\n", ub
->gpio
, ret
);
167 ret
= gpio_direction_input(ub
->gpio
);
169 pr_err("ubicom32input: failed to set "
170 "GPIO %d to input ret=%d\n", ub
->gpio
, ret
);
175 * Set the previous state to the non-active stae
177 ud
->prev_state
[i
] = ub
->active_low
;
179 input_set_capability(input_dev
,
180 ub
->type
? ub
->type
: EV_KEY
, ub
->code
);
186 ret
= input_register_polled_device(ud
->poll_dev
);
195 * release the GPIOs we have already requested.
198 gpio_free(pdata
->buttons
[i
].gpio
);
202 printk(KERN_ERR
"Ubicom32Input: Failed to register driver %d", ret
);
203 platform_set_drvdata(pdev
, NULL
);
204 input_free_polled_device(poll_dev
);
210 * ubicom32input_remove
212 static int __devexit
ubicom32input_remove(struct platform_device
*dev
)
214 struct ubicom32input_data
*ud
=
215 (struct ubicom32input_data
*)platform_get_drvdata(dev
);
221 for (i
= 0; i
< ud
->pdata
->nbuttons
; i
++) {
222 gpio_free(ud
->pdata
->buttons
[i
].gpio
);
225 platform_set_drvdata(dev
, NULL
);
226 input_unregister_polled_device(ud
->poll_dev
);
227 input_free_polled_device(ud
->poll_dev
);
234 static struct platform_driver ubicom32input_driver
= {
236 .name
= "ubicom32input",
237 .owner
= THIS_MODULE
,
239 .probe
= ubicom32input_probe
,
240 .remove
= __devexit_p(ubicom32input_remove
),
246 static int __devinit
ubicom32input_init(void)
248 return platform_driver_register(&ubicom32input_driver
);
254 static void __exit
ubicom32input_exit(void)
256 platform_driver_unregister(&ubicom32input_driver
);
259 module_init(ubicom32input_init
);
260 module_exit(ubicom32input_exit
);
262 MODULE_AUTHOR("Pat Tjin <pattjin@ubicom.com>");
263 MODULE_DESCRIPTION("Ubicom32 Input Driver");
264 MODULE_LICENSE("GPL");
265 MODULE_ALIAS("platform:ubicom32-input");