From: Jonathan Cameron <jic23@kernel.org>
To: Lars-Peter Clausen <lars@metafoo.de>
Cc: Jonathan Cameron <jic23@cam.ac.uk>,
Michael Hennerich <michael.hennerich@analog.com>,
linux-iio@vger.kernel.org,
device-drivers-devel@blackfin.uclinux.org, drivers@analog.com
Subject: Re: [PATCH v2 3/6] staging:iio:events: Use kfifo for event queue
Date: Mon, 19 Dec 2011 20:56:51 +0000 [thread overview]
Message-ID: <4EEFA513.5000707@kernel.org> (raw)
In-Reply-To: <1324290580-17511-3-git-send-email-lars@metafoo.de>
On 12/19/2011 10:29 AM, Lars-Peter Clausen wrote:
> The current IIO event code uses a list to emulate FIFO like behaviour.
> Just use a kfifo directly instead to implement the event queue. As part of this
> patch the maximum of events in the queue is increased from 10 to 16 since kfifo
> requires a power of two for the number of fifo elements.
>
> Signed-off-by: Lars-Peter Clausen <lars@metafoo.de>
Acked-by: Jonathan Cameron <jic23@kernel.org>
> ---
> drivers/staging/iio/industrialio-event.c | 88 +++++++-----------------------
> 1 files changed, 21 insertions(+), 67 deletions(-)
>
> diff --git a/drivers/staging/iio/industrialio-event.c b/drivers/staging/iio/industrialio-event.c
> index a7b345d..d63aa0b 100644
> --- a/drivers/staging/iio/industrialio-event.c
> +++ b/drivers/staging/iio/industrialio-event.c
> @@ -13,6 +13,7 @@
> #include <linux/device.h>
> #include <linux/fs.h>
> #include <linux/kernel.h>
> +#include <linux/kfifo.h>
> #include <linux/module.h>
> #include <linux/sched.h>
> #include <linux/slab.h>
> @@ -24,22 +25,10 @@
> #include "events.h"
>
> /**
> - * struct iio_detected_event_list - list element for events that have occurred
> - * @list: linked list header
> - * @ev: the event itself
> - */
> -struct iio_detected_event_list {
> - struct list_head list;
> - struct iio_event_data ev;
> -};
> -
> -/**
> * struct iio_event_interface - chrdev interface for an event line
> * @wait: wait queue to allow blocking reads of events
> * @event_list_lock: mutex to protect the list of detected events
> * @det_events: list of detected events
> - * @max_events: maximum number of events before new ones are dropped
> - * @current_events: number of events in detected list
> * @dev_attr_list: list of event interface sysfs attribute
> * @flags: file operations related flags including busy flag.
> * @group: event interface sysfs attribute group
> @@ -47,9 +36,8 @@ struct iio_detected_event_list {
> struct iio_event_interface {
> wait_queue_head_t wait;
> struct mutex event_list_lock;
> - struct list_head det_events;
> - int max_events;
> - int current_events;
> + DECLARE_KFIFO(det_events, struct iio_event_data, 16);
> +
> struct list_head dev_attr_list;
> unsigned long flags;
> struct attribute_group group;
> @@ -58,34 +46,25 @@ struct iio_event_interface {
> int iio_push_event(struct iio_dev *indio_dev, u64 ev_code, s64 timestamp)
> {
> struct iio_event_interface *ev_int = indio_dev->event_interface;
> - struct iio_detected_event_list *ev;
> - int ret = 0;
> + struct iio_event_data ev;
> + int copied;
>
> /* Does anyone care? */
> mutex_lock(&ev_int->event_list_lock);
> if (test_bit(IIO_BUSY_BIT_POS, &ev_int->flags)) {
> - if (ev_int->current_events == ev_int->max_events) {
> - mutex_unlock(&ev_int->event_list_lock);
> - return 0;
> - }
> - ev = kmalloc(sizeof(*ev), GFP_KERNEL);
> - if (ev == NULL) {
> - ret = -ENOMEM;
> - mutex_unlock(&ev_int->event_list_lock);
> - goto error_ret;
> - }
> - ev->ev.id = ev_code;
> - ev->ev.timestamp = timestamp;
>
> - list_add_tail(&ev->list, &ev_int->det_events);
> - ev_int->current_events++;
> + ev.id = ev_code;
> + ev.timestamp = timestamp;
> +
> + copied = kfifo_put(&ev_int->det_events, &ev);
> +
> mutex_unlock(&ev_int->event_list_lock);
> - wake_up_interruptible(&ev_int->wait);
> + if (copied != 0)
> + wake_up_interruptible(&ev_int->wait);
> } else
> mutex_unlock(&ev_int->event_list_lock);
>
> -error_ret:
> - return ret;
> + return 0;
> }
> EXPORT_SYMBOL(iio_push_event);
>
> @@ -95,15 +74,14 @@ static ssize_t iio_event_chrdev_read(struct file *filep,
> loff_t *f_ps)
> {
> struct iio_event_interface *ev_int = filep->private_data;
> - struct iio_detected_event_list *el;
> - size_t len = sizeof(el->ev);
> + unsigned int copied;
> int ret;
>
> - if (count < len)
> + if (count < sizeof(struct iio_event_data))
> return -EINVAL;
>
> mutex_lock(&ev_int->event_list_lock);
> - if (list_empty(&ev_int->det_events)) {
> + if (kfifo_is_empty(&ev_int->det_events)) {
> if (filep->f_flags & O_NONBLOCK) {
> ret = -EAGAIN;
> goto error_mutex_unlock;
> @@ -111,39 +89,25 @@ static ssize_t iio_event_chrdev_read(struct file *filep,
> mutex_unlock(&ev_int->event_list_lock);
> /* Blocking on device; waiting for something to be there */
> ret = wait_event_interruptible(ev_int->wait,
> - !list_empty(&ev_int
> - ->det_events));
> + !kfifo_is_empty(&ev_int->det_events));
> if (ret)
> goto error_ret;
> /* Single access device so no one else can get the data */
> mutex_lock(&ev_int->event_list_lock);
> }
>
> - el = list_first_entry(&ev_int->det_events,
> - struct iio_detected_event_list,
> - list);
> - if (copy_to_user(buf, &(el->ev), len)) {
> - ret = -EFAULT;
> - goto error_mutex_unlock;
> - }
> - list_del(&el->list);
> - ev_int->current_events--;
> mutex_unlock(&ev_int->event_list_lock);
> - kfree(el);
> -
> - return len;
> + ret = kfifo_to_user(&ev_int->det_events, buf, count, &copied);
>
> error_mutex_unlock:
> mutex_unlock(&ev_int->event_list_lock);
> error_ret:
> -
> - return ret;
> + return ret ? ret : copied;
> }
>
> static int iio_event_chrdev_release(struct inode *inode, struct file *filep)
> {
> struct iio_event_interface *ev_int = filep->private_data;
> - struct iio_detected_event_list *el, *t;
>
> mutex_lock(&ev_int->event_list_lock);
> clear_bit(IIO_BUSY_BIT_POS, &ev_int->flags);
> @@ -152,11 +116,7 @@ static int iio_event_chrdev_release(struct inode *inode, struct file *filep)
> * clear out any awaiting events. The mask will prevent
> * any new __iio_push_event calls running.
> */
> - list_for_each_entry_safe(el, t, &ev_int->det_events, list) {
> - list_del(&el->list);
> - kfree(el);
> - }
> - ev_int->current_events = 0;
> + kfifo_reset_out(&ev_int->det_events);
> mutex_unlock(&ev_int->event_list_lock);
>
> return 0;
> @@ -268,9 +228,6 @@ static ssize_t iio_ev_value_store(struct device *dev,
> unsigned long val;
> int ret;
>
> - if (!indio_dev->info->write_event_value)
> - return -EINVAL;
> -
> ret = strict_strtoul(buf, 10, &val);
> if (ret)
> return ret;
> @@ -401,10 +358,7 @@ static bool iio_check_for_dynamic_events(struct iio_dev *indio_dev)
> static void iio_setup_ev_int(struct iio_event_interface *ev_int)
> {
> mutex_init(&ev_int->event_list_lock);
> - /* discussion point - make this variable? */
> - ev_int->max_events = 10;
> - ev_int->current_events = 0;
> - INIT_LIST_HEAD(&ev_int->det_events);
> + INIT_KFIFO(ev_int->det_events);
> init_waitqueue_head(&ev_int->wait);
> }
>
next prev parent reply other threads:[~2011-12-19 20:56 UTC|newest]
Thread overview: 15+ messages / expand[flat|nested] mbox.gz Atom feed top
2011-12-19 10:29 [PATCH v2 1/6] staging:iio: Update iio_event_interface documentation Lars-Peter Clausen
2011-12-19 10:29 ` [PATCH v2 6/6] staging:iio:events: Use non-atmoic bitops Lars-Peter Clausen
2011-12-19 20:59 ` Jonathan Cameron
2012-01-29 10:49 ` Jonathan Cameron
2011-12-19 20:55 ` [PATCH v2 1/6] staging:iio: Update iio_event_interface documentation Jonathan Cameron
2011-12-19 21:28 ` Lars-Peter Clausen
[not found] ` <1324290580-17511-2-git-send-email-lars@metafoo.de>
2011-12-19 20:56 ` [PATCH v2 2/6] staging:iio: Factor out event handling into its own file Jonathan Cameron
[not found] ` <1324290580-17511-3-git-send-email-lars@metafoo.de>
2011-12-19 20:56 ` Jonathan Cameron [this message]
[not found] ` <1324290580-17511-4-git-send-email-lars@metafoo.de>
2011-12-19 20:57 ` [PATCH v2 4/6] staging:iio:events: Use waitqueue lock to protect event queue Jonathan Cameron
2011-12-19 21:28 ` Lars-Peter Clausen
2012-01-29 18:18 ` Jonathan Cameron
2012-01-31 17:26 ` Lars-Peter Clausen
2012-01-31 20:58 ` Jonathan Cameron
-- strict thread matches above, loose matches on Subject: below --
2012-02-01 18:45 [PATCH v2 0/6] staging:iio: Event handling updates Lars-Peter Clausen
2012-02-01 18:45 ` [PATCH v2 3/6] staging:iio:events: Use kfifo for event queue Lars-Peter Clausen
2012-02-01 21:17 [PATCH v2 0/6] staging:iio: Event handling updates Lars-Peter Clausen
2012-02-01 21:17 ` [PATCH v2 3/6] staging:iio:events: Use kfifo for event queue Lars-Peter Clausen
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=4EEFA513.5000707@kernel.org \
--to=jic23@kernel.org \
--cc=device-drivers-devel@blackfin.uclinux.org \
--cc=drivers@analog.com \
--cc=jic23@cam.ac.uk \
--cc=lars@metafoo.de \
--cc=linux-iio@vger.kernel.org \
--cc=michael.hennerich@analog.com \
/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 an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.