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