hwc: support multiple overlay layer 60/298160/2
authorChangyeon Lee <cyeon.lee@samsung.com>
Wed, 30 Aug 2023 11:54:16 +0000 (20:54 +0900)
committerChangyeon Lee <cyeon.lee@samsung.com>
Tue, 5 Sep 2023 02:38:27 +0000 (11:38 +0900)
Change-Id: I3033c586c6bda4b99a12a41292e02e962ad689f7

src/tdm_backend_vc4_types.h
src/tdm_vc4_display.c
src/tdm_vc4_hwc.c

index 9dd9aa5..07bab68 100644 (file)
@@ -189,8 +189,9 @@ struct _tdm_vc4_output {
        unsigned int connector_type_id;
        struct list_head layer_list;
        tdm_vc4_layer *primary_layer;
-       tdm_vc4_layer *overlay_layer;
+       int overlay_layer_count;
        tdm_vc4_layer *cursor_layer;
+       int layer_count;
 
        /* not fixed data below */
        hal_tdm_output_vblank_handler vblank_func;
index 6665ed6..39656e8 100644 (file)
@@ -612,9 +612,6 @@ _tdm_vc4_display_create_layer_list_type(tdm_vc4_display *display_data)
                                if (type == DRM_PLANE_TYPE_CURSOR) {
                                        if (output_data->cursor_layer)
                                                continue;
-                               } else if (type == DRM_PLANE_TYPE_OVERLAY)  {
-                                       if (output_data->overlay_layer)
-                                               continue;
                                } else if (type == DRM_PLANE_TYPE_PRIMARY) {
                                        if (output_data->primary_layer)
                                                continue;
@@ -640,17 +637,20 @@ _tdm_vc4_display_create_layer_list_type(tdm_vc4_display *display_data)
                if (type == DRM_PLANE_TYPE_CURSOR) {
                        layer_data->capabilities = TDM_VC4_LAYER_CAPABILITY_CURSOR |
                                                                           TDM_VC4_LAYER_CAPABILITY_GRAPHIC;
-                       layer_data->zpos = 2;
+                       layer_data->zpos = output_data->layer_count;
+                       output_data->layer_count++;
                        output_data->cursor_layer = layer_data;
                } else if (type == DRM_PLANE_TYPE_OVERLAY) {
                        layer_data->capabilities = TDM_VC4_LAYER_CAPABILITY_OVERLAY |
                                                                           TDM_VC4_LAYER_CAPABILITY_GRAPHIC;
-                       layer_data->zpos = 1;
-                       output_data->overlay_layer = layer_data;
+                       layer_data->zpos = output_data->layer_count;
+                       output_data->layer_count++;
+                       output_data->overlay_layer_count++;
                } else if (type == DRM_PLANE_TYPE_PRIMARY) {
                        layer_data->capabilities = TDM_VC4_LAYER_CAPABILITY_PRIMARY |
                                                                           TDM_VC4_LAYER_CAPABILITY_GRAPHIC;
-                       layer_data->zpos = 0;
+                       layer_data->zpos = output_data->layer_count;
+                       output_data->layer_count++;
                        output_data->primary_layer = layer_data;
                } else {
                        drmModeFreePlane(plane);
index bfc3504..e2d3476 100644 (file)
@@ -35,16 +35,8 @@ SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
 #include "tdm_backend_vc4.h"
 #include <pixman.h>
 
-#define NUM_LAYERS     4
 #define NUM_BUFFERS    3
 
-#define NUM_UI_LAYERS  2
-
-#define ZPOS_MAX       3
-#define ZPOS_CURSOR    2
-#define ZPOS_1         1
-#define ZPOS_0         0
-#define ZPOS_VIDEO1    0
 #define ZPOS_NONE      -999
 
 tbm_format hwc_window_video_formats[] = {
@@ -474,11 +466,15 @@ static hal_tdm_error
 _vc4_hwc_prepare_commit(tdm_vc4_hwc *hwc_data)
 {
        tdm_vc4_hwc_window *hwc_window_data = NULL;
+       tdm_vc4_output *output_data = hwc_data->output_data;
        tdm_vc4_layer *layer_data = NULL;
-       tdm_vc4_hwc_window *use_layer_windows[NUM_LAYERS] = {NULL, };
+       tdm_vc4_hwc_window **use_layer_windows;
        int lzpos = 0;
        int cursor_enabled = 0;
 
+       use_layer_windows = calloc(output_data->layer_count, sizeof(tdm_vc4_hwc_window *));
+       if (!use_layer_windows) return HAL_TDM_ERROR_OUT_OF_MEMORY;
+
        /* set target hwc window to the layer */
        hwc_data->target_hwc_window->attach_buffer_changed = 0;
        if (hwc_data->need_target_window)
@@ -506,7 +502,7 @@ _vc4_hwc_prepare_commit(tdm_vc4_hwc *hwc_data)
        }
 
        /* unset the unused layers */
-       for (lzpos = 0; lzpos < NUM_LAYERS; lzpos++) {
+       for (lzpos = 0; lzpos < output_data->layer_count; lzpos++) {
                layer_data = tdm_vc4_output_get_layer_data(hwc_data->output_data, lzpos);
                if (!layer_data)
                        continue;
@@ -518,9 +514,11 @@ _vc4_hwc_prepare_commit(tdm_vc4_hwc *hwc_data)
                _vc4_hwc_cursor_buffer_unset(hwc_data);
 
        /* for debug */
-       for (lzpos = NUM_LAYERS -1 ; lzpos >= 0; lzpos--)
+       for (lzpos = output_data->layer_count -1 ; lzpos >= 0; lzpos--)
                TDM_BACKEND_DBG(" lzpos(%d) : %s", lzpos, use_layer_windows[lzpos] ? "SET" : "UNSET");
 
+       free(use_layer_windows);
+
        return HAL_TDM_ERROR_NONE;
 }
 
@@ -530,18 +528,18 @@ _vc4_hwc_prepare_commit(tdm_vc4_hwc *hwc_data)
 static void
 _vc4_hwc_apply_policy(tdm_vc4_hwc *hwc_data , hal_tdm_hwc_window **composited_wnds, uint32_t num_wnds)
 {
+       tdm_vc4_output *output_data = hwc_data->output_data;
        tdm_vc4_hwc_window *hwc_window_data = NULL;
        tdm_vc4_hwc_window **composited_list = NULL;
-       int client_count = 0;
-       int device_count = 0;
-       int video_count = 0;
-       int cursor_count = 0;
-       int ui_lzpos_top = ZPOS_1;
-       int ui_lzpos_bottom = ZPOS_0;
-       int num_ui_layers = NUM_UI_LAYERS;
+       int client_count = 0, device_count = 0, video_count = 0, cursor_count = 0;
+       int ui_lzpos_top = 0, ui_lzpos_bottom = 0, num_ui_layers = 0, video_lzpos_top = 0;
        int set_clients_below = 0;
        int i = 0;
 
+       num_ui_layers = output_data->overlay_layer_count + 1;
+       ui_lzpos_top = output_data->overlay_layer_count;
+       ui_lzpos_bottom = 0;
+
        composited_list = (tdm_vc4_hwc_window **)composited_wnds;
 
        /* initialize the need_target_window */
@@ -566,9 +564,9 @@ _vc4_hwc_apply_policy(tdm_vc4_hwc *hwc_data , hal_tdm_hwc_window **composited_wn
                case HAL_TDM_HWC_WIN_COMPOSITION_VIDEO:
                        composited_list[i]->validated_type = HAL_TDM_HWC_WIN_COMPOSITION_VIDEO;
                        video_count++;
-                       num_ui_layers--;
                        continue;
                case HAL_TDM_HWC_WIN_COMPOSITION_CURSOR:
+                       if (!output_data->cursor_layer) break;
                        if (set_clients_below) break;
                        if (cursor_count > 0) break;
 
@@ -594,19 +592,19 @@ _vc4_hwc_apply_policy(tdm_vc4_hwc *hwc_data , hal_tdm_hwc_window **composited_wn
        }
 
        /* 2. check need target window and set ui_lzpos top and bottom */
-       num_ui_layers = NUM_UI_LAYERS;
+       num_ui_layers = output_data->overlay_layer_count + 1;
 
        if (video_count > 0) {
-               ui_lzpos_bottom++;
-               num_ui_layers--;
+               ui_lzpos_bottom += video_count;
+               num_ui_layers -= video_count;
+               video_lzpos_top = video_count - 1;
        }
 
-       if ((client_count > 0) ||
-               ((video_count > 0) && (device_count == NUM_UI_LAYERS))) {
+       if ((client_count > 0) || (device_count > num_ui_layers)) {
+               hwc_data->need_target_window = 1;
+               hwc_data->target_hwc_window->lzpos = ui_lzpos_bottom;
                ui_lzpos_bottom++;
                num_ui_layers--;
-               hwc_data->need_target_window = 1;
-               hwc_data->target_hwc_window->lzpos = ui_lzpos_bottom - 1;
        }
 
        if (num_ui_layers > device_count)
@@ -616,10 +614,12 @@ _vc4_hwc_apply_policy(tdm_vc4_hwc *hwc_data , hal_tdm_hwc_window **composited_wn
        for (i = 0; i < num_wnds; i++) {
                switch (composited_list[i]->validated_type) {
                case HAL_TDM_HWC_WIN_COMPOSITION_VIDEO:
-                       composited_list[i]->lzpos = ZPOS_VIDEO1;
+                       composited_list[i]->lzpos = video_lzpos_top;
+                       video_lzpos_top--;
                        continue;
                case HAL_TDM_HWC_WIN_COMPOSITION_CURSOR:
-                       composited_list[i]->lzpos = ZPOS_CURSOR;
+                       if (!output_data->cursor_layer) break;
+                       composited_list[i]->lzpos = output_data->cursor_layer->zpos;
                        continue;
                case HAL_TDM_HWC_WIN_COMPOSITION_DEVICE:
                        if (num_ui_layers <= 0) break;
@@ -859,7 +859,7 @@ vc4_hwc_validate(hal_tdm_hwc *hwc, hal_tdm_hwc_window **composited_wnds, uint32_
                        composited_list[i]->validated_type = HAL_TDM_HWC_WIN_COMPOSITION_CLIENT;
                }
                hwc_data->need_target_window = 1;
-               hwc_data->target_hwc_window->lzpos = ZPOS_0;
+               hwc_data->target_hwc_window->lzpos = 0;
        } else {
                _vc4_hwc_apply_policy(hwc_data, composited_wnds, num_wnds);
        }