2 * sound/oss/dev_table.c
7 * Copyright (C) by Hannu Savolainen 1993-1997
9 * OSS/Free for Linux is distributed under the GNU GENERAL PUBLIC LICENSE (GPL)
10 * Version 2 (June 1991). See the "COPYING" file distributed with this software
14 #include <linux/init.h>
16 #include "sound_config.h"
18 struct audio_operations
*audio_devs
[MAX_AUDIO_DEV
];
19 EXPORT_SYMBOL(audio_devs
);
22 EXPORT_SYMBOL(num_audiodevs
);
24 struct mixer_operations
*mixer_devs
[MAX_MIXER_DEV
];
25 EXPORT_SYMBOL(mixer_devs
);
28 EXPORT_SYMBOL(num_mixers
);
30 struct synth_operations
*synth_devs
[MAX_SYNTH_DEV
+MAX_MIDI_DEV
];
31 EXPORT_SYMBOL(synth_devs
);
35 struct midi_operations
*midi_devs
[MAX_MIDI_DEV
];
36 EXPORT_SYMBOL(midi_devs
);
39 EXPORT_SYMBOL(num_midis
);
41 struct sound_timer_operations
*sound_timer_devs
[MAX_TIMER_DEV
] = {
42 &default_sound_timer
, NULL
44 EXPORT_SYMBOL(sound_timer_devs
);
46 int num_sound_timers
= 1;
49 static int sound_alloc_audiodev(void);
51 int sound_install_audiodrv(int vers
, char *name
, struct audio_driver
*driver
,
52 int driver_size
, int flags
, unsigned int format_mask
,
53 void *devc
, int dma1
, int dma2
)
55 struct audio_driver
*d
;
56 struct audio_operations
*op
;
59 if (vers
!= AUDIO_DRIVER_VERSION
|| driver_size
> sizeof(struct audio_driver
)) {
60 printk(KERN_ERR
"Sound: Incompatible audio driver for %s\n", name
);
63 num
= sound_alloc_audiodev();
66 printk(KERN_ERR
"sound: Too many audio drivers\n");
69 d
= (struct audio_driver
*) (sound_mem_blocks
[sound_nblocks
] = vmalloc(sizeof(struct audio_driver
)));
71 if (sound_nblocks
>= MAX_MEM_BLOCKS
)
72 sound_nblocks
= MAX_MEM_BLOCKS
- 1;
74 op
= (struct audio_operations
*) (sound_mem_blocks
[sound_nblocks
] = vzalloc(sizeof(struct audio_operations
)));
76 if (sound_nblocks
>= MAX_MEM_BLOCKS
)
77 sound_nblocks
= MAX_MEM_BLOCKS
- 1;
79 if (d
== NULL
|| op
== NULL
) {
80 printk(KERN_ERR
"Sound: Can't allocate driver for (%s)\n", name
);
81 sound_unload_audiodev(num
);
84 init_waitqueue_head(&op
->in_sleeper
);
85 init_waitqueue_head(&op
->out_sleeper
);
86 init_waitqueue_head(&op
->poll_sleeper
);
87 if (driver_size
< sizeof(struct audio_driver
))
88 memset((char *) d
, 0, sizeof(struct audio_driver
));
90 memcpy((char *) d
, (char *) driver
, driver_size
);
93 strlcpy(op
->name
, name
, sizeof(op
->name
));
95 op
->format_mask
= format_mask
;
101 audio_devs
[num
] = op
;
103 DMAbuf_init(num
, dma1
, dma2
);
105 audio_init_devices();
108 EXPORT_SYMBOL(sound_install_audiodrv
);
110 int sound_install_mixer(int vers
, char *name
, struct mixer_operations
*driver
,
111 int driver_size
, void *devc
)
113 struct mixer_operations
*op
;
115 int n
= sound_alloc_mixerdev();
118 printk(KERN_ERR
"Sound: Too many mixer drivers\n");
121 if (vers
!= MIXER_DRIVER_VERSION
||
122 driver_size
> sizeof(struct mixer_operations
)) {
123 printk(KERN_ERR
"Sound: Incompatible mixer driver for %s\n", name
);
127 /* FIXME: This leaks a mixer_operations struct every time its called
128 until you unload sound! */
130 op
= (struct mixer_operations
*) (sound_mem_blocks
[sound_nblocks
] = vzalloc(sizeof(struct mixer_operations
)));
132 if (sound_nblocks
>= MAX_MEM_BLOCKS
)
133 sound_nblocks
= MAX_MEM_BLOCKS
- 1;
136 printk(KERN_ERR
"Sound: Can't allocate mixer driver for (%s)\n", name
);
139 memcpy((char *) op
, (char *) driver
, driver_size
);
141 strlcpy(op
->name
, name
, sizeof(op
->name
));
147 EXPORT_SYMBOL(sound_install_mixer
);
149 void sound_unload_audiodev(int dev
)
153 audio_devs
[dev
] = NULL
;
154 unregister_sound_dsp((dev
<<4)+3);
157 EXPORT_SYMBOL(sound_unload_audiodev
);
159 static int sound_alloc_audiodev(void)
161 int i
= register_sound_dsp(&oss_sound_fops
, -1);
166 num_audiodevs
= i
+ 1;
170 int sound_alloc_mididev(void)
172 int i
= register_sound_midi(&oss_sound_fops
, -1);
180 EXPORT_SYMBOL(sound_alloc_mididev
);
182 int sound_alloc_synthdev(void)
186 for (i
= 0; i
< MAX_SYNTH_DEV
; i
++) {
187 if (synth_devs
[i
] == NULL
) {
195 EXPORT_SYMBOL(sound_alloc_synthdev
);
197 int sound_alloc_mixerdev(void)
199 int i
= register_sound_mixer(&oss_sound_fops
, -1);
207 EXPORT_SYMBOL(sound_alloc_mixerdev
);
209 int sound_alloc_timerdev(void)
213 for (i
= 0; i
< MAX_TIMER_DEV
; i
++) {
214 if (sound_timer_devs
[i
] == NULL
) {
215 if (i
>= num_sound_timers
)
222 EXPORT_SYMBOL(sound_alloc_timerdev
);
224 void sound_unload_mixerdev(int dev
)
227 mixer_devs
[dev
] = NULL
;
228 unregister_sound_mixer(dev
<<4);
232 EXPORT_SYMBOL(sound_unload_mixerdev
);
234 void sound_unload_mididev(int dev
)
237 midi_devs
[dev
] = NULL
;
238 unregister_sound_midi((dev
<<4)+2);
241 EXPORT_SYMBOL(sound_unload_mididev
);
243 void sound_unload_synthdev(int dev
)
246 synth_devs
[dev
] = NULL
;
248 EXPORT_SYMBOL(sound_unload_synthdev
);
250 void sound_unload_timerdev(int dev
)
253 sound_timer_devs
[dev
] = NULL
;
255 EXPORT_SYMBOL(sound_unload_timerdev
);