diff options
Diffstat (limited to 'sound')
-rw-r--r-- | sound/core/Kconfig | 9 | ||||
-rw-r--r-- | sound/core/init.c | 25 |
2 files changed, 25 insertions, 9 deletions
diff --git a/sound/core/Kconfig b/sound/core/Kconfig index b413ed05e74d..c0c2f57a0d6f 100644 --- a/sound/core/Kconfig +++ b/sound/core/Kconfig | |||
@@ -157,6 +157,15 @@ config SND_DYNAMIC_MINORS | |||
157 | 157 | ||
158 | If you are unsure about this, say N here. | 158 | If you are unsure about this, say N here. |
159 | 159 | ||
160 | config SND_MAX_CARDS | ||
161 | int "Max number of sound cards" | ||
162 | range 4 256 | ||
163 | default 32 | ||
164 | depends on SND_DYNAMIC_MINORS | ||
165 | help | ||
166 | Specify the max number of sound cards that can be assigned | ||
167 | on a single machine. | ||
168 | |||
160 | config SND_SUPPORT_OLD_API | 169 | config SND_SUPPORT_OLD_API |
161 | bool "Support old ALSA API" | 170 | bool "Support old ALSA API" |
162 | default y | 171 | default y |
diff --git a/sound/core/init.c b/sound/core/init.c index ed4a4811b6a1..6b9087115da2 100644 --- a/sound/core/init.c +++ b/sound/core/init.c | |||
@@ -46,7 +46,8 @@ static LIST_HEAD(shutdown_files); | |||
46 | 46 | ||
47 | static const struct file_operations snd_shutdown_f_ops; | 47 | static const struct file_operations snd_shutdown_f_ops; |
48 | 48 | ||
49 | static unsigned int snd_cards_lock; /* locked for registering/using */ | 49 | /* locked for registering/using */ |
50 | static DECLARE_BITMAP(snd_cards_lock, SNDRV_CARDS); | ||
50 | struct snd_card *snd_cards[SNDRV_CARDS]; | 51 | struct snd_card *snd_cards[SNDRV_CARDS]; |
51 | EXPORT_SYMBOL(snd_cards); | 52 | EXPORT_SYMBOL(snd_cards); |
52 | 53 | ||
@@ -167,29 +168,35 @@ int snd_card_create(int idx, const char *xid, | |||
167 | err = 0; | 168 | err = 0; |
168 | mutex_lock(&snd_card_mutex); | 169 | mutex_lock(&snd_card_mutex); |
169 | if (idx < 0) { | 170 | if (idx < 0) { |
170 | for (idx2 = 0; idx2 < SNDRV_CARDS; idx2++) | 171 | for (idx2 = 0; idx2 < SNDRV_CARDS; idx2++) { |
171 | /* idx == -1 == 0xffff means: take any free slot */ | 172 | /* idx == -1 == 0xffff means: take any free slot */ |
172 | if (~snd_cards_lock & idx & 1<<idx2) { | 173 | if (idx2 < sizeof(int) && !(idx & (1U << idx2))) |
174 | continue; | ||
175 | if (!test_bit(idx2, snd_cards_lock)) { | ||
173 | if (module_slot_match(module, idx2)) { | 176 | if (module_slot_match(module, idx2)) { |
174 | idx = idx2; | 177 | idx = idx2; |
175 | break; | 178 | break; |
176 | } | 179 | } |
177 | } | 180 | } |
181 | } | ||
178 | } | 182 | } |
179 | if (idx < 0) { | 183 | if (idx < 0) { |
180 | for (idx2 = 0; idx2 < SNDRV_CARDS; idx2++) | 184 | for (idx2 = 0; idx2 < SNDRV_CARDS; idx2++) { |
181 | /* idx == -1 == 0xffff means: take any free slot */ | 185 | /* idx == -1 == 0xffff means: take any free slot */ |
182 | if (~snd_cards_lock & idx & 1<<idx2) { | 186 | if (idx2 < sizeof(int) && !(idx & (1U << idx2))) |
187 | continue; | ||
188 | if (!test_bit(idx2, snd_cards_lock)) { | ||
183 | if (!slots[idx2] || !*slots[idx2]) { | 189 | if (!slots[idx2] || !*slots[idx2]) { |
184 | idx = idx2; | 190 | idx = idx2; |
185 | break; | 191 | break; |
186 | } | 192 | } |
187 | } | 193 | } |
194 | } | ||
188 | } | 195 | } |
189 | if (idx < 0) | 196 | if (idx < 0) |
190 | err = -ENODEV; | 197 | err = -ENODEV; |
191 | else if (idx < snd_ecards_limit) { | 198 | else if (idx < snd_ecards_limit) { |
192 | if (snd_cards_lock & (1 << idx)) | 199 | if (test_bit(idx, snd_cards_lock)) |
193 | err = -EBUSY; /* invalid */ | 200 | err = -EBUSY; /* invalid */ |
194 | } else if (idx >= SNDRV_CARDS) | 201 | } else if (idx >= SNDRV_CARDS) |
195 | err = -ENODEV; | 202 | err = -ENODEV; |
@@ -199,7 +206,7 @@ int snd_card_create(int idx, const char *xid, | |||
199 | idx, snd_ecards_limit - 1, err); | 206 | idx, snd_ecards_limit - 1, err); |
200 | goto __error; | 207 | goto __error; |
201 | } | 208 | } |
202 | snd_cards_lock |= 1 << idx; /* lock it */ | 209 | set_bit(idx, snd_cards_lock); /* lock it */ |
203 | if (idx >= snd_ecards_limit) | 210 | if (idx >= snd_ecards_limit) |
204 | snd_ecards_limit = idx + 1; /* increase the limit */ | 211 | snd_ecards_limit = idx + 1; /* increase the limit */ |
205 | mutex_unlock(&snd_card_mutex); | 212 | mutex_unlock(&snd_card_mutex); |
@@ -249,7 +256,7 @@ int snd_card_locked(int card) | |||
249 | int locked; | 256 | int locked; |
250 | 257 | ||
251 | mutex_lock(&snd_card_mutex); | 258 | mutex_lock(&snd_card_mutex); |
252 | locked = snd_cards_lock & (1 << card); | 259 | locked = test_bit(card, snd_cards_lock); |
253 | mutex_unlock(&snd_card_mutex); | 260 | mutex_unlock(&snd_card_mutex); |
254 | return locked; | 261 | return locked; |
255 | } | 262 | } |
@@ -361,7 +368,7 @@ int snd_card_disconnect(struct snd_card *card) | |||
361 | /* phase 1: disable fops (user space) operations for ALSA API */ | 368 | /* phase 1: disable fops (user space) operations for ALSA API */ |
362 | mutex_lock(&snd_card_mutex); | 369 | mutex_lock(&snd_card_mutex); |
363 | snd_cards[card->number] = NULL; | 370 | snd_cards[card->number] = NULL; |
364 | snd_cards_lock &= ~(1 << card->number); | 371 | clear_bit(card->number, snd_cards_lock); |
365 | mutex_unlock(&snd_card_mutex); | 372 | mutex_unlock(&snd_card_mutex); |
366 | 373 | ||
367 | /* phase 2: replace file->f_op with special dummy operations */ | 374 | /* phase 2: replace file->f_op with special dummy operations */ |