summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorDaniel Scally <dan.scally@ideasonboard.com>2023-01-10 12:06:21 +0000
committerDaniel Scally <dan.scally@ideasonboard.com>2023-01-16 13:10:16 +0000
commit3a4e214882b362dc6dccd28d0862a258af75cf33 (patch)
treeb50d76bb0897ce00569b357e31c34611defffd11
parentafd7ad5f9dbef7f31162b9a49b9f85c0a309a3a0 (diff)
lib/stream: Add and handle new VIDEO_SOURCE_ENCODED type
Add functions to handle a new entry into video_source_type, representing data with an encoding step between the source and sink. When running through this route, buffers are allocated and mmaped on both the source and the sink, then imported to the source to be filled before being queued to the sink. Reviewed-by: Kieran Bingham <kieran.bingham@ideasonboard.com> Signed-off-by: Daniel Scally <dan.scally@ideasonboard.com>
-rw-r--r--include/uvcgadget/video-source.h1
-rw-r--r--lib/stream.c58
2 files changed, 59 insertions, 0 deletions
diff --git a/include/uvcgadget/video-source.h b/include/uvcgadget/video-source.h
index 61aeaf7..3497c49 100644
--- a/include/uvcgadget/video-source.h
+++ b/include/uvcgadget/video-source.h
@@ -44,6 +44,7 @@ typedef void(*video_source_buffer_handler_t)(void *, struct video_source *,
enum video_source_type {
VIDEO_SOURCE_DMABUF,
VIDEO_SOURCE_STATIC,
+ VIDEO_SOURCE_ENCODED,
};
struct video_source {
diff --git a/lib/stream.c b/lib/stream.c
index 4a562a5..3bd3e60 100644
--- a/lib/stream.c
+++ b/lib/stream.c
@@ -180,6 +180,60 @@ static int uvc_stream_start_no_alloc(struct uvc_stream *stream)
return 0;
}
+static int uvc_stream_start_encoded(struct uvc_stream *stream)
+{
+ struct v4l2_device *sink = uvc_v4l2_device(stream->uvc);
+ int ret;
+
+ /* Allocate the buffers on the source. */
+ ret = video_source_alloc_buffers(stream->src, 4);
+ if (ret < 0) {
+ printf("Failed to allocate source buffers: %s (%d)\n",
+ strerror(-ret), -ret);
+ return ret;
+ }
+
+ /* Allocate buffers on the sink. */
+ ret = v4l2_alloc_buffers(sink, V4L2_MEMORY_MMAP, 4);
+ if (ret < 0) {
+ printf("Failed to allocate sink buffers: %s (%d)\n",
+ strerror(-ret), -ret);
+ goto error_free_source;
+ }
+
+ /* mmap buffers. */
+ ret = v4l2_mmap_buffers(sink);
+ if (ret < 0) {
+ printf("Failed to query sink buffers: %s (%d)\n",
+ strerror(-ret), -ret);
+ goto error_free_sink;
+ }
+
+ /* Import the sink's buffers to the source */
+ ret = video_source_import_buffers(stream->src, &sink->buffers);
+ if (ret) {
+ printf("Failed to import sink buffers: %s (%d)\n",
+ strerror(ret), ret);
+ goto error_free_sink;
+ }
+
+ /* Start the source and sink. */
+ video_source_stream_on(stream->src);
+ v4l2_stream_on(sink);
+
+ events_watch_fd(stream->events, sink->fd, EVENT_WRITE,
+ uvc_stream_uvc_process, stream);
+
+ return 0;
+
+error_free_sink:
+ v4l2_free_buffers(sink);
+error_free_source:
+ video_source_free_buffers(stream->src);
+
+ return ret;
+}
+
static int uvc_stream_start(struct uvc_stream *stream)
{
printf("Starting video stream.\n");
@@ -191,6 +245,10 @@ static int uvc_stream_start(struct uvc_stream *stream)
return uvc_stream_start_alloc(stream);
case VIDEO_SOURCE_STATIC:
return uvc_stream_start_no_alloc(stream);
+ case VIDEO_SOURCE_ENCODED:
+ video_source_set_buffer_handler(stream->src, uvc_stream_source_process,
+ stream);
+ return uvc_stream_start_encoded(stream);
default:
fprintf(stderr, "invalid video source type\n");
break;