msm-pcm-afe.c 16 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625
  1. /* Copyright (c) 2011-2012, 2017, The Linux Foundation. All rights reserved.
  2. *
  3. * This program is free software; you can redistribute it and/or modify
  4. * it under the terms of the GNU General Public License version 2 and
  5. * only version 2 as published by the Free Software Foundation.
  6. *
  7. * This program is distributed in the hope that it will be useful,
  8. * but WITHOUT ANY WARRANTY; without even the implied warranty of
  9. * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
  10. * GNU General Public License for more details.
  11. */
  12. #include <linux/init.h>
  13. #include <linux/err.h>
  14. #include <linux/module.h>
  15. #include <linux/moduleparam.h>
  16. #include <linux/time.h>
  17. #include <linux/wait.h>
  18. #include <linux/platform_device.h>
  19. #include <linux/slab.h>
  20. #include <linux/dma-mapping.h>
  21. #include <sound/core.h>
  22. #include <sound/soc.h>
  23. #include <sound/soc-dapm.h>
  24. #include <sound/pcm.h>
  25. #include <sound/initval.h>
  26. #include <sound/control.h>
  27. #include <sound/q6adm.h>
  28. #include <asm/dma.h>
  29. #include <linux/memory_alloc.h>
  30. #include "msm-pcm-afe.h"
  31. #include "msm-pcm-q6.h"
  32. #define MIN_PERIOD_SIZE (128 * 2)
  33. #define MAX_PERIOD_SIZE (128 * 2 * 2 * 6)
  34. #define MIN_NUM_PERIODS 4
  35. #define MAX_NUM_PERIODS 768
  36. static struct snd_pcm_hardware msm_afe_hardware = {
  37. .info = (SNDRV_PCM_INFO_MMAP |
  38. SNDRV_PCM_INFO_BLOCK_TRANSFER |
  39. SNDRV_PCM_INFO_MMAP_VALID |
  40. SNDRV_PCM_INFO_INTERLEAVED),
  41. .formats = SNDRV_PCM_FMTBIT_S16_LE,
  42. .rates = (SNDRV_PCM_RATE_8000 |
  43. SNDRV_PCM_RATE_16000 |
  44. SNDRV_PCM_RATE_48000),
  45. .rate_min = 8000,
  46. .rate_max = 48000,
  47. .channels_min = 1,
  48. .channels_max = 2,
  49. .buffer_bytes_max = MAX_PERIOD_SIZE * MAX_NUM_PERIODS,
  50. .period_bytes_min = MIN_PERIOD_SIZE,
  51. .period_bytes_max = MAX_PERIOD_SIZE,
  52. .periods_min = MIN_NUM_PERIODS,
  53. .periods_max = MAX_NUM_PERIODS,
  54. .fifo_size = 0,
  55. };
  56. static enum hrtimer_restart afe_hrtimer_callback(struct hrtimer *hrt);
  57. static enum hrtimer_restart afe_hrtimer_rec_callback(struct hrtimer *hrt);
  58. static void q6asm_event_handler(uint32_t opcode,
  59. uint32_t token, uint32_t *payload, void *priv)
  60. {
  61. }
  62. static enum hrtimer_restart afe_hrtimer_callback(struct hrtimer *hrt)
  63. {
  64. struct pcm_afe_info *prtd =
  65. container_of(hrt, struct pcm_afe_info, hrt);
  66. struct snd_pcm_substream *substream = prtd->substream;
  67. struct snd_pcm_runtime *runtime = substream->runtime;
  68. if (prtd->start) {
  69. pr_debug("sending frame to DSP: poll_time: %d\n",
  70. prtd->poll_time);
  71. if (prtd->dsp_cnt == runtime->periods)
  72. prtd->dsp_cnt = 0;
  73. afe_rt_proxy_port_write(
  74. (prtd->dma_addr +
  75. (prtd->dsp_cnt *
  76. snd_pcm_lib_period_bytes(prtd->substream))),
  77. snd_pcm_lib_period_bytes(prtd->substream));
  78. prtd->dsp_cnt++;
  79. hrtimer_forward_now(hrt, ns_to_ktime(prtd->poll_time
  80. * 1000));
  81. return HRTIMER_RESTART;
  82. } else
  83. return HRTIMER_NORESTART;
  84. }
  85. static enum hrtimer_restart afe_hrtimer_rec_callback(struct hrtimer *hrt)
  86. {
  87. struct pcm_afe_info *prtd =
  88. container_of(hrt, struct pcm_afe_info, hrt);
  89. struct snd_pcm_substream *substream = prtd->substream;
  90. struct snd_pcm_runtime *runtime = substream->runtime;
  91. if (prtd->start) {
  92. if (prtd->dsp_cnt == runtime->periods)
  93. prtd->dsp_cnt = 0;
  94. afe_rt_proxy_port_read(
  95. (prtd->dma_addr + (prtd->dsp_cnt
  96. * snd_pcm_lib_period_bytes(prtd->substream))),
  97. snd_pcm_lib_period_bytes(prtd->substream));
  98. prtd->dsp_cnt++;
  99. pr_debug("sending frame rec to DSP: poll_time: %d\n",
  100. prtd->poll_time);
  101. hrtimer_forward_now(hrt, ns_to_ktime(prtd->poll_time
  102. * 1000));
  103. return HRTIMER_RESTART;
  104. } else
  105. return HRTIMER_NORESTART;
  106. }
  107. static void pcm_afe_process_tx_pkt(uint32_t opcode,
  108. uint32_t token, uint32_t *payload,
  109. void *priv)
  110. {
  111. struct pcm_afe_info *prtd = priv;
  112. unsigned long dsp_flags;
  113. struct snd_pcm_substream *substream = NULL;
  114. struct snd_pcm_runtime *runtime = NULL;
  115. uint16_t event;
  116. if (prtd == NULL)
  117. return;
  118. substream = prtd->substream;
  119. runtime = substream->runtime;
  120. pr_debug("%s\n", __func__);
  121. spin_lock_irqsave(&prtd->dsp_lock, dsp_flags);
  122. switch (opcode) {
  123. case AFE_EVENT_RT_PROXY_PORT_STATUS: {
  124. event = (uint16_t)((0xFFFF0000 & payload[0]) >> 0x10);
  125. switch (event) {
  126. case AFE_EVENT_RTPORT_START: {
  127. prtd->dsp_cnt = 0;
  128. prtd->poll_time = ((unsigned long)((
  129. snd_pcm_lib_period_bytes
  130. (prtd->substream) *
  131. 1000 * 1000)/
  132. (runtime->rate *
  133. runtime->channels * 2)));
  134. pr_debug("prtd->poll_time: %d",
  135. prtd->poll_time);
  136. break;
  137. }
  138. case AFE_EVENT_RTPORT_STOP:
  139. pr_debug("%s: event!=0\n", __func__);
  140. prtd->start = 0;
  141. snd_pcm_stop(substream, SNDRV_PCM_STATE_SETUP);
  142. break;
  143. case AFE_EVENT_RTPORT_LOW_WM:
  144. pr_debug("%s: Underrun\n", __func__);
  145. break;
  146. case AFE_EVENT_RTPORT_HI_WM:
  147. pr_debug("%s: Overrun\n", __func__);
  148. break;
  149. default:
  150. break;
  151. }
  152. break;
  153. }
  154. case APR_BASIC_RSP_RESULT: {
  155. switch (payload[0]) {
  156. case AFE_SERVICE_CMD_RTPORT_WR:
  157. pr_debug("write done\n");
  158. prtd->pcm_irq_pos += snd_pcm_lib_period_bytes
  159. (prtd->substream);
  160. snd_pcm_period_elapsed(prtd->substream);
  161. break;
  162. default:
  163. break;
  164. }
  165. break;
  166. }
  167. default:
  168. break;
  169. }
  170. spin_unlock_irqrestore(&prtd->dsp_lock, dsp_flags);
  171. }
  172. static void pcm_afe_process_rx_pkt(uint32_t opcode,
  173. uint32_t token, uint32_t *payload,
  174. void *priv)
  175. {
  176. struct pcm_afe_info *prtd = priv;
  177. unsigned long dsp_flags;
  178. struct snd_pcm_substream *substream = NULL;
  179. struct snd_pcm_runtime *runtime = NULL;
  180. uint16_t event;
  181. if (prtd == NULL)
  182. return;
  183. substream = prtd->substream;
  184. runtime = substream->runtime;
  185. pr_debug("%s\n", __func__);
  186. spin_lock_irqsave(&prtd->dsp_lock, dsp_flags);
  187. switch (opcode) {
  188. case AFE_EVENT_RT_PROXY_PORT_STATUS: {
  189. event = (uint16_t)((0xFFFF0000 & payload[0]) >> 0x10);
  190. switch (event) {
  191. case AFE_EVENT_RTPORT_START: {
  192. prtd->dsp_cnt = 0;
  193. prtd->poll_time = ((unsigned long)((
  194. snd_pcm_lib_period_bytes(prtd->substream)
  195. * 1000 * 1000)/(runtime->rate
  196. * runtime->channels * 2)));
  197. pr_debug("prtd->poll_time : %d", prtd->poll_time);
  198. break;
  199. }
  200. case AFE_EVENT_RTPORT_STOP:
  201. pr_debug("%s: event!=0\n", __func__);
  202. prtd->start = 0;
  203. snd_pcm_stop(substream, SNDRV_PCM_STATE_SETUP);
  204. break;
  205. case AFE_EVENT_RTPORT_LOW_WM:
  206. pr_debug("%s: Underrun\n", __func__);
  207. break;
  208. case AFE_EVENT_RTPORT_HI_WM:
  209. pr_debug("%s: Overrun\n", __func__);
  210. break;
  211. default:
  212. break;
  213. }
  214. break;
  215. }
  216. case APR_BASIC_RSP_RESULT: {
  217. switch (payload[0]) {
  218. case AFE_SERVICE_CMD_RTPORT_RD:
  219. pr_debug("Read done\n");
  220. prtd->pcm_irq_pos += snd_pcm_lib_period_bytes
  221. (prtd->substream);
  222. snd_pcm_period_elapsed(prtd->substream);
  223. break;
  224. default:
  225. break;
  226. }
  227. break;
  228. }
  229. default:
  230. break;
  231. }
  232. spin_unlock_irqrestore(&prtd->dsp_lock, dsp_flags);
  233. }
  234. static int msm_afe_playback_prepare(struct snd_pcm_substream *substream)
  235. {
  236. struct snd_pcm_runtime *runtime = substream->runtime;
  237. struct pcm_afe_info *prtd = runtime->private_data;
  238. struct snd_soc_pcm_runtime *rtd = substream->private_data;
  239. struct snd_soc_dai *dai = rtd->cpu_dai;
  240. int ret = 0;
  241. pr_debug("%s: sample_rate=%d\n", __func__, runtime->rate);
  242. pr_debug("%s: dai->id =%x\n", __func__, dai->id);
  243. ret = afe_register_get_events(dai->id,
  244. pcm_afe_process_tx_pkt, prtd);
  245. if (ret < 0) {
  246. pr_err("afe-pcm:register for events failed\n");
  247. return ret;
  248. }
  249. pr_debug("%s:success\n", __func__);
  250. prtd->prepared++;
  251. return ret;
  252. }
  253. static int msm_afe_capture_prepare(struct snd_pcm_substream *substream)
  254. {
  255. struct snd_pcm_runtime *runtime = substream->runtime;
  256. struct pcm_afe_info *prtd = runtime->private_data;
  257. struct snd_soc_pcm_runtime *rtd = substream->private_data;
  258. struct snd_soc_dai *dai = rtd->cpu_dai;
  259. int ret = 0;
  260. pr_debug("%s\n", __func__);
  261. pr_debug("%s: dai->id =%x\n", __func__, dai->id);
  262. ret = afe_register_get_events(dai->id,
  263. pcm_afe_process_rx_pkt, prtd);
  264. if (ret < 0) {
  265. pr_err("afe-pcm:register for events failed\n");
  266. return ret;
  267. }
  268. pr_debug("%s:success\n", __func__);
  269. prtd->prepared++;
  270. return 0;
  271. }
  272. /* Conventional and unconventional sample rate supported */
  273. static unsigned int supported_sample_rates[] = {
  274. 8000, 16000, 48000
  275. };
  276. static struct snd_pcm_hw_constraint_list constraints_sample_rates = {
  277. .count = ARRAY_SIZE(supported_sample_rates),
  278. .list = supported_sample_rates,
  279. .mask = 0,
  280. };
  281. static int msm_afe_open(struct snd_pcm_substream *substream)
  282. {
  283. struct snd_pcm_runtime *runtime = substream->runtime;
  284. struct pcm_afe_info *prtd = NULL;
  285. int ret = 0;
  286. prtd = kzalloc(sizeof(struct pcm_afe_info), GFP_KERNEL);
  287. if (prtd == NULL) {
  288. pr_err("Failed to allocate memory for msm_audio\n");
  289. return -ENOMEM;
  290. } else
  291. pr_debug("prtd %x\n", (unsigned int)prtd);
  292. mutex_init(&prtd->lock);
  293. spin_lock_init(&prtd->dsp_lock);
  294. prtd->dsp_cnt = 0;
  295. mutex_lock(&prtd->lock);
  296. runtime->hw = msm_afe_hardware;
  297. prtd->substream = substream;
  298. runtime->private_data = prtd;
  299. prtd->audio_client = q6asm_audio_client_alloc(
  300. (app_cb)q6asm_event_handler, prtd);
  301. if (!prtd->audio_client) {
  302. pr_debug("%s: Could not allocate memory\n", __func__);
  303. mutex_unlock(&prtd->lock);
  304. kfree(prtd);
  305. return -ENOMEM;
  306. }
  307. hrtimer_init(&prtd->hrt, CLOCK_MONOTONIC, HRTIMER_MODE_REL);
  308. if (substream->stream == SNDRV_PCM_STREAM_PLAYBACK)
  309. prtd->hrt.function = afe_hrtimer_callback;
  310. else if (substream->stream == SNDRV_PCM_STREAM_CAPTURE)
  311. prtd->hrt.function = afe_hrtimer_rec_callback;
  312. mutex_unlock(&prtd->lock);
  313. ret = snd_pcm_hw_constraint_list(runtime, 0,
  314. SNDRV_PCM_HW_PARAM_RATE,
  315. &constraints_sample_rates);
  316. if (ret < 0)
  317. pr_err("snd_pcm_hw_constraint_list failed\n");
  318. /* Ensure that buffer size is a multiple of period size */
  319. ret = snd_pcm_hw_constraint_integer(runtime,
  320. SNDRV_PCM_HW_PARAM_PERIODS);
  321. if (ret < 0)
  322. pr_err("snd_pcm_hw_constraint_integer failed\n");
  323. return 0;
  324. }
  325. static int msm_afe_close(struct snd_pcm_substream *substream)
  326. {
  327. int rc = 0;
  328. struct snd_dma_buffer *dma_buf;
  329. struct snd_pcm_runtime *runtime;
  330. struct pcm_afe_info *prtd;
  331. struct snd_soc_pcm_runtime *rtd = NULL;
  332. struct snd_soc_dai *dai = NULL;
  333. int dir = IN;
  334. int ret = 0;
  335. pr_debug("%s\n", __func__);
  336. if (substream == NULL) {
  337. pr_err("substream is NULL\n");
  338. return -EINVAL;
  339. }
  340. rtd = substream->private_data;
  341. dai = rtd->cpu_dai;
  342. runtime = substream->runtime;
  343. prtd = runtime->private_data;
  344. mutex_lock(&prtd->lock);
  345. if (substream->stream == SNDRV_PCM_STREAM_PLAYBACK) {
  346. dir = IN;
  347. ret = afe_unregister_get_events(dai->id);
  348. if (ret < 0)
  349. pr_err("AFE unregister for events failed\n");
  350. } else if (substream->stream == SNDRV_PCM_STREAM_CAPTURE) {
  351. dir = OUT;
  352. ret = afe_unregister_get_events(dai->id);
  353. if (ret < 0)
  354. pr_err("AFE unregister for events failed\n");
  355. }
  356. hrtimer_cancel(&prtd->hrt);
  357. rc = afe_cmd_memory_unmap(runtime->dma_addr);
  358. if (rc < 0)
  359. pr_err("AFE memory unmap failed\n");
  360. pr_debug("release all buffer\n");
  361. dma_buf = &substream->dma_buffer;
  362. if (dma_buf == NULL) {
  363. pr_debug("dma_buf is NULL\n");
  364. goto done;
  365. }
  366. if (dma_buf->area) {
  367. dma_buf->area = NULL;
  368. }
  369. q6asm_audio_client_buf_free_contiguous(dir,
  370. prtd->audio_client);
  371. done:
  372. pr_debug("%s: dai->id =%x\n", __func__, dai->id);
  373. q6asm_audio_client_free(prtd->audio_client);
  374. mutex_unlock(&prtd->lock);
  375. prtd->prepared--;
  376. kfree(prtd);
  377. runtime->private_data = NULL;
  378. return 0;
  379. }
  380. static int msm_afe_prepare(struct snd_pcm_substream *substream)
  381. {
  382. int ret = 0;
  383. struct snd_pcm_runtime *runtime = substream->runtime;
  384. struct pcm_afe_info *prtd = runtime->private_data;
  385. prtd->pcm_irq_pos = 0;
  386. if (prtd->prepared)
  387. return 0;
  388. mutex_lock(&prtd->lock);
  389. if (substream->stream == SNDRV_PCM_STREAM_PLAYBACK)
  390. ret = msm_afe_playback_prepare(substream);
  391. else if (substream->stream == SNDRV_PCM_STREAM_CAPTURE)
  392. ret = msm_afe_capture_prepare(substream);
  393. mutex_unlock(&prtd->lock);
  394. return ret;
  395. }
  396. static int msm_afe_mmap(struct snd_pcm_substream *substream,
  397. struct vm_area_struct *vma)
  398. {
  399. struct snd_pcm_runtime *runtime = substream->runtime;
  400. struct pcm_afe_info *prtd = runtime->private_data;
  401. int result = 0;
  402. pr_debug("%s\n", __func__);
  403. prtd->mmap_flag = 1;
  404. if (runtime->dma_addr && runtime->dma_bytes) {
  405. vma->vm_page_prot = pgprot_noncached(vma->vm_page_prot);
  406. result = remap_pfn_range(vma, vma->vm_start,
  407. runtime->dma_addr >> PAGE_SHIFT,
  408. runtime->dma_bytes,
  409. vma->vm_page_prot);
  410. } else {
  411. pr_err("Physical address or size of buf is NULL");
  412. return -EINVAL;
  413. }
  414. return result;
  415. }
  416. static int msm_afe_trigger(struct snd_pcm_substream *substream, int cmd)
  417. {
  418. int ret = 0;
  419. struct snd_pcm_runtime *runtime = substream->runtime;
  420. struct pcm_afe_info *prtd = runtime->private_data;
  421. switch (cmd) {
  422. case SNDRV_PCM_TRIGGER_START:
  423. case SNDRV_PCM_TRIGGER_RESUME:
  424. case SNDRV_PCM_TRIGGER_PAUSE_RELEASE:
  425. pr_debug("%s: SNDRV_PCM_TRIGGER_START\n", __func__);
  426. prtd->start = 1;
  427. hrtimer_start(&prtd->hrt, ns_to_ktime(0),
  428. HRTIMER_MODE_REL);
  429. break;
  430. case SNDRV_PCM_TRIGGER_STOP:
  431. case SNDRV_PCM_TRIGGER_SUSPEND:
  432. case SNDRV_PCM_TRIGGER_PAUSE_PUSH:
  433. pr_debug("%s: SNDRV_PCM_TRIGGER_STOP\n", __func__);
  434. prtd->start = 0;
  435. break;
  436. default:
  437. ret = -EINVAL;
  438. break;
  439. }
  440. return ret;
  441. }
  442. static int msm_afe_hw_params(struct snd_pcm_substream *substream,
  443. struct snd_pcm_hw_params *params)
  444. {
  445. struct snd_pcm_runtime *runtime = substream->runtime;
  446. struct snd_dma_buffer *dma_buf = &substream->dma_buffer;
  447. struct pcm_afe_info *prtd = runtime->private_data;
  448. struct audio_buffer *buf;
  449. int dir, ret;
  450. pr_debug("%s:\n", __func__);
  451. mutex_lock(&prtd->lock);
  452. if (substream->stream == SNDRV_PCM_STREAM_PLAYBACK)
  453. dir = IN;
  454. else
  455. dir = OUT;
  456. ret = q6asm_audio_client_buf_alloc_contiguous(dir,
  457. prtd->audio_client,
  458. runtime->hw.period_bytes_min,
  459. runtime->hw.periods_max);
  460. if (ret < 0) {
  461. pr_err("Audio Start: Buffer Allocation failed rc = %d\n", ret);
  462. mutex_unlock(&prtd->lock);
  463. return -ENOMEM;
  464. }
  465. buf = prtd->audio_client->port[dir].buf;
  466. if (buf == NULL || buf[0].data == NULL) {
  467. mutex_unlock(&prtd->lock);
  468. return -ENOMEM;
  469. }
  470. pr_debug("%s:buf = %p\n", __func__, buf);
  471. dma_buf->dev.type = SNDRV_DMA_TYPE_DEV;
  472. dma_buf->dev.dev = substream->pcm->card->dev;
  473. dma_buf->private_data = NULL;
  474. dma_buf->area = buf[0].data;
  475. dma_buf->addr = buf[0].phys;
  476. dma_buf->bytes = runtime->hw.buffer_bytes_max;
  477. if (!dma_buf->area) {
  478. pr_err("%s:MSM AFE physical memory allocation failed\n",
  479. __func__);
  480. mutex_unlock(&prtd->lock);
  481. return -ENOMEM;
  482. }
  483. memset(dma_buf->area, 0, runtime->hw.buffer_bytes_max);
  484. prtd->dma_addr = (u32) dma_buf->addr;
  485. mutex_unlock(&prtd->lock);
  486. snd_pcm_set_runtime_buffer(substream, &substream->dma_buffer);
  487. ret = afe_cmd_memory_map(dma_buf->addr, dma_buf->bytes);
  488. if (ret < 0)
  489. pr_err("fail to map memory to DSP\n");
  490. return ret;
  491. }
  492. static snd_pcm_uframes_t msm_afe_pointer(struct snd_pcm_substream *substream)
  493. {
  494. struct snd_pcm_runtime *runtime = substream->runtime;
  495. struct pcm_afe_info *prtd = runtime->private_data;
  496. if (prtd->pcm_irq_pos >= snd_pcm_lib_buffer_bytes(substream))
  497. prtd->pcm_irq_pos = 0;
  498. pr_debug("pcm_irq_pos = %d\n", prtd->pcm_irq_pos);
  499. return bytes_to_frames(runtime, (prtd->pcm_irq_pos));
  500. }
  501. static struct snd_pcm_ops msm_afe_ops = {
  502. .open = msm_afe_open,
  503. .hw_params = msm_afe_hw_params,
  504. .trigger = msm_afe_trigger,
  505. .close = msm_afe_close,
  506. .prepare = msm_afe_prepare,
  507. .mmap = msm_afe_mmap,
  508. .pointer = msm_afe_pointer,
  509. };
  510. static int msm_asoc_pcm_new(struct snd_soc_pcm_runtime *rtd)
  511. {
  512. struct snd_card *card = rtd->card->snd_card;
  513. int ret = 0;
  514. pr_debug("%s\n", __func__);
  515. if (!card->dev->coherent_dma_mask)
  516. card->dev->coherent_dma_mask = DMA_BIT_MASK(32);
  517. return ret;
  518. }
  519. static int msm_afe_afe_probe(struct snd_soc_platform *platform)
  520. {
  521. pr_debug("%s\n", __func__);
  522. return 0;
  523. }
  524. static struct snd_soc_platform_driver msm_soc_platform = {
  525. .ops = &msm_afe_ops,
  526. .pcm_new = msm_asoc_pcm_new,
  527. .probe = msm_afe_afe_probe,
  528. };
  529. static __devinit int msm_afe_probe(struct platform_device *pdev)
  530. {
  531. pr_debug("%s: dev name %s\n", __func__, dev_name(&pdev->dev));
  532. return snd_soc_register_platform(&pdev->dev,
  533. &msm_soc_platform);
  534. }
  535. static int msm_afe_remove(struct platform_device *pdev)
  536. {
  537. pr_debug("%s\n", __func__);
  538. snd_soc_unregister_platform(&pdev->dev);
  539. return 0;
  540. }
  541. static struct platform_driver msm_afe_driver = {
  542. .driver = {
  543. .name = "msm-pcm-afe",
  544. .owner = THIS_MODULE,
  545. },
  546. .probe = msm_afe_probe,
  547. .remove = __devexit_p(msm_afe_remove),
  548. };
  549. static int __init msm_soc_platform_init(void)
  550. {
  551. pr_debug("%s\n", __func__);
  552. return platform_driver_register(&msm_afe_driver);
  553. }
  554. module_init(msm_soc_platform_init);
  555. static void __exit msm_soc_platform_exit(void)
  556. {
  557. pr_debug("%s\n", __func__);
  558. platform_driver_unregister(&msm_afe_driver);
  559. }
  560. module_exit(msm_soc_platform_exit);
  561. MODULE_DESCRIPTION("AFE PCM module platform driver");
  562. MODULE_LICENSE("GPL v2");