Re: [PATCHv17 23/34] videobuf2-core: integrate with media requests

2018-08-13 Thread Mauro Carvalho Chehab
Em Sat,  4 Aug 2018 14:45:15 +0200
Hans Verkuil  escreveu:

> From: Hans Verkuil 
> 
> Buffers can now be prepared or queued for a request.
> 
> A buffer is unbound from the request at vb2_buffer_done time or
> when the queue is cancelled.
> 
> Signed-off-by: Hans Verkuil 
Reviewed-by: Mauro Carvalho Chehab 

> ---
>  .../media/common/videobuf2/videobuf2-core.c   | 133 +-
>  .../media/common/videobuf2/videobuf2-v4l2.c   |   4 +-
>  drivers/media/dvb-core/dvb_vb2.c  |   2 +-
>  include/media/videobuf2-core.h|  18 ++-
>  4 files changed, 147 insertions(+), 10 deletions(-)
> 
> diff --git a/drivers/media/common/videobuf2/videobuf2-core.c 
> b/drivers/media/common/videobuf2/videobuf2-core.c
> index 230f83d6d094..1efb9c8b359d 100644
> --- a/drivers/media/common/videobuf2/videobuf2-core.c
> +++ b/drivers/media/common/videobuf2/videobuf2-core.c
> @@ -499,8 +499,9 @@ static int __vb2_queue_free(struct vb2_queue *q, unsigned 
> int buffers)
>   pr_info(" buf_init: %u buf_cleanup: %u buf_prepare: 
> %u buf_finish: %u\n",
>   vb->cnt_buf_init, vb->cnt_buf_cleanup,
>   vb->cnt_buf_prepare, vb->cnt_buf_finish);
> - pr_info(" buf_queue: %u buf_done: %u\n",
> - vb->cnt_buf_queue, vb->cnt_buf_done);
> + pr_info(" buf_queue: %u buf_done: %u 
> buf_request_complete: %u\n",
> + vb->cnt_buf_queue, vb->cnt_buf_done,
> + vb->cnt_buf_request_complete);
>   pr_info(" alloc: %u put: %u prepare: %u finish: %u 
> mmap: %u\n",
>   vb->cnt_mem_alloc, vb->cnt_mem_put,
>   vb->cnt_mem_prepare, vb->cnt_mem_finish,
> @@ -936,6 +937,14 @@ void vb2_buffer_done(struct vb2_buffer *vb, enum 
> vb2_buffer_state state)
>   vb->state = state;
>   }
>   atomic_dec(>owned_by_drv_count);
> +
> + if (vb->req_obj.req) {
> + /* This is not supported at the moment */
> + WARN_ON(state == VB2_BUF_STATE_REQUEUEING);
> + media_request_object_unbind(>req_obj);
> + media_request_object_put(>req_obj);
> + }
> +
>   spin_unlock_irqrestore(>done_lock, flags);
>  
>   trace_vb2_buf_done(q, vb);
> @@ -1290,6 +1299,60 @@ static int __buf_prepare(struct vb2_buffer *vb)
>   return 0;
>  }
>  
> +static int vb2_req_prepare(struct media_request_object *obj)
> +{
> + struct vb2_buffer *vb = container_of(obj, struct vb2_buffer, req_obj);
> + int ret;
> +
> + if (WARN_ON(vb->state != VB2_BUF_STATE_IN_REQUEST))
> + return -EINVAL;
> +
> + mutex_lock(vb->vb2_queue->lock);
> + ret = __buf_prepare(vb);
> + mutex_unlock(vb->vb2_queue->lock);
> + return ret;
> +}
> +
> +static void __vb2_dqbuf(struct vb2_buffer *vb);
> +
> +static void vb2_req_unprepare(struct media_request_object *obj)
> +{
> + struct vb2_buffer *vb = container_of(obj, struct vb2_buffer, req_obj);
> +
> + mutex_lock(vb->vb2_queue->lock);
> + __vb2_dqbuf(vb);
> + vb->state = VB2_BUF_STATE_IN_REQUEST;
> + mutex_unlock(vb->vb2_queue->lock);
> + WARN_ON(!vb->req_obj.req);
> +}
> +
> +int vb2_core_qbuf(struct vb2_queue *q, unsigned int index, void *pb,
> +   struct media_request *req);
> +
> +static void vb2_req_queue(struct media_request_object *obj)
> +{
> + struct vb2_buffer *vb = container_of(obj, struct vb2_buffer, req_obj);
> +
> + mutex_lock(vb->vb2_queue->lock);
> + vb2_core_qbuf(vb->vb2_queue, vb->index, NULL, NULL);
> + mutex_unlock(vb->vb2_queue->lock);
> +}
> +
> +static void vb2_req_release(struct media_request_object *obj)
> +{
> + struct vb2_buffer *vb = container_of(obj, struct vb2_buffer, req_obj);
> +
> + if (vb->state == VB2_BUF_STATE_IN_REQUEST)
> + vb->state = VB2_BUF_STATE_DEQUEUED;

Shouldn't it be protected by the lock?

> +}
> +
> +static const struct media_request_object_ops vb2_core_req_ops = {
> + .prepare = vb2_req_prepare,
> + .unprepare = vb2_req_unprepare,
> + .queue = vb2_req_queue,
> + .release = vb2_req_release,
> +};
> +
>  int vb2_core_prepare_buf(struct vb2_queue *q, unsigned int index, void *pb)
>  {
>   struct vb2_buffer *vb;
> @@ -1315,7 +1378,7 @@ int vb2_core_prepare_buf(struct vb2_queue *q, unsigned 
> int index, void *pb)
>  
>   dprintk(2, "prepare of buffer %d succeeded\n", vb->index);
>  
> - return ret;
> + return 0;
>  }
>  EXPORT_SYMBOL_GPL(vb2_core_prepare_buf);
>  
> @@ -1382,7 +1445,8 @@ static int vb2_start_streaming(struct vb2_queue *q)
>   return ret;
>  }
>  
> -int vb2_core_qbuf(struct vb2_queue *q, unsigned int index, void *pb)
> +int vb2_core_qbuf(struct vb2_queue *q, unsigned int index, void *pb,
> +   struct media_request *req)
>  {
>   struct vb2_buffer *vb;
>   int 

[PATCHv17 23/34] videobuf2-core: integrate with media requests

2018-08-04 Thread Hans Verkuil
From: Hans Verkuil 

Buffers can now be prepared or queued for a request.

A buffer is unbound from the request at vb2_buffer_done time or
when the queue is cancelled.

Signed-off-by: Hans Verkuil 
---
 .../media/common/videobuf2/videobuf2-core.c   | 133 +-
 .../media/common/videobuf2/videobuf2-v4l2.c   |   4 +-
 drivers/media/dvb-core/dvb_vb2.c  |   2 +-
 include/media/videobuf2-core.h|  18 ++-
 4 files changed, 147 insertions(+), 10 deletions(-)

diff --git a/drivers/media/common/videobuf2/videobuf2-core.c 
b/drivers/media/common/videobuf2/videobuf2-core.c
index 230f83d6d094..1efb9c8b359d 100644
--- a/drivers/media/common/videobuf2/videobuf2-core.c
+++ b/drivers/media/common/videobuf2/videobuf2-core.c
@@ -499,8 +499,9 @@ static int __vb2_queue_free(struct vb2_queue *q, unsigned 
int buffers)
pr_info(" buf_init: %u buf_cleanup: %u buf_prepare: 
%u buf_finish: %u\n",
vb->cnt_buf_init, vb->cnt_buf_cleanup,
vb->cnt_buf_prepare, vb->cnt_buf_finish);
-   pr_info(" buf_queue: %u buf_done: %u\n",
-   vb->cnt_buf_queue, vb->cnt_buf_done);
+   pr_info(" buf_queue: %u buf_done: %u 
buf_request_complete: %u\n",
+   vb->cnt_buf_queue, vb->cnt_buf_done,
+   vb->cnt_buf_request_complete);
pr_info(" alloc: %u put: %u prepare: %u finish: %u 
mmap: %u\n",
vb->cnt_mem_alloc, vb->cnt_mem_put,
vb->cnt_mem_prepare, vb->cnt_mem_finish,
@@ -936,6 +937,14 @@ void vb2_buffer_done(struct vb2_buffer *vb, enum 
vb2_buffer_state state)
vb->state = state;
}
atomic_dec(>owned_by_drv_count);
+
+   if (vb->req_obj.req) {
+   /* This is not supported at the moment */
+   WARN_ON(state == VB2_BUF_STATE_REQUEUEING);
+   media_request_object_unbind(>req_obj);
+   media_request_object_put(>req_obj);
+   }
+
spin_unlock_irqrestore(>done_lock, flags);
 
trace_vb2_buf_done(q, vb);
@@ -1290,6 +1299,60 @@ static int __buf_prepare(struct vb2_buffer *vb)
return 0;
 }
 
+static int vb2_req_prepare(struct media_request_object *obj)
+{
+   struct vb2_buffer *vb = container_of(obj, struct vb2_buffer, req_obj);
+   int ret;
+
+   if (WARN_ON(vb->state != VB2_BUF_STATE_IN_REQUEST))
+   return -EINVAL;
+
+   mutex_lock(vb->vb2_queue->lock);
+   ret = __buf_prepare(vb);
+   mutex_unlock(vb->vb2_queue->lock);
+   return ret;
+}
+
+static void __vb2_dqbuf(struct vb2_buffer *vb);
+
+static void vb2_req_unprepare(struct media_request_object *obj)
+{
+   struct vb2_buffer *vb = container_of(obj, struct vb2_buffer, req_obj);
+
+   mutex_lock(vb->vb2_queue->lock);
+   __vb2_dqbuf(vb);
+   vb->state = VB2_BUF_STATE_IN_REQUEST;
+   mutex_unlock(vb->vb2_queue->lock);
+   WARN_ON(!vb->req_obj.req);
+}
+
+int vb2_core_qbuf(struct vb2_queue *q, unsigned int index, void *pb,
+ struct media_request *req);
+
+static void vb2_req_queue(struct media_request_object *obj)
+{
+   struct vb2_buffer *vb = container_of(obj, struct vb2_buffer, req_obj);
+
+   mutex_lock(vb->vb2_queue->lock);
+   vb2_core_qbuf(vb->vb2_queue, vb->index, NULL, NULL);
+   mutex_unlock(vb->vb2_queue->lock);
+}
+
+static void vb2_req_release(struct media_request_object *obj)
+{
+   struct vb2_buffer *vb = container_of(obj, struct vb2_buffer, req_obj);
+
+   if (vb->state == VB2_BUF_STATE_IN_REQUEST)
+   vb->state = VB2_BUF_STATE_DEQUEUED;
+}
+
+static const struct media_request_object_ops vb2_core_req_ops = {
+   .prepare = vb2_req_prepare,
+   .unprepare = vb2_req_unprepare,
+   .queue = vb2_req_queue,
+   .release = vb2_req_release,
+};
+
 int vb2_core_prepare_buf(struct vb2_queue *q, unsigned int index, void *pb)
 {
struct vb2_buffer *vb;
@@ -1315,7 +1378,7 @@ int vb2_core_prepare_buf(struct vb2_queue *q, unsigned 
int index, void *pb)
 
dprintk(2, "prepare of buffer %d succeeded\n", vb->index);
 
-   return ret;
+   return 0;
 }
 EXPORT_SYMBOL_GPL(vb2_core_prepare_buf);
 
@@ -1382,7 +1445,8 @@ static int vb2_start_streaming(struct vb2_queue *q)
return ret;
 }
 
-int vb2_core_qbuf(struct vb2_queue *q, unsigned int index, void *pb)
+int vb2_core_qbuf(struct vb2_queue *q, unsigned int index, void *pb,
+ struct media_request *req)
 {
struct vb2_buffer *vb;
int ret;
@@ -1394,8 +1458,39 @@ int vb2_core_qbuf(struct vb2_queue *q, unsigned int 
index, void *pb)
 
vb = q->bufs[index];
 
+   if (req) {
+   int ret;
+
+   if (vb->state != VB2_BUF_STATE_DEQUEUED) {
+   dprintk(1, "buffer %d not in