]> git.ipfire.org Git - thirdparty/kernel/linux.git/commitdiff
drm/amd/display: Add opp count validation to dml2.1
authorDmytro Laktyushkin <dmytro.laktyushkin@amd.com>
Tue, 14 Oct 2025 17:05:26 +0000 (13:05 -0400)
committerAlex Deucher <alexander.deucher@amd.com>
Tue, 28 Oct 2025 13:57:27 +0000 (09:57 -0400)
Newer asics can have mismatching dpp and opp counts and
dml needs to account for this.

Reviewed-by: Charlene Liu <charlene.liu@amd.com>
Signed-off-by: Dmytro Laktyushkin <dmytro.laktyushkin@amd.com>
Signed-off-by: Wayne Lin <wayne.lin@amd.com>
Tested-by: Dan Wheeler <daniel.wheeler@amd.com>
Signed-off-by: Alex Deucher <alexander.deucher@amd.com>
drivers/gpu/drm/amd/display/dc/dml2/dml21/src/dml2_core/dml2_core_dcn4.c
drivers/gpu/drm/amd/display/dc/dml2/dml21/src/dml2_core/dml2_core_dcn4_calcs.c
drivers/gpu/drm/amd/display/dc/dml2/dml21/src/dml2_core/dml2_core_shared_types.h

index 6ee37386f6728e24275730d25d1aba5c0cd4b480..eba948e187c1163648527fbfd1db261d0d1c5e93 100644 (file)
@@ -28,6 +28,7 @@ struct dml2_core_ip_params core_dcn4_ip_caps_base = {
        .writeback_interface_buffer_size_kbytes = 90,
        //Number of pipes after DCN Pipe harvesting
        .max_num_dpp = 4,
+       .max_num_opp = 4,
        .max_num_otg = 4,
        .max_num_wb = 1,
        .max_dchub_pscl_bw_pix_per_clk = 4,
index 4ccdb179b001d23d3cce034506b62456fa42ecab..f16792f79befae3dea07fdf4db4f02c5c1a9612c 100644 (file)
@@ -4047,7 +4047,9 @@ static bool ValidateODMMode(enum dml2_odm_mode ODMMode,
        bool UseDSC,
        unsigned int NumberOfDSCSlices,
        unsigned int TotalNumberOfActiveDPP,
+       unsigned int TotalNumberOfActiveOPP,
        unsigned int MaxNumDPP,
+       unsigned int MaxNumOPP,
        double DISPCLKRequired,
        unsigned int NumberOfDPPRequired,
        unsigned int MaxHActiveForDSC,
@@ -4063,7 +4065,7 @@ static bool ValidateODMMode(enum dml2_odm_mode ODMMode,
 
        if (DISPCLKRequired > MaxDispclk)
                return false;
-       if ((TotalNumberOfActiveDPP + NumberOfDPPRequired) > MaxNumDPP)
+       if ((TotalNumberOfActiveDPP + NumberOfDPPRequired) > MaxNumDPP || (TotalNumberOfActiveOPP + NumberOfDPPRequired) > MaxNumOPP)
                return false;
        if (are_odm_segments_symmetrical) {
                if (HActive % (NumberOfDPPRequired * pixels_per_clock_cycle))
@@ -4109,7 +4111,9 @@ static noinline_for_stack void CalculateODMMode(
        double MaxDispclk,
        bool DSCEnable,
        unsigned int TotalNumberOfActiveDPP,
+       unsigned int TotalNumberOfActiveOPP,
        unsigned int MaxNumDPP,
+       unsigned int MaxNumOPP,
        double PixelClock,
        unsigned int NumberOfDSCSlices,
 
@@ -4179,7 +4183,9 @@ static noinline_for_stack void CalculateODMMode(
                        UseDSC,
                        NumberOfDSCSlices,
                        TotalNumberOfActiveDPP,
+                       TotalNumberOfActiveOPP,
                        MaxNumDPP,
+                       MaxNumOPP,
                        DISPCLKRequired,
                        NumberOfDPPRequired,
                        MaxHActiveForDSC,
@@ -8358,6 +8364,7 @@ static bool dml_core_mode_support(struct dml2_core_calcs_mode_support_ex *in_out
        CalculateSwathAndDETConfiguration(&mode_lib->scratch, CalculateSwathAndDETConfiguration_params);
 
        mode_lib->ms.TotalNumberOfActiveDPP = 0;
+       mode_lib->ms.TotalNumberOfActiveOPP = 0;
        mode_lib->ms.support.TotalAvailablePipesSupport = true;
 
        for (k = 0; k < mode_lib->ms.num_active_planes; ++k) {
@@ -8393,7 +8400,9 @@ static bool dml_core_mode_support(struct dml2_core_calcs_mode_support_ex *in_out
                        mode_lib->ms.max_dispclk_freq_mhz,
                        false, // DSCEnable
                        mode_lib->ms.TotalNumberOfActiveDPP,
+                       mode_lib->ms.TotalNumberOfActiveOPP,
                        mode_lib->ip.max_num_dpp,
+                       mode_lib->ip.max_num_opp,
                        ((double)display_cfg->stream_descriptors[display_cfg->plane_descriptors[k].stream_index].timing.pixel_clock_khz / 1000),
                        mode_lib->ms.support.NumberOfDSCSlices[k],
 
@@ -8412,7 +8421,9 @@ static bool dml_core_mode_support(struct dml2_core_calcs_mode_support_ex *in_out
                        mode_lib->ms.max_dispclk_freq_mhz,
                        true, // DSCEnable
                        mode_lib->ms.TotalNumberOfActiveDPP,
+                       mode_lib->ms.TotalNumberOfActiveOPP,
                        mode_lib->ip.max_num_dpp,
+                       mode_lib->ip.max_num_opp,
                        ((double)display_cfg->stream_descriptors[display_cfg->plane_descriptors[k].stream_index].timing.pixel_clock_khz / 1000),
                        mode_lib->ms.support.NumberOfDSCSlices[k],
 
@@ -8516,20 +8527,23 @@ static bool dml_core_mode_support(struct dml2_core_calcs_mode_support_ex *in_out
        for (k = 0; k < mode_lib->ms.num_active_planes; ++k) {
                mode_lib->ms.MPCCombine[k] = false;
                mode_lib->ms.NoOfDPP[k] = 1;
+               mode_lib->ms.NoOfOPP[k] = 1;
 
                if (mode_lib->ms.ODMMode[k] == dml2_odm_mode_combine_4to1) {
                        mode_lib->ms.MPCCombine[k] = false;
                        mode_lib->ms.NoOfDPP[k] = 4;
+                       mode_lib->ms.NoOfOPP[k] = 4;
                } else if (mode_lib->ms.ODMMode[k] == dml2_odm_mode_combine_3to1) {
                        mode_lib->ms.MPCCombine[k] = false;
                        mode_lib->ms.NoOfDPP[k] = 3;
+                       mode_lib->ms.NoOfOPP[k] = 3;
                } else if (mode_lib->ms.ODMMode[k] == dml2_odm_mode_combine_2to1) {
                        mode_lib->ms.MPCCombine[k] = false;
                        mode_lib->ms.NoOfDPP[k] = 2;
+                       mode_lib->ms.NoOfOPP[k] = 2;
                } else if (display_cfg->plane_descriptors[k].overrides.mpcc_combine_factor == 2) {
                        mode_lib->ms.MPCCombine[k] = true;
                        mode_lib->ms.NoOfDPP[k] = 2;
-                       mode_lib->ms.TotalNumberOfActiveDPP++;
                } else if (display_cfg->plane_descriptors[k].overrides.mpcc_combine_factor == 1) {
                        mode_lib->ms.MPCCombine[k] = false;
                        mode_lib->ms.NoOfDPP[k] = 1;
@@ -8540,7 +8554,6 @@ static bool dml_core_mode_support(struct dml2_core_calcs_mode_support_ex *in_out
                        if ((mode_lib->ms.MinDPPCLKUsingSingleDPP[k] > mode_lib->ms.max_dppclk_freq_mhz) || !mode_lib->ms.SingleDPPViewportSizeSupportPerSurface[k]) {
                                mode_lib->ms.MPCCombine[k] = true;
                                mode_lib->ms.NoOfDPP[k] = 2;
-                               mode_lib->ms.TotalNumberOfActiveDPP++;
                        }
                }
 #if defined(__DML_VBA_DEBUG__)
@@ -8548,8 +8561,16 @@ static bool dml_core_mode_support(struct dml2_core_calcs_mode_support_ex *in_out
 #endif
        }
 
+       mode_lib->ms.TotalNumberOfActiveDPP = 0;
+       mode_lib->ms.TotalNumberOfActiveOPP = 0;
+       for (k = 0; k < mode_lib->ms.num_active_planes; ++k) {
+               mode_lib->ms.TotalNumberOfActiveDPP += mode_lib->ms.NoOfDPP[k];
+               mode_lib->ms.TotalNumberOfActiveOPP += mode_lib->ms.NoOfOPP[k];
+       }
        if (mode_lib->ms.TotalNumberOfActiveDPP > (unsigned int)mode_lib->ip.max_num_dpp)
                mode_lib->ms.support.TotalAvailablePipesSupport = false;
+       if (mode_lib->ms.TotalNumberOfActiveOPP > (unsigned int)mode_lib->ip.max_num_opp)
+               mode_lib->ms.support.TotalAvailablePipesSupport = false;
 
 
        mode_lib->ms.TotalNumberOfSingleDPPSurfaces = 0;
index ff1c47347610a971e464a91fd5e45ddaeda7b39d..051c31ec2f0e4e5f957c1d3be3939b417a2e2f50 100644 (file)
@@ -36,6 +36,7 @@ struct dml2_core_ip_params {
        unsigned int max_line_buffer_lines;
        unsigned int writeback_interface_buffer_size_kbytes;
        unsigned int max_num_dpp;
+       unsigned int max_num_opp;
        unsigned int max_num_otg;
        unsigned int TDLUT_33cube_count;
        unsigned int max_num_wb;
@@ -570,6 +571,7 @@ struct dml2_core_internal_mode_support {
        enum dml2_odm_mode ODMMode[DML2_MAX_PLANES];
        unsigned int SurfaceSizeInMALL[DML2_MAX_PLANES];
        unsigned int NoOfDPP[DML2_MAX_PLANES];
+       unsigned int NoOfOPP[DML2_MAX_PLANES];
        bool MPCCombine[DML2_MAX_PLANES];
        double dcfclk_deepsleep;
        double MinDPPCLKUsingSingleDPP[DML2_MAX_PLANES];
@@ -580,6 +582,7 @@ struct dml2_core_internal_mode_support {
        bool PTEBufferSizeNotExceeded[DML2_MAX_PLANES];
        bool DCCMetaBufferSizeNotExceeded[DML2_MAX_PLANES];
        unsigned int TotalNumberOfActiveDPP;
+       unsigned int TotalNumberOfActiveOPP;
        unsigned int TotalNumberOfSingleDPPSurfaces;
        unsigned int TotalNumberOfDCCActiveDPP;
        unsigned int Total3dlutActive;