|
@@ -454,7 +454,50 @@ static int __verify_mmap_ops(struct vb2_queue *q)
|
|
}
|
|
}
|
|
|
|
|
|
/**
|
|
/**
|
|
- * vb2_reqbufs() - Initiate streaming
|
|
|
|
|
|
+ * __verify_memory_type() - Check whether the memory type and buffer type
|
|
|
|
+ * passed to a buffer operation are compatible with the queue.
|
|
|
|
+ */
|
|
|
|
+static int __verify_memory_type(struct vb2_queue *q,
|
|
|
|
+ enum v4l2_memory memory, enum v4l2_buf_type type)
|
|
|
|
+{
|
|
|
|
+ if (memory != V4L2_MEMORY_MMAP && memory != V4L2_MEMORY_USERPTR) {
|
|
|
|
+ dprintk(1, "reqbufs: unsupported memory type\n");
|
|
|
|
+ return -EINVAL;
|
|
|
|
+ }
|
|
|
|
+
|
|
|
|
+ if (type != q->type) {
|
|
|
|
+ dprintk(1, "reqbufs: requested type is incorrect\n");
|
|
|
|
+ return -EINVAL;
|
|
|
|
+ }
|
|
|
|
+
|
|
|
|
+ /*
|
|
|
|
+ * Make sure all the required memory ops for given memory type
|
|
|
|
+ * are available.
|
|
|
|
+ */
|
|
|
|
+ if (memory == V4L2_MEMORY_MMAP && __verify_mmap_ops(q)) {
|
|
|
|
+ dprintk(1, "reqbufs: MMAP for current setup unsupported\n");
|
|
|
|
+ return -EINVAL;
|
|
|
|
+ }
|
|
|
|
+
|
|
|
|
+ if (memory == V4L2_MEMORY_USERPTR && __verify_userptr_ops(q)) {
|
|
|
|
+ dprintk(1, "reqbufs: USERPTR for current setup unsupported\n");
|
|
|
|
+ return -EINVAL;
|
|
|
|
+ }
|
|
|
|
+
|
|
|
|
+ /*
|
|
|
|
+ * Place the busy tests at the end: -EBUSY can be ignored when
|
|
|
|
+ * create_bufs is called with count == 0, but count == 0 should still
|
|
|
|
+ * do the memory and type validation.
|
|
|
|
+ */
|
|
|
|
+ if (q->fileio) {
|
|
|
|
+ dprintk(1, "reqbufs: file io in progress\n");
|
|
|
|
+ return -EBUSY;
|
|
|
|
+ }
|
|
|
|
+ return 0;
|
|
|
|
+}
|
|
|
|
+
|
|
|
|
+/**
|
|
|
|
+ * __reqbufs() - Initiate streaming
|
|
* @q: videobuf2 queue
|
|
* @q: videobuf2 queue
|
|
* @req: struct passed from userspace to vidioc_reqbufs handler in driver
|
|
* @req: struct passed from userspace to vidioc_reqbufs handler in driver
|
|
*
|
|
*
|
|
@@ -476,46 +519,16 @@ static int __verify_mmap_ops(struct vb2_queue *q)
|
|
* The return values from this function are intended to be directly returned
|
|
* The return values from this function are intended to be directly returned
|
|
* from vidioc_reqbufs handler in driver.
|
|
* from vidioc_reqbufs handler in driver.
|
|
*/
|
|
*/
|
|
-int vb2_reqbufs(struct vb2_queue *q, struct v4l2_requestbuffers *req)
|
|
|
|
|
|
+static int __reqbufs(struct vb2_queue *q, struct v4l2_requestbuffers *req)
|
|
{
|
|
{
|
|
unsigned int num_buffers, allocated_buffers, num_planes = 0;
|
|
unsigned int num_buffers, allocated_buffers, num_planes = 0;
|
|
- int ret = 0;
|
|
|
|
-
|
|
|
|
- if (q->fileio) {
|
|
|
|
- dprintk(1, "reqbufs: file io in progress\n");
|
|
|
|
- return -EBUSY;
|
|
|
|
- }
|
|
|
|
-
|
|
|
|
- if (req->memory != V4L2_MEMORY_MMAP
|
|
|
|
- && req->memory != V4L2_MEMORY_USERPTR) {
|
|
|
|
- dprintk(1, "reqbufs: unsupported memory type\n");
|
|
|
|
- return -EINVAL;
|
|
|
|
- }
|
|
|
|
-
|
|
|
|
- if (req->type != q->type) {
|
|
|
|
- dprintk(1, "reqbufs: requested type is incorrect\n");
|
|
|
|
- return -EINVAL;
|
|
|
|
- }
|
|
|
|
|
|
+ int ret;
|
|
|
|
|
|
if (q->streaming) {
|
|
if (q->streaming) {
|
|
dprintk(1, "reqbufs: streaming active\n");
|
|
dprintk(1, "reqbufs: streaming active\n");
|
|
return -EBUSY;
|
|
return -EBUSY;
|
|
}
|
|
}
|
|
|
|
|
|
- /*
|
|
|
|
- * Make sure all the required memory ops for given memory type
|
|
|
|
- * are available.
|
|
|
|
- */
|
|
|
|
- if (req->memory == V4L2_MEMORY_MMAP && __verify_mmap_ops(q)) {
|
|
|
|
- dprintk(1, "reqbufs: MMAP for current setup unsupported\n");
|
|
|
|
- return -EINVAL;
|
|
|
|
- }
|
|
|
|
-
|
|
|
|
- if (req->memory == V4L2_MEMORY_USERPTR && __verify_userptr_ops(q)) {
|
|
|
|
- dprintk(1, "reqbufs: USERPTR for current setup unsupported\n");
|
|
|
|
- return -EINVAL;
|
|
|
|
- }
|
|
|
|
-
|
|
|
|
if (req->count == 0 || q->num_buffers != 0 || q->memory != req->memory) {
|
|
if (req->count == 0 || q->num_buffers != 0 || q->memory != req->memory) {
|
|
/*
|
|
/*
|
|
* We already have buffers allocated, so first check if they
|
|
* We already have buffers allocated, so first check if they
|
|
@@ -595,10 +608,23 @@ int vb2_reqbufs(struct vb2_queue *q, struct v4l2_requestbuffers *req)
|
|
|
|
|
|
return 0;
|
|
return 0;
|
|
}
|
|
}
|
|
|
|
+
|
|
|
|
+/**
|
|
|
|
+ * vb2_reqbufs() - Wrapper for __reqbufs() that also verifies the memory and
|
|
|
|
+ * type values.
|
|
|
|
+ * @q: videobuf2 queue
|
|
|
|
+ * @req: struct passed from userspace to vidioc_reqbufs handler in driver
|
|
|
|
+ */
|
|
|
|
+int vb2_reqbufs(struct vb2_queue *q, struct v4l2_requestbuffers *req)
|
|
|
|
+{
|
|
|
|
+ int ret = __verify_memory_type(q, req->memory, req->type);
|
|
|
|
+
|
|
|
|
+ return ret ? ret : __reqbufs(q, req);
|
|
|
|
+}
|
|
EXPORT_SYMBOL_GPL(vb2_reqbufs);
|
|
EXPORT_SYMBOL_GPL(vb2_reqbufs);
|
|
|
|
|
|
/**
|
|
/**
|
|
- * vb2_create_bufs() - Allocate buffers and any required auxiliary structs
|
|
|
|
|
|
+ * __create_bufs() - Allocate buffers and any required auxiliary structs
|
|
* @q: videobuf2 queue
|
|
* @q: videobuf2 queue
|
|
* @create: creation parameters, passed from userspace to vidioc_create_bufs
|
|
* @create: creation parameters, passed from userspace to vidioc_create_bufs
|
|
* handler in driver
|
|
* handler in driver
|
|
@@ -612,40 +638,10 @@ EXPORT_SYMBOL_GPL(vb2_reqbufs);
|
|
* The return values from this function are intended to be directly returned
|
|
* The return values from this function are intended to be directly returned
|
|
* from vidioc_create_bufs handler in driver.
|
|
* from vidioc_create_bufs handler in driver.
|
|
*/
|
|
*/
|
|
-int vb2_create_bufs(struct vb2_queue *q, struct v4l2_create_buffers *create)
|
|
|
|
|
|
+static int __create_bufs(struct vb2_queue *q, struct v4l2_create_buffers *create)
|
|
{
|
|
{
|
|
unsigned int num_planes = 0, num_buffers, allocated_buffers;
|
|
unsigned int num_planes = 0, num_buffers, allocated_buffers;
|
|
- int ret = 0;
|
|
|
|
-
|
|
|
|
- if (q->fileio) {
|
|
|
|
- dprintk(1, "%s(): file io in progress\n", __func__);
|
|
|
|
- return -EBUSY;
|
|
|
|
- }
|
|
|
|
-
|
|
|
|
- if (create->memory != V4L2_MEMORY_MMAP
|
|
|
|
- && create->memory != V4L2_MEMORY_USERPTR) {
|
|
|
|
- dprintk(1, "%s(): unsupported memory type\n", __func__);
|
|
|
|
- return -EINVAL;
|
|
|
|
- }
|
|
|
|
-
|
|
|
|
- if (create->format.type != q->type) {
|
|
|
|
- dprintk(1, "%s(): requested type is incorrect\n", __func__);
|
|
|
|
- return -EINVAL;
|
|
|
|
- }
|
|
|
|
-
|
|
|
|
- /*
|
|
|
|
- * Make sure all the required memory ops for given memory type
|
|
|
|
- * are available.
|
|
|
|
- */
|
|
|
|
- if (create->memory == V4L2_MEMORY_MMAP && __verify_mmap_ops(q)) {
|
|
|
|
- dprintk(1, "%s(): MMAP for current setup unsupported\n", __func__);
|
|
|
|
- return -EINVAL;
|
|
|
|
- }
|
|
|
|
-
|
|
|
|
- if (create->memory == V4L2_MEMORY_USERPTR && __verify_userptr_ops(q)) {
|
|
|
|
- dprintk(1, "%s(): USERPTR for current setup unsupported\n", __func__);
|
|
|
|
- return -EINVAL;
|
|
|
|
- }
|
|
|
|
|
|
+ int ret;
|
|
|
|
|
|
if (q->num_buffers == VIDEO_MAX_FRAME) {
|
|
if (q->num_buffers == VIDEO_MAX_FRAME) {
|
|
dprintk(1, "%s(): maximum number of buffers already allocated\n",
|
|
dprintk(1, "%s(): maximum number of buffers already allocated\n",
|
|
@@ -653,8 +649,6 @@ int vb2_create_bufs(struct vb2_queue *q, struct v4l2_create_buffers *create)
|
|
return -ENOBUFS;
|
|
return -ENOBUFS;
|
|
}
|
|
}
|
|
|
|
|
|
- create->index = q->num_buffers;
|
|
|
|
-
|
|
|
|
if (!q->num_buffers) {
|
|
if (!q->num_buffers) {
|
|
memset(q->plane_sizes, 0, sizeof(q->plane_sizes));
|
|
memset(q->plane_sizes, 0, sizeof(q->plane_sizes));
|
|
memset(q->alloc_ctx, 0, sizeof(q->alloc_ctx));
|
|
memset(q->alloc_ctx, 0, sizeof(q->alloc_ctx));
|
|
@@ -719,6 +713,21 @@ int vb2_create_bufs(struct vb2_queue *q, struct v4l2_create_buffers *create)
|
|
|
|
|
|
return 0;
|
|
return 0;
|
|
}
|
|
}
|
|
|
|
+
|
|
|
|
+/**
|
|
|
|
+ * vb2_reqbufs() - Wrapper for __reqbufs() that also verifies the memory and
|
|
|
|
+ * type values.
|
|
|
|
+ * @q: videobuf2 queue
|
|
|
|
+ * @create: creation parameters, passed from userspace to vidioc_create_bufs
|
|
|
|
+ * handler in driver
|
|
|
|
+ */
|
|
|
|
+int vb2_create_bufs(struct vb2_queue *q, struct v4l2_create_buffers *create)
|
|
|
|
+{
|
|
|
|
+ int ret = __verify_memory_type(q, create->memory, create->format.type);
|
|
|
|
+
|
|
|
|
+ create->index = q->num_buffers;
|
|
|
|
+ return ret ? ret : __create_bufs(q, create);
|
|
|
|
+}
|
|
EXPORT_SYMBOL_GPL(vb2_create_bufs);
|
|
EXPORT_SYMBOL_GPL(vb2_create_bufs);
|
|
|
|
|
|
/**
|
|
/**
|