mirror of
https://github.com/AuxXxilium/linux_dsm_epyc7002.git
synced 2024-12-02 10:46:50 +07:00
drm/radeon: enable display scaling on all connectors (v2)
This enables the display scaler on all connectors for r5xx and newer asics. Previously we only enabled the scaler for fixed mode displays (eDP or LVDS) since they have to use the scaler to support non-native modes. Most other displays are multi-sync or have a built in scaler to support non-native modes. The default scaling mode for non-fixed displays is none which will use the scaler in the monitor. Note that we do not populate any fake modes like we do for fixed displays so it will only use the modes in the edid. For other modes, you'll need to populate them manually. bug: https://bugs.freedesktop.org/show_bug.cgi?id=80868 v2: properly handle scaling with no modes defined Signed-off-by: Alex Deucher <alexander.deucher@amd.com>
This commit is contained in:
parent
9c2448780f
commit
da9976206c
@ -331,12 +331,10 @@ static bool radeon_atom_mode_fixup(struct drm_encoder *encoder,
|
||||
&& (mode->crtc_vsync_start < (mode->crtc_vdisplay + 2)))
|
||||
adjusted_mode->crtc_vsync_start = adjusted_mode->crtc_vdisplay + 2;
|
||||
|
||||
/* get the native mode for LVDS */
|
||||
if (radeon_encoder->active_device & (ATOM_DEVICE_LCD_SUPPORT))
|
||||
/* get the native mode for scaling */
|
||||
if (radeon_encoder->active_device & (ATOM_DEVICE_LCD_SUPPORT)) {
|
||||
radeon_panel_mode_fixup(encoder, adjusted_mode);
|
||||
|
||||
/* get the native mode for TV */
|
||||
if (radeon_encoder->active_device & (ATOM_DEVICE_TV_SUPPORT)) {
|
||||
} else if (radeon_encoder->active_device & (ATOM_DEVICE_TV_SUPPORT)) {
|
||||
struct radeon_encoder_atom_dac *tv_dac = radeon_encoder->enc_priv;
|
||||
if (tv_dac) {
|
||||
if (tv_dac->tv_std == TV_STD_NTSC ||
|
||||
@ -346,6 +344,8 @@ static bool radeon_atom_mode_fixup(struct drm_encoder *encoder,
|
||||
else
|
||||
radeon_atom_get_tv_timings(rdev, 1, adjusted_mode);
|
||||
}
|
||||
} else if (radeon_encoder->rmx_type != RMX_OFF) {
|
||||
radeon_panel_mode_fixup(encoder, adjusted_mode);
|
||||
}
|
||||
|
||||
if (ASIC_IS_DCE3(rdev) &&
|
||||
|
@ -271,6 +271,27 @@ static struct drm_encoder *radeon_best_single_encoder(struct drm_connector *conn
|
||||
return NULL;
|
||||
}
|
||||
|
||||
static void radeon_get_native_mode(struct drm_connector *connector)
|
||||
{
|
||||
struct drm_encoder *encoder = radeon_best_single_encoder(connector);
|
||||
struct radeon_encoder *radeon_encoder;
|
||||
|
||||
if (encoder == NULL)
|
||||
return;
|
||||
|
||||
radeon_encoder = to_radeon_encoder(encoder);
|
||||
|
||||
if (!list_empty(&connector->probed_modes)) {
|
||||
struct drm_display_mode *preferred_mode =
|
||||
list_first_entry(&connector->probed_modes,
|
||||
struct drm_display_mode, head);
|
||||
|
||||
radeon_encoder->native_mode = *preferred_mode;
|
||||
} else {
|
||||
radeon_encoder->native_mode.clock = 0;
|
||||
}
|
||||
}
|
||||
|
||||
/*
|
||||
* radeon_connector_analog_encoder_conflict_solve
|
||||
* - search for other connectors sharing this encoder
|
||||
@ -571,6 +592,35 @@ static int radeon_connector_set_property(struct drm_connector *connector, struct
|
||||
radeon_property_change_mode(&radeon_encoder->base);
|
||||
}
|
||||
|
||||
if (property == dev->mode_config.scaling_mode_property) {
|
||||
enum radeon_rmx_type rmx_type;
|
||||
|
||||
if (connector->encoder)
|
||||
radeon_encoder = to_radeon_encoder(connector->encoder);
|
||||
else {
|
||||
struct drm_connector_helper_funcs *connector_funcs = connector->helper_private;
|
||||
radeon_encoder = to_radeon_encoder(connector_funcs->best_encoder(connector));
|
||||
}
|
||||
|
||||
switch (val) {
|
||||
default:
|
||||
case DRM_MODE_SCALE_NONE: rmx_type = RMX_OFF; break;
|
||||
case DRM_MODE_SCALE_CENTER: rmx_type = RMX_CENTER; break;
|
||||
case DRM_MODE_SCALE_ASPECT: rmx_type = RMX_ASPECT; break;
|
||||
case DRM_MODE_SCALE_FULLSCREEN: rmx_type = RMX_FULL; break;
|
||||
}
|
||||
if (radeon_encoder->rmx_type == rmx_type)
|
||||
return 0;
|
||||
|
||||
if ((rmx_type != DRM_MODE_SCALE_NONE) &&
|
||||
(radeon_encoder->native_mode.clock == 0))
|
||||
return 0;
|
||||
|
||||
radeon_encoder->rmx_type = rmx_type;
|
||||
|
||||
radeon_property_change_mode(&radeon_encoder->base);
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
@ -788,6 +838,8 @@ static int radeon_vga_get_modes(struct drm_connector *connector)
|
||||
|
||||
ret = radeon_ddc_get_modes(radeon_connector);
|
||||
|
||||
radeon_get_native_mode(connector);
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
@ -991,6 +1043,9 @@ static int radeon_dvi_get_modes(struct drm_connector *connector)
|
||||
int ret;
|
||||
|
||||
ret = radeon_ddc_get_modes(radeon_connector);
|
||||
|
||||
radeon_get_native_mode(connector);
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
@ -1358,6 +1413,8 @@ static int radeon_dp_get_modes(struct drm_connector *connector)
|
||||
radeon_atom_ext_encoder_setup_ddc(encoder);
|
||||
}
|
||||
ret = radeon_ddc_get_modes(radeon_connector);
|
||||
|
||||
radeon_get_native_mode(connector);
|
||||
}
|
||||
|
||||
return ret;
|
||||
@ -1717,6 +1774,9 @@ radeon_add_atom_connector(struct drm_device *dev,
|
||||
drm_object_attach_property(&radeon_connector->base.base,
|
||||
rdev->mode_info.load_detect_property,
|
||||
1);
|
||||
drm_object_attach_property(&radeon_connector->base.base,
|
||||
dev->mode_config.scaling_mode_property,
|
||||
DRM_MODE_SCALE_NONE);
|
||||
break;
|
||||
case DRM_MODE_CONNECTOR_DVII:
|
||||
case DRM_MODE_CONNECTOR_DVID:
|
||||
@ -1737,6 +1797,10 @@ radeon_add_atom_connector(struct drm_device *dev,
|
||||
rdev->mode_info.underscan_vborder_property,
|
||||
0);
|
||||
|
||||
drm_object_attach_property(&radeon_connector->base.base,
|
||||
dev->mode_config.scaling_mode_property,
|
||||
DRM_MODE_SCALE_NONE);
|
||||
|
||||
drm_object_attach_property(&radeon_connector->base.base,
|
||||
rdev->mode_info.dither_property,
|
||||
RADEON_FMT_DITHER_DISABLE);
|
||||
@ -1787,6 +1851,10 @@ radeon_add_atom_connector(struct drm_device *dev,
|
||||
drm_object_attach_property(&radeon_connector->base.base,
|
||||
rdev->mode_info.load_detect_property,
|
||||
1);
|
||||
if (ASIC_IS_AVIVO(rdev))
|
||||
drm_object_attach_property(&radeon_connector->base.base,
|
||||
dev->mode_config.scaling_mode_property,
|
||||
DRM_MODE_SCALE_NONE);
|
||||
/* no HPD on analog connectors */
|
||||
radeon_connector->hpd.hpd = RADEON_HPD_NONE;
|
||||
connector->polled = DRM_CONNECTOR_POLL_CONNECT;
|
||||
@ -1805,6 +1873,10 @@ radeon_add_atom_connector(struct drm_device *dev,
|
||||
drm_object_attach_property(&radeon_connector->base.base,
|
||||
rdev->mode_info.load_detect_property,
|
||||
1);
|
||||
if (ASIC_IS_AVIVO(rdev))
|
||||
drm_object_attach_property(&radeon_connector->base.base,
|
||||
dev->mode_config.scaling_mode_property,
|
||||
DRM_MODE_SCALE_NONE);
|
||||
/* no HPD on analog connectors */
|
||||
radeon_connector->hpd.hpd = RADEON_HPD_NONE;
|
||||
connector->interlace_allowed = true;
|
||||
@ -1838,17 +1910,18 @@ radeon_add_atom_connector(struct drm_device *dev,
|
||||
drm_object_attach_property(&radeon_connector->base.base,
|
||||
rdev->mode_info.underscan_vborder_property,
|
||||
0);
|
||||
drm_object_attach_property(&radeon_connector->base.base,
|
||||
rdev->mode_info.dither_property,
|
||||
RADEON_FMT_DITHER_DISABLE);
|
||||
drm_object_attach_property(&radeon_connector->base.base,
|
||||
dev->mode_config.scaling_mode_property,
|
||||
DRM_MODE_SCALE_NONE);
|
||||
}
|
||||
if (ASIC_IS_DCE2(rdev) && (radeon_audio != 0)) {
|
||||
drm_object_attach_property(&radeon_connector->base.base,
|
||||
rdev->mode_info.audio_property,
|
||||
RADEON_AUDIO_AUTO);
|
||||
}
|
||||
if (ASIC_IS_AVIVO(rdev)) {
|
||||
drm_object_attach_property(&radeon_connector->base.base,
|
||||
rdev->mode_info.dither_property,
|
||||
RADEON_FMT_DITHER_DISABLE);
|
||||
}
|
||||
if (connector_type == DRM_MODE_CONNECTOR_DVII) {
|
||||
radeon_connector->dac_load_detect = true;
|
||||
drm_object_attach_property(&radeon_connector->base.base,
|
||||
@ -1888,17 +1961,18 @@ radeon_add_atom_connector(struct drm_device *dev,
|
||||
drm_object_attach_property(&radeon_connector->base.base,
|
||||
rdev->mode_info.underscan_vborder_property,
|
||||
0);
|
||||
drm_object_attach_property(&radeon_connector->base.base,
|
||||
rdev->mode_info.dither_property,
|
||||
RADEON_FMT_DITHER_DISABLE);
|
||||
drm_object_attach_property(&radeon_connector->base.base,
|
||||
dev->mode_config.scaling_mode_property,
|
||||
DRM_MODE_SCALE_NONE);
|
||||
}
|
||||
if (ASIC_IS_DCE2(rdev) && (radeon_audio != 0)) {
|
||||
drm_object_attach_property(&radeon_connector->base.base,
|
||||
rdev->mode_info.audio_property,
|
||||
RADEON_AUDIO_AUTO);
|
||||
}
|
||||
if (ASIC_IS_AVIVO(rdev)) {
|
||||
drm_object_attach_property(&radeon_connector->base.base,
|
||||
rdev->mode_info.dither_property,
|
||||
RADEON_FMT_DITHER_DISABLE);
|
||||
}
|
||||
subpixel_order = SubPixelHorizontalRGB;
|
||||
connector->interlace_allowed = true;
|
||||
if (connector_type == DRM_MODE_CONNECTOR_HDMIB)
|
||||
@ -1935,18 +2009,18 @@ radeon_add_atom_connector(struct drm_device *dev,
|
||||
drm_object_attach_property(&radeon_connector->base.base,
|
||||
rdev->mode_info.underscan_vborder_property,
|
||||
0);
|
||||
drm_object_attach_property(&radeon_connector->base.base,
|
||||
rdev->mode_info.dither_property,
|
||||
RADEON_FMT_DITHER_DISABLE);
|
||||
drm_object_attach_property(&radeon_connector->base.base,
|
||||
dev->mode_config.scaling_mode_property,
|
||||
DRM_MODE_SCALE_NONE);
|
||||
}
|
||||
if (ASIC_IS_DCE2(rdev) && (radeon_audio != 0)) {
|
||||
drm_object_attach_property(&radeon_connector->base.base,
|
||||
rdev->mode_info.audio_property,
|
||||
RADEON_AUDIO_AUTO);
|
||||
}
|
||||
if (ASIC_IS_AVIVO(rdev)) {
|
||||
drm_object_attach_property(&radeon_connector->base.base,
|
||||
rdev->mode_info.dither_property,
|
||||
RADEON_FMT_DITHER_DISABLE);
|
||||
|
||||
}
|
||||
connector->interlace_allowed = true;
|
||||
/* in theory with a DP to VGA converter... */
|
||||
connector->doublescan_allowed = false;
|
||||
|
Loading…
Reference in New Issue
Block a user