Change callback custom buffer to media_packet 96/297096/9
authorKwanghoon Son <k.son@samsung.com>
Thu, 10 Aug 2023 06:45:27 +0000 (15:45 +0900)
committerKwanghoon Son <k.son@samsung.com>
Wed, 16 Aug 2023 04:18:41 +0000 (13:18 +0900)
Change-Id: I9a4fad6ead0eb7c3c3a586419e69512c2e54f331
Signed-off-by: Kwanghoon Son <k.son@samsung.com>
src/vision_source_v4l2.c
src/vision_source_v4l2_private.h
test/test_vision_source_v4l2.cpp

index d86ab9b0feac0b33815f31162bfc399db93176e6..b58d7e0134c284b0cf33fe2f13ab1714895c6302 100644 (file)
@@ -984,6 +984,74 @@ int vision_source_v4l2_set_stream_format(vision_source_h handle,
        return VISION_SOURCE_ERROR_NONE;
 }
 
+static int __convert_buffer_to_fmt(vision_source_buffer_s *buffer,
+                                                                  media_format_h fmt)
+{
+       media_format_mimetype_e mime;
+       switch (buffer->pixel_format) {
+       case VISION_SOURCE_PIXEL_FORMAT_RGB24:
+               mime = MEDIA_FORMAT_RGB888;
+               break;
+
+       default:
+               LOGE("Not supported format %d", buffer->pixel_format);
+               return VISION_SOURCE_ERROR_INVALID_PARAMETER;
+       }
+       if (media_format_set_video_mime(fmt, mime) != MEDIA_FORMAT_ERROR_NONE)
+               return VISION_SOURCE_ERROR_INTERNAL;
+       media_format_set_video_width(fmt, buffer->resolution.width);
+       media_format_set_video_height(fmt, buffer->resolution.height);
+
+       return VISION_SOURCE_ERROR_NONE;
+}
+
+static void __pkt_dispose_cb(media_packet_h packet, void *user_data)
+{
+       packet_context_s *pkt_ctx = (packet_context_s *) user_data;
+       if (__vision_source_v4l2_qbuf(pkt_ctx->device_fd, pkt_ctx->type,
+                                                                 pkt_ctx->memory,
+                                                                 pkt_ctx->index) != VISION_SOURCE_ERROR_NONE) {
+               LOGE("qbuf failed with device_fd: %d, type: %d, memory: %d, index: %d",
+                        pkt_ctx->device_fd, pkt_ctx->type, pkt_ctx->memory,
+                        pkt_ctx->index);
+       }
+
+       free(pkt_ctx);
+}
+
+static media_packet_h __make_media_packet(vision_source_buffer_s *buffer,
+                                                                                 int device_fd, int buffer_type,
+                                                                                 int index)
+{
+       media_packet_h pkt;
+       media_format_h fmt;
+       media_format_create(&fmt);
+       if (__convert_buffer_to_fmt(buffer, fmt) != VISION_SOURCE_ERROR_NONE) {
+               media_format_unref(fmt);
+               return NULL;
+       }
+
+       packet_context_s *pkt_ctx =
+                       (packet_context_s *) malloc(sizeof(packet_context_s));
+       if (!pkt_ctx) {
+               LOGE("packet_context_s malloc failed");
+               media_format_unref(fmt);
+               return NULL;
+       }
+
+       pkt_ctx->device_fd = device_fd;
+       pkt_ctx->type = buffer_type;
+       pkt_ctx->memory = V4L2_MEMORY_MMAP;
+       pkt_ctx->index = index;
+
+       media_packet_new_from_external_memory(fmt, buffer->planes[0].data,
+                                                                                 buffer->planes[0].used_size,
+                                                                                 __pkt_dispose_cb, pkt_ctx, &pkt);
+
+       media_format_unref(fmt);
+       return pkt;
+}
+
 static void *__fetch_buffer_and_callback(gpointer data)
 {
        vision_source_v4l2_s *v4l2_handle = (vision_source_v4l2_s *) data;
@@ -1017,20 +1085,19 @@ static void *__fetch_buffer_and_callback(gpointer data)
                        break;
                }
                g_mutex_unlock(&v4l2_handle->buffer_lock);
-               v4l2_handle->vision_source_buffers[index].planes[0].used_size =
-                               byte_size;
+               vision_source_buffer_s *buffer =
+                               &v4l2_handle->vision_source_buffers[index];
+               buffer->planes[0].used_size = byte_size;
 
                if (v4l2_handle->stream_callback) {
-                       v4l2_handle->stream_callback(
-                                       &v4l2_handle->vision_source_buffers[index],
-                                       v4l2_handle->stream_callback_data);
-               }
-               if (__vision_source_v4l2_qbuf(
-                                       v4l2_handle->device_fd, v4l2_handle->buffer_type,
-                                       V4L2_MEMORY_MMAP, index) != VISION_SOURCE_ERROR_NONE) {
-                       LOGE("qbuf failed");
-                       g_mutex_lock(&v4l2_handle->buffer_lock);
-                       break;
+                       media_packet_h pkt =
+                                       __make_media_packet(buffer, v4l2_handle->device_fd,
+                                                                               v4l2_handle->buffer_type, index);
+                       if (!pkt)
+                               return NULL;
+                       v4l2_handle->stream_callback(pkt,
+                                                                                v4l2_handle->stream_callback_data);
+                       media_packet_unref(pkt);
                }
                sched_yield();
 
index d28bbc1e4025e42d1c0c1c80bd3de37510f45b84..9c526d43ef1995d8c7972bac1835ddcc6d98e860 100644 (file)
@@ -85,4 +85,11 @@ typedef struct _vision_source_v4l2_s
        GMutex lock;
 } vision_source_v4l2_s;
 
+typedef struct _packet_context_s
+{
+       int device_fd;
+       int type;
+       int memory;
+       int index;
+} packet_context_s;
 #endif /* __VISION_SOURCE_V4L2_PRIVATE_H__ */
\ No newline at end of file
index 72e0698c57755a292e280da23574604b9be92a7e..3d78475e3f8a3ca008d48f96dcfb2ae53216b699 100644 (file)
@@ -137,7 +137,7 @@ TEST_F(VisionV4L2FixedFormat, StartStream)
        EXPECT_EQ(vision_source_stop_stream(ms_handle), VISION_SOURCE_ERROR_NONE);
 }
 
-static int test_cb(vision_source_buffer_s *buffer, void *user_data)
+static int test_cb(media_packet_h pkt, void *user_data)
 {
        FILE *file;
        clock_t end = clock();
@@ -148,9 +148,14 @@ static int test_cb(vision_source_buffer_s *buffer, void *user_data)
 
        snprintf(filename, 127, "out_%04u.data", (unsigned) delta_ms);
        file = fopen(filename, "w");
-
-       fwrite(buffer->planes[0].data, sizeof(unsigned char),
-                  buffer->planes[0].used_size, file);
+       if (!file)
+               return VISION_SOURCE_ERROR_INTERNAL;
+
+       char *data;
+       uint64_t size;
+       media_packet_get_buffer_data_ptr(pkt, (void **) &data);
+       media_packet_get_buffer_size(pkt, &size);
+       fwrite(data, sizeof(unsigned char), size, file);
        fclose(file);
        return 0;
 }