Re: [PATCH 1/2] input: Pegatron Lucid accelerometer

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

 



On Fri, Jan 14, 2011 at 9:14 PM, Andy Ross <andy@xxxxxxxxxxxxx> wrote:
> From: Andy Ross <andy.ross@xxxxxxxxxxxxx>
>
> Add driver for the ACPI accelerometer interface on the Pegatron Lucid
> tablet.
>
> Signed-off-by: Andy Ross <andy.ross@xxxxxxxxxxxxx>
> ---
> Âdrivers/input/misc/Kconfig   Â|  11 +++
> Âdrivers/input/misc/Makefile   |  Â2 +-
> Âdrivers/input/misc/pega-accel.c | Â133 +++++++++++++++++++++++++++++++++++++++
> Â3 files changed, 145 insertions(+), 1 deletions(-)
> Âcreate mode 100644 drivers/input/misc/pega-accel.c
>
> diff --git a/drivers/input/misc/Kconfig b/drivers/input/misc/Kconfig
> index b99b8cb..268c11d 100644
> --- a/drivers/input/misc/Kconfig
> +++ b/drivers/input/misc/Kconfig
> @@ -448,4 +448,15 @@ config INPUT_ADXL34X_SPI
> Â Â Â Â ÂTo compile this driver as a module, choose M here: the
> Â Â Â Â Âmodule will be called adxl34x-spi.
>
> +config INPUT_PEGA_ACCEL
> + Â Â Â tristate "Support Pegatron Lucid accelerometer"
> + Â Â Â depends on ASUS_LAPTOP
> + Â Â Â default y
> + Â Â Â help
> + Â Â Â Â Say Y here if you want support for the built-in ACPI
> + Â Â Â Â accelerometer device on Pegatron Lucid tablet devices.
> +
> + Â Â Â ÂTo compile this driver as a module, choose M here: the module
> + Â Â Â Âwill be called pega_accel.
> +
> Âendif
> diff --git a/drivers/input/misc/Makefile b/drivers/input/misc/Makefile
> index 1fe1f6c..2475305 100644
> --- a/drivers/input/misc/Makefile
> +++ b/drivers/input/misc/Makefile
> @@ -42,4 +42,4 @@ obj-$(CONFIG_INPUT_WINBOND_CIR) Â Â Â Â Â Â Â += winbond-cir.o
> Âobj-$(CONFIG_INPUT_WISTRON_BTNS) Â Â Â += wistron_btns.o
> Âobj-$(CONFIG_INPUT_WM831X_ON) Â Â Â Â Â+= wm831x-on.o
> Âobj-$(CONFIG_INPUT_YEALINK) Â Â Â Â Â Â+= yealink.o
> -
> +obj-$(CONFIG_INPUT_PEGA_ACCEL) Â Â Â Â += pega-accel.o
> diff --git a/drivers/input/misc/pega-accel.c b/drivers/input/misc/pega-accel.c
> new file mode 100644
> index 0000000..9b7ef05
> --- /dev/null
> +++ b/drivers/input/misc/pega-accel.c
> @@ -0,0 +1,133 @@
> +/*
> + * pega_accel.c - driver for accelerometer in Pegatron Lucid tablets
> + *
> + * Copyright (c) 2011 Wind River Systems
> + *
> + * Author: Andy Ross <andy.ross@xxxxxxxxxxxxx>
> + *
> + * This program is free software; you can redistribute it and/or modify
> + * it under the terms of the GNU General Public License as published by
> + * the Free Software Foundation; either version 2 of the License, or
> + * (at your option) any later version.
> + *
> + * 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/input-polldev.h>
> +#include <linux/module.h>
> +#include <linux/platform_device.h>
> +#include <acpi/acpi_bus.h>
> +
> +#define DRIVER_NAME "pega_accel"
> +#define DRIVER_DESC "Pegatron Lucid Tablet Accelerometer"
> +
> +/* 1G accel is reported as ~256, so clamp to 2G */
> +#define CLAMP 512
> +
> +static struct input_polled_dev *ipdev;
> +
> +/* FIXME: this mechanism is *very* slow: ~50ms to read the three
> + * values. ÂPre-caching an acpi handle with acpi_get_handle has no
> + * effect, so the issue isn't in the parsing or tree walking... */
> +static int acpi_s16(char *method)
> +{
> + Â Â Â unsigned long long val = 0;
> + Â Â Â acpi_evaluate_integer(NULL, method, NULL, &val);
> + Â Â Â return (short)val;
> +}
> +
> +static void pega_accel_poll(struct input_polled_dev *ipdev)
> +{
> + Â Â Â /* Note transform, convert to "right/up/out" in the native
> + Â Â Â Â* landscape orientation (i.e. the vector is the direction of
> + Â Â Â Â* "real up" in the device's cartiesian coordinates). ÂFIXME:
> + Â Â Â Â* is there a relevant convention to adhere to? */
> + Â Â Â int x = -acpi_s16("\\_SB.ATKD.XLRX");
> + Â Â Â int y = -acpi_s16("\\_SB.ATKD.XLRY");
> + Â Â Â int z = Âacpi_s16("\\_SB.ATKD.XLRZ");

Using the absolute path (\\_SB.ATKD) may not work on new hardware, you
should find the path of the device using the HID (AKT0100, or
something like that). But we may not core in this case since it's pega
specific.

> + Â Â Â x = clamp_val(x, -CLAMP, CLAMP);
> + Â Â Â y = clamp_val(y, -CLAMP, CLAMP);
> + Â Â Â z = clamp_val(z, -CLAMP, CLAMP);
> +
> + Â Â Â input_report_abs(ipdev->input, ABS_X, x);
y> + Â Â Â input_report_abs(ipdev->input, ABS_Y, y);
> + Â Â Â input_report_abs(ipdev->input, ABS_Z, z);
> + Â Â Â input_sync(ipdev->input);
> +}
> +
> +static void dev_noop_release(struct device *d) {}
> +
> +static int __devinit platform_probe(struct platform_device *pd)
> +{
> + Â Â Â int err = 0;

You should check if the device exists here, before trying to do
anything, (using the path or the HID, depending of what you'll do
about my previous comment)

> + Â Â Â ipdev = input_allocate_polled_device();
> + Â Â Â if (!ipdev)
> + Â Â Â Â Â Â Â return -ENOMEM;
> +
> + Â Â Â ipdev->poll = pega_accel_poll;
> + Â Â Â ipdev->poll_interval = 100;
> + Â Â Â ipdev->poll_interval_min = 10;
> + Â Â Â ipdev->poll_interval_max = 2000;
> +
> + Â Â Â ipdev->input->dev.parent = &pd->dev;
> + Â Â Â ipdev->input->dev.release = dev_noop_release;
> + Â Â Â ipdev->input->id.bustype = BUS_HOST;
> +
> + Â Â Â ipdev->input->name = DRIVER_DESC;
> + Â Â Â ipdev->input->phys = DRIVER_NAME "/input0";
> +
> + Â Â Â set_bit(EV_ABS, ipdev->input->evbit);
> + Â Â Â input_set_abs_params(ipdev->input, ABS_X, -CLAMP, CLAMP, 0, 0);
> + Â Â Â input_set_abs_params(ipdev->input, ABS_Y, -CLAMP, CLAMP, 0, 0);
> + Â Â Â input_set_abs_params(ipdev->input, ABS_Z, -CLAMP, CLAMP, 0, 0);
> +
> + Â Â Â err = input_register_polled_device(ipdev);
> + Â Â Â if (err)
> + Â Â Â Â Â Â Â input_free_polled_device(ipdev);
> +
> + Â Â Â return err;
> +}
> +
> +static int __devexit platform_remove(struct platform_device *pd)
> +{
> + Â Â Â input_unregister_polled_device(ipdev);
> + Â Â Â input_free_polled_device(ipdev);
> + Â Â Â ipdev = NULL;
> + Â Â Â return 0;
> +}
> +
> +static struct platform_driver platform_driver = {
> + Â Â Â .driver = {
> + Â Â Â Â Â Â Â .owner = THIS_MODULE,
> + Â Â Â Â Â Â Â .name Â= DRIVER_NAME,
> + Â Â Â },
> + Â Â Â .probe Â= platform_probe,
> + Â Â Â .remove = __devexit_p(platform_remove),
> +};
> +
> +static int __init mod_init(void)
> +{
> + Â Â Â return platform_driver_register(&platform_driver);
> +}
> +
> +static void __exit mod_exit(void)
> +{
> + Â Â Â platform_driver_unregister(&platform_driver);
> +}
> +
> +module_init(mod_init);
> +module_exit(mod_exit);
> +
> +MODULE_AUTHOR("Andy Ross <andy.ross@xxxxxxxxxxxxx>");
> +MODULE_LICENSE("GPL");
> +MODULE_DESCRIPTION(DRIVER_DESC);
> +MODULE_ALIAS("dmi:*:bvrLucid-CE-133:*");
> --
> 1.7.1
>
> --
> To unsubscribe from this list: send the line "unsubscribe linux-input" in
> the body of a message to majordomo@xxxxxxxxxxxxxxx
> More majordomo info at Âhttp://vger.kernel.org/majordomo-info.html
>



-- 
Corentin Chary
http://xf.iksaif.net
--
To unsubscribe from this list: send the line "unsubscribe linux-input" in
the body of a message to majordomo@xxxxxxxxxxxxxxx
More majordomo info at  http://vger.kernel.org/majordomo-info.html


[Index of Archives]     [Linux Media Devel]     [Linux USB Devel]     [Video for Linux]     [Linux Audio Users]     [Yosemite News]     [Linux Kernel]     [Linux SCSI]     [Linux Wireless Networking]     [Linux Omap]

  Powered by Linux