]> www.infradead.org Git - users/dwmw2/linux.git/commitdiff
drm/amd/display: fixed an error related to 4:2:0/4:2:2 DSC
authorGuo, Bing <Bing.Guo@amd.com>
Mon, 8 Nov 2021 22:17:46 +0000 (17:17 -0500)
committerAlex Deucher <alexander.deucher@amd.com>
Wed, 24 Nov 2021 19:06:52 +0000 (14:06 -0500)
[Why]
OPTC_BYTES_PER_PIXEL calculation for 4:2:2 and 4:2:0 could have error.

[How]
Change to use following formula:
OPTC_DSC_BYTES_PER_PIXEL = ceiling((chunk size * 2^28) / slice width)

v2: squash in 64 bit divide fix (Alex)

Reviewed-by: Wenjing Liu <Wenjing.Liu@amd.com>
Acked-by: Qingqing Zhuo <qingqing.zhuo@amd.com>
Signed-off-by: Bing Guo <Bing.Guo@amd.com>
Tested-by: Daniel Wheeler <daniel.wheeler@amd.com>
Signed-off-by: Alex Deucher <alexander.deucher@amd.com>
drivers/gpu/drm/amd/display/dc/dml/dsc/rc_calc_fpu.c
drivers/gpu/drm/amd/display/dc/dml/dsc/rc_calc_fpu.h
drivers/gpu/drm/amd/display/dc/dsc/rc_calc.c
drivers/gpu/drm/amd/display/dc/dsc/rc_calc.h
drivers/gpu/drm/amd/display/dc/dsc/rc_calc_dpi.c

index 3ee858f311d12a85679bca6500a7fa82688d0efd..122ba291a7efa9b576f092c5e553c465819018c8 100644 (file)
@@ -61,16 +61,6 @@ static double dsc_roundf(double num)
        return (int)(num);
 }
 
-static double dsc_ceil(double num)
-{
-       double retval = (int)num;
-
-       if (retval != num && num > 0)
-               retval = num + 1;
-
-       return (int)retval;
-}
-
 static void get_qp_set(qp_set qps, enum colour_mode cm, enum bits_per_comp bpc,
                       enum max_min max_min, float bpp)
 {
@@ -268,24 +258,3 @@ void _do_calc_rc_params(struct rc_params *rc,
        rc->rc_buf_thresh[13] = 8064;
 }
 
-u32 _do_bytes_per_pixel_calc(int slice_width,
-               u16 drm_bpp,
-               bool is_navite_422_or_420)
-{
-       float bpp;
-       u32 bytes_per_pixel;
-       double d_bytes_per_pixel;
-
-       dc_assert_fp_enabled();
-
-       bpp = ((float)drm_bpp / 16.0);
-       d_bytes_per_pixel = dsc_ceil(bpp * slice_width / 8.0) / slice_width;
-       // TODO: Make sure the formula for calculating this is precise (ceiling
-       // vs. floor, and at what point they should be applied)
-       if (is_navite_422_or_420)
-               d_bytes_per_pixel /= 2;
-
-       bytes_per_pixel = (u32)dsc_ceil(d_bytes_per_pixel * 0x10000000);
-
-       return bytes_per_pixel;
-}
index b93b95409fbe2d391f432324d0f21701403d2f5d..cad244c023cd3032b81b3d32c5f46ffbd0e8677a 100644 (file)
@@ -78,10 +78,6 @@ struct qp_entry {
 
 typedef struct qp_entry qp_table[];
 
-u32 _do_bytes_per_pixel_calc(int slice_width,
-               u16 drm_bpp,
-               bool is_navite_422_or_420);
-
 void _do_calc_rc_params(struct rc_params *rc,
                enum colour_mode cm,
                enum bits_per_comp bpc,
index b19d3aeb5962cec8ebf25c6db42eeb69bae9abfc..e97cf09be9d51955eb7a64a6ec91a2aa363b8917 100644 (file)
@@ -60,31 +60,3 @@ void calc_rc_params(struct rc_params *rc, const struct drm_dsc_config *pps)
                           pps->dsc_version_minor);
        DC_FP_END();
 }
-
-/**
- * calc_dsc_bytes_per_pixel - calculate bytes per pixel
- * @pps: DRM struct with all required DSC values
- *
- * Based on the information inside drm_dsc_config, this function calculates the
- * total of bytes per pixel.
- *
- * @note This calculation requires float point operation, most of it executes
- * under kernel_fpu_{begin,end}.
- *
- * Return:
- * Return the number of bytes per pixel
- */
-u32 calc_dsc_bytes_per_pixel(const struct drm_dsc_config *pps)
-
-{
-       u32 ret;
-       u16 drm_bpp = pps->bits_per_pixel;
-       int slice_width  = pps->slice_width;
-       bool is_navite_422_or_420 = pps->native_422 || pps->native_420;
-
-       DC_FP_START();
-       ret = _do_bytes_per_pixel_calc(slice_width, drm_bpp,
-                                      is_navite_422_or_420);
-       DC_FP_END();
-       return ret;
-}
index c2340e001b57842bea854a3cb51cef999902c45d..80921c1c0d53cc9cc59286f1bee0efed3650ed23 100644 (file)
@@ -30,7 +30,6 @@
 #include "dml/dsc/rc_calc_fpu.h"
 
 void calc_rc_params(struct rc_params *rc, const struct drm_dsc_config *pps);
-u32 calc_dsc_bytes_per_pixel(const struct drm_dsc_config *pps);
 
 #endif
 
index 1e19dd674e5a215a0b53e778f3008f27e21fbac4..7e306aa3e2b95c9f20aeafa6c6f2cd225fdd9884 100644 (file)
@@ -100,8 +100,7 @@ int dscc_compute_dsc_parameters(const struct drm_dsc_config *pps, struct dsc_par
        int              ret;
        struct rc_params rc;
        struct drm_dsc_config   dsc_cfg;
-
-       dsc_params->bytes_per_pixel = calc_dsc_bytes_per_pixel(pps);
+       unsigned long long tmp;
 
        calc_rc_params(&rc, pps);
        dsc_params->pps = *pps;
@@ -113,6 +112,9 @@ int dscc_compute_dsc_parameters(const struct drm_dsc_config *pps, struct dsc_par
        dsc_cfg.mux_word_size = dsc_params->pps.bits_per_component <= 10 ? 48 : 64;
 
        ret = drm_dsc_compute_rc_parameters(&dsc_cfg);
+       tmp = (unsigned long long)dsc_cfg.slice_chunk_size * 0x10000000 + (dsc_cfg.slice_width - 1);
+       do_div(tmp, (uint32_t)dsc_cfg.slice_width);  //ROUND-UP
+       dsc_params->bytes_per_pixel = (uint32_t)tmp;
 
        copy_pps_fields(&dsc_params->pps, &dsc_cfg);
        dsc_params->rc_buffer_model_size = dsc_cfg.rc_bits;