1// SPDX-License-Identifier: GPL-2.0
2/*
3 * APBridge ALSA SoC dummy codec driver
4 * Copyright 2016 Google Inc.
5 * Copyright 2016 Linaro Ltd.
6 */
7#include <linux/kernel.h>
8#include <linux/module.h>
9#include <linux/pm_runtime.h>
10#include <sound/soc.h>
11#include <sound/pcm_params.h>
12#include <uapi/linux/input.h>
13
14#include "audio_codec.h"
15#include "audio_apbridgea.h"
16#include "audio_manager.h"
17#include "audio_helper.h"
18
19static struct gbaudio_codec_info *gbcodec;
20
21static struct gbaudio_data_connection *
22find_data(struct gbaudio_module_info *module, int id)
23{
24 struct gbaudio_data_connection *data;
25
26 list_for_each_entry(data, &module->data_list, list) {
27 if (id == data->id)
28 return data;
29 }
30 return NULL;
31}
32
33static struct gbaudio_stream_params *
34find_dai_stream_params(struct gbaudio_codec_info *codec, int id, int stream)
35{
36 struct gbaudio_codec_dai *dai;
37
38 list_for_each_entry(dai, &codec->dai_list, list) {
39 if (dai->id == id)
40 return &dai->params[stream];
41 }
42 return NULL;
43}
44
45static int gbaudio_module_enable_tx(struct gbaudio_codec_info *codec,
46 struct gbaudio_module_info *module, int id)
47{
48 int module_state, ret = 0;
49 u16 data_cport, i2s_port, cportid;
50 u8 sig_bits, channels;
51 u32 format, rate;
52 struct gbaudio_data_connection *data;
53 struct gbaudio_stream_params *params;
54
55 /* find the dai */
56 data = find_data(module, id);
57 if (!data) {
58 dev_err(module->dev, "%d:DATA connection missing\n", id);
59 return -ENODEV;
60 }
61 module_state = data->state[SNDRV_PCM_STREAM_PLAYBACK];
62
63 params = find_dai_stream_params(codec, id, stream: SNDRV_PCM_STREAM_PLAYBACK);
64 if (!params) {
65 dev_err(codec->dev, "Failed to fetch dai_stream pointer\n");
66 return -EINVAL;
67 }
68
69 /* register cport */
70 if (module_state < GBAUDIO_CODEC_STARTUP) {
71 i2s_port = 0; /* fixed for now */
72 cportid = data->connection->hd_cport_id;
73 ret = gb_audio_apbridgea_register_cport(connection: data->connection,
74 i2s_port, cportid,
75 AUDIO_APBRIDGEA_DIRECTION_TX);
76 if (ret) {
77 dev_err_ratelimited(module->dev, "reg_cport failed:%d\n", ret);
78 return ret;
79 }
80 data->state[SNDRV_PCM_STREAM_PLAYBACK] = GBAUDIO_CODEC_STARTUP;
81 dev_dbg(module->dev, "Dynamic Register %d DAI\n", cportid);
82 }
83
84 /* hw_params */
85 if (module_state < GBAUDIO_CODEC_HWPARAMS) {
86 format = params->format;
87 channels = params->channels;
88 rate = params->rate;
89 sig_bits = params->sig_bits;
90 data_cport = data->connection->intf_cport_id;
91 ret = gb_audio_gb_set_pcm(connection: module->mgmt_connection, data_cport,
92 format, rate, channels, sig_bits);
93 if (ret) {
94 dev_err_ratelimited(module->dev, "set_pcm failed:%d\n", ret);
95 return ret;
96 }
97 data->state[SNDRV_PCM_STREAM_PLAYBACK] = GBAUDIO_CODEC_HWPARAMS;
98 dev_dbg(module->dev, "Dynamic hw_params %d DAI\n", data_cport);
99 }
100
101 /* prepare */
102 if (module_state < GBAUDIO_CODEC_PREPARE) {
103 data_cport = data->connection->intf_cport_id;
104 ret = gb_audio_gb_set_tx_data_size(connection: module->mgmt_connection,
105 data_cport, size: 192);
106 if (ret) {
107 dev_err_ratelimited(module->dev,
108 "set_tx_data_size failed:%d\n",
109 ret);
110 return ret;
111 }
112 ret = gb_audio_gb_activate_tx(connection: module->mgmt_connection, data_cport);
113 if (ret) {
114 dev_err_ratelimited(module->dev,
115 "activate_tx failed:%d\n", ret);
116 return ret;
117 }
118 data->state[SNDRV_PCM_STREAM_PLAYBACK] = GBAUDIO_CODEC_PREPARE;
119 dev_dbg(module->dev, "Dynamic prepare %d DAI\n", data_cport);
120 }
121
122 return 0;
123}
124
125static int gbaudio_module_disable_tx(struct gbaudio_module_info *module, int id)
126{
127 int ret;
128 u16 data_cport, cportid, i2s_port;
129 int module_state;
130 struct gbaudio_data_connection *data;
131
132 /* find the dai */
133 data = find_data(module, id);
134 if (!data) {
135 dev_err(module->dev, "%d:DATA connection missing\n", id);
136 return -ENODEV;
137 }
138 module_state = data->state[SNDRV_PCM_STREAM_PLAYBACK];
139
140 if (module_state > GBAUDIO_CODEC_HWPARAMS) {
141 data_cport = data->connection->intf_cport_id;
142 ret = gb_audio_gb_deactivate_tx(connection: module->mgmt_connection,
143 data_cport);
144 if (ret) {
145 dev_err_ratelimited(module->dev,
146 "deactivate_tx failed:%d\n", ret);
147 return ret;
148 }
149 dev_dbg(module->dev, "Dynamic deactivate %d DAI\n", data_cport);
150 data->state[SNDRV_PCM_STREAM_PLAYBACK] = GBAUDIO_CODEC_HWPARAMS;
151 }
152
153 if (module_state > GBAUDIO_CODEC_SHUTDOWN) {
154 i2s_port = 0; /* fixed for now */
155 cportid = data->connection->hd_cport_id;
156 ret = gb_audio_apbridgea_unregister_cport(connection: data->connection,
157 i2s_port, cportid,
158 AUDIO_APBRIDGEA_DIRECTION_TX);
159 if (ret) {
160 dev_err_ratelimited(module->dev,
161 "unregister_cport failed:%d\n", ret);
162 return ret;
163 }
164 dev_dbg(module->dev, "Dynamic Unregister %d DAI\n", cportid);
165 data->state[SNDRV_PCM_STREAM_PLAYBACK] = GBAUDIO_CODEC_SHUTDOWN;
166 }
167
168 return 0;
169}
170
171static int gbaudio_module_enable_rx(struct gbaudio_codec_info *codec,
172 struct gbaudio_module_info *module, int id)
173{
174 int module_state, ret = 0;
175 u16 data_cport, i2s_port, cportid;
176 u8 sig_bits, channels;
177 u32 format, rate;
178 struct gbaudio_data_connection *data;
179 struct gbaudio_stream_params *params;
180
181 /* find the dai */
182 data = find_data(module, id);
183 if (!data) {
184 dev_err(module->dev, "%d:DATA connection missing\n", id);
185 return -ENODEV;
186 }
187 module_state = data->state[SNDRV_PCM_STREAM_CAPTURE];
188
189 params = find_dai_stream_params(codec, id, stream: SNDRV_PCM_STREAM_CAPTURE);
190 if (!params) {
191 dev_err(codec->dev, "Failed to fetch dai_stream pointer\n");
192 return -EINVAL;
193 }
194
195 /* register cport */
196 if (module_state < GBAUDIO_CODEC_STARTUP) {
197 i2s_port = 0; /* fixed for now */
198 cportid = data->connection->hd_cport_id;
199 ret = gb_audio_apbridgea_register_cport(connection: data->connection,
200 i2s_port, cportid,
201 AUDIO_APBRIDGEA_DIRECTION_RX);
202 if (ret) {
203 dev_err_ratelimited(module->dev, "reg_cport failed:%d\n", ret);
204 return ret;
205 }
206 data->state[SNDRV_PCM_STREAM_CAPTURE] = GBAUDIO_CODEC_STARTUP;
207 dev_dbg(module->dev, "Dynamic Register %d DAI\n", cportid);
208 }
209
210 /* hw_params */
211 if (module_state < GBAUDIO_CODEC_HWPARAMS) {
212 format = params->format;
213 channels = params->channels;
214 rate = params->rate;
215 sig_bits = params->sig_bits;
216 data_cport = data->connection->intf_cport_id;
217 ret = gb_audio_gb_set_pcm(connection: module->mgmt_connection, data_cport,
218 format, rate, channels, sig_bits);
219 if (ret) {
220 dev_err_ratelimited(module->dev, "set_pcm failed:%d\n", ret);
221 return ret;
222 }
223 data->state[SNDRV_PCM_STREAM_CAPTURE] = GBAUDIO_CODEC_HWPARAMS;
224 dev_dbg(module->dev, "Dynamic hw_params %d DAI\n", data_cport);
225 }
226
227 /* prepare */
228 if (module_state < GBAUDIO_CODEC_PREPARE) {
229 data_cport = data->connection->intf_cport_id;
230 ret = gb_audio_gb_set_rx_data_size(connection: module->mgmt_connection,
231 data_cport, size: 192);
232 if (ret) {
233 dev_err_ratelimited(module->dev,
234 "set_rx_data_size failed:%d\n",
235 ret);
236 return ret;
237 }
238 ret = gb_audio_gb_activate_rx(connection: module->mgmt_connection,
239 data_cport);
240 if (ret) {
241 dev_err_ratelimited(module->dev,
242 "activate_rx failed:%d\n", ret);
243 return ret;
244 }
245 data->state[SNDRV_PCM_STREAM_CAPTURE] = GBAUDIO_CODEC_PREPARE;
246 dev_dbg(module->dev, "Dynamic prepare %d DAI\n", data_cport);
247 }
248
249 return 0;
250}
251
252static int gbaudio_module_disable_rx(struct gbaudio_module_info *module, int id)
253{
254 int ret;
255 u16 data_cport, cportid, i2s_port;
256 int module_state;
257 struct gbaudio_data_connection *data;
258
259 /* find the dai */
260 data = find_data(module, id);
261 if (!data) {
262 dev_err(module->dev, "%d:DATA connection missing\n", id);
263 return -ENODEV;
264 }
265 module_state = data->state[SNDRV_PCM_STREAM_CAPTURE];
266
267 if (module_state > GBAUDIO_CODEC_HWPARAMS) {
268 data_cport = data->connection->intf_cport_id;
269 ret = gb_audio_gb_deactivate_rx(connection: module->mgmt_connection,
270 data_cport);
271 if (ret) {
272 dev_err_ratelimited(module->dev,
273 "deactivate_rx failed:%d\n", ret);
274 return ret;
275 }
276 dev_dbg(module->dev, "Dynamic deactivate %d DAI\n", data_cport);
277 data->state[SNDRV_PCM_STREAM_CAPTURE] = GBAUDIO_CODEC_HWPARAMS;
278 }
279
280 if (module_state > GBAUDIO_CODEC_SHUTDOWN) {
281 i2s_port = 0; /* fixed for now */
282 cportid = data->connection->hd_cport_id;
283 ret = gb_audio_apbridgea_unregister_cport(connection: data->connection,
284 i2s_port, cportid,
285 AUDIO_APBRIDGEA_DIRECTION_RX);
286 if (ret) {
287 dev_err_ratelimited(module->dev,
288 "unregister_cport failed:%d\n", ret);
289 return ret;
290 }
291 dev_dbg(module->dev, "Dynamic Unregister %d DAI\n", cportid);
292 data->state[SNDRV_PCM_STREAM_CAPTURE] = GBAUDIO_CODEC_SHUTDOWN;
293 }
294
295 return 0;
296}
297
298int gbaudio_module_update(struct gbaudio_codec_info *codec,
299 struct snd_soc_dapm_widget *w,
300 struct gbaudio_module_info *module, int enable)
301{
302 int dai_id, ret;
303 char intf_name[NAME_SIZE], dir[NAME_SIZE];
304
305 dev_dbg(module->dev, "%s:Module update %s sequence\n", w->name,
306 enable ? "Enable" : "Disable");
307
308 if ((w->id != snd_soc_dapm_aif_in) && (w->id != snd_soc_dapm_aif_out)) {
309 dev_dbg(codec->dev, "No action required for %s\n", w->name);
310 return 0;
311 }
312
313 /* parse dai_id from AIF widget's stream_name */
314 ret = sscanf(w->sname, "%s %d %s", intf_name, &dai_id, dir);
315 if (ret < 3) {
316 dev_err(codec->dev, "Error while parsing dai_id for %s\n", w->name);
317 return -EINVAL;
318 }
319
320 mutex_lock(&codec->lock);
321 if (w->id == snd_soc_dapm_aif_in) {
322 if (enable)
323 ret = gbaudio_module_enable_tx(codec, module, id: dai_id);
324 else
325 ret = gbaudio_module_disable_tx(module, id: dai_id);
326 } else if (w->id == snd_soc_dapm_aif_out) {
327 if (enable)
328 ret = gbaudio_module_enable_rx(codec, module, id: dai_id);
329 else
330 ret = gbaudio_module_disable_rx(module, id: dai_id);
331 }
332
333 mutex_unlock(lock: &codec->lock);
334
335 return ret;
336}
337EXPORT_SYMBOL(gbaudio_module_update);
338
339/*
340 * codec DAI ops
341 */
342static int gbcodec_startup(struct snd_pcm_substream *substream,
343 struct snd_soc_dai *dai)
344{
345 struct gbaudio_codec_info *codec = dev_get_drvdata(dev: dai->dev);
346 struct gbaudio_stream_params *params;
347
348 mutex_lock(&codec->lock);
349
350 if (list_empty(head: &codec->module_list)) {
351 dev_err(codec->dev, "No codec module available\n");
352 mutex_unlock(lock: &codec->lock);
353 return -ENODEV;
354 }
355
356 params = find_dai_stream_params(codec, id: dai->id, stream: substream->stream);
357 if (!params) {
358 dev_err(codec->dev, "Failed to fetch dai_stream pointer\n");
359 mutex_unlock(lock: &codec->lock);
360 return -EINVAL;
361 }
362 params->state = GBAUDIO_CODEC_STARTUP;
363 mutex_unlock(lock: &codec->lock);
364 /* to prevent suspend in case of active audio */
365 pm_stay_awake(dev: dai->dev);
366
367 return 0;
368}
369
370static void gbcodec_shutdown(struct snd_pcm_substream *substream,
371 struct snd_soc_dai *dai)
372{
373 struct gbaudio_codec_info *codec = dev_get_drvdata(dev: dai->dev);
374 struct gbaudio_stream_params *params;
375
376 mutex_lock(&codec->lock);
377
378 if (list_empty(head: &codec->module_list))
379 dev_info(codec->dev, "No codec module available during shutdown\n");
380
381 params = find_dai_stream_params(codec, id: dai->id, stream: substream->stream);
382 if (!params) {
383 dev_err(codec->dev, "Failed to fetch dai_stream pointer\n");
384 mutex_unlock(lock: &codec->lock);
385 return;
386 }
387 params->state = GBAUDIO_CODEC_SHUTDOWN;
388 mutex_unlock(lock: &codec->lock);
389 pm_relax(dev: dai->dev);
390}
391
392static int gbcodec_hw_params(struct snd_pcm_substream *substream,
393 struct snd_pcm_hw_params *hwparams,
394 struct snd_soc_dai *dai)
395{
396 int ret;
397 u8 sig_bits, channels;
398 u32 format, rate;
399 struct gbaudio_module_info *module;
400 struct gbaudio_data_connection *data;
401 struct gb_bundle *bundle;
402 struct gbaudio_codec_info *codec = dev_get_drvdata(dev: dai->dev);
403 struct gbaudio_stream_params *params;
404
405 mutex_lock(&codec->lock);
406
407 if (list_empty(head: &codec->module_list)) {
408 dev_err(codec->dev, "No codec module available\n");
409 mutex_unlock(lock: &codec->lock);
410 return -ENODEV;
411 }
412
413 /*
414 * assuming, currently only 48000 Hz, 16BIT_LE, stereo
415 * is supported, validate params before configuring codec
416 */
417 if (params_channels(p: hwparams) != 2) {
418 dev_err(dai->dev, "Invalid channel count:%d\n",
419 params_channels(hwparams));
420 mutex_unlock(lock: &codec->lock);
421 return -EINVAL;
422 }
423 channels = params_channels(p: hwparams);
424
425 if (params_rate(p: hwparams) != 48000) {
426 dev_err(dai->dev, "Invalid sampling rate:%d\n",
427 params_rate(hwparams));
428 mutex_unlock(lock: &codec->lock);
429 return -EINVAL;
430 }
431 rate = GB_AUDIO_PCM_RATE_48000;
432
433 if (params_format(p: hwparams) != SNDRV_PCM_FORMAT_S16_LE) {
434 dev_err(dai->dev, "Invalid format:%d\n", params_format(hwparams));
435 mutex_unlock(lock: &codec->lock);
436 return -EINVAL;
437 }
438 format = GB_AUDIO_PCM_FMT_S16_LE;
439
440 /* find the data connection */
441 list_for_each_entry(module, &codec->module_list, list) {
442 data = find_data(module, id: dai->id);
443 if (data)
444 break;
445 }
446
447 if (!data) {
448 dev_err(dai->dev, "DATA connection missing\n");
449 mutex_unlock(lock: &codec->lock);
450 return -EINVAL;
451 }
452
453 params = find_dai_stream_params(codec, id: dai->id, stream: substream->stream);
454 if (!params) {
455 dev_err(codec->dev, "Failed to fetch dai_stream pointer\n");
456 mutex_unlock(lock: &codec->lock);
457 return -EINVAL;
458 }
459
460 bundle = to_gb_bundle(module->dev);
461 ret = gb_pm_runtime_get_sync(bundle);
462 if (ret) {
463 mutex_unlock(lock: &codec->lock);
464 return ret;
465 }
466
467 ret = gb_audio_apbridgea_set_config(connection: data->connection, i2s_port: 0,
468 AUDIO_APBRIDGEA_PCM_FMT_16,
469 AUDIO_APBRIDGEA_PCM_RATE_48000,
470 mclk_freq: 6144000);
471 if (ret) {
472 dev_err_ratelimited(dai->dev, "%d: Error during set_config\n",
473 ret);
474 gb_pm_runtime_put_noidle(bundle);
475 mutex_unlock(lock: &codec->lock);
476 return ret;
477 }
478
479 gb_pm_runtime_put_noidle(bundle);
480
481 if (substream->stream == SNDRV_PCM_STREAM_PLAYBACK)
482 sig_bits = dai->driver->playback.sig_bits;
483 else
484 sig_bits = dai->driver->capture.sig_bits;
485
486 params->state = GBAUDIO_CODEC_HWPARAMS;
487 params->format = format;
488 params->rate = rate;
489 params->channels = channels;
490 params->sig_bits = sig_bits;
491
492 mutex_unlock(lock: &codec->lock);
493 return 0;
494}
495
496static int gbcodec_prepare(struct snd_pcm_substream *substream,
497 struct snd_soc_dai *dai)
498{
499 int ret;
500 struct gbaudio_module_info *module = NULL, *iter;
501 struct gbaudio_data_connection *data;
502 struct gb_bundle *bundle;
503 struct gbaudio_codec_info *codec = dev_get_drvdata(dev: dai->dev);
504 struct gbaudio_stream_params *params;
505
506 mutex_lock(&codec->lock);
507
508 if (list_empty(head: &codec->module_list)) {
509 dev_err(codec->dev, "No codec module available\n");
510 mutex_unlock(lock: &codec->lock);
511 return -ENODEV;
512 }
513
514 list_for_each_entry(iter, &codec->module_list, list) {
515 /* find the dai */
516 data = find_data(module: iter, id: dai->id);
517 if (data) {
518 module = iter;
519 break;
520 }
521 }
522 if (!data) {
523 dev_err(dai->dev, "DATA connection missing\n");
524 mutex_unlock(lock: &codec->lock);
525 return -ENODEV;
526 }
527
528 params = find_dai_stream_params(codec, id: dai->id, stream: substream->stream);
529 if (!params) {
530 dev_err(codec->dev, "Failed to fetch dai_stream pointer\n");
531 mutex_unlock(lock: &codec->lock);
532 return -EINVAL;
533 }
534
535 bundle = to_gb_bundle(module->dev);
536 ret = gb_pm_runtime_get_sync(bundle);
537 if (ret) {
538 mutex_unlock(lock: &codec->lock);
539 return ret;
540 }
541
542 switch (substream->stream) {
543 case SNDRV_PCM_STREAM_PLAYBACK:
544 ret = gb_audio_apbridgea_set_tx_data_size(connection: data->connection, i2s_port: 0, size: 192);
545 break;
546 case SNDRV_PCM_STREAM_CAPTURE:
547 ret = gb_audio_apbridgea_set_rx_data_size(connection: data->connection, i2s_port: 0, size: 192);
548 break;
549 }
550 if (ret) {
551 gb_pm_runtime_put_noidle(bundle);
552 mutex_unlock(lock: &codec->lock);
553 dev_err_ratelimited(dai->dev, "set_data_size failed:%d\n", ret);
554 return ret;
555 }
556
557 gb_pm_runtime_put_noidle(bundle);
558
559 params->state = GBAUDIO_CODEC_PREPARE;
560 mutex_unlock(lock: &codec->lock);
561 return 0;
562}
563
564static int gbcodec_mute_stream(struct snd_soc_dai *dai, int mute, int stream)
565{
566 int ret;
567 struct gbaudio_data_connection *data;
568 struct gbaudio_module_info *module = NULL, *iter;
569 struct gb_bundle *bundle;
570 struct gbaudio_codec_info *codec = dev_get_drvdata(dev: dai->dev);
571 struct gbaudio_stream_params *params;
572
573 dev_dbg(dai->dev, "Mute:%d, Direction:%s\n", mute,
574 stream ? "CAPTURE" : "PLAYBACK");
575
576 mutex_lock(&codec->lock);
577
578 params = find_dai_stream_params(codec, id: dai->id, stream);
579 if (!params) {
580 dev_err(codec->dev, "Failed to fetch dai_stream pointer\n");
581 mutex_unlock(lock: &codec->lock);
582 return -EINVAL;
583 }
584
585 if (list_empty(head: &codec->module_list)) {
586 dev_err(codec->dev, "No codec module available\n");
587 if (mute) {
588 params->state = GBAUDIO_CODEC_STOP;
589 ret = 0;
590 } else {
591 ret = -ENODEV;
592 }
593 mutex_unlock(lock: &codec->lock);
594 return ret;
595 }
596
597 list_for_each_entry(iter, &codec->module_list, list) {
598 /* find the dai */
599 data = find_data(module: iter, id: dai->id);
600 if (data) {
601 module = iter;
602 break;
603 }
604 }
605 if (!data) {
606 dev_err(dai->dev, "%s DATA connection missing\n",
607 dai->name);
608 mutex_unlock(lock: &codec->lock);
609 return -ENODEV;
610 }
611
612 bundle = to_gb_bundle(module->dev);
613 ret = gb_pm_runtime_get_sync(bundle);
614 if (ret) {
615 mutex_unlock(lock: &codec->lock);
616 return ret;
617 }
618
619 if (!mute && !stream) {/* start playback */
620 ret = gb_audio_apbridgea_prepare_tx(connection: data->connection, i2s_port: 0);
621 if (!ret)
622 ret = gb_audio_apbridgea_start_tx(connection: data->connection, i2s_port: 0, timestamp: 0);
623 params->state = GBAUDIO_CODEC_START;
624 } else if (!mute && stream) {/* start capture */
625 ret = gb_audio_apbridgea_prepare_rx(connection: data->connection, i2s_port: 0);
626 if (!ret)
627 ret = gb_audio_apbridgea_start_rx(connection: data->connection, i2s_port: 0);
628 params->state = GBAUDIO_CODEC_START;
629 } else if (mute && !stream) {/* stop playback */
630 ret = gb_audio_apbridgea_stop_tx(connection: data->connection, i2s_port: 0);
631 if (!ret)
632 ret = gb_audio_apbridgea_shutdown_tx(connection: data->connection, i2s_port: 0);
633 params->state = GBAUDIO_CODEC_STOP;
634 } else if (mute && stream) {/* stop capture */
635 ret = gb_audio_apbridgea_stop_rx(connection: data->connection, i2s_port: 0);
636 if (!ret)
637 ret = gb_audio_apbridgea_shutdown_rx(connection: data->connection, i2s_port: 0);
638 params->state = GBAUDIO_CODEC_STOP;
639 } else {
640 ret = -EINVAL;
641 }
642
643 if (ret)
644 dev_err_ratelimited(dai->dev,
645 "%s:Error during %s %s stream:%d\n",
646 module->name, mute ? "Mute" : "Unmute",
647 stream ? "Capture" : "Playback", ret);
648
649 gb_pm_runtime_put_noidle(bundle);
650 mutex_unlock(lock: &codec->lock);
651 return ret;
652}
653
654static const struct snd_soc_dai_ops gbcodec_dai_ops = {
655 .startup = gbcodec_startup,
656 .shutdown = gbcodec_shutdown,
657 .hw_params = gbcodec_hw_params,
658 .prepare = gbcodec_prepare,
659 .mute_stream = gbcodec_mute_stream,
660};
661
662static struct snd_soc_dai_driver gbaudio_dai[] = {
663 {
664 .name = "apb-i2s0",
665 .id = 0,
666 .playback = {
667 .stream_name = "I2S 0 Playback",
668 .rates = SNDRV_PCM_RATE_48000,
669 .formats = SNDRV_PCM_FMTBIT_S16_LE,
670 .rate_max = 48000,
671 .rate_min = 48000,
672 .channels_min = 1,
673 .channels_max = 2,
674 .sig_bits = 16,
675 },
676 .capture = {
677 .stream_name = "I2S 0 Capture",
678 .rates = SNDRV_PCM_RATE_48000,
679 .formats = SNDRV_PCM_FMTBIT_S16_LE,
680 .rate_max = 48000,
681 .rate_min = 48000,
682 .channels_min = 1,
683 .channels_max = 2,
684 .sig_bits = 16,
685 },
686 .ops = &gbcodec_dai_ops,
687 },
688};
689
690static int gbaudio_init_jack(struct gbaudio_module_info *module,
691 struct snd_soc_card *card)
692{
693 int ret;
694 struct gbaudio_jack *jack, *n;
695 struct snd_soc_jack_pin *headset, *button;
696
697 if (!module->jack_mask)
698 return 0;
699
700 snprintf(buf: module->jack_name, NAME_SIZE, fmt: "GB %d Headset Jack",
701 module->dev_id);
702
703 headset = devm_kzalloc(dev: module->dev, size: sizeof(*headset), GFP_KERNEL);
704 if (!headset)
705 return -ENOMEM;
706
707 headset->pin = module->jack_name;
708 headset->mask = module->jack_mask;
709 ret = snd_soc_card_jack_new_pins(card, id: module->jack_name,
710 type: module->jack_mask,
711 jack: &module->headset.jack, pins: headset, num_pins: 1);
712 if (ret) {
713 dev_err(module->dev, "Failed to create new jack\n");
714 return ret;
715 }
716
717 /* Add to module's jack list */
718 list_add(new: &module->headset.list, head: &module->jack_list);
719
720 if (!module->button_mask)
721 return 0;
722
723 snprintf(buf: module->button_name, NAME_SIZE, fmt: "GB %d Button Jack",
724 module->dev_id);
725 button = devm_kzalloc(dev: module->dev, size: sizeof(*button), GFP_KERNEL);
726 if (!button) {
727 ret = -ENOMEM;
728 goto free_jacks;
729 }
730
731 button->pin = module->button_name;
732 button->mask = module->button_mask;
733 ret = snd_soc_card_jack_new_pins(card, id: module->button_name,
734 type: module->button_mask,
735 jack: &module->button.jack,
736 pins: button, num_pins: 1);
737 if (ret) {
738 dev_err(module->dev, "Failed to create button jack\n");
739 goto free_jacks;
740 }
741
742 /* Add to module's jack list */
743 list_add(new: &module->button.list, head: &module->jack_list);
744
745 /*
746 * Currently, max 4 buttons are supported with following key mapping
747 * BTN_0 = KEY_MEDIA
748 * BTN_1 = KEY_VOICECOMMAND
749 * BTN_2 = KEY_VOLUMEUP
750 * BTN_3 = KEY_VOLUMEDOWN
751 */
752
753 if (module->button_mask & SND_JACK_BTN_0) {
754 ret = snd_jack_set_key(jack: module->button.jack.jack, type: SND_JACK_BTN_0,
755 KEY_MEDIA);
756 if (ret) {
757 dev_err(module->dev, "Failed to set BTN_0\n");
758 goto free_jacks;
759 }
760 }
761
762 if (module->button_mask & SND_JACK_BTN_1) {
763 ret = snd_jack_set_key(jack: module->button.jack.jack, type: SND_JACK_BTN_1,
764 KEY_VOICECOMMAND);
765 if (ret) {
766 dev_err(module->dev, "Failed to set BTN_1\n");
767 goto free_jacks;
768 }
769 }
770
771 if (module->button_mask & SND_JACK_BTN_2) {
772 ret = snd_jack_set_key(jack: module->button.jack.jack, type: SND_JACK_BTN_2,
773 KEY_VOLUMEUP);
774 if (ret) {
775 dev_err(module->dev, "Failed to set BTN_2\n");
776 goto free_jacks;
777 }
778 }
779
780 if (module->button_mask & SND_JACK_BTN_3) {
781 ret = snd_jack_set_key(jack: module->button.jack.jack, type: SND_JACK_BTN_3,
782 KEY_VOLUMEDOWN);
783 if (ret) {
784 dev_err(module->dev, "Failed to set BTN_0\n");
785 goto free_jacks;
786 }
787 }
788
789 /* FIXME
790 * verify if this is really required
791 set_bit(INPUT_PROP_NO_DUMMY_RELEASE,
792 module->button.jack.jack->input_dev->propbit);
793 */
794
795 return 0;
796
797free_jacks:
798 list_for_each_entry_safe(jack, n, &module->jack_list, list) {
799 snd_device_free(card: card->snd_card, device_data: jack->jack.jack);
800 list_del(entry: &jack->list);
801 }
802
803 return ret;
804}
805
806int gbaudio_register_module(struct gbaudio_module_info *module)
807{
808 int ret;
809 struct snd_soc_component *comp;
810 struct gbaudio_jack *jack = NULL;
811
812 if (!gbcodec) {
813 dev_err(module->dev, "GB Codec not yet probed\n");
814 return -EAGAIN;
815 }
816
817 comp = gbcodec->component;
818
819 mutex_lock(&gbcodec->register_mutex);
820
821 if (module->num_dais) {
822 dev_err(gbcodec->dev,
823 "%d:DAIs not supported via gbcodec driver\n",
824 module->num_dais);
825 mutex_unlock(lock: &gbcodec->register_mutex);
826 return -EINVAL;
827 }
828
829 ret = gbaudio_init_jack(module, card: comp->card);
830 if (ret) {
831 mutex_unlock(lock: &gbcodec->register_mutex);
832 return ret;
833 }
834
835 if (module->dapm_widgets)
836 snd_soc_dapm_new_controls(dapm: &comp->dapm, widget: module->dapm_widgets,
837 num: module->num_dapm_widgets);
838 if (module->controls)
839 snd_soc_add_component_controls(component: comp, controls: module->controls,
840 num_controls: module->num_controls);
841 if (module->dapm_routes)
842 snd_soc_dapm_add_routes(dapm: &comp->dapm, route: module->dapm_routes,
843 num: module->num_dapm_routes);
844
845 /* card already instantiated, create widgets here only */
846 if (comp->card->instantiated) {
847 gbaudio_dapm_link_component_dai_widgets(card: comp->card, dapm: &comp->dapm);
848#ifdef CONFIG_SND_JACK
849 /*
850 * register jack devices for this module
851 * from codec->jack_list
852 */
853 list_for_each_entry(jack, &module->jack_list, list) {
854 snd_device_register(card: comp->card->snd_card,
855 device_data: jack->jack.jack);
856 }
857#endif
858 }
859
860 mutex_lock(&gbcodec->lock);
861 list_add(new: &module->list, head: &gbcodec->module_list);
862 mutex_unlock(lock: &gbcodec->lock);
863
864 if (comp->card->instantiated)
865 ret = snd_soc_dapm_new_widgets(card: comp->card);
866 dev_dbg(comp->dev, "Registered %s module\n", module->name);
867
868 mutex_unlock(lock: &gbcodec->register_mutex);
869 return ret;
870}
871EXPORT_SYMBOL(gbaudio_register_module);
872
873static void gbaudio_codec_clean_data_tx(struct gbaudio_data_connection *data)
874{
875 u16 i2s_port, cportid;
876 int ret;
877
878 if (list_is_singular(head: &gbcodec->module_list)) {
879 ret = gb_audio_apbridgea_stop_tx(connection: data->connection, i2s_port: 0);
880 if (ret)
881 return;
882 ret = gb_audio_apbridgea_shutdown_tx(connection: data->connection, i2s_port: 0);
883 if (ret)
884 return;
885 }
886 i2s_port = 0; /* fixed for now */
887 cportid = data->connection->hd_cport_id;
888 ret = gb_audio_apbridgea_unregister_cport(connection: data->connection,
889 i2s_port, cportid,
890 AUDIO_APBRIDGEA_DIRECTION_TX);
891 data->state[0] = GBAUDIO_CODEC_SHUTDOWN;
892}
893
894static void gbaudio_codec_clean_data_rx(struct gbaudio_data_connection *data)
895{
896 u16 i2s_port, cportid;
897 int ret;
898
899 if (list_is_singular(head: &gbcodec->module_list)) {
900 ret = gb_audio_apbridgea_stop_rx(connection: data->connection, i2s_port: 0);
901 if (ret)
902 return;
903 ret = gb_audio_apbridgea_shutdown_rx(connection: data->connection, i2s_port: 0);
904 if (ret)
905 return;
906 }
907 i2s_port = 0; /* fixed for now */
908 cportid = data->connection->hd_cport_id;
909 ret = gb_audio_apbridgea_unregister_cport(connection: data->connection,
910 i2s_port, cportid,
911 AUDIO_APBRIDGEA_DIRECTION_RX);
912 data->state[1] = GBAUDIO_CODEC_SHUTDOWN;
913}
914
915static void gbaudio_codec_cleanup(struct gbaudio_module_info *module)
916{
917 struct gbaudio_data_connection *data;
918 int pb_state, cap_state;
919
920 dev_dbg(gbcodec->dev, "%s: removed, cleanup APBridge\n", module->name);
921 list_for_each_entry(data, &module->data_list, list) {
922 pb_state = data->state[0];
923 cap_state = data->state[1];
924
925 if (pb_state > GBAUDIO_CODEC_SHUTDOWN)
926 gbaudio_codec_clean_data_tx(data);
927
928 if (cap_state > GBAUDIO_CODEC_SHUTDOWN)
929 gbaudio_codec_clean_data_rx(data);
930 }
931}
932
933void gbaudio_unregister_module(struct gbaudio_module_info *module)
934{
935 struct snd_soc_component *comp = gbcodec->component;
936 struct gbaudio_jack *jack, *n;
937 int mask;
938
939 dev_dbg(comp->dev, "Unregister %s module\n", module->name);
940
941 mutex_lock(&gbcodec->register_mutex);
942 mutex_lock(&gbcodec->lock);
943 gbaudio_codec_cleanup(module);
944 list_del(entry: &module->list);
945 dev_dbg(comp->dev, "Process Unregister %s module\n", module->name);
946 mutex_unlock(lock: &gbcodec->lock);
947
948#ifdef CONFIG_SND_JACK
949 /* free jack devices for this module jack_list */
950 list_for_each_entry_safe(jack, n, &module->jack_list, list) {
951 if (jack == &module->headset)
952 mask = GBCODEC_JACK_MASK;
953 else if (jack == &module->button)
954 mask = GBCODEC_JACK_BUTTON_MASK;
955 else
956 mask = 0;
957 if (mask) {
958 dev_dbg(module->dev, "Report %s removal\n",
959 jack->jack.jack->id);
960 snd_soc_jack_report(jack: &jack->jack, status: 0, mask);
961 snd_device_free(card: comp->card->snd_card,
962 device_data: jack->jack.jack);
963 list_del(entry: &jack->list);
964 }
965 }
966#endif
967
968 if (module->dapm_routes) {
969 dev_dbg(comp->dev, "Removing %d routes\n",
970 module->num_dapm_routes);
971 snd_soc_dapm_del_routes(dapm: &comp->dapm, route: module->dapm_routes,
972 num: module->num_dapm_routes);
973 }
974 if (module->controls) {
975 dev_dbg(comp->dev, "Removing %d controls\n",
976 module->num_controls);
977 /* release control semaphore */
978 gbaudio_remove_component_controls(component: comp, controls: module->controls,
979 num_controls: module->num_controls);
980 }
981 if (module->dapm_widgets) {
982 dev_dbg(comp->dev, "Removing %d widgets\n",
983 module->num_dapm_widgets);
984 gbaudio_dapm_free_controls(dapm: &comp->dapm, widget: module->dapm_widgets,
985 num: module->num_dapm_widgets);
986 }
987
988 dev_dbg(comp->dev, "Unregistered %s module\n", module->name);
989
990 mutex_unlock(lock: &gbcodec->register_mutex);
991}
992EXPORT_SYMBOL(gbaudio_unregister_module);
993
994/*
995 * component driver ops
996 */
997static int gbcodec_probe(struct snd_soc_component *comp)
998{
999 int i;
1000 struct gbaudio_codec_info *info;
1001 struct gbaudio_codec_dai *dai;
1002
1003 info = devm_kzalloc(dev: comp->dev, size: sizeof(*info), GFP_KERNEL);
1004 if (!info)
1005 return -ENOMEM;
1006
1007 info->dev = comp->dev;
1008 INIT_LIST_HEAD(list: &info->module_list);
1009 mutex_init(&info->lock);
1010 mutex_init(&info->register_mutex);
1011 INIT_LIST_HEAD(list: &info->dai_list);
1012
1013 /* init dai_list used to maintain runtime stream info */
1014 for (i = 0; i < ARRAY_SIZE(gbaudio_dai); i++) {
1015 dai = devm_kzalloc(dev: comp->dev, size: sizeof(*dai), GFP_KERNEL);
1016 if (!dai)
1017 return -ENOMEM;
1018 dai->id = gbaudio_dai[i].id;
1019 list_add(new: &dai->list, head: &info->dai_list);
1020 }
1021
1022 info->component = comp;
1023 snd_soc_component_set_drvdata(c: comp, data: info);
1024 gbcodec = info;
1025
1026 device_init_wakeup(dev: comp->dev, enable: 1);
1027 return 0;
1028}
1029
1030static int gbcodec_write(struct snd_soc_component *comp, unsigned int reg,
1031 unsigned int value)
1032{
1033 return 0;
1034}
1035
1036static unsigned int gbcodec_read(struct snd_soc_component *comp,
1037 unsigned int reg)
1038{
1039 return 0;
1040}
1041
1042static const struct snd_soc_component_driver soc_codec_dev_gbaudio = {
1043 .probe = gbcodec_probe,
1044 .read = gbcodec_read,
1045 .write = gbcodec_write,
1046};
1047
1048#ifdef CONFIG_PM
1049static int gbaudio_codec_suspend(struct device *dev)
1050{
1051 dev_dbg(dev, "%s: suspend\n", __func__);
1052 return 0;
1053}
1054
1055static int gbaudio_codec_resume(struct device *dev)
1056{
1057 dev_dbg(dev, "%s: resume\n", __func__);
1058 return 0;
1059}
1060
1061static const struct dev_pm_ops gbaudio_codec_pm_ops = {
1062 .suspend = gbaudio_codec_suspend,
1063 .resume = gbaudio_codec_resume,
1064};
1065#endif
1066
1067static int gbaudio_codec_probe(struct platform_device *pdev)
1068{
1069 return devm_snd_soc_register_component(dev: &pdev->dev,
1070 component_driver: &soc_codec_dev_gbaudio,
1071 dai_drv: gbaudio_dai, ARRAY_SIZE(gbaudio_dai));
1072}
1073
1074static const struct of_device_id greybus_asoc_machine_of_match[] = {
1075 { .compatible = "toshiba,apb-dummy-codec", },
1076 {},
1077};
1078
1079static struct platform_driver gbaudio_codec_driver = {
1080 .driver = {
1081 .name = "apb-dummy-codec",
1082#ifdef CONFIG_PM
1083 .pm = &gbaudio_codec_pm_ops,
1084#endif
1085 .of_match_table = greybus_asoc_machine_of_match,
1086 },
1087 .probe = gbaudio_codec_probe,
1088};
1089module_platform_driver(gbaudio_codec_driver);
1090
1091MODULE_DESCRIPTION("APBridge ALSA SoC dummy codec driver");
1092MODULE_AUTHOR("Vaibhav Agarwal <vaibhav.agarwal@linaro.org>");
1093MODULE_LICENSE("GPL v2");
1094MODULE_ALIAS("platform:apb-dummy-codec");
1095

source code of linux/drivers/staging/greybus/audio_codec.c