From: "Dmitriy Vasil'ev" <tech@digiton.ru>
To: Daniel Mack <daniel@caiaq.de>
Cc: linux-input@vger.kernel.org
Subject: Re: rotary encoder
Date: Thu, 17 Jun 2010 15:55:05 +0400 [thread overview]
Message-ID: <1E284238E08046EFA4038129CEA2527F@tech> (raw)
In-Reply-To: 20100617113725.GD17833@buzzloop.caiaq.de
diff utility make this strange result.
I added only one structure, debouncing timer and handle EV_KEY type.
You can see difference with "total commander" and it command "Files->Compare
by content..."
Thank you,
Dmitriy
----- Original Message -----
From: "Daniel Mack" <daniel@caiaq.de>
To: "Dmitriy Vasil'ev" <tech@digiton.ru>
Cc: <linux-input@vger.kernel.org>
Sent: Thursday, June 17, 2010 3:37 PM
Subject: Re: rotary encoder
> Hi Dmitriy,
>
> Sorry, but your patch can't be reviewed that way. It removes the whole
> driver and adds a complete new version, which is not what a patch should
> normally do.
>
> Could you please check out the latest sources from git, copy your
> version of the driver to the tree and then run 'git diff'?
>
> This howto can give you a good start:
>
> http://linux.yyz.us/git-howto.html
>
>
> Also, please have a look at the file Documentation/CodingStyle,
> especially because your indentation and comments are not as they should
> be.
>
> I'd be happy to give feedback, but there are some rules to follow to
> make that process feasible.
>
> Thanks,
> Daniel
>
>
> On Thu, Jun 17, 2010 at 03:29:51PM +0400, Dmitriy Vasil'ev wrote:
>> diff -ur linux-2.6.34/Documentation/input/rotary-encoder.txt
>> linux/Documentation/input/rotary-encoder.txt
>> --- linux-2.6.34/Documentation/input/rotary-encoder.txt Mon May 17
>> 01:17:36 2010
>> +++ linux/Documentation/input/rotary-encoder.txt Thu Jun 17 13:24:14 2010
>> @@ -86,16 +86,26 @@
>>
>> #define GPIO_ROTARY_A 1
>> #define GPIO_ROTARY_B 2
>> +#define GPIO_ROTARY_S 3
>>
>> static struct rotary_encoder_platform_data my_rotary_encoder_info = {
>> - .steps = 24,
>> - .axis = ABS_X,
>> - .relative_axis = false,
>> - .rollover = false,
>> + .steps = 1,
>> + .type = EV_KEY, //(EV_KEY, EV_REL, EV_ABS)
>> .gpio_a = GPIO_ROTARY_A,
>> .gpio_b = GPIO_ROTARY_B,
>> .inverted_a = 0,
>> .inverted_b = 0,
>> + .codeleft = KEY_LEFT, //(REL_X, REL_Y, ABS_X, ABS_Y, KEY_...)
>> + .coderight = KEY_RIGHT, //(REL_X, REL_Y, ABS_X, ABS_Y, KEY_...)
>> + .rollover = 0,
>> + .button = {
>> + .code = KEY_ENTER,
>> + .gpio = GPIO_ROTARY_S,
>> + .active_low = 1,
>> + .type = EV_KEY,
>> + .debounce_interval = 10,
>> + .rep = false
>> + }
>> };
>>
>> static struct platform_device rotary_encoder_device = {
>> diff -ur linux-2.6.34/drivers/input/misc/rotary_encoder.c
>> linux/drivers/input/misc/rotary_encoder.c
>> --- linux-2.6.34/drivers/input/misc/rotary_encoder.c Mon May 17
>> 01:17:36 2010
>> +++ linux/drivers/input/misc/rotary_encoder.c Thu Jun 17 13:40:16 2010
>> @@ -1,257 +1,356 @@
>> -/*
>> - * rotary_encoder.c
>> - *
>> - * (c) 2009 Daniel Mack <daniel@caiaq.de>
>> - *
>> - * state machine code inspired by code from Tim Ruetz
>> - *
>> - * A generic driver for rotary encoders connected to GPIO lines.
>> - * See file:Documentation/input/rotary_encoder.txt for more information
>> - *
>> - * This program is free software; you can redistribute it and/or modify
>> - * it under the terms of the GNU General Public License version 2 as
>> - * published by the Free Software Foundation.
>> - */
>> -
>> -#include <linux/kernel.h>
>> -#include <linux/module.h>
>> -#include <linux/init.h>
>> -#include <linux/interrupt.h>
>> -#include <linux/input.h>
>> -#include <linux/device.h>
>> -#include <linux/platform_device.h>
>> -#include <linux/gpio.h>
>> -#include <linux/rotary_encoder.h>
>> -#include <linux/slab.h>
>> -
>> -#define DRV_NAME "rotary-encoder"
>> -
>> -struct rotary_encoder {
>> - struct input_dev *input;
>> - struct rotary_encoder_platform_data *pdata;
>> -
>> - unsigned int axis;
>> - unsigned int pos;
>> -
>> - unsigned int irq_a;
>> - unsigned int irq_b;
>> -
>> - bool armed;
>> - unsigned char dir; /* 0 - clockwise, 1 - CCW */
>> -};
>> -
>> -static irqreturn_t rotary_encoder_irq(int irq, void *dev_id)
>> -{
>> - struct rotary_encoder *encoder = dev_id;
>> - struct rotary_encoder_platform_data *pdata = encoder->pdata;
>> - int a = !!gpio_get_value(pdata->gpio_a);
>> - int b = !!gpio_get_value(pdata->gpio_b);
>> - int state;
>> -
>> - a ^= pdata->inverted_a;
>> - b ^= pdata->inverted_b;
>> - state = (a << 1) | b;
>> -
>> - switch (state) {
>> -
>> - case 0x0:
>> - if (!encoder->armed)
>> - break;
>> -
>> - if (pdata->relative_axis) {
>> - input_report_rel(encoder->input, pdata->axis,
>> - encoder->dir ? -1 : 1);
>> - } else {
>> - unsigned int pos = encoder->pos;
>> -
>> - if (encoder->dir) {
>> - /* turning counter-clockwise */
>> - if (pdata->rollover)
>> - pos += pdata->steps;
>> - if (pos)
>> - pos--;
>> - } else {
>> - /* turning clockwise */
>> - if (pdata->rollover || pos < pdata->steps)
>> - pos++;
>> - }
>> - if (pdata->rollover)
>> - pos %= pdata->steps;
>> - encoder->pos = pos;
>> - input_report_abs(encoder->input, pdata->axis,
>> - encoder->pos);
>> - }
>> - input_sync(encoder->input);
>> -
>> - encoder->armed = false;
>> - break;
>> -
>> - case 0x1:
>> - case 0x2:
>> - if (encoder->armed)
>> - encoder->dir = state - 1;
>> - break;
>> -
>> - case 0x3:
>> - encoder->armed = true;
>> - break;
>> - }
>> -
>> - return IRQ_HANDLED;
>> -}
>> -
>> -static int __devinit rotary_encoder_probe(struct platform_device *pdev)
>> -{
>> - struct rotary_encoder_platform_data *pdata = pdev->dev.platform_data;
>> - struct rotary_encoder *encoder;
>> - struct input_dev *input;
>> - int err;
>> -
>> - if (!pdata) {
>> - dev_err(&pdev->dev, "missing platform data\n");
>> - return -ENOENT;
>> - }
>> -
>> - encoder = kzalloc(sizeof(struct rotary_encoder), GFP_KERNEL);
>> - input = input_allocate_device();
>> - if (!encoder || !input) {
>> - dev_err(&pdev->dev, "failed to allocate memory for device\n");
>> - err = -ENOMEM;
>> - goto exit_free_mem;
>> - }
>> -
>> - encoder->input = input;
>> - encoder->pdata = pdata;
>> - encoder->irq_a = gpio_to_irq(pdata->gpio_a);
>> - encoder->irq_b = gpio_to_irq(pdata->gpio_b);
>> -
>> - /* create and register the input driver */
>> - input->name = pdev->name;
>> - input->id.bustype = BUS_HOST;
>> - input->dev.parent = &pdev->dev;
>> -
>> - if (pdata->relative_axis) {
>> - input->evbit[0] = BIT_MASK(EV_REL);
>> - input->relbit[0] = BIT_MASK(pdata->axis);
>> - } else {
>> - input->evbit[0] = BIT_MASK(EV_ABS);
>> - input_set_abs_params(encoder->input,
>> - pdata->axis, 0, pdata->steps, 0, 1);
>> - }
>> -
>> - err = input_register_device(input);
>> - if (err) {
>> - dev_err(&pdev->dev, "failed to register input device\n");
>> - goto exit_free_mem;
>> - }
>> -
>> - /* request the GPIOs */
>> - err = gpio_request(pdata->gpio_a, DRV_NAME);
>> - if (err) {
>> - dev_err(&pdev->dev, "unable to request GPIO %d\n",
>> - pdata->gpio_a);
>> - goto exit_unregister_input;
>> - }
>> -
>> - err = gpio_direction_input(pdata->gpio_a);
>> - if (err) {
>> - dev_err(&pdev->dev, "unable to set GPIO %d for input\n",
>> - pdata->gpio_a);
>> - goto exit_unregister_input;
>> - }
>> -
>> - err = gpio_request(pdata->gpio_b, DRV_NAME);
>> - if (err) {
>> - dev_err(&pdev->dev, "unable to request GPIO %d\n",
>> - pdata->gpio_b);
>> - goto exit_free_gpio_a;
>> - }
>> -
>> - err = gpio_direction_input(pdata->gpio_b);
>> - if (err) {
>> - dev_err(&pdev->dev, "unable to set GPIO %d for input\n",
>> - pdata->gpio_b);
>> - goto exit_free_gpio_a;
>> - }
>> -
>> - /* request the IRQs */
>> - err = request_irq(encoder->irq_a, &rotary_encoder_irq,
>> - IORESOURCE_IRQ_HIGHEDGE | IORESOURCE_IRQ_LOWEDGE,
>> - DRV_NAME, encoder);
>> - if (err) {
>> - dev_err(&pdev->dev, "unable to request IRQ %d\n",
>> - encoder->irq_a);
>> - goto exit_free_gpio_b;
>> - }
>> -
>> - err = request_irq(encoder->irq_b, &rotary_encoder_irq,
>> - IORESOURCE_IRQ_HIGHEDGE | IORESOURCE_IRQ_LOWEDGE,
>> - DRV_NAME, encoder);
>> - if (err) {
>> - dev_err(&pdev->dev, "unable to request IRQ %d\n",
>> - encoder->irq_b);
>> - goto exit_free_irq_a;
>> - }
>> -
>> - platform_set_drvdata(pdev, encoder);
>> -
>> - return 0;
>> -
>> -exit_free_irq_a:
>> - free_irq(encoder->irq_a, encoder);
>> -exit_free_gpio_b:
>> - gpio_free(pdata->gpio_b);
>> -exit_free_gpio_a:
>> - gpio_free(pdata->gpio_a);
>> -exit_unregister_input:
>> - input_unregister_device(input);
>> - input = NULL; /* so we don't try to free it */
>> -exit_free_mem:
>> - input_free_device(input);
>> - kfree(encoder);
>> - return err;
>> -}
>> -
>> -static int __devexit rotary_encoder_remove(struct platform_device *pdev)
>> -{
>> - struct rotary_encoder *encoder = platform_get_drvdata(pdev);
>> - struct rotary_encoder_platform_data *pdata = pdev->dev.platform_data;
>> -
>> - free_irq(encoder->irq_a, encoder);
>> - free_irq(encoder->irq_b, encoder);
>> - gpio_free(pdata->gpio_a);
>> - gpio_free(pdata->gpio_b);
>> - input_unregister_device(encoder->input);
>> - platform_set_drvdata(pdev, NULL);
>> - kfree(encoder);
>> -
>> - return 0;
>> -}
>> -
>> -static struct platform_driver rotary_encoder_driver = {
>> - .probe = rotary_encoder_probe,
>> - .remove = __devexit_p(rotary_encoder_remove),
>> - .driver = {
>> - .name = DRV_NAME,
>> - .owner = THIS_MODULE,
>> - }
>> -};
>> -
>> -static int __init rotary_encoder_init(void)
>> -{
>> - return platform_driver_register(&rotary_encoder_driver);
>> -}
>> -
>> -static void __exit rotary_encoder_exit(void)
>> -{
>> - platform_driver_unregister(&rotary_encoder_driver);
>> -}
>> -
>> -module_init(rotary_encoder_init);
>> -module_exit(rotary_encoder_exit);
>> -
>> -MODULE_ALIAS("platform:" DRV_NAME);
>> -MODULE_DESCRIPTION("GPIO rotary encoder driver");
>> -MODULE_AUTHOR("Daniel Mack <daniel@caiaq.de>");
>> -MODULE_LICENSE("GPL v2");
>> -
>> +/*
>> + * rotary_encoder.c
>> + *
>> + * (c) 2009 Daniel Mack <daniel@caiaq.de>
>> + *
>> + * state machine code inspired by code from Tim Ruetz
>> + *
>> + * A generic driver for rotary encoders connected to GPIO lines.
>> + * See file:Documentation/input/rotary_encoder.txt for more information
>> + *
>> + * This program is free software; you can redistribute it and/or modify
>> + * it under the terms of the GNU General Public License version 2 as
>> + * published by the Free Software Foundation.
>> + */
>> +
>> +#include <linux/kernel.h>
>> +#include <linux/module.h>
>> +#include <linux/init.h>
>> +#include <linux/interrupt.h>
>> +#include <linux/input.h>
>> +#include <linux/device.h>
>> +#include <linux/platform_device.h>
>> +#include <linux/gpio.h>
>> +#include <linux/rotary_encoder.h>
>> +#include <linux/slab.h>
>> +#include <linux/workqueue.h>
>> +#include <linux/sched.h>
>> +
>> +#define DRV_NAME "rotary-encoder"
>> +
>> +struct rotary_encoder_button_data {
>> + struct rotary_encoder_button button;
>> + unsigned int irq;
>> + struct timer_list timer;
>> + struct work_struct work;
>> +};
>> +
>> +struct rotary_encoder {
>> + struct input_dev *input;
>> + struct rotary_encoder_platform_data *pdata;
>> +
>> + unsigned int pos;
>> +
>> + unsigned int irq_a;
>> + unsigned int irq_b;
>> +
>> + bool armed;
>> + unsigned char dir; /* 0 - clockwise, 1 - CCW */
>> +
>> + struct rotary_encoder_button_data bdata;
>> +};
>> +
>> +static struct rotary_encoder* encoder;
>> +
>> +static irqreturn_t rotary_encoder_irq(int irq, void *dev_id)
>> +{
>> + struct rotary_encoder *encoder = dev_id;
>> + struct rotary_encoder_platform_data *pdata = encoder->pdata;
>> + int a = !!gpio_get_value(pdata->gpio_a);
>> + int b = !!gpio_get_value(pdata->gpio_b);
>> + int state;
>> +
>> + a ^= pdata->inverted_a;
>> + b ^= pdata->inverted_b;
>> + state = (a << 1) | b;
>> +
>> + switch (state) {
>> +
>> + case 0x0:
>> + if (!encoder->armed)
>> + break;
>> +
>> + if (pdata->type == EV_REL) {
>> + input_report_rel(encoder->input, pdata->codeleft,
>> + encoder->dir ? -1 : 1);
>> + } else
>> + if (pdata->type == EV_ABS) {
>> + unsigned int pos = encoder->pos;
>> +
>> + if (encoder->dir) {
>> + /* turning counter-clockwise */
>> + if (pdata->rollover)
>> + pos += pdata->steps;
>> + if (pos)
>> + pos--;
>> + } else {
>> + /* turning clockwise */
>> + if (pdata->rollover || pos < pdata->steps)
>> + pos++;
>> + }
>> + if (pdata->rollover)
>> + pos %= pdata->steps;
>> + encoder->pos = pos;
>> + input_report_abs(encoder->input, pdata->codeleft,
>> + encoder->pos);
>> + } else
>> + if (pdata->type == EV_KEY)
>> + {
>> + input_report_key(encoder->input, encoder->dir ? pdata->codeleft
>> : pdata->coderight, 1);
>> + input_sync(encoder->input);
>> + input_report_key(encoder->input, encoder->dir ? pdata->codeleft
>> : pdata->coderight, 0);
>> + input_sync(encoder->input);
>> + }
>> +
>> + encoder->armed = false;
>> + break;
>> +
>> + case 0x1:
>> + case 0x2:
>> + if (encoder->armed)
>> + encoder->dir = state - 1;
>> + break;
>> +
>> + case 0x3:
>> + encoder->armed = true;
>> + break;
>> + }
>> +
>> + return IRQ_HANDLED;
>> +}
>> +
>> +static void rotary_encoder_report_event(struct rotary_encoder *encoder)
>> +{
>> + struct rotary_encoder_button *button = &(encoder->bdata.button);
>> + struct input_dev *input = encoder->input;
>> + int state = (gpio_get_value(button->gpio) ? 1 : 0) ^
>> button->active_low;
>> +
>> + input_event(input, EV_KEY, button->code, !!state);
>> + input_sync(input);
>> +}
>> +
>> +static void rotary_encoder_work_func(struct work_struct *work)
>> +{
>> + struct rotary_encoder *encoder =
>> + container_of(work, struct rotary_encoder, bdata.work);
>> +
>> + rotary_encoder_report_event(encoder);
>> +}
>> +
>> +static void rotary_encoder_timer(unsigned long _data)
>> +{
>> + struct rotary_encoder *encoder = (struct rotary_encoder *)_data;
>> +
>> + schedule_work(&encoder->bdata.work);
>> +}
>> +
>> +static irqreturn_t rotary_encoder_key_irq(int irq, void *dev_id)
>> +{
>> + struct rotary_encoder *encoder = dev_id;
>> + struct rotary_encoder_button_data *bdata = &encoder->bdata;
>> + struct rotary_encoder_button *button = &bdata->button;
>> +
>> + if (button->debounce_interval)
>> + mod_timer(&bdata->timer,
>> + jiffies + msecs_to_jiffies(button->debounce_interval));
>> + else
>> + schedule_work(&bdata->work);
>> +
>> + return IRQ_HANDLED;
>> +}
>> +
>> +static int __devinit rotary_encoder_probe(struct platform_device *pdev)
>> +{
>> + struct rotary_encoder_platform_data *pdata = pdev->dev.platform_data;
>> + struct rotary_encoder *encoder;
>> + struct input_dev *input;
>> + int err;
>> +
>> + if (!pdata) {
>> + dev_err(&pdev->dev, "missing platform data\n");
>> + return -ENOENT;
>> + }
>> +
>> + encoder = kzalloc(sizeof(struct rotary_encoder), GFP_KERNEL);
>> + input = input_allocate_device();
>> + if (!encoder || !input) {
>> + dev_err(&pdev->dev, "failed to allocate memory for device\n");
>> + err = -ENOMEM;
>> + goto exit_free_mem;
>> + }
>> +
>> + encoder->input = input;
>> + encoder->pdata = pdata;
>> + encoder->irq_a = gpio_to_irq(pdata->gpio_a);
>> + encoder->irq_b = gpio_to_irq(pdata->gpio_b);
>> + encoder->bdata.irq = gpio_to_irq(pdata->button.gpio);
>> +
>> + /* create and register the input driver */
>> + input->name = pdev->name;
>> + input->id.bustype = BUS_HOST;
>> + input->dev.parent = &pdev->dev;
>> +
>> + /* Enable auto repeat feature of Linux input subsystem */
>> + if (pdata->button.rep)
>> + set_bit(EV_REP, input->evbit);
>> +
>> + encoder->bdata.button = pdata->button;
>> + //input_set_capability(input, EV_KEY, bdata->button.code);
>> +
>> + set_bit(pdata->type, input->evbit);
>> + set_bit(pdata->codeleft, input->keybit);
>> + set_bit(pdata->coderight, input->keybit);
>> + //
>> + set_bit(encoder->bdata.button.type, input->evbit);
>> + set_bit(encoder->bdata.button.code, input->keybit);
>> +
>> + setup_timer(&encoder->bdata.timer, rotary_encoder_timer, (unsigned
>> long)encoder);
>> + INIT_WORK(&encoder->bdata.work, rotary_encoder_work_func);
>> +
>> + err = input_register_device(input);
>> + if (err) {
>> + dev_err(&pdev->dev, "failed to register input device\n");
>> + goto exit_free_mem;
>> + }
>> +
>> + /* request the GPIOs */
>> + err = gpio_request(pdata->gpio_a, DRV_NAME);
>> + if (err) {
>> + dev_err(&pdev->dev, "unable to request GPIO %d\n",
>> + pdata->gpio_a);
>> + goto exit_unregister_input;
>> + }
>> +
>> + err = gpio_direction_input(pdata->gpio_a);
>> + if (err) {
>> + dev_err(&pdev->dev, "unable to set GPIO %d for input\n",
>> + pdata->gpio_a);
>> + goto exit_unregister_input;
>> + }
>> +
>> + err = gpio_request(pdata->gpio_b, DRV_NAME);
>> + if (err) {
>> + dev_err(&pdev->dev, "unable to request GPIO %d\n",
>> + pdata->gpio_b);
>> + goto exit_free_gpio_a;
>> + }
>> +
>> + err = gpio_direction_input(pdata->gpio_b);
>> + if (err) {
>> + dev_err(&pdev->dev, "unable to set GPIO %d for input\n",
>> + pdata->gpio_b);
>> + goto exit_free_gpio_a;
>> + }
>> +
>> + err = gpio_request(pdata->button.gpio, DRV_NAME);
>> + if (err) {
>> + dev_err(&pdev->dev, "unable to request GPIO %d\n",
>> + pdata->button.gpio);
>> + goto exit_free_gpio_b;
>> + }
>> +
>> + err = gpio_direction_input(pdata->button.gpio);
>> + if (err) {
>> + dev_err(&pdev->dev, "unable to set GPIO %d for input\n",
>> + pdata->button.gpio);
>> + goto exit_free_gpio_b;
>> + }
>> +
>> + /* request the IRQs */
>> + err = request_irq(encoder->irq_a, &rotary_encoder_irq,
>> + IORESOURCE_IRQ_HIGHEDGE | IORESOURCE_IRQ_LOWEDGE,
>> + DRV_NAME, encoder);
>> + if (err) {
>> + dev_err(&pdev->dev, "unable to request IRQ %d\n",
>> + encoder->irq_a);
>> + goto exit_free_gpio_s;
>> + }
>> +
>> + err = request_irq(encoder->irq_b, &rotary_encoder_irq,
>> + IORESOURCE_IRQ_HIGHEDGE | IORESOURCE_IRQ_LOWEDGE,
>> + DRV_NAME, encoder);
>> + if (err) {
>> + dev_err(&pdev->dev, "unable to request IRQ %d\n",
>> + encoder->irq_b);
>> + goto exit_free_irq_a;
>> + }
>> +
>> + err = request_irq(encoder->bdata.irq, &rotary_encoder_key_irq,
>> + IORESOURCE_IRQ_HIGHEDGE | IORESOURCE_IRQ_LOWEDGE,
>> + DRV_NAME, encoder);
>> + if (err) {
>> + dev_err(&pdev->dev, "unable to request IRQ %d\n",
>> + encoder->bdata.irq);
>> + goto exit_free_irq_b;
>> + }
>> +
>> + platform_set_drvdata(pdev, encoder);
>> +
>> + return 0;
>> +exit_free_irq_b:
>> + free_irq(encoder->irq_b, encoder);
>> +exit_free_irq_a:
>> + free_irq(encoder->irq_a, encoder);
>> +exit_free_gpio_s:
>> + gpio_free(pdata->button.gpio);
>> +exit_free_gpio_b:
>> + gpio_free(pdata->gpio_b);
>> +exit_free_gpio_a:
>> + gpio_free(pdata->gpio_a);
>> +exit_unregister_input:
>> + input_unregister_device(input);
>> + input = NULL; /* so we don't try to free it */
>> +exit_free_mem:
>> + input_free_device(input);
>> + kfree(encoder);
>> + return err;
>> +}
>> +
>> +static int __devexit rotary_encoder_remove(struct platform_device *pdev)
>> +{
>> + struct rotary_encoder *encoder = platform_get_drvdata(pdev);
>> + struct rotary_encoder_platform_data *pdata = pdev->dev.platform_data;
>> +
>> + free_irq(encoder->irq_a, encoder);
>> + free_irq(encoder->irq_b, encoder);
>> + free_irq(encoder->bdata.irq, encoder);
>> + if (pdata->button.debounce_interval)
>> + del_timer_sync(&encoder->bdata.timer);
>> + cancel_work_sync(&encoder->bdata.work);
>> + gpio_free(pdata->gpio_a);
>> + gpio_free(pdata->gpio_b);
>> + gpio_free(pdata->button.gpio);
>> + input_unregister_device(encoder->input);
>> + platform_set_drvdata(pdev, NULL);
>> + kfree(encoder);
>> +
>> + return 0;
>> +}
>> +
>> +static struct platform_driver rotary_encoder_driver = {
>> + .probe = rotary_encoder_probe,
>> + .remove = __devexit_p(rotary_encoder_remove),
>> + .driver = {
>> + .name = DRV_NAME,
>> + .owner = THIS_MODULE,
>> + }
>> +};
>> +
>> +static int __init rotary_encoder_init(void)
>> +{
>> + return platform_driver_register(&rotary_encoder_driver);
>> +}
>> +
>> +static void __exit rotary_encoder_exit(void)
>> +{
>> + platform_driver_unregister(&rotary_encoder_driver);
>> +}
>> +
>> +module_init(rotary_encoder_init);
>> +module_exit(rotary_encoder_exit);
>> +
>> +MODULE_ALIAS("platform:" DRV_NAME);
>> +MODULE_DESCRIPTION("GPIO rotary encoder driver");
>> +MODULE_AUTHOR("Daniel Mack <daniel@caiaq.de>");
>> +MODULE_LICENSE("GPL v2");
>> +
>> diff -ur linux-2.6.34/include/linux/rotary_encoder.h
>> linux/include/linux/rotary_encoder.h
>> --- linux-2.6.34/include/linux/rotary_encoder.h Mon May 17 01:17:36 2010
>> +++ linux/include/linux/rotary_encoder.h Thu Jun 17 14:23:26 2010
>> @@ -1,15 +1,28 @@
>> #ifndef __ROTARY_ENCODER_H__
>> #define __ROTARY_ENCODER_H__
>>
>> +struct rotary_encoder_button {
>> + /* Configuration parameters */
>> + u16 code; /* input event code (KEY_*, SW_*) */
>> + int gpio;
>> + int active_low;
>> + //char *desc;
>> + u16 type; /* input event type (EV_KEY, EV_SW) */
>> + int debounce_interval; /* debounce ticks interval in msecs */
>> + bool rep;/* enable input subsystem auto repeat */
>> +};
>> +
>> struct rotary_encoder_platform_data {
>> unsigned int steps;
>> - unsigned int axis;
>> + u16 type; /*(EV_KEY, EV_REL, EV_ABS)*/
>> unsigned int gpio_a;
>> unsigned int gpio_b;
>> unsigned int inverted_a;
>> unsigned int inverted_b;
>> - bool relative_axis;
>> + u16 codeleft; /*(REL_X, REL_Y, ABS_X, ABS_Y, KEY_...)*/
>> + u16 coderight; /*(REL_X, REL_Y, ABS_X, ABS_Y, KEY_...)*/
>> bool rollover;
>> + struct rotary_encoder_button button;
>> };
>>
>> #endif /* __ROTARY_ENCODER_H__ */
>>
>> ----- Original Message ----- From: "Daniel Mack" <daniel@caiaq.de>
>> To: "Dmitriy Vasil'ev" <tech@digiton.ru>
>> Cc: <linux-input@vger.kernel.org>
>> Sent: Thursday, June 17, 2010 3:21 PM
>> Subject: Re: rotary encoder
>>
>>
>> >On Thu, Jun 17, 2010 at 02:48:08PM +0400, Dmitriy Vasil'ev wrote:
>> >>I added .diff file.
>> >>I am sorry, but I can do it only for kernel version 2.6.34
>> >>See attach.
>> >
>> >Please, just put the patch inline, not as attachment and not zipped.
>> >That way, the patch can be commented line-by-line.
>> >
>> >Thanks,
>> >Daniel
>>
next prev parent reply other threads:[~2010-06-17 11:55 UTC|newest]
Thread overview: 17+ messages / expand[flat|nested] mbox.gz Atom feed top
[not found] <7A46ED6446BE4CF7AAC51205F1B5A88B@tech>
2010-06-02 13:20 ` rotary encoder Daniel Mack
[not found] ` <BA41AF5D757645AD94502E4B0A29158A@tech>
2010-06-02 13:52 ` Daniel Mack
[not found] ` <888FDE7800AB4E278ED6DF185FEDC869@tech>
2010-06-17 10:10 ` Daniel Mack
[not found] ` <B221BAA24375436992F7587DF15BB812@tech>
2010-06-17 11:21 ` Daniel Mack
2010-06-17 11:29 ` Dmitriy Vasil'ev
2010-06-17 11:37 ` Daniel Mack
2010-06-17 11:55 ` Dmitriy Vasil'ev [this message]
2010-06-17 12:00 ` Daniel Mack
2010-06-28 18:22 ` Dmitry Torokhov
2010-06-28 18:32 ` Daniel Mack
2010-06-29 15:06 ` Dmitriy Vasil'ev
2010-06-30 8:40 ` Dmitry Torokhov
2010-06-30 9:33 ` Dmitriy Vasil'ev
2010-06-30 19:54 ` Dmitry Torokhov
2013-05-21 8:38 rotary_encoder Christian Gmeiner
2013-05-21 19:13 ` rotary_encoder Dmitry Torokhov
[not found] <4BE96550.9020800@solutionsradio.com>
2010-05-11 14:17 ` Rotary encoder Daniel Mack
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=1E284238E08046EFA4038129CEA2527F@tech \
--to=tech@digiton.ru \
--cc=daniel@caiaq.de \
--cc=linux-input@vger.kernel.org \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).