diff options
-rw-r--r-- | sound/soc/intel/skylake/skl-sst-ipc.h | 5 | ||||
-rw-r--r-- | sound/soc/intel/skylake/skl.c | 55 | ||||
-rw-r--r-- | sound/soc/intel/skylake/skl.h | 3 |
3 files changed, 60 insertions, 3 deletions
diff --git a/sound/soc/intel/skylake/skl-sst-ipc.h b/sound/soc/intel/skylake/skl-sst-ipc.h index 1bbcdb471cf2..d59d1ba62a43 100644 --- a/sound/soc/intel/skylake/skl-sst-ipc.h +++ b/sound/soc/intel/skylake/skl-sst-ipc.h | |||
@@ -55,6 +55,11 @@ struct skl_sst { | |||
55 | 55 | ||
56 | /* IPC messaging */ | 56 | /* IPC messaging */ |
57 | struct sst_generic_ipc ipc; | 57 | struct sst_generic_ipc ipc; |
58 | |||
59 | /* callback for miscbdge */ | ||
60 | void (*enable_miscbdcge)(struct device *dev, bool enable); | ||
61 | /*Is CGCTL.MISCBDCGE disabled*/ | ||
62 | bool miscbdcg_disabled; | ||
58 | }; | 63 | }; |
59 | 64 | ||
60 | struct skl_ipc_init_instance_msg { | 65 | struct skl_ipc_init_instance_msg { |
diff --git a/sound/soc/intel/skylake/skl.c b/sound/soc/intel/skylake/skl.c index b69649aa7809..dd38f5feb7c0 100644 --- a/sound/soc/intel/skylake/skl.c +++ b/sound/soc/intel/skylake/skl.c | |||
@@ -29,6 +29,8 @@ | |||
29 | #include <sound/pcm.h> | 29 | #include <sound/pcm.h> |
30 | #include "../common/sst-acpi.h" | 30 | #include "../common/sst-acpi.h" |
31 | #include "skl.h" | 31 | #include "skl.h" |
32 | #include "skl-sst-dsp.h" | ||
33 | #include "skl-sst-ipc.h" | ||
32 | 34 | ||
33 | /* | 35 | /* |
34 | * initialize the PCI registers | 36 | * initialize the PCI registers |
@@ -59,6 +61,49 @@ static void skl_init_pci(struct skl *skl) | |||
59 | skl_update_pci_byte(skl->pci, AZX_PCIREG_TCSEL, 0x07, 0); | 61 | skl_update_pci_byte(skl->pci, AZX_PCIREG_TCSEL, 0x07, 0); |
60 | } | 62 | } |
61 | 63 | ||
64 | static void update_pci_dword(struct pci_dev *pci, | ||
65 | unsigned int reg, u32 mask, u32 val) | ||
66 | { | ||
67 | u32 data = 0; | ||
68 | |||
69 | pci_read_config_dword(pci, reg, &data); | ||
70 | data &= ~mask; | ||
71 | data |= (val & mask); | ||
72 | pci_write_config_dword(pci, reg, data); | ||
73 | } | ||
74 | |||
75 | /* | ||
76 | * skl_enable_miscbdcge - enable/dsiable CGCTL.MISCBDCGE bits | ||
77 | * | ||
78 | * @dev: device pointer | ||
79 | * @enable: enable/disable flag | ||
80 | */ | ||
81 | static void skl_enable_miscbdcge(struct device *dev, bool enable) | ||
82 | { | ||
83 | struct pci_dev *pci = to_pci_dev(dev); | ||
84 | u32 val; | ||
85 | |||
86 | val = enable ? AZX_CGCTL_MISCBDCGE_MASK : 0; | ||
87 | |||
88 | update_pci_dword(pci, AZX_PCIREG_CGCTL, AZX_CGCTL_MISCBDCGE_MASK, val); | ||
89 | } | ||
90 | |||
91 | /* | ||
92 | * While performing reset, controller may not come back properly causing | ||
93 | * issues, so recommendation is to set CGCTL.MISCBDCGE to 0 then do reset | ||
94 | * (init chip) and then again set CGCTL.MISCBDCGE to 1 | ||
95 | */ | ||
96 | static int skl_init_chip(struct hdac_bus *bus, bool full_reset) | ||
97 | { | ||
98 | int ret; | ||
99 | |||
100 | skl_enable_miscbdcge(bus->dev, false); | ||
101 | ret = snd_hdac_bus_init_chip(bus, full_reset); | ||
102 | skl_enable_miscbdcge(bus->dev, true); | ||
103 | |||
104 | return ret; | ||
105 | } | ||
106 | |||
62 | /* called from IRQ */ | 107 | /* called from IRQ */ |
63 | static void skl_stream_update(struct hdac_bus *bus, struct hdac_stream *hstr) | 108 | static void skl_stream_update(struct hdac_bus *bus, struct hdac_stream *hstr) |
64 | { | 109 | { |
@@ -145,7 +190,9 @@ static int _skl_suspend(struct hdac_ext_bus *ebus) | |||
145 | return ret; | 190 | return ret; |
146 | 191 | ||
147 | snd_hdac_bus_stop_chip(bus); | 192 | snd_hdac_bus_stop_chip(bus); |
193 | skl_enable_miscbdcge(bus->dev, false); | ||
148 | snd_hdac_bus_enter_link_reset(bus); | 194 | snd_hdac_bus_enter_link_reset(bus); |
195 | skl_enable_miscbdcge(bus->dev, true); | ||
149 | 196 | ||
150 | return 0; | 197 | return 0; |
151 | } | 198 | } |
@@ -156,7 +203,7 @@ static int _skl_resume(struct hdac_ext_bus *ebus) | |||
156 | struct hdac_bus *bus = ebus_to_hbus(ebus); | 203 | struct hdac_bus *bus = ebus_to_hbus(ebus); |
157 | 204 | ||
158 | skl_init_pci(skl); | 205 | skl_init_pci(skl); |
159 | snd_hdac_bus_init_chip(bus, true); | 206 | skl_init_chip(bus, true); |
160 | 207 | ||
161 | return skl_resume_dsp(skl); | 208 | return skl_resume_dsp(skl); |
162 | } | 209 | } |
@@ -380,7 +427,7 @@ static int skl_codec_create(struct hdac_ext_bus *ebus) | |||
380 | * back to the sanity state. | 427 | * back to the sanity state. |
381 | */ | 428 | */ |
382 | snd_hdac_bus_stop_chip(bus); | 429 | snd_hdac_bus_stop_chip(bus); |
383 | snd_hdac_bus_init_chip(bus, true); | 430 | skl_init_chip(bus, true); |
384 | } | 431 | } |
385 | } | 432 | } |
386 | } | 433 | } |
@@ -490,7 +537,7 @@ static int skl_first_init(struct hdac_ext_bus *ebus) | |||
490 | /* initialize chip */ | 537 | /* initialize chip */ |
491 | skl_init_pci(skl); | 538 | skl_init_pci(skl); |
492 | 539 | ||
493 | snd_hdac_bus_init_chip(bus, true); | 540 | skl_init_chip(bus, true); |
494 | 541 | ||
495 | /* codec detection */ | 542 | /* codec detection */ |
496 | if (!bus->codec_mask) { | 543 | if (!bus->codec_mask) { |
@@ -539,6 +586,8 @@ static int skl_probe(struct pci_dev *pci, | |||
539 | dev_dbg(bus->dev, "error failed to register dsp\n"); | 586 | dev_dbg(bus->dev, "error failed to register dsp\n"); |
540 | goto out_mach_free; | 587 | goto out_mach_free; |
541 | } | 588 | } |
589 | skl->skl_sst->enable_miscbdcge = skl_enable_miscbdcge; | ||
590 | |||
542 | } | 591 | } |
543 | if (ebus->mlcap) | 592 | if (ebus->mlcap) |
544 | snd_hdac_ext_bus_get_ml_capabilities(ebus); | 593 | snd_hdac_ext_bus_get_ml_capabilities(ebus); |
diff --git a/sound/soc/intel/skylake/skl.h b/sound/soc/intel/skylake/skl.h index 36a1b8c5f6d0..8a08bb727991 100644 --- a/sound/soc/intel/skylake/skl.h +++ b/sound/soc/intel/skylake/skl.h | |||
@@ -48,6 +48,9 @@ | |||
48 | #define AZX_REG_VS_SDXEFIFOS_XBASE 0x1094 | 48 | #define AZX_REG_VS_SDXEFIFOS_XBASE 0x1094 |
49 | #define AZX_REG_VS_SDXEFIFOS_XINTERVAL 0x20 | 49 | #define AZX_REG_VS_SDXEFIFOS_XINTERVAL 0x20 |
50 | 50 | ||
51 | #define AZX_PCIREG_CGCTL 0x48 | ||
52 | #define AZX_CGCTL_MISCBDCGE_MASK (1 << 6) | ||
53 | |||
51 | struct skl_dsp_resource { | 54 | struct skl_dsp_resource { |
52 | u32 max_mcps; | 55 | u32 max_mcps; |
53 | u32 max_mem; | 56 | u32 max_mem; |