[Intel-gfx] [RFC 04/15] drm/i915: Add headers for non-HDAudio HDMI interface

Ville Syrjälä ville.syrjala at linux.intel.com
Thu Mar 10 18:00:39 UTC 2016


On Fri, Mar 04, 2016 at 08:50:41PM -0600, Pierre-Louis Bossart wrote:
> Add header files for interface available on Baytrail and CherryTrail
> 
> Initial code was downloaded from https://github.com/01org/baytrailaudio/
> ...and had the changes to .config stripped and the revert on sound/init.c
> done by David Henningson
> 
> Clean-up, port to 4.4 and intel-drm by Pierre Bossart
> 
> Signed-off-by: David Henningsson <david.henningsson at canonical.com>
> Signed-off-by: Pierre-Louis Bossart <pierre-louis.bossart at linux.intel.com>
> ---
>  drivers/gpu/drm/i915/hdmi_audio_if.h | 122 +++++++++++++++++++++++++++++++++++
>  drivers/gpu/drm/i915/i915_drv.h      |  31 +++++++++
>  drivers/gpu/drm/i915/i915_reg.h      |   7 ++
>  drivers/gpu/drm/i915/intel_drv.h     |  11 ++++
>  4 files changed, 171 insertions(+)
>  create mode 100644 drivers/gpu/drm/i915/hdmi_audio_if.h
> 
> diff --git a/drivers/gpu/drm/i915/hdmi_audio_if.h b/drivers/gpu/drm/i915/hdmi_audio_if.h
> new file mode 100644
> index 0000000..f968028
> --- /dev/null
> +++ b/drivers/gpu/drm/i915/hdmi_audio_if.h
> @@ -0,0 +1,122 @@
> +/*
> + * Copyright (c) 2010, Intel Corporation.
> + *
> + * This program is free software; you can redistribute it and/or modify it
> + * under the terms and conditions of the GNU General Public License,
> + * version 2, as published by the Free Software Foundation.
> + *
> + * This program is distributed in the hope it will be useful, but WITHOUT
> + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
> + * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License for
> + * more details.
> + *
> + * Authors:
> + *	jim liu <jim.liu at intel.com>
> + *	Uma Shankar <uma.shankar at intel.com>
> + */
> +
> +
> +#ifndef __HDMI_AUDIO_IF_H
> +#define __HDMI_AUDIO_IF_H
> +
> +#include <linux/types.h>
> +#include <drm/drmP.h>
> +
> +/* HDMI AUDIO INTERRUPT TYPE */
> +#define HDMI_AUDIO_UNDERRUN     (1UL<<0)
> +#define HDMI_AUDIO_BUFFER_DONE  (1UL<<1)
> +
> +/* the monitor type HDMI or DVI */
> +#define MONITOR_TYPE_HDMI 1
> +#define MONITOR_TYPE_DVI  2
> +
> +extern int i915_hdmi_state;
> +extern int i915_notify_had;
> +
> +enum had_caps_list {
> +	HAD_GET_ELD = 1,
> +	HAD_GET_SAMPLING_FREQ,
> +	HAD_GET_DISPLAY_RATE,
> +	HAD_GET_HDCP_STATUS,
> +	HAD_GET_AUDIO_STATUS,
> +	HAD_SET_ENABLE_AUDIO,
> +	HAD_SET_DISABLE_AUDIO,
> +	HAD_SET_ENABLE_AUDIO_INT,
> +	HAD_SET_DISABLE_AUDIO_INT,
> +	OTHERS_TBD,
> +};
> +
> +enum had_event_type {
> +	HAD_EVENT_HOT_PLUG = 1,
> +	HAD_EVENT_HOT_UNPLUG,
> +	HAD_EVENT_MODE_CHANGING,
> +	HAD_EVENT_PM_CHANGING,
> +	HAD_EVENT_AUDIO_BUFFER_DONE,
> +	HAD_EVENT_AUDIO_BUFFER_UNDERRUN,
> +	HAD_EVENT_QUERY_IS_AUDIO_BUSY,
> +	HAD_EVENT_QUERY_IS_AUDIO_SUSPENDED,

Kinda hard to see where everything gets used due to the way the patches
are split up.

At least the hotplug/mode change events are not needed. We only have the
two points where i915 should inform the audio driver about this stuff,
and those are the intel_audio_code_enable/disable(). For that we
already have the .pin_eld_notify() hook.

The interrupt stuff should mostly vanish from i915 with the subdevice
approach. As in i915 would just call the interrupt handler of the audio
driver based on the LPE bits in IIR, and the audio driver can then do
whatever it wants based on its own status register.

> +};
> +
> +/*
> + * HDMI Display Controller Audio Interface
> + *
> + */
> +typedef int (*had_event_call_back) (enum had_event_type event_type,
> +		void *ctxt_info);
> +
> +struct hdmi_audio_registers_ops {
> +	int (*hdmi_audio_read_register)(uint32_t reg_addr, uint32_t *data);
> +	int (*hdmi_audio_write_register)(uint32_t reg_addr, uint32_t data);
> +	int (*hdmi_audio_read_modify)(uint32_t reg_addr, uint32_t data,
> +			uint32_t mask);
> +};
> +
> +struct hdmi_audio_query_set_ops {
> +	int (*hdmi_audio_get_caps)(enum had_caps_list query_element,
> +			void *capabilties);
> +	int (*hdmi_audio_set_caps)(enum had_caps_list set_element,
> +			void *capabilties);
> +};
> +
> +typedef struct hdmi_audio_event {
> +	int type;
> +} hdmi_audio_event_t;
> +
> +struct snd_intel_had_interface {
> +	const char *name;
> +	int (*query)(void *had_data, hdmi_audio_event_t event);
> +	int (*suspend)(void *had_data, hdmi_audio_event_t event);
> +	int (*resume)(void *had_data);
> +};
> +
> +struct hdmi_audio_priv {
> +	struct drm_device *dev;
> +	u32 hdmib_reg;
> +
> +	bool is_hdcp_supported;
> +	bool hdmi_hpd_connected;
> +	int monitor_type;
> +	void *context;
> +};
> +
> +extern void i915_hdmi_audio_init(struct hdmi_audio_priv *p_hdmi_priv);
> +
> +extern bool mid_hdmi_audio_is_busy(struct drm_device *dev);
> +extern bool mid_hdmi_audio_suspend(struct drm_device *dev);
> +extern void mid_hdmi_audio_resume(struct drm_device *dev);
> +extern void mid_hdmi_audio_signal_event(struct drm_device *dev,
> +		enum had_event_type event);
> +
> +/* Added for HDMI Audio */
> +extern void hdmi_get_eld(uint8_t *eld);
> +extern int i915_enable_hdmi_audio_int(struct drm_device *dev);
> +extern int i915_disable_hdmi_audio_int(struct drm_device *dev);
> +extern int mid_hdmi_audio_setup(
> +	had_event_call_back audio_callbacks,
> +	struct hdmi_audio_registers_ops *reg_ops,
> +	struct hdmi_audio_query_set_ops *query_ops);
> +extern int mid_hdmi_audio_register(
> +	struct snd_intel_had_interface *driver,
> +	void *had_data);
> +
> +#endif /* __HDMI_AUDIO_IF_H */
> diff --git a/drivers/gpu/drm/i915/i915_drv.h b/drivers/gpu/drm/i915/i915_drv.h
> index 2cb0a41..5dceb5b 100644
> --- a/drivers/gpu/drm/i915/i915_drv.h
> +++ b/drivers/gpu/drm/i915/i915_drv.h
> @@ -53,6 +53,7 @@
>  #include <linux/kref.h>
>  #include <linux/pm_qos.h>
>  #include "intel_guc.h"
> +#include "hdmi_audio_if.h"
>  
>  /* General customization:
>   */
> @@ -1196,6 +1197,18 @@ struct intel_gen6_power_mgmt {
>  	struct mutex hw_lock;
>  };
>  
> +/* Runtime power management related */
> +struct intel_gen7_rpm {
> +	/* To track (num of get calls - num of put calls)
> +	 * made by procfs
> +	 */
> +	atomic_t procfs_count;
> +	/* To make sure ring get/put are in pair */
> +	bool ring_active;
> +	struct proc_dir_entry *i915_proc_dir;
> +	struct proc_dir_entry *i915_proc_file;
> +};
> +
>  /* defined intel_pm.c */
>  extern spinlock_t mchdev_lock;
>  
> @@ -2018,6 +2031,19 @@ struct drm_i915_private {
>  
>  	struct intel_encoder *dig_port_map[I915_MAX_PORTS];
>  
> +	/* Added for HDMI Audio */
> +	had_event_call_back had_event_callbacks;
> +	struct snd_intel_had_interface *had_interface;
> +	void *had_pvt_data;
> +	int tmds_clock_speed;
> +	int hdmi_audio_interrupt_mask;
> +	struct work_struct hdmi_audio_wq;
> +
> +	u32 hotplug_status;
> +
> +	/* Runtime power management related */
> +	struct intel_gen7_rpm rpm;
> +
>  	/*
>  	 * NOTE: This is the dri1/ums dungeon, don't add stuff here. Your patch
>  	 * will be rejected. Instead look for a better place.
> @@ -3537,6 +3563,11 @@ int intel_freq_opcode(struct drm_i915_private *dev_priv, int val);
>  	} while (upper != old_upper && loop++ < 2);			\
>  	(u64)upper << 32 | lower; })
>  
> +int i915_rpm_get_disp(struct drm_device *dev);
> +int i915_rpm_put_disp(struct drm_device *dev);
> +
> +bool i915_is_device_active(struct drm_device *dev);
> +
>  #define POSTING_READ(reg)	(void)I915_READ_NOTRACE(reg)
>  #define POSTING_READ16(reg)	(void)I915_READ16_NOTRACE(reg)
>  
> diff --git a/drivers/gpu/drm/i915/i915_reg.h b/drivers/gpu/drm/i915/i915_reg.h
> index 228b22f..370371c 100644
> --- a/drivers/gpu/drm/i915/i915_reg.h
> +++ b/drivers/gpu/drm/i915/i915_reg.h
> @@ -2062,7 +2062,12 @@ enum skl_disp_power_wells {
>  #define I915_WINVALID_INTERRUPT				(1<<1)
>  #define I915_USER_INTERRUPT				(1<<1)
>  #define I915_ASLE_INTERRUPT				(1<<0)
> +#define I915_LPE_AUDIO_HDMI_STATUS_A	_MMIO(dev_priv->info.display_mmio_offset + 0x65064)
> +#define I915_LPE_AUDIO_HDMI_STATUS_B	_MMIO(dev_priv->info.display_mmio_offset + 0x65864)
> +#define I915_HDMI_AUDIO_UNDERRUN			(1UL<<31)
> +#define I915_HDMI_AUDIO_BUFFER_DONE			(1UL<<29)
>  #define I915_BSD_USER_INTERRUPT				(1<<25)
> +#define I915_HDMI_AUDIO_UNDERRUN_ENABLE			(1UL<<15)
>  
>  #define GEN6_BSD_RNCID			_MMIO(0x12198)
>  
> @@ -3364,6 +3369,7 @@ enum skl_disp_power_wells {
>  #define _GEN3_SDVOC	0x61160
>  #define GEN3_SDVOB	_MMIO(_GEN3_SDVOB)
>  #define GEN3_SDVOC	_MMIO(_GEN3_SDVOC)
> +#define HDMIB	(dev_priv->info.display_mmio_offset + 0x61140)
>  #define GEN4_HDMIB	GEN3_SDVOB
>  #define GEN4_HDMIC	GEN3_SDVOC
>  #define VLV_HDMIB	_MMIO(VLV_DISPLAY_BASE + 0x61140)
> @@ -3373,6 +3379,7 @@ enum skl_disp_power_wells {
>  #define PCH_HDMIB	PCH_SDVOB
>  #define PCH_HDMIC	_MMIO(0xe1150)
>  #define PCH_HDMID	_MMIO(0xe1160)
> +#define PORT_ENABLE	(1 << 31)
>  
>  #define PORT_DFT_I9XX				_MMIO(0x61150)
>  #define   DC_BALANCE_RESET			(1 << 25)
> diff --git a/drivers/gpu/drm/i915/intel_drv.h b/drivers/gpu/drm/i915/intel_drv.h
> index cb413e2..adfd27c 100644
> --- a/drivers/gpu/drm/i915/intel_drv.h
> +++ b/drivers/gpu/drm/i915/intel_drv.h
> @@ -724,6 +724,14 @@ struct cxsr_latency {
>  #define to_intel_plane_state(x) container_of(x, struct intel_plane_state, base)
>  #define intel_fb_obj(x) (x ? to_intel_framebuffer(x)->obj : NULL)
>  
> +/* HDMI bits are shared with the DP bits */
> +#define   HDMIB_HOTPLUG_LIVE_STATUS             (1 << 29)
> +#define   HDMIC_HOTPLUG_LIVE_STATUS             (1 << 28)
> +#define   HDMID_HOTPLUG_LIVE_STATUS             (1 << 27)
> +#define   HDMI_LIVE_STATUS_BASE			30
> +#define   HDMI_LIVE_STATUS_DELAY_STEP		10
> +#define   HDMI_EDID_RETRY_COUNT			3
> +
>  struct intel_hdmi {
>  	i915_reg_t hdmi_reg;
>  	int ddc_bus;
> @@ -735,6 +743,9 @@ struct intel_hdmi {
>  	bool rgb_quant_range_selectable;
>  	enum hdmi_picture_aspect aspect_ratio;
>  	struct intel_connector *attached_connector;
> +	struct edid *edid;
> +	uint32_t edid_mode_count;
> +
>  	void (*write_infoframe)(struct drm_encoder *encoder,
>  				enum hdmi_infoframe_type type,
>  				const void *frame, ssize_t len);
> -- 
> 1.9.1
> 
> _______________________________________________
> Intel-gfx mailing list
> Intel-gfx at lists.freedesktop.org
> https://lists.freedesktop.org/mailman/listinfo/intel-gfx

-- 
Ville Syrjälä
Intel OTC


More information about the Intel-gfx mailing list