From c4a5ca6414ca362f0c3c548bb5a990bf5420cd1b Mon Sep 17 00:00:00 2001 From: Hyunil Date: Thu, 30 Mar 2017 18:01:54 +0900 Subject: [PATCH] waylandsink : modify code about create wlbuffer Change-Id: Ie7dbee267f00efd95d3578abf62e229b0ddf8e73 Signed-off-by: Hyunil --- ext/wayland/gstwaylandsink.c | 502 ++++++++++++++++++++++++++----------------- ext/wayland/gstwaylandsink.h | 3 +- ext/wayland/wlbuffer.c | 2 + ext/wayland/wlshmallocator.c | 16 +- ext/wayland/wlshmallocator.h | 1 + 5 files changed, 326 insertions(+), 198 deletions(-) diff --git a/ext/wayland/gstwaylandsink.c b/ext/wayland/gstwaylandsink.c index c334780..3a6861e 100755 --- a/ext/wayland/gstwaylandsink.c +++ b/ext/wayland/gstwaylandsink.c @@ -1828,6 +1828,7 @@ gst_wayland_sink_propose_allocation (GstBaseSink * bsink, GstQuery * query) GstWaylandSink *sink = GST_WAYLAND_SINK (bsink); GstStructure *config; guint size, min_bufs, max_bufs; + #ifdef TIZEN_FEATURE_WLSINK_ENHANCEMENT gboolean need_pool; GstCaps *caps; @@ -1835,7 +1836,7 @@ gst_wayland_sink_propose_allocation (GstBaseSink * bsink, GstQuery * query) if (sink->USE_TBM) { if (sink->display->is_native_format == TRUE) - return TRUE; + return FALSE; gst_query_parse_allocation (query, &caps, &need_pool); @@ -1968,43 +1969,288 @@ render_last_buffer (GstWaylandSink * sink) gst_wl_window_render (sink->window, wlbuffer, info); } + +static gboolean +gst_wayland_sink_has_wlbuffer (GstWaylandSink * sink, GstBuffer * buffer) +{ + GstWlBuffer *gstwlbuffer; + FUNCTION; + g_return_val_if_fail (sink != NULL, FALSE); + g_return_val_if_fail (buffer != NULL, FALSE); + + gstwlbuffer = gst_buffer_get_wl_buffer (buffer); + if (gstwlbuffer && gstwlbuffer->display == sink->display + && !gst_wayland_sink_is_gapless (sink) + && !sink->request_camera_flush_buf) { + /* gstbuffer has wlbuffer */ + /* e.g) last_buffer, buffer is created by previous plugin or waylandsink with BufferPool */ + GST_LOG ("buffer(%p) has GstWlBuffer(%p):wlbuffer(%p)", buffer, gstwlbuffer, + gstwlbuffer->wlbuffer); + return TRUE; + } + GST_LOG ("buffer(%p) has not wlbuffer", buffer); + return FALSE; +} + +static void +gst_wayland_sink_no_create_wlbuffer (GstWaylandSink * sink, GstBuffer * buffer) +{ + GstMemory *mem; + FUNCTION; + g_return_if_fail (sink != NULL); + g_return_if_fail (buffer != NULL); + + /* the last_buffer for flushing has wlbuffer or + buffer is created by previous plugins or waylandsink has wlbuffer */ + mem = gst_buffer_peek_memory (buffer, 0); + if (gst_is_wl_memory (mem)) { + GST_LOG ("buffer(%p) is created by waylandsink has a wl_buffer, " + "writing directly", buffer); + } else { + GST_LOG + ("buffer(%p) is created by previous plugins with BufferPool has a wl_buffer, " + "writing directly", buffer); + GST_LOG ("previous plugins must manage buffer index well"); + } + + sink->to_render = buffer; + + if (sink->dump_video && !sink->display->is_native_format) + gst_wayland_sink_dump_raw_video (sink, sink->to_render, + sink->display->dump_count++, sink->total_dump); +} + +static void +gst_wayland_sink_create_wlbuffer_with_wl_mem (GstWaylandSink * sink, + GstBuffer * buffer) +{ + GstMemory *mem; + struct wl_buffer *wbuf = NULL; + FUNCTION; + g_return_if_fail (sink != NULL); + g_return_if_fail (buffer != NULL); + + GST_LOG ("gstbuffer(%p) is created by wayland has not wlbuffer", buffer); + mem = gst_buffer_peek_memory (buffer, 0); + wbuf = + gst_wl_shm_memory_construct_wl_buffer (mem, sink->display, + &sink->video_info); + if (wbuf) { + gst_buffer_add_wl_buffer (buffer, wbuf, sink->display); + sink->to_render = buffer; + } +} + +static GstFlowReturn +gst_wayland_sink_create_wlbuffer_with_previous_plugin_tbm (GstWaylandSink * + sink, GstBuffer * buffer) +{ + GstMemory *mem; + GstWlBuffer *wlbuffer; + struct wl_buffer *wbuf = NULL; + GstFlowReturn ret = GST_FLOW_OK; + FUNCTION; + g_return_val_if_fail (sink != NULL, GST_FLOW_ERROR); + g_return_val_if_fail (buffer != NULL, GST_FLOW_ERROR); + sink->flush_gstbuf = NULL; + + GST_LOG + ("buffer(%p) is created by previous plugin with no BufferPool does not have a wl_buffer", + buffer); + GST_LOG ("Use native format with previous plugins TBM"); + /* in case of native format (SN12, ST12, SR32 and S420) */ + if (!gst_wayland_sink_get_mm_video_buf_info (sink, buffer)) { + return GST_FLOW_ERROR; + } + + wlbuffer = gst_buffer_get_wl_buffer (buffer); + /* last_buffer from gaplasee have wlbuffer */ + if (G_UNLIKELY (!wlbuffer) || sink->display->flush_request) { + mem = gst_buffer_peek_memory (buffer, 0); + wbuf = + gst_wl_shm_memory_construct_wl_buffer (mem, sink->display, + &sink->video_info); + if (G_UNLIKELY (!wbuf)) { + GST_ERROR ("could not create wl_buffer"); + return GST_FLOW_ERROR; + } + if (sink->display->flush_request) { + sink->flush_gstbuf = gst_buffer_new (); + GST_LOG ("To flush, new gstBuffer(%p)", sink->flush_gstbuf); + gst_buffer_add_wl_buffer (sink->flush_gstbuf, wbuf, sink->display); + } else { + gst_buffer_add_wl_buffer (buffer, wbuf, sink->display); + } + } + return ret; +} + +static GstFlowReturn + gst_wayland_sink_copy_input_gstbuffer_to_wl_gstbuffer_with_wl_mem + (GstWaylandSink * sink, GstBuffer * buffer) +{ + GstWlBuffer *wlbuffer; + GstMemory *mem; + GstWlShmMemory *shm_mem; + GstMapInfo src; + struct wl_buffer *wbuf = NULL; + GstFlowReturn ret = GST_FLOW_OK; + FUNCTION; + g_return_val_if_fail (sink != NULL, GST_FLOW_ERROR); + g_return_val_if_fail (buffer != NULL, GST_FLOW_ERROR); + + GST_LOG ("Use normal format with wayland TBM or SHM"); + /* sink->pool always exists (created in set_caps), but it may not + * be active if upstream is not using it */ + if (!gst_buffer_pool_is_active (sink->pool) && + !gst_buffer_pool_set_active (sink->pool, TRUE)) { + GST_ERROR ("failed to activate bufferpool."); + return GST_FLOW_ERROR; + } + + ret = gst_buffer_pool_acquire_buffer (sink->pool, &sink->to_render, NULL); + if (ret != GST_FLOW_OK) { + GST_WARNING ("could not create buffer"); + return ret; + } + /* the first time we acquire a buffer, + * we need to attach a wl_buffer on it */ + wlbuffer = gst_buffer_get_wl_buffer (buffer); + if (G_UNLIKELY (!wlbuffer)) { + mem = gst_buffer_peek_memory (sink->to_render, 0); + shm_mem = (GstWlShmMemory *) mem; + GST_LOG ("to_render(%p), shm_mem->fd(%d)", sink->to_render, shm_mem->fd); + wbuf = + gst_wl_shm_memory_construct_wl_buffer (mem, sink->display, + &sink->video_info); + if (G_UNLIKELY (!wbuf)) { + GST_ERROR ("could not create wl_buffer out of wl memory"); + return GST_FLOW_ERROR; + } + wlbuffer = gst_buffer_add_wl_buffer (sink->to_render, wbuf, sink->display); + } + + gst_buffer_map (buffer, &src, GST_MAP_READ); + gst_buffer_fill (sink->to_render, 0, src.data, src.size); + gst_buffer_unmap (buffer, &src); + + return ret; +} + +static GstFlowReturn +gst_wayland_sink_create_wlbuffer (GstWaylandSink * sink, GstBuffer * buffer) +{ + GstMemory *mem; + GstFlowReturn ret = GST_FLOW_OK; + FUNCTION; + g_return_val_if_fail (sink != NULL, GST_FLOW_ERROR); + g_return_val_if_fail (buffer != NULL, GST_FLOW_ERROR); + + sink->to_render = NULL; + + if (gst_wayland_sink_has_wlbuffer (sink, buffer)) { + gst_wayland_sink_no_create_wlbuffer (sink, buffer); + } else { + mem = gst_buffer_peek_memory (buffer, 0); + if (gst_is_wl_memory (mem)) { + /* SHM or TBM */ + gst_wayland_sink_create_wlbuffer_with_wl_mem (sink, buffer); + } else { + /* gstbuffer is not wl memory */ + if (sink->USE_TBM && sink->display->is_native_format) { + /* Use tbm of buffer directly */ + ret = + gst_wayland_sink_create_wlbuffer_with_previous_plugin_tbm (sink, + buffer); + } else { + /* Copy virtual addr to wayland SHM or TBM */ + ret = + gst_wayland_sink_copy_input_gstbuffer_to_wl_gstbuffer_with_wl_mem + (sink, buffer); + } + } + } + return ret; +} + +static void +gst_wayland_sink_buffer_replace (GstWaylandSink * sink, GstBuffer * buffer) +{ + FUNCTION; + g_return_if_fail (sink != NULL); + + if (sink->USE_TBM && sink->display->is_native_format) { + if (sink->flush_gstbuf && sink->display->flush_request) { + GST_LOG_OBJECT (sink, "replace last_buffer:(%p)->(%p)", sink->last_buffer, + sink->flush_gstbuf); + /* increase ref count of sink->fflush_gstbuf, decrease ref count of sink->last_buffer */ + gst_buffer_replace (&sink->last_buffer, sink->flush_gstbuf); + GST_LOG_OBJECT (sink, "after gst_buffer_replace buffer %p, ref_count(%d)", + sink->flush_gstbuf, GST_OBJECT_REFCOUNT_VALUE (sink->flush_gstbuf)); + /* decrease ref count of flush_buffer */ + gst_buffer_unref (sink->flush_gstbuf); + } else { + /* normal case */ + GST_LOG_OBJECT (sink, "replace last_buffer:(%p)->(%p)", sink->last_buffer, + buffer); + /* increase ref count of buffer decrease ref count of sink->last_buffer */ + gst_buffer_replace (&sink->last_buffer, buffer); + GST_LOG_OBJECT (sink, "after gst_buffer_replace buffer %p, ref_count(%d)", + buffer, GST_OBJECT_REFCOUNT_VALUE (buffer)); + } + } else { + gst_buffer_replace (&sink->last_buffer, sink->to_render); + GST_LOG_OBJECT (sink, "after gst_buffer_replace buffer %p, ref_count(%d)", + sink->to_render, GST_OBJECT_REFCOUNT_VALUE (sink->to_render)); + } +} + +static void +gst_wayland_sink_get_window (GstWaylandSink * sink) +{ + g_return_if_fail (sink != NULL); + FUNCTION; + + /* ask for window handle. Unlock render_lock while doing that because + * set_window_handle & friends will lock it in this context */ + g_mutex_unlock (&sink->render_lock); + gst_video_overlay_prepare_window_handle (GST_VIDEO_OVERLAY (sink)); + g_mutex_lock (&sink->render_lock); + + if (!sink->window) { + /* if we were not provided a window, create one ourselves */ + sink->window = + gst_wl_window_new_toplevel (sink->display, &sink->video_info); + } + gst_wayland_sink_update_window_geometry (sink); +} + static GstFlowReturn gst_wayland_sink_render (GstBaseSink * bsink, GstBuffer * buffer) { +#ifdef TIZEN_FEATURE_WLSINK_ENHANCEMENT + GstWaylandSink *sink = GST_WAYLAND_SINK (bsink); - GstBuffer *to_render; - GstBuffer *flush_gstbuf = NULL; - GstWlBuffer *wlbuffer; GstFlowReturn ret = GST_FLOW_OK; FUNCTION; g_mutex_lock (&sink->render_lock); - GST_LOG_OBJECT (sink, "render gstbuffer %p, ref_count(%d)", buffer, + GST_LOG_OBJECT (sink, "input gstbuffer %p, ref_count(%d)", buffer, GST_OBJECT_REFCOUNT_VALUE (buffer)); + /* check overlay */ if (gst_wayland_sink_is_disabled_overlay (sink)) { GST_LOG ("set disable_overlay, so skip"); goto done; } + /* check window */ if (G_UNLIKELY (!sink->window)) { - /* ask for window handle. Unlock render_lock while doing that because - * set_window_handle & friends will lock it in this context */ - g_mutex_unlock (&sink->render_lock); - gst_video_overlay_prepare_window_handle (GST_VIDEO_OVERLAY (sink)); - g_mutex_lock (&sink->render_lock); - - if (!sink->window) { - /* if we were not provided a window, create one ourselves */ - sink->window = - gst_wl_window_new_toplevel (sink->display, &sink->video_info); - } -#ifdef TIZEN_FEATURE_WLSINK_ENHANCEMENT - gst_wayland_sink_update_window_geometry (sink); -#endif + gst_wayland_sink_get_window (sink); } + /* fakesink function for media stream callback case */ if (sink->signal_handoffs) { GST_LOG ("g_signal_emit: hand-off "); g_signal_emit (sink, gst_waylandsink_signals[SIGNAL_HANDOFF], 0, buffer, @@ -2017,193 +2263,65 @@ gst_wayland_sink_render (GstBaseSink * bsink, GstBuffer * buffer) && !gst_wayland_sink_is_gapless (sink)) goto done; -#ifndef TIZEN_FEATURE_WLSINK_ENHANCEMENT /* for tizen view_port, we don't know window size */ - /* make sure that the application has called set_render_rectangle() */ - if (G_UNLIKELY (sink->window->render_rectangle.w == 0)) - goto no_window_size; -#endif -#ifdef TIZEN_FEATURE_WLSINK_ENHANCEMENT + /* create wl_buffer */ + ret = gst_wayland_sink_create_wlbuffer (sink, buffer); + if (ret != GST_FLOW_OK) + goto done; - wlbuffer = gst_buffer_get_wl_buffer (buffer); - if (G_LIKELY (wlbuffer && wlbuffer->display == sink->display) - && !(gst_wayland_sink_is_gapless (sink)) - && !sink->request_camera_flush_buf) { - GST_LOG_OBJECT (sink, "buffer %p has a wl_buffer from our display, " "writing directly", buffer); //buffer is from our pool and have wl_buffer - GST_LOG ("wl_buffer (%p)", wlbuffer->wlbuffer); - to_render = buffer; + /* drop double rendering */ + if ((G_UNLIKELY (buffer == sink->last_buffer) + && !(sink->display->flush_request))) { + GST_LOG_OBJECT (sink, "Buffer already being rendered"); + goto done; + } - if (sink->dump_video) - gst_wayland_sink_dump_raw_video (sink, to_render, - sink->display->dump_count++, sink->total_dump); + /* replace last_buffer */ + gst_wayland_sink_buffer_replace (sink, buffer); + /* rendering */ + if (sink->visible) { + render_last_buffer (sink); } else { - GstMemory *mem; - struct wl_buffer *wbuf = NULL; - - GST_LOG_OBJECT (sink, "buffer %p does not have a wl_buffer from our " "display, creating it", buffer); //buffer is from our pool but have not wl_buffer - mem = gst_buffer_peek_memory (buffer, 0); - if (gst_is_wl_shm_memory (mem)) { - FUNCTION; - wbuf = gst_wl_shm_memory_construct_wl_buffer (mem, sink->display, - &sink->video_info); - if (wbuf) { - gst_buffer_add_wl_buffer (buffer, wbuf, sink->display); //careat GstWlBuffer and add gstbuffer, wlbuffer, display and etc - to_render = buffer; - } - } else { //buffer is not from our pool and have not wl_buffer - GstMapInfo src; - /* we don't know how to create a wl_buffer directly from the provided - * memory, so we have to copy the data to a memory that we know how - * to handle... */ - - GST_LOG_OBJECT (sink, "buffer %p is not from our pool", buffer); - GST_LOG_OBJECT (sink, "buffer %p cannot have a wl_buffer, " "copying", - buffer); - - if (sink->USE_TBM && sink->display->is_native_format) { - /* in case of SN12 or ST12 */ - if (!gst_wayland_sink_get_mm_video_buf_info (sink, buffer)) { - ret = GST_FLOW_ERROR; - goto done; - } - - wlbuffer = gst_buffer_get_wl_buffer (buffer); - /* last_buffer from gaplasee have wlbuffer */ - if (G_UNLIKELY (!wlbuffer) || sink->display->flush_request) { - wbuf = - gst_wl_shm_memory_construct_wl_buffer (mem, sink->display, - &sink->video_info); - if (G_UNLIKELY (!wbuf)) - goto no_wl_buffer; - if (sink->display->flush_request) { - flush_gstbuf = gst_buffer_new (); - GST_LOG ("To flush, new gstBuffer(%p)", flush_gstbuf); - gst_buffer_add_wl_buffer (flush_gstbuf, wbuf, sink->display); - - } else { - gst_buffer_add_wl_buffer (buffer, wbuf, sink->display); - } - } - } else if (sink->USE_TBM && !sink->display->is_native_format) { - - /* sink->pool always exists (created in set_caps), but it may not - * be active if upstream is not using it */ - if (!gst_buffer_pool_is_active (sink->pool) - && !gst_buffer_pool_set_active (sink->pool, TRUE)) - goto activate_failed; - - ret = gst_buffer_pool_acquire_buffer (sink->pool, &to_render, NULL); - if (ret != GST_FLOW_OK) - goto no_buffer; - - //GstMemory *mem; - //mem = gst_buffer_peek_memory (to_render, 0); - //if (gst_is_wl_shm_memory (mem)) { - GST_LOG ("to_render buffer is our buffer"); - //} - /* the first time we acquire a buffer, - * we need to attach a wl_buffer on it */ - wlbuffer = gst_buffer_get_wl_buffer (buffer); - if (G_UNLIKELY (!wlbuffer)) { - mem = gst_buffer_peek_memory (to_render, 0); - wbuf = gst_wl_shm_memory_construct_wl_buffer (mem, sink->display, - &sink->video_info); - if (G_UNLIKELY (!wbuf)) - goto no_wl_buffer; - - wlbuffer = gst_buffer_add_wl_buffer (to_render, wbuf, sink->display); - } - - gst_buffer_map (buffer, &src, GST_MAP_READ); - gst_buffer_fill (to_render, 0, src.data, src.size); - gst_buffer_unmap (buffer, &src); - } else { /* USE SHM */ - /* sink->pool always exists (created in set_caps), but it may not - * be active if upstream is not using it */ - if (!gst_buffer_pool_is_active (sink->pool) && - !gst_buffer_pool_set_active (sink->pool, TRUE)) - goto activate_failed; - ret = gst_buffer_pool_acquire_buffer (sink->pool, &to_render, NULL); - if (ret != GST_FLOW_OK) - goto no_buffer; - /* the first time we acquire a buffer, - * we need to attach a wl_buffer on it */ - wlbuffer = gst_buffer_get_wl_buffer (buffer); - if (G_UNLIKELY (!wlbuffer)) { - mem = gst_buffer_peek_memory (to_render, 0); - wbuf = gst_wl_shm_memory_construct_wl_buffer (mem, sink->display, - &sink->video_info); - if (G_UNLIKELY (!wbuf)) - goto no_wl_buffer; - - gst_buffer_add_wl_buffer (to_render, wbuf, sink->display); - - } - - gst_buffer_map (buffer, &src, GST_MAP_READ); - gst_buffer_fill (to_render, 0, src.data, src.size); - gst_buffer_unmap (buffer, &src); - } - } + GST_LOG ("skip rendering"); } - if (sink->USE_TBM && sink->display->is_native_format) { - if ((G_UNLIKELY (buffer == sink->last_buffer) - && !(sink->display->flush_request))) { - GST_LOG_OBJECT (sink, "Buffer already being rendered"); - goto done; - } + if (sink->to_render) { + if (buffer != sink->to_render) + gst_buffer_unref (sink->to_render); + } - if (flush_gstbuf && sink->display->flush_request) { + goto done; - GST_LOG_OBJECT (sink, "replace last_buffer: (%p) -> (%p)", - sink->last_buffer, flush_gstbuf); - /* increase ref count of flush_gstbuf - decrease ref count of sink->last_buffer */ - gst_buffer_replace (&sink->last_buffer, flush_gstbuf); - GST_LOG_OBJECT (sink, "after gst_buffer_replace buffer %p, ref_count(%d)", - flush_gstbuf, GST_OBJECT_REFCOUNT_VALUE (flush_gstbuf)); - /* decrease ref count of flush_buffer */ - gst_buffer_unref (flush_gstbuf); +#else /* open source */ - } else { //normal case + GstWaylandSink *sink = GST_WAYLAND_SINK (bsink); + GstBuffer *to_render = NULL; + GstFlowReturn ret = GST_FLOW_OK; - GST_LOG_OBJECT (sink, "replace last_buffer: (%p) -> (%p)", - sink->last_buffer, buffer); - /* increase ref count of buffer - decrease ref count of sink->last_buffer */ - gst_buffer_replace (&sink->last_buffer, buffer); - GST_LOG_OBJECT (sink, "after gst_buffer_replace buffer %p, ref_count(%d)", - buffer, GST_OBJECT_REFCOUNT_VALUE (buffer)); - } - if (sink->visible) { - render_last_buffer (sink); - } else { - GST_LOG ("skip rendering"); - } - goto done; + g_mutex_lock (&sink->render_lock); - } else { /* USE SHM or normal format */ - /* drop double rendering */ - if (G_UNLIKELY (buffer == sink->last_buffer)) { - GST_LOG_OBJECT (sink, "Buffer already being rendered"); - goto done; - } - gst_buffer_replace (&sink->last_buffer, to_render); + if (G_UNLIKELY (!sink->window)) { + /* ask for window handle. Unlock render_lock while doing that because + * set_window_handle & friends will lock it in this context */ + g_mutex_unlock (&sink->render_lock); + gst_video_overlay_prepare_window_handle (GST_VIDEO_OVERLAY (sink)); + g_mutex_lock (&sink->render_lock); - if (sink->visible) { - render_last_buffer (sink); - } else { - GST_LOG ("skip rendering"); + if (!sink->window) { + /* if we were not provided a window, create one ourselves */ + sink->window = + gst_wl_window_new_toplevel (sink->display, &sink->video_info); } + } - if (buffer != to_render) - gst_buffer_unref (to_render); - + /* drop buffers until we get a frame callback */ + if (g_atomic_int_get (&sink->redraw_pending) == TRUE + && !gst_wayland_sink_is_gapless (sink)) goto done; - } -#else /* open source */ + /* make sure that the application has called set_render_rectangle() */ + if (G_UNLIKELY (sink->window->render_rectangle.w == 0)) + goto no_window_size; wlbuffer = gst_buffer_get_wl_buffer (buffer); @@ -2222,7 +2340,7 @@ gst_wayland_sink_render (GstBaseSink * bsink, GstBuffer * buffer) "buffer %p does not have a wl_buffer from our " "display, creating it", buffer); mem = gst_buffer_peek_memory (buffer, 0); - if (gst_is_wl_shm_memory (mem)) { + if (gst_is_wl_shm_memory (mem)) { /* is wayland memory */ FUNCTION; wbuf = gst_wl_shm_memory_construct_wl_buffer (mem, sink->display, &sink->video_info); @@ -2293,7 +2411,6 @@ no_window_size: ret = GST_FLOW_ERROR; goto done; } -#endif no_buffer: { GST_WARNING_OBJECT (sink, "could not create buffer"); @@ -2311,6 +2428,7 @@ activate_failed: ret = GST_FLOW_ERROR; goto done; } +#endif done: { g_mutex_unlock (&sink->render_lock); diff --git a/ext/wayland/gstwaylandsink.h b/ext/wayland/gstwaylandsink.h index 1864329..58c1e11 100644 --- a/ext/wayland/gstwaylandsink.h +++ b/ext/wayland/gstwaylandsink.h @@ -80,8 +80,9 @@ struct _GstWaylandSink gboolean redraw_pending; GMutex render_lock; GstBuffer *last_buffer; - #ifdef TIZEN_FEATURE_WLSINK_ENHANCEMENT + GstBuffer *to_render; + GstBuffer *flush_gstbuf; /* Framerate numerator and denominator */ gint fps_n; gint fps_d; diff --git a/ext/wayland/wlbuffer.c b/ext/wayland/wlbuffer.c index 11e0e53..9ba1815 100644 --- a/ext/wayland/wlbuffer.c +++ b/ext/wayland/wlbuffer.c @@ -253,6 +253,8 @@ gst_buffer_add_wl_buffer (GstBuffer * gstbuffer, struct wl_buffer *wlbuffer, #ifdef TIZEN_FEATURE_WLSINK_ENHANCEMENT //need to contribute to upstream !! wl_proxy_set_queue ((struct wl_proxy *) self->wlbuffer, self->display->queue); #endif + /* called gstbuffer_disposed when the gstbuffer is disposed, + or the same gstbuffer is being overwritten by below api */ gst_mini_object_set_qdata ((GstMiniObject *) gstbuffer, gst_wl_buffer_qdata_quark (), self, (GDestroyNotify) gstbuffer_disposed); GST_LOG ("GstWlBuffer (%p)", self); diff --git a/ext/wayland/wlshmallocator.c b/ext/wayland/wlshmallocator.c index e6a8bd4..f1cbc45 100644 --- a/ext/wayland/wlshmallocator.c +++ b/ext/wayland/wlshmallocator.c @@ -128,6 +128,7 @@ gst_wl_tbm_dump_native_raw_video (GstWlDisplay * display, guint dump_count) if (!virtual_addr.ptr) { strerror_r (errno, err_str, sizeof (err_str)); GST_ERROR ("get tbm bo handle failed: %s(%d)", err_str, errno); + fclose (fp); return; } data = (gchar *) virtual_addr.ptr; @@ -279,7 +280,7 @@ gst_wl_shm_allocator_free (GstAllocator * allocator, GstMemory * memory) { GstWlShmMemory *shm_mem = (GstWlShmMemory *) memory; FUNCTION; - + GST_LOG ("shm_mem->fd(%d)", shm_mem->fd); if (shm_mem->fd != -1) close (shm_mem->fd); munmap (shm_mem->data, memory->maxsize); @@ -342,6 +343,13 @@ gst_is_wl_shm_memory (GstMemory * mem) return gst_memory_is_type (mem, GST_ALLOCATOR_WL_SHM); } +gboolean +gst_is_wl_memory (GstMemory * mem) +{ + FUNCTION; + return gst_memory_is_type (mem, GST_ALLOCATOR_WL_SHM); +} + struct wl_buffer * gst_wl_shm_memory_construct_wl_buffer (GstMemory * mem, GstWlDisplay * display, const GstVideoInfo * info) @@ -405,7 +413,7 @@ gst_wl_shm_memory_construct_wl_buffer (GstMemory * mem, GstWlDisplay * display, size = GST_VIDEO_INFO_SIZE (info); format = gst_video_format_to_wl_tbm_format (GST_VIDEO_INFO_FORMAT (info)); - g_return_val_if_fail (gst_is_wl_shm_memory (mem), NULL); + g_return_val_if_fail (gst_is_wl_memory (mem), NULL); g_return_val_if_fail (size <= mem->size, NULL); g_return_val_if_fail (shm_mem->fd != -1, NULL); @@ -448,7 +456,7 @@ gst_wl_shm_memory_construct_wl_buffer (GstMemory * mem, GstWlDisplay * display, stride = GST_VIDEO_INFO_PLANE_STRIDE (info, 0); size = GST_VIDEO_INFO_SIZE (info); format = gst_video_format_to_wl_shm_format (GST_VIDEO_INFO_FORMAT (info)); - g_return_val_if_fail (gst_is_wl_shm_memory (mem), NULL); + g_return_val_if_fail (gst_is_wl_memory (mem), NULL); g_return_val_if_fail (size <= mem->size, NULL); g_return_val_if_fail (shm_mem->fd != -1, NULL); @@ -460,8 +468,6 @@ gst_wl_shm_memory_construct_wl_buffer (GstMemory * mem, GstWlDisplay * display, wbuffer = wl_shm_pool_create_buffer (wl_pool, 0, width, height, stride, format); - close (shm_mem->fd); - shm_mem->fd = -1; wl_shm_pool_destroy (wl_pool); } display->buffer_width = width; diff --git a/ext/wayland/wlshmallocator.h b/ext/wayland/wlshmallocator.h index 3dd9dfa..c06b182 100644 --- a/ext/wayland/wlshmallocator.h +++ b/ext/wayland/wlshmallocator.h @@ -74,6 +74,7 @@ struct wl_buffer *gst_wl_shm_memory_construct_wl_buffer (GstMemory * mem, #ifdef TIZEN_FEATURE_WLSINK_ENHANCEMENT gint gst_wl_fwrite_data (gchar * file, gpointer data, guint size); +gboolean gst_is_wl_memory (GstMemory * mem); #endif G_END_DECLS #endif /* __GST_WL_SHM_ALLOCATOR_H__ */ -- 2.7.4