[alsa-devel] [PATCH 2/4] drm/i915: Call audio hotplug notify function

David Henningsson david.henningsson at canonical.com
Tue Jul 21 09:57:25 CEST 2015


On HDMI hotplug events, notify the audio driver. This will enable
the audio driver to get the information at all times (even when
audio is in different powersave states), and also without reading
it from the hardware.

Signed-off-by: David Henningsson <david.henningsson at canonical.com>
---
 drivers/gpu/drm/i915/i915_drv.h    |    1 +
 drivers/gpu/drm/i915/intel_audio.c |   46 ++++++++++++++++++++++++++++++++++++
 2 files changed, 47 insertions(+)

diff --git a/drivers/gpu/drm/i915/i915_drv.h b/drivers/gpu/drm/i915/i915_drv.h
index 542fac6..696624c 100644
--- a/drivers/gpu/drm/i915/i915_drv.h
+++ b/drivers/gpu/drm/i915/i915_drv.h
@@ -1808,6 +1808,7 @@ struct drm_i915_private {
 	struct drm_property *force_audio_property;
 
 	/* hda/i915 audio component */
+	struct i915_audio_component *audio_component;
 	bool audio_component_registered;
 
 	uint32_t hw_context_size;
diff --git a/drivers/gpu/drm/i915/intel_audio.c b/drivers/gpu/drm/i915/intel_audio.c
index 3da9b84..eb29e1f 100644
--- a/drivers/gpu/drm/i915/intel_audio.c
+++ b/drivers/gpu/drm/i915/intel_audio.c
@@ -384,6 +384,44 @@ static void ilk_audio_codec_enable(struct drm_connector *connector,
 	I915_WRITE(aud_config, tmp);
 }
 
+static void audio_hotplug_notify(struct drm_i915_private *dev_priv,
+				 struct drm_connector *connector,
+				 struct intel_encoder *encoder,
+				 bool plugged_in)
+{
+	struct i915_audio_component *acomp = dev_priv->audio_component;
+	struct i915_audio_hotplug_info audio_info;
+	struct intel_digital_port *intel_dig_port =
+		enc_to_dig_port(&encoder->base);
+	enum port port = intel_dig_port->port;
+
+	if (!acomp || !acomp->cb_ops || !acomp->cb_ops->hotplug_notify)
+		return;
+
+	if (connector) {
+		audio_info.connector_type = connector->connector_type;
+		audio_info.connector_type_id = connector->connector_type_id;
+	} else {
+		audio_info.connector_type = -1;
+		audio_info.connector_type_id = -1;
+	}
+
+	audio_info.port = (int) port;
+	/* DP Mst is unsupported for now */
+	audio_info.port_multi_stream_device = 0;
+
+	audio_info.plugged_in = plugged_in;
+	if (plugged_in && connector) {
+		audio_info.eld = connector->eld;
+		audio_info.eld_size = drm_eld_size(audio_info.eld);
+	} else {
+		audio_info.eld = NULL;
+		audio_info.eld_size = 0;
+	}
+
+	acomp->cb_ops->hotplug_notify(acomp->hdac_bus, &audio_info);
+}
+
 /**
  * intel_audio_codec_enable - Enable the audio codec for HD audio
  * @intel_encoder: encoder on which to enable audio
@@ -419,6 +457,8 @@ void intel_audio_codec_enable(struct intel_encoder *intel_encoder)
 
 	if (dev_priv->display.audio_codec_enable)
 		dev_priv->display.audio_codec_enable(connector, intel_encoder, mode);
+
+	audio_hotplug_notify(dev_priv, connector, intel_encoder, true);
 }
 
 /**
@@ -435,6 +475,8 @@ void intel_audio_codec_disable(struct intel_encoder *encoder)
 
 	if (dev_priv->display.audio_codec_disable)
 		dev_priv->display.audio_codec_disable(encoder);
+
+	audio_hotplug_notify(dev_priv, NULL, encoder, false);
 }
 
 /**
@@ -525,12 +567,14 @@ static int i915_audio_component_bind(struct device *i915_dev,
 				     struct device *hda_dev, void *data)
 {
 	struct i915_audio_component *acomp = data;
+	struct drm_i915_private *dev_priv = dev_to_i915(i915_dev);
 
 	if (WARN_ON(acomp->ops || acomp->dev))
 		return -EEXIST;
 
 	acomp->ops = &i915_audio_component_ops;
 	acomp->dev = i915_dev;
+	dev_priv->audio_component = acomp;
 
 	return 0;
 }
@@ -539,9 +583,11 @@ static void i915_audio_component_unbind(struct device *i915_dev,
 					struct device *hda_dev, void *data)
 {
 	struct i915_audio_component *acomp = data;
+	struct drm_i915_private *dev_priv = dev_to_i915(i915_dev);
 
 	acomp->ops = NULL;
 	acomp->dev = NULL;
+	dev_priv->audio_component = NULL;
 }
 
 static const struct component_ops i915_audio_component_bind_ops = {
-- 
1.7.9.5



More information about the Alsa-devel mailing list