From: Nicholas Kazlauskas <nicholas.kazlaus...@amd.com>

[Why]
Color blending for NV12 formats is incorrect because we're using the
predefined SRGB degamma.

[How]
Calculate the correct input transfer function for degamma from the color
module depending on what the actual surface format is.

Signed-off-by: Nicholas Kazlauskas <nicholas.kazlaus...@amd.com>
Reviewed-by: Zhan Liu <zhan....@amd.com>
Acked-by: Rodrigo Siqueira <rodrigo.sique...@amd.com>
---
 .../amd/display/amdgpu_dm/amdgpu_dm_color.c   | 22 ++++++++++++++++---
 1 file changed, 19 insertions(+), 3 deletions(-)

diff --git a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_color.c 
b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_color.c
index 6b58761e4b04..d0554082f0dc 100644
--- a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_color.c
+++ b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_color.c
@@ -420,9 +420,21 @@ int amdgpu_dm_update_plane_color_mgmt(struct dm_crtc_state 
*crtc,
 {
        const struct drm_color_lut *degamma_lut;
        struct dc_plane_state *dc_plane_state = plane->dc_state;
+       enum dc_transfer_func_predefined tf = TRANSFER_FUNCTION_SRGB;
        uint32_t degamma_size;
        int r;
 
+       /* Get the correct base transfer function for implicit degamma. */
+       switch (dc_plane_state->format) {
+       case SURFACE_PIXEL_FORMAT_VIDEO_420_YCbCr:
+       case SURFACE_PIXEL_FORMAT_VIDEO_420_YCrCb:
+               /* DC doesn't have a transfer function for BT601 specifically. 
*/
+               tf = TRANSFER_FUNCTION_BT709;
+               break;
+       default:
+               break;
+       }
+
        if (crtc->cm_has_degamma) {
                degamma_lut = __extract_blob_lut(crtc->base.degamma_lut,
                                                 &degamma_size);
@@ -456,8 +468,7 @@ int amdgpu_dm_update_plane_color_mgmt(struct dm_crtc_state 
*crtc,
                 * map these to the atomic one instead.
                 */
                if (crtc->cm_is_degamma_srgb)
-                       dc_plane_state->in_transfer_func->tf =
-                               TRANSFER_FUNCTION_SRGB;
+                       dc_plane_state->in_transfer_func->tf = tf;
                else
                        dc_plane_state->in_transfer_func->tf =
                                TRANSFER_FUNCTION_LINEAR;
@@ -472,7 +483,12 @@ int amdgpu_dm_update_plane_color_mgmt(struct dm_crtc_state 
*crtc,
                 * in linear space. Assume that the input is sRGB.
                 */
                dc_plane_state->in_transfer_func->type = TF_TYPE_PREDEFINED;
-               dc_plane_state->in_transfer_func->tf = TRANSFER_FUNCTION_SRGB;
+               dc_plane_state->in_transfer_func->tf = tf;
+
+               if (tf != TRANSFER_FUNCTION_SRGB &&
+                   !mod_color_calculate_degamma_params(
+                           dc_plane_state->in_transfer_func, NULL, false))
+                       return -ENOMEM;
        } else {
                /* ...Otherwise we can just bypass the DGM block. */
                dc_plane_state->in_transfer_func->type = TF_TYPE_BYPASS;
-- 
2.26.0

_______________________________________________
amd-gfx mailing list
amd-gfx@lists.freedesktop.org
https://lists.freedesktop.org/mailman/listinfo/amd-gfx

Reply via email to