Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 374a5040 authored by Takashi Iwai's avatar Takashi Iwai
Browse files

Merge branch 'topic/intel-lpe-audio-dp' into for-next

Merged more patches for Intel LPE audio driver, now to support DP audio.
parents fc28ab18 b1c01f4d
Loading
Loading
Loading
Loading
+2 −1
Original line number Diff line number Diff line
@@ -3401,7 +3401,8 @@ int intel_lpe_audio_init(struct drm_i915_private *dev_priv);
void intel_lpe_audio_teardown(struct drm_i915_private *dev_priv);
void intel_lpe_audio_irq_handler(struct drm_i915_private *dev_priv);
void intel_lpe_audio_notify(struct drm_i915_private *dev_priv,
			void *eld, int port, int tmds_clk_speed);
			    void *eld, int port, int pipe, int tmds_clk_speed,
			    bool dp_output, int link_rate);

/* intel_i2c.c */
extern int intel_setup_gmbus(struct drm_device *dev);
+10 −0
Original line number Diff line number Diff line
@@ -2061,6 +2061,16 @@ enum skl_disp_power_wells {
#define I915_HDMI_LPE_AUDIO_BASE	(VLV_DISPLAY_BASE + 0x65000)
#define I915_HDMI_LPE_AUDIO_SIZE	0x1000

/* DisplayPort Audio w/ LPE */
#define _VLV_AUD_PORT_EN_B_DBG		(VLV_DISPLAY_BASE + 0x62F20)
#define _VLV_AUD_PORT_EN_C_DBG		(VLV_DISPLAY_BASE + 0x62F30)
#define _VLV_AUD_PORT_EN_D_DBG		(VLV_DISPLAY_BASE + 0x62F34)
#define VLV_AUD_PORT_EN_DBG(port)	_MMIO_PORT3((port) - PORT_B,	   \
						    _VLV_AUD_PORT_EN_B_DBG, \
						    _VLV_AUD_PORT_EN_C_DBG, \
						    _VLV_AUD_PORT_EN_D_DBG)
#define VLV_AMP_MUTE		        (1 << 1)

#define GEN6_BSD_RNCID			_MMIO(0x12198)

#define GEN7_FF_THREAD_MODE		_MMIO(0x20a0)
+25 −13
Original line number Diff line number Diff line
@@ -624,16 +624,28 @@ void intel_audio_codec_enable(struct intel_encoder *intel_encoder,
	dev_priv->av_enc_map[pipe] = intel_encoder;
	mutex_unlock(&dev_priv->av_mutex);

	if (acomp && acomp->audio_ops && acomp->audio_ops->pin_eld_notify) {
		/* audio drivers expect pipe = -1 to indicate Non-MST cases */
		if (intel_encoder->type != INTEL_OUTPUT_DP_MST)
			pipe = -1;

	if (acomp && acomp->audio_ops && acomp->audio_ops->pin_eld_notify)
		acomp->audio_ops->pin_eld_notify(acomp->audio_ops->audio_ptr,
						 (int) port, (int) pipe);
	}

	intel_lpe_audio_notify(dev_priv, connector->eld, port,
			crtc_state->port_clock);
	switch (intel_encoder->type) {
	case INTEL_OUTPUT_HDMI:
		intel_lpe_audio_notify(dev_priv, connector->eld, port, pipe,
				       crtc_state->port_clock,
				       false, 0);
		break;
	case INTEL_OUTPUT_DP:
		intel_lpe_audio_notify(dev_priv, connector->eld, port, pipe,
				       adjusted_mode->crtc_clock,
				       true, crtc_state->port_clock);
		break;
	default:
		break;
	}
}

/**
@@ -660,15 +672,15 @@ void intel_audio_codec_disable(struct intel_encoder *intel_encoder)
	dev_priv->av_enc_map[pipe] = NULL;
	mutex_unlock(&dev_priv->av_mutex);

	if (acomp && acomp->audio_ops && acomp->audio_ops->pin_eld_notify) {
		/* audio drivers expect pipe = -1 to indicate Non-MST cases */
		if (intel_encoder->type != INTEL_OUTPUT_DP_MST)
			pipe = -1;

	if (acomp && acomp->audio_ops && acomp->audio_ops->pin_eld_notify)
		acomp->audio_ops->pin_eld_notify(acomp->audio_ops->audio_ptr,
						 (int) port, (int) pipe);
	}

	intel_lpe_audio_notify(dev_priv, NULL, port, 0);
	intel_lpe_audio_notify(dev_priv, NULL, port, pipe, 0, false, 0);
}

/**
+20 −3
Original line number Diff line number Diff line
@@ -332,10 +332,12 @@ void intel_lpe_audio_teardown(struct drm_i915_private *dev_priv)
 * Notify lpe audio driver of eld change.
 */
void intel_lpe_audio_notify(struct drm_i915_private *dev_priv,
			void *eld, int port, int tmds_clk_speed)
			    void *eld, int port, int pipe, int tmds_clk_speed,
			    bool dp_output, int link_rate)
{
	unsigned long irq_flags;
	struct intel_hdmi_lpe_audio_pdata *pdata = NULL;
	u32 audio_enable;

	if (!HAS_LPE_AUDIO(dev_priv))
		return;
@@ -345,23 +347,38 @@ void intel_lpe_audio_notify(struct drm_i915_private *dev_priv,

	spin_lock_irqsave(&pdata->lpe_audio_slock, irq_flags);

	audio_enable = I915_READ(VLV_AUD_PORT_EN_DBG(port));

	if (eld != NULL) {
		memcpy(pdata->eld.eld_data, eld,
			HDMI_MAX_ELD_BYTES);
		pdata->eld.port_id = port;
		pdata->eld.pipe_id = pipe;
		pdata->hdmi_connected = true;

		pdata->dp_output = dp_output;
		if (tmds_clk_speed)
			pdata->tmds_clock_speed = tmds_clk_speed;
		if (link_rate)
			pdata->link_rate = link_rate;

		/* Unmute the amp for both DP and HDMI */
		I915_WRITE(VLV_AUD_PORT_EN_DBG(port),
			   audio_enable & ~VLV_AMP_MUTE);

	} else {
		memset(pdata->eld.eld_data, 0,
			HDMI_MAX_ELD_BYTES);
		pdata->hdmi_connected = false;
		pdata->dp_output = false;

		/* Mute the amp for both DP and HDMI */
		I915_WRITE(VLV_AUD_PORT_EN_DBG(port),
			   audio_enable | VLV_AMP_MUTE);
	}

	if (pdata->notify_audio_lpe)
		pdata->notify_audio_lpe(
			(eld != NULL) ? &pdata->eld : NULL);
		pdata->notify_audio_lpe(dev_priv->lpe_audio.platdev);
	else
		pdata->notify_pending = true;

+6 −1
Original line number Diff line number Diff line
@@ -27,10 +27,13 @@
#include <linux/types.h>
#include <linux/spinlock_types.h>

struct platform_device;

#define HDMI_MAX_ELD_BYTES	128

struct intel_hdmi_lpe_audio_eld {
	int port_id;
	int pipe_id;
	unsigned char eld_data[HDMI_MAX_ELD_BYTES];
};

@@ -38,8 +41,10 @@ struct intel_hdmi_lpe_audio_pdata {
	bool notify_pending;
	int tmds_clock_speed;
	bool hdmi_connected;
	bool dp_output;
	int link_rate;
	struct intel_hdmi_lpe_audio_eld eld;
	void (*notify_audio_lpe)(void *audio_ptr);
	void (*notify_audio_lpe)(struct platform_device *pdev);
	spinlock_t lpe_audio_slock;
};

Loading