pcm.c 23 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821
  1. // SPDX-License-Identifier: (GPL-2.0-only OR BSD-3-Clause)
  2. //
  3. // This file is provided under a dual BSD/GPLv2 license. When using or
  4. // redistributing this file, you may do so under either license.
  5. //
  6. // Copyright(c) 2018 Intel Corporation. All rights reserved.
  7. //
  8. // Author: Liam Girdwood <liam.r.girdwood@linux.intel.com>
  9. //
  10. // PCM Layer, interface between ALSA and IPC.
  11. //
  12. #include <linux/pm_runtime.h>
  13. #include <sound/pcm_params.h>
  14. #include <sound/sof.h>
  15. #include "sof-priv.h"
  16. #include "sof-audio.h"
  17. #include "ops.h"
  18. #if IS_ENABLED(CONFIG_SND_SOC_SOF_DEBUG_PROBES)
  19. #include "compress.h"
  20. #endif
  21. /* Create DMA buffer page table for DSP */
  22. static int create_page_table(struct snd_soc_component *component,
  23. struct snd_pcm_substream *substream,
  24. unsigned char *dma_area, size_t size)
  25. {
  26. struct snd_soc_pcm_runtime *rtd = asoc_substream_to_rtd(substream);
  27. struct snd_sof_pcm *spcm;
  28. struct snd_dma_buffer *dmab = snd_pcm_get_dma_buf(substream);
  29. int stream = substream->stream;
  30. spcm = snd_sof_find_spcm_dai(component, rtd);
  31. if (!spcm)
  32. return -EINVAL;
  33. return snd_sof_create_page_table(component->dev, dmab,
  34. spcm->stream[stream].page_table.area, size);
  35. }
  36. static int sof_pcm_dsp_params(struct snd_sof_pcm *spcm, struct snd_pcm_substream *substream,
  37. const struct sof_ipc_pcm_params_reply *reply)
  38. {
  39. struct snd_soc_component *scomp = spcm->scomp;
  40. struct snd_sof_dev *sdev = snd_soc_component_get_drvdata(scomp);
  41. /* validate offset */
  42. int ret = snd_sof_ipc_pcm_params(sdev, substream, reply);
  43. if (ret < 0)
  44. dev_err(scomp->dev, "error: got wrong reply for PCM %d\n",
  45. spcm->pcm.pcm_id);
  46. return ret;
  47. }
  48. /*
  49. * sof pcm period elapse work
  50. */
  51. void snd_sof_pcm_period_elapsed_work(struct work_struct *work)
  52. {
  53. struct snd_sof_pcm_stream *sps =
  54. container_of(work, struct snd_sof_pcm_stream,
  55. period_elapsed_work);
  56. snd_pcm_period_elapsed(sps->substream);
  57. }
  58. /*
  59. * sof pcm period elapse, this could be called at irq thread context.
  60. */
  61. void snd_sof_pcm_period_elapsed(struct snd_pcm_substream *substream)
  62. {
  63. struct snd_soc_pcm_runtime *rtd = asoc_substream_to_rtd(substream);
  64. struct snd_soc_component *component =
  65. snd_soc_rtdcom_lookup(rtd, SOF_AUDIO_PCM_DRV_NAME);
  66. struct snd_sof_pcm *spcm;
  67. spcm = snd_sof_find_spcm_dai(component, rtd);
  68. if (!spcm) {
  69. dev_err(component->dev,
  70. "error: period elapsed for unknown stream!\n");
  71. return;
  72. }
  73. /*
  74. * snd_pcm_period_elapsed() can be called in interrupt context
  75. * before IRQ_HANDLED is returned. Inside snd_pcm_period_elapsed(),
  76. * when the PCM is done draining or xrun happened, a STOP IPC will
  77. * then be sent and this IPC will hit IPC timeout.
  78. * To avoid sending IPC before the previous IPC is handled, we
  79. * schedule delayed work here to call the snd_pcm_period_elapsed().
  80. */
  81. schedule_work(&spcm->stream[substream->stream].period_elapsed_work);
  82. }
  83. EXPORT_SYMBOL(snd_sof_pcm_period_elapsed);
  84. static int sof_pcm_dsp_pcm_free(struct snd_pcm_substream *substream,
  85. struct snd_sof_dev *sdev,
  86. struct snd_sof_pcm *spcm)
  87. {
  88. struct sof_ipc_stream stream;
  89. struct sof_ipc_reply reply;
  90. int ret;
  91. stream.hdr.size = sizeof(stream);
  92. stream.hdr.cmd = SOF_IPC_GLB_STREAM_MSG | SOF_IPC_STREAM_PCM_FREE;
  93. stream.comp_id = spcm->stream[substream->stream].comp_id;
  94. /* send IPC to the DSP */
  95. ret = sof_ipc_tx_message(sdev->ipc, stream.hdr.cmd, &stream,
  96. sizeof(stream), &reply, sizeof(reply));
  97. if (!ret)
  98. spcm->prepared[substream->stream] = false;
  99. return ret;
  100. }
  101. static int sof_pcm_hw_params(struct snd_soc_component *component,
  102. struct snd_pcm_substream *substream,
  103. struct snd_pcm_hw_params *params)
  104. {
  105. struct snd_soc_pcm_runtime *rtd = asoc_substream_to_rtd(substream);
  106. struct snd_pcm_runtime *runtime = substream->runtime;
  107. struct snd_sof_dev *sdev = snd_soc_component_get_drvdata(component);
  108. struct snd_sof_pcm *spcm;
  109. struct sof_ipc_pcm_params pcm;
  110. struct sof_ipc_pcm_params_reply ipc_params_reply;
  111. int ret;
  112. /* nothing to do for BE */
  113. if (rtd->dai_link->no_pcm)
  114. return 0;
  115. spcm = snd_sof_find_spcm_dai(component, rtd);
  116. if (!spcm)
  117. return -EINVAL;
  118. /*
  119. * Handle repeated calls to hw_params() without free_pcm() in
  120. * between. At least ALSA OSS emulation depends on this.
  121. */
  122. if (spcm->prepared[substream->stream]) {
  123. ret = sof_pcm_dsp_pcm_free(substream, sdev, spcm);
  124. if (ret < 0)
  125. return ret;
  126. }
  127. dev_dbg(component->dev, "pcm: hw params stream %d dir %d\n",
  128. spcm->pcm.pcm_id, substream->stream);
  129. memset(&pcm, 0, sizeof(pcm));
  130. /* create compressed page table for audio firmware */
  131. if (runtime->buffer_changed) {
  132. ret = create_page_table(component, substream, runtime->dma_area,
  133. runtime->dma_bytes);
  134. if (ret < 0)
  135. return ret;
  136. }
  137. /* number of pages should be rounded up */
  138. pcm.params.buffer.pages = PFN_UP(runtime->dma_bytes);
  139. /* set IPC PCM parameters */
  140. pcm.hdr.size = sizeof(pcm);
  141. pcm.hdr.cmd = SOF_IPC_GLB_STREAM_MSG | SOF_IPC_STREAM_PCM_PARAMS;
  142. pcm.comp_id = spcm->stream[substream->stream].comp_id;
  143. pcm.params.hdr.size = sizeof(pcm.params);
  144. pcm.params.buffer.phy_addr =
  145. spcm->stream[substream->stream].page_table.addr;
  146. pcm.params.buffer.size = runtime->dma_bytes;
  147. pcm.params.direction = substream->stream;
  148. pcm.params.sample_valid_bytes = params_width(params) >> 3;
  149. pcm.params.buffer_fmt = SOF_IPC_BUFFER_INTERLEAVED;
  150. pcm.params.rate = params_rate(params);
  151. pcm.params.channels = params_channels(params);
  152. pcm.params.host_period_bytes = params_period_bytes(params);
  153. /* container size */
  154. ret = snd_pcm_format_physical_width(params_format(params));
  155. if (ret < 0)
  156. return ret;
  157. pcm.params.sample_container_bytes = ret >> 3;
  158. /* format */
  159. switch (params_format(params)) {
  160. case SNDRV_PCM_FORMAT_S16:
  161. pcm.params.frame_fmt = SOF_IPC_FRAME_S16_LE;
  162. break;
  163. case SNDRV_PCM_FORMAT_S24:
  164. pcm.params.frame_fmt = SOF_IPC_FRAME_S24_4LE;
  165. break;
  166. case SNDRV_PCM_FORMAT_S32:
  167. pcm.params.frame_fmt = SOF_IPC_FRAME_S32_LE;
  168. break;
  169. case SNDRV_PCM_FORMAT_FLOAT:
  170. pcm.params.frame_fmt = SOF_IPC_FRAME_FLOAT;
  171. break;
  172. default:
  173. return -EINVAL;
  174. }
  175. /* firmware already configured host stream */
  176. ret = snd_sof_pcm_platform_hw_params(sdev,
  177. substream,
  178. params,
  179. &pcm.params);
  180. if (ret < 0) {
  181. dev_err(component->dev, "error: platform hw params failed\n");
  182. return ret;
  183. }
  184. dev_dbg(component->dev, "stream_tag %d", pcm.params.stream_tag);
  185. /* send IPC to the DSP */
  186. ret = sof_ipc_tx_message(sdev->ipc, pcm.hdr.cmd, &pcm, sizeof(pcm),
  187. &ipc_params_reply, sizeof(ipc_params_reply));
  188. if (ret < 0) {
  189. dev_err(component->dev, "error: hw params ipc failed for stream %d\n",
  190. pcm.params.stream_tag);
  191. return ret;
  192. }
  193. ret = sof_pcm_dsp_params(spcm, substream, &ipc_params_reply);
  194. if (ret < 0)
  195. return ret;
  196. spcm->prepared[substream->stream] = true;
  197. /* save pcm hw_params */
  198. memcpy(&spcm->params[substream->stream], params, sizeof(*params));
  199. return ret;
  200. }
  201. static int sof_pcm_hw_free(struct snd_soc_component *component,
  202. struct snd_pcm_substream *substream)
  203. {
  204. struct snd_soc_pcm_runtime *rtd = asoc_substream_to_rtd(substream);
  205. struct snd_sof_dev *sdev = snd_soc_component_get_drvdata(component);
  206. struct snd_sof_pcm *spcm;
  207. int ret, err = 0;
  208. /* nothing to do for BE */
  209. if (rtd->dai_link->no_pcm)
  210. return 0;
  211. spcm = snd_sof_find_spcm_dai(component, rtd);
  212. if (!spcm)
  213. return -EINVAL;
  214. dev_dbg(component->dev, "pcm: free stream %d dir %d\n",
  215. spcm->pcm.pcm_id, substream->stream);
  216. if (spcm->prepared[substream->stream]) {
  217. ret = sof_pcm_dsp_pcm_free(substream, sdev, spcm);
  218. if (ret < 0)
  219. err = ret;
  220. }
  221. cancel_work_sync(&spcm->stream[substream->stream].period_elapsed_work);
  222. ret = snd_sof_pcm_platform_hw_free(sdev, substream);
  223. if (ret < 0) {
  224. dev_err(component->dev, "error: platform hw free failed\n");
  225. err = ret;
  226. }
  227. return err;
  228. }
  229. static int sof_pcm_prepare(struct snd_soc_component *component,
  230. struct snd_pcm_substream *substream)
  231. {
  232. struct snd_soc_pcm_runtime *rtd = asoc_substream_to_rtd(substream);
  233. struct snd_sof_pcm *spcm;
  234. int ret;
  235. /* nothing to do for BE */
  236. if (rtd->dai_link->no_pcm)
  237. return 0;
  238. spcm = snd_sof_find_spcm_dai(component, rtd);
  239. if (!spcm)
  240. return -EINVAL;
  241. if (spcm->prepared[substream->stream])
  242. return 0;
  243. dev_dbg(component->dev, "pcm: prepare stream %d dir %d\n",
  244. spcm->pcm.pcm_id, substream->stream);
  245. /* set hw_params */
  246. ret = sof_pcm_hw_params(component,
  247. substream, &spcm->params[substream->stream]);
  248. if (ret < 0) {
  249. dev_err(component->dev,
  250. "error: set pcm hw_params after resume\n");
  251. return ret;
  252. }
  253. return 0;
  254. }
  255. /*
  256. * FE dai link trigger actions are always executed in non-atomic context because
  257. * they involve IPC's.
  258. */
  259. static int sof_pcm_trigger(struct snd_soc_component *component,
  260. struct snd_pcm_substream *substream, int cmd)
  261. {
  262. struct snd_soc_pcm_runtime *rtd = asoc_substream_to_rtd(substream);
  263. struct snd_sof_dev *sdev = snd_soc_component_get_drvdata(component);
  264. struct snd_sof_pcm *spcm;
  265. struct sof_ipc_stream stream;
  266. struct sof_ipc_reply reply;
  267. bool reset_hw_params = false;
  268. bool ipc_first = false;
  269. int ret;
  270. /* nothing to do for BE */
  271. if (rtd->dai_link->no_pcm)
  272. return 0;
  273. spcm = snd_sof_find_spcm_dai(component, rtd);
  274. if (!spcm)
  275. return -EINVAL;
  276. dev_dbg(component->dev, "pcm: trigger stream %d dir %d cmd %d\n",
  277. spcm->pcm.pcm_id, substream->stream, cmd);
  278. stream.hdr.size = sizeof(stream);
  279. stream.hdr.cmd = SOF_IPC_GLB_STREAM_MSG;
  280. stream.comp_id = spcm->stream[substream->stream].comp_id;
  281. switch (cmd) {
  282. case SNDRV_PCM_TRIGGER_PAUSE_PUSH:
  283. stream.hdr.cmd |= SOF_IPC_STREAM_TRIG_PAUSE;
  284. ipc_first = true;
  285. break;
  286. case SNDRV_PCM_TRIGGER_PAUSE_RELEASE:
  287. stream.hdr.cmd |= SOF_IPC_STREAM_TRIG_RELEASE;
  288. break;
  289. case SNDRV_PCM_TRIGGER_RESUME:
  290. if (spcm->stream[substream->stream].suspend_ignored) {
  291. /*
  292. * this case will be triggered when INFO_RESUME is
  293. * supported, no need to resume streams that remained
  294. * enabled in D0ix.
  295. */
  296. spcm->stream[substream->stream].suspend_ignored = false;
  297. return 0;
  298. }
  299. /* set up hw_params */
  300. ret = sof_pcm_prepare(component, substream);
  301. if (ret < 0) {
  302. dev_err(component->dev,
  303. "error: failed to set up hw_params upon resume\n");
  304. return ret;
  305. }
  306. fallthrough;
  307. case SNDRV_PCM_TRIGGER_START:
  308. if (spcm->stream[substream->stream].suspend_ignored) {
  309. /*
  310. * This case will be triggered when INFO_RESUME is
  311. * not supported, no need to re-start streams that
  312. * remained enabled in D0ix.
  313. */
  314. spcm->stream[substream->stream].suspend_ignored = false;
  315. return 0;
  316. }
  317. stream.hdr.cmd |= SOF_IPC_STREAM_TRIG_START;
  318. break;
  319. case SNDRV_PCM_TRIGGER_SUSPEND:
  320. if (sdev->system_suspend_target == SOF_SUSPEND_S0IX &&
  321. spcm->stream[substream->stream].d0i3_compatible) {
  322. /*
  323. * trap the event, not sending trigger stop to
  324. * prevent the FW pipelines from being stopped,
  325. * and mark the flag to ignore the upcoming DAPM
  326. * PM events.
  327. */
  328. spcm->stream[substream->stream].suspend_ignored = true;
  329. return 0;
  330. }
  331. fallthrough;
  332. case SNDRV_PCM_TRIGGER_STOP:
  333. stream.hdr.cmd |= SOF_IPC_STREAM_TRIG_STOP;
  334. ipc_first = true;
  335. reset_hw_params = true;
  336. break;
  337. default:
  338. dev_err(component->dev, "error: unhandled trigger cmd %d\n",
  339. cmd);
  340. return -EINVAL;
  341. }
  342. /*
  343. * DMA and IPC sequence is different for start and stop. Need to send
  344. * STOP IPC before stop DMA
  345. */
  346. if (!ipc_first)
  347. snd_sof_pcm_platform_trigger(sdev, substream, cmd);
  348. /* send IPC to the DSP */
  349. ret = sof_ipc_tx_message(sdev->ipc, stream.hdr.cmd, &stream,
  350. sizeof(stream), &reply, sizeof(reply));
  351. /* need to STOP DMA even if STOP IPC failed */
  352. if (ipc_first)
  353. snd_sof_pcm_platform_trigger(sdev, substream, cmd);
  354. /* free PCM if reset_hw_params is set and the STOP IPC is successful */
  355. if (!ret && reset_hw_params)
  356. ret = sof_pcm_dsp_pcm_free(substream, sdev, spcm);
  357. return ret;
  358. }
  359. static snd_pcm_uframes_t sof_pcm_pointer(struct snd_soc_component *component,
  360. struct snd_pcm_substream *substream)
  361. {
  362. struct snd_soc_pcm_runtime *rtd = asoc_substream_to_rtd(substream);
  363. struct snd_sof_dev *sdev = snd_soc_component_get_drvdata(component);
  364. struct snd_sof_pcm *spcm;
  365. snd_pcm_uframes_t host, dai;
  366. /* nothing to do for BE */
  367. if (rtd->dai_link->no_pcm)
  368. return 0;
  369. /* use dsp ops pointer callback directly if set */
  370. if (sof_ops(sdev)->pcm_pointer)
  371. return sof_ops(sdev)->pcm_pointer(sdev, substream);
  372. spcm = snd_sof_find_spcm_dai(component, rtd);
  373. if (!spcm)
  374. return -EINVAL;
  375. /* read position from DSP */
  376. host = bytes_to_frames(substream->runtime,
  377. spcm->stream[substream->stream].posn.host_posn);
  378. dai = bytes_to_frames(substream->runtime,
  379. spcm->stream[substream->stream].posn.dai_posn);
  380. dev_vdbg(component->dev,
  381. "PCM: stream %d dir %d DMA position %lu DAI position %lu\n",
  382. spcm->pcm.pcm_id, substream->stream, host, dai);
  383. return host;
  384. }
  385. static int sof_pcm_open(struct snd_soc_component *component,
  386. struct snd_pcm_substream *substream)
  387. {
  388. struct snd_soc_pcm_runtime *rtd = asoc_substream_to_rtd(substream);
  389. struct snd_pcm_runtime *runtime = substream->runtime;
  390. struct snd_sof_dev *sdev = snd_soc_component_get_drvdata(component);
  391. const struct snd_sof_dsp_ops *ops = sof_ops(sdev);
  392. struct snd_sof_pcm *spcm;
  393. struct snd_soc_tplg_stream_caps *caps;
  394. int ret;
  395. /* nothing to do for BE */
  396. if (rtd->dai_link->no_pcm)
  397. return 0;
  398. spcm = snd_sof_find_spcm_dai(component, rtd);
  399. if (!spcm)
  400. return -EINVAL;
  401. dev_dbg(component->dev, "pcm: open stream %d dir %d\n",
  402. spcm->pcm.pcm_id, substream->stream);
  403. caps = &spcm->pcm.caps[substream->stream];
  404. /* set any runtime constraints based on topology */
  405. snd_pcm_hw_constraint_step(substream->runtime, 0,
  406. SNDRV_PCM_HW_PARAM_BUFFER_BYTES,
  407. le32_to_cpu(caps->period_size_min));
  408. snd_pcm_hw_constraint_step(substream->runtime, 0,
  409. SNDRV_PCM_HW_PARAM_PERIOD_BYTES,
  410. le32_to_cpu(caps->period_size_min));
  411. /* set runtime config */
  412. runtime->hw.info = ops->hw_info; /* platform-specific */
  413. runtime->hw.formats = le64_to_cpu(caps->formats);
  414. runtime->hw.period_bytes_min = le32_to_cpu(caps->period_size_min);
  415. runtime->hw.period_bytes_max = le32_to_cpu(caps->period_size_max);
  416. runtime->hw.periods_min = le32_to_cpu(caps->periods_min);
  417. runtime->hw.periods_max = le32_to_cpu(caps->periods_max);
  418. /*
  419. * caps->buffer_size_min is not used since the
  420. * snd_pcm_hardware structure only defines buffer_bytes_max
  421. */
  422. runtime->hw.buffer_bytes_max = le32_to_cpu(caps->buffer_size_max);
  423. dev_dbg(component->dev, "period min %zd max %zd bytes\n",
  424. runtime->hw.period_bytes_min,
  425. runtime->hw.period_bytes_max);
  426. dev_dbg(component->dev, "period count %d max %d\n",
  427. runtime->hw.periods_min,
  428. runtime->hw.periods_max);
  429. dev_dbg(component->dev, "buffer max %zd bytes\n",
  430. runtime->hw.buffer_bytes_max);
  431. /* set wait time - TODO: come from topology */
  432. substream->wait_time = 500;
  433. spcm->stream[substream->stream].posn.host_posn = 0;
  434. spcm->stream[substream->stream].posn.dai_posn = 0;
  435. spcm->stream[substream->stream].substream = substream;
  436. spcm->prepared[substream->stream] = false;
  437. ret = snd_sof_pcm_platform_open(sdev, substream);
  438. if (ret < 0)
  439. dev_err(component->dev, "error: pcm open failed %d\n", ret);
  440. return ret;
  441. }
  442. static int sof_pcm_close(struct snd_soc_component *component,
  443. struct snd_pcm_substream *substream)
  444. {
  445. struct snd_soc_pcm_runtime *rtd = asoc_substream_to_rtd(substream);
  446. struct snd_sof_dev *sdev = snd_soc_component_get_drvdata(component);
  447. struct snd_sof_pcm *spcm;
  448. int err;
  449. /* nothing to do for BE */
  450. if (rtd->dai_link->no_pcm)
  451. return 0;
  452. spcm = snd_sof_find_spcm_dai(component, rtd);
  453. if (!spcm)
  454. return -EINVAL;
  455. dev_dbg(component->dev, "pcm: close stream %d dir %d\n",
  456. spcm->pcm.pcm_id, substream->stream);
  457. err = snd_sof_pcm_platform_close(sdev, substream);
  458. if (err < 0) {
  459. dev_err(component->dev, "error: pcm close failed %d\n",
  460. err);
  461. /*
  462. * keep going, no point in preventing the close
  463. * from happening
  464. */
  465. }
  466. return 0;
  467. }
  468. /*
  469. * Pre-allocate playback/capture audio buffer pages.
  470. * no need to explicitly release memory preallocated by sof_pcm_new in pcm_free
  471. * snd_pcm_lib_preallocate_free_for_all() is called by the core.
  472. */
  473. static int sof_pcm_new(struct snd_soc_component *component,
  474. struct snd_soc_pcm_runtime *rtd)
  475. {
  476. struct snd_sof_dev *sdev = snd_soc_component_get_drvdata(component);
  477. struct snd_sof_pcm *spcm;
  478. struct snd_pcm *pcm = rtd->pcm;
  479. struct snd_soc_tplg_stream_caps *caps;
  480. int stream = SNDRV_PCM_STREAM_PLAYBACK;
  481. /* find SOF PCM for this RTD */
  482. spcm = snd_sof_find_spcm_dai(component, rtd);
  483. if (!spcm) {
  484. dev_warn(component->dev, "warn: can't find PCM with DAI ID %d\n",
  485. rtd->dai_link->id);
  486. return 0;
  487. }
  488. dev_dbg(component->dev, "creating new PCM %s\n", spcm->pcm.pcm_name);
  489. /* do we need to pre-allocate playback audio buffer pages */
  490. if (!spcm->pcm.playback)
  491. goto capture;
  492. caps = &spcm->pcm.caps[stream];
  493. /* pre-allocate playback audio buffer pages */
  494. dev_dbg(component->dev,
  495. "spcm: allocate %s playback DMA buffer size 0x%x max 0x%x\n",
  496. caps->name, caps->buffer_size_min, caps->buffer_size_max);
  497. if (!pcm->streams[stream].substream) {
  498. dev_err(component->dev, "error: NULL playback substream!\n");
  499. return -EINVAL;
  500. }
  501. snd_pcm_set_managed_buffer(pcm->streams[stream].substream,
  502. SNDRV_DMA_TYPE_DEV_SG, sdev->dev,
  503. 0, le32_to_cpu(caps->buffer_size_max));
  504. capture:
  505. stream = SNDRV_PCM_STREAM_CAPTURE;
  506. /* do we need to pre-allocate capture audio buffer pages */
  507. if (!spcm->pcm.capture)
  508. return 0;
  509. caps = &spcm->pcm.caps[stream];
  510. /* pre-allocate capture audio buffer pages */
  511. dev_dbg(component->dev,
  512. "spcm: allocate %s capture DMA buffer size 0x%x max 0x%x\n",
  513. caps->name, caps->buffer_size_min, caps->buffer_size_max);
  514. if (!pcm->streams[stream].substream) {
  515. dev_err(component->dev, "error: NULL capture substream!\n");
  516. return -EINVAL;
  517. }
  518. snd_pcm_set_managed_buffer(pcm->streams[stream].substream,
  519. SNDRV_DMA_TYPE_DEV_SG, sdev->dev,
  520. 0, le32_to_cpu(caps->buffer_size_max));
  521. return 0;
  522. }
  523. /* fixup the BE DAI link to match any values from topology */
  524. static int sof_pcm_dai_link_fixup(struct snd_soc_pcm_runtime *rtd,
  525. struct snd_pcm_hw_params *params)
  526. {
  527. struct snd_interval *rate = hw_param_interval(params,
  528. SNDRV_PCM_HW_PARAM_RATE);
  529. struct snd_interval *channels = hw_param_interval(params,
  530. SNDRV_PCM_HW_PARAM_CHANNELS);
  531. struct snd_mask *fmt = hw_param_mask(params, SNDRV_PCM_HW_PARAM_FORMAT);
  532. struct snd_soc_component *component =
  533. snd_soc_rtdcom_lookup(rtd, SOF_AUDIO_PCM_DRV_NAME);
  534. struct snd_sof_dai *dai =
  535. snd_sof_find_dai(component, (char *)rtd->dai_link->name);
  536. struct snd_soc_dpcm *dpcm;
  537. /* no topology exists for this BE, try a common configuration */
  538. if (!dai) {
  539. dev_warn(component->dev,
  540. "warning: no topology found for BE DAI %s config\n",
  541. rtd->dai_link->name);
  542. /* set 48k, stereo, 16bits by default */
  543. rate->min = 48000;
  544. rate->max = 48000;
  545. channels->min = 2;
  546. channels->max = 2;
  547. snd_mask_none(fmt);
  548. snd_mask_set_format(fmt, SNDRV_PCM_FORMAT_S16_LE);
  549. return 0;
  550. }
  551. /* read format from topology */
  552. snd_mask_none(fmt);
  553. switch (dai->comp_dai.config.frame_fmt) {
  554. case SOF_IPC_FRAME_S16_LE:
  555. snd_mask_set_format(fmt, SNDRV_PCM_FORMAT_S16_LE);
  556. break;
  557. case SOF_IPC_FRAME_S24_4LE:
  558. snd_mask_set_format(fmt, SNDRV_PCM_FORMAT_S24_LE);
  559. break;
  560. case SOF_IPC_FRAME_S32_LE:
  561. snd_mask_set_format(fmt, SNDRV_PCM_FORMAT_S32_LE);
  562. break;
  563. default:
  564. dev_err(component->dev, "error: No available DAI format!\n");
  565. return -EINVAL;
  566. }
  567. /* read rate and channels from topology */
  568. switch (dai->dai_config->type) {
  569. case SOF_DAI_INTEL_SSP:
  570. rate->min = dai->dai_config->ssp.fsync_rate;
  571. rate->max = dai->dai_config->ssp.fsync_rate;
  572. channels->min = dai->dai_config->ssp.tdm_slots;
  573. channels->max = dai->dai_config->ssp.tdm_slots;
  574. dev_dbg(component->dev,
  575. "rate_min: %d rate_max: %d\n", rate->min, rate->max);
  576. dev_dbg(component->dev,
  577. "channels_min: %d channels_max: %d\n",
  578. channels->min, channels->max);
  579. break;
  580. case SOF_DAI_INTEL_DMIC:
  581. /* DMIC only supports 16 or 32 bit formats */
  582. if (dai->comp_dai.config.frame_fmt == SOF_IPC_FRAME_S24_4LE) {
  583. dev_err(component->dev,
  584. "error: invalid fmt %d for DAI type %d\n",
  585. dai->comp_dai.config.frame_fmt,
  586. dai->dai_config->type);
  587. }
  588. break;
  589. case SOF_DAI_INTEL_HDA:
  590. /*
  591. * HDAudio does not follow the default trigger
  592. * sequence due to firmware implementation
  593. */
  594. for_each_dpcm_fe(rtd, SNDRV_PCM_STREAM_PLAYBACK, dpcm) {
  595. struct snd_soc_pcm_runtime *fe = dpcm->fe;
  596. fe->dai_link->trigger[SNDRV_PCM_STREAM_PLAYBACK] =
  597. SND_SOC_DPCM_TRIGGER_POST;
  598. }
  599. break;
  600. case SOF_DAI_INTEL_ALH:
  601. /* do nothing for ALH dai_link */
  602. break;
  603. case SOF_DAI_IMX_ESAI:
  604. rate->min = dai->dai_config->esai.fsync_rate;
  605. rate->max = dai->dai_config->esai.fsync_rate;
  606. channels->min = dai->dai_config->esai.tdm_slots;
  607. channels->max = dai->dai_config->esai.tdm_slots;
  608. dev_dbg(component->dev,
  609. "rate_min: %d rate_max: %d\n", rate->min, rate->max);
  610. dev_dbg(component->dev,
  611. "channels_min: %d channels_max: %d\n",
  612. channels->min, channels->max);
  613. break;
  614. case SOF_DAI_IMX_SAI:
  615. rate->min = dai->dai_config->sai.fsync_rate;
  616. rate->max = dai->dai_config->sai.fsync_rate;
  617. channels->min = dai->dai_config->sai.tdm_slots;
  618. channels->max = dai->dai_config->sai.tdm_slots;
  619. dev_dbg(component->dev,
  620. "rate_min: %d rate_max: %d\n", rate->min, rate->max);
  621. dev_dbg(component->dev,
  622. "channels_min: %d channels_max: %d\n",
  623. channels->min, channels->max);
  624. break;
  625. default:
  626. dev_err(component->dev, "error: invalid DAI type %d\n",
  627. dai->dai_config->type);
  628. break;
  629. }
  630. return 0;
  631. }
  632. static int sof_pcm_probe(struct snd_soc_component *component)
  633. {
  634. struct snd_sof_dev *sdev = snd_soc_component_get_drvdata(component);
  635. struct snd_sof_pdata *plat_data = sdev->pdata;
  636. const char *tplg_filename;
  637. int ret;
  638. /* load the default topology */
  639. sdev->component = component;
  640. tplg_filename = devm_kasprintf(sdev->dev, GFP_KERNEL,
  641. "%s/%s",
  642. plat_data->tplg_filename_prefix,
  643. plat_data->tplg_filename);
  644. if (!tplg_filename)
  645. return -ENOMEM;
  646. ret = snd_sof_load_topology(component, tplg_filename);
  647. if (ret < 0) {
  648. dev_err(component->dev, "error: failed to load DSP topology %d\n",
  649. ret);
  650. return ret;
  651. }
  652. return ret;
  653. }
  654. static void sof_pcm_remove(struct snd_soc_component *component)
  655. {
  656. /* remove topology */
  657. snd_soc_tplg_component_remove(component, SND_SOC_TPLG_INDEX_ALL);
  658. }
  659. void snd_sof_new_platform_drv(struct snd_sof_dev *sdev)
  660. {
  661. struct snd_soc_component_driver *pd = &sdev->plat_drv;
  662. struct snd_sof_pdata *plat_data = sdev->pdata;
  663. const char *drv_name;
  664. drv_name = plat_data->machine->drv_name;
  665. pd->name = "sof-audio-component";
  666. pd->probe = sof_pcm_probe;
  667. pd->remove = sof_pcm_remove;
  668. pd->open = sof_pcm_open;
  669. pd->close = sof_pcm_close;
  670. pd->hw_params = sof_pcm_hw_params;
  671. pd->prepare = sof_pcm_prepare;
  672. pd->hw_free = sof_pcm_hw_free;
  673. pd->trigger = sof_pcm_trigger;
  674. pd->pointer = sof_pcm_pointer;
  675. #if IS_ENABLED(CONFIG_SND_SOC_SOF_COMPRESS)
  676. pd->compress_ops = &sof_compressed_ops;
  677. #endif
  678. #if IS_ENABLED(CONFIG_SND_SOC_SOF_DEBUG_PROBES)
  679. /* override cops when probe support is enabled */
  680. pd->compress_ops = &sof_probe_compressed_ops;
  681. #endif
  682. pd->pcm_construct = sof_pcm_new;
  683. pd->ignore_machine = drv_name;
  684. pd->be_hw_params_fixup = sof_pcm_dai_link_fixup;
  685. pd->be_pcm_base = SOF_BE_PCM_BASE;
  686. pd->use_dai_pcm_id = true;
  687. pd->topology_name_prefix = "sof";
  688. /* increment module refcount when a pcm is opened */
  689. pd->module_get_upon_open = 1;
  690. }