#include <linux/sysrq.h>
#include <linux/interrupt.h>
#include <linux/dma-mapping.h>
+#include <linux/completion.h>
#include <asm/uaccess.h>
#include <asm/io.h>
s->started = 0;
s->bytecount = 0;
s->fragcount = 0;
- sema_init(&s->sem, s->nbfrags);
+ init_completion(&s->wfc);
+ s->wfc.done = s->nbfrags;
FN_OUT(0);
return 0;
err:
audio_process_dma(state->output_stream);
}
is->pending_frags = is->nbfrags;
- sema_init(&is->sem, 0);
+ init_completion(&is->wfc);
+ is->wfc.done = 0;
+
is->active = 1;
audio_process_dma(is);
*/
b = &s->buffers[s->usr_head];
if (b->offset &= ~3) {
- down(&s->sem);
+ /* Wait for a buffer to become free */
+ if (wait_for_completion_interruptible(&s->wfc))
+ return 0;
/*
* HACK ALERT !
* To avoid increased complexity in the rest of the code
/* Let's wait for all buffers to complete */
set_current_state(TASK_INTERRUPTIBLE);
add_wait_queue(&s->wq, &wait);
- while ((s->pending_frags || (atomic_read(&s->sem.count) < s->nbfrags))
+ while ((s->pending_frags || (s->wfc.done < s->nbfrags))
&& !signal_pending(current)) {
schedule();
set_current_state(TASK_INTERRUPTIBLE);
s->buffers[s->usr_head].offset = 0;
s->usr_head = s->dma_head;
s->pending_frags = 0;
- sema_init(&s->sem, s->nbfrags);
+ init_completion(&s->wfc);
+ s->wfc.done = s->nbfrags;
}
s->active = 0;
s->stopped = 0;
tasklet_schedule(&audio_isr_work2);
work_item_running = 0;
}
-
FN_OUT(0);
return;
}
s->dma_tail = 0;
if (!s->mapped)
- up(&s->sem);
+ complete(&s->wfc);
else
s->pending_frags++;
wake_up(&s->wq);
}
- audio_process_dma(s);
FN_OUT(0);
return;
#include <linux/sysrq.h>
#include <linux/delay.h>
#include <linux/device.h>
+#include <linux/completion.h>
#include <asm/uaccess.h>
#include <asm/io.h>
}
memcpy(&audio_state, codec_state, sizeof(audio_state_t));
+ sema_init(&audio_state.sem, 1);
ret = platform_device_register(&omap_audio_device);
if (ret != 0) {
/* Wait for a buffer to become free */
if (file->f_flags & O_NONBLOCK) {
ret = -EAGAIN;
- if (down_trylock(&s->sem))
- break;
- } else {
- ret = -ERESTARTSYS;
- if (down_interruptible(&s->sem))
+ if (!s->wfc.done)
break;
}
+ ret = -ERESTARTSYS;
+ if (wait_for_completion_interruptible(&s->wfc))
+ break;
/* Feed the current buffer */
chunksize = s->fragsize - b->offset;
DPRINTK("write %d to %d\n", chunksize, s->usr_head);
if (copy_from_user(b->data + b->offset, buffer, chunksize)) {
printk(KERN_ERR "Audio: CopyFrom User failed \n");
- up(&s->sem);
+ complete(&s->wfc);
return -EFAULT;
}
b->offset += chunksize;
if (b->offset < s->fragsize) {
- up(&s->sem);
+ complete(&s->wfc);
break;
}
/* Wait for a buffer to become full */
if (file->f_flags & O_NONBLOCK) {
ret = -EAGAIN;
- if (down_trylock(&s->sem))
- break;
- } else {
- ret = -ERESTARTSYS;
- if (down_interruptible(&s->sem))
+ if (!s->wfc.done)
break;
}
+ ret = -ERESTARTSYS;
+ if (wait_for_completion_interruptible(&s->wfc))
+ break;
/* Grab data from the current buffer */
chunksize = s->fragsize - b->offset;
chunksize = count;
DPRINTK("read %d from %d\n", chunksize, s->usr_head);
if (copy_to_user(buffer, b->data + b->offset, chunksize)) {
- up(&s->sem);
+ complete(&s->wfc);
return -EFAULT;
}
buffer += chunksize;
count -= chunksize;
b->offset += chunksize;
if (b->offset < s->fragsize) {
- up(&s->sem);
+ complete(&s->wfc);
break;
}
if (file->f_mode & FMODE_READ)
if ((is->mapped && is->bytecount > 0) ||
- (!is->mapped && atomic_read(&is->sem.count) > 0))
+ (!is->mapped && is->wfc.done > 0))
mask |= POLLIN | POLLRDNORM;
if (file->f_mode & FMODE_WRITE)
if ((os->mapped && os->bytecount > 0) ||
- (!os->mapped && atomic_read(&os->sem.count) > 0))
+ (!os->mapped && os->wfc.done > 0))
mask |= POLLOUT | POLLWRNORM;
DPRINTK("audio_poll() returned mask of %s%s\n",
local_irq_save(flags);
if (os->mapped && !os->pending_frags) {
os->pending_frags = os->nbfrags;
- sema_init(&os->sem, 0);
+ init_completion(&os->wfc);
+ os->wfc.done = 0;
os->active = 1;
}
os->stopped = 0;
FN_OUT(19);
return -ENOMEM;
}
- inf.bytes = atomic_read(&s->sem.count) * s->fragsize;
+ inf.bytes = s->wfc.done * s->fragsize;
inf.fragments = inf.bytes / s->fragsize;
inf.fragsize = s->fragsize;