diff --git a/msm/dsi/dsi_drm.c b/msm/dsi/dsi_drm.c index 43984cb9e4..90f03add80 100644 --- a/msm/dsi/dsi_drm.c +++ b/msm/dsi/dsi_drm.c @@ -472,6 +472,8 @@ int dsi_conn_get_mode_info(struct drm_connector *connector, { struct dsi_display_mode dsi_mode; struct dsi_mode_info *timing; + int chroma_format; + int src_bpp, tar_bpp; if (!drm_mode || !mode_info) return -EINVAL; @@ -498,17 +500,25 @@ int dsi_conn_get_mode_info(struct drm_connector *connector, mode_info->comp_info.comp_type = MSM_DISPLAY_COMPRESSION_NONE; if (dsi_mode.priv_info->dsc_enabled) { + chroma_format = dsi_mode.priv_info->dsc.chroma_format; mode_info->comp_info.comp_type = MSM_DISPLAY_COMPRESSION_DSC; memcpy(&mode_info->comp_info.dsc_info, &dsi_mode.priv_info->dsc, sizeof(dsi_mode.priv_info->dsc)); - mode_info->comp_info.comp_ratio = - MSM_DISPLAY_COMPRESSION_RATIO_3_TO_1; + tar_bpp = dsi_mode.priv_info->dsc.config.bits_per_pixel >> 4; + src_bpp = msm_get_src_bpc(chroma_format, + dsi_mode.priv_info->dsc.config.bits_per_component); + mode_info->comp_info.comp_ratio = mult_frac(1, src_bpp, + tar_bpp); } else if (dsi_mode.priv_info->vdc_enabled) { + chroma_format = dsi_mode.priv_info->vdc.chroma_format; mode_info->comp_info.comp_type = MSM_DISPLAY_COMPRESSION_VDC; memcpy(&mode_info->comp_info.vdc_info, &dsi_mode.priv_info->vdc, sizeof(dsi_mode.priv_info->vdc)); - mode_info->comp_info.comp_ratio = - MSM_DISPLAY_COMPRESSION_RATIO_4_TO_1; + tar_bpp = dsi_mode.priv_info->vdc.bits_per_pixel >> 4; + src_bpp = msm_get_src_bpc(chroma_format, + dsi_mode.priv_info->vdc.bits_per_component); + mode_info->comp_info.comp_ratio = mult_frac(1, src_bpp, + tar_bpp); } if (dsi_mode.priv_info->roi_caps.enabled) { diff --git a/msm/msm_drv.c b/msm/msm_drv.c index 4e315bdcf3..2623c4bdef 100644 --- a/msm/msm_drv.c +++ b/msm/msm_drv.c @@ -1,5 +1,5 @@ /* - * Copyright (c) 2016-2019, The Linux Foundation. All rights reserved. + * Copyright (c) 2016-2020, The Linux Foundation. All rights reserved. * Copyright (C) 2013 Red Hat * Author: Rob Clark * @@ -301,6 +301,28 @@ u32 msm_readl(const void __iomem *addr) return val; } +int msm_get_src_bpc(int chroma_format, + int bpc) +{ + int src_bpp; + + switch (chroma_format) { + case MSM_CHROMA_444: + src_bpp = bpc * 3; + break; + case MSM_CHROMA_422: + src_bpp = bpc * 2; + break; + case MSM_CHROMA_420: + src_bpp = mult_frac(bpc, 3, 2); + break; + default: + src_bpp = bpc * 3; + break; + } + return src_bpp; +} + struct vblank_work { struct kthread_work work; int crtc_id; diff --git a/msm/msm_drv.h b/msm/msm_drv.h index 4bf64fa57c..d8fb43e25b 100644 --- a/msm/msm_drv.h +++ b/msm/msm_drv.h @@ -228,20 +228,8 @@ enum msm_display_compression_type { MSM_DISPLAY_COMPRESSION_VDC }; -/** - * enum msm_display_compression_ratio - compression ratio - * @MSM_DISPLAY_COMPRESSION_NONE: no compression - * @MSM_DISPLAY_COMPRESSION_RATIO_2_TO_1: 2 to 1 compression - * @MSM_DISPLAY_COMPRESSION_RATIO_3_TO_1: 3 to 1 compression - * @MSM_DISPLAY_COMPRESSION_RATIO_4_TO_1: 4 to 1 compression - */ -enum msm_display_compression_ratio { - MSM_DISPLAY_COMPRESSION_RATIO_NONE, - MSM_DISPLAY_COMPRESSION_RATIO_2_TO_1, - MSM_DISPLAY_COMPRESSION_RATIO_3_TO_1, - MSM_DISPLAY_COMPRESSION_RATIO_4_TO_1, - MSM_DISPLAY_COMPRESSION_RATIO_MAX, -}; +#define MSM_DISPLAY_COMPRESSION_RATIO_NONE 1 +#define MSM_DISPLAY_COMPRESSION_RATIO_MAX 5 /** * enum msm_display_caps - features/capabilities supported by displays @@ -606,7 +594,7 @@ struct msm_display_vdc_info { */ struct msm_compression_info { enum msm_display_compression_type comp_type; - enum msm_display_compression_ratio comp_ratio; + u32 comp_ratio; union{ struct msm_display_dsc_info dsc_info; @@ -1231,4 +1219,6 @@ int msm_get_mixer_count(struct msm_drm_private *priv, const struct drm_display_mode *mode, const struct msm_resource_caps_info *res, u32 *num_lm); +int msm_get_src_bpc(int chroma_format, int bpc); + #endif /* __MSM_DRV_H__ */ diff --git a/msm/sde/sde_encoder_phys.h b/msm/sde/sde_encoder_phys.h index 59ea2cc1ae..6cea9324f8 100644 --- a/msm/sde/sde_encoder_phys.h +++ b/msm/sde/sde_encoder_phys.h @@ -310,7 +310,7 @@ struct sde_encoder_phys { struct sde_hw_intf_cfg intf_cfg; struct sde_hw_intf_cfg_v1 intf_cfg_v1; enum msm_display_compression_type comp_type; - enum msm_display_compression_ratio comp_ratio; + u32 comp_ratio; u32 dsc_extra_pclk_cycle_cnt; u32 dsc_extra_disp_width; bool wide_bus_en; diff --git a/msm/sde/sde_encoder_phys_vid.c b/msm/sde/sde_encoder_phys_vid.c index a8e779ab1a..31a1eb6167 100644 --- a/msm/sde/sde_encoder_phys_vid.c +++ b/msm/sde/sde_encoder_phys_vid.c @@ -50,8 +50,6 @@ static void drm_mode_to_intf_timing_params( struct intf_timing_params *timing) { const struct sde_encoder_phys *phys_enc = &vid_enc->base; - enum msm_display_compression_ratio comp_ratio = - MSM_DISPLAY_COMPRESSION_RATIO_NONE; memset(timing, 0, sizeof(*timing)); @@ -82,17 +80,12 @@ static void drm_mode_to_intf_timing_params( */ timing->width = mode->hdisplay; /* active width */ - if (phys_enc->hw_intf->cap->type != INTF_DP && - vid_enc->base.comp_type == MSM_DISPLAY_COMPRESSION_DSC) { - comp_ratio = vid_enc->base.comp_ratio; - if (comp_ratio == MSM_DISPLAY_COMPRESSION_RATIO_2_TO_1) - timing->width = DIV_ROUND_UP(timing->width, 2); - else - timing->width = DIV_ROUND_UP(timing->width, 3); - } else if (phys_enc->hw_intf->cap->type != INTF_DP && - vid_enc->base.comp_type == MSM_DISPLAY_COMPRESSION_VDC) { - comp_ratio = vid_enc->base.comp_ratio; - timing->width = DIV_ROUND_UP(timing->width, comp_ratio); + if (phys_enc->hw_intf->cap->type != INTF_DP) { + if ((vid_enc->base.comp_type == MSM_DISPLAY_COMPRESSION_DSC) || + (vid_enc->base.comp_type == + MSM_DISPLAY_COMPRESSION_VDC)) + timing->width = DIV_ROUND_UP(timing->width, + vid_enc->base.comp_ratio); } timing->height = mode->vdisplay; /* active height */