History

Merge remote-tracking branch 'asoc/topic/intel' into asoc-next

Mark Brown committed 9 years ago

Commit 460f6232 parents 39e0a0a 38a770830 files · +2419 −277Browse files

Unified · Split

30 files
  1. include/uapi/sound/snd_sst_tokens.h +91 −1
  2. sound/soc/codecs/Makefile +1 −0
  3. sound/soc/codecs/hdac_hdmi.c +34 −5
  4. sound/soc/codecs/max98371.c +8 −6
  5. sound/soc/intel/Kconfig +2 −1
  6. sound/soc/intel/atom/sst-mfld-platform-pcm.c +5 −5
  7. sound/soc/intel/atom/sst/sst_drv_interface.c +2 −2
  8. sound/soc/intel/atom/sst/sst_pci.c +1 −1
  9. sound/soc/intel/baytrail/sst-baytrail-pcm.c +2 −2
  10. sound/soc/intel/boards/bxt_rt298.c +82 −4
  11. sound/soc/intel/boards/kbl_rt5663_max98927.c +258 −52
  12. sound/soc/intel/boards/kbl_rt5663_rt5514_max98927.c +68 −13
  13. sound/soc/intel/boards/mfld_machine.c +1 −3
  14. sound/soc/intel/haswell/sst-haswell-pcm.c +1 −1
  15. sound/soc/intel/skylake/Makefile +3 −2
  16. sound/soc/intel/skylake/bxt-sst.c +7 −7
  17. sound/soc/intel/skylake/cnl-sst-dsp.c +274 −0
  18. sound/soc/intel/skylake/cnl-sst-dsp.h +112 −0
  19. sound/soc/intel/skylake/cnl-sst.c +497 −0
  20. sound/soc/intel/skylake/skl-messages.c +135 −28
  21. sound/soc/intel/skylake/skl-pcm.c +72 −10
  22. sound/soc/intel/skylake/skl-sst-dsp.c +3 −3
  23. sound/soc/intel/skylake/skl-sst-ipc.c +3 −3
  24. sound/soc/intel/skylake/skl-sst-ipc.h +8 −4
  25. sound/soc/intel/skylake/skl-sst-utils.c +1 −5
  26. sound/soc/intel/skylake/skl-sst.c +8 −4
  27. sound/soc/intel/skylake/skl-topology.c +633 −108
  28. sound/soc/intel/skylake/skl-topology.h +83 −0
  29. sound/soc/intel/skylake/skl.c +21 −7
  30. sound/soc/intel/skylake/skl.h +3 −0
include/uapi/sound/snd_sst_tokens.h+91−1
@@ -163,8 +163,71 @@ · 162 unmodified lines
163 *163 *
164 * %SKL_TKN_U32_DMA_BUF_SIZE: DMA buffer size in millisec164 * %SKL_TKN_U32_DMA_BUF_SIZE: DMA buffer size in millisec
165 *165 *
166 * %SKL_TKN_U32_PIPE_DIR: Specifies pipe direction. Can be
167 * playback/capture.
168 *
169 * %SKL_TKN_U32_NUM_CONFIGS: Number of pipe configs
170 *
171 * %SKL_TKN_U32_PATH_MEM_PGS: Size of memory (in pages) required for pipeline
172 * and its data
173 *
174 * %SKL_TKN_U32_PIPE_CONFIG_ID: Config id for the modules in the pipe
175 * and PCM params supported by that pipe
176 * config. This is used as index to fill
177 * up the pipe config and module config
178 * structure.
179 *
180 * %SKL_TKN_U32_CFG_FREQ:
181 * %SKL_TKN_U8_CFG_CHAN:
182 * %SKL_TKN_U8_CFG_BPS: PCM params (freq, channels, bits per sample)
183 * supported for each of the pipe configs.
184 *
185 * %SKL_TKN_CFG_MOD_RES_ID: Module's resource index for each of the
186 * pipe config
187 *
188 * %SKL_TKN_CFG_MOD_FMT_ID: Module's interface index for each of the
189 * pipe config
190 *
191 * %SKL_TKN_U8_NUM_MOD: Number of modules in the manifest
192 *
193 * %SKL_TKN_MM_U8_MOD_IDX: Current index of the module in the manifest
194 *
195 * %SKL_TKN_MM_U8_NUM_RES: Number of resources for the module
196 *
197 * %SKL_TKN_MM_U8_NUM_INTF: Number of interfaces for the module
198 *
199 * %SKL_TKN_MM_U32_RES_ID: Resource index for the resource info to
200 * be filled into.
201 * A module can support multiple resource
202 * configuration and is represnted as a
203 * resource table. This index is used to
204 * fill information into appropriate index.
205 *
206 * %SKL_TKN_MM_U32_CPS: DSP cycles per second
207 *
208 * %SKL_TKN_MM_U32_DMA_SIZE: Allocated buffer size for gateway DMA
209 *
210 * %SKL_TKN_MM_U32_CPC: DSP cycles allocated per frame
211 *
212 * %SKL_TKN_MM_U32_RES_PIN_ID: Resource pin index in the module
213 *
214 * %SKL_TKN_MM_U32_INTF_PIN_ID: Interface index in the module
215 *
216 * %SKL_TKN_MM_U32_PIN_BUF: Buffer size of the module pin
217 *
218 * %SKL_TKN_MM_U32_FMT_ID: Format index for each of the interface/
219 * format information to be filled into.
220 *
221 * %SKL_TKN_MM_U32_NUM_IN_FMT: Number of input formats
222 * %SKL_TKN_MM_U32_NUM_OUT_FMT: Number of output formats
223 *
166 * module_id and loadable flags dont have tokens as these values will be224 * module_id and loadable flags dont have tokens as these values will be
167 * read from the DSP FW manifest225 * read from the DSP FW manifest
226 *
227 * Tokens defined can be used either in the manifest or widget private data.
228 *
229 * SKL_TKN_MM is used as a suffix for all tokens that represent
230 * module data in the manifest.
168 */231 */
169enum SKL_TKNS {232enum SKL_TKNS {
170 SKL_TKN_UUID = 1,233 SKL_TKN_UUID = 1,
@@ -218,7 +281,34 @@ enum SKL_TKNS { · 47 unmodified lines
218 SKL_TKL_U32_D0I3_CAPS, /* Typo added at v4.10 */281 SKL_TKL_U32_D0I3_CAPS, /* Typo added at v4.10 */
219 SKL_TKN_U32_D0I3_CAPS = SKL_TKL_U32_D0I3_CAPS,282 SKL_TKN_U32_D0I3_CAPS = SKL_TKL_U32_D0I3_CAPS,
220 SKL_TKN_U32_DMA_BUF_SIZE,283 SKL_TKN_U32_DMA_BUF_SIZE,
221 SKL_TKN_MAX = SKL_TKN_U32_DMA_BUF_SIZE,284
285 SKL_TKN_U32_PIPE_DIRECTION,
286 SKL_TKN_U32_PIPE_CONFIG_ID,
287 SKL_TKN_U32_NUM_CONFIGS,
288 SKL_TKN_U32_PATH_MEM_PGS,
289
290 SKL_TKN_U32_CFG_FREQ,
291 SKL_TKN_U8_CFG_CHAN,
292 SKL_TKN_U8_CFG_BPS,
293 SKL_TKN_CFG_MOD_RES_ID,
294 SKL_TKN_CFG_MOD_FMT_ID,
295 SKL_TKN_U8_NUM_MOD,
296
297 SKL_TKN_MM_U8_MOD_IDX,
298 SKL_TKN_MM_U8_NUM_RES,
299 SKL_TKN_MM_U8_NUM_INTF,
300 SKL_TKN_MM_U32_RES_ID,
301 SKL_TKN_MM_U32_CPS,
302 SKL_TKN_MM_U32_DMA_SIZE,
303 SKL_TKN_MM_U32_CPC,
304 SKL_TKN_MM_U32_RES_PIN_ID,
305 SKL_TKN_MM_U32_INTF_PIN_ID,
306 SKL_TKN_MM_U32_PIN_BUF,
307 SKL_TKN_MM_U32_FMT_ID,
308 SKL_TKN_MM_U32_NUM_IN_FMT,
309 SKL_TKN_MM_U32_NUM_OUT_FMT,
310
311 SKL_TKN_MAX = SKL_TKN_MM_U32_NUM_OUT_FMT,
222};312};
223 313
224#endif314#endif
sound/soc/codecs/Makefile+1−0
@@ -321,6 +321,7 @@ obj-$(CONFIG_SND_SOC_MAX98088) += snd-soc-max98088.o · 320 unmodified lines
321obj-$(CONFIG_SND_SOC_MAX98090) += snd-soc-max98090.o321obj-$(CONFIG_SND_SOC_MAX98090) += snd-soc-max98090.o
322obj-$(CONFIG_SND_SOC_MAX98095) += snd-soc-max98095.o322obj-$(CONFIG_SND_SOC_MAX98095) += snd-soc-max98095.o
323obj-$(CONFIG_SND_SOC_MAX98357A) += snd-soc-max98357a.o323obj-$(CONFIG_SND_SOC_MAX98357A) += snd-soc-max98357a.o
324obj-$(CONFIG_SND_SOC_MAX98371) += snd-soc-max98371.o
324obj-$(CONFIG_SND_SOC_MAX9867) += snd-soc-max9867.o325obj-$(CONFIG_SND_SOC_MAX9867) += snd-soc-max9867.o
325obj-$(CONFIG_SND_SOC_MAX98925) += snd-soc-max98925.o326obj-$(CONFIG_SND_SOC_MAX98925) += snd-soc-max98925.o
326obj-$(CONFIG_SND_SOC_MAX98926) += snd-soc-max98926.o327obj-$(CONFIG_SND_SOC_MAX98926) += snd-soc-max98926.o
sound/soc/codecs/hdac_hdmi.c+34−5
@@ -121,6 +121,10 @@ struct hdac_hdmi_dai_port_map { · 120 unmodified lines
121 struct hdac_hdmi_cvt *cvt;121 struct hdac_hdmi_cvt *cvt;
122};122};
123 123
124struct hdac_hdmi_drv_data {
125 unsigned int vendor_nid;
126};
127
124struct hdac_hdmi_priv {128struct hdac_hdmi_priv {
125 struct hdac_hdmi_dai_port_map dai_map[HDA_MAX_CVTS];129 struct hdac_hdmi_dai_port_map dai_map[HDA_MAX_CVTS];
126 struct list_head pin_list;130 struct list_head pin_list;
@@ -131,6 +135,7 @@ struct hdac_hdmi_priv { · 4 unmodified lines
131 int num_ports;135 int num_ports;
132 struct mutex pin_mutex;136 struct mutex pin_mutex;
133 struct hdac_chmap chmap;137 struct hdac_chmap chmap;
138 struct hdac_hdmi_drv_data *drv_data;
134};139};
135 140
136static struct hdac_hdmi_pcm *141static struct hdac_hdmi_pcm *
@@ -1321,6 +1326,7 @@ static int hdac_hdmi_add_pin(struct hdac_ext_device *edev, hda_nid_t nid) · 1184 unmodified lines
1321}1326}
1322 1327
1323#define INTEL_VENDOR_NID 0x081328#define INTEL_VENDOR_NID 0x08
1329#define INTEL_GLK_VENDOR_NID 0x0b
1324#define INTEL_GET_VENDOR_VERB 0xf811330#define INTEL_GET_VENDOR_VERB 0xf81
1325#define INTEL_SET_VENDOR_VERB 0x7811331#define INTEL_SET_VENDOR_VERB 0x781
1326#define INTEL_EN_DP12 0x02 /* enable DP 1.2 features */1332#define INTEL_EN_DP12 0x02 /* enable DP 1.2 features */
@@ -1329,14 +1335,17 @@ static int hdac_hdmi_add_pin(struct hdac_ext_device *edev, hda_nid_t nid) · 2 unmodified lines
1329static void hdac_hdmi_skl_enable_all_pins(struct hdac_device *hdac)1335static void hdac_hdmi_skl_enable_all_pins(struct hdac_device *hdac)
1330{1336{
1331 unsigned int vendor_param;1337 unsigned int vendor_param;
1338 struct hdac_ext_device *edev = to_ehdac_device(hdac);
1339 struct hdac_hdmi_priv *hdmi = edev->private_data;
1340 unsigned int vendor_nid = hdmi->drv_data->vendor_nid;
1332 1341
1333 vendor_param = snd_hdac_codec_read(hdac, INTEL_VENDOR_NID, 0,1342 vendor_param = snd_hdac_codec_read(hdac, vendor_nid, 0,
1334 INTEL_GET_VENDOR_VERB, 0);1343 INTEL_GET_VENDOR_VERB, 0);
1335 if (vendor_param == -1 || vendor_param & INTEL_EN_ALL_PIN_CVTS)1344 if (vendor_param == -1 || vendor_param & INTEL_EN_ALL_PIN_CVTS)
1336 return;1345 return;
1337 1346
1338 vendor_param |= INTEL_EN_ALL_PIN_CVTS;1347 vendor_param |= INTEL_EN_ALL_PIN_CVTS;
1339 vendor_param = snd_hdac_codec_read(hdac, INTEL_VENDOR_NID, 0,1348 vendor_param = snd_hdac_codec_read(hdac, vendor_nid, 0,
1340 INTEL_SET_VENDOR_VERB, vendor_param);1349 INTEL_SET_VENDOR_VERB, vendor_param);
1341 if (vendor_param == -1)1350 if (vendor_param == -1)
1342 return;1351 return;
@@ -1345,15 +1354,18 @@ static void hdac_hdmi_skl_enable_all_pins(struct hdac_device *hdac) · 2 unmodified lines
1345static void hdac_hdmi_skl_enable_dp12(struct hdac_device *hdac)1354static void hdac_hdmi_skl_enable_dp12(struct hdac_device *hdac)
1346{1355{
1347 unsigned int vendor_param;1356 unsigned int vendor_param;
1357 struct hdac_ext_device *edev = to_ehdac_device(hdac);
1358 struct hdac_hdmi_priv *hdmi = edev->private_data;
1359 unsigned int vendor_nid = hdmi->drv_data->vendor_nid;
1348 1360
1349 vendor_param = snd_hdac_codec_read(hdac, INTEL_VENDOR_NID, 0,1361 vendor_param = snd_hdac_codec_read(hdac, vendor_nid, 0,
1350 INTEL_GET_VENDOR_VERB, 0);1362 INTEL_GET_VENDOR_VERB, 0);
1351 if (vendor_param == -1 || vendor_param & INTEL_EN_DP12)1363 if (vendor_param == -1 || vendor_param & INTEL_EN_DP12)
1352 return;1364 return;
1353 1365
1354 /* enable DP1.2 mode */1366 /* enable DP1.2 mode */
1355 vendor_param |= INTEL_EN_DP12;1367 vendor_param |= INTEL_EN_DP12;
1356 vendor_param = snd_hdac_codec_read(hdac, INTEL_VENDOR_NID, 0,1368 vendor_param = snd_hdac_codec_read(hdac, vendor_nid, 0,
1357 INTEL_SET_VENDOR_VERB, vendor_param);1369 INTEL_SET_VENDOR_VERB, vendor_param);
1358 if (vendor_param == -1)1370 if (vendor_param == -1)
1359 return;1371 return;
@@ -1927,6 +1939,14 @@ static int hdac_hdmi_get_spk_alloc(struct hdac_device *hdac, int pcm_idx) · 567 unmodified lines
1927 return port->eld.info.spk_alloc;1939 return port->eld.info.spk_alloc;
1928}1940}
1929 1941
1942static struct hdac_hdmi_drv_data intel_glk_drv_data = {
1943 .vendor_nid = INTEL_GLK_VENDOR_NID,
1944};
1945
1946static struct hdac_hdmi_drv_data intel_drv_data = {
1947 .vendor_nid = INTEL_VENDOR_NID,
1948};
1949
1930static int hdac_hdmi_dev_probe(struct hdac_ext_device *edev)1950static int hdac_hdmi_dev_probe(struct hdac_ext_device *edev)
1931{1951{
1932 struct hdac_device *codec = &edev->hdac;1952 struct hdac_device *codec = &edev->hdac;
@@ -1935,6 +1955,8 @@ static int hdac_hdmi_dev_probe(struct hdac_ext_device *edev) · 2 unmodified lines
1935 struct hdac_ext_link *hlink = NULL;1955 struct hdac_ext_link *hlink = NULL;
1936 int num_dais = 0;1956 int num_dais = 0;
1937 int ret = 0;1957 int ret = 0;
1958 struct hdac_driver *hdrv = drv_to_hdac_driver(codec->dev.driver);
1959 const struct hda_device_id *hdac_id = hdac_get_device_id(codec, hdrv);
1938 1960
1939 /* hold the ref while we probe */1961 /* hold the ref while we probe */
1940 hlink = snd_hdac_ext_bus_get_link(edev->ebus, dev_name(&edev->hdac.dev));1962 hlink = snd_hdac_ext_bus_get_link(edev->ebus, dev_name(&edev->hdac.dev));
@@ -1956,6 +1978,12 @@ static int hdac_hdmi_dev_probe(struct hdac_ext_device *edev) · 15 unmodified lines
1956 hdmi_priv->chmap.ops.is_pcm_attached = is_hdac_hdmi_pcm_attached;1978 hdmi_priv->chmap.ops.is_pcm_attached = is_hdac_hdmi_pcm_attached;
1957 hdmi_priv->chmap.ops.get_spk_alloc = hdac_hdmi_get_spk_alloc;1979 hdmi_priv->chmap.ops.get_spk_alloc = hdac_hdmi_get_spk_alloc;
1958 1980
1981 if (hdac_id->driver_data)
1982 hdmi_priv->drv_data =
1983 (struct hdac_hdmi_drv_data *)hdac_id->driver_data;
1984 else
1985 hdmi_priv->drv_data = &intel_drv_data;
1986
1959 dev_set_drvdata(&codec->dev, edev);1987 dev_set_drvdata(&codec->dev, edev);
1960 1988
1961 INIT_LIST_HEAD(&hdmi_priv->pin_list);1989 INIT_LIST_HEAD(&hdmi_priv->pin_list);
@@ -2127,7 +2155,8 @@ static const struct hda_device_id hdmi_list[] = { · 165 unmodified lines
2127 HDA_CODEC_EXT_ENTRY(0x80862809, 0x100000, "Skylake HDMI", 0),2155 HDA_CODEC_EXT_ENTRY(0x80862809, 0x100000, "Skylake HDMI", 0),
2128 HDA_CODEC_EXT_ENTRY(0x8086280a, 0x100000, "Broxton HDMI", 0),2156 HDA_CODEC_EXT_ENTRY(0x8086280a, 0x100000, "Broxton HDMI", 0),
2129 HDA_CODEC_EXT_ENTRY(0x8086280b, 0x100000, "Kabylake HDMI", 0),2157 HDA_CODEC_EXT_ENTRY(0x8086280b, 0x100000, "Kabylake HDMI", 0),
2130 HDA_CODEC_EXT_ENTRY(0x8086280d, 0x100000, "Geminilake HDMI", 0),2158 HDA_CODEC_EXT_ENTRY(0x8086280d, 0x100000, "Geminilake HDMI",
2159 &intel_glk_drv_data),
2131 {}2160 {}
2132};2161};
2133 2162
sound/soc/codecs/max98371.c+8−6
@@ -349,12 +349,14 @@ static struct snd_soc_dai_driver max98371_dai[] = { · 348 unmodified lines
349};349};
350 350
351static const struct snd_soc_codec_driver max98371_codec = {351static const struct snd_soc_codec_driver max98371_codec = {
352 .controls = max98371_snd_controls,352 .component_driver = {
353 .num_controls = ARRAY_SIZE(max98371_snd_controls),353 .controls = max98371_snd_controls,
354 .dapm_routes = max98371_audio_map,354 .num_controls = ARRAY_SIZE(max98371_snd_controls),
355 .num_dapm_routes = ARRAY_SIZE(max98371_audio_map),355 .dapm_routes = max98371_audio_map,
356 .dapm_widgets = max98371_dapm_widgets,356 .num_dapm_routes = ARRAY_SIZE(max98371_audio_map),
357 .num_dapm_widgets = ARRAY_SIZE(max98371_dapm_widgets),357 .dapm_widgets = max98371_dapm_widgets,
358 .num_dapm_widgets = ARRAY_SIZE(max98371_dapm_widgets),
359 },
358};360};
359 361
360static const struct regmap_config max98371_regmap = {362static const struct regmap_config max98371_regmap = {
sound/soc/intel/Kconfig+2−1
@@ -255,11 +255,12 @@ config SND_SOC_INTEL_KBL_RT5663_MAX98927_MACH · 254 unmodified lines
255 255
256config SND_SOC_INTEL_KBL_RT5663_RT5514_MAX98927_MACH256config SND_SOC_INTEL_KBL_RT5663_RT5514_MAX98927_MACH
257 tristate "ASoC Audio driver for KBL with RT5663, RT5514 and MAX98927 in I2S Mode"257 tristate "ASoC Audio driver for KBL with RT5663, RT5514 and MAX98927 in I2S Mode"
258 depends on X86_INTEL_LPSS && I2C258 depends on X86_INTEL_LPSS && I2C && SPI
259 select SND_SOC_INTEL_SST259 select SND_SOC_INTEL_SST
260 select SND_SOC_INTEL_SKYLAKE260 select SND_SOC_INTEL_SKYLAKE
261 select SND_SOC_RT5663261 select SND_SOC_RT5663
262 select SND_SOC_RT5514262 select SND_SOC_RT5514
263 select SND_SOC_RT5514_SPI
263 select SND_SOC_MAX98927264 select SND_SOC_MAX98927
264 select SND_SOC_HDAC_HDMI265 select SND_SOC_HDAC_HDMI
265 help266 help
sound/soc/intel/atom/sst-mfld-platform-pcm.c+5−5
@@ -76,7 +76,7 @@ int sst_unregister_dsp(struct sst_device *dev) · 75 unmodified lines
76}76}
77EXPORT_SYMBOL_GPL(sst_unregister_dsp);77EXPORT_SYMBOL_GPL(sst_unregister_dsp);
78 78
79static struct snd_pcm_hardware sst_platform_pcm_hw = {79static const struct snd_pcm_hardware sst_platform_pcm_hw = {
80 .info = (SNDRV_PCM_INFO_INTERLEAVED |80 .info = (SNDRV_PCM_INFO_INTERLEAVED |
81 SNDRV_PCM_INFO_DOUBLE |81 SNDRV_PCM_INFO_DOUBLE |
82 SNDRV_PCM_INFO_PAUSE |82 SNDRV_PCM_INFO_PAUSE |
@@ -471,7 +471,7 @@ static void sst_disable_ssp(struct snd_pcm_substream *substream, · 388 unmodified lines
471 }471 }
472}472}
473 473
474static struct snd_soc_dai_ops sst_media_dai_ops = {474static const struct snd_soc_dai_ops sst_media_dai_ops = {
475 .startup = sst_media_open,475 .startup = sst_media_open,
476 .shutdown = sst_media_close,476 .shutdown = sst_media_close,
477 .prepare = sst_media_prepare,477 .prepare = sst_media_prepare,
@@ -480,11 +480,11 @@ static struct snd_soc_dai_ops sst_media_dai_ops = { · 2 unmodified lines
480 .mute_stream = sst_media_digital_mute,480 .mute_stream = sst_media_digital_mute,
481};481};
482 482
483static struct snd_soc_dai_ops sst_compr_dai_ops = {483static const struct snd_soc_dai_ops sst_compr_dai_ops = {
484 .mute_stream = sst_media_digital_mute,484 .mute_stream = sst_media_digital_mute,
485};485};
486 486
487static struct snd_soc_dai_ops sst_be_dai_ops = {487static const struct snd_soc_dai_ops sst_be_dai_ops = {
488 .startup = sst_enable_ssp,488 .startup = sst_enable_ssp,
489 .hw_params = sst_be_hw_params,489 .hw_params = sst_be_hw_params,
490 .set_fmt = sst_set_format,490 .set_fmt = sst_set_format,
@@ -705,7 +705,7 @@ static int sst_soc_probe(struct snd_soc_platform *platform) · 214 unmodified lines
705 return sst_dsp_init_v2_dpcm(platform);705 return sst_dsp_init_v2_dpcm(platform);
706}706}
707 707
708static struct snd_soc_platform_driver sst_soc_platform_drv = {708static const struct snd_soc_platform_driver sst_soc_platform_drv = {
709 .probe = sst_soc_probe,709 .probe = sst_soc_probe,
710 .ops = &sst_platform_ops,710 .ops = &sst_platform_ops,
711 .compr_ops = &sst_platform_compr_ops,711 .compr_ops = &sst_platform_compr_ops,
sound/soc/intel/atom/sst/sst_drv_interface.c+2−2
@@ -407,7 +407,7 @@ static int sst_cdev_caps(struct snd_compr_caps *caps) · 406 unmodified lines
407 return 0;407 return 0;
408}408}
409 409
410static struct snd_compr_codec_caps caps_mp3 = {410static const struct snd_compr_codec_caps caps_mp3 = {
411 .num_descriptors = 1,411 .num_descriptors = 1,
412 .descriptor[0].max_ch = 2,412 .descriptor[0].max_ch = 2,
413 .descriptor[0].sample_rates[0] = 48000,413 .descriptor[0].sample_rates[0] = 48000,
@@ -424,7 +424,7 @@ static struct snd_compr_codec_caps caps_mp3 = { · 10 unmodified lines
424 .descriptor[0].formats = 0,424 .descriptor[0].formats = 0,
425};425};
426 426
427static struct snd_compr_codec_caps caps_aac = {427static const struct snd_compr_codec_caps caps_aac = {
428 .num_descriptors = 2,428 .num_descriptors = 2,
429 .descriptor[1].max_ch = 2,429 .descriptor[1].max_ch = 2,
430 .descriptor[0].sample_rates[0] = 48000,430 .descriptor[0].sample_rates[0] = 48000,
sound/soc/intel/atom/sst/sst_pci.c+1−1
@@ -181,7 +181,7 @@ static void intel_sst_remove(struct pci_dev *pci) · 180 unmodified lines
181}181}
182 182
183/* PCI Routines */183/* PCI Routines */
184static struct pci_device_id intel_sst_ids[] = {184static const struct pci_device_id intel_sst_ids[] = {
185 { PCI_VDEVICE(INTEL, SST_MRFLD_PCI_ID), 0},185 { PCI_VDEVICE(INTEL, SST_MRFLD_PCI_ID), 0},
186 { 0, }186 { 0, }
187};187};
sound/soc/intel/baytrail/sst-baytrail-pcm.c+2−2
@@ -309,7 +309,7 @@ static int sst_byt_pcm_mmap(struct snd_pcm_substream *substream, · 308 unmodified lines
309 return snd_pcm_lib_default_mmap(substream, vma);309 return snd_pcm_lib_default_mmap(substream, vma);
310}310}
311 311
312static struct snd_pcm_ops sst_byt_pcm_ops = {312static const struct snd_pcm_ops sst_byt_pcm_ops = {
313 .open = sst_byt_pcm_open,313 .open = sst_byt_pcm_open,
314 .close = sst_byt_pcm_close,314 .close = sst_byt_pcm_close,
315 .ioctl = snd_pcm_lib_ioctl,315 .ioctl = snd_pcm_lib_ioctl,
@@ -395,7 +395,7 @@ static int sst_byt_pcm_remove(struct snd_soc_platform *platform) · 79 unmodified lines
395 return 0;395 return 0;
396}396}
397 397
398static struct snd_soc_platform_driver byt_soc_platform = {398static const struct snd_soc_platform_driver byt_soc_platform = {
399 .probe = sst_byt_pcm_probe,399 .probe = sst_byt_pcm_probe,
400 .remove = sst_byt_pcm_remove,400 .remove = sst_byt_pcm_remove,
401 .ops = &sst_byt_pcm_ops,401 .ops = &sst_byt_pcm_ops,
sound/soc/intel/boards/bxt_rt298.c+82−4
@@ -114,7 +114,44 @@ static const struct snd_soc_dapm_route broxton_rt298_map[] = { · 113 unmodified lines
114 { "iDisp2 Tx", NULL, "iDisp2_out"},114 { "iDisp2 Tx", NULL, "iDisp2_out"},
115 { "hifi1", NULL, "iDisp1 Tx"},115 { "hifi1", NULL, "iDisp1 Tx"},
116 { "iDisp1 Tx", NULL, "iDisp1_out"},116 { "iDisp1 Tx", NULL, "iDisp1_out"},
117};
118
119static const struct snd_soc_dapm_route geminilake_rt298_map[] = {
120 /* speaker */
121 {"Speaker", NULL, "SPOR"},
122 {"Speaker", NULL, "SPOL"},
123
124 /* HP jack connectors - unknown if we have jack detect */
125 {"Headphone Jack", NULL, "HPO Pin"},
126
127 /* other jacks */
128 {"MIC1", NULL, "Mic Jack"},
129
130 /* digital mics */
131 {"DMIC1 Pin", NULL, "DMIC2"},
132 {"DMic", NULL, "SoC DMIC"},
133
134 {"HDMI1", NULL, "hif5-0 Output"},
135 {"HDMI2", NULL, "hif6-0 Output"},
136 {"HDMI2", NULL, "hif7-0 Output"},
137
138 /* CODEC BE connections */
139 { "AIF1 Playback", NULL, "ssp2 Tx"},
140 { "ssp2 Tx", NULL, "codec0_out"},
141 { "ssp2 Tx", NULL, "codec1_out"},
142
143 { "codec0_in", NULL, "ssp2 Rx" },
144 { "ssp2 Rx", NULL, "AIF1 Capture" },
117 145
146 { "dmic01_hifi", NULL, "DMIC01 Rx" },
147 { "DMIC01 Rx", NULL, "Capture" },
148
149 { "hifi3", NULL, "iDisp3 Tx"},
150 { "iDisp3 Tx", NULL, "iDisp3_out"},
151 { "hifi2", NULL, "iDisp2 Tx"},
152 { "iDisp2 Tx", NULL, "iDisp2_out"},
153 { "hifi1", NULL, "iDisp1 Tx"},
154 { "iDisp1 Tx", NULL, "iDisp1_out"},
118};155};
119 156
120static int broxton_rt298_fe_init(struct snd_soc_pcm_runtime *rtd)157static int broxton_rt298_fe_init(struct snd_soc_pcm_runtime *rtd)
@@ -492,7 +529,6 @@ static int bxt_card_late_probe(struct snd_soc_card *card) · 371 unmodified lines
492/* broxton audio machine driver for SPT + RT298S */529/* broxton audio machine driver for SPT + RT298S */
493static struct snd_soc_card broxton_rt298 = {530static struct snd_soc_card broxton_rt298 = {
494 .name = "broxton-rt298",531 .name = "broxton-rt298",
495 .owner = THIS_MODULE,
496 .dai_link = broxton_rt298_dais,532 .dai_link = broxton_rt298_dais,
497 .num_links = ARRAY_SIZE(broxton_rt298_dais),533 .num_links = ARRAY_SIZE(broxton_rt298_dais),
498 .controls = broxton_controls,534 .controls = broxton_controls,
@@ -506,9 +542,41 @@ static struct snd_soc_card broxton_rt298 = { · 7 unmodified lines
506 542
507};543};
508 544
545static struct snd_soc_card geminilake_rt298 = {
546 .name = "geminilake-rt298",
547 .dai_link = broxton_rt298_dais,
548 .num_links = ARRAY_SIZE(broxton_rt298_dais),
549 .controls = broxton_controls,
550 .num_controls = ARRAY_SIZE(broxton_controls),
551 .dapm_widgets = broxton_widgets,
552 .num_dapm_widgets = ARRAY_SIZE(broxton_widgets),
553 .dapm_routes = geminilake_rt298_map,
554 .num_dapm_routes = ARRAY_SIZE(geminilake_rt298_map),
555 .fully_routed = true,
556 .late_probe = bxt_card_late_probe,
557};
558
509static int broxton_audio_probe(struct platform_device *pdev)559static int broxton_audio_probe(struct platform_device *pdev)
510{560{
511 struct bxt_rt286_private *ctx;561 struct bxt_rt286_private *ctx;
562 struct snd_soc_card *card =
563 (struct snd_soc_card *)pdev->id_entry->driver_data;
564 int i;
565
566 for (i = 0; i < ARRAY_SIZE(broxton_rt298_dais); i++) {
567 if (!strncmp(card->dai_link[i].codec_name, "i2c-INT343A:00",
568 I2C_NAME_SIZE)) {
569 if (!strncmp(card->name, "broxton-rt298",
570 PLATFORM_NAME_SIZE)) {
571 card->dai_link[i].name = "SSP5-Codec";
572 card->dai_link[i].cpu_dai_name = "SSP5 Pin";
573 } else if (!strncmp(card->name, "geminilake-rt298",
574 PLATFORM_NAME_SIZE)) {
575 card->dai_link[i].name = "SSP2-Codec";
576 card->dai_link[i].cpu_dai_name = "SSP2 Pin";
577 }
578 }
579 }
512 580
513 ctx = devm_kzalloc(&pdev->dev, sizeof(*ctx), GFP_ATOMIC);581 ctx = devm_kzalloc(&pdev->dev, sizeof(*ctx), GFP_ATOMIC);
514 if (!ctx)582 if (!ctx)
@@ -516,18 +584,27 @@ static int broxton_audio_probe(struct platform_device *pdev) · 1 unmodified line
516 584
517 INIT_LIST_HEAD(&ctx->hdmi_pcm_list);585 INIT_LIST_HEAD(&ctx->hdmi_pcm_list);
518 586
519 broxton_rt298.dev = &pdev->dev;587 card->dev = &pdev->dev;
520 snd_soc_card_set_drvdata(&broxton_rt298, ctx);588 snd_soc_card_set_drvdata(card, ctx);
521 589
522 return devm_snd_soc_register_card(&pdev->dev, &broxton_rt298);590 return devm_snd_soc_register_card(&pdev->dev, card);
523}591}
524 592
593static const struct platform_device_id bxt_board_ids[] = {
594 { .name = "bxt_alc298s_i2s", .driver_data =
595 (unsigned long)&broxton_rt298 },
596 { .name = "glk_alc298s_i2s", .driver_data =
597 (unsigned long)&geminilake_rt298 },
598 {}
599};
600
525static struct platform_driver broxton_audio = {601static struct platform_driver broxton_audio = {
526 .probe = broxton_audio_probe,602 .probe = broxton_audio_probe,
527 .driver = {603 .driver = {
528 .name = "bxt_alc298s_i2s",604 .name = "bxt_alc298s_i2s",
529 .pm = &snd_soc_pm_ops,605 .pm = &snd_soc_pm_ops,
530 },606 },
607 .id_table = bxt_board_ids,
531};608};
532module_platform_driver(broxton_audio)609module_platform_driver(broxton_audio)
533 610
@@ -537,3 +614,4 @@ MODULE_AUTHOR("Senthilnathan Veppur <senthilnathanx.veppur@intel.com>"); · 3 unmodified lines
537MODULE_DESCRIPTION("Intel SST Audio for Broxton");614MODULE_DESCRIPTION("Intel SST Audio for Broxton");
538MODULE_LICENSE("GPL v2");615MODULE_LICENSE("GPL v2");
539MODULE_ALIAS("platform:bxt_alc298s_i2s");616MODULE_ALIAS("platform:bxt_alc298s_i2s");
617MODULE_ALIAS("platform:glk_alc298s_i2s");
sound/soc/intel/boards/kbl_rt5663_max98927.c+258−52
@@ -34,7 +34,7 @@ · 33 unmodified lines
34#define MAXIM_DEV0_NAME "i2c-MX98927:00"34#define MAXIM_DEV0_NAME "i2c-MX98927:00"
35#define MAXIM_DEV1_NAME "i2c-MX98927:01"35#define MAXIM_DEV1_NAME "i2c-MX98927:01"
36 36
37static struct snd_soc_card kabylake_audio_card;37static struct snd_soc_card *kabylake_audio_card;
38static const struct snd_pcm_hw_constraint_list *dmic_constraints;38static const struct snd_pcm_hw_constraint_list *dmic_constraints;
39static struct snd_soc_jack skylake_hdmi[3];39static struct snd_soc_jack skylake_hdmi[3];
40 40
@@ -52,6 +52,8 @@ struct kbl_rt5663_private { · 11 unmodified lines
52enum {52enum {
53 KBL_DPCM_AUDIO_PB = 0,53 KBL_DPCM_AUDIO_PB = 0,
54 KBL_DPCM_AUDIO_CP,54 KBL_DPCM_AUDIO_CP,
55 KBL_DPCM_AUDIO_HS_PB,
56 KBL_DPCM_AUDIO_ECHO_REF_CP,
55 KBL_DPCM_AUDIO_REF_CP,57 KBL_DPCM_AUDIO_REF_CP,
56 KBL_DPCM_AUDIO_DMIC_CP,58 KBL_DPCM_AUDIO_DMIC_CP,
57 KBL_DPCM_AUDIO_HDMI1_PB,59 KBL_DPCM_AUDIO_HDMI1_PB,
@@ -72,8 +74,9 @@ static const struct snd_soc_dapm_widget kabylake_widgets[] = { · 14 unmodified lines
72 SND_SOC_DAPM_SPK("Left Spk", NULL),74 SND_SOC_DAPM_SPK("Left Spk", NULL),
73 SND_SOC_DAPM_SPK("Right Spk", NULL),75 SND_SOC_DAPM_SPK("Right Spk", NULL),
74 SND_SOC_DAPM_MIC("SoC DMIC", NULL),76 SND_SOC_DAPM_MIC("SoC DMIC", NULL),
75 SND_SOC_DAPM_SPK("DP", NULL),77 SND_SOC_DAPM_SPK("HDMI1", NULL),
76 SND_SOC_DAPM_SPK("HDMI", NULL),78 SND_SOC_DAPM_SPK("HDMI2", NULL),
79 SND_SOC_DAPM_SPK("HDMI3", NULL),
77 80
78};81};
79 82
@@ -91,20 +94,22 @@ static const struct snd_soc_dapm_route kabylake_map[] = { · 11 unmodified lines
91 { "IN1N", NULL, "Headset Mic" },94 { "IN1N", NULL, "Headset Mic" },
92 { "DMic", NULL, "SoC DMIC" },95 { "DMic", NULL, "SoC DMIC" },
93 96
94 { "HDMI", NULL, "hif5 Output" },
95 { "DP", NULL, "hif6 Output" },
96
97 /* CODEC BE connections */97 /* CODEC BE connections */
98 { "Left HiFi Playback", NULL, "ssp0 Tx" },98 { "Left HiFi Playback", NULL, "ssp0 Tx" },
99 { "Right HiFi Playback", NULL, "ssp0 Tx" },99 { "Right HiFi Playback", NULL, "ssp0 Tx" },
100 { "ssp0 Tx", NULL, "codec0_out" },100 { "ssp0 Tx", NULL, "spk_out" },
101 101
102 { "AIF Playback", NULL, "ssp1 Tx" },102 { "AIF Playback", NULL, "ssp1 Tx" },
103 { "ssp1 Tx", NULL, "codec1_out" },103 { "ssp1 Tx", NULL, "hs_out" },
104 104
105 { "codec0_in", NULL, "ssp1 Rx" },105 { "hs_in", NULL, "ssp1 Rx" },
106 { "ssp1 Rx", NULL, "AIF Capture" },106 { "ssp1 Rx", NULL, "AIF Capture" },
107 107
108 /* IV feedback path */
109 { "codec0_fb_in", NULL, "ssp0 Rx"},
110 { "ssp0 Rx", NULL, "Left HiFi Capture" },
111 { "ssp0 Rx", NULL, "Right HiFi Capture" },
112
108 /* DMIC */113 /* DMIC */
109 { "dmic01_hifi", NULL, "DMIC01 Rx" },114 { "dmic01_hifi", NULL, "DMIC01 Rx" },
110 { "DMIC01 Rx", NULL, "DMIC AIF" },115 { "DMIC01 Rx", NULL, "DMIC AIF" },
@@ -117,6 +122,49 @@ static const struct snd_soc_dapm_route kabylake_map[] = { · 6 unmodified lines
117 { "iDisp1 Tx", NULL, "iDisp1_out"},122 { "iDisp1 Tx", NULL, "iDisp1_out"},
118};123};
119 124
125enum {
126 KBL_DPCM_AUDIO_5663_PB = 0,
127 KBL_DPCM_AUDIO_5663_CP,
128 KBL_DPCM_AUDIO_5663_HDMI1_PB,
129 KBL_DPCM_AUDIO_5663_HDMI2_PB,
130};
131
132static const struct snd_kcontrol_new kabylake_5663_controls[] = {
133 SOC_DAPM_PIN_SWITCH("Headphone Jack"),
134 SOC_DAPM_PIN_SWITCH("Headset Mic"),
135};
136
137static const struct snd_soc_dapm_widget kabylake_5663_widgets[] = {
138 SND_SOC_DAPM_HP("Headphone Jack", NULL),
139 SND_SOC_DAPM_MIC("Headset Mic", NULL),
140 SND_SOC_DAPM_SPK("DP", NULL),
141 SND_SOC_DAPM_SPK("HDMI", NULL),
142};
143
144static const struct snd_soc_dapm_route kabylake_5663_map[] = {
145 { "Headphone Jack", NULL, "HPOL" },
146 { "Headphone Jack", NULL, "HPOR" },
147
148 /* other jacks */
149 { "IN1P", NULL, "Headset Mic" },
150 { "IN1N", NULL, "Headset Mic" },
151
152 { "HDMI", NULL, "hif5 Output" },
153 { "DP", NULL, "hif6 Output" },
154
155 /* CODEC BE connections */
156 { "AIF Playback", NULL, "ssp1 Tx" },
157 { "ssp1 Tx", NULL, "codec1_out" },
158
159 { "codec0_in", NULL, "ssp1 Rx" },
160 { "ssp1 Rx", NULL, "AIF Capture" },
161
162 { "hifi2", NULL, "iDisp2 Tx"},
163 { "iDisp2 Tx", NULL, "iDisp2_out"},
164 { "hifi1", NULL, "iDisp1 Tx"},
165 { "iDisp1 Tx", NULL, "iDisp1_out"},
166};
167
120static struct snd_soc_codec_conf max98927_codec_conf[] = {168static struct snd_soc_codec_conf max98927_codec_conf[] = {
121 {169 {
122 .dev_name = MAXIM_DEV0_NAME,170 .dev_name = MAXIM_DEV0_NAME,
@@ -165,7 +213,7 @@ static int kabylake_rt5663_codec_init(struct snd_soc_pcm_runtime *rtd) · 42 unmodified lines
165 * Headset buttons map to the google Reference headset.213 * Headset buttons map to the google Reference headset.
166 * These can be configured by userspace.214 * These can be configured by userspace.
167 */215 */
168 ret = snd_soc_card_jack_new(&kabylake_audio_card, "Headset Jack",216 ret = snd_soc_card_jack_new(kabylake_audio_card, "Headset Jack",
169 SND_JACK_HEADSET | SND_JACK_BTN_0 | SND_JACK_BTN_1 |217 SND_JACK_HEADSET | SND_JACK_BTN_0 | SND_JACK_BTN_1 |
170 SND_JACK_BTN_2 | SND_JACK_BTN_3, &ctx->kabylake_headset,218 SND_JACK_BTN_2 | SND_JACK_BTN_3, &ctx->kabylake_headset,
171 NULL, 0);219 NULL, 0);
@@ -173,8 +221,18 @@ static int kabylake_rt5663_codec_init(struct snd_soc_pcm_runtime *rtd) · 1 unmodified line
173 dev_err(rtd->dev, "Headset Jack creation failed %d\n", ret);221 dev_err(rtd->dev, "Headset Jack creation failed %d\n", ret);
174 return ret;222 return ret;
175 }223 }
176
177 rt5663_set_jack_detect(codec, &ctx->kabylake_headset);224 rt5663_set_jack_detect(codec, &ctx->kabylake_headset);
225 return ret;
226}
227
228static int kabylake_rt5663_max98927_codec_init(struct snd_soc_pcm_runtime *rtd)
229{
230 int ret;
231
232 ret = kabylake_rt5663_codec_init(rtd);
233 if (ret)
234 return ret;
235
178 ret = snd_soc_dapm_ignore_suspend(&rtd->card->dapm, "SoC DMIC");236 ret = snd_soc_dapm_ignore_suspend(&rtd->card->dapm, "SoC DMIC");
179 if (ret) {237 if (ret) {
180 dev_err(rtd->dev, "SoC DMIC ignore suspend failed %d\n", ret);238 dev_err(rtd->dev, "SoC DMIC ignore suspend failed %d\n", ret);
@@ -184,7 +242,7 @@ static int kabylake_rt5663_codec_init(struct snd_soc_pcm_runtime *rtd) · 3 unmodified lines
184 return ret;242 return ret;
185}243}
186 244
187static int kabylake_hdmi1_init(struct snd_soc_pcm_runtime *rtd)245static int kabylake_hdmi_init(struct snd_soc_pcm_runtime *rtd, int device)
188{246{
189 struct kbl_rt5663_private *ctx = snd_soc_card_get_drvdata(rtd->card);247 struct kbl_rt5663_private *ctx = snd_soc_card_get_drvdata(rtd->card);
190 struct snd_soc_dai *dai = rtd->codec_dai;248 struct snd_soc_dai *dai = rtd->codec_dai;
@@ -194,7 +252,7 @@ static int kabylake_hdmi1_init(struct snd_soc_pcm_runtime *rtd) · 3 unmodified lines
194 if (!pcm)252 if (!pcm)
195 return -ENOMEM;253 return -ENOMEM;
196 254
197 pcm->device = KBL_DPCM_AUDIO_HDMI1_PB;255 pcm->device = device;
198 pcm->codec_dai = dai;256 pcm->codec_dai = dai;
199 257
200 list_add_tail(&pcm->head, &ctx->hdmi_pcm_list);258 list_add_tail(&pcm->head, &ctx->hdmi_pcm_list);
@@ -202,47 +260,36 @@ static int kabylake_hdmi1_init(struct snd_soc_pcm_runtime *rtd) · 1 unmodified line
202 return 0;260 return 0;
203}261}
204 262
205static int kabylake_hdmi2_init(struct snd_soc_pcm_runtime *rtd)263static int kabylake_hdmi1_init(struct snd_soc_pcm_runtime *rtd)
206{264{
207 struct kbl_rt5663_private *ctx = snd_soc_card_get_drvdata(rtd->card);265 return kabylake_hdmi_init(rtd, KBL_DPCM_AUDIO_HDMI1_PB);
208 struct snd_soc_dai *dai = rtd->codec_dai;266}
209 struct kbl_hdmi_pcm *pcm;
210
211 pcm = devm_kzalloc(rtd->card->dev, sizeof(*pcm), GFP_KERNEL);
212 if (!pcm)
213 return -ENOMEM;
214
215 pcm->device = KBL_DPCM_AUDIO_HDMI2_PB;
216 pcm->codec_dai = dai;
217
218 list_add_tail(&pcm->head, &ctx->hdmi_pcm_list);
219 267
220 return 0;268static int kabylake_hdmi2_init(struct snd_soc_pcm_runtime *rtd)
269{
270 return kabylake_hdmi_init(rtd, KBL_DPCM_AUDIO_HDMI2_PB);
221}271}
222 272
223static int kabylake_hdmi3_init(struct snd_soc_pcm_runtime *rtd)273static int kabylake_hdmi3_init(struct snd_soc_pcm_runtime *rtd)
224{274{
225 struct kbl_rt5663_private *ctx = snd_soc_card_get_drvdata(rtd->card);275 return kabylake_hdmi_init(rtd, KBL_DPCM_AUDIO_HDMI3_PB);
226 struct snd_soc_dai *dai = rtd->codec_dai;276}
227 struct kbl_hdmi_pcm *pcm;
228
229 pcm = devm_kzalloc(rtd->card->dev, sizeof(*pcm), GFP_KERNEL);
230 if (!pcm)
231 return -ENOMEM;
232
233 pcm->device = KBL_DPCM_AUDIO_HDMI3_PB;
234 pcm->codec_dai = dai;
235 277
236 list_add_tail(&pcm->head, &ctx->hdmi_pcm_list);278static int kabylake_5663_hdmi1_init(struct snd_soc_pcm_runtime *rtd)
279{
280 return kabylake_hdmi_init(rtd, KBL_DPCM_AUDIO_5663_HDMI1_PB);
281}
237 282
238 return 0;283static int kabylake_5663_hdmi2_init(struct snd_soc_pcm_runtime *rtd)
284{
285 return kabylake_hdmi_init(rtd, KBL_DPCM_AUDIO_5663_HDMI2_PB);
239}286}
240 287
241static unsigned int rates[] = {288static unsigned int rates[] = {
242 48000,289 48000,
243};290};
244 291
245static struct snd_pcm_hw_constraint_list constraints_rates = {292static const struct snd_pcm_hw_constraint_list constraints_rates = {
246 .count = ARRAY_SIZE(rates),293 .count = ARRAY_SIZE(rates),
247 .list = rates,294 .list = rates,
248 .mask = 0,295 .mask = 0,
@@ -252,7 +299,7 @@ static unsigned int channels[] = { · 3 unmodified lines
252 2,299 2,
253};300};
254 301
255static struct snd_pcm_hw_constraint_list constraints_channels = {302static const struct snd_pcm_hw_constraint_list constraints_channels = {
256 .count = ARRAY_SIZE(channels),303 .count = ARRAY_SIZE(channels),
257 .list = channels,304 .list = channels,
258 .mask = 0,305 .mask = 0,
@@ -312,11 +359,13 @@ static int kabylake_rt5663_hw_params(struct snd_pcm_substream *substream, · 53 unmodified lines
312 struct snd_soc_dai *codec_dai = rtd->codec_dai;359 struct snd_soc_dai *codec_dai = rtd->codec_dai;
313 int ret;360 int ret;
314 361
315 ret = snd_soc_dai_set_sysclk(codec_dai,
316 RT5663_SCLK_S_MCLK, 24576000, SND_SOC_CLOCK_IN);
317 /* use ASRC for internal clocks, as PLL rate isn't multiple of BCLK */362 /* use ASRC for internal clocks, as PLL rate isn't multiple of BCLK */
318 rt5663_sel_asrc_clk_src(codec_dai->codec, RT5663_DA_STEREO_FILTER, 1);363 rt5663_sel_asrc_clk_src(codec_dai->codec,
364 RT5663_DA_STEREO_FILTER | RT5663_AD_STEREO_FILTER,
365 RT5663_CLK_SEL_I2S1_ASRC);
319 366
367 ret = snd_soc_dai_set_sysclk(codec_dai,
368 RT5663_SCLK_S_MCLK, 24576000, SND_SOC_CLOCK_IN);
320 if (ret < 0)369 if (ret < 0)
321 dev_err(rtd->dev, "snd_soc_dai_set_sysclk err = %d\n", ret);370 dev_err(rtd->dev, "snd_soc_dai_set_sysclk err = %d\n", ret);
322 371
@@ -381,7 +430,7 @@ static unsigned int rates_16000[] = { · 58 unmodified lines
381 16000,430 16000,
382};431};
383 432
384static struct snd_pcm_hw_constraint_list constraints_16000 = {433static const struct snd_pcm_hw_constraint_list constraints_16000 = {
385 .count = ARRAY_SIZE(rates_16000),434 .count = ARRAY_SIZE(rates_16000),
386 .list = rates_16000,435 .list = rates_16000,
387};436};
@@ -443,6 +492,28 @@ static struct snd_soc_dai_link kabylake_dais[] = { · 55 unmodified lines
443 .dpcm_capture = 1,492 .dpcm_capture = 1,
444 .ops = &kabylake_rt5663_fe_ops,493 .ops = &kabylake_rt5663_fe_ops,
445 },494 },
495 [KBL_DPCM_AUDIO_HS_PB] = {
496 .name = "Kbl Audio Headset Playback",
497 .stream_name = "Headset Audio",
498 .cpu_dai_name = "System Pin2",
499 .codec_name = "snd-soc-dummy",
500 .codec_dai_name = "snd-soc-dummy-dai",
501 .platform_name = "0000:00:1f.3",
502 .dpcm_playback = 1,
503 .nonatomic = 1,
504 .dynamic = 1,
505 },
506 [KBL_DPCM_AUDIO_ECHO_REF_CP] = {
507 .name = "Kbl Audio Echo Reference cap",
508 .stream_name = "Echoreference Capture",
509 .cpu_dai_name = "Echoref Pin",
510 .codec_name = "snd-soc-dummy",
511 .codec_dai_name = "snd-soc-dummy-dai",
512 .platform_name = "0000:00:1f.3",
513 .init = NULL,
514 .capture_only = 1,
515 .nonatomic = 1,
516 },
446 [KBL_DPCM_AUDIO_REF_CP] = {517 [KBL_DPCM_AUDIO_REF_CP] = {
447 .name = "Kbl Audio Reference cap",518 .name = "Kbl Audio Reference cap",
448 .stream_name = "Wake on Voice",519 .stream_name = "Wake on Voice",
@@ -538,7 +609,7 @@ static struct snd_soc_dai_link kabylake_dais[] = { · 89 unmodified lines
538 .no_pcm = 1,609 .no_pcm = 1,
539 .codec_name = "i2c-10EC5663:00",610 .codec_name = "i2c-10EC5663:00",
540 .codec_dai_name = KBL_REALTEK_CODEC_DAI,611 .codec_dai_name = KBL_REALTEK_CODEC_DAI,
541 .init = kabylake_rt5663_codec_init,612 .init = kabylake_rt5663_max98927_codec_init,
542 .dai_fmt = SND_SOC_DAIFMT_I2S | SND_SOC_DAIFMT_NB_NF |613 .dai_fmt = SND_SOC_DAIFMT_I2S | SND_SOC_DAIFMT_NB_NF |
543 SND_SOC_DAIFMT_CBS_CFS,614 SND_SOC_DAIFMT_CBS_CFS,
544 .ignore_pmdown_time = 1,615 .ignore_pmdown_time = 1,
@@ -594,15 +665,119 @@ static struct snd_soc_dai_link kabylake_dais[] = { · 49 unmodified lines
594 },665 },
595};666};
596 667
668static struct snd_soc_dai_link kabylake_5663_dais[] = {
669 /* Front End DAI links */
670 [KBL_DPCM_AUDIO_5663_PB] = {
671 .name = "Kbl Audio Port",
672 .stream_name = "Audio",
673 .cpu_dai_name = "System Pin",
674 .platform_name = "0000:00:1f.3",
675 .dynamic = 1,
676 .codec_name = "snd-soc-dummy",
677 .codec_dai_name = "snd-soc-dummy-dai",
678 .nonatomic = 1,
679 .trigger = {
680 SND_SOC_DPCM_TRIGGER_POST, SND_SOC_DPCM_TRIGGER_POST},
681 .dpcm_playback = 1,
682 .ops = &kabylake_rt5663_fe_ops,
683 },
684 [KBL_DPCM_AUDIO_5663_CP] = {
685 .name = "Kbl Audio Capture Port",
686 .stream_name = "Audio Record",
687 .cpu_dai_name = "System Pin",
688 .platform_name = "0000:00:1f.3",
689 .dynamic = 1,
690 .codec_name = "snd-soc-dummy",
691 .codec_dai_name = "snd-soc-dummy-dai",
692 .nonatomic = 1,
693 .trigger = {
694 SND_SOC_DPCM_TRIGGER_POST, SND_SOC_DPCM_TRIGGER_POST},
695 .dpcm_capture = 1,
696 .ops = &kabylake_rt5663_fe_ops,
697 },
698 [KBL_DPCM_AUDIO_5663_HDMI1_PB] = {
699 .name = "Kbl HDMI Port1",
700 .stream_name = "Hdmi1",
701 .cpu_dai_name = "HDMI1 Pin",
702 .codec_name = "snd-soc-dummy",
703 .codec_dai_name = "snd-soc-dummy-dai",
704 .platform_name = "0000:00:1f.3",
705 .dpcm_playback = 1,
706 .init = NULL,
707 .trigger = {
708 SND_SOC_DPCM_TRIGGER_POST, SND_SOC_DPCM_TRIGGER_POST},
709 .nonatomic = 1,
710 .dynamic = 1,
711 },
712 [KBL_DPCM_AUDIO_5663_HDMI2_PB] = {
713 .name = "Kbl HDMI Port2",
714 .stream_name = "Hdmi2",
715 .cpu_dai_name = "HDMI2 Pin",
716 .codec_name = "snd-soc-dummy",
717 .codec_dai_name = "snd-soc-dummy-dai",
718 .platform_name = "0000:00:1f.3",
719 .dpcm_playback = 1,
720 .init = NULL,
721 .trigger = {
722 SND_SOC_DPCM_TRIGGER_POST, SND_SOC_DPCM_TRIGGER_POST},
723 .nonatomic = 1,
724 .dynamic = 1,
725 },
726
727 /* Back End DAI links */
728 {
729 /* SSP1 - Codec */
730 .name = "SSP1-Codec",
731 .id = 0,
732 .cpu_dai_name = "SSP1 Pin",
733 .platform_name = "0000:00:1f.3",
734 .no_pcm = 1,
735 .codec_name = "i2c-10EC5663:00",
736 .codec_dai_name = KBL_REALTEK_CODEC_DAI,
737 .init = kabylake_rt5663_codec_init,
738 .dai_fmt = SND_SOC_DAIFMT_I2S | SND_SOC_DAIFMT_NB_NF |
739 SND_SOC_DAIFMT_CBS_CFS,
740 .ignore_pmdown_time = 1,
741 .be_hw_params_fixup = kabylake_ssp_fixup,
742 .ops = &kabylake_rt5663_ops,
743 .dpcm_playback = 1,
744 .dpcm_capture = 1,
745 },
746 {
747 .name = "iDisp1",
748 .id = 1,
749 .cpu_dai_name = "iDisp1 Pin",
750 .codec_name = "ehdaudio0D2",
751 .codec_dai_name = "intel-hdmi-hifi1",
752 .platform_name = "0000:00:1f.3",
753 .dpcm_playback = 1,
754 .init = kabylake_5663_hdmi1_init,
755 .no_pcm = 1,
756 },
757 {
758 .name = "iDisp2",
759 .id = 2,
760 .cpu_dai_name = "iDisp2 Pin",
761 .codec_name = "ehdaudio0D2",
762 .codec_dai_name = "intel-hdmi-hifi2",
763 .platform_name = "0000:00:1f.3",
764 .init = kabylake_5663_hdmi2_init,
765 .dpcm_playback = 1,
766 .no_pcm = 1,
767 },
768};
769
597#define NAME_SIZE 32770#define NAME_SIZE 32
598static int kabylake_card_late_probe(struct snd_soc_card *card)771static int kabylake_card_late_probe(struct snd_soc_card *card)
599{772{
600 struct kbl_rt5663_private *ctx = snd_soc_card_get_drvdata(card);773 struct kbl_rt5663_private *ctx = snd_soc_card_get_drvdata(card);
601 struct kbl_hdmi_pcm *pcm;774 struct kbl_hdmi_pcm *pcm;
775 struct snd_soc_codec *codec = NULL;
602 int err, i = 0;776 int err, i = 0;
603 char jack_name[NAME_SIZE];777 char jack_name[NAME_SIZE];
604 778
605 list_for_each_entry(pcm, &ctx->hdmi_pcm_list, head) {779 list_for_each_entry(pcm, &ctx->hdmi_pcm_list, head) {
780 codec = pcm->codec_dai->codec;
606 snprintf(jack_name, sizeof(jack_name),781 snprintf(jack_name, sizeof(jack_name),
607 "HDMI/DP, pcm=%d Jack", pcm->device);782 "HDMI/DP, pcm=%d Jack", pcm->device);
608 err = snd_soc_card_jack_new(card, jack_name,783 err = snd_soc_card_jack_new(card, jack_name,
@@ -620,11 +795,14 @@ static int kabylake_card_late_probe(struct snd_soc_card *card) · 11 unmodified lines
620 i++;795 i++;
621 }796 }
622 797
623 return 0;798 if (!codec)
799 return -EINVAL;
800
801 return hdac_hdmi_jack_port_init(codec, &card->dapm);
624}802}
625 803
626/* kabylake audio machine driver for SPT + RT5663 */804/* kabylake audio machine driver for SPT + RT5663 */
627static struct snd_soc_card kabylake_audio_card = {805static struct snd_soc_card kabylake_audio_card_rt5663_m98927 = {
628 .name = "kblrt5663max",806 .name = "kblrt5663max",
629 .owner = THIS_MODULE,807 .owner = THIS_MODULE,
630 .dai_link = kabylake_dais,808 .dai_link = kabylake_dais,
@@ -641,6 +819,22 @@ static struct snd_soc_card kabylake_audio_card = { · 10 unmodified lines
641 .late_probe = kabylake_card_late_probe,819 .late_probe = kabylake_card_late_probe,
642};820};
643 821
822/* kabylake audio machine driver for RT5663 */
823static struct snd_soc_card kabylake_audio_card_rt5663 = {
824 .name = "kblrt5663",
825 .owner = THIS_MODULE,
826 .dai_link = kabylake_5663_dais,
827 .num_links = ARRAY_SIZE(kabylake_5663_dais),
828 .controls = kabylake_5663_controls,
829 .num_controls = ARRAY_SIZE(kabylake_5663_controls),
830 .dapm_widgets = kabylake_5663_widgets,
831 .num_dapm_widgets = ARRAY_SIZE(kabylake_5663_widgets),
832 .dapm_routes = kabylake_5663_map,
833 .num_dapm_routes = ARRAY_SIZE(kabylake_5663_map),
834 .fully_routed = true,
835 .late_probe = kabylake_card_late_probe,
836};
837
644static int kabylake_audio_probe(struct platform_device *pdev)838static int kabylake_audio_probe(struct platform_device *pdev)
645{839{
646 struct kbl_rt5663_private *ctx;840 struct kbl_rt5663_private *ctx;
@@ -652,19 +846,30 @@ static int kabylake_audio_probe(struct platform_device *pdev) · 5 unmodified lines
652 846
653 INIT_LIST_HEAD(&ctx->hdmi_pcm_list);847 INIT_LIST_HEAD(&ctx->hdmi_pcm_list);
654 848
655 kabylake_audio_card.dev = &pdev->dev;849 kabylake_audio_card =
656 snd_soc_card_set_drvdata(&kabylake_audio_card, ctx);850 (struct snd_soc_card *)pdev->id_entry->driver_data;
851
852 kabylake_audio_card->dev = &pdev->dev;
853 snd_soc_card_set_drvdata(kabylake_audio_card, ctx);
657 854
658 pdata = dev_get_drvdata(&pdev->dev);855 pdata = dev_get_drvdata(&pdev->dev);
659 if (pdata)856 if (pdata)
660 dmic_constraints = pdata->dmic_num == 2 ?857 dmic_constraints = pdata->dmic_num == 2 ?
661 &constraints_dmic_2ch : &constraints_dmic_channels;858 &constraints_dmic_2ch : &constraints_dmic_channels;
662 859
663 return devm_snd_soc_register_card(&pdev->dev, &kabylake_audio_card);860 return devm_snd_soc_register_card(&pdev->dev, kabylake_audio_card);
664}861}
665 862
666static const struct platform_device_id kbl_board_ids[] = {863static const struct platform_device_id kbl_board_ids[] = {
667 { .name = "kbl_rt5663_m98927" },864 {
865 .name = "kbl_rt5663",
866 .driver_data = (kernel_ulong_t)&kabylake_audio_card_rt5663,
867 },
868 {
869 .name = "kbl_rt5663_m98927",
870 .driver_data =
871 (kernel_ulong_t)&kabylake_audio_card_rt5663_m98927,
872 },
668 { }873 { }
669};874};
670 875
@@ -684,4 +889,5 @@ MODULE_DESCRIPTION("Audio Machine driver-RT5663 & MAX98927 in I2S mode"); · 13 unmodified lines
684MODULE_AUTHOR("Naveen M <naveen.m@intel.com>");889MODULE_AUTHOR("Naveen M <naveen.m@intel.com>");
685MODULE_AUTHOR("Harsha Priya <harshapriya.n@intel.com>");890MODULE_AUTHOR("Harsha Priya <harshapriya.n@intel.com>");
686MODULE_LICENSE("GPL v2");891MODULE_LICENSE("GPL v2");
892MODULE_ALIAS("platform:kbl_rt5663");
687MODULE_ALIAS("platform:kbl_rt5663_m98927");893MODULE_ALIAS("platform:kbl_rt5663_m98927");
sound/soc/intel/boards/kbl_rt5663_rt5514_max98927.c+68−13
@@ -18,6 +18,7 @@ · 17 unmodified lines
18 * GNU General Public License for more details.18 * GNU General Public License for more details.
19 */19 */
20 20
21#include <linux/input.h>
21#include <linux/module.h>22#include <linux/module.h>
22#include <linux/platform_device.h>23#include <linux/platform_device.h>
23#include <sound/core.h>24#include <sound/core.h>
@@ -62,7 +63,10 @@ struct kbl_codec_private { · 38 unmodified lines
62enum {63enum {
63 KBL_DPCM_AUDIO_PB = 0,64 KBL_DPCM_AUDIO_PB = 0,
64 KBL_DPCM_AUDIO_CP,65 KBL_DPCM_AUDIO_CP,
66 KBL_DPCM_AUDIO_HS_PB,
67 KBL_DPCM_AUDIO_ECHO_REF_CP,
65 KBL_DPCM_AUDIO_DMIC_CP,68 KBL_DPCM_AUDIO_DMIC_CP,
69 KBL_DPCM_AUDIO_RT5514_DSP,
66 KBL_DPCM_AUDIO_HDMI1_PB,70 KBL_DPCM_AUDIO_HDMI1_PB,
67 KBL_DPCM_AUDIO_HDMI2_PB,71 KBL_DPCM_AUDIO_HDMI2_PB,
68};72};
@@ -81,8 +85,8 @@ static const struct snd_soc_dapm_widget kabylake_widgets[] = { · 12 unmodified lines
81 SND_SOC_DAPM_SPK("Left Spk", NULL),85 SND_SOC_DAPM_SPK("Left Spk", NULL),
82 SND_SOC_DAPM_SPK("Right Spk", NULL),86 SND_SOC_DAPM_SPK("Right Spk", NULL),
83 SND_SOC_DAPM_MIC("DMIC", NULL),87 SND_SOC_DAPM_MIC("DMIC", NULL),
84 SND_SOC_DAPM_SPK("DP", NULL),88 SND_SOC_DAPM_SPK("HDMI1", NULL),
85 SND_SOC_DAPM_SPK("HDMI", NULL),89 SND_SOC_DAPM_SPK("HDMI2", NULL),
86 90
87};91};
88 92
@@ -99,23 +103,25 @@ static const struct snd_soc_dapm_route kabylake_map[] = { · 10 unmodified lines
99 { "IN1P", NULL, "Headset Mic" },103 { "IN1P", NULL, "Headset Mic" },
100 { "IN1N", NULL, "Headset Mic" },104 { "IN1N", NULL, "Headset Mic" },
101 105
102 { "HDMI", NULL, "hif5 Output" },
103 { "DP", NULL, "hif6 Output" },
104
105 /* CODEC BE connections */106 /* CODEC BE connections */
106 { "Left HiFi Playback", NULL, "ssp0 Tx" },107 { "Left HiFi Playback", NULL, "ssp0 Tx" },
107 { "Right HiFi Playback", NULL, "ssp0 Tx" },108 { "Right HiFi Playback", NULL, "ssp0 Tx" },
108 { "ssp0 Tx", NULL, "codec0_out" },109 { "ssp0 Tx", NULL, "spk_out" },
109 110
110 { "AIF Playback", NULL, "ssp1 Tx" },111 { "AIF Playback", NULL, "ssp1 Tx" },
111 { "ssp1 Tx", NULL, "codec1_out" },112 { "ssp1 Tx", NULL, "hs_out" },
112 113
113 { "codec0_in", NULL, "ssp1 Rx" },114 { "hs_in", NULL, "ssp1 Rx" },
114 { "ssp1 Rx", NULL, "AIF Capture" },115 { "ssp1 Rx", NULL, "AIF Capture" },
115 116
116 { "codec1_in", NULL, "ssp0 Rx" },117 { "codec1_in", NULL, "ssp0 Rx" },
117 { "ssp0 Rx", NULL, "AIF1 Capture" },118 { "ssp0 Rx", NULL, "AIF1 Capture" },
118 119
120 /* IV feedback path */
121 { "codec0_fb_in", NULL, "ssp0 Rx"},
122 { "ssp0 Rx", NULL, "Left HiFi Capture" },
123 { "ssp0 Rx", NULL, "Right HiFi Capture" },
124
119 /* DMIC */125 /* DMIC */
120 { "DMIC1L", NULL, "DMIC" },126 { "DMIC1L", NULL, "DMIC" },
121 { "DMIC1R", NULL, "DMIC" },127 { "DMIC1R", NULL, "DMIC" },
@@ -173,6 +179,7 @@ static int kabylake_rt5663_codec_init(struct snd_soc_pcm_runtime *rtd) · 51 unmodified lines
173 int ret;179 int ret;
174 struct kbl_codec_private *ctx = snd_soc_card_get_drvdata(rtd->card);180 struct kbl_codec_private *ctx = snd_soc_card_get_drvdata(rtd->card);
175 struct snd_soc_codec *codec = rtd->codec;181 struct snd_soc_codec *codec = rtd->codec;
182 struct snd_soc_jack *jack;
176 183
177 /*184 /*
178 * Headset buttons map to the google Reference headset.185 * Headset buttons map to the google Reference headset.
@@ -187,6 +194,12 @@ static int kabylake_rt5663_codec_init(struct snd_soc_pcm_runtime *rtd) · 8 unmodified lines
187 return ret;194 return ret;
188 }195 }
189 196
197 jack = &ctx->kabylake_headset;
198 snd_jack_set_key(jack->jack, SND_JACK_BTN_0, KEY_MEDIA);
199 snd_jack_set_key(jack->jack, SND_JACK_BTN_1, KEY_VOICECOMMAND);
200 snd_jack_set_key(jack->jack, SND_JACK_BTN_2, KEY_VOLUMEUP);
201 snd_jack_set_key(jack->jack, SND_JACK_BTN_3, KEY_VOLUMEDOWN);
202
190 rt5663_set_jack_detect(codec, &ctx->kabylake_headset);203 rt5663_set_jack_detect(codec, &ctx->kabylake_headset);
191 204
192 ret = snd_soc_dapm_ignore_suspend(&rtd->card->dapm, "DMIC");205 ret = snd_soc_dapm_ignore_suspend(&rtd->card->dapm, "DMIC");
@@ -358,11 +371,18 @@ static int kabylake_ssp0_hw_params(struct snd_pcm_substream *substream, · 165 unmodified lines
358 return ret;371 return ret;
359 }372 }
360 }373 }
361 if (!strcmp(codec_dai->component->name, MAXIM_DEV0_NAME) ||374 if (!strcmp(codec_dai->component->name, MAXIM_DEV0_NAME)) {
362 !strcmp(codec_dai->component->name, MAXIM_DEV1_NAME)) {375 ret = snd_soc_dai_set_tdm_slot(codec_dai, 0x30, 3, 8, 16);
363 ret = snd_soc_dai_set_tdm_slot(codec_dai, 0xF0, 3, 8, 16);
364 if (ret < 0) {376 if (ret < 0) {
365 dev_err(rtd->dev, "set TDM slot err:%d\n", ret);377 dev_err(rtd->dev, "DEV0 TDM slot err:%d\n", ret);
378 return ret;
379 }
380 }
381
382 if (!strcmp(codec_dai->component->name, MAXIM_DEV1_NAME)) {
383 ret = snd_soc_dai_set_tdm_slot(codec_dai, 0xC0, 3, 8, 16);
384 if (ret < 0) {
385 dev_err(rtd->dev, "DEV1 TDM slot err:%d\n", ret);
366 return ret;386 return ret;
367 }387 }
368 }388 }
@@ -442,6 +462,36 @@ static struct snd_soc_dai_link kabylake_dais[] = { · 73 unmodified lines
442 .dpcm_capture = 1,462 .dpcm_capture = 1,
443 .ops = &kabylake_rt5663_fe_ops,463 .ops = &kabylake_rt5663_fe_ops,
444 },464 },
465 [KBL_DPCM_AUDIO_HS_PB] = {
466 .name = "Kbl Audio Headset Playback",
467 .stream_name = "Headset Audio",
468 .cpu_dai_name = "System Pin2",
469 .codec_name = "snd-soc-dummy",
470 .codec_dai_name = "snd-soc-dummy-dai",
471 .platform_name = "0000:00:1f.3",
472 .dpcm_playback = 1,
473 .nonatomic = 1,
474 .dynamic = 1,
475 },
476 [KBL_DPCM_AUDIO_ECHO_REF_CP] = {
477 .name = "Kbl Audio Echo Reference cap",
478 .stream_name = "Echoreference Capture",
479 .cpu_dai_name = "Echoref Pin",
480 .codec_name = "snd-soc-dummy",
481 .codec_dai_name = "snd-soc-dummy-dai",
482 .platform_name = "0000:00:1f.3",
483 .init = NULL,
484 .capture_only = 1,
485 .nonatomic = 1,
486 },
487 [KBL_DPCM_AUDIO_RT5514_DSP] = {
488 .name = "rt5514 dsp",
489 .stream_name = "Wake on Voice",
490 .cpu_dai_name = "spi-PRP0001:00",
491 .platform_name = "spi-PRP0001:00",
492 .codec_name = "snd-soc-dummy",
493 .codec_dai_name = "snd-soc-dummy-dai",
494 },
445 [KBL_DPCM_AUDIO_DMIC_CP] = {495 [KBL_DPCM_AUDIO_DMIC_CP] = {
446 .name = "Kbl Audio DMIC cap",496 .name = "Kbl Audio DMIC cap",
447 .stream_name = "dmiccap",497 .stream_name = "dmiccap",
@@ -548,10 +598,12 @@ static int kabylake_card_late_probe(struct snd_soc_card *card) · 100 unmodified lines
548{598{
549 struct kbl_codec_private *ctx = snd_soc_card_get_drvdata(card);599 struct kbl_codec_private *ctx = snd_soc_card_get_drvdata(card);
550 struct kbl_hdmi_pcm *pcm;600 struct kbl_hdmi_pcm *pcm;
601 struct snd_soc_codec *codec = NULL;
551 int err, i = 0;602 int err, i = 0;
552 char jack_name[NAME_SIZE];603 char jack_name[NAME_SIZE];
553 604
554 list_for_each_entry(pcm, &ctx->hdmi_pcm_list, head) {605 list_for_each_entry(pcm, &ctx->hdmi_pcm_list, head) {
606 codec = pcm->codec_dai->codec;
555 err = snd_soc_card_jack_new(card, jack_name,607 err = snd_soc_card_jack_new(card, jack_name,
556 SND_JACK_AVOUT, &ctx->kabylake_hdmi[i],608 SND_JACK_AVOUT, &ctx->kabylake_hdmi[i],
557 NULL, 0);609 NULL, 0);
@@ -565,7 +617,10 @@ static int kabylake_card_late_probe(struct snd_soc_card *card) · 7 unmodified lines
565 i++;617 i++;
566 }618 }
567 619
568 return 0;620 if (!codec)
621 return -EINVAL;
622
623 return hdac_hdmi_jack_port_init(codec, &card->dapm);
569}624}
570 625
571/*626/*
sound/soc/intel/boards/mfld_machine.c+1−3
@@ -376,10 +376,8 @@ static int snd_mfld_mc_probe(struct platform_device *pdev) · 375 unmodified lines
376 /* audio interrupt base of SRAM location where376 /* audio interrupt base of SRAM location where
377 * interrupts are stored by System FW */377 * interrupts are stored by System FW */
378 mc_drv_ctx = devm_kzalloc(&pdev->dev, sizeof(*mc_drv_ctx), GFP_ATOMIC);378 mc_drv_ctx = devm_kzalloc(&pdev->dev, sizeof(*mc_drv_ctx), GFP_ATOMIC);
379 if (!mc_drv_ctx) {379 if (!mc_drv_ctx)
380 pr_err("allocation failed\n");
381 return -ENOMEM;380 return -ENOMEM;
382 }
383 381
384 irq_mem = platform_get_resource_byname(382 irq_mem = platform_get_resource_byname(
385 pdev, IORESOURCE_MEM, "IRQ_BASE");383 pdev, IORESOURCE_MEM, "IRQ_BASE");
sound/soc/intel/haswell/sst-haswell-pcm.c+1−1
@@ -1135,7 +1135,7 @@ static int hsw_pcm_remove(struct snd_soc_platform *platform) · 1134 unmodified lines
1135 return 0;1135 return 0;
1136}1136}
1137 1137
1138static struct snd_soc_platform_driver hsw_soc_platform = {1138static const struct snd_soc_platform_driver hsw_soc_platform = {
1139 .probe = hsw_pcm_probe,1139 .probe = hsw_pcm_probe,
1140 .remove = hsw_pcm_remove,1140 .remove = hsw_pcm_remove,
1141 .ops = &hsw_pcm_ops,1141 .ops = &hsw_pcm_ops,
sound/soc/intel/skylake/Makefile+3−2
@@ -8,7 +8,8 @@ endif · 7 unmodified lines
8obj-$(CONFIG_SND_SOC_INTEL_SKYLAKE) += snd-soc-skl.o8obj-$(CONFIG_SND_SOC_INTEL_SKYLAKE) += snd-soc-skl.o
9 9
10# Skylake IPC Support10# Skylake IPC Support
11snd-soc-skl-ipc-objs := skl-sst-ipc.o skl-sst-dsp.o skl-sst-cldma.o \11snd-soc-skl-ipc-objs := skl-sst-ipc.o skl-sst-dsp.o cnl-sst-dsp.o \
12 skl-sst.o bxt-sst.o skl-sst-utils.o12 skl-sst-cldma.o skl-sst.o bxt-sst.o cnl-sst.o \
13 skl-sst-utils.o
13 14
14obj-$(CONFIG_SND_SOC_INTEL_SKYLAKE) += snd-soc-skl-ipc.o15obj-$(CONFIG_SND_SOC_INTEL_SKYLAKE) += snd-soc-skl-ipc.o
sound/soc/intel/skylake/bxt-sst.c+7−7
@@ -530,7 +530,7 @@ static int bxt_set_dsp_D3(struct sst_dsp *ctx, unsigned int core_id) · 529 unmodified lines
530 return 0;530 return 0;
531}531}
532 532
533static struct skl_dsp_fw_ops bxt_fw_ops = {533static const struct skl_dsp_fw_ops bxt_fw_ops = {
534 .set_state_D0 = bxt_set_dsp_D0,534 .set_state_D0 = bxt_set_dsp_D0,
535 .set_state_D3 = bxt_set_dsp_D3,535 .set_state_D3 = bxt_set_dsp_D3,
536 .set_state_D0i3 = bxt_schedule_dsp_D0i3,536 .set_state_D0i3 = bxt_schedule_dsp_D0i3,
@@ -581,10 +581,15 @@ int bxt_sst_dsp_init(struct device *dev, void __iomem *mmio_base, int irq, · 44 unmodified lines
581 sst_dsp_mailbox_init(sst, (BXT_ADSP_SRAM0_BASE + SKL_ADSP_W0_STAT_SZ),581 sst_dsp_mailbox_init(sst, (BXT_ADSP_SRAM0_BASE + SKL_ADSP_W0_STAT_SZ),
582 SKL_ADSP_W0_UP_SZ, BXT_ADSP_SRAM1_BASE, SKL_ADSP_W1_SZ);582 SKL_ADSP_W0_UP_SZ, BXT_ADSP_SRAM1_BASE, SKL_ADSP_W1_SZ);
583 583
584 ret = skl_ipc_init(dev, skl);
585 if (ret) {
586 skl_dsp_free(sst);
587 return ret;
588 }
589
584 /* set the D0i3 check */590 /* set the D0i3 check */
585 skl->ipc.ops.check_dsp_lp_on = skl_ipc_check_D0i0;591 skl->ipc.ops.check_dsp_lp_on = skl_ipc_check_D0i0;
586 592
587 skl->cores.count = 2;
588 skl->boot_complete = false;593 skl->boot_complete = false;
589 init_waitqueue_head(&skl->boot_wait);594 init_waitqueue_head(&skl->boot_wait);
590 INIT_DELAYED_WORK(&skl->d0i3.work, bxt_set_dsp_D0i3);595 INIT_DELAYED_WORK(&skl->d0i3.work, bxt_set_dsp_D0i3);
@@ -629,11 +634,6 @@ void bxt_sst_dsp_cleanup(struct device *dev, struct skl_sst *ctx) · 38 unmodified lines
629 release_firmware(ctx->dsp->fw);634 release_firmware(ctx->dsp->fw);
630 skl_freeup_uuid_list(ctx);635 skl_freeup_uuid_list(ctx);
631 skl_ipc_free(&ctx->ipc);636 skl_ipc_free(&ctx->ipc);
632 ctx->dsp->cl_dev.ops.cl_cleanup_controller(ctx->dsp);
633
634 if (ctx->dsp->addr.lpe)
635 iounmap(ctx->dsp->addr.lpe);
636
637 ctx->dsp->ops->free(ctx->dsp);637 ctx->dsp->ops->free(ctx->dsp);
638}638}
639EXPORT_SYMBOL_GPL(bxt_sst_dsp_cleanup);639EXPORT_SYMBOL_GPL(bxt_sst_dsp_cleanup);
sound/soc/intel/skylake/cnl-sst-dsp.c+274−0
@@ -0,0 +1,274 @@
1/*
2 * cnl-sst-dsp.c - CNL SST library generic function
3 *
4 * Copyright (C) 2016-17, Intel Corporation.
5 * Author: Guneshwor Singh <guneshwor.o.singh@intel.com>
6 *
7 * Modified from:
8 * SKL SST library generic function
9 * Copyright (C) 2014-15, Intel Corporation.
10 * ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
11 *
12 * This program is free software; you can redistribute it and/or modify
13 * it under the terms of the GNU General Public License as version 2, as
14 * published by the Free Software Foundation.
15 *
16 * This program is distributed in the hope that it will be useful, but
17 * WITHOUT ANY WARRANTY; without even the implied warranty of
18 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
19 * General Public License for more details.
20 *
21 * ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
22 */
23#include <linux/device.h>
24#include "../common/sst-dsp.h"
25#include "../common/sst-ipc.h"
26#include "../common/sst-dsp-priv.h"
27#include "cnl-sst-dsp.h"
28
29/* various timeout values */
30#define CNL_DSP_PU_TO 50
31#define CNL_DSP_PD_TO 50
32#define CNL_DSP_RESET_TO 50
33
34static int
35cnl_dsp_core_set_reset_state(struct sst_dsp *ctx, unsigned int core_mask)
36{
37 /* update bits */
38 sst_dsp_shim_update_bits_unlocked(ctx,
39 CNL_ADSP_REG_ADSPCS, CNL_ADSPCS_CRST(core_mask),
40 CNL_ADSPCS_CRST(core_mask));
41
42 /* poll with timeout to check if operation successful */
43 return sst_dsp_register_poll(ctx,
44 CNL_ADSP_REG_ADSPCS,
45 CNL_ADSPCS_CRST(core_mask),
46 CNL_ADSPCS_CRST(core_mask),
47 CNL_DSP_RESET_TO,
48 "Set reset");
49}
50
51static int
52cnl_dsp_core_unset_reset_state(struct sst_dsp *ctx, unsigned int core_mask)
53{
54 /* update bits */
55 sst_dsp_shim_update_bits_unlocked(ctx, CNL_ADSP_REG_ADSPCS,
56 CNL_ADSPCS_CRST(core_mask), 0);
57
58 /* poll with timeout to check if operation successful */
59 return sst_dsp_register_poll(ctx,
60 CNL_ADSP_REG_ADSPCS,
61 CNL_ADSPCS_CRST(core_mask),
62 0,
63 CNL_DSP_RESET_TO,
64 "Unset reset");
65}
66
67static bool is_cnl_dsp_core_enable(struct sst_dsp *ctx, unsigned int core_mask)
68{
69 int val;
70 bool is_enable;
71
72 val = sst_dsp_shim_read_unlocked(ctx, CNL_ADSP_REG_ADSPCS);
73
74 is_enable = (val & CNL_ADSPCS_CPA(core_mask)) &&
75 (val & CNL_ADSPCS_SPA(core_mask)) &&
76 !(val & CNL_ADSPCS_CRST(core_mask)) &&
77 !(val & CNL_ADSPCS_CSTALL(core_mask));
78
79 dev_dbg(ctx->dev, "DSP core(s) enabled? %d: core_mask %#x\n",
80 is_enable, core_mask);
81
82 return is_enable;
83}
84
85static int cnl_dsp_reset_core(struct sst_dsp *ctx, unsigned int core_mask)
86{
87 /* stall core */
88 sst_dsp_shim_update_bits_unlocked(ctx, CNL_ADSP_REG_ADSPCS,
89 CNL_ADSPCS_CSTALL(core_mask),
90 CNL_ADSPCS_CSTALL(core_mask));
91
92 /* set reset state */
93 return cnl_dsp_core_set_reset_state(ctx, core_mask);
94}
95
96static int cnl_dsp_start_core(struct sst_dsp *ctx, unsigned int core_mask)
97{
98 int ret;
99
100 /* unset reset state */
101 ret = cnl_dsp_core_unset_reset_state(ctx, core_mask);
102 if (ret < 0)
103 return ret;
104
105 /* run core */
106 sst_dsp_shim_update_bits_unlocked(ctx, CNL_ADSP_REG_ADSPCS,
107 CNL_ADSPCS_CSTALL(core_mask), 0);
108
109 if (!is_cnl_dsp_core_enable(ctx, core_mask)) {
110 cnl_dsp_reset_core(ctx, core_mask);
111 dev_err(ctx->dev, "DSP core mask %#x enable failed\n",
112 core_mask);
113 ret = -EIO;
114 }
115
116 return ret;
117}
118
119static int cnl_dsp_core_power_up(struct sst_dsp *ctx, unsigned int core_mask)
120{
121 /* update bits */
122 sst_dsp_shim_update_bits_unlocked(ctx, CNL_ADSP_REG_ADSPCS,
123 CNL_ADSPCS_SPA(core_mask),
124 CNL_ADSPCS_SPA(core_mask));
125
126 /* poll with timeout to check if operation successful */
127 return sst_dsp_register_poll(ctx, CNL_ADSP_REG_ADSPCS,
128 CNL_ADSPCS_CPA(core_mask),
129 CNL_ADSPCS_CPA(core_mask),
130 CNL_DSP_PU_TO,
131 "Power up");
132}
133
134static int cnl_dsp_core_power_down(struct sst_dsp *ctx, unsigned int core_mask)
135{
136 /* update bits */
137 sst_dsp_shim_update_bits_unlocked(ctx, CNL_ADSP_REG_ADSPCS,
138 CNL_ADSPCS_SPA(core_mask), 0);
139
140 /* poll with timeout to check if operation successful */
141 return sst_dsp_register_poll(ctx,
142 CNL_ADSP_REG_ADSPCS,
143 CNL_ADSPCS_CPA(core_mask),
144 0,
145 CNL_DSP_PD_TO,
146 "Power down");
147}
148
149int cnl_dsp_enable_core(struct sst_dsp *ctx, unsigned int core_mask)
150{
151 int ret;
152
153 /* power up */
154 ret = cnl_dsp_core_power_up(ctx, core_mask);
155 if (ret < 0) {
156 dev_dbg(ctx->dev, "DSP core mask %#x power up failed",
157 core_mask);
158 return ret;
159 }
160
161 return cnl_dsp_start_core(ctx, core_mask);
162}
163
164int cnl_dsp_disable_core(struct sst_dsp *ctx, unsigned int core_mask)
165{
166 int ret;
167
168 ret = cnl_dsp_reset_core(ctx, core_mask);
169 if (ret < 0) {
170 dev_err(ctx->dev, "DSP core mask %#x reset failed\n",
171 core_mask);
172 return ret;
173 }
174
175 /* power down core*/
176 ret = cnl_dsp_core_power_down(ctx, core_mask);
177 if (ret < 0) {
178 dev_err(ctx->dev, "DSP core mask %#x power down failed\n",
179 core_mask);
180 return ret;
181 }
182
183 if (is_cnl_dsp_core_enable(ctx, core_mask)) {
184 dev_err(ctx->dev, "DSP core mask %#x disable failed\n",
185 core_mask);
186 ret = -EIO;
187 }
188
189 return ret;
190}
191
192irqreturn_t cnl_dsp_sst_interrupt(int irq, void *dev_id)
193{
194 struct sst_dsp *ctx = dev_id;
195 u32 val;
196 irqreturn_t ret = IRQ_NONE;
197
198 spin_lock(&ctx->spinlock);
199
200 val = sst_dsp_shim_read_unlocked(ctx, CNL_ADSP_REG_ADSPIS);
201 ctx->intr_status = val;
202
203 if (val == 0xffffffff) {
204 spin_unlock(&ctx->spinlock);
205 return IRQ_NONE;
206 }
207
208 if (val & CNL_ADSPIS_IPC) {
209 cnl_ipc_int_disable(ctx);
210 ret = IRQ_WAKE_THREAD;
211 }
212
213 spin_unlock(&ctx->spinlock);
214
215 return ret;
216}
217
218void cnl_dsp_free(struct sst_dsp *dsp)
219{
220 cnl_ipc_int_disable(dsp);
221
222 free_irq(dsp->irq, dsp);
223 cnl_ipc_op_int_disable(dsp);
224 cnl_dsp_disable_core(dsp, SKL_DSP_CORE0_MASK);
225}
226EXPORT_SYMBOL_GPL(cnl_dsp_free);
227
228void cnl_ipc_int_enable(struct sst_dsp *ctx)
229{
230 sst_dsp_shim_update_bits(ctx, CNL_ADSP_REG_ADSPIC,
231 CNL_ADSPIC_IPC, CNL_ADSPIC_IPC);
232}
233
234void cnl_ipc_int_disable(struct sst_dsp *ctx)
235{
236 sst_dsp_shim_update_bits_unlocked(ctx, CNL_ADSP_REG_ADSPIC,
237 CNL_ADSPIC_IPC, 0);
238}
239
240void cnl_ipc_op_int_enable(struct sst_dsp *ctx)
241{
242 /* enable IPC DONE interrupt */
243 sst_dsp_shim_update_bits(ctx, CNL_ADSP_REG_HIPCCTL,
244 CNL_ADSP_REG_HIPCCTL_DONE,
245 CNL_ADSP_REG_HIPCCTL_DONE);
246
247 /* enable IPC BUSY interrupt */
248 sst_dsp_shim_update_bits(ctx, CNL_ADSP_REG_HIPCCTL,
249 CNL_ADSP_REG_HIPCCTL_BUSY,
250 CNL_ADSP_REG_HIPCCTL_BUSY);
251}
252
253void cnl_ipc_op_int_disable(struct sst_dsp *ctx)
254{
255 /* disable IPC DONE interrupt */
256 sst_dsp_shim_update_bits(ctx, CNL_ADSP_REG_HIPCCTL,
257 CNL_ADSP_REG_HIPCCTL_DONE, 0);
258
259 /* disable IPC BUSY interrupt */
260 sst_dsp_shim_update_bits(ctx, CNL_ADSP_REG_HIPCCTL,
261 CNL_ADSP_REG_HIPCCTL_BUSY, 0);
262}
263
264bool cnl_ipc_int_status(struct sst_dsp *ctx)
265{
266 return sst_dsp_shim_read_unlocked(ctx, CNL_ADSP_REG_ADSPIS) &
267 CNL_ADSPIS_IPC;
268}
269
270void cnl_ipc_free(struct sst_generic_ipc *ipc)
271{
272 cnl_ipc_op_int_disable(ipc->dsp);
273 sst_ipc_fini(ipc);
274}
sound/soc/intel/skylake/cnl-sst-dsp.h+112−0
@@ -0,0 +1,112 @@
1/*
2 * Cannonlake SST DSP Support
3 *
4 * Copyright (C) 2016-17, Intel Corporation.
5 *
6 * This program is free software; you can redistribute it and/or modify
7 * it under the terms of the GNU General Public License as version 2, as
8 * published by the Free Software Foundation.
9 *
10 * This program is distributed in the hope that it will be useful, but
11 * WITHOUT ANY WARRANTY; without even the implied warranty of
12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
13 * General Public License for more details.
14 */
15
16#ifndef __CNL_SST_DSP_H__
17#define __CNL_SST_DSP_H__
18
19struct sst_dsp;
20struct skl_sst;
21struct sst_dsp_device;
22struct sst_generic_ipc;
23
24/* Intel HD Audio General DSP Registers */
25#define CNL_ADSP_GEN_BASE 0x0
26#define CNL_ADSP_REG_ADSPCS (CNL_ADSP_GEN_BASE + 0x04)
27#define CNL_ADSP_REG_ADSPIC (CNL_ADSP_GEN_BASE + 0x08)
28#define CNL_ADSP_REG_ADSPIS (CNL_ADSP_GEN_BASE + 0x0c)
29
30/* Intel HD Audio Inter-Processor Communication Registers */
31#define CNL_ADSP_IPC_BASE 0xc0
32#define CNL_ADSP_REG_HIPCTDR (CNL_ADSP_IPC_BASE + 0x00)
33#define CNL_ADSP_REG_HIPCTDA (CNL_ADSP_IPC_BASE + 0x04)
34#define CNL_ADSP_REG_HIPCTDD (CNL_ADSP_IPC_BASE + 0x08)
35#define CNL_ADSP_REG_HIPCIDR (CNL_ADSP_IPC_BASE + 0x10)
36#define CNL_ADSP_REG_HIPCIDA (CNL_ADSP_IPC_BASE + 0x14)
37#define CNL_ADSP_REG_HIPCIDD (CNL_ADSP_IPC_BASE + 0x18)
38#define CNL_ADSP_REG_HIPCCTL (CNL_ADSP_IPC_BASE + 0x28)
39
40/* HIPCTDR */
41#define CNL_ADSP_REG_HIPCTDR_BUSY BIT(31)
42
43/* HIPCTDA */
44#define CNL_ADSP_REG_HIPCTDA_DONE BIT(31)
45
46/* HIPCIDR */
47#define CNL_ADSP_REG_HIPCIDR_BUSY BIT(31)
48
49/* HIPCIDA */
50#define CNL_ADSP_REG_HIPCIDA_DONE BIT(31)
51
52/* CNL HIPCCTL */
53#define CNL_ADSP_REG_HIPCCTL_DONE BIT(1)
54#define CNL_ADSP_REG_HIPCCTL_BUSY BIT(0)
55
56/* CNL HIPCT */
57#define CNL_ADSP_REG_HIPCT_BUSY BIT(31)
58
59/* Intel HD Audio SRAM Window 1 */
60#define CNL_ADSP_SRAM1_BASE 0xa0000
61
62#define CNL_ADSP_MMIO_LEN 0x10000
63
64#define CNL_ADSP_W0_STAT_SZ 0x1000
65
66#define CNL_ADSP_W0_UP_SZ 0x1000
67
68#define CNL_ADSP_W1_SZ 0x1000
69
70#define CNL_FW_STS_MASK 0xf
71
72#define CNL_ADSPIC_IPC 0x1
73#define CNL_ADSPIS_IPC 0x1
74
75#define CNL_DSP_CORES 4
76#define CNL_DSP_CORES_MASK ((1 << CNL_DSP_CORES) - 1)
77
78/* core reset - asserted high */
79#define CNL_ADSPCS_CRST_SHIFT 0
80#define CNL_ADSPCS_CRST(x) (x << CNL_ADSPCS_CRST_SHIFT)
81
82/* core run/stall - when set to 1 core is stalled */
83#define CNL_ADSPCS_CSTALL_SHIFT 8
84#define CNL_ADSPCS_CSTALL(x) (x << CNL_ADSPCS_CSTALL_SHIFT)
85
86/* set power active - when set to 1 turn core on */
87#define CNL_ADSPCS_SPA_SHIFT 16
88#define CNL_ADSPCS_SPA(x) (x << CNL_ADSPCS_SPA_SHIFT)
89
90/* current power active - power status of cores, set by hardware */
91#define CNL_ADSPCS_CPA_SHIFT 24
92#define CNL_ADSPCS_CPA(x) (x << CNL_ADSPCS_CPA_SHIFT)
93
94int cnl_dsp_enable_core(struct sst_dsp *ctx, unsigned int core);
95int cnl_dsp_disable_core(struct sst_dsp *ctx, unsigned int core);
96irqreturn_t cnl_dsp_sst_interrupt(int irq, void *dev_id);
97void cnl_dsp_free(struct sst_dsp *dsp);
98
99void cnl_ipc_int_enable(struct sst_dsp *ctx);
100void cnl_ipc_int_disable(struct sst_dsp *ctx);
101void cnl_ipc_op_int_enable(struct sst_dsp *ctx);
102void cnl_ipc_op_int_disable(struct sst_dsp *ctx);
103bool cnl_ipc_int_status(struct sst_dsp *ctx);
104void cnl_ipc_free(struct sst_generic_ipc *ipc);
105
106int cnl_sst_dsp_init(struct device *dev, void __iomem *mmio_base, int irq,
107 const char *fw_name, struct skl_dsp_loader_ops dsp_ops,
108 struct skl_sst **dsp);
109int cnl_sst_init_fw(struct device *dev, struct skl_sst *ctx);
110void cnl_sst_dsp_cleanup(struct device *dev, struct skl_sst *ctx);
111
112#endif /*__CNL_SST_DSP_H__*/
sound/soc/intel/skylake/cnl-sst.c+497−0
@@ -0,0 +1,497 @@
1/*
2 * cnl-sst.c - DSP library functions for CNL platform
3 *
4 * Copyright (C) 2016-17, Intel Corporation.
5 *
6 * Author: Guneshwor Singh <guneshwor.o.singh@intel.com>
7 *
8 * Modified from:
9 * HDA DSP library functions for SKL platform
10 * Copyright (C) 2014-15, Intel Corporation.
11 *
12 * ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
13 *
14 * This program is free software; you can redistribute it and/or modify
15 * it under the terms of the GNU General Public License as version 2, as
16 * published by the Free Software Foundation.
17 *
18 * This program is distributed in the hope that it will be useful, but
19 * WITHOUT ANY WARRANTY; without even the implied warranty of
20 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
21 * General Public License for more details.
22 *
23 * ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
24 */
25
26#include <linux/module.h>
27#include <linux/delay.h>
28#include <linux/firmware.h>
29#include <linux/device.h>
30
31#include "../common/sst-dsp.h"
32#include "../common/sst-dsp-priv.h"
33#include "../common/sst-ipc.h"
34#include "cnl-sst-dsp.h"
35#include "skl-sst-dsp.h"
36#include "skl-sst-ipc.h"
37
38#define CNL_FW_ROM_INIT 0x1
39#define CNL_FW_INIT 0x5
40#define CNL_IPC_PURGE 0x01004000
41#define CNL_INIT_TIMEOUT 300
42#define CNL_BASEFW_TIMEOUT 3000
43
44#define CNL_ADSP_SRAM0_BASE 0x80000
45
46/* Firmware status window */
47#define CNL_ADSP_FW_STATUS CNL_ADSP_SRAM0_BASE
48#define CNL_ADSP_ERROR_CODE (CNL_ADSP_FW_STATUS + 0x4)
49
50#define CNL_INSTANCE_ID 0
51#define CNL_BASE_FW_MODULE_ID 0
52#define CNL_ADSP_FW_HDR_OFFSET 0x2000
53#define CNL_ROM_CTRL_DMA_ID 0x9
54
55static int cnl_prepare_fw(struct sst_dsp *ctx, const void *fwdata, u32 fwsize)
56{
57
58 int ret, stream_tag;
59
60 stream_tag = ctx->dsp_ops.prepare(ctx->dev, 0x40, fwsize, &ctx->dmab);
61 if (stream_tag <= 0) {
62 dev_err(ctx->dev, "dma prepare failed: 0%#x\n", stream_tag);
63 return stream_tag;
64 }
65
66 ctx->dsp_ops.stream_tag = stream_tag;
67 memcpy(ctx->dmab.area, fwdata, fwsize);
68
69 /* purge FW request */
70 sst_dsp_shim_write(ctx, CNL_ADSP_REG_HIPCIDR,
71 CNL_ADSP_REG_HIPCIDR_BUSY | (CNL_IPC_PURGE |
72 ((stream_tag - 1) << CNL_ROM_CTRL_DMA_ID)));
73
74 ret = cnl_dsp_enable_core(ctx, SKL_DSP_CORE0_MASK);
75 if (ret < 0) {
76 dev_err(ctx->dev, "dsp boot core failed ret: %d\n", ret);
77 ret = -EIO;
78 goto base_fw_load_failed;
79 }
80
81 /* enable interrupt */
82 cnl_ipc_int_enable(ctx);
83 cnl_ipc_op_int_enable(ctx);
84
85 ret = sst_dsp_register_poll(ctx, CNL_ADSP_FW_STATUS, CNL_FW_STS_MASK,
86 CNL_FW_ROM_INIT, CNL_INIT_TIMEOUT,
87 "rom load");
88 if (ret < 0) {
89 dev_err(ctx->dev, "rom init timeout, ret: %d\n", ret);
90 goto base_fw_load_failed;
91 }
92
93 return 0;
94
95base_fw_load_failed:
96 ctx->dsp_ops.cleanup(ctx->dev, &ctx->dmab, stream_tag);
97 cnl_dsp_disable_core(ctx, SKL_DSP_CORE0_MASK);
98
99 return ret;
100}
101
102static int sst_transfer_fw_host_dma(struct sst_dsp *ctx)
103{
104 int ret;
105
106 ctx->dsp_ops.trigger(ctx->dev, true, ctx->dsp_ops.stream_tag);
107 ret = sst_dsp_register_poll(ctx, CNL_ADSP_FW_STATUS, CNL_FW_STS_MASK,
108 CNL_FW_INIT, CNL_BASEFW_TIMEOUT,
109 "firmware boot");
110
111 ctx->dsp_ops.trigger(ctx->dev, false, ctx->dsp_ops.stream_tag);
112 ctx->dsp_ops.cleanup(ctx->dev, &ctx->dmab, ctx->dsp_ops.stream_tag);
113
114 return ret;
115}
116
117static int cnl_load_base_firmware(struct sst_dsp *ctx)
118{
119 struct firmware stripped_fw;
120 struct skl_sst *cnl = ctx->thread_context;
121 int ret;
122
123 if (!ctx->fw) {
124 ret = request_firmware(&ctx->fw, ctx->fw_name, ctx->dev);
125 if (ret < 0) {
126 dev_err(ctx->dev, "request firmware failed: %d\n", ret);
127 goto cnl_load_base_firmware_failed;
128 }
129 }
130
131 /* parse uuids if first boot */
132 if (cnl->is_first_boot) {
133 ret = snd_skl_parse_uuids(ctx, ctx->fw,
134 CNL_ADSP_FW_HDR_OFFSET, 0);
135 if (ret < 0)
136 goto cnl_load_base_firmware_failed;
137 }
138
139 stripped_fw.data = ctx->fw->data;
140 stripped_fw.size = ctx->fw->size;
141 skl_dsp_strip_extended_manifest(&stripped_fw);
142
143 ret = cnl_prepare_fw(ctx, stripped_fw.data, stripped_fw.size);
144 if (ret < 0) {
145 dev_err(ctx->dev, "prepare firmware failed: %d\n", ret);
146 goto cnl_load_base_firmware_failed;
147 }
148
149 ret = sst_transfer_fw_host_dma(ctx);
150 if (ret < 0) {
151 dev_err(ctx->dev, "transfer firmware failed: %d\n", ret);
152 cnl_dsp_disable_core(ctx, SKL_DSP_CORE0_MASK);
153 goto cnl_load_base_firmware_failed;
154 }
155
156 ret = wait_event_timeout(cnl->boot_wait, cnl->boot_complete,
157 msecs_to_jiffies(SKL_IPC_BOOT_MSECS));
158 if (ret == 0) {
159 dev_err(ctx->dev, "FW ready timed-out\n");
160 cnl_dsp_disable_core(ctx, SKL_DSP_CORE0_MASK);
161 ret = -EIO;
162 goto cnl_load_base_firmware_failed;
163 }
164
165 cnl->fw_loaded = true;
166
167 return 0;
168
169cnl_load_base_firmware_failed:
170 release_firmware(ctx->fw);
171 ctx->fw = NULL;
172
173 return ret;
174}
175
176static int cnl_set_dsp_D0(struct sst_dsp *ctx, unsigned int core_id)
177{
178 struct skl_sst *cnl = ctx->thread_context;
179 unsigned int core_mask = SKL_DSP_CORE_MASK(core_id);
180 struct skl_ipc_dxstate_info dx;
181 int ret;
182
183 if (!cnl->fw_loaded) {
184 cnl->boot_complete = false;
185 ret = cnl_load_base_firmware(ctx);
186 if (ret < 0) {
187 dev_err(ctx->dev, "fw reload failed: %d\n", ret);
188 return ret;
189 }
190
191 cnl->cores.state[core_id] = SKL_DSP_RUNNING;
192 return ret;
193 }
194
195 ret = cnl_dsp_enable_core(ctx, core_mask);
196 if (ret < 0) {
197 dev_err(ctx->dev, "enable dsp core %d failed: %d\n",
198 core_id, ret);
199 goto err;
200 }
201
202 if (core_id == SKL_DSP_CORE0_ID) {
203 /* enable interrupt */
204 cnl_ipc_int_enable(ctx);
205 cnl_ipc_op_int_enable(ctx);
206 cnl->boot_complete = false;
207
208 ret = wait_event_timeout(cnl->boot_wait, cnl->boot_complete,
209 msecs_to_jiffies(SKL_IPC_BOOT_MSECS));
210 if (ret == 0) {
211 dev_err(ctx->dev,
212 "dsp boot timeout, status=%#x error=%#x\n",
213 sst_dsp_shim_read(ctx, CNL_ADSP_FW_STATUS),
214 sst_dsp_shim_read(ctx, CNL_ADSP_ERROR_CODE));
215 goto err;
216 }
217 } else {
218 dx.core_mask = core_mask;
219 dx.dx_mask = core_mask;
220
221 ret = skl_ipc_set_dx(&cnl->ipc, CNL_INSTANCE_ID,
222 CNL_BASE_FW_MODULE_ID, &dx);
223 if (ret < 0) {
224 dev_err(ctx->dev, "set_dx failed, core: %d ret: %d\n",
225 core_id, ret);
226 goto err;
227 }
228 }
229 cnl->cores.state[core_id] = SKL_DSP_RUNNING;
230
231 return 0;
232err:
233 cnl_dsp_disable_core(ctx, core_mask);
234
235 return ret;
236}
237
238static int cnl_set_dsp_D3(struct sst_dsp *ctx, unsigned int core_id)
239{
240 struct skl_sst *cnl = ctx->thread_context;
241 unsigned int core_mask = SKL_DSP_CORE_MASK(core_id);
242 struct skl_ipc_dxstate_info dx;
243 int ret;
244
245 dx.core_mask = core_mask;
246 dx.dx_mask = SKL_IPC_D3_MASK;
247
248 ret = skl_ipc_set_dx(&cnl->ipc, CNL_INSTANCE_ID,
249 CNL_BASE_FW_MODULE_ID, &dx);
250 if (ret < 0) {
251 dev_err(ctx->dev,
252 "dsp core %d to d3 failed; continue reset\n",
253 core_id);
254 cnl->fw_loaded = false;
255 }
256
257 /* disable interrupts if core 0 */
258 if (core_id == SKL_DSP_CORE0_ID) {
259 skl_ipc_op_int_disable(ctx);
260 skl_ipc_int_disable(ctx);
261 }
262
263 ret = cnl_dsp_disable_core(ctx, core_mask);
264 if (ret < 0) {
265 dev_err(ctx->dev, "disable dsp core %d failed: %d\n",
266 core_id, ret);
267 return ret;
268 }
269
270 cnl->cores.state[core_id] = SKL_DSP_RESET;
271
272 return ret;
273}
274
275static unsigned int cnl_get_errno(struct sst_dsp *ctx)
276{
277 return sst_dsp_shim_read(ctx, CNL_ADSP_ERROR_CODE);
278}
279
280static const struct skl_dsp_fw_ops cnl_fw_ops = {
281 .set_state_D0 = cnl_set_dsp_D0,
282 .set_state_D3 = cnl_set_dsp_D3,
283 .load_fw = cnl_load_base_firmware,
284 .get_fw_errcode = cnl_get_errno,
285};
286
287static struct sst_ops cnl_ops = {
288 .irq_handler = cnl_dsp_sst_interrupt,
289 .write = sst_shim32_write,
290 .read = sst_shim32_read,
291 .ram_read = sst_memcpy_fromio_32,
292 .ram_write = sst_memcpy_toio_32,
293 .free = cnl_dsp_free,
294};
295
296#define CNL_IPC_GLB_NOTIFY_RSP_SHIFT 29
297#define CNL_IPC_GLB_NOTIFY_RSP_MASK 0x1
298#define CNL_IPC_GLB_NOTIFY_RSP_TYPE(x) (((x) >> CNL_IPC_GLB_NOTIFY_RSP_SHIFT) \
299 & CNL_IPC_GLB_NOTIFY_RSP_MASK)
300
301static irqreturn_t cnl_dsp_irq_thread_handler(int irq, void *context)
302{
303 struct sst_dsp *dsp = context;
304 struct skl_sst *cnl = sst_dsp_get_thread_context(dsp);
305 struct sst_generic_ipc *ipc = &cnl->ipc;
306 struct skl_ipc_header header = {0};
307 u32 hipcida, hipctdr, hipctdd;
308 int ipc_irq = 0;
309
310 /* here we handle ipc interrupts only */
311 if (!(dsp->intr_status & CNL_ADSPIS_IPC))
312 return IRQ_NONE;
313
314 hipcida = sst_dsp_shim_read_unlocked(dsp, CNL_ADSP_REG_HIPCIDA);
315 hipctdr = sst_dsp_shim_read_unlocked(dsp, CNL_ADSP_REG_HIPCTDR);
316
317 /* reply message from dsp */
318 if (hipcida & CNL_ADSP_REG_HIPCIDA_DONE) {
319 sst_dsp_shim_update_bits(dsp, CNL_ADSP_REG_HIPCCTL,
320 CNL_ADSP_REG_HIPCCTL_DONE, 0);
321
322 /* clear done bit - tell dsp operation is complete */
323 sst_dsp_shim_update_bits_forced(dsp, CNL_ADSP_REG_HIPCIDA,
324 CNL_ADSP_REG_HIPCIDA_DONE, CNL_ADSP_REG_HIPCIDA_DONE);
325
326 ipc_irq = 1;
327
328 /* unmask done interrupt */
329 sst_dsp_shim_update_bits(dsp, CNL_ADSP_REG_HIPCCTL,
330 CNL_ADSP_REG_HIPCCTL_DONE, CNL_ADSP_REG_HIPCCTL_DONE);
331 }
332
333 /* new message from dsp */
334 if (hipctdr & CNL_ADSP_REG_HIPCTDR_BUSY) {
335 hipctdd = sst_dsp_shim_read_unlocked(dsp, CNL_ADSP_REG_HIPCTDD);
336 header.primary = hipctdr;
337 header.extension = hipctdd;
338 dev_dbg(dsp->dev, "IPC irq: Firmware respond primary:%x",
339 header.primary);
340 dev_dbg(dsp->dev, "IPC irq: Firmware respond extension:%x",
341 header.extension);
342
343 if (CNL_IPC_GLB_NOTIFY_RSP_TYPE(header.primary)) {
344 /* Handle Immediate reply from DSP Core */
345 skl_ipc_process_reply(ipc, header);
346 } else {
347 dev_dbg(dsp->dev, "IPC irq: Notification from firmware\n");
348 skl_ipc_process_notification(ipc, header);
349 }
350 /* clear busy interrupt */
351 sst_dsp_shim_update_bits_forced(dsp, CNL_ADSP_REG_HIPCTDR,
352 CNL_ADSP_REG_HIPCTDR_BUSY, CNL_ADSP_REG_HIPCTDR_BUSY);
353
354 /* set done bit to ack dsp */
355 sst_dsp_shim_update_bits_forced(dsp, CNL_ADSP_REG_HIPCTDA,
356 CNL_ADSP_REG_HIPCTDA_DONE, CNL_ADSP_REG_HIPCTDA_DONE);
357 ipc_irq = 1;
358 }
359
360 if (ipc_irq == 0)
361 return IRQ_NONE;
362
363 cnl_ipc_int_enable(dsp);
364
365 /* continue to send any remaining messages */
366 schedule_work(&ipc->kwork);
367
368 return IRQ_HANDLED;
369}
370
371static struct sst_dsp_device cnl_dev = {
372 .thread = cnl_dsp_irq_thread_handler,
373 .ops = &cnl_ops,
374};
375
376static void cnl_ipc_tx_msg(struct sst_generic_ipc *ipc, struct ipc_message *msg)
377{
378 struct skl_ipc_header *header = (struct skl_ipc_header *)(&msg->header);
379
380 if (msg->tx_size)
381 sst_dsp_outbox_write(ipc->dsp, msg->tx_data, msg->tx_size);
382 sst_dsp_shim_write_unlocked(ipc->dsp, CNL_ADSP_REG_HIPCIDD,
383 header->extension);
384 sst_dsp_shim_write_unlocked(ipc->dsp, CNL_ADSP_REG_HIPCIDR,
385 header->primary | CNL_ADSP_REG_HIPCIDR_BUSY);
386}
387
388static bool cnl_ipc_is_dsp_busy(struct sst_dsp *dsp)
389{
390 u32 hipcidr;
391
392 hipcidr = sst_dsp_shim_read_unlocked(dsp, CNL_ADSP_REG_HIPCIDR);
393
394 return (hipcidr & CNL_ADSP_REG_HIPCIDR_BUSY);
395}
396
397static int cnl_ipc_init(struct device *dev, struct skl_sst *cnl)
398{
399 struct sst_generic_ipc *ipc;
400 int err;
401
402 ipc = &cnl->ipc;
403 ipc->dsp = cnl->dsp;
404 ipc->dev = dev;
405
406 ipc->tx_data_max_size = CNL_ADSP_W1_SZ;
407 ipc->rx_data_max_size = CNL_ADSP_W0_UP_SZ;
408
409 err = sst_ipc_init(ipc);
410 if (err)
411 return err;
412
413 /*
414 * overriding tx_msg and is_dsp_busy since
415 * ipc registers are different for cnl
416 */
417 ipc->ops.tx_msg = cnl_ipc_tx_msg;
418 ipc->ops.tx_data_copy = skl_ipc_tx_data_copy;
419 ipc->ops.is_dsp_busy = cnl_ipc_is_dsp_busy;
420
421 return 0;
422}
423
424int cnl_sst_dsp_init(struct device *dev, void __iomem *mmio_base, int irq,
425 const char *fw_name, struct skl_dsp_loader_ops dsp_ops,
426 struct skl_sst **dsp)
427{
428 struct skl_sst *cnl;
429 struct sst_dsp *sst;
430 int ret;
431
432 ret = skl_sst_ctx_init(dev, irq, fw_name, dsp_ops, dsp, &cnl_dev);
433 if (ret < 0) {
434 dev_err(dev, "%s: no device\n", __func__);
435 return ret;
436 }
437
438 cnl = *dsp;
439 sst = cnl->dsp;
440 sst->fw_ops = cnl_fw_ops;
441 sst->addr.lpe = mmio_base;
442 sst->addr.shim = mmio_base;
443 sst->addr.sram0_base = CNL_ADSP_SRAM0_BASE;
444 sst->addr.sram1_base = CNL_ADSP_SRAM1_BASE;
445 sst->addr.w0_stat_sz = CNL_ADSP_W0_STAT_SZ;
446 sst->addr.w0_up_sz = CNL_ADSP_W0_UP_SZ;
447
448 sst_dsp_mailbox_init(sst, (CNL_ADSP_SRAM0_BASE + CNL_ADSP_W0_STAT_SZ),
449 CNL_ADSP_W0_UP_SZ, CNL_ADSP_SRAM1_BASE,
450 CNL_ADSP_W1_SZ);
451
452 ret = cnl_ipc_init(dev, cnl);
453 if (ret) {
454 skl_dsp_free(sst);
455 return ret;
456 }
457
458 cnl->boot_complete = false;
459 init_waitqueue_head(&cnl->boot_wait);
460
461 return 0;
462}
463EXPORT_SYMBOL_GPL(cnl_sst_dsp_init);
464
465int cnl_sst_init_fw(struct device *dev, struct skl_sst *ctx)
466{
467 int ret;
468 struct sst_dsp *sst = ctx->dsp;
469
470 ret = ctx->dsp->fw_ops.load_fw(sst);
471 if (ret < 0) {
472 dev_err(dev, "load base fw failed: %d", ret);
473 return ret;
474 }
475
476 skl_dsp_init_core_state(sst);
477
478 ctx->is_first_boot = false;
479
480 return 0;
481}
482EXPORT_SYMBOL_GPL(cnl_sst_init_fw);
483
484void cnl_sst_dsp_cleanup(struct device *dev, struct skl_sst *ctx)
485{
486 if (ctx->dsp->fw)
487 release_firmware(ctx->dsp->fw);
488
489 skl_freeup_uuid_list(ctx);
490 cnl_ipc_free(&ctx->ipc);
491
492 ctx->dsp->ops->free(ctx->dsp);
493}
494EXPORT_SYMBOL_GPL(cnl_sst_dsp_cleanup);
495
496MODULE_LICENSE("GPL v2");
497MODULE_DESCRIPTION("Intel Cannonlake IPC driver");
sound/soc/intel/skylake/skl-messages.c+135−28
@@ -22,6 +22,7 @@ · 21 unmodified lines
22#include <sound/core.h>22#include <sound/core.h>
23#include <sound/pcm.h>23#include <sound/pcm.h>
24#include "skl-sst-dsp.h"24#include "skl-sst-dsp.h"
25#include "cnl-sst-dsp.h"
25#include "skl-sst-ipc.h"26#include "skl-sst-ipc.h"
26#include "skl.h"27#include "skl.h"
27#include "../common/sst-dsp.h"28#include "../common/sst-dsp.h"
@@ -201,6 +202,7 @@ static struct skl_dsp_loader_ops bxt_get_loader_ops(void) · 173 unmodified lines
201static const struct skl_dsp_ops dsp_ops[] = {202static const struct skl_dsp_ops dsp_ops[] = {
202 {203 {
203 .id = 0x9d70,204 .id = 0x9d70,
205 .num_cores = 2,
204 .loader_ops = skl_get_loader_ops,206 .loader_ops = skl_get_loader_ops,
205 .init = skl_sst_dsp_init,207 .init = skl_sst_dsp_init,
206 .init_fw = skl_sst_init_fw,208 .init_fw = skl_sst_init_fw,
@@ -208,6 +210,7 @@ static const struct skl_dsp_ops dsp_ops[] = { · 1 unmodified line
208 },210 },
209 {211 {
210 .id = 0x9d71,212 .id = 0x9d71,
213 .num_cores = 2,
211 .loader_ops = skl_get_loader_ops,214 .loader_ops = skl_get_loader_ops,
212 .init = kbl_sst_dsp_init,215 .init = kbl_sst_dsp_init,
213 .init_fw = skl_sst_init_fw,216 .init_fw = skl_sst_init_fw,
@@ -215,6 +218,7 @@ static const struct skl_dsp_ops dsp_ops[] = { · 1 unmodified line
215 },218 },
216 {219 {
217 .id = 0x5a98,220 .id = 0x5a98,
221 .num_cores = 2,
218 .loader_ops = bxt_get_loader_ops,222 .loader_ops = bxt_get_loader_ops,
219 .init = bxt_sst_dsp_init,223 .init = bxt_sst_dsp_init,
220 .init_fw = bxt_sst_init_fw,224 .init_fw = bxt_sst_init_fw,
@@ -222,11 +226,20 @@ static const struct skl_dsp_ops dsp_ops[] = { · 1 unmodified line
222 },226 },
223 {227 {
224 .id = 0x3198,228 .id = 0x3198,
229 .num_cores = 2,
225 .loader_ops = bxt_get_loader_ops,230 .loader_ops = bxt_get_loader_ops,
226 .init = bxt_sst_dsp_init,231 .init = bxt_sst_dsp_init,
227 .init_fw = bxt_sst_init_fw,232 .init_fw = bxt_sst_init_fw,
228 .cleanup = bxt_sst_dsp_cleanup233 .cleanup = bxt_sst_dsp_cleanup
229 },234 },
235 {
236 .id = 0x9dc8,
237 .num_cores = 4,
238 .loader_ops = bxt_get_loader_ops,
239 .init = cnl_sst_dsp_init,
240 .init_fw = cnl_sst_init_fw,
241 .cleanup = cnl_sst_dsp_cleanup
242 },
230};243};
231 244
232const struct skl_dsp_ops *skl_get_dsp_ops(int pci_id)245const struct skl_dsp_ops *skl_get_dsp_ops(int pci_id)
@@ -249,6 +262,7 @@ int skl_init_dsp(struct skl *skl) · 16 unmodified lines
249 struct skl_dsp_loader_ops loader_ops;262 struct skl_dsp_loader_ops loader_ops;
250 int irq = bus->irq;263 int irq = bus->irq;
251 const struct skl_dsp_ops *ops;264 const struct skl_dsp_ops *ops;
265 struct skl_dsp_cores *cores;
252 int ret;266 int ret;
253 267
254 /* enable ppcap interrupt */268 /* enable ppcap interrupt */
@@ -263,8 +277,10 @@ int skl_init_dsp(struct skl *skl) · 8 unmodified lines
263 }277 }
264 278
265 ops = skl_get_dsp_ops(skl->pci->device);279 ops = skl_get_dsp_ops(skl->pci->device);
266 if (!ops)280 if (!ops) {
267 return -EIO;281 ret = -EIO;
282 goto unmap_mmio;
283 }
268 284
269 loader_ops = ops->loader_ops();285 loader_ops = ops->loader_ops();
270 ret = ops->init(bus->dev, mmio_base, irq,286 ret = ops->init(bus->dev, mmio_base, irq,
@@ -272,11 +288,35 @@ int skl_init_dsp(struct skl *skl) · 1 unmodified line
272 &skl->skl_sst);288 &skl->skl_sst);
273 289
274 if (ret < 0)290 if (ret < 0)
275 return ret;291 goto unmap_mmio;
276 292
277 skl->skl_sst->dsp_ops = ops;293 skl->skl_sst->dsp_ops = ops;
294 cores = &skl->skl_sst->cores;
295 cores->count = ops->num_cores;
296
297 cores->state = kcalloc(cores->count, sizeof(*cores->state), GFP_KERNEL);
298 if (!cores->state) {
299 ret = -ENOMEM;
300 goto unmap_mmio;
301 }
302
303 cores->usage_count = kcalloc(cores->count, sizeof(*cores->usage_count),
304 GFP_KERNEL);
305 if (!cores->usage_count) {
306 ret = -ENOMEM;
307 goto free_core_state;
308 }
309
278 dev_dbg(bus->dev, "dsp registration status=%d\n", ret);310 dev_dbg(bus->dev, "dsp registration status=%d\n", ret);
279 311
312 return 0;
313
314free_core_state:
315 kfree(cores->state);
316
317unmap_mmio:
318 iounmap(mmio_base);
319
280 return ret;320 return ret;
281}321}
282 322
@@ -291,6 +331,9 @@ int skl_free_dsp(struct skl *skl) · 8 unmodified lines
291 331
292 ctx->dsp_ops->cleanup(bus->dev, ctx);332 ctx->dsp_ops->cleanup(bus->dev, ctx);
293 333
334 kfree(ctx->cores.state);
335 kfree(ctx->cores.usage_count);
336
294 if (ctx->dsp->addr.lpe)337 if (ctx->dsp->addr.lpe)
295 iounmap(ctx->dsp->addr.lpe);338 iounmap(ctx->dsp->addr.lpe);
296 339
@@ -400,9 +443,12 @@ static void skl_set_base_module_format(struct skl_sst *ctx, · 103 unmodified lines
400 struct skl_module_cfg *mconfig,443 struct skl_module_cfg *mconfig,
401 struct skl_base_cfg *base_cfg)444 struct skl_base_cfg *base_cfg)
402{445{
403 struct skl_module_fmt *format = &mconfig->in_fmt[0];446 struct skl_module *module = mconfig->module;
447 struct skl_module_res *res = &module->resources[mconfig->res_idx];
448 struct skl_module_iface *fmt = &module->formats[mconfig->fmt_idx];
449 struct skl_module_fmt *format = &fmt->inputs[0].fmt;
404 450
405 base_cfg->audio_fmt.number_of_channels = (u8)format->channels;451 base_cfg->audio_fmt.number_of_channels = format->channels;
406 452
407 base_cfg->audio_fmt.s_freq = format->s_freq;453 base_cfg->audio_fmt.s_freq = format->s_freq;
408 base_cfg->audio_fmt.bit_depth = format->bit_depth;454 base_cfg->audio_fmt.bit_depth = format->bit_depth;
@@ -417,10 +463,10 @@ static void skl_set_base_module_format(struct skl_sst *ctx, · 8 unmodified lines
417 463
418 base_cfg->audio_fmt.interleaving = format->interleaving_style;464 base_cfg->audio_fmt.interleaving = format->interleaving_style;
419 465
420 base_cfg->cps = mconfig->mcps;466 base_cfg->cps = res->cps;
421 base_cfg->ibs = mconfig->ibs;467 base_cfg->ibs = res->ibs;
422 base_cfg->obs = mconfig->obs;468 base_cfg->obs = res->obs;
423 base_cfg->is_pages = mconfig->mem_pages;469 base_cfg->is_pages = res->is_pages;
424}470}
425 471
426/*472/*
@@ -508,6 +554,9 @@ static void skl_setup_cpr_gateway_cfg(struct skl_sst *ctx, · 81 unmodified lines
508 struct skl_cpr_cfg *cpr_mconfig)554 struct skl_cpr_cfg *cpr_mconfig)
509{555{
510 u32 dma_io_buf;556 u32 dma_io_buf;
557 struct skl_module_res *res;
558 int res_idx = mconfig->res_idx;
559 struct skl *skl = get_skl_ctx(ctx->dev);
511 560
512 cpr_mconfig->gtw_cfg.node_id = skl_get_node_id(ctx, mconfig);561 cpr_mconfig->gtw_cfg.node_id = skl_get_node_id(ctx, mconfig);
513 562
@@ -516,19 +565,27 @@ static void skl_setup_cpr_gateway_cfg(struct skl_sst *ctx, · 2 unmodified lines
516 return;565 return;
517 }566 }
518 567
568 if (skl->nr_modules) {
569 res = &mconfig->module->resources[mconfig->res_idx];
570 cpr_mconfig->gtw_cfg.dma_buffer_size = res->dma_buffer_size;
571 goto skip_buf_size_calc;
572 } else {
573 res = &mconfig->module->resources[res_idx];
574 }
575
519 switch (mconfig->hw_conn_type) {576 switch (mconfig->hw_conn_type) {
520 case SKL_CONN_SOURCE:577 case SKL_CONN_SOURCE:
521 if (mconfig->dev_type == SKL_DEVICE_HDAHOST)578 if (mconfig->dev_type == SKL_DEVICE_HDAHOST)
522 dma_io_buf = mconfig->ibs;579 dma_io_buf = res->ibs;
523 else580 else
524 dma_io_buf = mconfig->obs;581 dma_io_buf = res->obs;
525 break;582 break;
526 583
527 case SKL_CONN_SINK:584 case SKL_CONN_SINK:
528 if (mconfig->dev_type == SKL_DEVICE_HDAHOST)585 if (mconfig->dev_type == SKL_DEVICE_HDAHOST)
529 dma_io_buf = mconfig->obs;586 dma_io_buf = res->obs;
530 else587 else
531 dma_io_buf = mconfig->ibs;588 dma_io_buf = res->ibs;
532 break;589 break;
533 590
534 default:591 default:
@@ -543,11 +600,12 @@ static void skl_setup_cpr_gateway_cfg(struct skl_sst *ctx, · 8 unmodified lines
543 /* fallback to 2ms default value */600 /* fallback to 2ms default value */
544 if (!cpr_mconfig->gtw_cfg.dma_buffer_size) {601 if (!cpr_mconfig->gtw_cfg.dma_buffer_size) {
545 if (mconfig->hw_conn_type == SKL_CONN_SOURCE)602 if (mconfig->hw_conn_type == SKL_CONN_SOURCE)
546 cpr_mconfig->gtw_cfg.dma_buffer_size = 2 * mconfig->obs;603 cpr_mconfig->gtw_cfg.dma_buffer_size = 2 * res->obs;
547 else604 else
548 cpr_mconfig->gtw_cfg.dma_buffer_size = 2 * mconfig->ibs;605 cpr_mconfig->gtw_cfg.dma_buffer_size = 2 * res->ibs;
549 }606 }
550 607
608skip_buf_size_calc:
551 cpr_mconfig->cpr_feature_mask = 0;609 cpr_mconfig->cpr_feature_mask = 0;
552 cpr_mconfig->gtw_cfg.config_length = 0;610 cpr_mconfig->gtw_cfg.config_length = 0;
553 611
@@ -595,7 +653,9 @@ static void skl_setup_out_format(struct skl_sst *ctx, · 41 unmodified lines
595 struct skl_module_cfg *mconfig,653 struct skl_module_cfg *mconfig,
596 struct skl_audio_data_format *out_fmt)654 struct skl_audio_data_format *out_fmt)
597{655{
598 struct skl_module_fmt *format = &mconfig->out_fmt[0];656 struct skl_module *module = mconfig->module;
657 struct skl_module_iface *fmt = &module->formats[mconfig->fmt_idx];
658 struct skl_module_fmt *format = &fmt->outputs[0].fmt;
599 659
600 out_fmt->number_of_channels = (u8)format->channels;660 out_fmt->number_of_channels = (u8)format->channels;
601 out_fmt->s_freq = format->s_freq;661 out_fmt->s_freq = format->s_freq;
@@ -620,7 +680,9 @@ static void skl_set_src_format(struct skl_sst *ctx, · 18 unmodified lines
620 struct skl_module_cfg *mconfig,680 struct skl_module_cfg *mconfig,
621 struct skl_src_module_cfg *src_mconfig)681 struct skl_src_module_cfg *src_mconfig)
622{682{
623 struct skl_module_fmt *fmt = &mconfig->out_fmt[0];683 struct skl_module *module = mconfig->module;
684 struct skl_module_iface *iface = &module->formats[mconfig->fmt_idx];
685 struct skl_module_fmt *fmt = &iface->outputs[0].fmt;
624 686
625 skl_set_base_module_format(ctx, mconfig,687 skl_set_base_module_format(ctx, mconfig,
626 (struct skl_base_cfg *)src_mconfig);688 (struct skl_base_cfg *)src_mconfig);
@@ -637,7 +699,9 @@ static void skl_set_updown_mixer_format(struct skl_sst *ctx, · 10 unmodified lines
637 struct skl_module_cfg *mconfig,699 struct skl_module_cfg *mconfig,
638 struct skl_up_down_mixer_cfg *mixer_mconfig)700 struct skl_up_down_mixer_cfg *mixer_mconfig)
639{701{
640 struct skl_module_fmt *fmt = &mconfig->out_fmt[0];702 struct skl_module *module = mconfig->module;
703 struct skl_module_iface *iface = &module->formats[mconfig->fmt_idx];
704 struct skl_module_fmt *fmt = &iface->outputs[0].fmt;
641 int i = 0;705 int i = 0;
642 706
643 skl_set_base_module_format(ctx, mconfig,707 skl_set_base_module_format(ctx, mconfig,
@@ -950,7 +1014,7 @@ static void skl_dump_bind_info(struct skl_sst *ctx, struct skl_module_cfg · 306 unmodified lines
950{1014{
951 dev_dbg(ctx->dev, "%s: src module_id = %d src_instance=%d\n",1015 dev_dbg(ctx->dev, "%s: src module_id = %d src_instance=%d\n",
952 __func__, src_module->id.module_id, src_module->id.pvt_id);1016 __func__, src_module->id.module_id, src_module->id.pvt_id);
953 dev_dbg(ctx->dev, "%s: dst_module=%d dst_instacne=%d\n", __func__,1017 dev_dbg(ctx->dev, "%s: dst_module=%d dst_instance=%d\n", __func__,
954 dst_module->id.module_id, dst_module->id.pvt_id);1018 dst_module->id.module_id, dst_module->id.pvt_id);
955 1019
956 dev_dbg(ctx->dev, "src_module state = %d dst module state = %d\n",1020 dev_dbg(ctx->dev, "src_module state = %d dst module state = %d\n",
@@ -970,8 +1034,8 @@ int skl_unbind_modules(struct skl_sst *ctx, · 13 unmodified lines
970 struct skl_ipc_bind_unbind_msg msg;1034 struct skl_ipc_bind_unbind_msg msg;
971 struct skl_module_inst_id src_id = src_mcfg->id;1035 struct skl_module_inst_id src_id = src_mcfg->id;
972 struct skl_module_inst_id dst_id = dst_mcfg->id;1036 struct skl_module_inst_id dst_id = dst_mcfg->id;
973 int in_max = dst_mcfg->max_in_queue;1037 int in_max = dst_mcfg->module->max_input_pins;
974 int out_max = src_mcfg->max_out_queue;1038 int out_max = src_mcfg->module->max_output_pins;
975 int src_index, dst_index, src_pin_state, dst_pin_state;1039 int src_index, dst_index, src_pin_state, dst_pin_state;
976 1040
977 skl_dump_bind_info(ctx, src_mcfg, dst_mcfg);1041 skl_dump_bind_info(ctx, src_mcfg, dst_mcfg);
@@ -1019,6 +1083,21 @@ int skl_unbind_modules(struct skl_sst *ctx, · 41 unmodified lines
1019 return ret;1083 return ret;
1020}1084}
1021 1085
1086static void fill_pin_params(struct skl_audio_data_format *pin_fmt,
1087 struct skl_module_fmt *format)
1088{
1089 pin_fmt->number_of_channels = format->channels;
1090 pin_fmt->s_freq = format->s_freq;
1091 pin_fmt->bit_depth = format->bit_depth;
1092 pin_fmt->valid_bit_depth = format->valid_bit_depth;
1093 pin_fmt->ch_cfg = format->ch_cfg;
1094 pin_fmt->sample_type = format->sample_type;
1095 pin_fmt->channel_map = format->ch_map;
1096 pin_fmt->interleaving = format->interleaving_style;
1097}
1098
1099#define CPR_SINK_FMT_PARAM_ID 2
1100
1022/*1101/*
1023 * Once a module is instantiated it need to be 'bind' with other modules in1102 * Once a module is instantiated it need to be 'bind' with other modules in
1024 * the pipeline. For binding we need to find the module pins which are bind1103 * the pipeline. For binding we need to find the module pins which are bind
@@ -1030,11 +1109,15 @@ int skl_bind_modules(struct skl_sst *ctx, · 5 unmodified lines
1030 struct skl_module_cfg *src_mcfg,1109 struct skl_module_cfg *src_mcfg,
1031 struct skl_module_cfg *dst_mcfg)1110 struct skl_module_cfg *dst_mcfg)
1032{1111{
1033 int ret;1112 int ret = 0;
1034 struct skl_ipc_bind_unbind_msg msg;1113 struct skl_ipc_bind_unbind_msg msg;
1035 int in_max = dst_mcfg->max_in_queue;1114 int in_max = dst_mcfg->module->max_input_pins;
1036 int out_max = src_mcfg->max_out_queue;1115 int out_max = src_mcfg->module->max_output_pins;
1037 int src_index, dst_index;1116 int src_index, dst_index;
1117 struct skl_module_fmt *format;
1118 struct skl_cpr_pin_fmt pin_fmt;
1119 struct skl_module *module;
1120 struct skl_module_iface *fmt;
1038 1121
1039 skl_dump_bind_info(ctx, src_mcfg, dst_mcfg);1122 skl_dump_bind_info(ctx, src_mcfg, dst_mcfg);
1040 1123
@@ -1053,6 +1136,29 @@ int skl_bind_modules(struct skl_sst *ctx, · 12 unmodified lines
1053 return -EINVAL;1136 return -EINVAL;
1054 }1137 }
1055 1138
1139 /*
1140 * Copier module requires the separate large_config_set_ipc to
1141 * configure the pins other than 0
1142 */
1143 if (src_mcfg->m_type == SKL_MODULE_TYPE_COPIER && src_index > 0) {
1144 pin_fmt.sink_id = src_index;
1145 module = src_mcfg->module;
1146 fmt = &module->formats[src_mcfg->fmt_idx];
1147
1148 /* Input fmt is same as that of src module input cfg */
1149 format = &fmt->inputs[0].fmt;
1150 fill_pin_params(&(pin_fmt.src_fmt), format);
1151
1152 format = &fmt->outputs[src_index].fmt;
1153 fill_pin_params(&(pin_fmt.dst_fmt), format);
1154 ret = skl_set_module_params(ctx, (void *)&pin_fmt,
1155 sizeof(struct skl_cpr_pin_fmt),
1156 CPR_SINK_FMT_PARAM_ID, src_mcfg);
1157
1158 if (ret < 0)
1159 goto out;
1160 }
1161
1056 msg.dst_queue = dst_index;1162 msg.dst_queue = dst_index;
1057 1163
1058 dev_dbg(ctx->dev, "src queue = %d dst queue =%d\n",1164 dev_dbg(ctx->dev, "src queue = %d dst queue =%d\n",
@@ -1070,11 +1176,12 @@ int skl_bind_modules(struct skl_sst *ctx, · 11 unmodified lines
1070 src_mcfg->m_state = SKL_MODULE_BIND_DONE;1176 src_mcfg->m_state = SKL_MODULE_BIND_DONE;
1071 src_mcfg->m_out_pin[src_index].pin_state = SKL_PIN_BIND_DONE;1177 src_mcfg->m_out_pin[src_index].pin_state = SKL_PIN_BIND_DONE;
1072 dst_mcfg->m_in_pin[dst_index].pin_state = SKL_PIN_BIND_DONE;1178 dst_mcfg->m_in_pin[dst_index].pin_state = SKL_PIN_BIND_DONE;
1073 } else {1179 return ret;
1074 /* error case , if IPC fails, clear the queue index */
1075 skl_free_queue(src_mcfg->m_out_pin, src_index);
1076 skl_free_queue(dst_mcfg->m_in_pin, dst_index);
1077 }1180 }
1181out:
1182 /* error case , if IPC fails, clear the queue index */
1183 skl_free_queue(src_mcfg->m_out_pin, src_index);
1184 skl_free_queue(dst_mcfg->m_in_pin, dst_index);
1078 1185
1079 return ret;1186 return ret;
1080}1187}
sound/soc/intel/skylake/skl-pcm.c+72−10
@@ -33,7 +33,7 @@ · 32 unmodified lines
33#define HDA_STEREO 233#define HDA_STEREO 2
34#define HDA_QUAD 434#define HDA_QUAD 4
35 35
36static struct snd_pcm_hardware azx_pcm_hw = {36static const struct snd_pcm_hardware azx_pcm_hw = {
37 .info = (SNDRV_PCM_INFO_MMAP |37 .info = (SNDRV_PCM_INFO_MMAP |
38 SNDRV_PCM_INFO_INTERLEAVED |38 SNDRV_PCM_INFO_INTERLEAVED |
39 SNDRV_PCM_INFO_BLOCK_TRANSFER |39 SNDRV_PCM_INFO_BLOCK_TRANSFER |
@@ -628,7 +628,7 @@ static int skl_link_hw_free(struct snd_pcm_substream *substream, · 588 unmodified lines
628 return 0;628 return 0;
629}629}
630 630
631static struct snd_soc_dai_ops skl_pcm_dai_ops = {631static const struct snd_soc_dai_ops skl_pcm_dai_ops = {
632 .startup = skl_pcm_open,632 .startup = skl_pcm_open,
633 .shutdown = skl_pcm_close,633 .shutdown = skl_pcm_close,
634 .prepare = skl_pcm_prepare,634 .prepare = skl_pcm_prepare,
@@ -637,15 +637,15 @@ static struct snd_soc_dai_ops skl_pcm_dai_ops = { · 2 unmodified lines
637 .trigger = skl_pcm_trigger,637 .trigger = skl_pcm_trigger,
638};638};
639 639
640static struct snd_soc_dai_ops skl_dmic_dai_ops = {640static const struct snd_soc_dai_ops skl_dmic_dai_ops = {
641 .hw_params = skl_be_hw_params,641 .hw_params = skl_be_hw_params,
642};642};
643 643
644static struct snd_soc_dai_ops skl_be_ssp_dai_ops = {644static const struct snd_soc_dai_ops skl_be_ssp_dai_ops = {
645 .hw_params = skl_be_hw_params,645 .hw_params = skl_be_hw_params,
646};646};
647 647
648static struct snd_soc_dai_ops skl_link_dai_ops = {648static const struct snd_soc_dai_ops skl_link_dai_ops = {
649 .prepare = skl_link_pcm_prepare,649 .prepare = skl_link_pcm_prepare,
650 .hw_params = skl_link_hw_params,650 .hw_params = skl_link_hw_params,
651 .hw_free = skl_link_hw_free,651 .hw_free = skl_link_hw_free,
@@ -674,6 +674,32 @@ static struct snd_soc_dai_driver skl_platform_dai[] = { · 22 unmodified lines
674 .sig_bits = 32,674 .sig_bits = 32,
675 },675 },
676},676},
677{
678 .name = "System Pin2",
679 .ops = &skl_pcm_dai_ops,
680 .playback = {
681 .stream_name = "Headset Playback",
682 .channels_min = HDA_MONO,
683 .channels_max = HDA_STEREO,
684 .rates = SNDRV_PCM_RATE_48000 | SNDRV_PCM_RATE_16000 |
685 SNDRV_PCM_RATE_8000,
686 .formats = SNDRV_PCM_FMTBIT_S16_LE |
687 SNDRV_PCM_FMTBIT_S24_LE | SNDRV_PCM_FMTBIT_S32_LE,
688 },
689},
690{
691 .name = "Echoref Pin",
692 .ops = &skl_pcm_dai_ops,
693 .capture = {
694 .stream_name = "Echoreference Capture",
695 .channels_min = HDA_STEREO,
696 .channels_max = HDA_STEREO,
697 .rates = SNDRV_PCM_RATE_48000 | SNDRV_PCM_RATE_16000 |
698 SNDRV_PCM_RATE_8000,
699 .formats = SNDRV_PCM_FMTBIT_S16_LE |
700 SNDRV_PCM_FMTBIT_S24_LE | SNDRV_PCM_FMTBIT_S32_LE,
701 },
702},
677{703{
678 .name = "Reference Pin",704 .name = "Reference Pin",
679 .ops = &skl_pcm_dai_ops,705 .ops = &skl_pcm_dai_ops,
@@ -1194,8 +1220,11 @@ static int skl_pcm_new(struct snd_soc_pcm_runtime *rtd) · 514 unmodified lines
1194static int skl_get_module_info(struct skl *skl, struct skl_module_cfg *mconfig)1220static int skl_get_module_info(struct skl *skl, struct skl_module_cfg *mconfig)
1195{1221{
1196 struct skl_sst *ctx = skl->skl_sst;1222 struct skl_sst *ctx = skl->skl_sst;
1223 struct skl_module_inst_id *pin_id;
1224 uuid_le *uuid_mod, *uuid_tplg;
1225 struct skl_module *skl_module;
1197 struct uuid_module *module;1226 struct uuid_module *module;
1198 uuid_le *uuid_mod;1227 int i, ret = -EIO;
1199 1228
1200 uuid_mod = (uuid_le *)mconfig->guid;1229 uuid_mod = (uuid_le *)mconfig->guid;
1201 1230
@@ -1207,12 +1236,45 @@ static int skl_get_module_info(struct skl *skl, struct skl_module_cfg *mconfig) · 5 unmodified lines
1207 list_for_each_entry(module, &ctx->uuid_list, list) {1236 list_for_each_entry(module, &ctx->uuid_list, list) {
1208 if (uuid_le_cmp(*uuid_mod, module->uuid) == 0) {1237 if (uuid_le_cmp(*uuid_mod, module->uuid) == 0) {
1209 mconfig->id.module_id = module->id;1238 mconfig->id.module_id = module->id;
1210 mconfig->is_loadable = module->is_loadable;1239 if (mconfig->module)
1211 return 0;1240 mconfig->module->loadable = module->is_loadable;
1241 ret = 0;
1242 break;
1243 }
1244 }
1245
1246 if (ret)
1247 return ret;
1248
1249 uuid_mod = &module->uuid;
1250 ret = -EIO;
1251 for (i = 0; i < skl->nr_modules; i++) {
1252 skl_module = skl->modules[i];
1253 uuid_tplg = &skl_module->uuid;
1254 if (!uuid_le_cmp(*uuid_mod, *uuid_tplg)) {
1255 mconfig->module = skl_module;
1256 ret = 0;
1257 break;
1212 }1258 }
1213 }1259 }
1260 if (skl->nr_modules && ret)
1261 return ret;
1214 1262
1215 return -EIO;1263 list_for_each_entry(module, &ctx->uuid_list, list) {
1264 for (i = 0; i < MAX_IN_QUEUE; i++) {
1265 pin_id = &mconfig->m_in_pin[i].id;
1266 if (!uuid_le_cmp(pin_id->mod_uuid, module->uuid))
1267 pin_id->module_id = module->id;
1268 }
1269
1270 for (i = 0; i < MAX_OUT_QUEUE; i++) {
1271 pin_id = &mconfig->m_out_pin[i].id;
1272 if (!uuid_le_cmp(pin_id->mod_uuid, module->uuid))
1273 pin_id->module_id = module->id;
1274 }
1275 }
1276
1277 return 0;
1216}1278}
1217 1279
1218static int skl_populate_modules(struct skl *skl)1280static int skl_populate_modules(struct skl *skl)
@@ -1284,7 +1346,7 @@ static int skl_platform_soc_probe(struct snd_soc_platform *platform) · 65 unmodified lines
1284 1346
1285 return 0;1347 return 0;
1286}1348}
1287static struct snd_soc_platform_driver skl_platform_drv = {1349static const struct snd_soc_platform_driver skl_platform_drv = {
1288 .probe = skl_platform_soc_probe,1350 .probe = skl_platform_soc_probe,
1289 .ops = &skl_platform_ops,1351 .ops = &skl_platform_ops,
1290 .pcm_new = skl_pcm_new,1352 .pcm_new = skl_pcm_new,
sound/soc/intel/skylake/skl-sst-dsp.c+3−3
@@ -47,7 +47,7 @@ void skl_dsp_init_core_state(struct sst_dsp *ctx) · 46 unmodified lines
47 skl->cores.state[SKL_DSP_CORE0_ID] = SKL_DSP_RUNNING;47 skl->cores.state[SKL_DSP_CORE0_ID] = SKL_DSP_RUNNING;
48 skl->cores.usage_count[SKL_DSP_CORE0_ID] = 1;48 skl->cores.usage_count[SKL_DSP_CORE0_ID] = 1;
49 49
50 for (i = SKL_DSP_CORE0_ID + 1; i < SKL_DSP_CORES_MAX; i++) {50 for (i = SKL_DSP_CORE0_ID + 1; i < skl->cores.count; i++) {
51 skl->cores.state[i] = SKL_DSP_RESET;51 skl->cores.state[i] = SKL_DSP_RESET;
52 skl->cores.usage_count[i] = 0;52 skl->cores.usage_count[i] = 0;
53 }53 }
@@ -351,6 +351,8 @@ int skl_dsp_get_core(struct sst_dsp *ctx, unsigned int core_id) · 297 unmodified lines
351 return -EINVAL;351 return -EINVAL;
352 }352 }
353 353
354 skl->cores.usage_count[core_id]++;
355
354 if (skl->cores.state[core_id] == SKL_DSP_RESET) {356 if (skl->cores.state[core_id] == SKL_DSP_RESET) {
355 ret = ctx->fw_ops.set_state_D0(ctx, core_id);357 ret = ctx->fw_ops.set_state_D0(ctx, core_id);
356 if (ret < 0) {358 if (ret < 0) {
@@ -359,8 +361,6 @@ int skl_dsp_get_core(struct sst_dsp *ctx, unsigned int core_id) · 2 unmodified lines
359 }361 }
360 }362 }
361 363
362 skl->cores.usage_count[core_id]++;
363
364out:364out:
365 dev_dbg(ctx->dev, "core id %d state %d usage_count %d\n",365 dev_dbg(ctx->dev, "core id %d state %d usage_count %d\n",
366 core_id, skl->cores.state[core_id],366 core_id, skl->cores.state[core_id],
sound/soc/intel/skylake/skl-sst-ipc.c+3−3
@@ -283,7 +283,7 @@ enum skl_ipc_module_msg { · 282 unmodified lines
283 IPC_MOD_SET_D0IX = 8283 IPC_MOD_SET_D0IX = 8
284};284};
285 285
286static void skl_ipc_tx_data_copy(struct ipc_message *msg, char *tx_data,286void skl_ipc_tx_data_copy(struct ipc_message *msg, char *tx_data,
287 size_t tx_size)287 size_t tx_size)
288{288{
289 if (tx_size)289 if (tx_size)
@@ -347,7 +347,7 @@ out: · 57 unmodified lines
347 347
348}348}
349 349
350static int skl_ipc_process_notification(struct sst_generic_ipc *ipc,350int skl_ipc_process_notification(struct sst_generic_ipc *ipc,
351 struct skl_ipc_header header)351 struct skl_ipc_header header)
352{352{
353 struct skl_sst *skl = container_of(ipc, struct skl_sst, ipc);353 struct skl_sst *skl = container_of(ipc, struct skl_sst, ipc);
@@ -406,7 +406,7 @@ static int skl_ipc_set_reply_error_code(u32 reply) · 52 unmodified lines
406 }406 }
407}407}
408 408
409static void skl_ipc_process_reply(struct sst_generic_ipc *ipc,409void skl_ipc_process_reply(struct sst_generic_ipc *ipc,
410 struct skl_ipc_header header)410 struct skl_ipc_header header)
411{411{
412 struct ipc_message *msg;412 struct ipc_message *msg;
sound/soc/intel/skylake/skl-sst-ipc.h+8−4
@@ -44,12 +44,10 @@ struct skl_ipc_header { · 43 unmodified lines
44 u32 extension;44 u32 extension;
45};45};
46 46
47#define SKL_DSP_CORES_MAX 2
48
49struct skl_dsp_cores {47struct skl_dsp_cores {
50 unsigned int count;48 unsigned int count;
51 enum skl_dsp_states state[SKL_DSP_CORES_MAX];49 enum skl_dsp_states *state;
52 int usage_count[SKL_DSP_CORES_MAX];50 int *usage_count;
53};51};
54 52
55/**53/**
@@ -214,4 +212,10 @@ void skl_ipc_free(struct sst_generic_ipc *ipc); · 158 unmodified lines
214int skl_ipc_init(struct device *dev, struct skl_sst *skl);212int skl_ipc_init(struct device *dev, struct skl_sst *skl);
215void skl_clear_module_cnt(struct sst_dsp *ctx);213void skl_clear_module_cnt(struct sst_dsp *ctx);
216 214
215void skl_ipc_process_reply(struct sst_generic_ipc *ipc,
216 struct skl_ipc_header header);
217int skl_ipc_process_notification(struct sst_generic_ipc *ipc,
218 struct skl_ipc_header header);
219void skl_ipc_tx_data_copy(struct ipc_message *msg, char *tx_data,
220 size_t tx_size);
217#endif /* __SKL_IPC_H */221#endif /* __SKL_IPC_H */
sound/soc/intel/skylake/skl-sst-utils.c+1−5
@@ -368,7 +368,6 @@ int skl_sst_ctx_init(struct device *dev, int irq, const char *fw_name, · 367 unmodified lines
368{368{
369 struct skl_sst *skl;369 struct skl_sst *skl;
370 struct sst_dsp *sst;370 struct sst_dsp *sst;
371 int ret;
372 371
373 skl = devm_kzalloc(dev, sizeof(*skl), GFP_KERNEL);372 skl = devm_kzalloc(dev, sizeof(*skl), GFP_KERNEL);
374 if (skl == NULL)373 if (skl == NULL)
@@ -388,15 +387,12 @@ int skl_sst_ctx_init(struct device *dev, int irq, const char *fw_name, · 13 unmodified lines
388 sst->dsp_ops = dsp_ops;387 sst->dsp_ops = dsp_ops;
389 init_waitqueue_head(&skl->mod_load_wait);388 init_waitqueue_head(&skl->mod_load_wait);
390 INIT_LIST_HEAD(&sst->module_list);389 INIT_LIST_HEAD(&sst->module_list);
391 ret = skl_ipc_init(dev, skl);
392 if (ret)
393 return ret;
394 390
395 skl->is_first_boot = true;391 skl->is_first_boot = true;
396 if (dsp)392 if (dsp)
397 *dsp = skl;393 *dsp = skl;
398 394
399 return ret;395 return 0;
400}396}
401 397
402int skl_prepare_lib_load(struct skl_sst *skl, struct skl_lib_info *linfo,398int skl_prepare_lib_load(struct skl_sst *skl, struct skl_lib_info *linfo,
sound/soc/intel/skylake/skl-sst.c+8−4
@@ -503,7 +503,7 @@ static void skl_clear_module_table(struct sst_dsp *ctx) · 502 unmodified lines
503 }503 }
504}504}
505 505
506static struct skl_dsp_fw_ops skl_fw_ops = {506static const struct skl_dsp_fw_ops skl_fw_ops = {
507 .set_state_D0 = skl_set_dsp_D0,507 .set_state_D0 = skl_set_dsp_D0,
508 .set_state_D3 = skl_set_dsp_D3,508 .set_state_D3 = skl_set_dsp_D3,
509 .load_fw = skl_load_base_firmware,509 .load_fw = skl_load_base_firmware,
@@ -512,7 +512,7 @@ static struct skl_dsp_fw_ops skl_fw_ops = { · 2 unmodified lines
512 .unload_mod = skl_unload_module,512 .unload_mod = skl_unload_module,
513};513};
514 514
515static struct skl_dsp_fw_ops kbl_fw_ops = {515static const struct skl_dsp_fw_ops kbl_fw_ops = {
516 .set_state_D0 = skl_set_dsp_D0,516 .set_state_D0 = skl_set_dsp_D0,
517 .set_state_D3 = skl_set_dsp_D3,517 .set_state_D3 = skl_set_dsp_D3,
518 .load_fw = skl_load_base_firmware,518 .load_fw = skl_load_base_firmware,
@@ -561,9 +561,13 @@ int skl_sst_dsp_init(struct device *dev, void __iomem *mmio_base, int irq, · 42 unmodified lines
561 sst_dsp_mailbox_init(sst, (SKL_ADSP_SRAM0_BASE + SKL_ADSP_W0_STAT_SZ),561 sst_dsp_mailbox_init(sst, (SKL_ADSP_SRAM0_BASE + SKL_ADSP_W0_STAT_SZ),
562 SKL_ADSP_W0_UP_SZ, SKL_ADSP_SRAM1_BASE, SKL_ADSP_W1_SZ);562 SKL_ADSP_W0_UP_SZ, SKL_ADSP_SRAM1_BASE, SKL_ADSP_W1_SZ);
563 563
564 sst->fw_ops = skl_fw_ops;564 ret = skl_ipc_init(dev, skl);
565 if (ret) {
566 skl_dsp_free(sst);
567 return ret;
568 }
565 569
566 skl->cores.count = 2;570 sst->fw_ops = skl_fw_ops;
567 571
568 return 0;572 return 0;
569}573}
sound/soc/intel/skylake/skl-topology.c+633−108
@@ -49,6 +49,9 @@ static const int mic_quatro_list[][SKL_CH_QUATRO] = { · 48 unmodified lines
49{0, 1, 2, 3},49{0, 1, 2, 3},
50};50};
51 51
52#define CHECK_HW_PARAMS(ch, freq, bps, prm_ch, prm_freq, prm_bps) \
53 ((ch == prm_ch) && (bps == prm_bps) && (freq == prm_freq))
54
52void skl_tplg_d0i3_get(struct skl *skl, enum d0i3_capability caps)55void skl_tplg_d0i3_get(struct skl *skl, enum d0i3_capability caps)
53{56{
54 struct skl_d0i3_data *d0i3 = &skl->skl_sst->d0i3;57 struct skl_d0i3_data *d0i3 = &skl->skl_sst->d0i3;
@@ -153,8 +156,10 @@ static bool skl_is_pipe_mcps_avail(struct skl *skl, · 98 unmodified lines
153 struct skl_module_cfg *mconfig)156 struct skl_module_cfg *mconfig)
154{157{
155 struct skl_sst *ctx = skl->skl_sst;158 struct skl_sst *ctx = skl->skl_sst;
159 u8 res_idx = mconfig->res_idx;
160 struct skl_module_res *res = &mconfig->module->resources[res_idx];
156 161
157 if (skl->resource.mcps + mconfig->mcps > skl->resource.max_mcps) {162 if (skl->resource.mcps + res->cps > skl->resource.max_mcps) {
158 dev_err(ctx->dev,163 dev_err(ctx->dev,
159 "%s: module_id %d instance %d\n", __func__,164 "%s: module_id %d instance %d\n", __func__,
160 mconfig->id.module_id, mconfig->id.instance_id);165 mconfig->id.module_id, mconfig->id.instance_id);
@@ -170,7 +175,10 @@ static bool skl_is_pipe_mcps_avail(struct skl *skl, · 9 unmodified lines
170static void skl_tplg_alloc_pipe_mcps(struct skl *skl,175static void skl_tplg_alloc_pipe_mcps(struct skl *skl,
171 struct skl_module_cfg *mconfig)176 struct skl_module_cfg *mconfig)
172{177{
173 skl->resource.mcps += mconfig->mcps;178 u8 res_idx = mconfig->res_idx;
179 struct skl_module_res *res = &mconfig->module->resources[res_idx];
180
181 skl->resource.mcps += res->cps;
174}182}
175 183
176/*184/*
@@ -179,7 +187,11 @@ static void skl_tplg_alloc_pipe_mcps(struct skl *skl, · 2 unmodified lines
179static void187static void
180skl_tplg_free_pipe_mcps(struct skl *skl, struct skl_module_cfg *mconfig)188skl_tplg_free_pipe_mcps(struct skl *skl, struct skl_module_cfg *mconfig)
181{189{
182 skl->resource.mcps -= mconfig->mcps;190 u8 res_idx = mconfig->res_idx;
191 struct skl_module_res *res = &mconfig->module->resources[res_idx];
192
193 res = &mconfig->module->resources[res_idx];
194 skl->resource.mcps -= res->cps;
183}195}
184 196
185/*197/*
@@ -195,17 +207,21 @@ skl_tplg_free_pipe_mem(struct skl *skl, struct skl_module_cfg *mconfig) · 9 unmodified lines
195static void skl_dump_mconfig(struct skl_sst *ctx,207static void skl_dump_mconfig(struct skl_sst *ctx,
196 struct skl_module_cfg *mcfg)208 struct skl_module_cfg *mcfg)
197{209{
210 struct skl_module_iface *iface = &mcfg->module->formats[0];
211
198 dev_dbg(ctx->dev, "Dumping config\n");212 dev_dbg(ctx->dev, "Dumping config\n");
199 dev_dbg(ctx->dev, "Input Format:\n");213 dev_dbg(ctx->dev, "Input Format:\n");
200 dev_dbg(ctx->dev, "channels = %d\n", mcfg->in_fmt[0].channels);214 dev_dbg(ctx->dev, "channels = %d\n", iface->inputs[0].fmt.channels);
201 dev_dbg(ctx->dev, "s_freq = %d\n", mcfg->in_fmt[0].s_freq);215 dev_dbg(ctx->dev, "s_freq = %d\n", iface->inputs[0].fmt.s_freq);
202 dev_dbg(ctx->dev, "ch_cfg = %d\n", mcfg->in_fmt[0].ch_cfg);216 dev_dbg(ctx->dev, "ch_cfg = %d\n", iface->inputs[0].fmt.ch_cfg);
203 dev_dbg(ctx->dev, "valid bit depth = %d\n", mcfg->in_fmt[0].valid_bit_depth);217 dev_dbg(ctx->dev, "valid bit depth = %d\n",
218 iface->inputs[0].fmt.valid_bit_depth);
204 dev_dbg(ctx->dev, "Output Format:\n");219 dev_dbg(ctx->dev, "Output Format:\n");
205 dev_dbg(ctx->dev, "channels = %d\n", mcfg->out_fmt[0].channels);220 dev_dbg(ctx->dev, "channels = %d\n", iface->outputs[0].fmt.channels);
206 dev_dbg(ctx->dev, "s_freq = %d\n", mcfg->out_fmt[0].s_freq);221 dev_dbg(ctx->dev, "s_freq = %d\n", iface->outputs[0].fmt.s_freq);
207 dev_dbg(ctx->dev, "valid bit depth = %d\n", mcfg->out_fmt[0].valid_bit_depth);222 dev_dbg(ctx->dev, "valid bit depth = %d\n",
208 dev_dbg(ctx->dev, "ch_cfg = %d\n", mcfg->out_fmt[0].ch_cfg);223 iface->outputs[0].fmt.valid_bit_depth);
224 dev_dbg(ctx->dev, "ch_cfg = %d\n", iface->outputs[0].fmt.ch_cfg);
209}225}
210 226
211static void skl_tplg_update_chmap(struct skl_module_fmt *fmt, int chs)227static void skl_tplg_update_chmap(struct skl_module_fmt *fmt, int chs)
@@ -273,8 +289,8 @@ static void skl_tplg_update_params_fixup(struct skl_module_cfg *m_cfg, · 61 unmodified lines
273 struct skl_module_fmt *in_fmt, *out_fmt;289 struct skl_module_fmt *in_fmt, *out_fmt;
274 290
275 /* Fixups will be applied to pin 0 only */291 /* Fixups will be applied to pin 0 only */
276 in_fmt = &m_cfg->in_fmt[0];292 in_fmt = &m_cfg->module->formats[0].inputs[0].fmt;
277 out_fmt = &m_cfg->out_fmt[0];293 out_fmt = &m_cfg->module->formats[0].outputs[0].fmt;
278 294
279 if (params->stream == SNDRV_PCM_STREAM_PLAYBACK) {295 if (params->stream == SNDRV_PCM_STREAM_PLAYBACK) {
280 if (is_fe) {296 if (is_fe) {
@@ -312,21 +328,23 @@ static void skl_tplg_update_buffer_size(struct skl_sst *ctx, · 31 unmodified lines
312{328{
313 int multiplier = 1;329 int multiplier = 1;
314 struct skl_module_fmt *in_fmt, *out_fmt;330 struct skl_module_fmt *in_fmt, *out_fmt;
331 struct skl_module_res *res;
315 332
316 /* Since fixups is applied to pin 0 only, ibs, obs needs333 /* Since fixups is applied to pin 0 only, ibs, obs needs
317 * change for pin 0 only334 * change for pin 0 only
318 */335 */
319 in_fmt = &mcfg->in_fmt[0];336 res = &mcfg->module->resources[0];
320 out_fmt = &mcfg->out_fmt[0];337 in_fmt = &mcfg->module->formats[0].inputs[0].fmt;
338 out_fmt = &mcfg->module->formats[0].outputs[0].fmt;
321 339
322 if (mcfg->m_type == SKL_MODULE_TYPE_SRCINT)340 if (mcfg->m_type == SKL_MODULE_TYPE_SRCINT)
323 multiplier = 5;341 multiplier = 5;
324 342
325 mcfg->ibs = DIV_ROUND_UP(in_fmt->s_freq, 1000) *343 res->ibs = DIV_ROUND_UP(in_fmt->s_freq, 1000) *
326 in_fmt->channels * (in_fmt->bit_depth >> 3) *344 in_fmt->channels * (in_fmt->bit_depth >> 3) *
327 multiplier;345 multiplier;
328 346
329 mcfg->obs = DIV_ROUND_UP(out_fmt->s_freq, 1000) *347 res->obs = DIV_ROUND_UP(out_fmt->s_freq, 1000) *
330 out_fmt->channels * (out_fmt->bit_depth >> 3) *348 out_fmt->channels * (out_fmt->bit_depth >> 3) *
331 multiplier;349 multiplier;
332}350}
@@ -365,6 +383,8 @@ static int skl_tplg_update_be_blob(struct snd_soc_dapm_widget *w, · 32 unmodified lines
365 struct nhlt_specific_cfg *cfg;383 struct nhlt_specific_cfg *cfg;
366 struct skl *skl = get_skl_ctx(ctx->dev);384 struct skl *skl = get_skl_ctx(ctx->dev);
367 u8 dev_type = skl_tplg_be_dev_type(m_cfg->dev_type);385 u8 dev_type = skl_tplg_be_dev_type(m_cfg->dev_type);
386 int fmt_idx = m_cfg->fmt_idx;
387 struct skl_module_iface *m_iface = &m_cfg->module->formats[fmt_idx];
368 388
369 /* check if we already have blob */389 /* check if we already have blob */
370 if (m_cfg->formats_config.caps_size > 0)390 if (m_cfg->formats_config.caps_size > 0)
@@ -375,23 +395,23 @@ static int skl_tplg_update_be_blob(struct snd_soc_dapm_widget *w, · 4 unmodified lines
375 case SKL_DEVICE_DMIC:395 case SKL_DEVICE_DMIC:
376 link_type = NHLT_LINK_DMIC;396 link_type = NHLT_LINK_DMIC;
377 dir = SNDRV_PCM_STREAM_CAPTURE;397 dir = SNDRV_PCM_STREAM_CAPTURE;
378 s_freq = m_cfg->in_fmt[0].s_freq;398 s_freq = m_iface->inputs[0].fmt.s_freq;
379 s_fmt = m_cfg->in_fmt[0].bit_depth;399 s_fmt = m_iface->inputs[0].fmt.bit_depth;
380 ch = m_cfg->in_fmt[0].channels;400 ch = m_iface->inputs[0].fmt.channels;
381 break;401 break;
382 402
383 case SKL_DEVICE_I2S:403 case SKL_DEVICE_I2S:
384 link_type = NHLT_LINK_SSP;404 link_type = NHLT_LINK_SSP;
385 if (m_cfg->hw_conn_type == SKL_CONN_SOURCE) {405 if (m_cfg->hw_conn_type == SKL_CONN_SOURCE) {
386 dir = SNDRV_PCM_STREAM_PLAYBACK;406 dir = SNDRV_PCM_STREAM_PLAYBACK;
387 s_freq = m_cfg->out_fmt[0].s_freq;407 s_freq = m_iface->outputs[0].fmt.s_freq;
388 s_fmt = m_cfg->out_fmt[0].bit_depth;408 s_fmt = m_iface->outputs[0].fmt.bit_depth;
389 ch = m_cfg->out_fmt[0].channels;409 ch = m_iface->outputs[0].fmt.channels;
390 } else {410 } else {
391 dir = SNDRV_PCM_STREAM_CAPTURE;411 dir = SNDRV_PCM_STREAM_CAPTURE;
392 s_freq = m_cfg->in_fmt[0].s_freq;412 s_freq = m_iface->inputs[0].fmt.s_freq;
393 s_fmt = m_cfg->in_fmt[0].bit_depth;413 s_fmt = m_iface->inputs[0].fmt.bit_depth;
394 ch = m_cfg->in_fmt[0].channels;414 ch = m_iface->inputs[0].fmt.channels;
395 }415 }
396 break;416 break;
397 417
@@ -549,6 +569,7 @@ skl_tplg_init_pipe_modules(struct skl *skl, struct skl_pipe *pipe) · 151 unmodified lines
549 struct snd_soc_dapm_widget *w;569 struct snd_soc_dapm_widget *w;
550 struct skl_module_cfg *mconfig;570 struct skl_module_cfg *mconfig;
551 struct skl_sst *ctx = skl->skl_sst;571 struct skl_sst *ctx = skl->skl_sst;
572 u8 cfg_idx;
552 int ret = 0;573 int ret = 0;
553 574
554 list_for_each_entry(w_module, &pipe->w_list, node) {575 list_for_each_entry(w_module, &pipe->w_list, node) {
@@ -564,11 +585,15 @@ skl_tplg_init_pipe_modules(struct skl *skl, struct skl_pipe *pipe) · 9 unmodified lines
564 return -EIO;585 return -EIO;
565 }586 }
566 587
588 cfg_idx = mconfig->pipe->cur_config_idx;
589 mconfig->fmt_idx = mconfig->mod_cfg[cfg_idx].fmt_idx;
590 mconfig->res_idx = mconfig->mod_cfg[cfg_idx].res_idx;
591
567 /* check resource available */592 /* check resource available */
568 if (!skl_is_pipe_mcps_avail(skl, mconfig))593 if (!skl_is_pipe_mcps_avail(skl, mconfig))
569 return -ENOMEM;594 return -ENOMEM;
570 595
571 if (mconfig->is_loadable && ctx->dsp->fw_ops.load_mod) {596 if (mconfig->module->loadable && ctx->dsp->fw_ops.load_mod) {
572 ret = ctx->dsp->fw_ops.load_mod(ctx->dsp,597 ret = ctx->dsp->fw_ops.load_mod(ctx->dsp,
573 mconfig->id.module_id, mconfig->guid);598 mconfig->id.module_id, mconfig->guid);
574 if (ret < 0)599 if (ret < 0)
@@ -596,24 +621,35 @@ skl_tplg_init_pipe_modules(struct skl *skl, struct skl_pipe *pipe) · 21 unmodified lines
596 if (mconfig->id.pvt_id < 0)621 if (mconfig->id.pvt_id < 0)
597 return ret;622 return ret;
598 skl_tplg_set_module_init_data(w);623 skl_tplg_set_module_init_data(w);
624
625 ret = skl_dsp_get_core(ctx->dsp, mconfig->core_id);
626 if (ret < 0) {
627 dev_err(ctx->dev, "Failed to wake up core %d ret=%d\n",
628 mconfig->core_id, ret);
629 return ret;
630 }
631
599 ret = skl_init_module(ctx, mconfig);632 ret = skl_init_module(ctx, mconfig);
600 if (ret < 0) {633 if (ret < 0) {
601 skl_put_pvt_id(ctx, uuid_mod, &mconfig->id.pvt_id);634 skl_put_pvt_id(ctx, uuid_mod, &mconfig->id.pvt_id);
602 return ret;635 goto err;
603 }636 }
604 skl_tplg_alloc_pipe_mcps(skl, mconfig);637 skl_tplg_alloc_pipe_mcps(skl, mconfig);
605 ret = skl_tplg_set_module_params(w, ctx);638 ret = skl_tplg_set_module_params(w, ctx);
606 if (ret < 0)639 if (ret < 0)
607 return ret;640 goto err;
608 }641 }
609 642
610 return 0;643 return 0;
644err:
645 skl_dsp_put_core(ctx->dsp, mconfig->core_id);
646 return ret;
611}647}
612 648
613static int skl_tplg_unload_pipe_modules(struct skl_sst *ctx,649static int skl_tplg_unload_pipe_modules(struct skl_sst *ctx,
614 struct skl_pipe *pipe)650 struct skl_pipe *pipe)
615{651{
616 int ret;652 int ret = 0;
617 struct skl_pipe_module *w_module = NULL;653 struct skl_pipe_module *w_module = NULL;
618 struct skl_module_cfg *mconfig = NULL;654 struct skl_module_cfg *mconfig = NULL;
619 655
@@ -622,7 +658,7 @@ static int skl_tplg_unload_pipe_modules(struct skl_sst *ctx, · 2 unmodified lines
622 mconfig = w_module->w->priv;658 mconfig = w_module->w->priv;
623 uuid_mod = (uuid_le *)mconfig->guid;659 uuid_mod = (uuid_le *)mconfig->guid;
624 660
625 if (mconfig->is_loadable && ctx->dsp->fw_ops.unload_mod &&661 if (mconfig->module->loadable && ctx->dsp->fw_ops.unload_mod &&
626 mconfig->m_state > SKL_MODULE_UNINIT) {662 mconfig->m_state > SKL_MODULE_UNINIT) {
627 ret = ctx->dsp->fw_ops.unload_mod(ctx->dsp,663 ret = ctx->dsp->fw_ops.unload_mod(ctx->dsp,
628 mconfig->id.module_id);664 mconfig->id.module_id);
@@ -630,10 +666,76 @@ static int skl_tplg_unload_pipe_modules(struct skl_sst *ctx, · 1 unmodified line
630 return -EIO;666 return -EIO;
631 }667 }
632 skl_put_pvt_id(ctx, uuid_mod, &mconfig->id.pvt_id);668 skl_put_pvt_id(ctx, uuid_mod, &mconfig->id.pvt_id);
669
670 ret = skl_dsp_put_core(ctx->dsp, mconfig->core_id);
671 if (ret < 0) {
672 /* don't return; continue with other modules */
673 dev_err(ctx->dev, "Failed to sleep core %d ret=%d\n",
674 mconfig->core_id, ret);
675 }
633 }676 }
634 677
635 /* no modules to unload in this path, so return */678 /* no modules to unload in this path, so return */
636 return 0;679 return ret;
680}
681
682/*
683 * Here, we select pipe format based on the pipe type and pipe
684 * direction to determine the current config index for the pipeline.
685 * The config index is then used to select proper module resources.
686 * Intermediate pipes currently have a fixed format hence we select the
687 * 0th configuratation by default for such pipes.
688 */
689static int
690skl_tplg_get_pipe_config(struct skl *skl, struct skl_module_cfg *mconfig)
691{
692 struct skl_sst *ctx = skl->skl_sst;
693 struct skl_pipe *pipe = mconfig->pipe;
694 struct skl_pipe_params *params = pipe->p_params;
695 struct skl_path_config *pconfig = &pipe->configs[0];
696 struct skl_pipe_fmt *fmt = NULL;
697 bool in_fmt = false;
698 int i;
699
700 if (pipe->nr_cfgs == 0) {
701 pipe->cur_config_idx = 0;
702 return 0;
703 }
704
705 if (pipe->conn_type == SKL_PIPE_CONN_TYPE_NONE) {
706 dev_dbg(ctx->dev, "No conn_type detected, take 0th config\n");
707 pipe->cur_config_idx = 0;
708 pipe->memory_pages = pconfig->mem_pages;
709
710 return 0;
711 }
712
713 if ((pipe->conn_type == SKL_PIPE_CONN_TYPE_FE &&
714 pipe->direction == SNDRV_PCM_STREAM_PLAYBACK) ||
715 (pipe->conn_type == SKL_PIPE_CONN_TYPE_BE &&
716 pipe->direction == SNDRV_PCM_STREAM_CAPTURE))
717 in_fmt = true;
718
719 for (i = 0; i < pipe->nr_cfgs; i++) {
720 pconfig = &pipe->configs[i];
721 if (in_fmt)
722 fmt = &pconfig->in_fmt;
723 else
724 fmt = &pconfig->out_fmt;
725
726 if (CHECK_HW_PARAMS(params->ch, params->s_freq, params->s_fmt,
727 fmt->channels, fmt->freq, fmt->bps)) {
728 pipe->cur_config_idx = i;
729 pipe->memory_pages = pconfig->mem_pages;
730 dev_dbg(ctx->dev, "Using pipe config: %d\n", i);
731
732 return 0;
733 }
734 }
735
736 dev_err(ctx->dev, "Invalid pipe config: %d %d %d for pipe: %d\n",
737 params->ch, params->s_freq, params->s_fmt, pipe->ppl_id);
738 return -EINVAL;
637}739}
638 740
639/*741/*
@@ -655,6 +757,10 @@ static int skl_tplg_mixer_dapm_pre_pmu_event(struct snd_soc_dapm_widget *w, · 15 unmodified lines
655 struct skl_sst *ctx = skl->skl_sst;757 struct skl_sst *ctx = skl->skl_sst;
656 struct skl_module_deferred_bind *modules;758 struct skl_module_deferred_bind *modules;
657 759
760 ret = skl_tplg_get_pipe_config(skl, mconfig);
761 if (ret < 0)
762 return ret;
763
658 /* check resource available */764 /* check resource available */
659 if (!skl_is_pipe_mcps_avail(skl, mconfig))765 if (!skl_is_pipe_mcps_avail(skl, mconfig))
660 return -EBUSY;766 return -EBUSY;
@@ -758,12 +864,12 @@ static int skl_tplg_set_module_bind_params(struct snd_soc_dapm_widget *w, · 97 unmodified lines
758 * check all out/in pins are in bind state.864 * check all out/in pins are in bind state.
759 * if so set the module param865 * if so set the module param
760 */866 */
761 for (i = 0; i < mcfg->max_out_queue; i++) {867 for (i = 0; i < mcfg->module->max_output_pins; i++) {
762 if (mcfg->m_out_pin[i].pin_state != SKL_PIN_BIND_DONE)868 if (mcfg->m_out_pin[i].pin_state != SKL_PIN_BIND_DONE)
763 return 0;869 return 0;
764 }870 }
765 871
766 for (i = 0; i < mcfg->max_in_queue; i++) {872 for (i = 0; i < mcfg->module->max_input_pins; i++) {
767 if (mcfg->m_in_pin[i].pin_state != SKL_PIN_BIND_DONE)873 if (mcfg->m_in_pin[i].pin_state != SKL_PIN_BIND_DONE)
768 return 0;874 return 0;
769 }875 }
@@ -814,7 +920,7 @@ static int skl_tplg_module_add_deferred_bind(struct skl *skl, · 44 unmodified lines
814 int i;920 int i;
815 921
816 /* only supported for module with static pin connection */922 /* only supported for module with static pin connection */
817 for (i = 0; i < dst->max_in_queue; i++) {923 for (i = 0; i < dst->module->max_input_pins; i++) {
818 struct skl_module_pin *pin = &dst->m_in_pin[i];924 struct skl_module_pin *pin = &dst->m_in_pin[i];
819 925
820 if (pin->is_dynamic)926 if (pin->is_dynamic)
@@ -925,7 +1031,7 @@ static int skl_tplg_bind_sinks(struct snd_soc_dapm_widget *w, · 104 unmodified lines
925 }1031 }
926 }1032 }
927 1033
928 if (!sink)1034 if (!sink && next_sink)
929 return skl_tplg_bind_sinks(next_sink, skl, src_w, src_mconfig);1035 return skl_tplg_bind_sinks(next_sink, skl, src_w, src_mconfig);
930 1036
931 return 0;1037 return 0;
@@ -1074,7 +1180,7 @@ static int skl_tplg_mixer_dapm_pre_pmd_event(struct snd_soc_dapm_widget *w, · 142 unmodified lines
1074 if (ret)1180 if (ret)
1075 return ret;1181 return ret;
1076 1182
1077 for (i = 0; i < sink_mconfig->max_in_queue; i++) {1183 for (i = 0; i < sink_mconfig->module->max_input_pins; i++) {
1078 if (sink_mconfig->m_in_pin[i].pin_state == SKL_PIN_BIND_DONE) {1184 if (sink_mconfig->m_in_pin[i].pin_state == SKL_PIN_BIND_DONE) {
1079 src_mconfig = sink_mconfig->m_in_pin[i].tgt_mcfg;1185 src_mconfig = sink_mconfig->m_in_pin[i].tgt_mcfg;
1080 if (!src_mconfig)1186 if (!src_mconfig)
@@ -1185,7 +1291,7 @@ static int skl_tplg_pga_dapm_post_pmd_event(struct snd_soc_dapm_widget *w, · 104 unmodified lines
1185 if (ret)1291 if (ret)
1186 return ret;1292 return ret;
1187 1293
1188 for (i = 0; i < src_mconfig->max_out_queue; i++) {1294 for (i = 0; i < src_mconfig->module->max_output_pins; i++) {
1189 if (src_mconfig->m_out_pin[i].pin_state == SKL_PIN_BIND_DONE) {1295 if (src_mconfig->m_out_pin[i].pin_state == SKL_PIN_BIND_DONE) {
1190 sink_mconfig = src_mconfig->m_out_pin[i].tgt_mcfg;1296 sink_mconfig = src_mconfig->m_out_pin[i].tgt_mcfg;
1191 if (!sink_mconfig)1297 if (!sink_mconfig)
@@ -1479,14 +1585,22 @@ int skl_tplg_update_pipe_params(struct device *dev, · 287 unmodified lines
1479 struct skl_module_cfg *mconfig,1585 struct skl_module_cfg *mconfig,
1480 struct skl_pipe_params *params)1586 struct skl_pipe_params *params)
1481{1587{
1588 struct skl_module_res *res = &mconfig->module->resources[0];
1589 struct skl *skl = get_skl_ctx(dev);
1482 struct skl_module_fmt *format = NULL;1590 struct skl_module_fmt *format = NULL;
1591 u8 cfg_idx = mconfig->pipe->cur_config_idx;
1483 1592
1484 skl_tplg_fill_dma_id(mconfig, params);1593 skl_tplg_fill_dma_id(mconfig, params);
1594 mconfig->fmt_idx = mconfig->mod_cfg[cfg_idx].fmt_idx;
1595 mconfig->res_idx = mconfig->mod_cfg[cfg_idx].res_idx;
1596
1597 if (skl->nr_modules)
1598 return 0;
1485 1599
1486 if (params->stream == SNDRV_PCM_STREAM_PLAYBACK)1600 if (params->stream == SNDRV_PCM_STREAM_PLAYBACK)
1487 format = &mconfig->in_fmt[0];1601 format = &mconfig->module->formats[0].inputs[0].fmt;
1488 else1602 else
1489 format = &mconfig->out_fmt[0];1603 format = &mconfig->module->formats[0].outputs[0].fmt;
1490 1604
1491 /* set the hw_params */1605 /* set the hw_params */
1492 format->s_freq = params->s_freq;1606 format->s_freq = params->s_freq;
@@ -1514,11 +1628,11 @@ int skl_tplg_update_pipe_params(struct device *dev, · 21 unmodified lines
1514 }1628 }
1515 1629
1516 if (params->stream == SNDRV_PCM_STREAM_PLAYBACK) {1630 if (params->stream == SNDRV_PCM_STREAM_PLAYBACK) {
1517 mconfig->ibs = (format->s_freq / 1000) *1631 res->ibs = (format->s_freq / 1000) *
1518 (format->channels) *1632 (format->channels) *
1519 (format->bit_depth >> 3);1633 (format->bit_depth >> 3);
1520 } else {1634 } else {
1521 mconfig->obs = (format->s_freq / 1000) *1635 res->obs = (format->s_freq / 1000) *
1522 (format->channels) *1636 (format->channels) *
1523 (format->bit_depth >> 3);1637 (format->bit_depth >> 3);
1524 }1638 }
@@ -1792,6 +1906,54 @@ static const struct snd_soc_tplg_kcontrol_ops skl_tplg_kcontrol_ops[] = { · 267 unmodified lines
1792 },1906 },
1793};1907};
1794 1908
1909static int skl_tplg_fill_pipe_cfg(struct device *dev,
1910 struct skl_pipe *pipe, u32 tkn,
1911 u32 tkn_val, int conf_idx, int dir)
1912{
1913 struct skl_pipe_fmt *fmt;
1914 struct skl_path_config *config;
1915
1916 switch (dir) {
1917 case SKL_DIR_IN:
1918 fmt = &pipe->configs[conf_idx].in_fmt;
1919 break;
1920
1921 case SKL_DIR_OUT:
1922 fmt = &pipe->configs[conf_idx].out_fmt;
1923 break;
1924
1925 default:
1926 dev_err(dev, "Invalid direction: %d\n", dir);
1927 return -EINVAL;
1928 }
1929
1930 config = &pipe->configs[conf_idx];
1931
1932 switch (tkn) {
1933 case SKL_TKN_U32_CFG_FREQ:
1934 fmt->freq = tkn_val;
1935 break;
1936
1937 case SKL_TKN_U8_CFG_CHAN:
1938 fmt->channels = tkn_val;
1939 break;
1940
1941 case SKL_TKN_U8_CFG_BPS:
1942 fmt->bps = tkn_val;
1943 break;
1944
1945 case SKL_TKN_U32_PATH_MEM_PGS:
1946 config->mem_pages = tkn_val;
1947 break;
1948
1949 default:
1950 dev_err(dev, "Invalid token config: %d\n", tkn);
1951 return -EINVAL;
1952 }
1953
1954 return 0;
1955}
1956
1795static int skl_tplg_fill_pipe_tkn(struct device *dev,1957static int skl_tplg_fill_pipe_tkn(struct device *dev,
1796 struct skl_pipe *pipe, u32 tkn,1958 struct skl_pipe *pipe, u32 tkn,
1797 u32 tkn_val)1959 u32 tkn_val)
@@ -1814,6 +1976,14 @@ static int skl_tplg_fill_pipe_tkn(struct device *dev, · 16 unmodified lines
1814 pipe->lp_mode = tkn_val;1976 pipe->lp_mode = tkn_val;
1815 break;1977 break;
1816 1978
1979 case SKL_TKN_U32_PIPE_DIRECTION:
1980 pipe->direction = tkn_val;
1981 break;
1982
1983 case SKL_TKN_U32_NUM_CONFIGS:
1984 pipe->nr_cfgs = tkn_val;
1985 break;
1986
1817 default:1987 default:
1818 dev_err(dev, "Token not handled %d\n", tkn);1988 dev_err(dev, "Token not handled %d\n", tkn);
1819 return -EINVAL;1989 return -EINVAL;
@@ -1930,27 +2100,9 @@ static int skl_tplg_fill_pins_info(struct device *dev, · 110 unmodified lines
1930 * on the direction2100 * on the direction
1931 */2101 */
1932static int skl_tplg_fill_fmt(struct device *dev,2102static int skl_tplg_fill_fmt(struct device *dev,
1933 struct skl_module_cfg *mconfig, u32 tkn,2103 struct skl_module_fmt *dst_fmt,
1934 u32 value, u32 dir, u32 pin_count)2104 u32 tkn, u32 value)
1935{2105{
1936 struct skl_module_fmt *dst_fmt;
1937
1938 switch (dir) {
1939 case SKL_DIR_IN:
1940 dst_fmt = mconfig->in_fmt;
1941 dst_fmt += pin_count;
1942 break;
1943
1944 case SKL_DIR_OUT:
1945 dst_fmt = mconfig->out_fmt;
1946 dst_fmt += pin_count;
1947 break;
1948
1949 default:
1950 dev_err(dev, "Invalid direction value\n");
1951 return -EINVAL;
1952 }
1953
1954 switch (tkn) {2106 switch (tkn) {
1955 case SKL_TKN_U32_FMT_CH:2107 case SKL_TKN_U32_FMT_CH:
1956 dst_fmt->channels = value;2108 dst_fmt->channels = value;
@@ -1992,6 +2144,32 @@ static int skl_tplg_fill_fmt(struct device *dev, · 35 unmodified lines
1992 return 0;2144 return 0;
1993}2145}
1994 2146
2147static int skl_tplg_widget_fill_fmt(struct device *dev,
2148 struct skl_module_iface *fmt,
2149 u32 tkn, u32 val, u32 dir, int fmt_idx)
2150{
2151 struct skl_module_fmt *dst_fmt;
2152
2153 if (!fmt)
2154 return -EINVAL;
2155
2156 switch (dir) {
2157 case SKL_DIR_IN:
2158 dst_fmt = &fmt->inputs[fmt_idx].fmt;
2159 break;
2160
2161 case SKL_DIR_OUT:
2162 dst_fmt = &fmt->outputs[fmt_idx].fmt;
2163 break;
2164
2165 default:
2166 dev_err(dev, "Invalid direction: %d\n", dir);
2167 return -EINVAL;
2168 }
2169
2170 return skl_tplg_fill_fmt(dev, dst_fmt, tkn, val);
2171}
2172
1995static int skl_tplg_get_uuid(struct device *dev, struct skl_module_cfg *mconfig,2173static int skl_tplg_get_uuid(struct device *dev, struct skl_module_cfg *mconfig,
1996 struct snd_soc_tplg_vendor_uuid_elem *uuid_tkn)2174 struct snd_soc_tplg_vendor_uuid_elem *uuid_tkn)
1997{2175{
@@ -2014,6 +2192,108 @@ static void skl_tplg_fill_pin_dynamic_val( · 16 unmodified lines
2014 mpin[i].is_dynamic = value;2192 mpin[i].is_dynamic = value;
2015}2193}
2016 2194
2195/*
2196 * Resource table in the manifest has pin specific resources
2197 * like pin and pin buffer size
2198 */
2199static int skl_tplg_manifest_pin_res_tkn(struct device *dev,
2200 struct snd_soc_tplg_vendor_value_elem *tkn_elem,
2201 struct skl_module_res *res, int pin_idx, int dir)
2202{
2203 struct skl_module_pin_resources *m_pin;
2204
2205 switch (dir) {
2206 case SKL_DIR_IN:
2207 m_pin = &res->input[pin_idx];
2208 break;
2209
2210 case SKL_DIR_OUT:
2211 m_pin = &res->output[pin_idx];
2212 break;
2213
2214 default:
2215 dev_err(dev, "Invalid pin direction: %d\n", dir);
2216 return -EINVAL;
2217 }
2218
2219 switch (tkn_elem->token) {
2220 case SKL_TKN_MM_U32_RES_PIN_ID:
2221 m_pin->pin_index = tkn_elem->value;
2222 break;
2223
2224 case SKL_TKN_MM_U32_PIN_BUF:
2225 m_pin->buf_size = tkn_elem->value;
2226 break;
2227
2228 default:
2229 dev_err(dev, "Invalid token: %d\n", tkn_elem->token);
2230 return -EINVAL;
2231 }
2232
2233 return 0;
2234}
2235
2236/*
2237 * Fill module specific resources from the manifest's resource
2238 * table like CPS, DMA size, mem_pages.
2239 */
2240static int skl_tplg_fill_res_tkn(struct device *dev,
2241 struct snd_soc_tplg_vendor_value_elem *tkn_elem,
2242 struct skl_module_res *res,
2243 int pin_idx, int dir)
2244{
2245 int ret, tkn_count = 0;
2246
2247 if (!res)
2248 return -EINVAL;
2249
2250 switch (tkn_elem->token) {
2251 case SKL_TKN_MM_U32_CPS:
2252 res->cps = tkn_elem->value;
2253 break;
2254
2255 case SKL_TKN_MM_U32_DMA_SIZE:
2256 res->dma_buffer_size = tkn_elem->value;
2257 break;
2258
2259 case SKL_TKN_MM_U32_CPC:
2260 res->cpc = tkn_elem->value;
2261 break;
2262
2263 case SKL_TKN_U32_MEM_PAGES:
2264 res->is_pages = tkn_elem->value;
2265 break;
2266
2267 case SKL_TKN_U32_OBS:
2268 res->obs = tkn_elem->value;
2269 break;
2270
2271 case SKL_TKN_U32_IBS:
2272 res->ibs = tkn_elem->value;
2273 break;
2274
2275 case SKL_TKN_U32_MAX_MCPS:
2276 res->cps = tkn_elem->value;
2277 break;
2278
2279 case SKL_TKN_MM_U32_RES_PIN_ID:
2280 case SKL_TKN_MM_U32_PIN_BUF:
2281 ret = skl_tplg_manifest_pin_res_tkn(dev, tkn_elem, res,
2282 pin_idx, dir);
2283 if (ret < 0)
2284 return ret;
2285 break;
2286
2287 default:
2288 dev_err(dev, "Not a res type token: %d", tkn_elem->token);
2289 return -EINVAL;
2290
2291 }
2292 tkn_count++;
2293
2294 return tkn_count;
2295}
2296
2017/*2297/*
2018 * Parse tokens to fill up the module private data2298 * Parse tokens to fill up the module private data
2019 */2299 */
@@ -2024,49 +2304,54 @@ static int skl_tplg_get_token(struct device *dev, · 4 unmodified lines
2024 int tkn_count = 0;2304 int tkn_count = 0;
2025 int ret;2305 int ret;
2026 static int is_pipe_exists;2306 static int is_pipe_exists;
2027 static int pin_index, dir;2307 static int pin_index, dir, conf_idx;
2308 struct skl_module_iface *iface = NULL;
2309 struct skl_module_res *res = NULL;
2310 int res_idx = mconfig->res_idx;
2311 int fmt_idx = mconfig->fmt_idx;
2312
2313 /*
2314 * If the manifest structure contains no modules, fill all
2315 * the module data to 0th index.
2316 * res_idx and fmt_idx are default set to 0.
2317 */
2318 if (skl->nr_modules == 0) {
2319 res = &mconfig->module->resources[res_idx];
2320 iface = &mconfig->module->formats[fmt_idx];
2321 }
2028 2322
2029 if (tkn_elem->token > SKL_TKN_MAX)2323 if (tkn_elem->token > SKL_TKN_MAX)
2030 return -EINVAL;2324 return -EINVAL;
2031 2325
2032 switch (tkn_elem->token) {2326 switch (tkn_elem->token) {
2033 case SKL_TKN_U8_IN_QUEUE_COUNT:2327 case SKL_TKN_U8_IN_QUEUE_COUNT:
2034 mconfig->max_in_queue = tkn_elem->value;2328 mconfig->module->max_input_pins = tkn_elem->value;
2035 mconfig->m_in_pin = devm_kzalloc(dev, mconfig->max_in_queue *
2036 sizeof(*mconfig->m_in_pin),
2037 GFP_KERNEL);
2038 if (!mconfig->m_in_pin)
2039 return -ENOMEM;
2040
2041 break;2329 break;
2042 2330
2043 case SKL_TKN_U8_OUT_QUEUE_COUNT:2331 case SKL_TKN_U8_OUT_QUEUE_COUNT:
2044 mconfig->max_out_queue = tkn_elem->value;2332 mconfig->module->max_output_pins = tkn_elem->value;
2045 mconfig->m_out_pin = devm_kzalloc(dev, mconfig->max_out_queue *
2046 sizeof(*mconfig->m_out_pin),
2047 GFP_KERNEL);
2048
2049 if (!mconfig->m_out_pin)
2050 return -ENOMEM;
2051
2052 break;2333 break;
2053 2334
2054 case SKL_TKN_U8_DYN_IN_PIN:2335 case SKL_TKN_U8_DYN_IN_PIN:
2336 if (!mconfig->m_in_pin)
2337 mconfig->m_in_pin = devm_kzalloc(dev, MAX_IN_QUEUE *
2338 sizeof(*mconfig->m_in_pin), GFP_KERNEL);
2055 if (!mconfig->m_in_pin)2339 if (!mconfig->m_in_pin)
2056 return -ENOMEM;2340 return -ENOMEM;
2057 2341
2058 skl_tplg_fill_pin_dynamic_val(mconfig->m_in_pin,2342 skl_tplg_fill_pin_dynamic_val(mconfig->m_in_pin, MAX_IN_QUEUE,
2059 mconfig->max_in_queue, tkn_elem->value);2343 tkn_elem->value);
2060
2061 break;2344 break;
2062 2345
2063 case SKL_TKN_U8_DYN_OUT_PIN:2346 case SKL_TKN_U8_DYN_OUT_PIN:
2347 if (!mconfig->m_out_pin)
2348 mconfig->m_out_pin = devm_kzalloc(dev, MAX_IN_QUEUE *
2349 sizeof(*mconfig->m_in_pin), GFP_KERNEL);
2064 if (!mconfig->m_out_pin)2350 if (!mconfig->m_out_pin)
2065 return -ENOMEM;2351 return -ENOMEM;
2066 2352
2067 skl_tplg_fill_pin_dynamic_val(mconfig->m_out_pin,2353 skl_tplg_fill_pin_dynamic_val(mconfig->m_out_pin, MAX_OUT_QUEUE,
2068 mconfig->max_out_queue, tkn_elem->value);2354 tkn_elem->value);
2069
2070 break;2355 break;
2071 2356
2072 case SKL_TKN_U8_TIME_SLOT:2357 case SKL_TKN_U8_TIME_SLOT:
@@ -2094,19 +2379,13 @@ static int skl_tplg_get_token(struct device *dev, · 21 unmodified lines
2094 break;2379 break;
2095 2380
2096 case SKL_TKN_U32_MEM_PAGES:2381 case SKL_TKN_U32_MEM_PAGES:
2097 mconfig->mem_pages = tkn_elem->value;
2098 break;
2099
2100 case SKL_TKN_U32_MAX_MCPS:2382 case SKL_TKN_U32_MAX_MCPS:
2101 mconfig->mcps = tkn_elem->value;
2102 break;
2103
2104 case SKL_TKN_U32_OBS:2383 case SKL_TKN_U32_OBS:
2105 mconfig->obs = tkn_elem->value;
2106 break;
2107
2108 case SKL_TKN_U32_IBS:2384 case SKL_TKN_U32_IBS:
2109 mconfig->ibs = tkn_elem->value;2385 ret = skl_tplg_fill_res_tkn(dev, tkn_elem, res, dir, pin_index);
2386 if (ret < 0)
2387 return ret;
2388
2110 break;2389 break;
2111 2390
2112 case SKL_TKN_U32_VBUS_ID:2391 case SKL_TKN_U32_VBUS_ID:
@@ -2139,10 +2418,16 @@ static int skl_tplg_get_token(struct device *dev, · 26 unmodified lines
2139 2418
2140 break;2419 break;
2141 2420
2421 case SKL_TKN_U32_PIPE_CONFIG_ID:
2422 conf_idx = tkn_elem->value;
2423 break;
2424
2142 case SKL_TKN_U32_PIPE_CONN_TYPE:2425 case SKL_TKN_U32_PIPE_CONN_TYPE:
2143 case SKL_TKN_U32_PIPE_PRIORITY:2426 case SKL_TKN_U32_PIPE_PRIORITY:
2144 case SKL_TKN_U32_PIPE_MEM_PGS:2427 case SKL_TKN_U32_PIPE_MEM_PGS:
2145 case SKL_TKN_U32_PMODE:2428 case SKL_TKN_U32_PMODE:
2429 case SKL_TKN_U32_PIPE_DIRECTION:
2430 case SKL_TKN_U32_NUM_CONFIGS:
2146 if (is_pipe_exists) {2431 if (is_pipe_exists) {
2147 ret = skl_tplg_fill_pipe_tkn(dev, mconfig->pipe,2432 ret = skl_tplg_fill_pipe_tkn(dev, mconfig->pipe,
2148 tkn_elem->token, tkn_elem->value);2433 tkn_elem->token, tkn_elem->value);
@@ -2152,6 +2437,27 @@ static int skl_tplg_get_token(struct device *dev, · 3 unmodified lines
2152 2437
2153 break;2438 break;
2154 2439
2440 case SKL_TKN_U32_PATH_MEM_PGS:
2441 case SKL_TKN_U32_CFG_FREQ:
2442 case SKL_TKN_U8_CFG_CHAN:
2443 case SKL_TKN_U8_CFG_BPS:
2444 if (mconfig->pipe->nr_cfgs) {
2445 ret = skl_tplg_fill_pipe_cfg(dev, mconfig->pipe,
2446 tkn_elem->token, tkn_elem->value,
2447 conf_idx, dir);
2448 if (ret < 0)
2449 return ret;
2450 }
2451 break;
2452
2453 case SKL_TKN_CFG_MOD_RES_ID:
2454 mconfig->mod_cfg[conf_idx].res_idx = tkn_elem->value;
2455 break;
2456
2457 case SKL_TKN_CFG_MOD_FMT_ID:
2458 mconfig->mod_cfg[conf_idx].fmt_idx = tkn_elem->value;
2459 break;
2460
2155 /*2461 /*
2156 * SKL_TKN_U32_DIR_PIN_COUNT token has the value for both2462 * SKL_TKN_U32_DIR_PIN_COUNT token has the value for both
2157 * direction and the pin count. The first four bits represent2463 * direction and the pin count. The first four bits represent
@@ -2172,7 +2478,7 @@ static int skl_tplg_get_token(struct device *dev, · 14 unmodified lines
2172 case SKL_TKN_U32_FMT_INTERLEAVE:2478 case SKL_TKN_U32_FMT_INTERLEAVE:
2173 case SKL_TKN_U32_FMT_SAMPLE_TYPE:2479 case SKL_TKN_U32_FMT_SAMPLE_TYPE:
2174 case SKL_TKN_U32_FMT_CH_MAP:2480 case SKL_TKN_U32_FMT_CH_MAP:
2175 ret = skl_tplg_fill_fmt(dev, mconfig, tkn_elem->token,2481 ret = skl_tplg_widget_fill_fmt(dev, iface, tkn_elem->token,
2176 tkn_elem->value, dir, pin_index);2482 tkn_elem->value, dir, pin_index);
2177 2483
2178 if (ret < 0)2484 if (ret < 0)
@@ -2397,11 +2703,11 @@ static void skl_clear_pin_config(struct snd_soc_platform *platform, · 218 unmodified lines
2397 strlen(platform->component.name))) {2703 strlen(platform->component.name))) {
2398 mconfig = w->priv;2704 mconfig = w->priv;
2399 pipe = mconfig->pipe;2705 pipe = mconfig->pipe;
2400 for (i = 0; i < mconfig->max_in_queue; i++) {2706 for (i = 0; i < mconfig->module->max_input_pins; i++) {
2401 mconfig->m_in_pin[i].in_use = false;2707 mconfig->m_in_pin[i].in_use = false;
2402 mconfig->m_in_pin[i].pin_state = SKL_PIN_UNBIND;2708 mconfig->m_in_pin[i].pin_state = SKL_PIN_UNBIND;
2403 }2709 }
2404 for (i = 0; i < mconfig->max_out_queue; i++) {2710 for (i = 0; i < mconfig->module->max_output_pins; i++) {
2405 mconfig->m_out_pin[i].in_use = false;2711 mconfig->m_out_pin[i].in_use = false;
2406 mconfig->m_out_pin[i].pin_state = SKL_PIN_UNBIND;2712 mconfig->m_out_pin[i].pin_state = SKL_PIN_UNBIND;
2407 }2713 }
@@ -2460,6 +2766,13 @@ static int skl_tplg_widget_load(struct snd_soc_component *cmpnt, · 52 unmodified lines
2460 if (!mconfig)2766 if (!mconfig)
2461 return -ENOMEM;2767 return -ENOMEM;
2462 2768
2769 if (skl->nr_modules == 0) {
2770 mconfig->module = devm_kzalloc(bus->dev,
2771 sizeof(*mconfig->module), GFP_KERNEL);
2772 if (!mconfig->module)
2773 return -ENOMEM;
2774 }
2775
2463 w->priv = mconfig;2776 w->priv = mconfig;
2464 2777
2465 /*2778 /*
@@ -2602,13 +2915,13 @@ static int skl_tplg_fill_str_mfest_tkn(struct device *dev, · 136 unmodified lines
2602 str_elem->string,2915 str_elem->string,
2603 ARRAY_SIZE(skl->skl_sst->lib_info[ref_count].name));2916 ARRAY_SIZE(skl->skl_sst->lib_info[ref_count].name));
2604 ref_count++;2917 ref_count++;
2605 tkn_count++;
2606 break;2918 break;
2607 2919
2608 default:2920 default:
2609 dev_err(dev, "Not a string token %d\n", str_elem->token);2921 dev_err(dev, "Not a string token %d\n", str_elem->token);
2610 break;2922 break;
2611 }2923 }
2924 tkn_count++;
2612 2925
2613 return tkn_count;2926 return tkn_count;
2614}2927}
@@ -2634,26 +2947,236 @@ static int skl_tplg_get_str_tkn(struct device *dev, · 19 unmodified lines
2634 return tkn_count;2947 return tkn_count;
2635}2948}
2636 2949
2950static int skl_tplg_manifest_fill_fmt(struct device *dev,
2951 struct skl_module_iface *fmt,
2952 struct snd_soc_tplg_vendor_value_elem *tkn_elem,
2953 u32 dir, int fmt_idx)
2954{
2955 struct skl_module_pin_fmt *dst_fmt;
2956 struct skl_module_fmt *mod_fmt;
2957 int ret;
2958
2959 if (!fmt)
2960 return -EINVAL;
2961
2962 switch (dir) {
2963 case SKL_DIR_IN:
2964 dst_fmt = &fmt->inputs[fmt_idx];
2965 break;
2966
2967 case SKL_DIR_OUT:
2968 dst_fmt = &fmt->outputs[fmt_idx];
2969 break;
2970
2971 default:
2972 dev_err(dev, "Invalid direction: %d\n", dir);
2973 return -EINVAL;
2974 }
2975
2976 mod_fmt = &dst_fmt->fmt;
2977
2978 switch (tkn_elem->token) {
2979 case SKL_TKN_MM_U32_INTF_PIN_ID:
2980 dst_fmt->id = tkn_elem->value;
2981 break;
2982
2983 default:
2984 ret = skl_tplg_fill_fmt(dev, mod_fmt, tkn_elem->token,
2985 tkn_elem->value);
2986 if (ret < 0)
2987 return ret;
2988 break;
2989 }
2990
2991 return 0;
2992}
2993
2994static int skl_tplg_fill_mod_info(struct device *dev,
2995 struct snd_soc_tplg_vendor_value_elem *tkn_elem,
2996 struct skl_module *mod)
2997{
2998
2999 if (!mod)
3000 return -EINVAL;
3001
3002 switch (tkn_elem->token) {
3003 case SKL_TKN_U8_IN_PIN_TYPE:
3004 mod->input_pin_type = tkn_elem->value;
3005 break;
3006
3007 case SKL_TKN_U8_OUT_PIN_TYPE:
3008 mod->output_pin_type = tkn_elem->value;
3009 break;
3010
3011 case SKL_TKN_U8_IN_QUEUE_COUNT:
3012 mod->max_input_pins = tkn_elem->value;
3013 break;
3014
3015 case SKL_TKN_U8_OUT_QUEUE_COUNT:
3016 mod->max_output_pins = tkn_elem->value;
3017 break;
3018
3019 case SKL_TKN_MM_U8_NUM_RES:
3020 mod->nr_resources = tkn_elem->value;
3021 break;
3022
3023 case SKL_TKN_MM_U8_NUM_INTF:
3024 mod->nr_interfaces = tkn_elem->value;
3025 break;
3026
3027 default:
3028 dev_err(dev, "Invalid mod info token %d", tkn_elem->token);
3029 return -EINVAL;
3030 }
3031
3032 return 0;
3033}
3034
3035
2637static int skl_tplg_get_int_tkn(struct device *dev,3036static int skl_tplg_get_int_tkn(struct device *dev,
2638 struct snd_soc_tplg_vendor_value_elem *tkn_elem,3037 struct snd_soc_tplg_vendor_value_elem *tkn_elem,
2639 struct skl *skl)3038 struct skl *skl)
2640{3039{
2641 int tkn_count = 0;3040 int tkn_count = 0, ret;
3041 static int mod_idx, res_val_idx, intf_val_idx, dir, pin_idx;
3042 struct skl_module_res *res = NULL;
3043 struct skl_module_iface *fmt = NULL;
3044 struct skl_module *mod = NULL;
3045 int i;
3046
3047 if (skl->modules) {
3048 mod = skl->modules[mod_idx];
3049 res = &mod->resources[res_val_idx];
3050 fmt = &mod->formats[intf_val_idx];
3051 }
2642 3052
2643 switch (tkn_elem->token) {3053 switch (tkn_elem->token) {
2644 case SKL_TKN_U32_LIB_COUNT:3054 case SKL_TKN_U32_LIB_COUNT:
2645 skl->skl_sst->lib_count = tkn_elem->value;3055 skl->skl_sst->lib_count = tkn_elem->value;
2646 tkn_count++;3056 break;
3057
3058 case SKL_TKN_U8_NUM_MOD:
3059 skl->nr_modules = tkn_elem->value;
3060 skl->modules = devm_kcalloc(dev, skl->nr_modules,
3061 sizeof(*skl->modules), GFP_KERNEL);
3062 if (!skl->modules)
3063 return -ENOMEM;
3064
3065 for (i = 0; i < skl->nr_modules; i++) {
3066 skl->modules[i] = devm_kzalloc(dev,
3067 sizeof(struct skl_module), GFP_KERNEL);
3068 if (!skl->modules[i])
3069 return -ENOMEM;
3070 }
3071 break;
3072
3073 case SKL_TKN_MM_U8_MOD_IDX:
3074 mod_idx = tkn_elem->value;
3075 break;
3076
3077 case SKL_TKN_U8_IN_PIN_TYPE:
3078 case SKL_TKN_U8_OUT_PIN_TYPE:
3079 case SKL_TKN_U8_IN_QUEUE_COUNT:
3080 case SKL_TKN_U8_OUT_QUEUE_COUNT:
3081 case SKL_TKN_MM_U8_NUM_RES:
3082 case SKL_TKN_MM_U8_NUM_INTF:
3083 ret = skl_tplg_fill_mod_info(dev, tkn_elem, mod);
3084 if (ret < 0)
3085 return ret;
3086 break;
3087
3088 case SKL_TKN_U32_DIR_PIN_COUNT:
3089 dir = tkn_elem->value & SKL_IN_DIR_BIT_MASK;
3090 pin_idx = (tkn_elem->value & SKL_PIN_COUNT_MASK) >> 4;
3091 break;
3092
3093 case SKL_TKN_MM_U32_RES_ID:
3094 if (!res)
3095 return -EINVAL;
3096
3097 res->id = tkn_elem->value;
3098 res_val_idx = tkn_elem->value;
3099 break;
3100
3101 case SKL_TKN_MM_U32_FMT_ID:
3102 if (!fmt)
3103 return -EINVAL;
3104
3105 fmt->fmt_idx = tkn_elem->value;
3106 intf_val_idx = tkn_elem->value;
3107 break;
3108
3109 case SKL_TKN_MM_U32_CPS:
3110 case SKL_TKN_MM_U32_DMA_SIZE:
3111 case SKL_TKN_MM_U32_CPC:
3112 case SKL_TKN_U32_MEM_PAGES:
3113 case SKL_TKN_U32_OBS:
3114 case SKL_TKN_U32_IBS:
3115 case SKL_TKN_MM_U32_RES_PIN_ID:
3116 case SKL_TKN_MM_U32_PIN_BUF:
3117 ret = skl_tplg_fill_res_tkn(dev, tkn_elem, res, pin_idx, dir);
3118 if (ret < 0)
3119 return ret;
3120
3121 break;
3122
3123 case SKL_TKN_MM_U32_NUM_IN_FMT:
3124 if (!fmt)
3125 return -EINVAL;
3126
3127 res->nr_input_pins = tkn_elem->value;
3128 break;
3129
3130 case SKL_TKN_MM_U32_NUM_OUT_FMT:
3131 if (!fmt)
3132 return -EINVAL;
3133
3134 res->nr_output_pins = tkn_elem->value;
3135 break;
3136
3137 case SKL_TKN_U32_FMT_CH:
3138 case SKL_TKN_U32_FMT_FREQ:
3139 case SKL_TKN_U32_FMT_BIT_DEPTH:
3140 case SKL_TKN_U32_FMT_SAMPLE_SIZE:
3141 case SKL_TKN_U32_FMT_CH_CONFIG:
3142 case SKL_TKN_U32_FMT_INTERLEAVE:
3143 case SKL_TKN_U32_FMT_SAMPLE_TYPE:
3144 case SKL_TKN_U32_FMT_CH_MAP:
3145 case SKL_TKN_MM_U32_INTF_PIN_ID:
3146 ret = skl_tplg_manifest_fill_fmt(dev, fmt, tkn_elem,
3147 dir, pin_idx);
3148 if (ret < 0)
3149 return ret;
2647 break;3150 break;
2648 3151
2649 default:3152 default:
2650 dev_err(dev, "Not a manifest token %d\n", tkn_elem->token);3153 dev_err(dev, "Not a manifest token %d\n", tkn_elem->token);
2651 return -EINVAL;3154 return -EINVAL;
2652 }3155 }
3156 tkn_count++;
2653 3157
2654 return tkn_count;3158 return tkn_count;
2655}3159}
2656 3160
3161static int skl_tplg_get_manifest_uuid(struct device *dev,
3162 struct skl *skl,
3163 struct snd_soc_tplg_vendor_uuid_elem *uuid_tkn)
3164{
3165 static int ref_count;
3166 struct skl_module *mod;
3167
3168 if (uuid_tkn->token == SKL_TKN_UUID) {
3169 mod = skl->modules[ref_count];
3170 memcpy(&mod->uuid, &uuid_tkn->uuid, sizeof(uuid_tkn->uuid));
3171 ref_count++;
3172 } else {
3173 dev_err(dev, "Not an UUID token tkn %d\n", uuid_tkn->token);
3174 return -EINVAL;
3175 }
3176
3177 return 0;
3178}
3179
2657/*3180/*
2658 * Fill the manifest structure by parsing the tokens based on the3181 * Fill the manifest structure by parsing the tokens based on the
2659 * type.3182 * type.
@@ -2686,7 +3209,11 @@ static int skl_tplg_get_manifest_tkn(struct device *dev, · 26 unmodified lines
2686 continue;3209 continue;
2687 3210
2688 case SND_SOC_TPLG_TUPLE_TYPE_UUID:3211 case SND_SOC_TPLG_TUPLE_TYPE_UUID:
2689 dev_warn(dev, "no uuid tokens for skl tplf manifest\n");3212 ret = skl_tplg_get_manifest_uuid(dev, skl, array->uuid);
3213 if (ret < 0)
3214 return ret;
3215
3216 tuple_size += sizeof(*array->uuid);
2690 continue;3217 continue;
2691 3218
2692 default:3219 default:
@@ -2703,14 +3230,12 @@ static int skl_tplg_get_manifest_tkn(struct device *dev, · 10 unmodified lines
2703 3230
2704 tkn_count = tkn_count + ret;3231 tkn_count = tkn_count + ret;
2705 tkn_elem++;3232 tkn_elem++;
2706 tuple_size += tkn_count *
2707 sizeof(struct snd_soc_tplg_vendor_value_elem);
2708 break;
2709 }3233 }
3234 tuple_size += (tkn_count * sizeof(*tkn_elem));
2710 tkn_count = 0;3235 tkn_count = 0;
2711 }3236 }
2712 3237
2713 return 0;3238 return off;
2714}3239}
2715 3240
2716/*3241/*
@@ -2733,11 +3258,10 @@ static int skl_tplg_get_manifest_data(struct snd_soc_tplg_manifest *manifest, · 16 unmodified lines
2733 num_blocks = ret;3258 num_blocks = ret;
2734 3259
2735 off += array->size;3260 off += array->size;
2736 array = (struct snd_soc_tplg_vendor_array *)
2737 (manifest->priv.data + off);
2738
2739 /* Read the BLOCK_TYPE and BLOCK_SIZE descriptor */3261 /* Read the BLOCK_TYPE and BLOCK_SIZE descriptor */
2740 while (num_blocks > 0) {3262 while (num_blocks > 0) {
3263 array = (struct snd_soc_tplg_vendor_array *)
3264 (manifest->priv.data + off);
2741 ret = skl_tplg_get_desc_blocks(dev, array);3265 ret = skl_tplg_get_desc_blocks(dev, array);
2742 3266
2743 if (ret < 0)3267 if (ret < 0)
@@ -2771,6 +3295,7 @@ static int skl_tplg_get_manifest_data(struct snd_soc_tplg_manifest *manifest, · 27 unmodified lines
2771 } else {3295 } else {
2772 return -EINVAL;3296 return -EINVAL;
2773 }3297 }
3298 off += ret;
2774 }3299 }
2775 3300
2776 return 0;3301 return 0;
sound/soc/intel/skylake/skl-topology.h+83−0
@@ -44,6 +44,13 @@ · 43 unmodified lines
44#define SKL_DEFAULT_MIC_SEL_GAIN 0x3FF44#define SKL_DEFAULT_MIC_SEL_GAIN 0x3FF
45#define SKL_MIC_SEL_SWITCH 0x345#define SKL_MIC_SEL_SWITCH 0x3
46 46
47#define SKL_OUTPUT_PIN 0
48#define SKL_INPUT_PIN 1
49#define SKL_MAX_PATH_CONFIGS 8
50#define SKL_MAX_MODULES_IN_PIPE 8
51#define SKL_MAX_MODULE_FORMATS 32
52#define SKL_MAX_MODULE_RESOURCES 32
53
47enum skl_channel_index {54enum skl_channel_index {
48 SKL_CHANNEL_LEFT = 0,55 SKL_CHANNEL_LEFT = 0,
49 SKL_CHANNEL_RIGHT = 1,56 SKL_CHANNEL_RIGHT = 1,
@@ -131,6 +138,11 @@ struct skl_cpr_cfg { · 81 unmodified lines
131 struct skl_cpr_gtw_cfg gtw_cfg;138 struct skl_cpr_gtw_cfg gtw_cfg;
132} __packed;139} __packed;
133 140
141struct skl_cpr_pin_fmt {
142 u32 sink_id;
143 struct skl_audio_data_format src_fmt;
144 struct skl_audio_data_format dst_fmt;
145} __packed;
134 146
135struct skl_src_module_cfg {147struct skl_src_module_cfg {
136 struct skl_base_cfg base_cfg;148 struct skl_base_cfg base_cfg;
@@ -214,6 +226,7 @@ struct skl_kpb_params { · 77 unmodified lines
214};226};
215 227
216struct skl_module_inst_id {228struct skl_module_inst_id {
229 uuid_le mod_uuid;
217 int module_id;230 int module_id;
218 u32 instance_id;231 u32 instance_id;
219 int pvt_id;232 int pvt_id;
@@ -266,6 +279,23 @@ struct skl_pipe_params { · 46 unmodified lines
266 unsigned int link_bps;279 unsigned int link_bps;
267};280};
268 281
282struct skl_pipe_fmt {
283 u32 freq;
284 u8 channels;
285 u8 bps;
286};
287
288struct skl_pipe_mcfg {
289 u8 res_idx;
290 u8 fmt_idx;
291};
292
293struct skl_path_config {
294 u8 mem_pages;
295 struct skl_pipe_fmt in_fmt;
296 struct skl_pipe_fmt out_fmt;
297};
298
269struct skl_pipe {299struct skl_pipe {
270 u8 ppl_id;300 u8 ppl_id;
271 u8 pipe_priority;301 u8 pipe_priority;
@@ -274,6 +304,10 @@ struct skl_pipe { · 2 unmodified lines
274 u8 lp_mode;304 u8 lp_mode;
275 struct skl_pipe_params *p_params;305 struct skl_pipe_params *p_params;
276 enum skl_pipe_state state;306 enum skl_pipe_state state;
307 u8 direction;
308 u8 cur_config_idx;
309 u8 nr_cfgs;
310 struct skl_path_config configs[SKL_MAX_PATH_CONFIGS];
277 struct list_head w_list;311 struct list_head w_list;
278 bool passthru;312 bool passthru;
279};313};
@@ -292,9 +326,57 @@ enum d0i3_capability { · 12 unmodified lines
292 SKL_D0I3_NON_STREAMING = 2,326 SKL_D0I3_NON_STREAMING = 2,
293};327};
294 328
329struct skl_module_pin_fmt {
330 u8 id;
331 struct skl_module_fmt fmt;
332};
333
334struct skl_module_iface {
335 u8 fmt_idx;
336 u8 nr_in_fmt;
337 u8 nr_out_fmt;
338 struct skl_module_pin_fmt inputs[MAX_IN_QUEUE];
339 struct skl_module_pin_fmt outputs[MAX_OUT_QUEUE];
340};
341
342struct skl_module_pin_resources {
343 u8 pin_index;
344 u32 buf_size;
345};
346
347struct skl_module_res {
348 u8 id;
349 u32 is_pages;
350 u32 cps;
351 u32 ibs;
352 u32 obs;
353 u32 dma_buffer_size;
354 u32 cpc;
355 u8 nr_input_pins;
356 u8 nr_output_pins;
357 struct skl_module_pin_resources input[MAX_IN_QUEUE];
358 struct skl_module_pin_resources output[MAX_OUT_QUEUE];
359};
360
361struct skl_module {
362 uuid_le uuid;
363 u8 loadable;
364 u8 input_pin_type;
365 u8 output_pin_type;
366 u8 max_input_pins;
367 u8 max_output_pins;
368 u8 nr_resources;
369 u8 nr_interfaces;
370 struct skl_module_res resources[SKL_MAX_MODULE_RESOURCES];
371 struct skl_module_iface formats[SKL_MAX_MODULE_FORMATS];
372};
373
295struct skl_module_cfg {374struct skl_module_cfg {
296 u8 guid[16];375 u8 guid[16];
297 struct skl_module_inst_id id;376 struct skl_module_inst_id id;
377 struct skl_module *module;
378 int res_idx;
379 int fmt_idx;
298 u8 domain;380 u8 domain;
299 bool homogenous_inputs;381 bool homogenous_inputs;
300 bool homogenous_outputs;382 bool homogenous_outputs;
@@ -329,6 +411,7 @@ struct skl_module_cfg { · 28 unmodified lines
329 enum skl_module_state m_state;411 enum skl_module_state m_state;
330 struct skl_pipe *pipe;412 struct skl_pipe *pipe;
331 struct skl_specific_cfg formats_config;413 struct skl_specific_cfg formats_config;
414 struct skl_pipe_mcfg mod_cfg[SKL_MAX_MODULES_IN_PIPE];
332};415};
333 416
334struct skl_algo_data {417struct skl_algo_data {
sound/soc/intel/skylake/skl.c+21−7
@@ -415,7 +415,7 @@ static int skl_free(struct hdac_ext_bus *ebus) · 414 unmodified lines
415 snd_hdac_ext_stop_streams(ebus);415 snd_hdac_ext_stop_streams(ebus);
416 416
417 if (bus->irq >= 0)417 if (bus->irq >= 0)
418 free_irq(bus->irq, (void *)bus);418 free_irq(bus->irq, (void *)ebus);
419 snd_hdac_bus_free_stream_pages(bus);419 snd_hdac_bus_free_stream_pages(bus);
420 snd_hdac_stream_free_all(ebus);420 snd_hdac_stream_free_all(ebus);
421 snd_hdac_link_free_all(ebus);421 snd_hdac_link_free_all(ebus);
@@ -528,7 +528,7 @@ static int probe_codec(struct hdac_ext_bus *ebus, int addr) · 106 unmodified lines
528}528}
529 529
530/* Codec initialization */530/* Codec initialization */
531static int skl_codec_create(struct hdac_ext_bus *ebus)531static void skl_codec_create(struct hdac_ext_bus *ebus)
532{532{
533 struct hdac_bus *bus = ebus_to_hbus(ebus);533 struct hdac_bus *bus = ebus_to_hbus(ebus);
534 int c, max_slots;534 int c, max_slots;
@@ -559,8 +559,6 @@ static int skl_codec_create(struct hdac_ext_bus *ebus) · 24 unmodified lines
559 }559 }
560 }560 }
561 }561 }
562
563 return 0;
564}562}
565 563
566static const struct hdac_bus_ops bus_core_ops = {564static const struct hdac_bus_ops bus_core_ops = {
@@ -612,9 +610,7 @@ static void skl_probe_work(struct work_struct *work) · 45 unmodified lines
612 dev_info(bus->dev, "no hda codecs found!\n");610 dev_info(bus->dev, "no hda codecs found!\n");
613 611
614 /* create codec instances */612 /* create codec instances */
615 err = skl_codec_create(ebus);613 skl_codec_create(ebus);
616 if (err < 0)
617 goto out_err;
618 614
619 if (IS_ENABLED(CONFIG_SND_SOC_HDAC_HDMI)) {615 if (IS_ENABLED(CONFIG_SND_SOC_HDAC_HDMI)) {
620 err = snd_hdac_display_power(bus, false);616 err = snd_hdac_display_power(bus, false);
@@ -702,6 +698,8 @@ static int skl_first_init(struct hdac_ext_bus *ebus) · 81 unmodified lines
702 return -ENXIO;698 return -ENXIO;
703 }699 }
704 700
701 skl_init_chip(bus, true);
702
705 snd_hdac_bus_parse_capabilities(bus);703 snd_hdac_bus_parse_capabilities(bus);
706 704
707 if (skl_acquire_irq(ebus, 0) < 0)705 if (skl_acquire_irq(ebus, 0) < 0)
@@ -982,6 +980,11 @@ static struct sst_acpi_mach sst_kbl_devdata[] = { · 274 unmodified lines
982 .quirk_data = &kbl_poppy_codecs,980 .quirk_data = &kbl_poppy_codecs,
983 .pdata = &skl_dmic_data981 .pdata = &skl_dmic_data
984 },982 },
983 {
984 .id = "10EC5663",
985 .drv_name = "kbl_rt5663",
986 .fw_filename = "intel/dsp_fw_kbl.bin",
987 },
985 988
986 {}989 {}
987};990};
@@ -995,6 +998,14 @@ static struct sst_acpi_mach sst_glk_devdata[] = { · 7 unmodified lines
995 {}998 {}
996};999};
997 1000
1001static const struct sst_acpi_mach sst_cnl_devdata[] = {
1002 {
1003 .id = "INT34C2",
1004 .drv_name = "cnl_rt274",
1005 .fw_filename = "intel/dsp_fw_cnl.bin",
1006 },
1007};
1008
998/* PCI IDs */1009/* PCI IDs */
999static const struct pci_device_id skl_ids[] = {1010static const struct pci_device_id skl_ids[] = {
1000 /* Sunrise Point-LP */1011 /* Sunrise Point-LP */
@@ -1009,6 +1020,9 @@ static const struct pci_device_id skl_ids[] = { · 8 unmodified lines
1009 /* GLK */1020 /* GLK */
1010 { PCI_DEVICE(0x8086, 0x3198),1021 { PCI_DEVICE(0x8086, 0x3198),
1011 .driver_data = (unsigned long)&sst_glk_devdata},1022 .driver_data = (unsigned long)&sst_glk_devdata},
1023 /* CNL */
1024 { PCI_DEVICE(0x8086, 0x9dc8),
1025 .driver_data = (unsigned long)&sst_cnl_devdata},
1012 { 0, }1026 { 0, }
1013};1027};
1014MODULE_DEVICE_TABLE(pci, skl_ids);1028MODULE_DEVICE_TABLE(pci, skl_ids);
sound/soc/intel/skylake/skl.h+3−0
@@ -71,6 +71,8 @@ struct skl { · 70 unmodified lines
71 struct work_struct probe_work;71 struct work_struct probe_work;
72 72
73 struct skl_debug *debugfs;73 struct skl_debug *debugfs;
74 u8 nr_modules;
75 struct skl_module **modules;
74};76};
75 77
76#define skl_to_ebus(s) (&(s)->ebus)78#define skl_to_ebus(s) (&(s)->ebus)
@@ -90,6 +92,7 @@ struct skl_machine_pdata { · 13 unmodified lines
90 92
91struct skl_dsp_ops {93struct skl_dsp_ops {
92 int id;94 int id;
95 unsigned int num_cores;
93 struct skl_dsp_loader_ops (*loader_ops)(void);96 struct skl_dsp_loader_ops (*loader_ops)(void);
94 int (*init)(struct device *dev, void __iomem *mmio_base,97 int (*init)(struct device *dev, void __iomem *mmio_base,
95 int irq, const char *fw_name,98 int irq, const char *fw_name,

Keyboard shortcuts

General

Show keyboard shortcuts
?
Focus the current search
/

Issues and pull requests

Open filters
f

Issues, pull requests and Inbox

Select next item
j↓
Select previous item
k↑
Open selected item
Enter
Dismiss filters or clear selection
Esc

Repository code

Go to file
t