diff options
author | Alex Deucher <alexander.deucher@amd.com> | 2015-04-07 09:52:42 -0400 |
---|---|---|
committer | Alex Deucher <alexander.deucher@amd.com> | 2015-04-27 09:54:55 -0400 |
commit | 0f55db36d49d45b80eff0c0a2a498766016f458b (patch) | |
tree | 7604d53da685ea0e8a44e078bb01b714e1a9c728 | |
parent | 362ff251390f3d1f8fe94666f4fc4e5876381114 (diff) |
drm/radeon: only mark audio as connected if the monitor supports it (v3)
Otherwise the driver may try and send audio which may confuse the
monitor.
v2: set pin to NULL if no audio
v3: avoid crash with analog encoders
Signed-off-by: Alex Deucher <alexander.deucher@amd.com>
Cc: stable@vger.kernel.org
-rw-r--r-- | drivers/gpu/drm/radeon/radeon_audio.c | 27 | ||||
-rw-r--r-- | drivers/gpu/drm/radeon/radeon_connectors.c | 8 |
2 files changed, 21 insertions, 14 deletions
diff --git a/drivers/gpu/drm/radeon/radeon_audio.c b/drivers/gpu/drm/radeon/radeon_audio.c index 2c17df978d61..8b82abb78df1 100644 --- a/drivers/gpu/drm/radeon/radeon_audio.c +++ b/drivers/gpu/drm/radeon/radeon_audio.c | |||
@@ -460,30 +460,33 @@ void radeon_audio_detect(struct drm_connector *connector, | |||
460 | if (!connector || !connector->encoder) | 460 | if (!connector || !connector->encoder) |
461 | return; | 461 | return; |
462 | 462 | ||
463 | if (!radeon_encoder_is_digital(connector->encoder)) | ||
464 | return; | ||
465 | |||
463 | rdev = connector->encoder->dev->dev_private; | 466 | rdev = connector->encoder->dev->dev_private; |
464 | radeon_encoder = to_radeon_encoder(connector->encoder); | 467 | radeon_encoder = to_radeon_encoder(connector->encoder); |
465 | dig = radeon_encoder->enc_priv; | 468 | dig = radeon_encoder->enc_priv; |
466 | 469 | ||
467 | if (status == connector_status_connected) { | 470 | if (!dig->afmt) |
468 | struct radeon_connector *radeon_connector; | 471 | return; |
469 | int sink_type; | ||
470 | |||
471 | if (!drm_detect_monitor_audio(radeon_connector_edid(connector))) { | ||
472 | radeon_encoder->audio = NULL; | ||
473 | return; | ||
474 | } | ||
475 | 472 | ||
476 | radeon_connector = to_radeon_connector(connector); | 473 | if (status == connector_status_connected) { |
477 | sink_type = radeon_dp_getsinktype(radeon_connector); | 474 | struct radeon_connector *radeon_connector = to_radeon_connector(connector); |
478 | 475 | ||
479 | if (connector->connector_type == DRM_MODE_CONNECTOR_DisplayPort && | 476 | if (connector->connector_type == DRM_MODE_CONNECTOR_DisplayPort && |
480 | sink_type == CONNECTOR_OBJECT_ID_DISPLAYPORT) | 477 | radeon_dp_getsinktype(radeon_connector) == |
478 | CONNECTOR_OBJECT_ID_DISPLAYPORT) | ||
481 | radeon_encoder->audio = rdev->audio.dp_funcs; | 479 | radeon_encoder->audio = rdev->audio.dp_funcs; |
482 | else | 480 | else |
483 | radeon_encoder->audio = rdev->audio.hdmi_funcs; | 481 | radeon_encoder->audio = rdev->audio.hdmi_funcs; |
484 | 482 | ||
485 | dig->afmt->pin = radeon_audio_get_pin(connector->encoder); | 483 | dig->afmt->pin = radeon_audio_get_pin(connector->encoder); |
486 | radeon_audio_enable(rdev, dig->afmt->pin, 0xf); | 484 | if (drm_detect_monitor_audio(radeon_connector_edid(connector))) { |
485 | radeon_audio_enable(rdev, dig->afmt->pin, 0xf); | ||
486 | } else { | ||
487 | radeon_audio_enable(rdev, dig->afmt->pin, 0); | ||
488 | dig->afmt->pin = NULL; | ||
489 | } | ||
487 | } else { | 490 | } else { |
488 | radeon_audio_enable(rdev, dig->afmt->pin, 0); | 491 | radeon_audio_enable(rdev, dig->afmt->pin, 0); |
489 | dig->afmt->pin = NULL; | 492 | dig->afmt->pin = NULL; |
diff --git a/drivers/gpu/drm/radeon/radeon_connectors.c b/drivers/gpu/drm/radeon/radeon_connectors.c index cebb65e07e1d..d17d251dbd4f 100644 --- a/drivers/gpu/drm/radeon/radeon_connectors.c +++ b/drivers/gpu/drm/radeon/radeon_connectors.c | |||
@@ -1379,8 +1379,10 @@ out: | |||
1379 | /* updated in get modes as well since we need to know if it's analog or digital */ | 1379 | /* updated in get modes as well since we need to know if it's analog or digital */ |
1380 | radeon_connector_update_scratch_regs(connector, ret); | 1380 | radeon_connector_update_scratch_regs(connector, ret); |
1381 | 1381 | ||
1382 | if (radeon_audio != 0) | 1382 | if (radeon_audio != 0) { |
1383 | radeon_connector_get_edid(connector); | ||
1383 | radeon_audio_detect(connector, ret); | 1384 | radeon_audio_detect(connector, ret); |
1385 | } | ||
1384 | 1386 | ||
1385 | exit: | 1387 | exit: |
1386 | pm_runtime_mark_last_busy(connector->dev->dev); | 1388 | pm_runtime_mark_last_busy(connector->dev->dev); |
@@ -1717,8 +1719,10 @@ radeon_dp_detect(struct drm_connector *connector, bool force) | |||
1717 | 1719 | ||
1718 | radeon_connector_update_scratch_regs(connector, ret); | 1720 | radeon_connector_update_scratch_regs(connector, ret); |
1719 | 1721 | ||
1720 | if (radeon_audio != 0) | 1722 | if (radeon_audio != 0) { |
1723 | radeon_connector_get_edid(connector); | ||
1721 | radeon_audio_detect(connector, ret); | 1724 | radeon_audio_detect(connector, ret); |
1725 | } | ||
1722 | 1726 | ||
1723 | out: | 1727 | out: |
1724 | pm_runtime_mark_last_busy(connector->dev->dev); | 1728 | pm_runtime_mark_last_busy(connector->dev->dev); |