drm/amd/display: Use drm_connector in create_stream_for_sink
authorHarry Wentland <harry.wentland@amd.com>
Fri, 1 Dec 2023 13:25:27 +0000 (06:25 -0700)
committerAlex Deucher <alexander.deucher@amd.com>
Wed, 6 Dec 2023 20:22:35 +0000 (15:22 -0500)
[WHAT]
We need to use this function for both amdgpu_dm_connectors
and drm_writeback_connectors. Modify it to operate on
a drm_connector as a common base.

Tested-by: Daniel Wheeler <daniel.wheeler@amd.com>
Reviewed-by: Alex Hung <alex.hung@amd.com>
Signed-off-by: Harry Wentland <harry.wentland@amd.com>
Signed-off-by: Alex Hung <alex.hung@amd.com>
Signed-off-by: Alex Deucher <alexander.deucher@amd.com>
drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c

index 5c89a043ac106acfecaf962492d5f9dbc25d5897..46477192265ee985a09a0d930464578043e7f132 100644 (file)
@@ -5558,6 +5558,7 @@ static void fill_stream_properties_from_drm_display_mode(
                        && stream->signal == SIGNAL_TYPE_HDMI_TYPE_A)
                timing_out->pixel_encoding = PIXEL_ENCODING_YCBCR420;
        else if (drm_mode_is_420_also(info, mode_in)
+                       && aconnector
                        && aconnector->force_yuv420_output)
                timing_out->pixel_encoding = PIXEL_ENCODING_YCBCR420;
        else if ((connector->display_info.color_formats & DRM_COLOR_FORMAT_YCBCR444)
@@ -5593,7 +5594,7 @@ static void fill_stream_properties_from_drm_display_mode(
                timing_out->hdmi_vic = hv_frame.vic;
        }
 
-       if (is_freesync_video_mode(mode_in, aconnector)) {
+       if (aconnector && is_freesync_video_mode(mode_in, aconnector)) {
                timing_out->h_addressable = mode_in->hdisplay;
                timing_out->h_total = mode_in->htotal;
                timing_out->h_sync_width = mode_in->hsync_end - mode_in->hsync_start;
@@ -6070,14 +6071,14 @@ static void apply_dsc_policy_for_stream(struct amdgpu_dm_connector *aconnector,
 }
 
 static struct dc_stream_state *
-create_stream_for_sink(struct amdgpu_dm_connector *aconnector,
+create_stream_for_sink(struct drm_connector *connector,
                       const struct drm_display_mode *drm_mode,
                       const struct dm_connector_state *dm_state,
                       const struct dc_stream_state *old_stream,
                       int requested_bpc)
 {
+       struct amdgpu_dm_connector *aconnector = NULL;
        struct drm_display_mode *preferred_mode = NULL;
-       struct drm_connector *drm_connector;
        const struct drm_connector_state *con_state = &dm_state->base;
        struct dc_stream_state *stream = NULL;
        struct drm_display_mode mode;
@@ -6096,20 +6097,22 @@ create_stream_for_sink(struct amdgpu_dm_connector *aconnector,
        drm_mode_init(&mode, drm_mode);
        memset(&saved_mode, 0, sizeof(saved_mode));
 
-       if (aconnector == NULL) {
-               DRM_ERROR("aconnector is NULL!\n");
+       if (connector == NULL) {
+               DRM_ERROR("connector is NULL!\n");
                return stream;
        }
 
-       drm_connector = &aconnector->base;
-
-       if (!aconnector->dc_sink) {
-               sink = create_fake_sink(aconnector);
-               if (!sink)
-                       return stream;
-       } else {
-               sink = aconnector->dc_sink;
-               dc_sink_retain(sink);
+       if (connector->connector_type != DRM_MODE_CONNECTOR_WRITEBACK) {
+               aconnector = NULL;
+               aconnector = to_amdgpu_dm_connector(connector);
+               if (!aconnector->dc_sink) {
+                       sink = create_fake_sink(aconnector);
+                       if (!sink)
+                               return stream;
+               } else {
+                       sink = aconnector->dc_sink;
+                       dc_sink_retain(sink);
+               }
        }
 
        stream = dc_create_stream_for_sink(sink);
@@ -6119,12 +6122,13 @@ create_stream_for_sink(struct amdgpu_dm_connector *aconnector,
                goto finish;
        }
 
+       /* We leave this NULL for writeback connectors */
        stream->dm_stream_context = aconnector;
 
        stream->timing.flags.LTE_340MCSC_SCRAMBLE =
-               drm_connector->display_info.hdmi.scdc.scrambling.low_rates;
+               connector->display_info.hdmi.scdc.scrambling.low_rates;
 
-       list_for_each_entry(preferred_mode, &aconnector->base.modes, head) {
+       list_for_each_entry(preferred_mode, &connector->modes, head) {
                /* Search for preferred mode */
                if (preferred_mode->type & DRM_MODE_TYPE_PREFERRED) {
                        native_mode_found = true;
@@ -6133,7 +6137,7 @@ create_stream_for_sink(struct amdgpu_dm_connector *aconnector,
        }
        if (!native_mode_found)
                preferred_mode = list_first_entry_or_null(
-                               &aconnector->base.modes,
+                               &connector->modes,
                                struct drm_display_mode,
                                head);
 
@@ -6147,7 +6151,7 @@ create_stream_for_sink(struct amdgpu_dm_connector *aconnector,
                 * and the modelist may not be filled in time.
                 */
                DRM_DEBUG_DRIVER("No preferred mode found\n");
-       } else {
+       } else if (aconnector) {
                recalculate_timing = is_freesync_video_mode(&mode, aconnector);
                if (recalculate_timing) {
                        freesync_mode = get_highest_refresh_rate_mode(aconnector, false);
@@ -6170,13 +6174,17 @@ create_stream_for_sink(struct amdgpu_dm_connector *aconnector,
         */
        if (!scale || mode_refresh != preferred_refresh)
                fill_stream_properties_from_drm_display_mode(
-                       stream, &mode, &aconnector->base, con_state, NULL,
+                       stream, &mode, connector, con_state, NULL,
                        requested_bpc);
        else
                fill_stream_properties_from_drm_display_mode(
-                       stream, &mode, &aconnector->base, con_state, old_stream,
+                       stream, &mode, connector, con_state, old_stream,
                        requested_bpc);
 
+       /* The rest isn't needed for writeback connectors */
+       if (!aconnector)
+               goto finish;
+
        if (aconnector->timing_changed) {
                drm_dbg(aconnector->base.dev,
                        "overriding timing for automated test, bpc %d, changing to %d\n",
@@ -6194,7 +6202,7 @@ create_stream_for_sink(struct amdgpu_dm_connector *aconnector,
 
        fill_audio_info(
                &stream->audio_info,
-               drm_connector,
+               connector,
                sink);
 
        update_stream_signal(stream, sink);
@@ -6662,7 +6670,7 @@ create_validate_stream_for_sink(struct amdgpu_dm_connector *aconnector,
        enum dc_status dc_result = DC_OK;
 
        do {
-               stream = create_stream_for_sink(aconnector, drm_mode,
+               stream = create_stream_for_sink(connector, drm_mode,
                                                dm_state, old_stream,
                                                requested_bpc);
                if (stream == NULL) {
@@ -9418,15 +9426,16 @@ static int dm_update_crtc_state(struct amdgpu_display_manager *dm,
        dm_new_crtc_state = to_dm_crtc_state(new_crtc_state);
        acrtc = to_amdgpu_crtc(crtc);
        connector = amdgpu_dm_find_first_crtc_matching_connector(state, crtc);
-       aconnector = to_amdgpu_dm_connector(connector);
+       if (connector && connector->connector_type != DRM_MODE_CONNECTOR_WRITEBACK)
+               aconnector = to_amdgpu_dm_connector(connector);
 
        /* TODO This hack should go away */
-       if (aconnector && enable) {
+       if (connector && enable) {
                /* Make sure fake sink is created in plug-in scenario */
                drm_new_conn_state = drm_atomic_get_new_connector_state(state,
-                                                           &aconnector->base);
+                                                                       connector);
                drm_old_conn_state = drm_atomic_get_old_connector_state(state,
-                                                           &aconnector->base);
+                                                                       connector);
 
                if (IS_ERR(drm_new_conn_state)) {
                        ret = PTR_ERR_OR_ZERO(drm_new_conn_state);
@@ -9573,7 +9582,7 @@ static int dm_update_crtc_state(struct amdgpu_display_manager *dm,
                 * added MST connectors not found in existing crtc_state in the chained mode
                 * TODO: need to dig out the root cause of that
                 */
-               if (!aconnector)
+               if (!connector)
                        goto skip_modeset;
 
                if (modereset_required(new_crtc_state))
@@ -9616,7 +9625,7 @@ skip_modeset:
         * We want to do dc stream updates that do not require a
         * full modeset below.
         */
-       if (!(enable && aconnector && new_crtc_state->active))
+       if (!(enable && connector && new_crtc_state->active))
                return 0;
        /*
         * Given above conditions, the dc state cannot be NULL because: