aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorBartlomiej Zolnierkiewicz <bzolnier@gmail.com>2009-08-23 09:27:25 -0400
committerTakashi Iwai <tiwai@suse.de>2009-08-23 12:58:07 -0400
commit70bdbd3d1ae9c4ca3e84a43df34262face26575d (patch)
tree667e5e1b54749f5dedfabb22f5d884429332a145
parentf065fabc864f4c98857bf67caa2365e9f8545751 (diff)
ALSA: ali5451: fix timeout handling in snd_ali_{codecs,timer}_ready()
Modify loops in such way that the register value is checked also after the timeout condition, just in case the heavy interrupt load etc. caused the thread to sleep for the time period exceeding the timeout value. While at it remove an extra ALI_STIMER read from snd_ali_stimer_ready(). Reported-by: Jack Byer <ojbyer@usa.net> Signed-off-by: Bartlomiej Zolnierkiewicz <bzolnier@gmail.com> Signed-off-by: Takashi Iwai <tiwai@suse.de>
-rw-r--r--sound/pci/ali5451/ali5451.c18
1 files changed, 12 insertions, 6 deletions
diff --git a/sound/pci/ali5451/ali5451.c b/sound/pci/ali5451/ali5451.c
index c551006e2920..76d76c08339b 100644
--- a/sound/pci/ali5451/ali5451.c
+++ b/sound/pci/ali5451/ali5451.c
@@ -310,12 +310,16 @@ static int snd_ali_codec_ready(struct snd_ali *codec,
310 unsigned int res; 310 unsigned int res;
311 311
312 end_time = jiffies + msecs_to_jiffies(250); 312 end_time = jiffies + msecs_to_jiffies(250);
313 do { 313
314 for (;;) {
314 res = snd_ali_5451_peek(codec,port); 315 res = snd_ali_5451_peek(codec,port);
315 if (!(res & 0x8000)) 316 if (!(res & 0x8000))
316 return 0; 317 return 0;
318 if (!time_after_eq(end_time, jiffies))
319 break;
317 schedule_timeout_uninterruptible(1); 320 schedule_timeout_uninterruptible(1);
318 } while (time_after_eq(end_time, jiffies)); 321 }
322
319 snd_ali_5451_poke(codec, port, res & ~0x8000); 323 snd_ali_5451_poke(codec, port, res & ~0x8000);
320 snd_printdd("ali_codec_ready: codec is not ready.\n "); 324 snd_printdd("ali_codec_ready: codec is not ready.\n ");
321 return -EIO; 325 return -EIO;
@@ -327,15 +331,17 @@ static int snd_ali_stimer_ready(struct snd_ali *codec)
327 unsigned long dwChk1,dwChk2; 331 unsigned long dwChk1,dwChk2;
328 332
329 dwChk1 = snd_ali_5451_peek(codec, ALI_STIMER); 333 dwChk1 = snd_ali_5451_peek(codec, ALI_STIMER);
330 dwChk2 = snd_ali_5451_peek(codec, ALI_STIMER);
331
332 end_time = jiffies + msecs_to_jiffies(250); 334 end_time = jiffies + msecs_to_jiffies(250);
333 do { 335
336 for (;;) {
334 dwChk2 = snd_ali_5451_peek(codec, ALI_STIMER); 337 dwChk2 = snd_ali_5451_peek(codec, ALI_STIMER);
335 if (dwChk2 != dwChk1) 338 if (dwChk2 != dwChk1)
336 return 0; 339 return 0;
340 if (!time_after_eq(end_time, jiffies))
341 break;
337 schedule_timeout_uninterruptible(1); 342 schedule_timeout_uninterruptible(1);
338 } while (time_after_eq(end_time, jiffies)); 343 }
344
339 snd_printk(KERN_ERR "ali_stimer_read: stimer is not ready.\n"); 345 snd_printk(KERN_ERR "ali_stimer_read: stimer is not ready.\n");
340 return -EIO; 346 return -EIO;
341} 347}