]> git.karo-electronics.de Git - karo-tx-linux.git/blob - sound/core/pcm.c
Merge remote-tracking branch 'lzo-update/lzo-update'
[karo-tx-linux.git] / sound / core / pcm.c
1 /*
2  *  Digital Audio (PCM) abstract layer
3  *  Copyright (c) by Jaroslav Kysela <perex@perex.cz>
4  *
5  *
6  *   This program is free software; you can redistribute it and/or modify
7  *   it under the terms of the GNU General Public License as published by
8  *   the Free Software Foundation; either version 2 of the License, or
9  *   (at your option) any later version.
10  *
11  *   This program is distributed in the hope that it will be useful,
12  *   but WITHOUT ANY WARRANTY; without even the implied warranty of
13  *   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
14  *   GNU General Public License for more details.
15  *
16  *   You should have received a copy of the GNU General Public License
17  *   along with this program; if not, write to the Free Software
18  *   Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
19  *
20  */
21
22 #include <linux/init.h>
23 #include <linux/slab.h>
24 #include <linux/module.h>
25 #include <linux/time.h>
26 #include <linux/mutex.h>
27 #include <linux/device.h>
28 #include <sound/core.h>
29 #include <sound/minors.h>
30 #include <sound/pcm.h>
31 #include <sound/control.h>
32 #include <sound/info.h>
33
34 MODULE_AUTHOR("Jaroslav Kysela <perex@perex.cz>, Abramo Bagnara <abramo@alsa-project.org>");
35 MODULE_DESCRIPTION("Midlevel PCM code for ALSA.");
36 MODULE_LICENSE("GPL");
37
38 static LIST_HEAD(snd_pcm_devices);
39 static LIST_HEAD(snd_pcm_notify_list);
40 static DEFINE_MUTEX(register_mutex);
41
42 static int snd_pcm_free(struct snd_pcm *pcm);
43 static int snd_pcm_dev_free(struct snd_device *device);
44 static int snd_pcm_dev_register(struct snd_device *device);
45 static int snd_pcm_dev_disconnect(struct snd_device *device);
46
47 static struct snd_pcm *snd_pcm_get(struct snd_card *card, int device)
48 {
49         struct snd_pcm *pcm;
50
51         list_for_each_entry(pcm, &snd_pcm_devices, list) {
52                 if (pcm->card == card && pcm->device == device)
53                         return pcm;
54         }
55         return NULL;
56 }
57
58 static int snd_pcm_next(struct snd_card *card, int device)
59 {
60         struct snd_pcm *pcm;
61
62         list_for_each_entry(pcm, &snd_pcm_devices, list) {
63                 if (pcm->card == card && pcm->device > device)
64                         return pcm->device;
65                 else if (pcm->card->number > card->number)
66                         return -1;
67         }
68         return -1;
69 }
70
71 static int snd_pcm_add(struct snd_pcm *newpcm)
72 {
73         struct snd_pcm *pcm;
74
75         list_for_each_entry(pcm, &snd_pcm_devices, list) {
76                 if (pcm->card == newpcm->card && pcm->device == newpcm->device)
77                         return -EBUSY;
78                 if (pcm->card->number > newpcm->card->number ||
79                                 (pcm->card == newpcm->card &&
80                                 pcm->device > newpcm->device)) {
81                         list_add(&newpcm->list, pcm->list.prev);
82                         return 0;
83                 }
84         }
85         list_add_tail(&newpcm->list, &snd_pcm_devices);
86         return 0;
87 }
88
89 static int snd_pcm_control_ioctl(struct snd_card *card,
90                                  struct snd_ctl_file *control,
91                                  unsigned int cmd, unsigned long arg)
92 {
93         switch (cmd) {
94         case SNDRV_CTL_IOCTL_PCM_NEXT_DEVICE:
95                 {
96                         int device;
97
98                         if (get_user(device, (int __user *)arg))
99                                 return -EFAULT;
100                         mutex_lock(&register_mutex);
101                         device = snd_pcm_next(card, device);
102                         mutex_unlock(&register_mutex);
103                         if (put_user(device, (int __user *)arg))
104                                 return -EFAULT;
105                         return 0;
106                 }
107         case SNDRV_CTL_IOCTL_PCM_INFO:
108                 {
109                         struct snd_pcm_info __user *info;
110                         unsigned int device, subdevice;
111                         int stream;
112                         struct snd_pcm *pcm;
113                         struct snd_pcm_str *pstr;
114                         struct snd_pcm_substream *substream;
115                         int err;
116
117                         info = (struct snd_pcm_info __user *)arg;
118                         if (get_user(device, &info->device))
119                                 return -EFAULT;
120                         if (get_user(stream, &info->stream))
121                                 return -EFAULT;
122                         if (stream < 0 || stream > 1)
123                                 return -EINVAL;
124                         if (get_user(subdevice, &info->subdevice))
125                                 return -EFAULT;
126                         mutex_lock(&register_mutex);
127                         pcm = snd_pcm_get(card, device);
128                         if (pcm == NULL) {
129                                 err = -ENXIO;
130                                 goto _error;
131                         }
132                         pstr = &pcm->streams[stream];
133                         if (pstr->substream_count == 0) {
134                                 err = -ENOENT;
135                                 goto _error;
136                         }
137                         if (subdevice >= pstr->substream_count) {
138                                 err = -ENXIO;
139                                 goto _error;
140                         }
141                         for (substream = pstr->substream; substream;
142                              substream = substream->next)
143                                 if (substream->number == (int)subdevice)
144                                         break;
145                         if (substream == NULL) {
146                                 err = -ENXIO;
147                                 goto _error;
148                         }
149                         err = snd_pcm_info_user(substream, info);
150                 _error:
151                         mutex_unlock(&register_mutex);
152                         return err;
153                 }
154         case SNDRV_CTL_IOCTL_PCM_PREFER_SUBDEVICE:
155                 {
156                         int val;
157                         
158                         if (get_user(val, (int __user *)arg))
159                                 return -EFAULT;
160                         control->prefer_pcm_subdevice = val;
161                         return 0;
162                 }
163         }
164         return -ENOIOCTLCMD;
165 }
166
167 #define FORMAT(v) [SNDRV_PCM_FORMAT_##v] = #v
168
169 static char *snd_pcm_format_names[] = {
170         FORMAT(S8),
171         FORMAT(U8),
172         FORMAT(S16_LE),
173         FORMAT(S16_BE),
174         FORMAT(U16_LE),
175         FORMAT(U16_BE),
176         FORMAT(S24_LE),
177         FORMAT(S24_BE),
178         FORMAT(U24_LE),
179         FORMAT(U24_BE),
180         FORMAT(S32_LE),
181         FORMAT(S32_BE),
182         FORMAT(U32_LE),
183         FORMAT(U32_BE),
184         FORMAT(FLOAT_LE),
185         FORMAT(FLOAT_BE),
186         FORMAT(FLOAT64_LE),
187         FORMAT(FLOAT64_BE),
188         FORMAT(IEC958_SUBFRAME_LE),
189         FORMAT(IEC958_SUBFRAME_BE),
190         FORMAT(MU_LAW),
191         FORMAT(A_LAW),
192         FORMAT(IMA_ADPCM),
193         FORMAT(MPEG),
194         FORMAT(GSM),
195         FORMAT(SPECIAL),
196         FORMAT(S24_3LE),
197         FORMAT(S24_3BE),
198         FORMAT(U24_3LE),
199         FORMAT(U24_3BE),
200         FORMAT(S20_3LE),
201         FORMAT(S20_3BE),
202         FORMAT(U20_3LE),
203         FORMAT(U20_3BE),
204         FORMAT(S18_3LE),
205         FORMAT(S18_3BE),
206         FORMAT(U18_3LE),
207         FORMAT(U18_3BE),
208         FORMAT(G723_24),
209         FORMAT(G723_24_1B),
210         FORMAT(G723_40),
211         FORMAT(G723_40_1B),
212         FORMAT(DSD_U8),
213         FORMAT(DSD_U16_LE),
214 };
215
216 const char *snd_pcm_format_name(snd_pcm_format_t format)
217 {
218         if ((__force unsigned int)format >= ARRAY_SIZE(snd_pcm_format_names))
219                 return "Unknown";
220         return snd_pcm_format_names[(__force unsigned int)format];
221 }
222 EXPORT_SYMBOL_GPL(snd_pcm_format_name);
223
224 #ifdef CONFIG_SND_VERBOSE_PROCFS
225
226 #define STATE(v) [SNDRV_PCM_STATE_##v] = #v
227 #define STREAM(v) [SNDRV_PCM_STREAM_##v] = #v
228 #define READY(v) [SNDRV_PCM_READY_##v] = #v
229 #define XRUN(v) [SNDRV_PCM_XRUN_##v] = #v
230 #define SILENCE(v) [SNDRV_PCM_SILENCE_##v] = #v
231 #define TSTAMP(v) [SNDRV_PCM_TSTAMP_##v] = #v
232 #define ACCESS(v) [SNDRV_PCM_ACCESS_##v] = #v
233 #define START(v) [SNDRV_PCM_START_##v] = #v
234 #define SUBFORMAT(v) [SNDRV_PCM_SUBFORMAT_##v] = #v 
235
236 static char *snd_pcm_stream_names[] = {
237         STREAM(PLAYBACK),
238         STREAM(CAPTURE),
239 };
240
241 static char *snd_pcm_state_names[] = {
242         STATE(OPEN),
243         STATE(SETUP),
244         STATE(PREPARED),
245         STATE(RUNNING),
246         STATE(XRUN),
247         STATE(DRAINING),
248         STATE(PAUSED),
249         STATE(SUSPENDED),
250 };
251
252 static char *snd_pcm_access_names[] = {
253         ACCESS(MMAP_INTERLEAVED), 
254         ACCESS(MMAP_NONINTERLEAVED),
255         ACCESS(MMAP_COMPLEX),
256         ACCESS(RW_INTERLEAVED),
257         ACCESS(RW_NONINTERLEAVED),
258 };
259
260 static char *snd_pcm_subformat_names[] = {
261         SUBFORMAT(STD), 
262 };
263
264 static char *snd_pcm_tstamp_mode_names[] = {
265         TSTAMP(NONE),
266         TSTAMP(ENABLE),
267 };
268
269 static const char *snd_pcm_stream_name(int stream)
270 {
271         return snd_pcm_stream_names[stream];
272 }
273
274 static const char *snd_pcm_access_name(snd_pcm_access_t access)
275 {
276         return snd_pcm_access_names[(__force int)access];
277 }
278
279 static const char *snd_pcm_subformat_name(snd_pcm_subformat_t subformat)
280 {
281         return snd_pcm_subformat_names[(__force int)subformat];
282 }
283
284 static const char *snd_pcm_tstamp_mode_name(int mode)
285 {
286         return snd_pcm_tstamp_mode_names[mode];
287 }
288
289 static const char *snd_pcm_state_name(snd_pcm_state_t state)
290 {
291         return snd_pcm_state_names[(__force int)state];
292 }
293
294 #if defined(CONFIG_SND_PCM_OSS) || defined(CONFIG_SND_PCM_OSS_MODULE)
295 #include <linux/soundcard.h>
296
297 static const char *snd_pcm_oss_format_name(int format)
298 {
299         switch (format) {
300         case AFMT_MU_LAW:
301                 return "MU_LAW";
302         case AFMT_A_LAW:
303                 return "A_LAW";
304         case AFMT_IMA_ADPCM:
305                 return "IMA_ADPCM";
306         case AFMT_U8:
307                 return "U8";
308         case AFMT_S16_LE:
309                 return "S16_LE";
310         case AFMT_S16_BE:
311                 return "S16_BE";
312         case AFMT_S8:
313                 return "S8";
314         case AFMT_U16_LE:
315                 return "U16_LE";
316         case AFMT_U16_BE:
317                 return "U16_BE";
318         case AFMT_MPEG:
319                 return "MPEG";
320         default:
321                 return "unknown";
322         }
323 }
324 #endif
325
326 static void snd_pcm_proc_info_read(struct snd_pcm_substream *substream,
327                                    struct snd_info_buffer *buffer)
328 {
329         struct snd_pcm_info *info;
330         int err;
331
332         if (! substream)
333                 return;
334
335         info = kmalloc(sizeof(*info), GFP_KERNEL);
336         if (! info) {
337                 printk(KERN_DEBUG "snd_pcm_proc_info_read: cannot malloc\n");
338                 return;
339         }
340
341         err = snd_pcm_info(substream, info);
342         if (err < 0) {
343                 snd_iprintf(buffer, "error %d\n", err);
344                 kfree(info);
345                 return;
346         }
347         snd_iprintf(buffer, "card: %d\n", info->card);
348         snd_iprintf(buffer, "device: %d\n", info->device);
349         snd_iprintf(buffer, "subdevice: %d\n", info->subdevice);
350         snd_iprintf(buffer, "stream: %s\n", snd_pcm_stream_name(info->stream));
351         snd_iprintf(buffer, "id: %s\n", info->id);
352         snd_iprintf(buffer, "name: %s\n", info->name);
353         snd_iprintf(buffer, "subname: %s\n", info->subname);
354         snd_iprintf(buffer, "class: %d\n", info->dev_class);
355         snd_iprintf(buffer, "subclass: %d\n", info->dev_subclass);
356         snd_iprintf(buffer, "subdevices_count: %d\n", info->subdevices_count);
357         snd_iprintf(buffer, "subdevices_avail: %d\n", info->subdevices_avail);
358         kfree(info);
359 }
360
361 static void snd_pcm_stream_proc_info_read(struct snd_info_entry *entry,
362                                           struct snd_info_buffer *buffer)
363 {
364         snd_pcm_proc_info_read(((struct snd_pcm_str *)entry->private_data)->substream,
365                                buffer);
366 }
367
368 static void snd_pcm_substream_proc_info_read(struct snd_info_entry *entry,
369                                              struct snd_info_buffer *buffer)
370 {
371         snd_pcm_proc_info_read(entry->private_data, buffer);
372 }
373
374 static void snd_pcm_substream_proc_hw_params_read(struct snd_info_entry *entry,
375                                                   struct snd_info_buffer *buffer)
376 {
377         struct snd_pcm_substream *substream = entry->private_data;
378         struct snd_pcm_runtime *runtime;
379
380         mutex_lock(&substream->pcm->open_mutex);
381         runtime = substream->runtime;
382         if (!runtime) {
383                 snd_iprintf(buffer, "closed\n");
384                 goto unlock;
385         }
386         if (runtime->status->state == SNDRV_PCM_STATE_OPEN) {
387                 snd_iprintf(buffer, "no setup\n");
388                 goto unlock;
389         }
390         snd_iprintf(buffer, "access: %s\n", snd_pcm_access_name(runtime->access));
391         snd_iprintf(buffer, "format: %s\n", snd_pcm_format_name(runtime->format));
392         snd_iprintf(buffer, "subformat: %s\n", snd_pcm_subformat_name(runtime->subformat));
393         snd_iprintf(buffer, "channels: %u\n", runtime->channels);       
394         snd_iprintf(buffer, "rate: %u (%u/%u)\n", runtime->rate, runtime->rate_num, runtime->rate_den); 
395         snd_iprintf(buffer, "period_size: %lu\n", runtime->period_size);        
396         snd_iprintf(buffer, "buffer_size: %lu\n", runtime->buffer_size);        
397 #if defined(CONFIG_SND_PCM_OSS) || defined(CONFIG_SND_PCM_OSS_MODULE)
398         if (substream->oss.oss) {
399                 snd_iprintf(buffer, "OSS format: %s\n", snd_pcm_oss_format_name(runtime->oss.format));
400                 snd_iprintf(buffer, "OSS channels: %u\n", runtime->oss.channels);       
401                 snd_iprintf(buffer, "OSS rate: %u\n", runtime->oss.rate);
402                 snd_iprintf(buffer, "OSS period bytes: %lu\n", (unsigned long)runtime->oss.period_bytes);
403                 snd_iprintf(buffer, "OSS periods: %u\n", runtime->oss.periods);
404                 snd_iprintf(buffer, "OSS period frames: %lu\n", (unsigned long)runtime->oss.period_frames);
405         }
406 #endif
407  unlock:
408         mutex_unlock(&substream->pcm->open_mutex);
409 }
410
411 static void snd_pcm_substream_proc_sw_params_read(struct snd_info_entry *entry,
412                                                   struct snd_info_buffer *buffer)
413 {
414         struct snd_pcm_substream *substream = entry->private_data;
415         struct snd_pcm_runtime *runtime;
416
417         mutex_lock(&substream->pcm->open_mutex);
418         runtime = substream->runtime;
419         if (!runtime) {
420                 snd_iprintf(buffer, "closed\n");
421                 goto unlock;
422         }
423         if (runtime->status->state == SNDRV_PCM_STATE_OPEN) {
424                 snd_iprintf(buffer, "no setup\n");
425                 goto unlock;
426         }
427         snd_iprintf(buffer, "tstamp_mode: %s\n", snd_pcm_tstamp_mode_name(runtime->tstamp_mode));
428         snd_iprintf(buffer, "period_step: %u\n", runtime->period_step);
429         snd_iprintf(buffer, "avail_min: %lu\n", runtime->control->avail_min);
430         snd_iprintf(buffer, "start_threshold: %lu\n", runtime->start_threshold);
431         snd_iprintf(buffer, "stop_threshold: %lu\n", runtime->stop_threshold);
432         snd_iprintf(buffer, "silence_threshold: %lu\n", runtime->silence_threshold);
433         snd_iprintf(buffer, "silence_size: %lu\n", runtime->silence_size);
434         snd_iprintf(buffer, "boundary: %lu\n", runtime->boundary);
435  unlock:
436         mutex_unlock(&substream->pcm->open_mutex);
437 }
438
439 static void snd_pcm_substream_proc_status_read(struct snd_info_entry *entry,
440                                                struct snd_info_buffer *buffer)
441 {
442         struct snd_pcm_substream *substream = entry->private_data;
443         struct snd_pcm_runtime *runtime;
444         struct snd_pcm_status status;
445         int err;
446
447         mutex_lock(&substream->pcm->open_mutex);
448         runtime = substream->runtime;
449         if (!runtime) {
450                 snd_iprintf(buffer, "closed\n");
451                 goto unlock;
452         }
453         memset(&status, 0, sizeof(status));
454         err = snd_pcm_status(substream, &status);
455         if (err < 0) {
456                 snd_iprintf(buffer, "error %d\n", err);
457                 goto unlock;
458         }
459         snd_iprintf(buffer, "state: %s\n", snd_pcm_state_name(status.state));
460         snd_iprintf(buffer, "owner_pid   : %d\n", pid_vnr(substream->pid));
461         snd_iprintf(buffer, "trigger_time: %ld.%09ld\n",
462                 status.trigger_tstamp.tv_sec, status.trigger_tstamp.tv_nsec);
463         snd_iprintf(buffer, "tstamp      : %ld.%09ld\n",
464                 status.tstamp.tv_sec, status.tstamp.tv_nsec);
465         snd_iprintf(buffer, "delay       : %ld\n", status.delay);
466         snd_iprintf(buffer, "avail       : %ld\n", status.avail);
467         snd_iprintf(buffer, "avail_max   : %ld\n", status.avail_max);
468         snd_iprintf(buffer, "-----\n");
469         snd_iprintf(buffer, "hw_ptr      : %ld\n", runtime->status->hw_ptr);
470         snd_iprintf(buffer, "appl_ptr    : %ld\n", runtime->control->appl_ptr);
471  unlock:
472         mutex_unlock(&substream->pcm->open_mutex);
473 }
474
475 #ifdef CONFIG_SND_PCM_XRUN_DEBUG
476 static void snd_pcm_xrun_debug_read(struct snd_info_entry *entry,
477                                     struct snd_info_buffer *buffer)
478 {
479         struct snd_pcm_str *pstr = entry->private_data;
480         snd_iprintf(buffer, "%d\n", pstr->xrun_debug);
481 }
482
483 static void snd_pcm_xrun_debug_write(struct snd_info_entry *entry,
484                                      struct snd_info_buffer *buffer)
485 {
486         struct snd_pcm_str *pstr = entry->private_data;
487         char line[64];
488         if (!snd_info_get_line(buffer, line, sizeof(line)))
489                 pstr->xrun_debug = simple_strtoul(line, NULL, 10);
490 }
491 #endif
492
493 static int snd_pcm_stream_proc_init(struct snd_pcm_str *pstr)
494 {
495         struct snd_pcm *pcm = pstr->pcm;
496         struct snd_info_entry *entry;
497         char name[16];
498
499         sprintf(name, "pcm%i%c", pcm->device, 
500                 pstr->stream == SNDRV_PCM_STREAM_PLAYBACK ? 'p' : 'c');
501         if ((entry = snd_info_create_card_entry(pcm->card, name, pcm->card->proc_root)) == NULL)
502                 return -ENOMEM;
503         entry->mode = S_IFDIR | S_IRUGO | S_IXUGO;
504         if (snd_info_register(entry) < 0) {
505                 snd_info_free_entry(entry);
506                 return -ENOMEM;
507         }
508         pstr->proc_root = entry;
509
510         if ((entry = snd_info_create_card_entry(pcm->card, "info", pstr->proc_root)) != NULL) {
511                 snd_info_set_text_ops(entry, pstr, snd_pcm_stream_proc_info_read);
512                 if (snd_info_register(entry) < 0) {
513                         snd_info_free_entry(entry);
514                         entry = NULL;
515                 }
516         }
517         pstr->proc_info_entry = entry;
518
519 #ifdef CONFIG_SND_PCM_XRUN_DEBUG
520         if ((entry = snd_info_create_card_entry(pcm->card, "xrun_debug",
521                                                 pstr->proc_root)) != NULL) {
522                 entry->c.text.read = snd_pcm_xrun_debug_read;
523                 entry->c.text.write = snd_pcm_xrun_debug_write;
524                 entry->mode |= S_IWUSR;
525                 entry->private_data = pstr;
526                 if (snd_info_register(entry) < 0) {
527                         snd_info_free_entry(entry);
528                         entry = NULL;
529                 }
530         }
531         pstr->proc_xrun_debug_entry = entry;
532 #endif
533         return 0;
534 }
535
536 static int snd_pcm_stream_proc_done(struct snd_pcm_str *pstr)
537 {
538 #ifdef CONFIG_SND_PCM_XRUN_DEBUG
539         snd_info_free_entry(pstr->proc_xrun_debug_entry);
540         pstr->proc_xrun_debug_entry = NULL;
541 #endif
542         snd_info_free_entry(pstr->proc_info_entry);
543         pstr->proc_info_entry = NULL;
544         snd_info_free_entry(pstr->proc_root);
545         pstr->proc_root = NULL;
546         return 0;
547 }
548
549 static int snd_pcm_substream_proc_init(struct snd_pcm_substream *substream)
550 {
551         struct snd_info_entry *entry;
552         struct snd_card *card;
553         char name[16];
554
555         card = substream->pcm->card;
556
557         sprintf(name, "sub%i", substream->number);
558         if ((entry = snd_info_create_card_entry(card, name, substream->pstr->proc_root)) == NULL)
559                 return -ENOMEM;
560         entry->mode = S_IFDIR | S_IRUGO | S_IXUGO;
561         if (snd_info_register(entry) < 0) {
562                 snd_info_free_entry(entry);
563                 return -ENOMEM;
564         }
565         substream->proc_root = entry;
566
567         if ((entry = snd_info_create_card_entry(card, "info", substream->proc_root)) != NULL) {
568                 snd_info_set_text_ops(entry, substream,
569                                       snd_pcm_substream_proc_info_read);
570                 if (snd_info_register(entry) < 0) {
571                         snd_info_free_entry(entry);
572                         entry = NULL;
573                 }
574         }
575         substream->proc_info_entry = entry;
576
577         if ((entry = snd_info_create_card_entry(card, "hw_params", substream->proc_root)) != NULL) {
578                 snd_info_set_text_ops(entry, substream,
579                                       snd_pcm_substream_proc_hw_params_read);
580                 if (snd_info_register(entry) < 0) {
581                         snd_info_free_entry(entry);
582                         entry = NULL;
583                 }
584         }
585         substream->proc_hw_params_entry = entry;
586
587         if ((entry = snd_info_create_card_entry(card, "sw_params", substream->proc_root)) != NULL) {
588                 snd_info_set_text_ops(entry, substream,
589                                       snd_pcm_substream_proc_sw_params_read);
590                 if (snd_info_register(entry) < 0) {
591                         snd_info_free_entry(entry);
592                         entry = NULL;
593                 }
594         }
595         substream->proc_sw_params_entry = entry;
596
597         if ((entry = snd_info_create_card_entry(card, "status", substream->proc_root)) != NULL) {
598                 snd_info_set_text_ops(entry, substream,
599                                       snd_pcm_substream_proc_status_read);
600                 if (snd_info_register(entry) < 0) {
601                         snd_info_free_entry(entry);
602                         entry = NULL;
603                 }
604         }
605         substream->proc_status_entry = entry;
606
607         return 0;
608 }
609
610 static int snd_pcm_substream_proc_done(struct snd_pcm_substream *substream)
611 {
612         snd_info_free_entry(substream->proc_info_entry);
613         substream->proc_info_entry = NULL;
614         snd_info_free_entry(substream->proc_hw_params_entry);
615         substream->proc_hw_params_entry = NULL;
616         snd_info_free_entry(substream->proc_sw_params_entry);
617         substream->proc_sw_params_entry = NULL;
618         snd_info_free_entry(substream->proc_status_entry);
619         substream->proc_status_entry = NULL;
620         snd_info_free_entry(substream->proc_root);
621         substream->proc_root = NULL;
622         return 0;
623 }
624 #else /* !CONFIG_SND_VERBOSE_PROCFS */
625 static inline int snd_pcm_stream_proc_init(struct snd_pcm_str *pstr) { return 0; }
626 static inline int snd_pcm_stream_proc_done(struct snd_pcm_str *pstr) { return 0; }
627 static inline int snd_pcm_substream_proc_init(struct snd_pcm_substream *substream) { return 0; }
628 static inline int snd_pcm_substream_proc_done(struct snd_pcm_substream *substream) { return 0; }
629 #endif /* CONFIG_SND_VERBOSE_PROCFS */
630
631 /**
632  * snd_pcm_new_stream - create a new PCM stream
633  * @pcm: the pcm instance
634  * @stream: the stream direction, SNDRV_PCM_STREAM_XXX
635  * @substream_count: the number of substreams
636  *
637  * Creates a new stream for the pcm.
638  * The corresponding stream on the pcm must have been empty before
639  * calling this, i.e. zero must be given to the argument of
640  * snd_pcm_new().
641  *
642  * Return: Zero if successful, or a negative error code on failure.
643  */
644 int snd_pcm_new_stream(struct snd_pcm *pcm, int stream, int substream_count)
645 {
646         int idx, err;
647         struct snd_pcm_str *pstr = &pcm->streams[stream];
648         struct snd_pcm_substream *substream, *prev;
649
650 #if defined(CONFIG_SND_PCM_OSS) || defined(CONFIG_SND_PCM_OSS_MODULE)
651         mutex_init(&pstr->oss.setup_mutex);
652 #endif
653         pstr->stream = stream;
654         pstr->pcm = pcm;
655         pstr->substream_count = substream_count;
656         if (substream_count > 0 && !pcm->internal) {
657                 err = snd_pcm_stream_proc_init(pstr);
658                 if (err < 0) {
659                         snd_printk(KERN_ERR "Error in snd_pcm_stream_proc_init\n");
660                         return err;
661                 }
662         }
663         prev = NULL;
664         for (idx = 0, prev = NULL; idx < substream_count; idx++) {
665                 substream = kzalloc(sizeof(*substream), GFP_KERNEL);
666                 if (substream == NULL) {
667                         snd_printk(KERN_ERR "Cannot allocate PCM substream\n");
668                         return -ENOMEM;
669                 }
670                 substream->pcm = pcm;
671                 substream->pstr = pstr;
672                 substream->number = idx;
673                 substream->stream = stream;
674                 sprintf(substream->name, "subdevice #%i", idx);
675                 substream->buffer_bytes_max = UINT_MAX;
676                 if (prev == NULL)
677                         pstr->substream = substream;
678                 else
679                         prev->next = substream;
680
681                 if (!pcm->internal) {
682                         err = snd_pcm_substream_proc_init(substream);
683                         if (err < 0) {
684                                 snd_printk(KERN_ERR "Error in snd_pcm_stream_proc_init\n");
685                                 if (prev == NULL)
686                                         pstr->substream = NULL;
687                                 else
688                                         prev->next = NULL;
689                                 kfree(substream);
690                                 return err;
691                         }
692                 }
693                 substream->group = &substream->self_group;
694                 spin_lock_init(&substream->self_group.lock);
695                 INIT_LIST_HEAD(&substream->self_group.substreams);
696                 list_add_tail(&substream->link_list, &substream->self_group.substreams);
697                 atomic_set(&substream->mmap_count, 0);
698                 prev = substream;
699         }
700         return 0;
701 }                               
702
703 EXPORT_SYMBOL(snd_pcm_new_stream);
704
705 static int _snd_pcm_new(struct snd_card *card, const char *id, int device,
706                 int playback_count, int capture_count, bool internal,
707                 struct snd_pcm **rpcm)
708 {
709         struct snd_pcm *pcm;
710         int err;
711         static struct snd_device_ops ops = {
712                 .dev_free = snd_pcm_dev_free,
713                 .dev_register = snd_pcm_dev_register,
714                 .dev_disconnect = snd_pcm_dev_disconnect,
715         };
716
717         if (snd_BUG_ON(!card))
718                 return -ENXIO;
719         if (rpcm)
720                 *rpcm = NULL;
721         pcm = kzalloc(sizeof(*pcm), GFP_KERNEL);
722         if (pcm == NULL) {
723                 snd_printk(KERN_ERR "Cannot allocate PCM\n");
724                 return -ENOMEM;
725         }
726         pcm->card = card;
727         pcm->device = device;
728         pcm->internal = internal;
729         if (id)
730                 strlcpy(pcm->id, id, sizeof(pcm->id));
731         if ((err = snd_pcm_new_stream(pcm, SNDRV_PCM_STREAM_PLAYBACK, playback_count)) < 0) {
732                 snd_pcm_free(pcm);
733                 return err;
734         }
735         if ((err = snd_pcm_new_stream(pcm, SNDRV_PCM_STREAM_CAPTURE, capture_count)) < 0) {
736                 snd_pcm_free(pcm);
737                 return err;
738         }
739         mutex_init(&pcm->open_mutex);
740         init_waitqueue_head(&pcm->open_wait);
741         if ((err = snd_device_new(card, SNDRV_DEV_PCM, pcm, &ops)) < 0) {
742                 snd_pcm_free(pcm);
743                 return err;
744         }
745         if (rpcm)
746                 *rpcm = pcm;
747         return 0;
748 }
749
750 /**
751  * snd_pcm_new - create a new PCM instance
752  * @card: the card instance
753  * @id: the id string
754  * @device: the device index (zero based)
755  * @playback_count: the number of substreams for playback
756  * @capture_count: the number of substreams for capture
757  * @rpcm: the pointer to store the new pcm instance
758  *
759  * Creates a new PCM instance.
760  *
761  * The pcm operators have to be set afterwards to the new instance
762  * via snd_pcm_set_ops().
763  *
764  * Return: Zero if successful, or a negative error code on failure.
765  */
766 int snd_pcm_new(struct snd_card *card, const char *id, int device,
767                 int playback_count, int capture_count, struct snd_pcm **rpcm)
768 {
769         return _snd_pcm_new(card, id, device, playback_count, capture_count,
770                         false, rpcm);
771 }
772 EXPORT_SYMBOL(snd_pcm_new);
773
774 /**
775  * snd_pcm_new_internal - create a new internal PCM instance
776  * @card: the card instance
777  * @id: the id string
778  * @device: the device index (zero based - shared with normal PCMs)
779  * @playback_count: the number of substreams for playback
780  * @capture_count: the number of substreams for capture
781  * @rpcm: the pointer to store the new pcm instance
782  *
783  * Creates a new internal PCM instance with no userspace device or procfs
784  * entries. This is used by ASoC Back End PCMs in order to create a PCM that
785  * will only be used internally by kernel drivers. i.e. it cannot be opened
786  * by userspace. It provides existing ASoC components drivers with a substream
787  * and access to any private data.
788  *
789  * The pcm operators have to be set afterwards to the new instance
790  * via snd_pcm_set_ops().
791  *
792  * Return: Zero if successful, or a negative error code on failure.
793  */
794 int snd_pcm_new_internal(struct snd_card *card, const char *id, int device,
795         int playback_count, int capture_count,
796         struct snd_pcm **rpcm)
797 {
798         return _snd_pcm_new(card, id, device, playback_count, capture_count,
799                         true, rpcm);
800 }
801 EXPORT_SYMBOL(snd_pcm_new_internal);
802
803 static void snd_pcm_free_stream(struct snd_pcm_str * pstr)
804 {
805         struct snd_pcm_substream *substream, *substream_next;
806 #if defined(CONFIG_SND_PCM_OSS) || defined(CONFIG_SND_PCM_OSS_MODULE)
807         struct snd_pcm_oss_setup *setup, *setupn;
808 #endif
809         substream = pstr->substream;
810         while (substream) {
811                 substream_next = substream->next;
812                 snd_pcm_timer_done(substream);
813                 snd_pcm_substream_proc_done(substream);
814                 kfree(substream);
815                 substream = substream_next;
816         }
817         snd_pcm_stream_proc_done(pstr);
818 #if defined(CONFIG_SND_PCM_OSS) || defined(CONFIG_SND_PCM_OSS_MODULE)
819         for (setup = pstr->oss.setup_list; setup; setup = setupn) {
820                 setupn = setup->next;
821                 kfree(setup->task_name);
822                 kfree(setup);
823         }
824 #endif
825 }
826
827 static int snd_pcm_free(struct snd_pcm *pcm)
828 {
829         struct snd_pcm_notify *notify;
830
831         if (!pcm)
832                 return 0;
833         list_for_each_entry(notify, &snd_pcm_notify_list, list) {
834                 notify->n_unregister(pcm);
835         }
836         if (pcm->private_free)
837                 pcm->private_free(pcm);
838         snd_pcm_lib_preallocate_free_for_all(pcm);
839         snd_pcm_free_stream(&pcm->streams[SNDRV_PCM_STREAM_PLAYBACK]);
840         snd_pcm_free_stream(&pcm->streams[SNDRV_PCM_STREAM_CAPTURE]);
841         kfree(pcm);
842         return 0;
843 }
844
845 static int snd_pcm_dev_free(struct snd_device *device)
846 {
847         struct snd_pcm *pcm = device->device_data;
848         return snd_pcm_free(pcm);
849 }
850
851 int snd_pcm_attach_substream(struct snd_pcm *pcm, int stream,
852                              struct file *file,
853                              struct snd_pcm_substream **rsubstream)
854 {
855         struct snd_pcm_str * pstr;
856         struct snd_pcm_substream *substream;
857         struct snd_pcm_runtime *runtime;
858         struct snd_ctl_file *kctl;
859         struct snd_card *card;
860         int prefer_subdevice = -1;
861         size_t size;
862
863         if (snd_BUG_ON(!pcm || !rsubstream))
864                 return -ENXIO;
865         *rsubstream = NULL;
866         pstr = &pcm->streams[stream];
867         if (pstr->substream == NULL || pstr->substream_count == 0)
868                 return -ENODEV;
869
870         card = pcm->card;
871         read_lock(&card->ctl_files_rwlock);
872         list_for_each_entry(kctl, &card->ctl_files, list) {
873                 if (kctl->pid == task_pid(current)) {
874                         prefer_subdevice = kctl->prefer_pcm_subdevice;
875                         if (prefer_subdevice != -1)
876                                 break;
877                 }
878         }
879         read_unlock(&card->ctl_files_rwlock);
880
881         switch (stream) {
882         case SNDRV_PCM_STREAM_PLAYBACK:
883                 if (pcm->info_flags & SNDRV_PCM_INFO_HALF_DUPLEX) {
884                         for (substream = pcm->streams[SNDRV_PCM_STREAM_CAPTURE].substream; substream; substream = substream->next) {
885                                 if (SUBSTREAM_BUSY(substream))
886                                         return -EAGAIN;
887                         }
888                 }
889                 break;
890         case SNDRV_PCM_STREAM_CAPTURE:
891                 if (pcm->info_flags & SNDRV_PCM_INFO_HALF_DUPLEX) {
892                         for (substream = pcm->streams[SNDRV_PCM_STREAM_PLAYBACK].substream; substream; substream = substream->next) {
893                                 if (SUBSTREAM_BUSY(substream))
894                                         return -EAGAIN;
895                         }
896                 }
897                 break;
898         default:
899                 return -EINVAL;
900         }
901
902         if (file->f_flags & O_APPEND) {
903                 if (prefer_subdevice < 0) {
904                         if (pstr->substream_count > 1)
905                                 return -EINVAL; /* must be unique */
906                         substream = pstr->substream;
907                 } else {
908                         for (substream = pstr->substream; substream;
909                              substream = substream->next)
910                                 if (substream->number == prefer_subdevice)
911                                         break;
912                 }
913                 if (! substream)
914                         return -ENODEV;
915                 if (! SUBSTREAM_BUSY(substream))
916                         return -EBADFD;
917                 substream->ref_count++;
918                 *rsubstream = substream;
919                 return 0;
920         }
921
922         if (prefer_subdevice >= 0) {
923                 for (substream = pstr->substream; substream; substream = substream->next)
924                         if (!SUBSTREAM_BUSY(substream) && substream->number == prefer_subdevice)
925                                 goto __ok;
926         }
927         for (substream = pstr->substream; substream; substream = substream->next)
928                 if (!SUBSTREAM_BUSY(substream))
929                         break;
930       __ok:
931         if (substream == NULL)
932                 return -EAGAIN;
933
934         runtime = kzalloc(sizeof(*runtime), GFP_KERNEL);
935         if (runtime == NULL)
936                 return -ENOMEM;
937
938         size = PAGE_ALIGN(sizeof(struct snd_pcm_mmap_status));
939         runtime->status = snd_malloc_pages(size, GFP_KERNEL);
940         if (runtime->status == NULL) {
941                 kfree(runtime);
942                 return -ENOMEM;
943         }
944         memset((void*)runtime->status, 0, size);
945
946         size = PAGE_ALIGN(sizeof(struct snd_pcm_mmap_control));
947         runtime->control = snd_malloc_pages(size, GFP_KERNEL);
948         if (runtime->control == NULL) {
949                 snd_free_pages((void*)runtime->status,
950                                PAGE_ALIGN(sizeof(struct snd_pcm_mmap_status)));
951                 kfree(runtime);
952                 return -ENOMEM;
953         }
954         memset((void*)runtime->control, 0, size);
955
956         init_waitqueue_head(&runtime->sleep);
957         init_waitqueue_head(&runtime->tsleep);
958
959         runtime->status->state = SNDRV_PCM_STATE_OPEN;
960
961         substream->runtime = runtime;
962         substream->private_data = pcm->private_data;
963         substream->ref_count = 1;
964         substream->f_flags = file->f_flags;
965         substream->pid = get_pid(task_pid(current));
966         pstr->substream_opened++;
967         *rsubstream = substream;
968         return 0;
969 }
970
971 void snd_pcm_detach_substream(struct snd_pcm_substream *substream)
972 {
973         struct snd_pcm_runtime *runtime;
974
975         if (PCM_RUNTIME_CHECK(substream))
976                 return;
977         runtime = substream->runtime;
978         if (runtime->private_free != NULL)
979                 runtime->private_free(runtime);
980         snd_free_pages((void*)runtime->status,
981                        PAGE_ALIGN(sizeof(struct snd_pcm_mmap_status)));
982         snd_free_pages((void*)runtime->control,
983                        PAGE_ALIGN(sizeof(struct snd_pcm_mmap_control)));
984         kfree(runtime->hw_constraints.rules);
985 #ifdef CONFIG_SND_PCM_XRUN_DEBUG
986         kfree(runtime->hwptr_log);
987 #endif
988         kfree(runtime);
989         substream->runtime = NULL;
990         put_pid(substream->pid);
991         substream->pid = NULL;
992         substream->pstr->substream_opened--;
993 }
994
995 static ssize_t show_pcm_class(struct device *dev,
996                               struct device_attribute *attr, char *buf)
997 {
998         struct snd_pcm *pcm;
999         const char *str;
1000         static const char *strs[SNDRV_PCM_CLASS_LAST + 1] = {
1001                 [SNDRV_PCM_CLASS_GENERIC] = "generic",
1002                 [SNDRV_PCM_CLASS_MULTI] = "multi",
1003                 [SNDRV_PCM_CLASS_MODEM] = "modem",
1004                 [SNDRV_PCM_CLASS_DIGITIZER] = "digitizer",
1005         };
1006
1007         if (! (pcm = dev_get_drvdata(dev)) ||
1008             pcm->dev_class > SNDRV_PCM_CLASS_LAST)
1009                 str = "none";
1010         else
1011                 str = strs[pcm->dev_class];
1012         return snprintf(buf, PAGE_SIZE, "%s\n", str);
1013 }
1014
1015 static struct device_attribute pcm_attrs =
1016         __ATTR(pcm_class, S_IRUGO, show_pcm_class, NULL);
1017
1018 static int snd_pcm_dev_register(struct snd_device *device)
1019 {
1020         int cidx, err;
1021         struct snd_pcm_substream *substream;
1022         struct snd_pcm_notify *notify;
1023         char str[16];
1024         struct snd_pcm *pcm;
1025         struct device *dev;
1026
1027         if (snd_BUG_ON(!device || !device->device_data))
1028                 return -ENXIO;
1029         pcm = device->device_data;
1030         mutex_lock(&register_mutex);
1031         err = snd_pcm_add(pcm);
1032         if (err) {
1033                 mutex_unlock(&register_mutex);
1034                 return err;
1035         }
1036         for (cidx = 0; cidx < 2; cidx++) {
1037                 int devtype = -1;
1038                 if (pcm->streams[cidx].substream == NULL || pcm->internal)
1039                         continue;
1040                 switch (cidx) {
1041                 case SNDRV_PCM_STREAM_PLAYBACK:
1042                         sprintf(str, "pcmC%iD%ip", pcm->card->number, pcm->device);
1043                         devtype = SNDRV_DEVICE_TYPE_PCM_PLAYBACK;
1044                         break;
1045                 case SNDRV_PCM_STREAM_CAPTURE:
1046                         sprintf(str, "pcmC%iD%ic", pcm->card->number, pcm->device);
1047                         devtype = SNDRV_DEVICE_TYPE_PCM_CAPTURE;
1048                         break;
1049                 }
1050                 /* device pointer to use, pcm->dev takes precedence if
1051                  * it is assigned, otherwise fall back to card's device
1052                  * if possible */
1053                 dev = pcm->dev;
1054                 if (!dev)
1055                         dev = snd_card_get_device_link(pcm->card);
1056                 /* register pcm */
1057                 err = snd_register_device_for_dev(devtype, pcm->card,
1058                                                   pcm->device,
1059                                                   &snd_pcm_f_ops[cidx],
1060                                                   pcm, str, dev);
1061                 if (err < 0) {
1062                         list_del(&pcm->list);
1063                         mutex_unlock(&register_mutex);
1064                         return err;
1065                 }
1066                 snd_add_device_sysfs_file(devtype, pcm->card, pcm->device,
1067                                           &pcm_attrs);
1068                 for (substream = pcm->streams[cidx].substream; substream; substream = substream->next)
1069                         snd_pcm_timer_init(substream);
1070         }
1071
1072         list_for_each_entry(notify, &snd_pcm_notify_list, list)
1073                 notify->n_register(pcm);
1074
1075         mutex_unlock(&register_mutex);
1076         return 0;
1077 }
1078
1079 static int snd_pcm_dev_disconnect(struct snd_device *device)
1080 {
1081         struct snd_pcm *pcm = device->device_data;
1082         struct snd_pcm_notify *notify;
1083         struct snd_pcm_substream *substream;
1084         int cidx, devtype;
1085
1086         mutex_lock(&register_mutex);
1087         if (list_empty(&pcm->list))
1088                 goto unlock;
1089
1090         mutex_lock(&pcm->open_mutex);
1091         wake_up(&pcm->open_wait);
1092         list_del_init(&pcm->list);
1093         for (cidx = 0; cidx < 2; cidx++)
1094                 for (substream = pcm->streams[cidx].substream; substream; substream = substream->next) {
1095                         snd_pcm_stream_lock_irq(substream);
1096                         if (substream->runtime) {
1097                                 substream->runtime->status->state = SNDRV_PCM_STATE_DISCONNECTED;
1098                                 wake_up(&substream->runtime->sleep);
1099                                 wake_up(&substream->runtime->tsleep);
1100                         }
1101                         snd_pcm_stream_unlock_irq(substream);
1102                 }
1103         list_for_each_entry(notify, &snd_pcm_notify_list, list) {
1104                 notify->n_disconnect(pcm);
1105         }
1106         for (cidx = 0; cidx < 2; cidx++) {
1107                 devtype = -1;
1108                 switch (cidx) {
1109                 case SNDRV_PCM_STREAM_PLAYBACK:
1110                         devtype = SNDRV_DEVICE_TYPE_PCM_PLAYBACK;
1111                         break;
1112                 case SNDRV_PCM_STREAM_CAPTURE:
1113                         devtype = SNDRV_DEVICE_TYPE_PCM_CAPTURE;
1114                         break;
1115                 }
1116                 snd_unregister_device(devtype, pcm->card, pcm->device);
1117                 if (pcm->streams[cidx].chmap_kctl) {
1118                         snd_ctl_remove(pcm->card, pcm->streams[cidx].chmap_kctl);
1119                         pcm->streams[cidx].chmap_kctl = NULL;
1120                 }
1121         }
1122         mutex_unlock(&pcm->open_mutex);
1123  unlock:
1124         mutex_unlock(&register_mutex);
1125         return 0;
1126 }
1127
1128 int snd_pcm_notify(struct snd_pcm_notify *notify, int nfree)
1129 {
1130         struct snd_pcm *pcm;
1131
1132         if (snd_BUG_ON(!notify ||
1133                        !notify->n_register ||
1134                        !notify->n_unregister ||
1135                        !notify->n_disconnect))
1136                 return -EINVAL;
1137         mutex_lock(&register_mutex);
1138         if (nfree) {
1139                 list_del(&notify->list);
1140                 list_for_each_entry(pcm, &snd_pcm_devices, list)
1141                         notify->n_unregister(pcm);
1142         } else {
1143                 list_add_tail(&notify->list, &snd_pcm_notify_list);
1144                 list_for_each_entry(pcm, &snd_pcm_devices, list)
1145                         notify->n_register(pcm);
1146         }
1147         mutex_unlock(&register_mutex);
1148         return 0;
1149 }
1150
1151 EXPORT_SYMBOL(snd_pcm_notify);
1152
1153 #ifdef CONFIG_PROC_FS
1154 /*
1155  *  Info interface
1156  */
1157
1158 static void snd_pcm_proc_read(struct snd_info_entry *entry,
1159                               struct snd_info_buffer *buffer)
1160 {
1161         struct snd_pcm *pcm;
1162
1163         mutex_lock(&register_mutex);
1164         list_for_each_entry(pcm, &snd_pcm_devices, list) {
1165                 snd_iprintf(buffer, "%02i-%02i: %s : %s",
1166                             pcm->card->number, pcm->device, pcm->id, pcm->name);
1167                 if (pcm->streams[SNDRV_PCM_STREAM_PLAYBACK].substream)
1168                         snd_iprintf(buffer, " : playback %i",
1169                                     pcm->streams[SNDRV_PCM_STREAM_PLAYBACK].substream_count);
1170                 if (pcm->streams[SNDRV_PCM_STREAM_CAPTURE].substream)
1171                         snd_iprintf(buffer, " : capture %i",
1172                                     pcm->streams[SNDRV_PCM_STREAM_CAPTURE].substream_count);
1173                 snd_iprintf(buffer, "\n");
1174         }
1175         mutex_unlock(&register_mutex);
1176 }
1177
1178 static struct snd_info_entry *snd_pcm_proc_entry;
1179
1180 static void snd_pcm_proc_init(void)
1181 {
1182         struct snd_info_entry *entry;
1183
1184         if ((entry = snd_info_create_module_entry(THIS_MODULE, "pcm", NULL)) != NULL) {
1185                 snd_info_set_text_ops(entry, NULL, snd_pcm_proc_read);
1186                 if (snd_info_register(entry) < 0) {
1187                         snd_info_free_entry(entry);
1188                         entry = NULL;
1189                 }
1190         }
1191         snd_pcm_proc_entry = entry;
1192 }
1193
1194 static void snd_pcm_proc_done(void)
1195 {
1196         snd_info_free_entry(snd_pcm_proc_entry);
1197 }
1198
1199 #else /* !CONFIG_PROC_FS */
1200 #define snd_pcm_proc_init()
1201 #define snd_pcm_proc_done()
1202 #endif /* CONFIG_PROC_FS */
1203
1204
1205 /*
1206  *  ENTRY functions
1207  */
1208
1209 static int __init alsa_pcm_init(void)
1210 {
1211         snd_ctl_register_ioctl(snd_pcm_control_ioctl);
1212         snd_ctl_register_ioctl_compat(snd_pcm_control_ioctl);
1213         snd_pcm_proc_init();
1214         return 0;
1215 }
1216
1217 static void __exit alsa_pcm_exit(void)
1218 {
1219         snd_ctl_unregister_ioctl(snd_pcm_control_ioctl);
1220         snd_ctl_unregister_ioctl_compat(snd_pcm_control_ioctl);
1221         snd_pcm_proc_done();
1222 }
1223
1224 module_init(alsa_pcm_init)
1225 module_exit(alsa_pcm_exit)