Simplify v4l2_cap support

This commit is contained in:
Kamil Trzcinski
2022-04-10 10:44:31 +02:00
parent 4d01c86398
commit ca07c62f25
5 changed files with 47 additions and 52 deletions

View File

@ -46,7 +46,7 @@ camera_t *camera_open(camera_options_t *options)
camera->camera->allow_dma = camera->options.allow_dma;
if (strstr(camera->camera->v4l2_cap.bus_info, "usb")) {
if (strstr(camera->camera->bus_info, "usb")) {
E_LOG_INFO(camera, "Disabling DMA since device uses USB (which is likely not working properly).");
camera->camera->allow_dma = false;
}

View File

@ -3,42 +3,50 @@
#include "device/hw/device.h"
#include "device/hw/v4l2.h"
buffer_list_t *buffer_list_open(const char *name, struct device_s *dev, unsigned type, bool do_mmap)
buffer_list_t *buffer_list_open(const char *name, struct device_s *dev, bool do_capture, bool do_mmap)
{
buffer_list_t *buf_list = calloc(1, sizeof(buffer_list_t));
buf_list->device = dev;
buf_list->name = strdup(name);
buf_list->v4l2.type = type;
buf_list->do_capture = do_capture;
switch(type) {
case V4L2_BUF_TYPE_VIDEO_OUTPUT:
buf_list->do_mmap = do_mmap;
buf_list->do_dma = do_mmap;
break;
struct v4l2_capability v4l2_cap;
E_XIOCTL(dev, dev->fd, VIDIOC_QUERYCAP, &v4l2_cap, "Can't query device capabilities");
case V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE:
buf_list->do_mmap = do_mmap;
if (do_capture) {
if (v4l2_cap.capabilities & V4L2_CAP_VIDEO_CAPTURE) {
buf_list->v4l2.type = V4L2_BUF_TYPE_VIDEO_CAPTURE;
buf_list->do_dma = do_mmap;
buf_list->do_mmap = do_mmap;
} else if (v4l2_cap.capabilities & (V4L2_CAP_VIDEO_CAPTURE_MPLANE | V4L2_CAP_VIDEO_M2M_MPLANE)) {
buf_list->v4l2.type = V4L2_BUF_TYPE_VIDEO_CAPTURE_MPLANE;
buf_list->v4l2.do_mplanes = true;
break;
case V4L2_BUF_TYPE_VIDEO_CAPTURE:
buf_list->do_dma = do_mmap;
buf_list->do_mmap = do_mmap;
buf_list->do_capture = true;
break;
case V4L2_BUF_TYPE_VIDEO_CAPTURE_MPLANE:
buf_list->do_dma = do_mmap;
} else {
E_LOG_ERROR(dev, "Video capture is not supported by device: %08x", v4l2_cap.capabilities);
}
} else {
if (v4l2_cap.capabilities & V4L2_CAP_VIDEO_OUTPUT) {
buf_list->v4l2.type = V4L2_BUF_TYPE_VIDEO_OUTPUT;
buf_list->do_mmap = do_mmap;
buf_list->do_dma = do_mmap;
} else if (v4l2_cap.capabilities & (V4L2_CAP_VIDEO_OUTPUT_MPLANE | V4L2_CAP_VIDEO_M2M_MPLANE)) {
buf_list->v4l2.type = V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE;
buf_list->v4l2.do_mplanes = true;
buf_list->do_capture = true;
break;
buf_list->do_mmap = do_mmap;
buf_list->do_dma = do_mmap;
} else {
E_LOG_ERROR(dev, "Video output is not supported by device: %08x", v4l2_cap.capabilities);
}
}
default:
E_LOG_PERROR(buf_list, "Unknown type=%d", type);
goto error;
// Add suffix for debug purposes
if (v4l2_cap.capabilities & (V4L2_CAP_VIDEO_CAPTURE_MPLANE | V4L2_CAP_VIDEO_M2M_MPLANE | V4L2_CAP_VIDEO_OUTPUT_MPLANE | V4L2_CAP_VIDEO_M2M_MPLANE)) {
#define MPLANE_SUFFIX ":mplane"
buf_list->name = realloc(buf_list->name, strlen(buf_list->name) + strlen(MPLANE_SUFFIX) + 1);
strcat(buf_list->name, MPLANE_SUFFIX);
}
return buf_list;

View File

@ -30,7 +30,7 @@ typedef struct buffer_list_s {
int frames;
} buffer_list_t;
buffer_list_t *buffer_list_open(const char *name, struct device_s *dev, unsigned type, bool do_mmap);
buffer_list_t *buffer_list_open(const char *name, struct device_s *dev, bool do_capture, bool do_mmap);
void buffer_list_close(buffer_list_t *buf_list);
int buffer_list_set_stream(buffer_list_t *buf_list, bool do_on);

View File

@ -16,12 +16,15 @@ device_t *device_open(const char *name, const char *path, device_hw_t *hw) {
}
E_LOG_DEBUG(dev, "Querying device capabilities ...");
E_XIOCTL(dev, dev->fd, VIDIOC_QUERYCAP, &dev->v4l2_cap, "Can't query device capabilities");\
struct v4l2_capability v4l2_cap;
E_XIOCTL(dev, dev->fd, VIDIOC_QUERYCAP, &v4l2_cap, "Can't query device capabilities");
if (!(dev->v4l2_cap.capabilities & V4L2_CAP_STREAMING)) {
if (!(v4l2_cap.capabilities & V4L2_CAP_STREAMING)) {
E_LOG_ERROR(dev, "Device doesn't support streaming IO");
}
strcpy(dev->bus_info, v4l2_cap.bus_info);
E_LOG_INFO(dev, "Device path=%s fd=%d opened", dev->path, dev->fd);
dev->subdev_fd = device_open_v4l2_subdev(dev, 0);
@ -81,15 +84,7 @@ int device_open_buffer_list(device_t *dev, bool do_capture, unsigned width, unsi
E_LOG_ERROR(dev, "The capture_list is already created.");
}
if (dev->v4l2_cap.capabilities & V4L2_CAP_VIDEO_CAPTURE) {
type = V4L2_BUF_TYPE_VIDEO_CAPTURE;
sprintf(name, "%s:capture", dev->name);
} else if (dev->v4l2_cap.capabilities & (V4L2_CAP_VIDEO_CAPTURE_MPLANE | V4L2_CAP_VIDEO_M2M_MPLANE)) {
type = V4L2_BUF_TYPE_VIDEO_CAPTURE_MPLANE;
sprintf(name, "%s:capture:mplane", dev->name);
} else {
E_LOG_ERROR(dev, "Video capture is not supported by device: %08x", dev->v4l2_cap.capabilities);
}
} else {
buf_list = &dev->output_list;
@ -97,18 +92,10 @@ int device_open_buffer_list(device_t *dev, bool do_capture, unsigned width, unsi
E_LOG_ERROR(dev, "The output_list is already created.");
}
if (dev->v4l2_cap.capabilities & V4L2_CAP_VIDEO_OUTPUT) {
type = V4L2_BUF_TYPE_VIDEO_OUTPUT;
sprintf(name, "%s:output", dev->name);
} else if (dev->v4l2_cap.capabilities & (V4L2_CAP_VIDEO_OUTPUT_MPLANE | V4L2_CAP_VIDEO_M2M_MPLANE)) {
type = V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE;
sprintf(name, "%s:output:mplane", dev->name);
} else {
E_LOG_ERROR(dev, "Video output is not supported by device: %08x", dev->v4l2_cap.capabilities);
}
}
*buf_list = buffer_list_open(name, dev, type, do_mmap);
*buf_list = buffer_list_open(name, dev, do_capture, do_mmap);
if (!*buf_list) {
goto error;
}

View File

@ -13,9 +13,9 @@ typedef struct device_hw_s {
typedef struct device_s {
char *name;
char *path;
char bus_info[64];
int fd;
int subdev_fd;
struct v4l2_capability v4l2_cap;
bool allow_dma;
device_hw_t *hw;