e_hwc_window_queue: Fix overwriting to the queue buffer of target queue 94/318594/1
authorChangyeon Lee <cyeon.lee@samsung.com>
Mon, 20 Jan 2025 08:17:26 +0000 (17:17 +0900)
committerTizen Window System <tizen.windowsystem@gmail.com>
Tue, 21 Jan 2025 03:10:25 +0000 (12:10 +0900)
Do not change queue state to unset until all buffers drawn by client
have been released even if queue is target.

Fetch null buffer if client is deleted and exported buffer is destroyed
for unreferencing the queue buffer.

Change-Id: Ib6c7fd304ad7b25199244c2a15f41bbcd081bddb

src/bin/displaymgr/e_hwc_window.c
src/bin/displaymgr/e_hwc_window_queue.c
src/bin/displaymgr/e_hwc_window_queue_intern.h

index 2cb6a7856615bfe2af9e346d52b4d2022cbf63a2..1bcdf43a50d16d26088fa8482840aad002f10b0b 100644 (file)
@@ -829,6 +829,7 @@ _e_hwc_window_del(E_Hwc_Window *hwc_window)
    e_hwc_window_state_set(hwc_window, E_HWC_WINDOW_STATE_NONE, EINA_TRUE);
 
    e_hwc_window_changed_set(hwc_window, E_HWC_WINS_CHANGED_WIN_VISIBLE);
+   e_hwc_window_changed_set(hwc_window, E_HWC_WINS_CHANGED_WIN_BUFFER);
 
    e_object_del(E_OBJECT(hwc_window));
 }
@@ -1194,6 +1195,7 @@ _e_hwc_window_client_cb_del(void *data EINA_UNUSED, E_Client *ec)
 
    e_hwc_window_restriction_set(hwc_window, E_HWC_WINDOW_RESTRICTION_DELETED);
    e_hwc_window_client_type_override(hwc_window);
+   e_hwc_window_changed_set(hwc_window, E_HWC_WINS_CHANGED_WIN_BUFFER);
 }
 
 static void
index c6491df00628efcca0711f6c90cae4b0d9b3db53..a6cf7ee98e73110a7b65afa2a645f338810ae98a 100644 (file)
@@ -513,6 +513,9 @@ _e_hwc_window_queue_exported_buffer_destroy_cb(struct wl_listener *listener, voi
            queue_buffer->tsurface, queue->tqueue,
            queue_buffer->exported_wl_buffer);
 
+   if (hwc_window)
+     e_hwc_window_changed_set(hwc_window, E_HWC_WINS_CHANGED_WIN_BUFFER);
+
    if (queue_buffer->reseted)
      {
         queue->buffers = eina_list_remove(queue->buffers, queue_buffer);
@@ -737,7 +740,7 @@ _e_hwc_window_queue_buffers_retrieve_done(E_Hwc_Window_Queue *queue)
         if (queue_buffer->copying)
           return EINA_FALSE;
 
-        if ((!queue->is_target) && (queue_buffer->acquired))
+        if ((queue_buffer->internal_enqueued) && (queue_buffer->acquired))
           return EINA_FALSE;
      }
 
@@ -1697,7 +1700,9 @@ _e_hwc_window_queue_cb_buffer_change(void *data, E_Client *ec)
 
    hwc_window = ec->hwc_window;
    if (!hwc_window) return;
-   if ((ec->exp_iconify.buffer_flush) && (e_policy_visibility_client_is_iconic(ec)))
+   if ((!e_view_client_visible_get(e_client_view_get(ec))) &&
+       (ec->exp_iconify.buffer_flush) &&
+       (e_policy_visibility_client_is_iconic(ec)))
      return;
 
    _e_hwc_window_queue_copy_thread_check_and_run(hwc_window);
@@ -2221,6 +2226,7 @@ e_hwc_window_queue_buffer_enqueue(E_Hwc_Window_Queue *queue, E_Hwc_Window_Queue_
    if (!queue->tqueue) return EINA_FALSE;
 
    queue_buffer->dequeued = EINA_FALSE;
+   queue_buffer->internal_enqueued = EINA_TRUE;
 
    user = queue->user;
    EHWQTRACE("ENQ ts:%p tq:%p",
@@ -2304,6 +2310,7 @@ e_hwc_window_queue_buffer_release(E_Hwc_Window_Queue *queue, E_Hwc_Window_Queue_
    queue_buffer->released = EINA_TRUE;
    queue_buffer->dequeued = EINA_FALSE;
    queue_buffer->acquired = EINA_FALSE;
+   queue_buffer->internal_enqueued = EINA_FALSE;
 
    if (queue->type == E_HWC_WINDOW_QUEUE_TYPE_GBM_SURFACE)
      {
@@ -2331,8 +2338,7 @@ e_hwc_window_queue_buffer_release(E_Hwc_Window_Queue *queue, E_Hwc_Window_Queue_
                        NULL, NULL, queue, queue_buffer, queue_buffer->tsurface);
           }
 
-        if ((!queue->is_target) &&
-            (queue->state == E_HWC_WINDOW_QUEUE_STATE_UNSET_WAITING))
+        if (queue->state == E_HWC_WINDOW_QUEUE_STATE_UNSET_WAITING)
           {
              if (_e_hwc_window_queue_buffers_retrieve_done(queue))
                _e_hwc_window_queue_unset(queue);
@@ -2432,6 +2438,15 @@ e_hwc_window_queue_buffer_reference(E_Hwc_Window_Queue_Buffer_Ref *ref, E_Hwc_Wi
                         EHWQINF("Wait detach ts:%p tq:%p", NULL, NULL, ref->buffer->queue,
                                 ref->buffer->tsurface, ref->buffer->queue->tqueue);
                      }
+                   else if ((ref->buffer->queue->state == E_HWC_WINDOW_QUEUE_STATE_UNSET_WAITING) &&
+                            (ref->buffer->copying))
+                     {
+                        ref->buffer->acquired = EINA_FALSE;
+                        ref->buffer->dequeued = EINA_TRUE;
+
+                        EHWQINF("Wait copying ts:%p tq:%p", NULL, NULL, ref->buffer->queue,
+                                ref->buffer->tsurface, ref->buffer->queue->tqueue);
+                     }
                    else
                      {
                         e_hwc_window_queue_buffer_release(ref->buffer->queue, ref->buffer);
@@ -2575,11 +2590,11 @@ e_hwc_window_queue_debug_info_get(Eldbus_Message_Iter *iter)
           {
              snprintf(info_str, sizeof(info_str),
                       " └─ [%2d] Queue_Buffer(%8p) tsurface(%8p) exported_wl_buffer(%u)"
-                      " exported(%d) usable(%d) released(%d) acquired(%d) dequeued(%d) copying(%d)",
+                      " exported(%d) usable(%d) released(%d) acquired(%d) dequeued(%d) copying(%d) internal_enqueued(%d)",
                       ++buf_idx, queue_buffer, queue_buffer->tsurface,
                       queue_buffer->exported_wl_buffer ? wl_resource_get_id(queue_buffer->exported_wl_buffer) : 0,
                       queue_buffer->exported, queue_buffer->usable, queue_buffer->released,
-                      queue_buffer->acquired, queue_buffer->dequeued, queue_buffer->copying);
+                      queue_buffer->acquired, queue_buffer->dequeued, queue_buffer->copying, queue_buffer->internal_enqueued);
              eldbus_message_iter_basic_append(line_array, 's', info_str);
           }
         eldbus_message_iter_basic_append(line_array, 's', "");
index 102413ea0feaab880c8d870e226b65eb3e81c582..897102b2ad28269440b30c403546548058f3ca64 100644 (file)
@@ -62,6 +62,7 @@ struct _E_Hwc_Window_Queue_Buffer
    struct wl_resource            *exported_wl_buffer;
    struct wl_listener             exported_destroy_listener;
    Eina_Bool                      exported;
+   Eina_Bool                      internal_enqueued;
    Eina_Bool                      usable;
    Eina_Bool                      released;
    Eina_Bool                      acquired;