diff options
| -rw-r--r-- | drivers/media/radio/radio-cadet.c | 12 |
1 files changed, 9 insertions, 3 deletions
diff --git a/drivers/media/radio/radio-cadet.c b/drivers/media/radio/radio-cadet.c index b701ea6e7c7..bc9ad0897c5 100644 --- a/drivers/media/radio/radio-cadet.c +++ b/drivers/media/radio/radio-cadet.c | |||
| @@ -328,11 +328,10 @@ static ssize_t cadet_read(struct file *file, char __user *data, size_t count, lo | |||
| 328 | unsigned char readbuf[RDS_BUFFER]; | 328 | unsigned char readbuf[RDS_BUFFER]; |
| 329 | int i = 0; | 329 | int i = 0; |
| 330 | 330 | ||
| 331 | mutex_lock(&dev->lock); | ||
| 331 | if (dev->rdsstat == 0) { | 332 | if (dev->rdsstat == 0) { |
| 332 | mutex_lock(&dev->lock); | ||
| 333 | dev->rdsstat = 1; | 333 | dev->rdsstat = 1; |
| 334 | outb(0x80, dev->io); /* Select RDS fifo */ | 334 | outb(0x80, dev->io); /* Select RDS fifo */ |
| 335 | mutex_unlock(&dev->lock); | ||
| 336 | init_timer(&dev->readtimer); | 335 | init_timer(&dev->readtimer); |
| 337 | dev->readtimer.function = cadet_handler; | 336 | dev->readtimer.function = cadet_handler; |
| 338 | dev->readtimer.data = (unsigned long)dev; | 337 | dev->readtimer.data = (unsigned long)dev; |
| @@ -340,12 +339,15 @@ static ssize_t cadet_read(struct file *file, char __user *data, size_t count, lo | |||
| 340 | add_timer(&dev->readtimer); | 339 | add_timer(&dev->readtimer); |
| 341 | } | 340 | } |
| 342 | if (dev->rdsin == dev->rdsout) { | 341 | if (dev->rdsin == dev->rdsout) { |
| 342 | mutex_unlock(&dev->lock); | ||
| 343 | if (file->f_flags & O_NONBLOCK) | 343 | if (file->f_flags & O_NONBLOCK) |
| 344 | return -EWOULDBLOCK; | 344 | return -EWOULDBLOCK; |
| 345 | interruptible_sleep_on(&dev->read_queue); | 345 | interruptible_sleep_on(&dev->read_queue); |
| 346 | mutex_lock(&dev->lock); | ||
| 346 | } | 347 | } |
| 347 | while (i < count && dev->rdsin != dev->rdsout) | 348 | while (i < count && dev->rdsin != dev->rdsout) |
| 348 | readbuf[i++] = dev->rdsbuf[dev->rdsout++]; | 349 | readbuf[i++] = dev->rdsbuf[dev->rdsout++]; |
| 350 | mutex_unlock(&dev->lock); | ||
| 349 | 351 | ||
| 350 | if (copy_to_user(data, readbuf, i)) | 352 | if (copy_to_user(data, readbuf, i)) |
| 351 | return -EFAULT; | 353 | return -EFAULT; |
| @@ -525,9 +527,11 @@ static int cadet_open(struct file *file) | |||
| 525 | { | 527 | { |
| 526 | struct cadet *dev = video_drvdata(file); | 528 | struct cadet *dev = video_drvdata(file); |
| 527 | 529 | ||
| 530 | mutex_lock(&dev->lock); | ||
| 528 | dev->users++; | 531 | dev->users++; |
| 529 | if (1 == dev->users) | 532 | if (1 == dev->users) |
| 530 | init_waitqueue_head(&dev->read_queue); | 533 | init_waitqueue_head(&dev->read_queue); |
| 534 | mutex_unlock(&dev->lock); | ||
| 531 | return 0; | 535 | return 0; |
| 532 | } | 536 | } |
| 533 | 537 | ||
| @@ -535,11 +539,13 @@ static int cadet_release(struct file *file) | |||
| 535 | { | 539 | { |
| 536 | struct cadet *dev = video_drvdata(file); | 540 | struct cadet *dev = video_drvdata(file); |
| 537 | 541 | ||
| 542 | mutex_lock(&dev->lock); | ||
| 538 | dev->users--; | 543 | dev->users--; |
| 539 | if (0 == dev->users) { | 544 | if (0 == dev->users) { |
| 540 | del_timer_sync(&dev->readtimer); | 545 | del_timer_sync(&dev->readtimer); |
| 541 | dev->rdsstat = 0; | 546 | dev->rdsstat = 0; |
| 542 | } | 547 | } |
| 548 | mutex_unlock(&dev->lock); | ||
| 543 | return 0; | 549 | return 0; |
| 544 | } | 550 | } |
| 545 | 551 | ||
| @@ -559,7 +565,7 @@ static const struct v4l2_file_operations cadet_fops = { | |||
| 559 | .open = cadet_open, | 565 | .open = cadet_open, |
| 560 | .release = cadet_release, | 566 | .release = cadet_release, |
| 561 | .read = cadet_read, | 567 | .read = cadet_read, |
| 562 | .ioctl = video_ioctl2, | 568 | .unlocked_ioctl = video_ioctl2, |
| 563 | .poll = cadet_poll, | 569 | .poll = cadet_poll, |
| 564 | }; | 570 | }; |
| 565 | 571 | ||
