1 | // SPDX-License-Identifier: GPL-2.0+ |
2 | /* |
3 | * u_audio.c -- interface to USB gadget "ALSA sound card" utilities |
4 | * |
5 | * Copyright (C) 2016 |
6 | * Author: Ruslan Bilovol <ruslan.bilovol@gmail.com> |
7 | * |
8 | * Sound card implementation was cut-and-pasted with changes |
9 | * from f_uac2.c and has: |
10 | * Copyright (C) 2011 |
11 | * Yadwinder Singh (yadi.brar01@gmail.com) |
12 | * Jaswinder Singh (jaswinder.singh@linaro.org) |
13 | */ |
14 | |
15 | #include <linux/kernel.h> |
16 | #include <linux/module.h> |
17 | #include <sound/core.h> |
18 | #include <sound/pcm.h> |
19 | #include <sound/pcm_params.h> |
20 | #include <sound/control.h> |
21 | #include <sound/tlv.h> |
22 | #include <linux/usb/audio.h> |
23 | |
24 | #include "u_audio.h" |
25 | |
26 | #define BUFF_SIZE_MAX (PAGE_SIZE * 16) |
27 | #define PRD_SIZE_MAX PAGE_SIZE |
28 | #define MIN_PERIODS 4 |
29 | |
30 | enum { |
31 | UAC_FBACK_CTRL, |
32 | UAC_P_PITCH_CTRL, |
33 | UAC_MUTE_CTRL, |
34 | UAC_VOLUME_CTRL, |
35 | UAC_RATE_CTRL, |
36 | }; |
37 | |
38 | /* Runtime data params for one stream */ |
39 | struct uac_rtd_params { |
40 | struct snd_uac_chip *uac; /* parent chip */ |
41 | bool ep_enabled; /* if the ep is enabled */ |
42 | |
43 | struct snd_pcm_substream *ss; |
44 | |
45 | /* Ring buffer */ |
46 | ssize_t hw_ptr; |
47 | |
48 | void *rbuf; |
49 | |
50 | unsigned int pitch; /* Stream pitch ratio to 1000000 */ |
51 | unsigned int max_psize; /* MaxPacketSize of endpoint */ |
52 | |
53 | struct usb_request **reqs; |
54 | |
55 | struct usb_request *req_fback; /* Feedback endpoint request */ |
56 | bool fb_ep_enabled; /* if the ep is enabled */ |
57 | |
58 | /* Volume/Mute controls and their state */ |
59 | int fu_id; /* Feature Unit ID */ |
60 | struct snd_kcontrol *snd_kctl_volume; |
61 | struct snd_kcontrol *snd_kctl_mute; |
62 | s16 volume_min, volume_max, volume_res; |
63 | s16 volume; |
64 | int mute; |
65 | |
66 | struct snd_kcontrol *snd_kctl_rate; /* read-only current rate */ |
67 | int srate; /* selected samplerate */ |
68 | int active; /* playback/capture running */ |
69 | |
70 | spinlock_t lock; /* lock for control transfers */ |
71 | |
72 | }; |
73 | |
74 | struct snd_uac_chip { |
75 | struct g_audio *audio_dev; |
76 | |
77 | struct uac_rtd_params p_prm; |
78 | struct uac_rtd_params c_prm; |
79 | |
80 | struct snd_card *card; |
81 | struct snd_pcm *pcm; |
82 | |
83 | /* pre-calculated values for playback iso completion */ |
84 | unsigned long long p_residue_mil; |
85 | unsigned int p_interval; |
86 | unsigned int p_framesize; |
87 | }; |
88 | |
89 | static const struct snd_pcm_hardware uac_pcm_hardware = { |
90 | .info = SNDRV_PCM_INFO_INTERLEAVED | SNDRV_PCM_INFO_BLOCK_TRANSFER |
91 | | SNDRV_PCM_INFO_MMAP | SNDRV_PCM_INFO_MMAP_VALID |
92 | | SNDRV_PCM_INFO_PAUSE | SNDRV_PCM_INFO_RESUME, |
93 | .rates = SNDRV_PCM_RATE_CONTINUOUS, |
94 | .periods_max = BUFF_SIZE_MAX / PRD_SIZE_MAX, |
95 | .buffer_bytes_max = BUFF_SIZE_MAX, |
96 | .period_bytes_max = PRD_SIZE_MAX, |
97 | .periods_min = MIN_PERIODS, |
98 | }; |
99 | |
100 | static void u_audio_set_fback_frequency(enum usb_device_speed speed, |
101 | struct usb_ep *out_ep, |
102 | unsigned long long freq, |
103 | unsigned int pitch, |
104 | void *buf) |
105 | { |
106 | u32 ff = 0; |
107 | const struct usb_endpoint_descriptor *ep_desc; |
108 | |
109 | /* |
110 | * Because the pitch base is 1000000, the final divider here |
111 | * will be 1000 * 1000000 = 1953125 << 9 |
112 | * |
113 | * Instead of dealing with big numbers lets fold this 9 left shift |
114 | */ |
115 | |
116 | if (speed == USB_SPEED_FULL) { |
117 | /* |
118 | * Full-speed feedback endpoints report frequency |
119 | * in samples/frame |
120 | * Format is encoded in Q10.10 left-justified in the 24 bits, |
121 | * so that it has a Q10.14 format. |
122 | * |
123 | * ff = (freq << 14) / 1000 |
124 | */ |
125 | freq <<= 5; |
126 | } else { |
127 | /* |
128 | * High-speed feedback endpoints report frequency |
129 | * in samples/microframe. |
130 | * Format is encoded in Q12.13 fitted into four bytes so that |
131 | * the binary point is located between the second and the third |
132 | * byte fromat (that is Q16.16) |
133 | * |
134 | * ff = (freq << 16) / 8000 |
135 | * |
136 | * Win10 and OSX UAC2 drivers require number of samples per packet |
137 | * in order to honor the feedback value. |
138 | * Linux snd-usb-audio detects the applied bit-shift automatically. |
139 | */ |
140 | ep_desc = out_ep->desc; |
141 | freq <<= 4 + (ep_desc->bInterval - 1); |
142 | } |
143 | |
144 | ff = DIV_ROUND_CLOSEST_ULL((freq * pitch), 1953125); |
145 | |
146 | *(__le32 *)buf = cpu_to_le32(ff); |
147 | } |
148 | |
149 | static void u_audio_iso_complete(struct usb_ep *ep, struct usb_request *req) |
150 | { |
151 | unsigned int pending; |
152 | unsigned int hw_ptr; |
153 | int status = req->status; |
154 | struct snd_pcm_substream *substream; |
155 | struct snd_pcm_runtime *runtime; |
156 | struct uac_rtd_params *prm = req->context; |
157 | struct snd_uac_chip *uac = prm->uac; |
158 | unsigned int frames, p_pktsize; |
159 | unsigned long long pitched_rate_mil, p_pktsize_residue_mil, |
160 | residue_frames_mil, div_result; |
161 | |
162 | /* i/f shutting down */ |
163 | if (!prm->ep_enabled) { |
164 | usb_ep_free_request(ep, req); |
165 | return; |
166 | } |
167 | |
168 | if (req->status == -ESHUTDOWN) |
169 | return; |
170 | |
171 | /* |
172 | * We can't really do much about bad xfers. |
173 | * Afterall, the ISOCH xfers could fail legitimately. |
174 | */ |
175 | if (status) |
176 | pr_debug("%s: iso_complete status(%d) %d/%d\n" , |
177 | __func__, status, req->actual, req->length); |
178 | |
179 | substream = prm->ss; |
180 | |
181 | /* Do nothing if ALSA isn't active */ |
182 | if (!substream) |
183 | goto exit; |
184 | |
185 | snd_pcm_stream_lock(substream); |
186 | |
187 | runtime = substream->runtime; |
188 | if (!runtime || !snd_pcm_running(substream)) { |
189 | snd_pcm_stream_unlock(substream); |
190 | goto exit; |
191 | } |
192 | |
193 | if (substream->stream == SNDRV_PCM_STREAM_PLAYBACK) { |
194 | /* |
195 | * For each IN packet, take the quotient of the current data |
196 | * rate and the endpoint's interval as the base packet size. |
197 | * If there is a residue from this division, add it to the |
198 | * residue accumulator. |
199 | */ |
200 | unsigned long long p_interval_mil = uac->p_interval * 1000000ULL; |
201 | |
202 | pitched_rate_mil = (unsigned long long) prm->srate * prm->pitch; |
203 | div_result = pitched_rate_mil; |
204 | do_div(div_result, uac->p_interval); |
205 | do_div(div_result, 1000000); |
206 | frames = (unsigned int) div_result; |
207 | |
208 | pr_debug("p_srate %d, pitch %d, interval_mil %llu, frames %d\n" , |
209 | prm->srate, prm->pitch, p_interval_mil, frames); |
210 | |
211 | p_pktsize = min_t(unsigned int, |
212 | uac->p_framesize * frames, |
213 | ep->maxpacket); |
214 | |
215 | if (p_pktsize < ep->maxpacket) { |
216 | residue_frames_mil = pitched_rate_mil - frames * p_interval_mil; |
217 | p_pktsize_residue_mil = uac->p_framesize * residue_frames_mil; |
218 | } else |
219 | p_pktsize_residue_mil = 0; |
220 | |
221 | req->length = p_pktsize; |
222 | uac->p_residue_mil += p_pktsize_residue_mil; |
223 | |
224 | /* |
225 | * Whenever there are more bytes in the accumulator p_residue_mil than we |
226 | * need to add one more sample frame, increase this packet's |
227 | * size and decrease the accumulator. |
228 | */ |
229 | div_result = uac->p_residue_mil; |
230 | do_div(div_result, uac->p_interval); |
231 | do_div(div_result, 1000000); |
232 | if ((unsigned int) div_result >= uac->p_framesize) { |
233 | req->length += uac->p_framesize; |
234 | uac->p_residue_mil -= uac->p_framesize * p_interval_mil; |
235 | pr_debug("increased req length to %d\n" , req->length); |
236 | } |
237 | pr_debug("remains uac->p_residue_mil %llu\n" , uac->p_residue_mil); |
238 | |
239 | req->actual = req->length; |
240 | } |
241 | |
242 | hw_ptr = prm->hw_ptr; |
243 | |
244 | /* Pack USB load in ALSA ring buffer */ |
245 | pending = runtime->dma_bytes - hw_ptr; |
246 | |
247 | if (substream->stream == SNDRV_PCM_STREAM_PLAYBACK) { |
248 | if (unlikely(pending < req->actual)) { |
249 | memcpy(req->buf, runtime->dma_area + hw_ptr, pending); |
250 | memcpy(req->buf + pending, runtime->dma_area, |
251 | req->actual - pending); |
252 | } else { |
253 | memcpy(req->buf, runtime->dma_area + hw_ptr, |
254 | req->actual); |
255 | } |
256 | } else { |
257 | if (unlikely(pending < req->actual)) { |
258 | memcpy(runtime->dma_area + hw_ptr, req->buf, pending); |
259 | memcpy(runtime->dma_area, req->buf + pending, |
260 | req->actual - pending); |
261 | } else { |
262 | memcpy(runtime->dma_area + hw_ptr, req->buf, |
263 | req->actual); |
264 | } |
265 | } |
266 | |
267 | /* update hw_ptr after data is copied to memory */ |
268 | prm->hw_ptr = (hw_ptr + req->actual) % runtime->dma_bytes; |
269 | hw_ptr = prm->hw_ptr; |
270 | snd_pcm_stream_unlock(substream); |
271 | |
272 | if ((hw_ptr % snd_pcm_lib_period_bytes(substream)) < req->actual) |
273 | snd_pcm_period_elapsed(substream); |
274 | |
275 | exit: |
276 | if (usb_ep_queue(ep, req, GFP_ATOMIC)) |
277 | dev_err(uac->card->dev, "%d Error!\n" , __LINE__); |
278 | } |
279 | |
280 | static void u_audio_iso_fback_complete(struct usb_ep *ep, |
281 | struct usb_request *req) |
282 | { |
283 | struct uac_rtd_params *prm = req->context; |
284 | struct snd_uac_chip *uac = prm->uac; |
285 | struct g_audio *audio_dev = uac->audio_dev; |
286 | int status = req->status; |
287 | |
288 | /* i/f shutting down */ |
289 | if (!prm->fb_ep_enabled) { |
290 | kfree(objp: req->buf); |
291 | usb_ep_free_request(ep, req); |
292 | return; |
293 | } |
294 | |
295 | if (req->status == -ESHUTDOWN) |
296 | return; |
297 | |
298 | /* |
299 | * We can't really do much about bad xfers. |
300 | * Afterall, the ISOCH xfers could fail legitimately. |
301 | */ |
302 | if (status) |
303 | pr_debug("%s: iso_complete status(%d) %d/%d\n" , |
304 | __func__, status, req->actual, req->length); |
305 | |
306 | u_audio_set_fback_frequency(speed: audio_dev->gadget->speed, out_ep: audio_dev->out_ep, |
307 | freq: prm->srate, pitch: prm->pitch, |
308 | buf: req->buf); |
309 | |
310 | if (usb_ep_queue(ep, req, GFP_ATOMIC)) |
311 | dev_err(uac->card->dev, "%d Error!\n" , __LINE__); |
312 | } |
313 | |
314 | static int uac_pcm_trigger(struct snd_pcm_substream *substream, int cmd) |
315 | { |
316 | struct snd_uac_chip *uac = snd_pcm_substream_chip(substream); |
317 | struct uac_rtd_params *prm; |
318 | struct g_audio *audio_dev; |
319 | struct uac_params *params; |
320 | int err = 0; |
321 | |
322 | audio_dev = uac->audio_dev; |
323 | params = &audio_dev->params; |
324 | |
325 | if (substream->stream == SNDRV_PCM_STREAM_PLAYBACK) |
326 | prm = &uac->p_prm; |
327 | else |
328 | prm = &uac->c_prm; |
329 | |
330 | /* Reset */ |
331 | prm->hw_ptr = 0; |
332 | |
333 | switch (cmd) { |
334 | case SNDRV_PCM_TRIGGER_START: |
335 | case SNDRV_PCM_TRIGGER_RESUME: |
336 | prm->ss = substream; |
337 | break; |
338 | case SNDRV_PCM_TRIGGER_STOP: |
339 | case SNDRV_PCM_TRIGGER_SUSPEND: |
340 | prm->ss = NULL; |
341 | break; |
342 | default: |
343 | err = -EINVAL; |
344 | } |
345 | |
346 | /* Clear buffer after Play stops */ |
347 | if (substream->stream == SNDRV_PCM_STREAM_PLAYBACK && !prm->ss) |
348 | memset(prm->rbuf, 0, prm->max_psize * params->req_number); |
349 | |
350 | return err; |
351 | } |
352 | |
353 | static snd_pcm_uframes_t uac_pcm_pointer(struct snd_pcm_substream *substream) |
354 | { |
355 | struct snd_uac_chip *uac = snd_pcm_substream_chip(substream); |
356 | struct uac_rtd_params *prm; |
357 | |
358 | if (substream->stream == SNDRV_PCM_STREAM_PLAYBACK) |
359 | prm = &uac->p_prm; |
360 | else |
361 | prm = &uac->c_prm; |
362 | |
363 | return bytes_to_frames(runtime: substream->runtime, size: prm->hw_ptr); |
364 | } |
365 | |
366 | static u64 uac_ssize_to_fmt(int ssize) |
367 | { |
368 | u64 ret; |
369 | |
370 | switch (ssize) { |
371 | case 3: |
372 | ret = SNDRV_PCM_FMTBIT_S24_3LE; |
373 | break; |
374 | case 4: |
375 | ret = SNDRV_PCM_FMTBIT_S32_LE; |
376 | break; |
377 | default: |
378 | ret = SNDRV_PCM_FMTBIT_S16_LE; |
379 | break; |
380 | } |
381 | |
382 | return ret; |
383 | } |
384 | |
385 | static int uac_pcm_open(struct snd_pcm_substream *substream) |
386 | { |
387 | struct snd_uac_chip *uac = snd_pcm_substream_chip(substream); |
388 | struct snd_pcm_runtime *runtime = substream->runtime; |
389 | struct g_audio *audio_dev; |
390 | struct uac_params *params; |
391 | struct uac_rtd_params *prm; |
392 | int p_ssize, c_ssize; |
393 | int p_chmask, c_chmask; |
394 | |
395 | audio_dev = uac->audio_dev; |
396 | params = &audio_dev->params; |
397 | p_ssize = params->p_ssize; |
398 | c_ssize = params->c_ssize; |
399 | p_chmask = params->p_chmask; |
400 | c_chmask = params->c_chmask; |
401 | uac->p_residue_mil = 0; |
402 | |
403 | runtime->hw = uac_pcm_hardware; |
404 | |
405 | if (substream->stream == SNDRV_PCM_STREAM_PLAYBACK) { |
406 | runtime->hw.formats = uac_ssize_to_fmt(ssize: p_ssize); |
407 | runtime->hw.channels_min = num_channels(chanmask: p_chmask); |
408 | prm = &uac->p_prm; |
409 | } else { |
410 | runtime->hw.formats = uac_ssize_to_fmt(ssize: c_ssize); |
411 | runtime->hw.channels_min = num_channels(chanmask: c_chmask); |
412 | prm = &uac->c_prm; |
413 | } |
414 | |
415 | runtime->hw.period_bytes_min = 2 * prm->max_psize |
416 | / runtime->hw.periods_min; |
417 | runtime->hw.rate_min = prm->srate; |
418 | runtime->hw.rate_max = runtime->hw.rate_min; |
419 | runtime->hw.channels_max = runtime->hw.channels_min; |
420 | |
421 | snd_pcm_hw_constraint_integer(runtime, SNDRV_PCM_HW_PARAM_PERIODS); |
422 | |
423 | return 0; |
424 | } |
425 | |
426 | /* ALSA cries without these function pointers */ |
427 | static int uac_pcm_null(struct snd_pcm_substream *substream) |
428 | { |
429 | return 0; |
430 | } |
431 | |
432 | static const struct snd_pcm_ops uac_pcm_ops = { |
433 | .open = uac_pcm_open, |
434 | .close = uac_pcm_null, |
435 | .trigger = uac_pcm_trigger, |
436 | .pointer = uac_pcm_pointer, |
437 | .prepare = uac_pcm_null, |
438 | }; |
439 | |
440 | static inline void free_ep(struct uac_rtd_params *prm, struct usb_ep *ep) |
441 | { |
442 | struct snd_uac_chip *uac = prm->uac; |
443 | struct g_audio *audio_dev; |
444 | struct uac_params *params; |
445 | int i; |
446 | |
447 | if (!prm->ep_enabled) |
448 | return; |
449 | |
450 | audio_dev = uac->audio_dev; |
451 | params = &audio_dev->params; |
452 | |
453 | for (i = 0; i < params->req_number; i++) { |
454 | if (prm->reqs[i]) { |
455 | if (usb_ep_dequeue(ep, req: prm->reqs[i])) |
456 | usb_ep_free_request(ep, req: prm->reqs[i]); |
457 | /* |
458 | * If usb_ep_dequeue() cannot successfully dequeue the |
459 | * request, the request will be freed by the completion |
460 | * callback. |
461 | */ |
462 | |
463 | prm->reqs[i] = NULL; |
464 | } |
465 | } |
466 | |
467 | prm->ep_enabled = false; |
468 | |
469 | if (usb_ep_disable(ep)) |
470 | dev_err(uac->card->dev, "%s:%d Error!\n" , __func__, __LINE__); |
471 | } |
472 | |
473 | static inline void free_ep_fback(struct uac_rtd_params *prm, struct usb_ep *ep) |
474 | { |
475 | struct snd_uac_chip *uac = prm->uac; |
476 | |
477 | if (!prm->fb_ep_enabled) |
478 | return; |
479 | |
480 | if (prm->req_fback) { |
481 | if (usb_ep_dequeue(ep, req: prm->req_fback)) { |
482 | kfree(objp: prm->req_fback->buf); |
483 | usb_ep_free_request(ep, req: prm->req_fback); |
484 | } |
485 | prm->req_fback = NULL; |
486 | } |
487 | |
488 | prm->fb_ep_enabled = false; |
489 | |
490 | if (usb_ep_disable(ep)) |
491 | dev_err(uac->card->dev, "%s:%d Error!\n" , __func__, __LINE__); |
492 | } |
493 | |
494 | static void set_active(struct uac_rtd_params *prm, bool active) |
495 | { |
496 | // notifying through the Rate ctrl |
497 | struct snd_kcontrol *kctl = prm->snd_kctl_rate; |
498 | unsigned long flags; |
499 | |
500 | spin_lock_irqsave(&prm->lock, flags); |
501 | if (prm->active != active) { |
502 | prm->active = active; |
503 | snd_ctl_notify(card: prm->uac->card, SNDRV_CTL_EVENT_MASK_VALUE, |
504 | id: &kctl->id); |
505 | } |
506 | spin_unlock_irqrestore(lock: &prm->lock, flags); |
507 | } |
508 | |
509 | int u_audio_set_capture_srate(struct g_audio *audio_dev, int srate) |
510 | { |
511 | struct uac_params *params = &audio_dev->params; |
512 | struct snd_uac_chip *uac = audio_dev->uac; |
513 | struct uac_rtd_params *prm; |
514 | int i; |
515 | unsigned long flags; |
516 | |
517 | dev_dbg(&audio_dev->gadget->dev, "%s: srate %d\n" , __func__, srate); |
518 | prm = &uac->c_prm; |
519 | for (i = 0; i < UAC_MAX_RATES; i++) { |
520 | if (params->c_srates[i] == srate) { |
521 | spin_lock_irqsave(&prm->lock, flags); |
522 | prm->srate = srate; |
523 | spin_unlock_irqrestore(lock: &prm->lock, flags); |
524 | return 0; |
525 | } |
526 | if (params->c_srates[i] == 0) |
527 | break; |
528 | } |
529 | |
530 | return -EINVAL; |
531 | } |
532 | EXPORT_SYMBOL_GPL(u_audio_set_capture_srate); |
533 | |
534 | int u_audio_get_capture_srate(struct g_audio *audio_dev, u32 *val) |
535 | { |
536 | struct snd_uac_chip *uac = audio_dev->uac; |
537 | struct uac_rtd_params *prm; |
538 | unsigned long flags; |
539 | |
540 | prm = &uac->c_prm; |
541 | spin_lock_irqsave(&prm->lock, flags); |
542 | *val = prm->srate; |
543 | spin_unlock_irqrestore(lock: &prm->lock, flags); |
544 | return 0; |
545 | } |
546 | EXPORT_SYMBOL_GPL(u_audio_get_capture_srate); |
547 | |
548 | int u_audio_set_playback_srate(struct g_audio *audio_dev, int srate) |
549 | { |
550 | struct uac_params *params = &audio_dev->params; |
551 | struct snd_uac_chip *uac = audio_dev->uac; |
552 | struct uac_rtd_params *prm; |
553 | int i; |
554 | unsigned long flags; |
555 | |
556 | dev_dbg(&audio_dev->gadget->dev, "%s: srate %d\n" , __func__, srate); |
557 | prm = &uac->p_prm; |
558 | for (i = 0; i < UAC_MAX_RATES; i++) { |
559 | if (params->p_srates[i] == srate) { |
560 | spin_lock_irqsave(&prm->lock, flags); |
561 | prm->srate = srate; |
562 | spin_unlock_irqrestore(lock: &prm->lock, flags); |
563 | return 0; |
564 | } |
565 | if (params->p_srates[i] == 0) |
566 | break; |
567 | } |
568 | |
569 | return -EINVAL; |
570 | } |
571 | EXPORT_SYMBOL_GPL(u_audio_set_playback_srate); |
572 | |
573 | int u_audio_get_playback_srate(struct g_audio *audio_dev, u32 *val) |
574 | { |
575 | struct snd_uac_chip *uac = audio_dev->uac; |
576 | struct uac_rtd_params *prm; |
577 | unsigned long flags; |
578 | |
579 | prm = &uac->p_prm; |
580 | spin_lock_irqsave(&prm->lock, flags); |
581 | *val = prm->srate; |
582 | spin_unlock_irqrestore(lock: &prm->lock, flags); |
583 | return 0; |
584 | } |
585 | EXPORT_SYMBOL_GPL(u_audio_get_playback_srate); |
586 | |
587 | int u_audio_start_capture(struct g_audio *audio_dev) |
588 | { |
589 | struct snd_uac_chip *uac = audio_dev->uac; |
590 | struct usb_gadget *gadget = audio_dev->gadget; |
591 | struct device *dev = &gadget->dev; |
592 | struct usb_request *req, *req_fback; |
593 | struct usb_ep *ep, *ep_fback; |
594 | struct uac_rtd_params *prm; |
595 | struct uac_params *params = &audio_dev->params; |
596 | int req_len, i; |
597 | |
598 | prm = &uac->c_prm; |
599 | dev_dbg(dev, "start capture with rate %d\n" , prm->srate); |
600 | ep = audio_dev->out_ep; |
601 | config_ep_by_speed(g: gadget, f: &audio_dev->func, ep: ep); |
602 | req_len = ep->maxpacket; |
603 | |
604 | prm->ep_enabled = true; |
605 | usb_ep_enable(ep); |
606 | |
607 | for (i = 0; i < params->req_number; i++) { |
608 | if (!prm->reqs[i]) { |
609 | req = usb_ep_alloc_request(ep, GFP_ATOMIC); |
610 | if (req == NULL) |
611 | return -ENOMEM; |
612 | |
613 | prm->reqs[i] = req; |
614 | |
615 | req->zero = 0; |
616 | req->context = prm; |
617 | req->length = req_len; |
618 | req->complete = u_audio_iso_complete; |
619 | req->buf = prm->rbuf + i * ep->maxpacket; |
620 | } |
621 | |
622 | if (usb_ep_queue(ep, req: prm->reqs[i], GFP_ATOMIC)) |
623 | dev_err(dev, "%s:%d Error!\n" , __func__, __LINE__); |
624 | } |
625 | |
626 | set_active(prm: &uac->c_prm, active: true); |
627 | |
628 | ep_fback = audio_dev->in_ep_fback; |
629 | if (!ep_fback) |
630 | return 0; |
631 | |
632 | /* Setup feedback endpoint */ |
633 | config_ep_by_speed(g: gadget, f: &audio_dev->func, ep: ep_fback); |
634 | prm->fb_ep_enabled = true; |
635 | usb_ep_enable(ep: ep_fback); |
636 | req_len = ep_fback->maxpacket; |
637 | |
638 | req_fback = usb_ep_alloc_request(ep: ep_fback, GFP_ATOMIC); |
639 | if (req_fback == NULL) |
640 | return -ENOMEM; |
641 | |
642 | prm->req_fback = req_fback; |
643 | req_fback->zero = 0; |
644 | req_fback->context = prm; |
645 | req_fback->length = req_len; |
646 | req_fback->complete = u_audio_iso_fback_complete; |
647 | |
648 | req_fback->buf = kzalloc(size: req_len, GFP_ATOMIC); |
649 | if (!req_fback->buf) |
650 | return -ENOMEM; |
651 | |
652 | /* |
653 | * Configure the feedback endpoint's reported frequency. |
654 | * Always start with original frequency since its deviation can't |
655 | * be meauserd at start of playback |
656 | */ |
657 | prm->pitch = 1000000; |
658 | u_audio_set_fback_frequency(speed: audio_dev->gadget->speed, out_ep: ep, |
659 | freq: prm->srate, pitch: prm->pitch, |
660 | buf: req_fback->buf); |
661 | |
662 | if (usb_ep_queue(ep: ep_fback, req: req_fback, GFP_ATOMIC)) |
663 | dev_err(dev, "%s:%d Error!\n" , __func__, __LINE__); |
664 | |
665 | return 0; |
666 | } |
667 | EXPORT_SYMBOL_GPL(u_audio_start_capture); |
668 | |
669 | void u_audio_stop_capture(struct g_audio *audio_dev) |
670 | { |
671 | struct snd_uac_chip *uac = audio_dev->uac; |
672 | |
673 | set_active(prm: &uac->c_prm, active: false); |
674 | if (audio_dev->in_ep_fback) |
675 | free_ep_fback(prm: &uac->c_prm, ep: audio_dev->in_ep_fback); |
676 | free_ep(prm: &uac->c_prm, ep: audio_dev->out_ep); |
677 | } |
678 | EXPORT_SYMBOL_GPL(u_audio_stop_capture); |
679 | |
680 | int u_audio_start_playback(struct g_audio *audio_dev) |
681 | { |
682 | struct snd_uac_chip *uac = audio_dev->uac; |
683 | struct usb_gadget *gadget = audio_dev->gadget; |
684 | struct device *dev = &gadget->dev; |
685 | struct usb_request *req; |
686 | struct usb_ep *ep; |
687 | struct uac_rtd_params *prm; |
688 | struct uac_params *params = &audio_dev->params; |
689 | unsigned int factor; |
690 | const struct usb_endpoint_descriptor *ep_desc; |
691 | int req_len, i; |
692 | unsigned int p_pktsize; |
693 | |
694 | prm = &uac->p_prm; |
695 | dev_dbg(dev, "start playback with rate %d\n" , prm->srate); |
696 | ep = audio_dev->in_ep; |
697 | config_ep_by_speed(g: gadget, f: &audio_dev->func, ep: ep); |
698 | |
699 | ep_desc = ep->desc; |
700 | /* |
701 | * Always start with original frequency |
702 | */ |
703 | prm->pitch = 1000000; |
704 | |
705 | /* pre-calculate the playback endpoint's interval */ |
706 | if (gadget->speed == USB_SPEED_FULL) |
707 | factor = 1000; |
708 | else |
709 | factor = 8000; |
710 | |
711 | /* pre-compute some values for iso_complete() */ |
712 | uac->p_framesize = params->p_ssize * |
713 | num_channels(chanmask: params->p_chmask); |
714 | uac->p_interval = factor / (1 << (ep_desc->bInterval - 1)); |
715 | p_pktsize = min_t(unsigned int, |
716 | uac->p_framesize * |
717 | (prm->srate / uac->p_interval), |
718 | ep->maxpacket); |
719 | |
720 | req_len = p_pktsize; |
721 | uac->p_residue_mil = 0; |
722 | |
723 | prm->ep_enabled = true; |
724 | usb_ep_enable(ep); |
725 | |
726 | for (i = 0; i < params->req_number; i++) { |
727 | if (!prm->reqs[i]) { |
728 | req = usb_ep_alloc_request(ep, GFP_ATOMIC); |
729 | if (req == NULL) |
730 | return -ENOMEM; |
731 | |
732 | prm->reqs[i] = req; |
733 | |
734 | req->zero = 0; |
735 | req->context = prm; |
736 | req->length = req_len; |
737 | req->complete = u_audio_iso_complete; |
738 | req->buf = prm->rbuf + i * ep->maxpacket; |
739 | } |
740 | |
741 | if (usb_ep_queue(ep, req: prm->reqs[i], GFP_ATOMIC)) |
742 | dev_err(dev, "%s:%d Error!\n" , __func__, __LINE__); |
743 | } |
744 | |
745 | set_active(prm: &uac->p_prm, active: true); |
746 | |
747 | return 0; |
748 | } |
749 | EXPORT_SYMBOL_GPL(u_audio_start_playback); |
750 | |
751 | void u_audio_stop_playback(struct g_audio *audio_dev) |
752 | { |
753 | struct snd_uac_chip *uac = audio_dev->uac; |
754 | |
755 | set_active(prm: &uac->p_prm, active: false); |
756 | free_ep(prm: &uac->p_prm, ep: audio_dev->in_ep); |
757 | } |
758 | EXPORT_SYMBOL_GPL(u_audio_stop_playback); |
759 | |
760 | void u_audio_suspend(struct g_audio *audio_dev) |
761 | { |
762 | struct snd_uac_chip *uac = audio_dev->uac; |
763 | |
764 | set_active(prm: &uac->p_prm, active: false); |
765 | set_active(prm: &uac->c_prm, active: false); |
766 | } |
767 | EXPORT_SYMBOL_GPL(u_audio_suspend); |
768 | |
769 | int u_audio_get_volume(struct g_audio *audio_dev, int playback, s16 *val) |
770 | { |
771 | struct snd_uac_chip *uac = audio_dev->uac; |
772 | struct uac_rtd_params *prm; |
773 | unsigned long flags; |
774 | |
775 | if (playback) |
776 | prm = &uac->p_prm; |
777 | else |
778 | prm = &uac->c_prm; |
779 | |
780 | spin_lock_irqsave(&prm->lock, flags); |
781 | *val = prm->volume; |
782 | spin_unlock_irqrestore(lock: &prm->lock, flags); |
783 | |
784 | return 0; |
785 | } |
786 | EXPORT_SYMBOL_GPL(u_audio_get_volume); |
787 | |
788 | int u_audio_set_volume(struct g_audio *audio_dev, int playback, s16 val) |
789 | { |
790 | struct snd_uac_chip *uac = audio_dev->uac; |
791 | struct uac_rtd_params *prm; |
792 | unsigned long flags; |
793 | int change = 0; |
794 | |
795 | if (playback) |
796 | prm = &uac->p_prm; |
797 | else |
798 | prm = &uac->c_prm; |
799 | |
800 | spin_lock_irqsave(&prm->lock, flags); |
801 | val = clamp(val, prm->volume_min, prm->volume_max); |
802 | if (prm->volume != val) { |
803 | prm->volume = val; |
804 | change = 1; |
805 | } |
806 | spin_unlock_irqrestore(lock: &prm->lock, flags); |
807 | |
808 | if (change) |
809 | snd_ctl_notify(card: uac->card, SNDRV_CTL_EVENT_MASK_VALUE, |
810 | id: &prm->snd_kctl_volume->id); |
811 | |
812 | return 0; |
813 | } |
814 | EXPORT_SYMBOL_GPL(u_audio_set_volume); |
815 | |
816 | int u_audio_get_mute(struct g_audio *audio_dev, int playback, int *val) |
817 | { |
818 | struct snd_uac_chip *uac = audio_dev->uac; |
819 | struct uac_rtd_params *prm; |
820 | unsigned long flags; |
821 | |
822 | if (playback) |
823 | prm = &uac->p_prm; |
824 | else |
825 | prm = &uac->c_prm; |
826 | |
827 | spin_lock_irqsave(&prm->lock, flags); |
828 | *val = prm->mute; |
829 | spin_unlock_irqrestore(lock: &prm->lock, flags); |
830 | |
831 | return 0; |
832 | } |
833 | EXPORT_SYMBOL_GPL(u_audio_get_mute); |
834 | |
835 | int u_audio_set_mute(struct g_audio *audio_dev, int playback, int val) |
836 | { |
837 | struct snd_uac_chip *uac = audio_dev->uac; |
838 | struct uac_rtd_params *prm; |
839 | unsigned long flags; |
840 | int change = 0; |
841 | int mute; |
842 | |
843 | if (playback) |
844 | prm = &uac->p_prm; |
845 | else |
846 | prm = &uac->c_prm; |
847 | |
848 | mute = val ? 1 : 0; |
849 | |
850 | spin_lock_irqsave(&prm->lock, flags); |
851 | if (prm->mute != mute) { |
852 | prm->mute = mute; |
853 | change = 1; |
854 | } |
855 | spin_unlock_irqrestore(lock: &prm->lock, flags); |
856 | |
857 | if (change) |
858 | snd_ctl_notify(card: uac->card, SNDRV_CTL_EVENT_MASK_VALUE, |
859 | id: &prm->snd_kctl_mute->id); |
860 | |
861 | return 0; |
862 | } |
863 | EXPORT_SYMBOL_GPL(u_audio_set_mute); |
864 | |
865 | |
866 | static int u_audio_pitch_info(struct snd_kcontrol *kcontrol, |
867 | struct snd_ctl_elem_info *uinfo) |
868 | { |
869 | struct uac_rtd_params *prm = snd_kcontrol_chip(kcontrol); |
870 | struct snd_uac_chip *uac = prm->uac; |
871 | struct g_audio *audio_dev = uac->audio_dev; |
872 | struct uac_params *params = &audio_dev->params; |
873 | unsigned int pitch_min, pitch_max; |
874 | |
875 | pitch_min = (1000 - FBACK_SLOW_MAX) * 1000; |
876 | pitch_max = (1000 + params->fb_max) * 1000; |
877 | |
878 | uinfo->type = SNDRV_CTL_ELEM_TYPE_INTEGER; |
879 | uinfo->count = 1; |
880 | uinfo->value.integer.min = pitch_min; |
881 | uinfo->value.integer.max = pitch_max; |
882 | uinfo->value.integer.step = 1; |
883 | return 0; |
884 | } |
885 | |
886 | static int u_audio_pitch_get(struct snd_kcontrol *kcontrol, |
887 | struct snd_ctl_elem_value *ucontrol) |
888 | { |
889 | struct uac_rtd_params *prm = snd_kcontrol_chip(kcontrol); |
890 | |
891 | ucontrol->value.integer.value[0] = prm->pitch; |
892 | |
893 | return 0; |
894 | } |
895 | |
896 | static int u_audio_pitch_put(struct snd_kcontrol *kcontrol, |
897 | struct snd_ctl_elem_value *ucontrol) |
898 | { |
899 | struct uac_rtd_params *prm = snd_kcontrol_chip(kcontrol); |
900 | struct snd_uac_chip *uac = prm->uac; |
901 | struct g_audio *audio_dev = uac->audio_dev; |
902 | struct uac_params *params = &audio_dev->params; |
903 | unsigned int val; |
904 | unsigned int pitch_min, pitch_max; |
905 | int change = 0; |
906 | |
907 | pitch_min = (1000 - FBACK_SLOW_MAX) * 1000; |
908 | pitch_max = (1000 + params->fb_max) * 1000; |
909 | |
910 | val = ucontrol->value.integer.value[0]; |
911 | |
912 | if (val < pitch_min) |
913 | val = pitch_min; |
914 | if (val > pitch_max) |
915 | val = pitch_max; |
916 | |
917 | if (prm->pitch != val) { |
918 | prm->pitch = val; |
919 | change = 1; |
920 | } |
921 | |
922 | return change; |
923 | } |
924 | |
925 | static int u_audio_mute_info(struct snd_kcontrol *kcontrol, |
926 | struct snd_ctl_elem_info *uinfo) |
927 | { |
928 | uinfo->type = SNDRV_CTL_ELEM_TYPE_BOOLEAN; |
929 | uinfo->count = 1; |
930 | uinfo->value.integer.min = 0; |
931 | uinfo->value.integer.max = 1; |
932 | uinfo->value.integer.step = 1; |
933 | |
934 | return 0; |
935 | } |
936 | |
937 | static int u_audio_mute_get(struct snd_kcontrol *kcontrol, |
938 | struct snd_ctl_elem_value *ucontrol) |
939 | { |
940 | struct uac_rtd_params *prm = snd_kcontrol_chip(kcontrol); |
941 | unsigned long flags; |
942 | |
943 | spin_lock_irqsave(&prm->lock, flags); |
944 | ucontrol->value.integer.value[0] = !prm->mute; |
945 | spin_unlock_irqrestore(lock: &prm->lock, flags); |
946 | |
947 | return 0; |
948 | } |
949 | |
950 | static int u_audio_mute_put(struct snd_kcontrol *kcontrol, |
951 | struct snd_ctl_elem_value *ucontrol) |
952 | { |
953 | struct uac_rtd_params *prm = snd_kcontrol_chip(kcontrol); |
954 | struct snd_uac_chip *uac = prm->uac; |
955 | struct g_audio *audio_dev = uac->audio_dev; |
956 | unsigned int val; |
957 | unsigned long flags; |
958 | int change = 0; |
959 | |
960 | val = !ucontrol->value.integer.value[0]; |
961 | |
962 | spin_lock_irqsave(&prm->lock, flags); |
963 | if (val != prm->mute) { |
964 | prm->mute = val; |
965 | change = 1; |
966 | } |
967 | spin_unlock_irqrestore(lock: &prm->lock, flags); |
968 | |
969 | if (change && audio_dev->notify) |
970 | audio_dev->notify(audio_dev, prm->fu_id, UAC_FU_MUTE); |
971 | |
972 | return change; |
973 | } |
974 | |
975 | /* |
976 | * TLV callback for mixer volume controls |
977 | */ |
978 | static int u_audio_volume_tlv(struct snd_kcontrol *kcontrol, int op_flag, |
979 | unsigned int size, unsigned int __user *_tlv) |
980 | { |
981 | struct uac_rtd_params *prm = snd_kcontrol_chip(kcontrol); |
982 | DECLARE_TLV_DB_MINMAX(scale, 0, 0); |
983 | |
984 | if (size < sizeof(scale)) |
985 | return -ENOMEM; |
986 | |
987 | /* UAC volume resolution is 1/256 dB, TLV is 1/100 dB */ |
988 | scale[2] = (prm->volume_min * 100) / 256; |
989 | scale[3] = (prm->volume_max * 100) / 256; |
990 | if (copy_to_user(to: _tlv, from: scale, n: sizeof(scale))) |
991 | return -EFAULT; |
992 | |
993 | return 0; |
994 | } |
995 | |
996 | static int u_audio_volume_info(struct snd_kcontrol *kcontrol, |
997 | struct snd_ctl_elem_info *uinfo) |
998 | { |
999 | struct uac_rtd_params *prm = snd_kcontrol_chip(kcontrol); |
1000 | |
1001 | uinfo->type = SNDRV_CTL_ELEM_TYPE_INTEGER; |
1002 | uinfo->count = 1; |
1003 | uinfo->value.integer.min = 0; |
1004 | uinfo->value.integer.max = |
1005 | (prm->volume_max - prm->volume_min + prm->volume_res - 1) |
1006 | / prm->volume_res; |
1007 | uinfo->value.integer.step = 1; |
1008 | |
1009 | return 0; |
1010 | } |
1011 | |
1012 | static int u_audio_volume_get(struct snd_kcontrol *kcontrol, |
1013 | struct snd_ctl_elem_value *ucontrol) |
1014 | { |
1015 | struct uac_rtd_params *prm = snd_kcontrol_chip(kcontrol); |
1016 | unsigned long flags; |
1017 | |
1018 | spin_lock_irqsave(&prm->lock, flags); |
1019 | ucontrol->value.integer.value[0] = |
1020 | (prm->volume - prm->volume_min) / prm->volume_res; |
1021 | spin_unlock_irqrestore(lock: &prm->lock, flags); |
1022 | |
1023 | return 0; |
1024 | } |
1025 | |
1026 | static int u_audio_volume_put(struct snd_kcontrol *kcontrol, |
1027 | struct snd_ctl_elem_value *ucontrol) |
1028 | { |
1029 | struct uac_rtd_params *prm = snd_kcontrol_chip(kcontrol); |
1030 | struct snd_uac_chip *uac = prm->uac; |
1031 | struct g_audio *audio_dev = uac->audio_dev; |
1032 | unsigned int val; |
1033 | s16 volume; |
1034 | unsigned long flags; |
1035 | int change = 0; |
1036 | |
1037 | val = ucontrol->value.integer.value[0]; |
1038 | |
1039 | spin_lock_irqsave(&prm->lock, flags); |
1040 | volume = (val * prm->volume_res) + prm->volume_min; |
1041 | volume = clamp(volume, prm->volume_min, prm->volume_max); |
1042 | if (volume != prm->volume) { |
1043 | prm->volume = volume; |
1044 | change = 1; |
1045 | } |
1046 | spin_unlock_irqrestore(lock: &prm->lock, flags); |
1047 | |
1048 | if (change && audio_dev->notify) |
1049 | audio_dev->notify(audio_dev, prm->fu_id, UAC_FU_VOLUME); |
1050 | |
1051 | return change; |
1052 | } |
1053 | |
1054 | static int get_max_srate(const int *srates) |
1055 | { |
1056 | int i, max_srate = 0; |
1057 | |
1058 | for (i = 0; i < UAC_MAX_RATES; i++) { |
1059 | if (srates[i] == 0) |
1060 | break; |
1061 | if (srates[i] > max_srate) |
1062 | max_srate = srates[i]; |
1063 | } |
1064 | return max_srate; |
1065 | } |
1066 | |
1067 | static int get_min_srate(const int *srates) |
1068 | { |
1069 | int i, min_srate = INT_MAX; |
1070 | |
1071 | for (i = 0; i < UAC_MAX_RATES; i++) { |
1072 | if (srates[i] == 0) |
1073 | break; |
1074 | if (srates[i] < min_srate) |
1075 | min_srate = srates[i]; |
1076 | } |
1077 | return min_srate; |
1078 | } |
1079 | |
1080 | static int u_audio_rate_info(struct snd_kcontrol *kcontrol, |
1081 | struct snd_ctl_elem_info *uinfo) |
1082 | { |
1083 | const int *srates; |
1084 | struct uac_rtd_params *prm = snd_kcontrol_chip(kcontrol); |
1085 | struct snd_uac_chip *uac = prm->uac; |
1086 | struct g_audio *audio_dev = uac->audio_dev; |
1087 | struct uac_params *params = &audio_dev->params; |
1088 | |
1089 | uinfo->type = SNDRV_CTL_ELEM_TYPE_INTEGER; |
1090 | uinfo->count = 1; |
1091 | |
1092 | if (prm == &uac->c_prm) |
1093 | srates = params->c_srates; |
1094 | else |
1095 | srates = params->p_srates; |
1096 | uinfo->value.integer.min = get_min_srate(srates); |
1097 | uinfo->value.integer.max = get_max_srate(srates); |
1098 | return 0; |
1099 | } |
1100 | |
1101 | static int u_audio_rate_get(struct snd_kcontrol *kcontrol, |
1102 | struct snd_ctl_elem_value *ucontrol) |
1103 | { |
1104 | struct uac_rtd_params *prm = snd_kcontrol_chip(kcontrol); |
1105 | unsigned long flags; |
1106 | |
1107 | spin_lock_irqsave(&prm->lock, flags); |
1108 | if (prm->active) |
1109 | ucontrol->value.integer.value[0] = prm->srate; |
1110 | else |
1111 | /* not active: reporting zero rate */ |
1112 | ucontrol->value.integer.value[0] = 0; |
1113 | spin_unlock_irqrestore(lock: &prm->lock, flags); |
1114 | return 0; |
1115 | } |
1116 | |
1117 | static struct snd_kcontrol_new u_audio_controls[] = { |
1118 | [UAC_FBACK_CTRL] { |
1119 | .iface = SNDRV_CTL_ELEM_IFACE_PCM, |
1120 | .name = "Capture Pitch 1000000" , |
1121 | .info = u_audio_pitch_info, |
1122 | .get = u_audio_pitch_get, |
1123 | .put = u_audio_pitch_put, |
1124 | }, |
1125 | [UAC_P_PITCH_CTRL] { |
1126 | .iface = SNDRV_CTL_ELEM_IFACE_PCM, |
1127 | .name = "Playback Pitch 1000000" , |
1128 | .info = u_audio_pitch_info, |
1129 | .get = u_audio_pitch_get, |
1130 | .put = u_audio_pitch_put, |
1131 | }, |
1132 | [UAC_MUTE_CTRL] { |
1133 | .iface = SNDRV_CTL_ELEM_IFACE_MIXER, |
1134 | .name = "" , /* will be filled later */ |
1135 | .info = u_audio_mute_info, |
1136 | .get = u_audio_mute_get, |
1137 | .put = u_audio_mute_put, |
1138 | }, |
1139 | [UAC_VOLUME_CTRL] { |
1140 | .iface = SNDRV_CTL_ELEM_IFACE_MIXER, |
1141 | .name = "" , /* will be filled later */ |
1142 | .info = u_audio_volume_info, |
1143 | .get = u_audio_volume_get, |
1144 | .put = u_audio_volume_put, |
1145 | }, |
1146 | [UAC_RATE_CTRL] { |
1147 | .iface = SNDRV_CTL_ELEM_IFACE_PCM, |
1148 | .name = "" , /* will be filled later */ |
1149 | .access = SNDRV_CTL_ELEM_ACCESS_READ | SNDRV_CTL_ELEM_ACCESS_VOLATILE, |
1150 | .info = u_audio_rate_info, |
1151 | .get = u_audio_rate_get, |
1152 | }, |
1153 | }; |
1154 | |
1155 | int g_audio_setup(struct g_audio *g_audio, const char *pcm_name, |
1156 | const char *card_name) |
1157 | { |
1158 | struct snd_uac_chip *uac; |
1159 | struct snd_card *card; |
1160 | struct snd_pcm *pcm; |
1161 | struct snd_kcontrol *kctl; |
1162 | struct uac_params *params; |
1163 | int p_chmask, c_chmask; |
1164 | int i, err; |
1165 | |
1166 | if (!g_audio) |
1167 | return -EINVAL; |
1168 | |
1169 | uac = kzalloc(size: sizeof(*uac), GFP_KERNEL); |
1170 | if (!uac) |
1171 | return -ENOMEM; |
1172 | g_audio->uac = uac; |
1173 | uac->audio_dev = g_audio; |
1174 | |
1175 | params = &g_audio->params; |
1176 | p_chmask = params->p_chmask; |
1177 | c_chmask = params->c_chmask; |
1178 | |
1179 | if (c_chmask) { |
1180 | struct uac_rtd_params *prm = &uac->c_prm; |
1181 | |
1182 | spin_lock_init(&prm->lock); |
1183 | uac->c_prm.uac = uac; |
1184 | prm->max_psize = g_audio->out_ep_maxpsize; |
1185 | prm->srate = params->c_srates[0]; |
1186 | |
1187 | prm->reqs = kcalloc(n: params->req_number, |
1188 | size: sizeof(struct usb_request *), |
1189 | GFP_KERNEL); |
1190 | if (!prm->reqs) { |
1191 | err = -ENOMEM; |
1192 | goto fail; |
1193 | } |
1194 | |
1195 | prm->rbuf = kcalloc(n: params->req_number, size: prm->max_psize, |
1196 | GFP_KERNEL); |
1197 | if (!prm->rbuf) { |
1198 | prm->max_psize = 0; |
1199 | err = -ENOMEM; |
1200 | goto fail; |
1201 | } |
1202 | } |
1203 | |
1204 | if (p_chmask) { |
1205 | struct uac_rtd_params *prm = &uac->p_prm; |
1206 | |
1207 | spin_lock_init(&prm->lock); |
1208 | uac->p_prm.uac = uac; |
1209 | prm->max_psize = g_audio->in_ep_maxpsize; |
1210 | prm->srate = params->p_srates[0]; |
1211 | |
1212 | prm->reqs = kcalloc(n: params->req_number, |
1213 | size: sizeof(struct usb_request *), |
1214 | GFP_KERNEL); |
1215 | if (!prm->reqs) { |
1216 | err = -ENOMEM; |
1217 | goto fail; |
1218 | } |
1219 | |
1220 | prm->rbuf = kcalloc(n: params->req_number, size: prm->max_psize, |
1221 | GFP_KERNEL); |
1222 | if (!prm->rbuf) { |
1223 | prm->max_psize = 0; |
1224 | err = -ENOMEM; |
1225 | goto fail; |
1226 | } |
1227 | } |
1228 | |
1229 | /* Choose any slot, with no id */ |
1230 | err = snd_card_new(parent: &g_audio->gadget->dev, |
1231 | idx: -1, NULL, THIS_MODULE, extra_size: 0, card_ret: &card); |
1232 | if (err < 0) |
1233 | goto fail; |
1234 | |
1235 | uac->card = card; |
1236 | |
1237 | /* |
1238 | * Create first PCM device |
1239 | * Create a substream only for non-zero channel streams |
1240 | */ |
1241 | err = snd_pcm_new(card: uac->card, id: pcm_name, device: 0, |
1242 | playback_count: p_chmask ? 1 : 0, capture_count: c_chmask ? 1 : 0, rpcm: &pcm); |
1243 | if (err < 0) |
1244 | goto snd_fail; |
1245 | |
1246 | strscpy(pcm->name, pcm_name, sizeof(pcm->name)); |
1247 | pcm->private_data = uac; |
1248 | uac->pcm = pcm; |
1249 | |
1250 | snd_pcm_set_ops(pcm, direction: SNDRV_PCM_STREAM_PLAYBACK, ops: &uac_pcm_ops); |
1251 | snd_pcm_set_ops(pcm, direction: SNDRV_PCM_STREAM_CAPTURE, ops: &uac_pcm_ops); |
1252 | |
1253 | /* |
1254 | * Create mixer and controls |
1255 | * Create only if it's required on USB side |
1256 | */ |
1257 | if ((c_chmask && g_audio->in_ep_fback) |
1258 | || (p_chmask && params->p_fu.id) |
1259 | || (c_chmask && params->c_fu.id)) |
1260 | strscpy(card->mixername, card_name, sizeof(card->driver)); |
1261 | |
1262 | if (c_chmask && g_audio->in_ep_fback) { |
1263 | kctl = snd_ctl_new1(kcontrolnew: &u_audio_controls[UAC_FBACK_CTRL], |
1264 | private_data: &uac->c_prm); |
1265 | if (!kctl) { |
1266 | err = -ENOMEM; |
1267 | goto snd_fail; |
1268 | } |
1269 | |
1270 | kctl->id.device = pcm->device; |
1271 | kctl->id.subdevice = 0; |
1272 | |
1273 | err = snd_ctl_add(card, kcontrol: kctl); |
1274 | if (err < 0) |
1275 | goto snd_fail; |
1276 | } |
1277 | |
1278 | if (p_chmask) { |
1279 | kctl = snd_ctl_new1(kcontrolnew: &u_audio_controls[UAC_P_PITCH_CTRL], |
1280 | private_data: &uac->p_prm); |
1281 | if (!kctl) { |
1282 | err = -ENOMEM; |
1283 | goto snd_fail; |
1284 | } |
1285 | |
1286 | kctl->id.device = pcm->device; |
1287 | kctl->id.subdevice = 0; |
1288 | |
1289 | err = snd_ctl_add(card, kcontrol: kctl); |
1290 | if (err < 0) |
1291 | goto snd_fail; |
1292 | } |
1293 | |
1294 | for (i = 0; i <= SNDRV_PCM_STREAM_LAST; i++) { |
1295 | struct uac_rtd_params *prm; |
1296 | struct uac_fu_params *fu; |
1297 | char ctrl_name[24]; |
1298 | char *direction; |
1299 | |
1300 | if (!pcm->streams[i].substream_count) |
1301 | continue; |
1302 | |
1303 | if (i == SNDRV_PCM_STREAM_PLAYBACK) { |
1304 | prm = &uac->p_prm; |
1305 | fu = ¶ms->p_fu; |
1306 | direction = "Playback" ; |
1307 | } else { |
1308 | prm = &uac->c_prm; |
1309 | fu = ¶ms->c_fu; |
1310 | direction = "Capture" ; |
1311 | } |
1312 | |
1313 | prm->fu_id = fu->id; |
1314 | |
1315 | if (fu->mute_present) { |
1316 | snprintf(buf: ctrl_name, size: sizeof(ctrl_name), |
1317 | fmt: "PCM %s Switch" , direction); |
1318 | |
1319 | u_audio_controls[UAC_MUTE_CTRL].name = ctrl_name; |
1320 | |
1321 | kctl = snd_ctl_new1(kcontrolnew: &u_audio_controls[UAC_MUTE_CTRL], |
1322 | private_data: prm); |
1323 | if (!kctl) { |
1324 | err = -ENOMEM; |
1325 | goto snd_fail; |
1326 | } |
1327 | |
1328 | kctl->id.device = pcm->device; |
1329 | kctl->id.subdevice = 0; |
1330 | |
1331 | err = snd_ctl_add(card, kcontrol: kctl); |
1332 | if (err < 0) |
1333 | goto snd_fail; |
1334 | prm->snd_kctl_mute = kctl; |
1335 | prm->mute = 0; |
1336 | } |
1337 | |
1338 | if (fu->volume_present) { |
1339 | snprintf(buf: ctrl_name, size: sizeof(ctrl_name), |
1340 | fmt: "PCM %s Volume" , direction); |
1341 | |
1342 | u_audio_controls[UAC_VOLUME_CTRL].name = ctrl_name; |
1343 | |
1344 | kctl = snd_ctl_new1(kcontrolnew: &u_audio_controls[UAC_VOLUME_CTRL], |
1345 | private_data: prm); |
1346 | if (!kctl) { |
1347 | err = -ENOMEM; |
1348 | goto snd_fail; |
1349 | } |
1350 | |
1351 | kctl->id.device = pcm->device; |
1352 | kctl->id.subdevice = 0; |
1353 | |
1354 | |
1355 | kctl->tlv.c = u_audio_volume_tlv; |
1356 | kctl->vd[0].access |= SNDRV_CTL_ELEM_ACCESS_TLV_READ | |
1357 | SNDRV_CTL_ELEM_ACCESS_TLV_CALLBACK; |
1358 | |
1359 | err = snd_ctl_add(card, kcontrol: kctl); |
1360 | if (err < 0) |
1361 | goto snd_fail; |
1362 | prm->snd_kctl_volume = kctl; |
1363 | prm->volume = fu->volume_max; |
1364 | prm->volume_max = fu->volume_max; |
1365 | prm->volume_min = fu->volume_min; |
1366 | prm->volume_res = fu->volume_res; |
1367 | } |
1368 | |
1369 | /* Add rate control */ |
1370 | snprintf(buf: ctrl_name, size: sizeof(ctrl_name), |
1371 | fmt: "%s Rate" , direction); |
1372 | u_audio_controls[UAC_RATE_CTRL].name = ctrl_name; |
1373 | |
1374 | kctl = snd_ctl_new1(kcontrolnew: &u_audio_controls[UAC_RATE_CTRL], private_data: prm); |
1375 | if (!kctl) { |
1376 | err = -ENOMEM; |
1377 | goto snd_fail; |
1378 | } |
1379 | |
1380 | kctl->id.device = pcm->device; |
1381 | kctl->id.subdevice = 0; |
1382 | |
1383 | err = snd_ctl_add(card, kcontrol: kctl); |
1384 | if (err < 0) |
1385 | goto snd_fail; |
1386 | prm->snd_kctl_rate = kctl; |
1387 | } |
1388 | |
1389 | strscpy(card->driver, card_name, sizeof(card->driver)); |
1390 | strscpy(card->shortname, card_name, sizeof(card->shortname)); |
1391 | sprintf(buf: card->longname, fmt: "%s %i" , card_name, card->dev->id); |
1392 | |
1393 | snd_pcm_set_managed_buffer_all(pcm, SNDRV_DMA_TYPE_CONTINUOUS, |
1394 | NULL, size: 0, BUFF_SIZE_MAX); |
1395 | |
1396 | err = snd_card_register(card); |
1397 | |
1398 | if (!err) |
1399 | return 0; |
1400 | |
1401 | snd_fail: |
1402 | snd_card_free(card); |
1403 | fail: |
1404 | kfree(objp: uac->p_prm.reqs); |
1405 | kfree(objp: uac->c_prm.reqs); |
1406 | kfree(objp: uac->p_prm.rbuf); |
1407 | kfree(objp: uac->c_prm.rbuf); |
1408 | kfree(objp: uac); |
1409 | |
1410 | return err; |
1411 | } |
1412 | EXPORT_SYMBOL_GPL(g_audio_setup); |
1413 | |
1414 | void g_audio_cleanup(struct g_audio *g_audio) |
1415 | { |
1416 | struct snd_uac_chip *uac; |
1417 | struct snd_card *card; |
1418 | |
1419 | if (!g_audio || !g_audio->uac) |
1420 | return; |
1421 | |
1422 | uac = g_audio->uac; |
1423 | card = uac->card; |
1424 | if (card) |
1425 | snd_card_free_when_closed(card); |
1426 | |
1427 | kfree(objp: uac->p_prm.reqs); |
1428 | kfree(objp: uac->c_prm.reqs); |
1429 | kfree(objp: uac->p_prm.rbuf); |
1430 | kfree(objp: uac->c_prm.rbuf); |
1431 | kfree(objp: uac); |
1432 | } |
1433 | EXPORT_SYMBOL_GPL(g_audio_cleanup); |
1434 | |
1435 | MODULE_LICENSE("GPL" ); |
1436 | MODULE_DESCRIPTION("USB gadget \"ALSA sound card\" utilities" ); |
1437 | MODULE_AUTHOR("Ruslan Bilovol" ); |
1438 | |