From: Lars-Peter Clausen <l...@metafoo.de>

Add output buffer support to the kfifo buffer implementation.

The implementation is straight forward and mostly just wraps the kfifo
API to provide the required operations.

Signed-off-by: Lars-Peter Clausen <l...@metafoo.de>
Signed-off-by: Alexandru Ardelean <alexandru.ardel...@analog.com>
---
 drivers/iio/buffer/kfifo_buf.c | 50 ++++++++++++++++++++++++++++++++++
 1 file changed, 50 insertions(+)

diff --git a/drivers/iio/buffer/kfifo_buf.c b/drivers/iio/buffer/kfifo_buf.c
index 34289ce12f20..e8a434f84778 100644
--- a/drivers/iio/buffer/kfifo_buf.c
+++ b/drivers/iio/buffer/kfifo_buf.c
@@ -138,10 +138,60 @@ static void iio_kfifo_buffer_release(struct iio_buffer 
*buffer)
        kfree(kf);
 }
 
+static size_t iio_kfifo_buf_space_available(struct iio_buffer *r)
+{
+       struct iio_kfifo *kf = iio_to_kfifo(r);
+       size_t avail;
+
+       mutex_lock(&kf->user_lock);
+       avail = kfifo_avail(&kf->kf);
+       mutex_unlock(&kf->user_lock);
+
+       return avail;
+}
+
+static int iio_kfifo_remove_from(struct iio_buffer *r, void *data)
+{
+       int ret;
+       struct iio_kfifo *kf = iio_to_kfifo(r);
+
+       if (kfifo_size(&kf->kf) < r->bytes_per_datum)
+               return -EBUSY;
+
+       ret = kfifo_out(&kf->kf, data, r->bytes_per_datum);
+       if (ret != r->bytes_per_datum)
+               return -EBUSY;
+
+       wake_up_interruptible_poll(&r->pollq, POLLOUT | POLLWRNORM);
+
+       return 0;
+}
+
+static int iio_kfifo_write(struct iio_buffer *r, size_t n,
+       const char __user *buf)
+{
+       struct iio_kfifo *kf = iio_to_kfifo(r);
+       int ret, copied;
+
+       mutex_lock(&kf->user_lock);
+       if (!kfifo_initialized(&kf->kf) || n < kfifo_esize(&kf->kf))
+               ret = -EINVAL;
+       else
+               ret = kfifo_from_user(&kf->kf, buf, n, &copied);
+       mutex_unlock(&kf->user_lock);
+       if (ret)
+               return ret;
+
+       return copied;
+}
+
 static const struct iio_buffer_access_funcs kfifo_access_funcs = {
        .store_to = &iio_store_to_kfifo,
        .read = &iio_read_kfifo,
        .data_available = iio_kfifo_buf_data_available,
+       .remove_from = &iio_kfifo_remove_from,
+       .write = &iio_kfifo_write,
+       .space_available = &iio_kfifo_buf_space_available,
        .request_update = &iio_request_update_kfifo,
        .set_bytes_per_datum = &iio_set_bytes_per_datum_kfifo,
        .set_length = &iio_set_length_kfifo,
-- 
2.17.1

Reply via email to