xref: /linux/drivers/iio/dummy/iio_simple_dummy_buffer.c (revision dd2e16cf482d98ab2dd938f08d79d9f6d869730f)
1d2912cb1SThomas Gleixner // SPDX-License-Identifier: GPL-2.0-only
2*dd2e16cfSLee Jones /*
3415f7924SCristina Opriceana  * Copyright (c) 2011 Jonathan Cameron
4415f7924SCristina Opriceana  *
5415f7924SCristina Opriceana  * Buffer handling elements of industrial I/O reference driver.
6415f7924SCristina Opriceana  * Uses the kfifo buffer.
7415f7924SCristina Opriceana  *
8415f7924SCristina Opriceana  * To test without hardware use the sysfs trigger.
9415f7924SCristina Opriceana  */
10415f7924SCristina Opriceana 
11415f7924SCristina Opriceana #include <linux/kernel.h>
12415f7924SCristina Opriceana #include <linux/export.h>
13415f7924SCristina Opriceana #include <linux/slab.h>
14415f7924SCristina Opriceana #include <linux/interrupt.h>
15415f7924SCristina Opriceana #include <linux/irq.h>
16415f7924SCristina Opriceana #include <linux/bitmap.h>
17415f7924SCristina Opriceana 
18415f7924SCristina Opriceana #include <linux/iio/iio.h>
19415f7924SCristina Opriceana #include <linux/iio/trigger_consumer.h>
208abd5ba5SJonathan Cameron #include <linux/iio/buffer.h>
21415f7924SCristina Opriceana #include <linux/iio/kfifo_buf.h>
22415f7924SCristina Opriceana 
23415f7924SCristina Opriceana #include "iio_simple_dummy.h"
24415f7924SCristina Opriceana 
25415f7924SCristina Opriceana /* Some fake data */
26415f7924SCristina Opriceana 
27415f7924SCristina Opriceana static const s16 fakedata[] = {
28f3cf3fb7SGreg Kroah-Hartman 	[DUMMY_INDEX_VOLTAGE_0] = 7,
29f3cf3fb7SGreg Kroah-Hartman 	[DUMMY_INDEX_DIFFVOLTAGE_1M2] = -33,
30f3cf3fb7SGreg Kroah-Hartman 	[DUMMY_INDEX_DIFFVOLTAGE_3M4] = -2,
31f3cf3fb7SGreg Kroah-Hartman 	[DUMMY_INDEX_ACCELX] = 344,
32415f7924SCristina Opriceana };
33415f7924SCristina Opriceana 
34415f7924SCristina Opriceana /**
35415f7924SCristina Opriceana  * iio_simple_dummy_trigger_h() - the trigger handler function
36415f7924SCristina Opriceana  * @irq: the interrupt number
37415f7924SCristina Opriceana  * @p: private data - always a pointer to the poll func.
38415f7924SCristina Opriceana  *
39415f7924SCristina Opriceana  * This is the guts of buffered capture. On a trigger event occurring,
40415f7924SCristina Opriceana  * if the pollfunc is attached then this handler is called as a threaded
41415f7924SCristina Opriceana  * interrupt (and hence may sleep). It is responsible for grabbing data
42415f7924SCristina Opriceana  * from the device and pushing it into the associated buffer.
43415f7924SCristina Opriceana  */
44415f7924SCristina Opriceana static irqreturn_t iio_simple_dummy_trigger_h(int irq, void *p)
45415f7924SCristina Opriceana {
46415f7924SCristina Opriceana 	struct iio_poll_func *pf = p;
47415f7924SCristina Opriceana 	struct iio_dev *indio_dev = pf->indio_dev;
48415f7924SCristina Opriceana 	int len = 0;
49415f7924SCristina Opriceana 	u16 *data;
50415f7924SCristina Opriceana 
51415f7924SCristina Opriceana 	data = kmalloc(indio_dev->scan_bytes, GFP_KERNEL);
52415f7924SCristina Opriceana 	if (!data)
53415f7924SCristina Opriceana 		goto done;
54415f7924SCristina Opriceana 
55415f7924SCristina Opriceana 	if (!bitmap_empty(indio_dev->active_scan_mask, indio_dev->masklength)) {
56415f7924SCristina Opriceana 		/*
57415f7924SCristina Opriceana 		 * Three common options here:
58415f7924SCristina Opriceana 		 * hardware scans: certain combinations of channels make
59415f7924SCristina Opriceana 		 *   up a fast read.  The capture will consist of all of them.
60415f7924SCristina Opriceana 		 *   Hence we just call the grab data function and fill the
61415f7924SCristina Opriceana 		 *   buffer without processing.
62415f7924SCristina Opriceana 		 * software scans: can be considered to be random access
63415f7924SCristina Opriceana 		 *   so efficient reading is just a case of minimal bus
64415f7924SCristina Opriceana 		 *   transactions.
65415f7924SCristina Opriceana 		 * software culled hardware scans:
66415f7924SCristina Opriceana 		 *   occasionally a driver may process the nearest hardware
67415f7924SCristina Opriceana 		 *   scan to avoid storing elements that are not desired. This
68415f7924SCristina Opriceana 		 *   is the fiddliest option by far.
69415f7924SCristina Opriceana 		 * Here let's pretend we have random access. And the values are
70415f7924SCristina Opriceana 		 * in the constant table fakedata.
71415f7924SCristina Opriceana 		 */
72415f7924SCristina Opriceana 		int i, j;
73415f7924SCristina Opriceana 
74415f7924SCristina Opriceana 		for (i = 0, j = 0;
75415f7924SCristina Opriceana 		     i < bitmap_weight(indio_dev->active_scan_mask,
76415f7924SCristina Opriceana 				       indio_dev->masklength);
77415f7924SCristina Opriceana 		     i++, j++) {
78415f7924SCristina Opriceana 			j = find_next_bit(indio_dev->active_scan_mask,
79415f7924SCristina Opriceana 					  indio_dev->masklength, j);
80415f7924SCristina Opriceana 			/* random access read from the 'device' */
81415f7924SCristina Opriceana 			data[i] = fakedata[j];
82415f7924SCristina Opriceana 			len += 2;
83415f7924SCristina Opriceana 		}
84415f7924SCristina Opriceana 	}
85415f7924SCristina Opriceana 
86bc2b7dabSGregor Boirie 	iio_push_to_buffers_with_timestamp(indio_dev, data,
87bc2b7dabSGregor Boirie 					   iio_get_time_ns(indio_dev));
88415f7924SCristina Opriceana 
89415f7924SCristina Opriceana 	kfree(data);
90415f7924SCristina Opriceana 
91415f7924SCristina Opriceana done:
92415f7924SCristina Opriceana 	/*
93415f7924SCristina Opriceana 	 * Tell the core we are done with this trigger and ready for the
94415f7924SCristina Opriceana 	 * next one.
95415f7924SCristina Opriceana 	 */
96415f7924SCristina Opriceana 	iio_trigger_notify_done(indio_dev->trig);
97415f7924SCristina Opriceana 
98415f7924SCristina Opriceana 	return IRQ_HANDLED;
99415f7924SCristina Opriceana }
100415f7924SCristina Opriceana 
101415f7924SCristina Opriceana static const struct iio_buffer_setup_ops iio_simple_dummy_buffer_setup_ops = {
102415f7924SCristina Opriceana };
103415f7924SCristina Opriceana 
104415f7924SCristina Opriceana int iio_simple_dummy_configure_buffer(struct iio_dev *indio_dev)
105415f7924SCristina Opriceana {
106415f7924SCristina Opriceana 	int ret;
107415f7924SCristina Opriceana 	struct iio_buffer *buffer;
108415f7924SCristina Opriceana 
109415f7924SCristina Opriceana 	/* Allocate a buffer to use - here a kfifo */
110415f7924SCristina Opriceana 	buffer = iio_kfifo_allocate();
111415f7924SCristina Opriceana 	if (!buffer) {
112415f7924SCristina Opriceana 		ret = -ENOMEM;
113415f7924SCristina Opriceana 		goto error_ret;
114415f7924SCristina Opriceana 	}
115415f7924SCristina Opriceana 
116415f7924SCristina Opriceana 	iio_device_attach_buffer(indio_dev, buffer);
117415f7924SCristina Opriceana 
118415f7924SCristina Opriceana 	/*
119415f7924SCristina Opriceana 	 * Tell the core what device type specific functions should
120415f7924SCristina Opriceana 	 * be run on either side of buffer capture enable / disable.
121415f7924SCristina Opriceana 	 */
122415f7924SCristina Opriceana 	indio_dev->setup_ops = &iio_simple_dummy_buffer_setup_ops;
123415f7924SCristina Opriceana 
124415f7924SCristina Opriceana 	/*
125415f7924SCristina Opriceana 	 * Configure a polling function.
126415f7924SCristina Opriceana 	 * When a trigger event with this polling function connected
127415f7924SCristina Opriceana 	 * occurs, this function is run. Typically this grabs data
128415f7924SCristina Opriceana 	 * from the device.
129415f7924SCristina Opriceana 	 *
130415f7924SCristina Opriceana 	 * NULL for the bottom half. This is normally implemented only if we
131415f7924SCristina Opriceana 	 * either want to ping a capture now pin (no sleeping) or grab
132415f7924SCristina Opriceana 	 * a timestamp as close as possible to a data ready trigger firing.
133415f7924SCristina Opriceana 	 *
134415f7924SCristina Opriceana 	 * IRQF_ONESHOT ensures irqs are masked such that only one instance
135415f7924SCristina Opriceana 	 * of the handler can run at a time.
136415f7924SCristina Opriceana 	 *
137415f7924SCristina Opriceana 	 * "iio_simple_dummy_consumer%d" formatting string for the irq 'name'
138415f7924SCristina Opriceana 	 * as seen under /proc/interrupts. Remaining parameters as per printk.
139415f7924SCristina Opriceana 	 */
140415f7924SCristina Opriceana 	indio_dev->pollfunc = iio_alloc_pollfunc(NULL,
141415f7924SCristina Opriceana 						 &iio_simple_dummy_trigger_h,
142415f7924SCristina Opriceana 						 IRQF_ONESHOT,
143415f7924SCristina Opriceana 						 indio_dev,
144415f7924SCristina Opriceana 						 "iio_simple_dummy_consumer%d",
145415f7924SCristina Opriceana 						 indio_dev->id);
146415f7924SCristina Opriceana 
147415f7924SCristina Opriceana 	if (!indio_dev->pollfunc) {
148415f7924SCristina Opriceana 		ret = -ENOMEM;
149415f7924SCristina Opriceana 		goto error_free_buffer;
150415f7924SCristina Opriceana 	}
151415f7924SCristina Opriceana 
152415f7924SCristina Opriceana 	/*
153415f7924SCristina Opriceana 	 * Notify the core that this device is capable of buffered capture
154415f7924SCristina Opriceana 	 * driven by a trigger.
155415f7924SCristina Opriceana 	 */
156415f7924SCristina Opriceana 	indio_dev->modes |= INDIO_BUFFER_TRIGGERED;
157415f7924SCristina Opriceana 
158415f7924SCristina Opriceana 	return 0;
159415f7924SCristina Opriceana 
160415f7924SCristina Opriceana error_free_buffer:
161415f7924SCristina Opriceana 	iio_kfifo_free(indio_dev->buffer);
162415f7924SCristina Opriceana error_ret:
163415f7924SCristina Opriceana 	return ret;
164415f7924SCristina Opriceana }
165415f7924SCristina Opriceana 
166415f7924SCristina Opriceana /**
167415f7924SCristina Opriceana  * iio_simple_dummy_unconfigure_buffer() - release buffer resources
168*dd2e16cfSLee Jones  * @indio_dev: device instance state
169415f7924SCristina Opriceana  */
170415f7924SCristina Opriceana void iio_simple_dummy_unconfigure_buffer(struct iio_dev *indio_dev)
171415f7924SCristina Opriceana {
172415f7924SCristina Opriceana 	iio_dealloc_pollfunc(indio_dev->pollfunc);
173415f7924SCristina Opriceana 	iio_kfifo_free(indio_dev->buffer);
174415f7924SCristina Opriceana }
175