2 * @file sn9c20x-queue.c
3 * @author Brian Johnson
5 * @brief Buffer management
7 * @note Original code from UVC webcam driver
8 * @note Copyright (C) 2005-2008 Laurent Pinchart (laurent.pinchart@skynet.be)
9 * @note Copyright (C) 2008 Brian Johnson (brijohn@gmail.com)
11 * This program is free software; you can redistribute it and/or modify
12 * it under the terms of the GNU General Public License as published by
13 * the Free Software Foundation; either version 2 of the License, or
14 * (at your option) any later version.
16 * ------------------------------------------------------------------------
18 * Video buffers queue management.
20 * Video queues is initialized by sn9c20x_queue_init(). The function performs
21 * basic initialization of the sn9c20x_video_queue struct and never fails.
23 * Video buffer allocation and freeing are performed by sn9c20x_alloc_buffers()
24 * and sn9c20x_free_buffers() respectively. The former acquires the video queue
25 * lock, while the later must be called with the lock held (so that allocation
26 * can free previously allocated buffers). Trying to free buffers that are
27 * mapped to user space will return -EBUSY.
29 * Video buffers are managed using two queues. However, unlike most USB video
30 * drivers which use an in queue and an out queue, we use a main queue which
31 * holds all queued buffers (both 'empty' and 'done' buffers), and an irq
32 * queue which holds empty buffers. This design (copied from video-buf)
33 * minimizes locking in interrupt, as only one queue is shared between
34 * interrupt and user contexts.
39 * Unless stated otherwise, all operations which modify the irq buffers queue
40 * are protected by the irq spinlock.
42 * 1. The user queues the buffers, starts streaming and dequeues a buffer.
44 * The buffers are added to the main and irq queues. Both operations are
45 * protected by the queue lock, and the latert is protected by the irq
48 * The completion handler fetches a buffer from the irq queue and fills it
49 * with video data. If no buffer is available (irq queue empty), the handler
50 * returns immediately.
52 * When the buffer is full, the completion handler removes it from the irq
53 * queue, marks it as ready (SN9C20X_BUF_STATE_DONE) and wake its wait
54 * queue. At that point, any process waiting on the buffer will be woken up.
55 * If a process tries to dequeue a buffer after it has been marked ready,
56 * the dequeing will succeed immediately.
58 * 2. Buffers are queued, user is waiting on a buffer and the device gets
61 * When the device is disconnected, the kernel calls the completion handler
62 * with an appropriate status code. The handler marks all buffers in the
63 * irq queue as being erroneous (SN9C20X_BUF_STATE_ERROR) and wakes them up
64 * so that any process waiting on a buffer gets woken up.
66 * Waking up up the first buffer on the irq list is not enough, as the
67 * process waiting on the buffer might restart the dequeue operation
72 #include <linux/kernel.h>
73 #include <linux/version.h>
74 #include <linux/list.h>
75 #include <linux/module.h>
76 #include <linux/usb.h>
77 #include <linux/videodev.h>
78 #include <linux/vmalloc.h>
79 #include <linux/wait.h>
81 #include <asm/atomic.h>
89 void sn9c20x_queue_init(struct sn9c20x_video_queue
*queue
)
91 mutex_init(&queue
->mutex
);
92 spin_lock_init(&queue
->irqlock
);
93 INIT_LIST_HEAD(&queue
->mainqueue
);
94 INIT_LIST_HEAD(&queue
->irqqueue
);
98 * @brief Allocate the video buffers.
104 * Pages are reserved to make sure they will not be swaped, as they will be
105 * filled in URB completion handler.
107 * Buffers will be individually mapped, so they must all be page aligned.
109 int sn9c20x_alloc_buffers(struct sn9c20x_video_queue
*queue
,
110 unsigned int nbuffers
, unsigned int buflength
)
112 unsigned int bufsize
= PAGE_ALIGN(buflength
);
118 mutex_lock(&queue
->mutex
);
120 ret
= sn9c20x_free_buffers(queue
);
124 /* Bail out if no buffers should be allocated. */
128 if (nbuffers
< queue
->min_buffers
)
129 nbuffers
= queue
->min_buffers
;
130 else if (nbuffers
> queue
->max_buffers
)
131 nbuffers
= queue
->max_buffers
;
133 /* Decrement the number of buffers until allocation succeeds. */
134 for (; nbuffers
>= queue
->min_buffers
; --nbuffers
) {
135 mem
= vmalloc_32(nbuffers
* bufsize
);
136 buffer
= kzalloc(nbuffers
* sizeof(struct sn9c20x_buffer
),
138 if (mem
!= NULL
&& buffer
!= NULL
)
146 if (mem
== NULL
|| buffer
== NULL
) {
150 queue
->buffer
= buffer
;
152 for (i
= 0; i
< nbuffers
; ++i
) {
153 memset(&queue
->buffer
[i
], 0, sizeof queue
->buffer
[i
]);
154 queue
->buffer
[i
].buf
.index
= i
;
155 queue
->buffer
[i
].buf
.m
.offset
= i
* bufsize
;
156 queue
->buffer
[i
].buf
.length
= buflength
;
157 queue
->buffer
[i
].buf
.type
= V4L2_BUF_TYPE_VIDEO_CAPTURE
;
158 queue
->buffer
[i
].buf
.sequence
= 0;
159 queue
->buffer
[i
].buf
.field
= V4L2_FIELD_NONE
;
160 queue
->buffer
[i
].buf
.memory
= V4L2_MEMORY_MMAP
;
161 queue
->buffer
[i
].buf
.flags
= 0;
162 init_waitqueue_head(&queue
->buffer
[i
].wait
);
166 queue
->count
= nbuffers
;
167 queue
->buf_size
= bufsize
;
171 mutex_unlock(&queue
->mutex
);
176 * @brief Free the video buffers.
180 * This function must be called with the queue lock held.
182 int sn9c20x_free_buffers(struct sn9c20x_video_queue
*queue
)
185 UDIA_DEBUG("Freeing %d v4l2 buffers\n", queue
->count
);
187 for (i
= 0; i
< queue
->count
; ++i
) {
188 if (queue
->buffer
[i
].vma_use_count
!= 0)
194 kfree(queue
->buffer
);
195 INIT_LIST_HEAD(&queue
->mainqueue
);
196 INIT_LIST_HEAD(&queue
->irqqueue
);
208 static void __sn9c20x_query_buffer(struct sn9c20x_buffer
*buf
,
209 struct v4l2_buffer
*v4l2_buf
)
211 memcpy(v4l2_buf
, &buf
->buf
, sizeof *v4l2_buf
);
213 if (buf
->vma_use_count
)
214 v4l2_buf
->flags
|= V4L2_BUF_FLAG_MAPPED
;
216 switch (buf
->state
) {
217 case SN9C20X_BUF_STATE_ERROR
:
218 case SN9C20X_BUF_STATE_DONE
:
219 v4l2_buf
->flags
|= V4L2_BUF_FLAG_DONE
;
221 case SN9C20X_BUF_STATE_QUEUED
:
222 case SN9C20X_BUF_STATE_ACTIVE
:
223 v4l2_buf
->flags
|= V4L2_BUF_FLAG_QUEUED
;
225 case SN9C20X_BUF_STATE_IDLE
:
235 * @return 0 or negative error code
238 int sn9c20x_query_buffer(struct sn9c20x_video_queue
*queue
,
239 struct v4l2_buffer
*v4l2_buf
)
243 mutex_lock(&queue
->mutex
);
244 if (v4l2_buf
->index
>= queue
->count
) {
249 __sn9c20x_query_buffer(&queue
->buffer
[v4l2_buf
->index
], v4l2_buf
);
252 mutex_unlock(&queue
->mutex
);
257 * @brief Queue a video buffer.
262 * @return 0 or negative error code
264 * Attempting to queue a buffer that has already been
265 * queued will return -EINVAL.
267 int sn9c20x_queue_buffer(struct sn9c20x_video_queue
*queue
,
268 struct v4l2_buffer
*v4l2_buf
)
270 struct sn9c20x_buffer
*buf
;
274 UDIA_DEBUG("Queuing buffer %u.\n", v4l2_buf
->index
);
276 if (v4l2_buf
->type
!= V4L2_BUF_TYPE_VIDEO_CAPTURE
||
277 v4l2_buf
->memory
!= V4L2_MEMORY_MMAP
) {
278 UDIA_ERROR("[E] Invalid buffer type (%u) "
279 "and/or memory (%u).\n", v4l2_buf
->type
,
284 mutex_lock(&queue
->mutex
);
285 if (v4l2_buf
->index
>= queue
->count
) {
286 UDIA_ERROR("[E] Out of range index.\n");
291 buf
= &queue
->buffer
[v4l2_buf
->index
];
292 if (buf
->state
!= SN9C20X_BUF_STATE_IDLE
) {
293 UDIA_ERROR("[E] Invalid buffer state "
294 "(%u).\n", buf
->state
);
299 spin_lock_irqsave(&queue
->irqlock
, flags
);
300 if (queue
->flags
& SN9C20X_QUEUE_DISCONNECTED
) {
301 spin_unlock_irqrestore(&queue
->irqlock
, flags
);
306 buf
->state
= SN9C20X_BUF_STATE_QUEUED
;
307 buf
->buf
.bytesused
= 0;
308 list_add_tail(&buf
->stream
, &queue
->mainqueue
);
309 list_add_tail(&buf
->queue
, &queue
->irqqueue
);
310 spin_unlock_irqrestore(&queue
->irqlock
, flags
);
313 mutex_unlock(&queue
->mutex
);
322 static int sn9c20x_queue_waiton(struct sn9c20x_buffer
*buf
, int nonblocking
)
325 return (buf
->state
!= SN9C20X_BUF_STATE_QUEUED
&&
326 buf
->state
!= SN9C20X_BUF_STATE_ACTIVE
)
330 return wait_event_interruptible(buf
->wait
,
331 buf
->state
!= SN9C20X_BUF_STATE_QUEUED
&&
332 buf
->state
!= SN9C20X_BUF_STATE_ACTIVE
);
336 * @brief Dequeue a video buffer.
342 * @return 0 or negative error code
344 * If nonblocking is false, block until a buffer is
347 int sn9c20x_dequeue_buffer(struct sn9c20x_video_queue
*queue
,
348 struct v4l2_buffer
*v4l2_buf
, int nonblocking
)
350 struct sn9c20x_buffer
*buf
;
353 if (v4l2_buf
->type
!= V4L2_BUF_TYPE_VIDEO_CAPTURE
||
354 v4l2_buf
->memory
!= V4L2_MEMORY_MMAP
) {
355 UDIA_ERROR("[E] Invalid buffer type (%u) "
356 "and/or memory (%u).\n", v4l2_buf
->type
,
361 mutex_lock(&queue
->mutex
);
362 if (list_empty(&queue
->mainqueue
)) {
363 UDIA_ERROR("[E] Empty buffer queue.\n");
368 buf
= list_first_entry(&queue
->mainqueue
, struct sn9c20x_buffer
,
371 ret
= sn9c20x_queue_waiton(buf
, nonblocking
);
375 UDIA_DEBUG("Dequeuing buffer %u (%u, %u bytes).\n",
376 buf
->buf
.index
, buf
->state
, buf
->buf
.bytesused
);
378 switch (buf
->state
) {
379 case SN9C20X_BUF_STATE_ERROR
:
380 UDIA_WARNING("[W] Corrupted data (transmission error).\n");
382 case SN9C20X_BUF_STATE_DONE
:
383 buf
->state
= SN9C20X_BUF_STATE_IDLE
;
386 case SN9C20X_BUF_STATE_IDLE
:
387 case SN9C20X_BUF_STATE_QUEUED
:
388 case SN9C20X_BUF_STATE_ACTIVE
:
390 UDIA_ERROR("[E] Invalid buffer state %u "
391 "(driver bug?).\n", buf
->state
);
396 list_del(&buf
->stream
);
397 __sn9c20x_query_buffer(buf
, v4l2_buf
);
400 mutex_unlock(&queue
->mutex
);
405 * @brief Poll the video queue.
411 * This function implements video queue polling and is intended to be used by
412 * the device poll handler.
414 unsigned int sn9c20x_queue_poll(struct sn9c20x_video_queue
*queue
,
415 struct file
*file
, poll_table
*wait
)
417 struct sn9c20x_buffer
*buf
;
418 unsigned int mask
= 0;
420 mutex_lock(&queue
->mutex
);
421 if (list_empty(&queue
->mainqueue
)) {
425 buf
= list_first_entry(&queue
->mainqueue
, struct sn9c20x_buffer
,
428 poll_wait(file
, &buf
->wait
, wait
);
429 if (buf
->state
== SN9C20X_BUF_STATE_DONE
||
430 buf
->state
== SN9C20X_BUF_STATE_ERROR
)
431 mask
|= POLLIN
| POLLRDNORM
;
434 mutex_unlock(&queue
->mutex
);
439 * @brief Enable or disable the video buffers queue.
444 * @return 0 or negative error code
446 * The queue must be enabled before starting video acquisition and must be
447 * disabled after stopping it. This ensures that the video buffers queue
448 * state can be properly initialized before buffers are accessed from the
451 * Enabling the video queue initializes parameters (such as sequence number,
452 * sync pattern, ...). If the queue is already enabled, return -EBUSY.
454 * Disabling the video queue cancels the queue and removes all buffers from
457 * This function can't be called from interrupt context. Use
458 * sn9c20x_queue_cancel() instead.
460 int sn9c20x_queue_enable(struct sn9c20x_video_queue
*queue
, int enable
)
465 mutex_lock(&queue
->mutex
);
467 if (sn9c20x_queue_streaming(queue
)) {
472 queue
->flags
|= SN9C20X_QUEUE_STREAMING
;
474 sn9c20x_queue_cancel(queue
, 0);
475 INIT_LIST_HEAD(&queue
->mainqueue
);
477 for (i
= 0; i
< queue
->count
; ++i
)
478 queue
->buffer
[i
].state
= SN9C20X_BUF_STATE_IDLE
;
480 queue
->flags
&= ~SN9C20X_QUEUE_STREAMING
;
484 mutex_unlock(&queue
->mutex
);
489 * @brief Cancel the video buffers queue.
495 * Cancelling the queue marks all buffers on the irq queue as erroneous,
496 * wakes them up and remove them from the queue.
498 * If the disconnect parameter is set, further calls to uvc_queue_buffer will
501 * This function acquires the irq spinlock and can be called from interrupt
504 void sn9c20x_queue_cancel(struct sn9c20x_video_queue
*queue
, int disconnect
)
506 struct sn9c20x_buffer
*buf
;
509 spin_lock_irqsave(&queue
->irqlock
, flags
);
510 while (!list_empty(&queue
->irqqueue
)) {
511 buf
= list_first_entry(&queue
->irqqueue
, struct sn9c20x_buffer
,
513 list_del(&buf
->queue
);
514 buf
->state
= SN9C20X_BUF_STATE_ERROR
;
517 /* This must be protected by the irqlock spinlock to avoid race
518 * conditions between sn9c20x_queue_buffer and the disconnection
519 * event that could result in an interruptible wait in
520 * sn9c20x_dequeue_buffer. Do not blindly replace this logic by
521 * checking for the SN9C20X_DEV_DISCONNECTED state outside the
525 queue
->flags
|= SN9C20X_QUEUE_DISCONNECTED
;
526 spin_unlock_irqrestore(&queue
->irqlock
, flags
);
534 struct sn9c20x_buffer
*sn9c20x_queue_next_buffer(
535 struct sn9c20x_video_queue
*queue
,
536 struct sn9c20x_buffer
*buf
)
538 struct sn9c20x_buffer
*nextbuf
;
541 if ((queue
->flags
& SN9C20X_QUEUE_DROP_INCOMPLETE
) &&
542 buf
->buf
.length
!= buf
->buf
.bytesused
) {
543 buf
->state
= SN9C20X_BUF_STATE_QUEUED
;
544 buf
->buf
.bytesused
= 0;
548 spin_lock_irqsave(&queue
->irqlock
, flags
);
549 list_del(&buf
->queue
);
550 if (!list_empty(&queue
->irqqueue
))
551 nextbuf
= list_first_entry(&queue
->irqqueue
,
552 struct sn9c20x_buffer
, queue
);
555 spin_unlock_irqrestore(&queue
->irqlock
, flags
);
557 buf
->buf
.sequence
= queue
->sequence
++;
558 do_gettimeofday(&buf
->buf
.timestamp
);