1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
|
/* SPDX-License-Identifier: LGPL-2.1-or-later */
/*
* V4L2 Devices
*
* Copyright (C) 2018 Laurent Pinchart
*
* This file originally comes from the omap3-isp-live project
* (git://git.ideasonboard.org/omap3-isp-live.git)
*
* Copyright (C) 2010-2011 Ideas on board SPRL
*
* Contact: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
*/
#ifndef __V4L2_H
#define __V4L2_H
#include <stdbool.h>
#include <linux/videodev2.h>
#include <sys/time.h>
#include "list.h"
/*
* struct v4l2_video_buffer - Video buffer information
* @index: Zero-based buffer index, limited to the number of buffers minus one
* @size: Size of the video memory, in bytes
* @bytesused: Number of bytes used by video data, smaller or equal to @size
* @timestamp: Time stamp at which the buffer has been captured
* @error: True if an error occured while capturing video data for the buffer
* @allocated: True if memory for the buffer has been allocated
* @mem: Video data memory
* @dmabuf: Video data dmabuf handle
*/
struct v4l2_video_buffer
{
unsigned int index;
unsigned int size;
unsigned int bytesused;
struct timeval timestamp;
bool error;
bool allocated;
void *mem;
int dmabuf;
};
struct v4l2_device
{
int fd;
char *name;
enum v4l2_buf_type type;
enum v4l2_memory memtype;
struct list_entry formats;
struct v4l2_pix_format format;
struct v4l2_rect crop;
unsigned int nbufs;
struct v4l2_video_buffer *buffers;
};
/*
* v4l2_open - Open a V4L2 device
* @devname: Name (including path) of the device node
*
* Open the V4L2 device referenced by @devname for video capture or display in
* non-blocking mode.
*
* If the device can be opened, query its capabilities and enumerates frame
* formats, sizes and intervals.
*
* Return a pointer to a newly allocated v4l2_device structure instance on
* success and NULL on failure. The returned pointer must be freed with
* v4l2_close when the device isn't needed anymore.
*/
struct v4l2_device *v4l2_open(const char *devname);
/*
* v4l2_close - Close a V4L2 device
* @dev: Device instance
*
* Close the device instance given as argument and free allocated resources.
* Access to the device instance is forbidden after this function returns.
*/
void v4l2_close(struct v4l2_device *dev);
/*
* v4l2_get_format - Retrieve the current pixel format
* @dev: Device instance
* @format: Pixel format structure to be filled
*
* Query the device to retrieve the current pixel format and frame size and fill
* the @format structure.
*
* Return 0 on success or a negative error code on failure.
*/
int v4l2_get_format(struct v4l2_device *dev, struct v4l2_pix_format *format);
/*
* v4l2_set_format - Set the pixel format
* @dev: Device instance
* @format: Pixel format structure to be set
*
* Set the pixel format and frame size stored in @format. The device can modify
* the requested format and size, in which case the @format structure will be
* updated to reflect the modified settings.
*
* Return 0 on success or a negative error code on failure.
*/
int v4l2_set_format(struct v4l2_device *dev, struct v4l2_pix_format *format);
/*
* v4l2_get_crop - Retrieve the current crop rectangle
* @dev: Device instance
* @rect: Crop rectangle structure to be filled
*
* Query the device to retrieve the current crop rectangle and fill the @rect
* structure.
*
* Return 0 on success or a negative error code on failure.
*/
int v4l2_get_crop(struct v4l2_device *dev, struct v4l2_rect *rect);
/*
* v4l2_set_crop - Set the crop rectangle
* @dev: Device instance
* @rect: Crop rectangle structure to be set
*
* Set the crop rectangle stored in @rect. The device can modify the requested
* rectangle, in which case the @rect structure will be updated to reflect the
* modified settings.
*
* Return 0 on success or a negative error code on failure.
*/
int v4l2_set_crop(struct v4l2_device *dev, struct v4l2_rect *rect);
/*
* v4l2_alloc_buffers - Allocate buffers for video frames
* @dev: Device instance
* @memtype: Type of buffers
* @nbufs: Number of buffers to allocate
*
* Request the driver to allocate @nbufs buffers. The driver can modify the
* number of buffers depending on its needs. The number of allocated buffers
* will be stored in the @dev::nbufs field.
*
* When @memtype is set to V4L2_MEMORY_MMAP the buffers are allocated by the
* driver. They can then be mapped to userspace by calling v4l2_mmap_buffers().
* When @memtype is set to V4L2_MEMORY_DMABUF the driver only allocates buffer
* objects and relies on the application to provide memory storage for video
* frames.
*
* Return 0 on success or a negative error code on failure.
*/
int v4l2_alloc_buffers(struct v4l2_device *dev, enum v4l2_memory memtype,
unsigned int nbufs);
/*
* v4l2_free_buffers - Free buffers
* @dev: Device instance
*
* Free buffers previously allocated by v4l2_alloc_buffers(). If the buffers
* have been allocated with the V4L2_MEMORY_DMABUF memory type only the buffer
* objects are freed, and the caller is responsible for freeing the video frames
* memory if required.
*
* When successful this function sets the @dev::nbufs field to zero.
*
* Return 0 on success or a negative error code on failure.
*/
int v4l2_free_buffers(struct v4l2_device *dev);
/*
* v4l2_export_buffers - Export buffers as dmabuf objects
* @dev: Device instance
*
* Export all the buffers previously allocated by v4l2_alloc_buffers() as dmabuf
* objects. The dmabuf objects handles can be accessed through the dmabuf field
* of each entry in the @dev::buffers array.
*
* The dmabuf objects handles will be automatically closed when the buffers are
* freed with v4l2_free_buffers().
*
* This function can only be called when buffers have been allocated with the
* memory type set to V4L2_MEMORY_MMAP. If the memory type is different, or if
* no buffers have been allocated, it will return -EINVAL.
*
* Return 0 on success or a negative error code on failure.
*/
int v4l2_export_buffers(struct v4l2_device *dev);
/*
* v4l2_import_buffers - Import buffer backing store as dmabuf objects
* @dev: Device instance
* @nbufs: Number of buffers in the @buffers array
* @buffers: Buffers to be imported
*
* Import the dmabuf objects from @buffers as backing store for the device
* buffers previously allocated by v4l2_alloc_buffers().
*
* The dmabuf file handles are duplicated and stored in the dmabuf field of the
* @dev::buffers array. The handles from the @buffers array can thus be closed
* independently without impacting usage of the imported dmabuf objects. The
* duplicated file handles will be automatically closed when the buffers are
* freed with v4l2_free_buffers().
*
* This function can only be called when buffers have been allocated with the
* memory type set to V4L2_MEMORY_DMABUF. If the memory type is different, if no
* buffers have been allocated, or if the number of allocated buffers is larger
* than @nbufs, it will return -EINVAL.
*
* Return 0 on success or a negative error code on failure.
*/
int v4l2_import_buffers(struct v4l2_device *dev, unsigned int nbufs,
const struct v4l2_video_buffer *buffers);
/*
* v4l2_mmap_buffers - Map buffers to application memory space
* @dev: Device instance
*
* Map all the buffers previously allocated by v4l2_alloc_buffers() to the
* application memory space. The buffer memory can be accessed through the mem
* field of each entry in the @dev::buffers array.
*
* Buffers will be automatically unmapped when freed with v4l2_free_buffers().
*
* This function can only be called when buffers have been allocated with the
* memory type set to V4L2_MEMORY_MMAP. If the memory type is different, or if
* no buffers have been allocated, it will return -EINVAL.
*
* Return 0 on success or a negative error code on failure.
*/
int v4l2_mmap_buffers(struct v4l2_device *dev);
/*
* v4l2_queue_buffer - Queue a buffer for video capture/output
* @dev: Device instance
* @buffer: Buffer to be queued
*
* Queue the buffer identified by @buffer for video capture or output, depending
* on the device type.
*
* The caller must initialize the @buffer::index field with the index of the
* buffer to be queued. The index is zero-based and must be lower than the
* number of allocated buffers.
*
* For V4L2_MEMORY_DMABUF buffers, the caller must initialize the @buffer::dmabuf
* field with the address of the video frame memory, and the @buffer:length
* field with its size in bytes. For optimal performances the address and length
* should be identical between v4l2_queue_buffer() calls for a given buffer
* index.
*
* For video output, the caller must initialize the @buffer::bytesused field
* with the size of video data. The value should differ from the buffer length
* for variable-size video formats only.
*
* Upon successful return the buffer ownership is transferred to the driver. The
* caller must not touch video memory for that buffer before calling
* v4l2_dequeue_buffer(). Attempting to queue an already queued buffer will
* fail.
*
* Return 0 on success or a negative error code on failure.
*/
int v4l2_queue_buffer(struct v4l2_device *dev, struct v4l2_video_buffer *buffer);
/*
* v4l2_dequeue_buffer - Dequeue the next buffer
* @dev: Device instance
* @buffer: Dequeued buffer data to be filled
*
* Dequeue the next buffer processed by the driver and fill all fields in
* @buffer.
*
* This function does not block. If no buffer is ready it will return
* immediately with -EAGAIN.
*
* If an error occured during video capture or display, the @buffer::error field
* is set to true. Depending on the device the video data can be partly
* corrupted or complete garbage.
*
* Once dequeued the buffer ownership is transferred to the caller. Video memory
* for that buffer can be safely read from and written to.
*
* Return 0 on success or a negative error code on failure. An error that
* results in @buffer:error being set is not considered as a failure condition
* for the purpose of the return value.
*/
int v4l2_dequeue_buffer(struct v4l2_device *dev, struct v4l2_video_buffer *buffer);
/*
* v4l2_stream_on - Start video streaming
* @dev: Device instance
*
* Start video capture or output on the device. For video output devices at
* least one buffer must be queued before starting the stream.
*
* Return 0 on success or a negative error code on failure.
*/
int v4l2_stream_on(struct v4l2_device *dev);
/*
* v4l2_stream_off - Stop video streaming
* @dev: Device instance
*
* Stop video capture or output on the device. Upon successful return ownership
* of all buffers is returned to the caller.
*
* Return 0 on success or a negative error code on failure.
*/
int v4l2_stream_off(struct v4l2_device *dev);
/*
* v4l2_get_control - Read the value of a control
* @dev: Device instance
* @id: Control ID
* @value: Control value to be filled
*
* Retrieve the current value of control @id and store it in @value.
*
* Return 0 on success or a negative error code on failure.
*/
int v4l2_get_control(struct v4l2_device *dev, unsigned int id, int32_t *value);
/*
* v4l2_set_control - Write the value of a control
* @dev: Device instance
* @id: Control ID
* @value: Control value
*
* Set control @id to @value. The device is allowed to modify the requested
* value, in which case @value is updated to the modified value.
*
* Return 0 on success or a negative error code on failure.
*/
int v4l2_set_control(struct v4l2_device *dev, unsigned int id, int32_t *value);
/*
* v4l2_get_controls - Read the value of multiple controls
* @dev: Device instance
* @count: Number of controls
* @ctrls: Controls to be read
*
* Retrieve the current value of controls identified by @ctrls.
*
* Return 0 on success or a negative error code on failure.
*/
int v4l2_get_controls(struct v4l2_device *dev, unsigned int count,
struct v4l2_ext_control *ctrls);
/*
* v4l2_set_controls - Write the value of multiple controls
* @dev: Device instance
* @count: Number of controls
* @ctrls: Controls to be written
*
* Set controls identified by @ctrls. The device is allowed to modify the
* requested values, in which case @ctrls is updated to the modified value.
*
* Return 0 on success or a negative error code on failure.
*/
int v4l2_set_controls(struct v4l2_device *dev, unsigned int count,
struct v4l2_ext_control *ctrls);
#endif
|