Re: [RFC] V4L2 unified low-level decoder API

2017-06-08 Thread Pawel Osciak
Hi,

On Fri, May 19, 2017 at 1:08 AM, Hugues FRUCHET  wrote:
> Before merging this work Hans would like to have feedback from peers, in
> order to be sure that this is inline with other SoC vendors drivers
> expectations.
>
> Thomasz, Pawel, could you give your view regarding ChromeOS and Rockchip
> driver ?

The drivers for Rockchip codecs are submitted to the public Chromium OS kernel
and working on our RK-based platforms. We have also since added a VP9 API as
well, which is also working on devices that support it. This gives us
a set of H.264,
VP8 and VP9 APIs on both kernel and userspace side (in the open source
Chromium browser) that are working currently and can be used for
further testing.

We are interested in merging the API patches as well as these drivers upstream
(they were posted on this list two years ago), however we've been blocked by the
progress of request API, which is required for this. Alexandre Courbot
is currently
looking into creating a minimal version of the request API that would provide
enough functionality for stateless codecs, and also plans to further work on
re-submitting the particular codec API patches, once the request API
is finalized.

Thanks,
Pawel


Re: [PATCH v4 2/4] [media] videobuf2: return -EPIPE from DQBUF after the last buffer

2015-04-12 Thread Pawel Osciak
Hi,

On Wed, Mar 25, 2015 at 2:46 AM, Philipp Zabel  wrote:
> If the last buffer was dequeued from a capture queue, let poll return
> immediately and let DQBUF return -EPIPE to signal there will no more
> buffers to dequeue until STREAMOFF.
> The driver signals the last buffer by setting the V4L2_BUF_FLAG_LAST.
> To reenable dequeuing on the capture queue, the driver must explicitly
> call vb2_clear_last_buffer_queued. The last buffer queued flag is
> cleared automatically during STREAMOFF.
>
> Signed-off-by: Philipp Zabel 
> ---
> Changes since v3:
>  - Added DocBook update mentioning DQBUF returning -EPIPE in the 
> encoder/decoder
>stop command documentation.
> ---
>  Documentation/DocBook/media/v4l/vidioc-decoder-cmd.xml |  4 +++-
>  Documentation/DocBook/media/v4l/vidioc-encoder-cmd.xml |  4 +++-
>  Documentation/DocBook/media/v4l/vidioc-qbuf.xml|  8 
>  drivers/media/v4l2-core/v4l2-mem2mem.c | 10 +-
>  drivers/media/v4l2-core/videobuf2-core.c   | 18 
> +-
>  include/media/videobuf2-core.h | 10 ++
>  6 files changed, 50 insertions(+), 4 deletions(-)
>
> diff --git a/Documentation/DocBook/media/v4l/vidioc-decoder-cmd.xml 
> b/Documentation/DocBook/media/v4l/vidioc-decoder-cmd.xml

Would it make sense to perhaps split this patch into docbook and vb2
changes please?

> diff --git a/drivers/media/v4l2-core/v4l2-mem2mem.c 
> b/drivers/media/v4l2-core/v4l2-mem2mem.c
> index 80c588f..1b5b432 100644
> --- a/drivers/media/v4l2-core/v4l2-mem2mem.c
> +++ b/drivers/media/v4l2-core/v4l2-mem2mem.c
> @@ -564,8 +564,16 @@ unsigned int v4l2_m2m_poll(struct file *file, struct 
> v4l2_m2m_ctx *m2m_ctx,
>
> if (list_empty(&src_q->done_list))
> poll_wait(file, &src_q->done_wq, wait);
> -   if (list_empty(&dst_q->done_list))
> +   if (list_empty(&dst_q->done_list)) {
> +   /*
> +* If the last buffer was dequeued from the capture queue,
> +* return immediately. DQBUF will return -EPIPE.
> +*/
> +   if (dst_q->last_buffer_dequeued)
> +   return rc | POLLIN | POLLRDNORM;

These indicate there is data to be read. Is there something else we
could return? Maybe POLLHUP?

> +
> poll_wait(file, &dst_q->done_wq, wait);
> +   }
>
> if (m2m_ctx->m2m_dev->m2m_ops->lock)
> m2m_ctx->m2m_dev->m2m_ops->lock(m2m_ctx->priv);
> diff --git a/drivers/media/v4l2-core/videobuf2-core.c 
> b/drivers/media/v4l2-core/videobuf2-core.c
> index bc08a82..a0b9946 100644
> --- a/drivers/media/v4l2-core/videobuf2-core.c
> +++ b/drivers/media/v4l2-core/videobuf2-core.c
> @@ -2046,6 +2046,10 @@ static int vb2_internal_dqbuf(struct vb2_queue *q, 
> struct v4l2_buffer *b, bool n
> struct vb2_buffer *vb = NULL;
> int ret;
>
> +   if (q->last_buffer_dequeued) {
> +   dprintk(3, "last buffer dequeued already\n");
> +   return -EPIPE;
> +   }

This should go after the check for queue type at least. However, best
probably to __vb2_wait_for_done_vb(), where we already have the checks
for q->streaming and q->error.

> if (b->type != q->type) {
> dprintk(1, "invalid buffer type\n");
> return -EINVAL;
> @@ -2073,6 +2077,9 @@ static int vb2_internal_dqbuf(struct vb2_queue *q, 
> struct v4l2_buffer *b, bool n
> /* Remove from videobuf queue */
> list_del(&vb->queued_entry);
> q->queued_count--;
> +   if (!V4L2_TYPE_IS_OUTPUT(q->type) &&
> +   vb->v4l2_buf.flags & V4L2_BUF_FLAG_LAST)
> +   q->last_buffer_dequeued = true;
> /* go back to dequeued state */
> __vb2_dqbuf(vb);
>
> @@ -2286,6 +2293,7 @@ static int vb2_internal_streamoff(struct vb2_queue *q, 
> enum v4l2_buf_type type)
>  */
> __vb2_queue_cancel(q);
> q->waiting_for_buffers = !V4L2_TYPE_IS_OUTPUT(q->type);
> +   q->last_buffer_dequeued = false;
>
> dprintk(3, "successful\n");
> return 0;
> @@ -2628,8 +2636,16 @@ unsigned int vb2_poll(struct vb2_queue *q, struct file 
> *file, poll_table *wait)
> if (V4L2_TYPE_IS_OUTPUT(q->type) && q->queued_count < q->num_buffers)
> return res | POLLOUT | POLLWRNORM;
>
> -   if (list_empty(&q->done_list))
> +   if (list_empty(&q->done_list)) {
> +   /*
> +* If the last buffer was dequeued from a capture queue,
> +* return immediately. DQBUF will return -EPIPE.
> +*/
> +   if (!V4L2_TYPE_IS_OUTPUT(q->type) && q->last_buffer_dequeued)

Do we need to check !V4L2_TYPE_IS_OUTPUT(q->type) here? We wouldn't
have set last_buffer_dequeued to true if it wasn't, so we could drop
this check?

> +   return res | POLLIN | POLLRDNORM;

Same comment as above.

> +
> poll_wait(file, &q->done_wq, wa

Re: [PATCH v4 1/4] [media] videodev2: Add V4L2_BUF_FLAG_LAST

2015-04-12 Thread Pawel Osciak
Hi,
Thanks for working on this!

On Wed, Mar 25, 2015 at 2:46 AM, Philipp Zabel  wrote:
> From: Peter Seiderer 
>
> This v4l2_buffer flag can be used by drivers to mark a capture buffer
> as the last generated buffer, for example after a V4L2_DEC_CMD_STOP
> command was issued.
> The DocBook is updated to mention mem2mem codecs and the mem2mem draining flow
> signals in the VIDIOC_DECODER_CMD V4L2_DEC_CMD_STOP and VIDIOC_ENCODER_CMD
> V4L2_ENC_CMD_STOP documentation.
>
> Signed-off-by: Peter Seiderer 
> Signed-off-by: Philipp Zabel 
> ---
> Changes since v3:
>  - Added DocBook update mentioning V4L2_BUF_FLAG_LAST in the encoder/decoder
>stop command documentation.
> ---
>  Documentation/DocBook/media/v4l/io.xml | 10 ++
>  Documentation/DocBook/media/v4l/vidioc-decoder-cmd.xml |  6 +-
>  Documentation/DocBook/media/v4l/vidioc-encoder-cmd.xml |  5 -
>  include/trace/events/v4l2.h|  3 ++-
>  include/uapi/linux/videodev2.h |  2 ++
>  5 files changed, 23 insertions(+), 3 deletions(-)
>
> diff --git a/Documentation/DocBook/media/v4l/io.xml 
> b/Documentation/DocBook/media/v4l/io.xml
> index 1c17f80..f3b8bc0 100644
> --- a/Documentation/DocBook/media/v4l/io.xml
> +++ b/Documentation/DocBook/media/v4l/io.xml
> @@ -1129,6 +1129,16 @@ in this buffer has not been created by the CPU but by 
> some DMA-capable unit,
>  in which case caches have not been used.
>   
>   
> +   V4L2_BUF_FLAG_LAST
> +   0x0010
> +   Last buffer produced by the hardware. mem2mem codec drivers
> +set this flag on the capture queue for the last buffer when the
> +VIDIOC_QUERYBUF or
> +VIDIOC_DQBUF ioctl is called. After the
> +queue is drained, the VIDIOC_DQBUF ioctl 
> will

Perhaps just s/After the queue is drained, the/Any subsequent/ ? This
would make it more clear I feel.
DQBUF of LAST is the end of draining.

> +not block anymore, but return an &EPIPE;.
> + 
> + 
> V4L2_BUF_FLAG_TIMESTAMP_MASK
> 0xe000
> Mask for timestamp types below. To test the
> diff --git a/Documentation/DocBook/media/v4l/vidioc-decoder-cmd.xml 
> b/Documentation/DocBook/media/v4l/vidioc-decoder-cmd.xml
> index 9215627..cbb7135 100644
> --- a/Documentation/DocBook/media/v4l/vidioc-decoder-cmd.xml
> +++ b/Documentation/DocBook/media/v4l/vidioc-decoder-cmd.xml
> @@ -197,7 +197,11 @@ be muted when playing back at a non-standard speed.
>  this command does nothing. This command has two flags:
>  if V4L2_DEC_CMD_STOP_TO_BLACK is set, then the decoder 
> will
>  set the picture to black after it stopped decoding. Otherwise the last image 
> will
> -repeat. If V4L2_DEC_CMD_STOP_IMMEDIATELY is set, then 
> the decoder
> +repeat. mem2mem decoders will stop producing new frames altogether. They 
> will send
> +a V4L2_EVENT_EOS event after the last frame was decoded 
> and

s/was decoded/has been decoded and all frames are ready to be dequeued/

> +will set the V4L2_BUF_FLAG_LAST buffer flag when there 
> will
> +be no new buffers produced to dequeue.

To make the timing description more explicit, s/when there will be no
new buffers produced to dequeue./on the final buffer being dequeued/
perhaps?
EOS indicates "no more buffers will be produced and all are ready to
be dequeued", while LAST indicates "final buffer being dequeued".

> +If V4L2_DEC_CMD_STOP_IMMEDIATELY is set, then the 
> decoder
>  stops immediately (ignoring the pts value), 
> otherwise it
>  will keep decoding until timestamp >= pts or until the last of the pending 
> data from
>  its internal buffers was decoded.
> diff --git a/Documentation/DocBook/media/v4l/vidioc-encoder-cmd.xml 
> b/Documentation/DocBook/media/v4l/vidioc-encoder-cmd.xml
> index 0619ca5..e9cf601 100644
> --- a/Documentation/DocBook/media/v4l/vidioc-encoder-cmd.xml
> +++ b/Documentation/DocBook/media/v4l/vidioc-encoder-cmd.xml
> @@ -129,7 +129,10 @@ this command.
>  encoding will continue until the end of the current Group
>  Of Pictures, otherwise encoding will stop immediately.
>  When the encoder is already stopped, this command does
> -nothing.
> +nothing. mem2mem encoders will send a V4L2_EVENT_EOS 
> event
> +after the last frame was encoded and will set the
> +V4L2_BUF_FLAG_LAST buffer flag on the capture queue when
> +there will be no new buffers produced to dequeue

I'd propose the same here.

-- 
Thanks,
Pawel
--
To unsubscribe from this list: send the line "unsubscribe linux-media" in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [PATCH v3 0/5] Signalling last decoded frame by V4L2_BUF_FLAG_LAST and -EPIPE

2015-04-08 Thread Pawel Osciak
Hi,

On Tue, Apr 7, 2015 at 11:44 PM, Kamil Debski  wrote:
> Hi,
>
> From: Hans Verkuil [mailto:hverk...@xs4all.nl]
> Sent: Tuesday, March 17, 2015 5:09 PM
>>
>> On 03/17/2015 11:46 AM, Philipp Zabel wrote:
>> > Hi,
>> >
>> > Am Freitag, den 06.03.2015, 11:18 +0100 schrieb Philipp Zabel:
>> >> At the V4L2 codec API session during ELC-E 2014, we agreed that for
>> >> the decoder draining flow, after a V4L2_DEC_CMD_STOP decoder command
>> >> was issued, the last decoded buffer should get dequeued with a
>> >> V4L2_BUF_FLAG_LAST set. After that, poll should immediately return
>> >> and all following VIDIOC_DQBUF should return -EPIPE until the stream
>> is stopped or decoding continued via V4L2_DEC_CMD_START.
>> >> (or STREAMOFF/STREAMON).
>> >>
>> >> Changes since v2:
>> >>  - Made V4L2_BUF_FLAG_LAST known to trace events
>> >>
>> >> regards
>> >> Philipp
>> >>
>> >> Peter Seiderer (1):
>> >>   [media] videodev2: Add V4L2_BUF_FLAG_LAST
>> >>
>> >> Philipp Zabel (4):
>> >>   [media] videobuf2: return -EPIPE from DQBUF after the last buffer
>> >>   [media] coda: Set last buffer flag and fix EOS event
>> >>   [media] s5p-mfc: Set last buffer flag
>> >>   [media] DocBooc: mention mem2mem codecs for encoder/decoder
>> >> commands
>> >>
>> >>  Documentation/DocBook/media/v4l/io.xml | 10 
>> >>  .../DocBook/media/v4l/vidioc-decoder-cmd.xml   |  6 -
>> >>  .../DocBook/media/v4l/vidioc-encoder-cmd.xml   |  5 +++-
>> >>  Documentation/DocBook/media/v4l/vidioc-qbuf.xml|  8 +++
>> >>  drivers/media/platform/coda/coda-bit.c |  4 ++--
>> >>  drivers/media/platform/coda/coda-common.c  | 27 +--
>> ---
>> >>  drivers/media/platform/coda/coda.h |  3 +++
>> >>  drivers/media/platform/s5p-mfc/s5p_mfc.c   |  1 +
>> >>  drivers/media/v4l2-core/v4l2-mem2mem.c | 10 +++-
>> >>  drivers/media/v4l2-core/videobuf2-core.c   | 18
>> ++-
>> >>  include/media/videobuf2-core.h | 10 
>> >>  include/trace/events/v4l2.h|  3 ++-
>> >>  include/uapi/linux/videodev2.h |  2 ++
>> >>  13 files changed, 84 insertions(+), 23 deletions(-)
>> >
>> > are there any further changes that I should make to this series?
>>
>> I'd like to see some Acks, esp. from Kamil and Pawel.
>>
>> I'll take another look as well, probably on Friday.
>>
>
> The patches look good to me, the 4th version is already queued in my tree.
> However I would like to see your opinion. Especially from you Pawel :)

Sorry for the delay, I've been very busy lately, but I really need to
take a look at them. I'll do my best to review this weekend. Putting
on my calendar.
-- 
Regards,
Pawel
--
To unsubscribe from this list: send the line "unsubscribe linux-media" in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: coda: not generating EOS event

2015-01-22 Thread Pawel Osciak
Hi Philipp,

On Thu, Jan 22, 2015 at 11:58 PM, Philipp Zabel  wrote:
> Hi,
>
> Are you planning to pour the workshop's codec API document into a V4L2
> documentation patch?

Yes, definitely, I am a bit delayed, but will do this eventually, this
is in progress. Sorry for the delay. Please feel free to submit
anything related to EOS if you decide to work on this.

-- 
Best regards,
Pawel
--
To unsubscribe from this list: send the line "unsubscribe linux-media" in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [REVIEWv7 PATCH 12/12] vb2: use dma_map_sg_attrs to prevent unnecessary sync

2014-11-23 Thread Pawel Osciak
On Tue, Nov 18, 2014 at 9:51 PM, Hans Verkuil  wrote:
> From: Hans Verkuil 
>
> By default dma_map_sg syncs the mapped buffer to the device. But
> buf_prepare expects a buffer syncs for the cpu and the buffer
> will be synced to the device in the prepare memop.
>
> The reverse is true for dma_unmap_sg, buf_finish and the finish
> memop.
>
> To prevent unnecessary syncs we ask dma_(un)map_sg to skip the
> sync.
>
> Signed-off-by: Hans Verkuil 

Acked-by: Pawel Osciak 

> ---
>  drivers/media/v4l2-core/videobuf2-dma-contig.c | 24 +++
>  drivers/media/v4l2-core/videobuf2-dma-sg.c | 33 
> +-
>  2 files changed, 47 insertions(+), 10 deletions(-)
>
> diff --git a/drivers/media/v4l2-core/videobuf2-dma-contig.c 
> b/drivers/media/v4l2-core/videobuf2-dma-contig.c
> index 0bfc488..b481d20 100644
> --- a/drivers/media/v4l2-core/videobuf2-dma-contig.c
> +++ b/drivers/media/v4l2-core/videobuf2-dma-contig.c
> @@ -511,7 +511,15 @@ static void vb2_dc_put_userptr(void *buf_priv)
> struct sg_table *sgt = buf->dma_sgt;
>
> if (sgt) {
> -   dma_unmap_sg(buf->dev, sgt->sgl, sgt->orig_nents, 
> buf->dma_dir);
> +   DEFINE_DMA_ATTRS(attrs);
> +
> +   dma_set_attr(DMA_ATTR_SKIP_CPU_SYNC, &attrs);
> +   /*
> +* No need to sync to CPU, it's already synced to the CPU
> +* since the finish() memop will have been called before this.
> +*/
> +   dma_unmap_sg_attrs(buf->dev, sgt->sgl, sgt->orig_nents,
> +  buf->dma_dir, &attrs);
> if (!vma_is_io(buf->vma))
> vb2_dc_sgt_foreach_page(sgt, vb2_dc_put_dirty_page);
>
> @@ -568,6 +576,9 @@ static void *vb2_dc_get_userptr(void *alloc_ctx, unsigned 
> long vaddr,
> struct sg_table *sgt;
> unsigned long contig_size;
> unsigned long dma_align = dma_get_cache_alignment();
> +   DEFINE_DMA_ATTRS(attrs);
> +
> +   dma_set_attr(DMA_ATTR_SKIP_CPU_SYNC, &attrs);
>
> /* Only cache aligned DMA transfers are reliable */
> if (!IS_ALIGNED(vaddr | size, dma_align)) {
> @@ -654,8 +665,12 @@ static void *vb2_dc_get_userptr(void *alloc_ctx, 
> unsigned long vaddr,
> kfree(pages);
> pages = NULL;
>
> -   sgt->nents = dma_map_sg(buf->dev, sgt->sgl, sgt->orig_nents,
> -   buf->dma_dir);
> +   /*
> +* No need to sync to the device, this will happen later when the
> +* prepare() memop is called.
> +*/
> +   sgt->nents = dma_map_sg_attrs(buf->dev, sgt->sgl, sgt->orig_nents,
> + buf->dma_dir, &attrs);
> if (sgt->nents <= 0) {
> pr_err("failed to map scatterlist\n");
> ret = -EIO;
> @@ -677,7 +692,8 @@ static void *vb2_dc_get_userptr(void *alloc_ctx, unsigned 
> long vaddr,
> return buf;
>
>  fail_map_sg:
> -   dma_unmap_sg(buf->dev, sgt->sgl, sgt->orig_nents, buf->dma_dir);
> +   dma_unmap_sg_attrs(buf->dev, sgt->sgl, sgt->orig_nents,
> +  buf->dma_dir, &attrs);
>
>  fail_sgt_init:
> if (!vma_is_io(buf->vma))
> diff --git a/drivers/media/v4l2-core/videobuf2-dma-sg.c 
> b/drivers/media/v4l2-core/videobuf2-dma-sg.c
> index c2ec2c4..d75fcf1 100644
> --- a/drivers/media/v4l2-core/videobuf2-dma-sg.c
> +++ b/drivers/media/v4l2-core/videobuf2-dma-sg.c
> @@ -107,6 +107,9 @@ static void *vb2_dma_sg_alloc(void *alloc_ctx, unsigned 
> long size,
> struct sg_table *sgt;
> int ret;
> int num_pages;
> +   DEFINE_DMA_ATTRS(attrs);
> +
> +   dma_set_attr(DMA_ATTR_SKIP_CPU_SYNC, &attrs);
>
> if (WARN_ON(alloc_ctx == NULL))
> return NULL;
> @@ -140,9 +143,13 @@ static void *vb2_dma_sg_alloc(void *alloc_ctx, unsigned 
> long size,
> buf->dev = get_device(conf->dev);
>
> sgt = &buf->sg_table;
> -   if (dma_map_sg(buf->dev, sgt->sgl, sgt->nents, buf->dma_dir) == 0)
> +   /*
> +* No need to sync to the device, this will happen later when the
> +* prepare() memop is called.
> +*/
> +   if (dma_map_sg_attrs(buf->dev, sgt->sgl, sgt->nents,
> +buf->dma_dir, &attrs) == 0)
> goto fail_map;
> -   dma_sync_sg_for_cpu(buf->dev, sgt->sgl, sgt->nents, buf->dma_dir);
>
> buf->handler.refcoun

Re: [REVIEWv7 PATCH 01/12] videobuf2-core.h: improve documentation

2014-11-23 Thread Pawel Osciak
On Tue, Nov 18, 2014 at 9:50 PM, Hans Verkuil  wrote:
> From: Hans Verkuil 
>
> Document that drivers can access/modify the buffer contents in buf_prepare
> and buf_finish. That was not clearly stated before.
>
> Signed-off-by: Hans Verkuil 

Acked-by: Pawel Osciak 

> ---
>  include/media/videobuf2-core.h | 32 +---
>  1 file changed, 17 insertions(+), 15 deletions(-)
>
> diff --git a/include/media/videobuf2-core.h b/include/media/videobuf2-core.h
> index 6ef2d01..70ace7c 100644
> --- a/include/media/videobuf2-core.h
> +++ b/include/media/videobuf2-core.h
> @@ -270,22 +270,24 @@ struct vb2_buffer {
>   * queue setup from completing successfully; optional.
>   * @buf_prepare:   called every time the buffer is queued from userspace
>   * and from the VIDIOC_PREPARE_BUF ioctl; drivers may
> - * perform any initialization required before each 
> hardware
> - * operation in this callback; drivers that support
> - * VIDIOC_CREATE_BUFS must also validate the buffer size;
> - * if an error is returned, the buffer will not be queued
> - * in driver; optional.
> + * perform any initialization required before each
> + * hardware operation in this callback; drivers can
> + * access/modify the buffer here as it is still synced 
> for
> + * the CPU; drivers that support VIDIOC_CREATE_BUFS must
> + * also validate the buffer size; if an error is 
> returned,
> + * the buffer will not be queued in driver; optional.
>   * @buf_finish:called before every dequeue of the buffer 
> back to
> - * userspace; drivers may perform any operations required
> - * before userspace accesses the buffer; optional. The
> - * buffer state can be one of the following: DONE and
> - * ERROR occur while streaming is in progress, and the
> - * PREPARED state occurs when the queue has been canceled
> - * and all pending buffers are being returned to their
> - * default DEQUEUED state. Typically you only have to do
> - * something if the state is VB2_BUF_STATE_DONE, since in
> - * all other cases the buffer contents will be ignored
> - * anyway.
> + * userspace; the buffer is synced for the CPU, so 
> drivers
> + * can access/modify the buffer contents; drivers may
> + * perform any operations required before userspace
> + * accesses the buffer; optional. The buffer state can be
> + * one of the following: DONE and ERROR occur while
> + * streaming is in progress, and the PREPARED state 
> occurs
> + * when the queue has been canceled and all pending
> + * buffers are being returned to their default DEQUEUED
> + * state. Typically you only have to do something if the
> + * state is VB2_BUF_STATE_DONE, since in all other cases
> + * the buffer contents will be ignored anyway.
>   * @buf_cleanup:   called once before the buffer is freed; drivers may
>   *         perform any additional cleanup; optional.
>   * @start_streaming:   called once to enter 'streaming' state; the driver may
> --
> 2.1.1
>



-- 
Best regards,
Pawel Osciak
--
To unsubscribe from this list: send the line "unsubscribe linux-media" in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [REVIEWv7 PATCH 09/12] vb2-vmalloc: add support for dmabuf exports

2014-11-23 Thread Pawel Osciak
On Tue, Nov 18, 2014 at 9:51 PM, Hans Verkuil  wrote:
> From: Hans Verkuil 
>
> Add support for DMABUF exporting to the vb2-vmalloc implementation.
>
> All memory models now have support for both importing and exporting of 
> DMABUFs.
>
> Signed-off-by: Hans Verkuil 

Acked-by: Pawel Osciak 

> ---
>  drivers/media/v4l2-core/videobuf2-vmalloc.c | 171 
> 
>  1 file changed, 171 insertions(+)
>
> diff --git a/drivers/media/v4l2-core/videobuf2-vmalloc.c 
> b/drivers/media/v4l2-core/videobuf2-vmalloc.c
> index bba2460..3966b12 100644
> --- a/drivers/media/v4l2-core/videobuf2-vmalloc.c
> +++ b/drivers/media/v4l2-core/videobuf2-vmalloc.c
> @@ -213,6 +213,176 @@ static int vb2_vmalloc_mmap(void *buf_priv, struct 
> vm_area_struct *vma)
>  }
>
>  /*/
> +/* DMABUF ops for exporters  */
> +/*/
> +
> +struct vb2_vmalloc_attachment {
> +   struct sg_table sgt;
> +   enum dma_data_direction dma_dir;
> +};
> +
> +static int vb2_vmalloc_dmabuf_ops_attach(struct dma_buf *dbuf, struct device 
> *dev,
> +   struct dma_buf_attachment *dbuf_attach)
> +{
> +   struct vb2_vmalloc_attachment *attach;
> +   struct vb2_vmalloc_buf *buf = dbuf->priv;
> +   int num_pages = PAGE_ALIGN(buf->size) / PAGE_SIZE;
> +   struct sg_table *sgt;
> +   struct scatterlist *sg;
> +   void *vaddr = buf->vaddr;
> +   int ret;
> +   int i;
> +
> +   attach = kzalloc(sizeof(*attach), GFP_KERNEL);
> +   if (!attach)
> +   return -ENOMEM;
> +
> +   sgt = &attach->sgt;
> +   ret = sg_alloc_table(sgt, num_pages, GFP_KERNEL);
> +   if (ret) {
> +   kfree(attach);
> +   return ret;
> +   }
> +   for_each_sg(sgt->sgl, sg, sgt->nents, i) {
> +   struct page *page = vmalloc_to_page(vaddr);
> +
> +   if (!page) {
> +   sg_free_table(sgt);
> +   kfree(attach);
> +   return -ENOMEM;
> +   }
> +   sg_set_page(sg, page, PAGE_SIZE, 0);
> +   vaddr += PAGE_SIZE;
> +   }
> +
> +   attach->dma_dir = DMA_NONE;
> +   dbuf_attach->priv = attach;
> +   return 0;
> +}
> +
> +static void vb2_vmalloc_dmabuf_ops_detach(struct dma_buf *dbuf,
> +   struct dma_buf_attachment *db_attach)
> +{
> +   struct vb2_vmalloc_attachment *attach = db_attach->priv;
> +   struct sg_table *sgt;
> +
> +   if (!attach)
> +   return;
> +
> +   sgt = &attach->sgt;
> +
> +   /* release the scatterlist cache */
> +   if (attach->dma_dir != DMA_NONE)
> +   dma_unmap_sg(db_attach->dev, sgt->sgl, sgt->orig_nents,
> +   attach->dma_dir);
> +   sg_free_table(sgt);
> +   kfree(attach);
> +   db_attach->priv = NULL;
> +}
> +
> +static struct sg_table *vb2_vmalloc_dmabuf_ops_map(
> +   struct dma_buf_attachment *db_attach, enum dma_data_direction dma_dir)
> +{
> +   struct vb2_vmalloc_attachment *attach = db_attach->priv;
> +   /* stealing dmabuf mutex to serialize map/unmap operations */
> +   struct mutex *lock = &db_attach->dmabuf->lock;
> +   struct sg_table *sgt;
> +   int ret;
> +
> +   mutex_lock(lock);
> +
> +   sgt = &attach->sgt;
> +   /* return previously mapped sg table */
> +   if (attach->dma_dir == dma_dir) {
> +   mutex_unlock(lock);
> +   return sgt;
> +   }
> +
> +   /* release any previous cache */
> +   if (attach->dma_dir != DMA_NONE) {
> +   dma_unmap_sg(db_attach->dev, sgt->sgl, sgt->orig_nents,
> +   attach->dma_dir);
> +   attach->dma_dir = DMA_NONE;
> +   }
> +
> +   /* mapping to the client with new direction */
> +   ret = dma_map_sg(db_attach->dev, sgt->sgl, sgt->orig_nents, dma_dir);
> +   if (ret <= 0) {
> +   pr_err("failed to map scatterlist\n");
> +   mutex_unlock(lock);
> +   return ERR_PTR(-EIO);
> +   }
> +
> +   attach->dma_dir = dma_dir;
> +
> +   mutex_unlock(lock);
> +
> +   return sgt;
> +}
> +
> +static void vb2_vmalloc_dmabuf_ops_unmap(struct dma_buf_attachment 
> *db_attach,
> +   struct sg_table *sgt, enum dma_data_direction dma_dir)
> +{
> +   /* nothing to be done here */
> +}
> +
> +s

Re: [REVIEWv7 PATCH 05/12] vb2-dma-sg: add allocation context to dma-sg

2014-11-23 Thread Pawel Osciak
On Tue, Nov 18, 2014 at 9:51 PM, Hans Verkuil  wrote:
> From: Hans Verkuil 
>
> Require that dma-sg also uses an allocation context. This is in preparation
> for adding prepare/finish memops to sync the memory between DMA and CPU.
>
> Signed-off-by: Hans Verkuil 

Acked-by: Pawel Osciak 

-- 
Best regards,
Pawel Osciak
--
To unsubscribe from this list: send the line "unsubscribe linux-media" in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [REVIEWv7 PATCH 04/12] vb2: don't free alloc context if it is ERR_PTR

2014-11-23 Thread Pawel Osciak
On Tue, Nov 18, 2014 at 9:51 PM, Hans Verkuil  wrote:
> From: Hans Verkuil 
>
> Don't try to free a pointer containing an ERR_PTR().
>
> Signed-off-by: Hans Verkuil 

Acked-by: Pawel Osciak 

-- 
Best regards,
Pawel Osciak
--
To unsubscribe from this list: send the line "unsubscribe linux-media" in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [RFCv6 PATCH 11/16] vb2: use dma_map_sg_attrs to prevent unnecessary sync

2014-11-18 Thread Pawel Osciak
On Mon, Nov 10, 2014 at 8:49 PM, Hans Verkuil  wrote:
> From: Hans Verkuil 
>
> By default dma_map_sg syncs the mapped buffer to the device. But
> buf_prepare expects a buffer syncs for the cpu and the buffer
> will be synced to the device in the prepare memop.
>
> The reverse is true for dma_unmap_sg, buf_finish and the finish
> memop.
>
> To prevent unnecessary syncs we ask dma_(un)map_sg to skip the
> sync.
>
> Signed-off-by: Hans Verkuil 
> ---
>  drivers/media/v4l2-core/videobuf2-dma-contig.c | 29 +-
>  drivers/media/v4l2-core/videobuf2-dma-sg.c | 33 
> +-
>  2 files changed, 50 insertions(+), 12 deletions(-)
>
> diff --git a/drivers/media/v4l2-core/videobuf2-dma-contig.c 
> b/drivers/media/v4l2-core/videobuf2-dma-contig.c
> index c4305bf..27f5926 100644
> --- a/drivers/media/v4l2-core/videobuf2-dma-contig.c
> +++ b/drivers/media/v4l2-core/videobuf2-dma-contig.c
> @@ -317,8 +317,9 @@ static struct sg_table *vb2_dc_dmabuf_ops_map(
> attach->dma_dir = DMA_NONE;
> }
>
> -   /* mapping to the client with new direction */
> -   ret = dma_map_sg(db_attach->dev, sgt->sgl, sgt->orig_nents, dma_dir);
> +   /* Mapping to the client with new direction */
> +   ret = dma_map_sg(db_attach->dev, sgt->sgl, sgt->orig_nents,
> +dma_dir);

Do we need this chunk?

-- 
Best regards,
Pawel Osciak
--
To unsubscribe from this list: send the line "unsubscribe linux-media" in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [RFCv6 PATCH 09/16] vivid: enable vb2_expbuf support.

2014-11-18 Thread Pawel Osciak
On Mon, Nov 10, 2014 at 8:49 PM, Hans Verkuil  wrote:
> From: Hans Verkuil 
>
> Now that vb2 supports DMABUF export for dma-sg and vmalloc memory
> modes, we can enable the vb2_expbuf support in vivid.
>
> Signed-off-by: Hans Verkuil 

Reviewed-by: Pawel Osciak 

> ---
>  drivers/media/platform/vivid/vivid-core.c | 2 +-
>  1 file changed, 1 insertion(+), 1 deletion(-)
>
> diff --git a/drivers/media/platform/vivid/vivid-core.c 
> b/drivers/media/platform/vivid/vivid-core.c
> index 2c61a62..7de8d9d 100644
> --- a/drivers/media/platform/vivid/vivid-core.c
> +++ b/drivers/media/platform/vivid/vivid-core.c
> @@ -588,7 +588,7 @@ static const struct v4l2_ioctl_ops vivid_ioctl_ops = {
> .vidioc_querybuf= vb2_ioctl_querybuf,
> .vidioc_qbuf= vb2_ioctl_qbuf,
> .vidioc_dqbuf   = vb2_ioctl_dqbuf,
> -/* Not yet .vidioc_expbuf  = vb2_ioctl_expbuf,*/
> +   .vidioc_expbuf  = vb2_ioctl_expbuf,
> .vidioc_streamon= vb2_ioctl_streamon,
> .vidioc_streamoff       = vb2_ioctl_streamoff,
>
> --
> 2.1.1
>


-- 
Best regards,
Pawel Osciak
--
To unsubscribe from this list: send the line "unsubscribe linux-media" in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [RFCv6 PATCH 08/16] vb2-vmalloc: add support for dmabuf exports

2014-11-18 Thread Pawel Osciak
On Mon, Nov 10, 2014 at 8:49 PM, Hans Verkuil  wrote:
> From: Hans Verkuil 
>
> Add support for DMABUF exporting to the vb2-vmalloc implementation.
>
> All memory models now have support for both importing and exporting of 
> DMABUFs.
> Signed-off-by: Hans Verkuil 
> ---
>  drivers/media/v4l2-core/videobuf2-vmalloc.c | 174 
> 
>  1 file changed, 174 insertions(+)
>
> diff --git a/drivers/media/v4l2-core/videobuf2-vmalloc.c 
> b/drivers/media/v4l2-core/videobuf2-vmalloc.c
> index bba2460..dfbb6d5 100644
> --- a/drivers/media/v4l2-core/videobuf2-vmalloc.c
> +++ b/drivers/media/v4l2-core/videobuf2-vmalloc.c
> @@ -31,6 +31,9 @@ struct vb2_vmalloc_buf {
> atomic_trefcount;
> struct vb2_vmarea_handler   handler;
> struct dma_buf  *dbuf;
> +
> +   /* DMABUF related */
> +   struct dma_buf_attachment   *db_attach;

Unused?

-- 
Best regards,
Pawel Osciak
--
To unsubscribe from this list: send the line "unsubscribe linux-media" in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [RFCv6 PATCH 10/16] vim2m: support expbuf

2014-11-18 Thread Pawel Osciak
On Mon, Nov 10, 2014 at 8:49 PM, Hans Verkuil  wrote:
> From: Hans Verkuil 
>
> Signed-off-by: Hans Verkuil 

Reviewed-by: Pawel Osciak 

> ---
>  drivers/media/platform/vim2m.c | 1 +
>  1 file changed, 1 insertion(+)
>
> diff --git a/drivers/media/platform/vim2m.c b/drivers/media/platform/vim2m.c
> index 87af47a..1105c11 100644
> --- a/drivers/media/platform/vim2m.c
> +++ b/drivers/media/platform/vim2m.c
> @@ -697,6 +697,7 @@ static const struct v4l2_ioctl_ops vim2m_ioctl_ops = {
> .vidioc_querybuf= v4l2_m2m_ioctl_querybuf,
> .vidioc_qbuf= v4l2_m2m_ioctl_qbuf,
> .vidioc_dqbuf   = v4l2_m2m_ioctl_dqbuf,
> +   .vidioc_expbuf  = v4l2_m2m_ioctl_expbuf,
>
> .vidioc_streamon= v4l2_m2m_ioctl_streamon,
> .vidioc_streamoff   = v4l2_m2m_ioctl_streamoff,
> --
> 2.1.1
>


-- 
Best regards,
Pawel Osciak
--
To unsubscribe from this list: send the line "unsubscribe linux-media" in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [RFCv6 PATCH 07/16] vb2-dma-sg: add support for dmabuf exports

2014-11-16 Thread Pawel Osciak
On Mon, Nov 10, 2014 at 8:49 PM, Hans Verkuil  wrote:
> From: Hans Verkuil 
>
> Add DMABUF export support to vb2-dma-sg.
>
> Signed-off-by: Hans Verkuil 

Acked-by: Pawel Osciak 

-- 
Best regards,
Pawel Osciak
--
To unsubscribe from this list: send the line "unsubscribe linux-media" in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [RFCv6 PATCH 06/16] vb2-dma-sg: add dmabuf import support

2014-11-16 Thread Pawel Osciak
On Mon, Nov 10, 2014 at 8:49 PM, Hans Verkuil  wrote:
> From: Hans Verkuil 
>
> Add support for importing dmabuf to videobuf2-dma-sg.
>
> Signed-off-by: Hans Verkuil 

Acked-by: Pawel Osciak 


-- 
Best regards,
Pawel Osciak
--
To unsubscribe from this list: send the line "unsubscribe linux-media" in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [RFCv6 PATCH 04/16] vb2-dma-sg: add allocation context to dma-sg

2014-11-16 Thread Pawel Osciak
On Mon, Nov 10, 2014 at 8:49 PM, Hans Verkuil  wrote:
> From: Hans Verkuil 
>
> Require that dma-sg also uses an allocation context. This is in preparation
> for adding prepare/finish memops to sync the memory between DMA and CPU.
>
> Signed-off-by: Hans Verkuil 
> ---

[...]

> @@ -166,6 +177,7 @@ static void *vb2_dma_sg_get_userptr(void *alloc_ctx, 
> unsigned long vaddr,
> unsigned long size,
> enum dma_data_direction dma_dir)
>  {
> +   struct vb2_dma_sg_conf *conf = alloc_ctx;
> struct vb2_dma_sg_buf *buf;
> unsigned long first, last;
> int num_pages_from_user;
> @@ -235,6 +247,8 @@ static void *vb2_dma_sg_get_userptr(void *alloc_ctx, 
> unsigned long vaddr,
> buf->num_pages, buf->offset, size, 0))
> goto userptr_fail_alloc_table_from_pages;
>
> +   /* Prevent the device from being released while the buffer is used */
> +   buf->dev = get_device(conf->dev);

I'm not sure if we should be managing this... As far as I understand
the logic behind taking a ref in alloc, if we are the exporter, we may
have to keep it in case we need to free the buffers after our device
goes away. But for userptr, we only need this for syncs, and in that
case it's triggered by our driver, so I think we don't have to worry
about that. If we do though, then dma-contig should be doing this as
well.

> return buf;
>
>  userptr_fail_alloc_table_from_pages:
> @@ -274,6 +288,7 @@ static void vb2_dma_sg_put_userptr(void *buf_priv)
> }
> kfree(buf->pages);
> vb2_put_vma(buf->vma);
> +   put_device(buf->dev);
> kfree(buf);
>  }
>
> @@ -356,6 +371,27 @@ const struct vb2_mem_ops vb2_dma_sg_memops = {
>  };
>  EXPORT_SYMBOL_GPL(vb2_dma_sg_memops);
>
> +void *vb2_dma_sg_init_ctx(struct device *dev)
> +{
> +   struct vb2_dma_sg_conf *conf;
> +
> +   conf = kzalloc(sizeof(*conf), GFP_KERNEL);
> +   if (!conf)
> +   return ERR_PTR(-ENOMEM);
> +
> +   conf->dev = dev;
> +
> +   return conf;
> +}
> +EXPORT_SYMBOL_GPL(vb2_dma_sg_init_ctx);
> +
> +void vb2_dma_sg_cleanup_ctx(void *alloc_ctx)
> +{
> +   if (!IS_ERR_OR_NULL(alloc_ctx))

I would prefer not doing this, it's very weird and would really just
be a programming bug.


-- 
Best regards,
Pawel Osciak
--
To unsubscribe from this list: send the line "unsubscribe linux-media" in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [RFCv6 PATCH 03/16] vb2: add dma_dir to the alloc memop.

2014-11-16 Thread Pawel Osciak
On Mon, Nov 10, 2014 at 8:49 PM, Hans Verkuil  wrote:
> From: Hans Verkuil 
>
> This is needed for the next patch where the dma-sg alloc memop needs
> to know the dma_dir.
>
> Signed-off-by: Hans Verkuil 

Acked-by: Pawel Osciak 

-- 
Best regards,
Pawel Osciak
--
To unsubscribe from this list: send the line "unsubscribe linux-media" in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [RFCv6 PATCH 02/16] vb2: replace 'write' by 'dma_dir'

2014-11-16 Thread Pawel Osciak
On Mon, Nov 10, 2014 at 8:49 PM, Hans Verkuil  wrote:
> From: Hans Verkuil 
>
> The 'write' argument is very ambiguous. I first assumed that if it is 1,
> then we're doing video output but instead it meant the reverse.
>
> Since it is used to setup the dma_dir value anyway it is now replaced by
> the correct dma_dir value which is unambiguous.
>
> Signed-off-by: Hans Verkuil 

Acked-by: Pawel Osciak 

-- 
Best regards,
Pawel Osciak
--
To unsubscribe from this list: send the line "unsubscribe linux-media" in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [RFCv5 PATCH 07/15] vb2: replace 'write' by 'dma_dir'

2014-11-08 Thread Pawel Osciak
Hi Hans,

On Fri, Nov 7, 2014 at 5:50 PM, Hans Verkuil  wrote:
> From: Hans Verkuil 
>
> The 'write' argument is very ambiguous. I first assumed that if it is 1,
> then we're doing video output but instead it meant the reverse.
>
> Since it is used to setup the dma_dir value anyway it is now replaced by
> the correct dma_dir value which is unambiguous.

Do we need the first patch adding write then? Maybe we could squash
somehow and redo the series please?

-- 
Best regards,
Pawel Osciak
--
To unsubscribe from this list: send the line "unsubscribe linux-media" in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [RFCv5 PATCH 05/15] vb2-dma-sg: add get_dmabuf

2014-11-08 Thread Pawel Osciak
Hi Hans,
Thank you for the patch.

On Fri, Nov 7, 2014 at 5:50 PM, Hans Verkuil  wrote:
> From: Hans Verkuil 
>
> Add DMABUF export support to vb2-dma-sg.

I think we should mention in the subject that this adds dmabuf export to dma-sg.

> Signed-off-by: Hans Verkuil 
> ---
>  drivers/media/v4l2-core/videobuf2-dma-sg.c | 170 
> +
>  1 file changed, 170 insertions(+)
>
> diff --git a/drivers/media/v4l2-core/videobuf2-dma-sg.c 
> b/drivers/media/v4l2-core/videobuf2-dma-sg.c
> index 2795c27..ca28a50 100644
> --- a/drivers/media/v4l2-core/videobuf2-dma-sg.c
> +++ b/drivers/media/v4l2-core/videobuf2-dma-sg.c
> @@ -407,6 +407,175 @@ static int vb2_dma_sg_mmap(void *buf_priv, struct 
> vm_area_struct *vma)
>  }
>
>  /*/
> +/* DMABUF ops for exporters  */
> +/*/
> +
> +struct vb2_dma_sg_attachment {
> +   struct sg_table sgt;
> +   enum dma_data_direction dir;
> +};
> +
> +static int vb2_dma_sg_dmabuf_ops_attach(struct dma_buf *dbuf, struct device 
> *dev,
> +   struct dma_buf_attachment *dbuf_attach)
> +{
> +   struct vb2_dma_sg_attachment *attach;
> +   unsigned int i;
> +   struct scatterlist *rd, *wr;
> +   struct sg_table *sgt;
> +   struct vb2_dma_sg_buf *buf = dbuf->priv;
> +   int ret;
> +
> +   attach = kzalloc(sizeof(*attach), GFP_KERNEL);
> +   if (!attach)
> +   return -ENOMEM;
> +
> +   sgt = &attach->sgt;
> +   /* Copy the buf->base_sgt scatter list to the attachment, as we can't
> +* map the same scatter list to multiple attachments at the same time.
> +*/
> +   ret = sg_alloc_table(sgt, buf->dma_sgt->orig_nents, GFP_KERNEL);
> +   if (ret) {
> +   kfree(attach);
> +   return -ENOMEM;
> +   }
> +
> +   rd = buf->dma_sgt->sgl;
> +   wr = sgt->sgl;
> +   for (i = 0; i < sgt->orig_nents; ++i) {
> +   sg_set_page(wr, sg_page(rd), rd->length, rd->offset);
> +   rd = sg_next(rd);
> +   wr = sg_next(wr);
> +   }
> +
> +   attach->dir = DMA_NONE;
> +   dbuf_attach->priv = attach;
> +
> +   return 0;
> +}
> +
> +static void vb2_dma_sg_dmabuf_ops_detach(struct dma_buf *dbuf,
> +   struct dma_buf_attachment *db_attach)
> +{
> +   struct vb2_dma_sg_attachment *attach = db_attach->priv;
> +   struct sg_table *sgt;
> +
> +   if (!attach)
> +   return;
> +
> +   sgt = &attach->sgt;
> +
> +   /* release the scatterlist cache */
> +   if (attach->dir != DMA_NONE)
> +   dma_unmap_sg(db_attach->dev, sgt->sgl, sgt->orig_nents,
> +   attach->dir);
> +   sg_free_table(sgt);
> +   kfree(attach);
> +   db_attach->priv = NULL;
> +}
> +
> +static struct sg_table *vb2_dma_sg_dmabuf_ops_map(
> +   struct dma_buf_attachment *db_attach, enum dma_data_direction dir)
> +{
> +   struct vb2_dma_sg_attachment *attach = db_attach->priv;
> +   /* stealing dmabuf mutex to serialize map/unmap operations */
> +   struct mutex *lock = &db_attach->dmabuf->lock;
> +   struct sg_table *sgt;
> +   int ret;
> +
> +   mutex_lock(lock);
> +
> +   sgt = &attach->sgt;
> +   /* return previously mapped sg table */
> +   if (attach->dir == dir) {
> +   mutex_unlock(lock);
> +   return sgt;
> +   }
> +
> +   /* release any previous cache */
> +   if (attach->dir != DMA_NONE) {
> +   dma_unmap_sg(db_attach->dev, sgt->sgl, sgt->orig_nents,
> +   attach->dir);
> +   attach->dir = DMA_NONE;
> +   }
> +
> +   /* mapping to the client with new direction */
> +   ret = dma_map_sg(db_attach->dev, sgt->sgl, sgt->orig_nents, dir);
> +   if (ret <= 0) {
> +   pr_err("failed to map scatterlist\n");
> +   mutex_unlock(lock);
> +   return ERR_PTR(-EIO);
> +   }
> +
> +   attach->dir = dir;
> +
> +   mutex_unlock(lock);
> +
> +   return sgt;
> +}
> +
> +static void vb2_dma_sg_dmabuf_ops_unmap(struct dma_buf_attachment *db_attach,
> +   struct sg_table *sgt, enum dma_data_direction dir)
> +{
> +   /* nothing to be done here */
> +}
> +
> +static void vb2_dma_sg_dmabuf_ops_release(struct dma_buf *dbuf)
> +{
> +   /* drop reference obtained i

Re: [RFCv5 PATCH 04/15] vb2-dma-sg: add dmabuf import support

2014-11-08 Thread Pawel Osciak
On Sat, Nov 8, 2014 at 7:20 PM, Pawel Osciak  wrote:
> Hi Hans,
> Thank you for the patch.
>
> On Fri, Nov 7, 2014 at 5:50 PM, Hans Verkuil  wrote:
>> From: Hans Verkuil 
>>
>> Add support for dmabuf to vb2-dma-sg.
>
> importing dmabuf into videobuf2-dma-sg.
>

One thing I missed in the review, I think vb2_dma_sg_vaddr() needs to
be updated in this patch to take into account that we may have an
attachment present, just like it's done in dma-contig, i.e. if !vaddr
and attachment present, call the dma_buf_vmap() dmabuf op instead of
vm_map_ram.

-- 
Best regards,
Pawel Osciak
--
To unsubscribe from this list: send the line "unsubscribe linux-media" in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [RFCv5 PATCH 04/15] vb2-dma-sg: add dmabuf import support

2014-11-08 Thread Pawel Osciak
tr_fail_alloc_table_from_pages;
>
> @@ -319,7 +333,7 @@ static void vb2_dma_sg_put_userptr(void *buf_priv)
> dma_unmap_sg(buf->dev, sgt->sgl, sgt->nents, buf->dma_dir);
> if (buf->vaddr)
> vm_unmap_ram(buf->vaddr, buf->num_pages);
> -   sg_free_table(&buf->sg_table);
> +   sg_free_table(buf->dma_sgt);
> while (--i >= 0) {
> if (buf->write)
> set_page_dirty_lock(buf->pages[i]);
> @@ -392,11 +406,105 @@ static int vb2_dma_sg_mmap(void *buf_priv, struct 
> vm_area_struct *vma)
> return 0;
>  }
>
> +/*/
> +/*   callbacks for DMABUF buffers*/
> +/*/
> +
> +static int vb2_dma_sg_map_dmabuf(void *mem_priv)
> +{
> +   struct vb2_dma_sg_buf *buf = mem_priv;
> +   struct sg_table *sgt;
> +
> +   if (WARN_ON(!buf->db_attach)) {
> +   pr_err("trying to pin a non attached buffer\n");
> +   return -EINVAL;
> +   }
> +
> +   if (WARN_ON(buf->dma_sgt)) {
> +   pr_err("dmabuf buffer is already pinned\n");
> +   return 0;
> +   }
> +
> +   /* get the associated scatterlist for this buffer */
> +   sgt = dma_buf_map_attachment(buf->db_attach, buf->dma_dir);
> +   if (IS_ERR_OR_NULL(sgt)) {

Hm, this was changed to IS_ERR() in dma-contig quite a long time ago
(see 
http://git.linuxtv.org/cgit.cgi/media_tree.git/commit/drivers/media/v4l2-core/videobuf2-dma-contig.c?id=fee0c54e28f6ca187add93dfca226a8093cfa931).
Are you basing this on an old version of dma-contig?

> +   pr_err("Error getting dmabuf scatterlist\n");
> +   return -EINVAL;
> +   }
> +
> +   buf->dma_sgt = sgt;

In another patch also upstream in contig
(http://git.linuxtv.org/cgit.cgi/media_tree.git/commit/drivers/media/v4l2-core/videobuf2-dma-contig.c?id=6bbd4fec0cd93823fe651fa3907bee2bc6c814f6),
we have

buf->vaddr = NULL;

> +
> +   return 0;
> +}
> +
> +static void vb2_dma_sg_unmap_dmabuf(void *mem_priv)
> +{
> +   struct vb2_dma_sg_buf *buf = mem_priv;
> +   struct sg_table *sgt = buf->dma_sgt;
> +
> +   if (WARN_ON(!buf->db_attach)) {
> +   pr_err("trying to unpin a not attached buffer\n");
> +   return;
> +   }
> +
> +   if (WARN_ON(!sgt)) {
> +   pr_err("dmabuf buffer is already unpinned\n");
> +   return;
> +   }
> +
> +   dma_buf_unmap_attachment(buf->db_attach, sgt, buf->dma_dir);
> +
> +   buf->dma_sgt = NULL;
> +}
> +
> +static void vb2_dma_sg_detach_dmabuf(void *mem_priv)
> +{
> +   struct vb2_dma_sg_buf *buf = mem_priv;
> +
> +   /* if vb2 works correctly you should never detach mapped buffer */
> +   if (WARN_ON(buf->dma_sgt))
> +   vb2_dma_sg_unmap_dmabuf(buf);
> +
> +   /* detach this attachment */
> +   dma_buf_detach(buf->db_attach->dmabuf, buf->db_attach);
> +   kfree(buf);
> +}
> +
> +static void *vb2_dma_sg_attach_dmabuf(void *alloc_ctx, struct dma_buf *dbuf,
> +   unsigned long size, int write)
> +{
> +   struct vb2_dma_sg_conf *conf = alloc_ctx;
> +   struct vb2_dma_sg_buf *buf;
> +   struct dma_buf_attachment *dba;
> +
> +   if (dbuf->size < size)
> +   return ERR_PTR(-EFAULT);
> +
> +   buf = kzalloc(sizeof(*buf), GFP_KERNEL);
> +   if (!buf)
> +   return ERR_PTR(-ENOMEM);
> +
> +   buf->dev = conf->dev;
> +   /* create attachment for the dmabuf with the user device */

I'd remove this comment, it's not that correct either.

> +   dba = dma_buf_attach(dbuf, buf->dev);
> +   if (IS_ERR(dba)) {
> +   pr_err("failed to attach dmabuf\n");
> +   kfree(buf);
> +   return dba;
> +   }
> +
> +   buf->dma_dir = write ? DMA_FROM_DEVICE : DMA_TO_DEVICE;
> +   buf->size = size;
> +   buf->db_attach = dba;
> +
> +   return buf;
> +}
> +
>  static void *vb2_dma_sg_cookie(void *buf_priv)
>  {
> struct vb2_dma_sg_buf *buf = buf_priv;
>
> -   return &buf->sg_table;
> +   return buf->dma_sgt;
>  }
>
>  const struct vb2_mem_ops vb2_dma_sg_memops = {
> @@ -409,6 +517,10 @@ const struct vb2_mem_ops vb2_dma_sg_memops = {
> .vaddr  = vb2_dma_sg_vaddr,
> .mmap   = vb2_dma_sg_mmap,
> .num_users  = vb2_dma_sg_num_users,
> +   .map_dmabuf = vb2_dma_sg_map_dmabuf,
> +   .unmap_dmabuf   = vb2_dma_sg_unmap_dmabuf,
> +   .attach_dmabuf  = vb2_dma_sg_attach_dmabuf,
> +   .detach_dmabuf  = vb2_dma_sg_detach_dmabuf,
> .cookie = vb2_dma_sg_cookie,
>  };
>  EXPORT_SYMBOL_GPL(vb2_dma_sg_memops);
> --
> 2.1.1
>



-- 
Best regards,
Pawel Osciak
--
To unsubscribe from this list: send the line "unsubscribe linux-media" in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [RFCv5 PATCH 03/15] vb2-dma-sg: move dma_(un)map_sg here

2014-11-08 Thread Pawel Osciak
Hi Hans,
Thank you for the patch.

On Fri, Nov 7, 2014 at 5:50 PM, Hans Verkuil  wrote:
> From: Hans Verkuil 
>
> This moves dma_(un)map_sg to the get_userptr/put_userptr and alloc/put
> memops of videobuf2-dma-sg.c and adds dma_sync_sg_for_device/cpu to the
> prepare/finish memops.
>
> Now that vb2-dma-sg will sync the buffers for you in the prepare/finish
> memops we can drop that from the drivers that use dma-sg.
>
> For the solo6x10 driver that was a bit more involved because it needs to
> copy JPEG or MPEG headers to the buffer before returning it to userspace,
> and that cannot be done in the old place since the buffer there is still
> setup for DMA access, not for CPU access. However, the buf_finish
> op is the ideal place to do this. By the time buf_finish is called
> the buffer is available for CPU access, so copying to the buffer is fine.
>
> Signed-off-by: Hans Verkuil 

Acked-by: Pawel Osciak 

-- 
Best regards,
Pawel Osciak
--
To unsubscribe from this list: send the line "unsubscribe linux-media" in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [RFCv5 PATCH 02/15] vb2-dma-sg: add allocation context to dma-sg

2014-11-08 Thread Pawel Osciak
vb2_dma_sg_alloc(void *alloc_ctx, unsigned 
> long size, gfp_t gfp_fla
> if (ret)
> goto fail_table_alloc;
>
> +   /* Prevent the device from being released while the buffer is used */
> +   buf->dev = get_device(conf->dev);
> buf->handler.refcount = &buf->refcount;
> buf->handler.put = vb2_dma_sg_put;
> buf->handler.arg = buf;
> @@ -152,6 +165,7 @@ static void vb2_dma_sg_put(void *buf_priv)
> while (--i >= 0)
> __free_page(buf->pages[i]);
> kfree(buf->pages);
> +   put_device(buf->dev);
> kfree(buf);
> }
>  }
> @@ -164,6 +178,7 @@ static inline int vma_is_io(struct vm_area_struct *vma)
>  static void *vb2_dma_sg_get_userptr(void *alloc_ctx, unsigned long vaddr,
> unsigned long size, int write)
>  {
> +   struct vb2_dma_sg_conf *conf = alloc_ctx;
> struct vb2_dma_sg_buf *buf;
> unsigned long first, last;
> int num_pages_from_user;
> @@ -177,6 +192,7 @@ static void *vb2_dma_sg_get_userptr(void *alloc_ctx, 
> unsigned long vaddr,
> buf->write = write;
> buf->offset = vaddr & ~PAGE_MASK;
> buf->size = size;
> +   buf->dma_dir = write ? DMA_FROM_DEVICE : DMA_TO_DEVICE;
>
> first = (vaddr   & PAGE_MASK) >> PAGE_SHIFT;
> last  = ((vaddr + size - 1) & PAGE_MASK) >> PAGE_SHIFT;
> @@ -233,6 +249,8 @@ static void *vb2_dma_sg_get_userptr(void *alloc_ctx, 
> unsigned long vaddr,
> buf->num_pages, buf->offset, size, 0))
> goto userptr_fail_alloc_table_from_pages;
>
> +   /* Prevent the device from being released while the buffer is used */
> +   buf->dev = get_device(conf->dev);
> return buf;
>
>  userptr_fail_alloc_table_from_pages:
> @@ -272,6 +290,7 @@ static void vb2_dma_sg_put_userptr(void *buf_priv)
> }
> kfree(buf->pages);
> vb2_put_vma(buf->vma);
> +   put_device(buf->dev);
> kfree(buf);
>  }
>
> @@ -354,6 +373,27 @@ const struct vb2_mem_ops vb2_dma_sg_memops = {
>  };
>  EXPORT_SYMBOL_GPL(vb2_dma_sg_memops);
>
> +void *vb2_dma_sg_init_ctx(struct device *dev)
> +{
> +   struct vb2_dma_sg_conf *conf;
> +
> +   conf = kzalloc(sizeof(*conf), GFP_KERNEL);
> +   if (!conf)
> +   return ERR_PTR(-ENOMEM);
> +
> +   conf->dev = dev;
> +
> +   return conf;
> +}
> +EXPORT_SYMBOL_GPL(vb2_dma_sg_init_ctx);
> +
> +void vb2_dma_sg_cleanup_ctx(void *alloc_ctx)
> +{
> +   if (!IS_ERR_OR_NULL(alloc_ctx))
> +   kfree(alloc_ctx);
> +}
> +EXPORT_SYMBOL_GPL(vb2_dma_sg_cleanup_ctx);
> +
>  MODULE_DESCRIPTION("dma scatter/gather memory handling routines for 
> videobuf2");
>  MODULE_AUTHOR("Andrzej Pietrasiewicz");
>  MODULE_LICENSE("GPL");
> diff --git a/drivers/media/v4l2-core/videobuf2-vmalloc.c 
> b/drivers/media/v4l2-core/videobuf2-vmalloc.c
> index 313d977..d77e397 100644
> --- a/drivers/media/v4l2-core/videobuf2-vmalloc.c
> +++ b/drivers/media/v4l2-core/videobuf2-vmalloc.c
> @@ -35,7 +35,8 @@ struct vb2_vmalloc_buf {
>
>  static void vb2_vmalloc_put(void *buf_priv);
>
> -static void *vb2_vmalloc_alloc(void *alloc_ctx, unsigned long size, gfp_t 
> gfp_flags)
> +static void *vb2_vmalloc_alloc(void *alloc_ctx, unsigned long size, int 
> write,
> +  gfp_t gfp_flags)
>  {
> struct vb2_vmalloc_buf *buf;
>
> diff --git a/include/media/videobuf2-core.h b/include/media/videobuf2-core.h
> index 70ace7c..49e278b 100644
> --- a/include/media/videobuf2-core.h
> +++ b/include/media/videobuf2-core.h
> @@ -82,7 +82,8 @@ struct vb2_threadio_data;
>   *   unmap_dmabuf.
>   */
>  struct vb2_mem_ops {
> -   void*(*alloc)(void *alloc_ctx, unsigned long size, gfp_t 
> gfp_flags);
> +   void*(*alloc)(void *alloc_ctx, unsigned long size, int 
> write,
> + gfp_t gfp_flags);
> void(*put)(void *buf_priv);
> struct dma_buf *(*get_dmabuf)(void *buf_priv, unsigned long flags);
>
> diff --git a/include/media/videobuf2-dma-sg.h 
> b/include/media/videobuf2-dma-sg.h
> index 7b89852..14ce306 100644
> --- a/include/media/videobuf2-dma-sg.h
> +++ b/include/media/videobuf2-dma-sg.h
> @@ -21,6 +21,9 @@ static inline struct sg_table *vb2_dma_sg_plane_desc(
> return (struct sg_table *)vb2_plane_cookie(vb, plane_no);
>  }
>
> +void *vb2_dma_sg_init_ctx(struct device *dev);
> +void vb2_dma_sg_cleanup_ctx(void *alloc_ctx);
> +
>  extern const struct vb2_mem_ops vb2_dma_sg_memops;
>
>  #endif
> --
> 2.1.1
>



-- 
Best regards,
Pawel Osciak
--
To unsubscribe from this list: send the line "unsubscribe linux-media" in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: RFC: vb2: replace alloc_ctx by struct device * in vb2_queue

2014-09-21 Thread Pawel Osciak
Hi Hans,
I'm not very much against it, but I'm not sure how option 2 is
significantly simpler than option 1. It's just one cast away from
being the same, unless you have some more rework in mind, e.g. making
vb2 aware of devices somehow and skip driver's involvement for
example?
Thanks,
Pawel

On Sun, Sep 21, 2014 at 10:05 PM, Hans Verkuil  wrote:
> Hi Marek, Pawel,
>
> Currently for dma_config (and the dma_sg code that I posted before) drivers 
> have
> to allocate a alloc_ctx context, but in practice that just contains a device 
> pointer.
>
> Is there any reason why we can't just change in struct vb2_queue:
>
> void*alloc_ctx[VIDEO_MAX_PLANES];
>
> to:
>
> struct device   *alloc_ctx[VIDEO_MAX_PLANES];
>
> or possibly even just:
>
> struct device   *alloc_ctx;
>
> That simplifies the code quite a bit and I don't see and need for anything
> else. The last option would make it impossible to have different allocation
> contexts for different planes, but that might be something that Samsumg needs.
>
> Regards,
>
> Hans



-- 
Best regards,
Pawel Osciak
--
To unsubscribe from this list: send the line "unsubscribe linux-media" in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [RFCv2 PATCH 10/14] vb2: add 'new_cookies' flag

2014-09-14 Thread Pawel Osciak
Hi Hans,

On Fri, Sep 12, 2014 at 8:59 PM, Hans Verkuil  wrote:
> From: Hans Verkuil 
>
> This flag helps drivers that need to reprogram their DMA engine whenever
> a plane cookie (== DMA address or DMA scatter-gather list) changes.
>
> Otherwise they would have to reprogram the DMA engine for every frame.
>
> Note that it is not possible to do this in buf_init() since dma_map_sg has
> to be done first, which happens just before buf_prepare() in the prepare()
> memop. It is dma_map_sg that sets up the dma addresses that are needed to
> configure the DMA engine.

Perhaps I'm missing something, but couldn't we just dma_map_sg on
allocation/get in dma-sg and unmap on put?

-- 
Best regards,
Pawel Osciak
--
To unsubscribe from this list: send the line "unsubscribe linux-media" in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [RFC PATCH 06/12] vb2-dma-sg: add dmabuf import support

2014-09-14 Thread Pawel Osciak
 +311,7 @@ static void vb2_dma_sg_put_userptr(void *buf_priv)
>__func__, buf->num_pages);
> if (buf->vaddr)
> vm_unmap_ram(buf->vaddr, buf->num_pages);
> -   sg_free_table(&buf->sg_table);
> +   sg_free_table(buf->dma_sgt);
> while (--i >= 0) {
> if (buf->write)
> set_page_dirty_lock(buf->pages[i]);
> @@ -370,11 +384,104 @@ static int vb2_dma_sg_mmap(void *buf_priv, struct 
> vm_area_struct *vma)
> return 0;
>  }
>
> +/*/
> +/*   callbacks for DMABUF buffers*/
> +/*/
> +
> +static int vb2_dma_sg_map_dmabuf(void *mem_priv)
> +{
> +   struct vb2_dma_sg_buf *buf = mem_priv;
> +   struct sg_table *sgt;
> +
> +   if (WARN_ON(!buf->db_attach)) {
> +   pr_err("trying to pin a non attached buffer\n");

s/a non attached/an unattached/
In general, it would perhaps be nice to clean up/pretty up messages in
this file while we have the chance please...

> +   return -EINVAL;
> +   }
> +
> +   if (WARN_ON(buf->dma_sgt)) {
> +   pr_err("dmabuf buffer is already pinned\n");
> +   return 0;
> +   }
> +
> +   /* get the associated scatterlist for this buffer */

This comment doesn't really add value, and there is a few like this around.
I know they are copied from dma-contig, but I think we should remove them.
Others include "detach", "create attachment", etc.

-- 
Best regards,
Pawel Osciak
--
To unsubscribe from this list: send the line "unsubscribe linux-media" in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [RFCv2 PATCH 03/14] vb2-dma-sg: add prepare/finish memops

2014-09-13 Thread Pawel Osciak
Hi Hans,
Thank you for working on this.

On Fri, Sep 12, 2014 at 8:59 PM, Hans Verkuil  wrote:
> From: Hans Verkuil 
>
> This moves dma_(un)map_sg to the prepare/finish memops of videobuf2-dma-sg.c.

I agree with Laurent. dma_map and unmap should be done when we alloc
(or get) and put a buffer, while prepare and finish should only sync.

-- 
Best regards,
Pawel Osciak
--
To unsubscribe from this list: send the line "unsubscribe linux-media" in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [RFCv2 PATCH 02/14] vb2-dma-sg: add allocation context to dma-sg

2014-09-13 Thread Pawel Osciak
Hi Hans,
Thank you for working on this!

On Fri, Sep 12, 2014 at 8:59 PM, Hans Verkuil  wrote:
> From: Hans Verkuil 
>
> Require that dma-sg also uses an allocation context. This is in preparation
> for adding prepare/finish memops to sync the memory between DMA and CPU.
>
> Signed-off-by: Hans Verkuil 

[...]

> diff --git a/drivers/media/pci/cx23885/cx23885-core.c 
> b/drivers/media/pci/cx23885/cx23885-core.c
> index cb94366b..8a36fcd 100644
> --- a/drivers/media/pci/cx23885/cx23885-core.c
> +++ b/drivers/media/pci/cx23885/cx23885-core.c
> @@ -1997,9 +1997,14 @@ static int cx23885_initdev(struct pci_dev *pci_dev,
> if (!pci_dma_supported(pci_dev, 0x)) {
> printk("%s/0: Oops: no 32bit PCI DMA ???\n", dev->name);
> err = -EIO;
> -   goto fail_irq;
> +   goto fail_context;
> }
>
> +   dev->alloc_ctx = vb2_dma_sg_init_ctx(&pci_dev->dev);
> +   if (IS_ERR(dev->alloc_ctx)) {
> +   err = -ENOMEM;

err = PTR_ERR(dev->alloc_ctx) ?

> +   goto fail_context;
> +   }
> err = request_irq(pci_dev->irq, cx23885_irq,
>   IRQF_SHARED, dev->name, dev);
> if (err < 0) {
> @@ -2028,6 +2033,8 @@ static int cx23885_initdev(struct pci_dev *pci_dev,
> return 0;
>
>  fail_irq:
> +   vb2_dma_sg_cleanup_ctx(dev->alloc_ctx);
> +fail_context:
> cx23885_dev_unregister(dev);
>  fail_ctrl:
> v4l2_ctrl_handler_free(hdl);
> @@ -2053,6 +2060,7 @@ static void cx23885_finidev(struct pci_dev *pci_dev)
> free_irq(pci_dev->irq, dev);
>
> cx23885_dev_unregister(dev);
> +   vb2_dma_sg_cleanup_ctx(dev->alloc_ctx);
> v4l2_ctrl_handler_free(&dev->ctrl_handler);
> v4l2_device_unregister(v4l2_dev);
> kfree(dev);

[...]

> diff --git a/drivers/media/platform/marvell-ccic/mcam-core.h 
> b/drivers/media/platform/marvell-ccic/mcam-core.h
> index e0e628c..7b8c201 100644
> --- a/drivers/media/platform/marvell-ccic/mcam-core.h
> +++ b/drivers/media/platform/marvell-ccic/mcam-core.h
> @@ -176,6 +176,7 @@ struct mcam_camera {
> /* DMA buffers - DMA modes */
> struct mcam_vb_buffer *vb_bufs[MAX_DMA_BUFS];
> struct vb2_alloc_ctx *vb_alloc_ctx;
> +   struct vb2_alloc_ctx *vb_alloc_ctx_sg;

Should this be under #ifdef MCAM_MODE_DMA_SG?

>
> /* Mode-specific ops, set at open time */
> void (*dma_setup)(struct mcam_camera *cam);

[...]

> diff --git a/drivers/media/v4l2-core/videobuf2-vmalloc.c 
> b/drivers/media/v4l2-core/videobuf2-vmalloc.c
> index 313d977..d77e397 100644
> --- a/drivers/media/v4l2-core/videobuf2-vmalloc.c
> +++ b/drivers/media/v4l2-core/videobuf2-vmalloc.c
> @@ -35,7 +35,8 @@ struct vb2_vmalloc_buf {
>
>  static void vb2_vmalloc_put(void *buf_priv);
>
> -static void *vb2_vmalloc_alloc(void *alloc_ctx, unsigned long size, gfp_t 
> gfp_flags)
> +static void *vb2_vmalloc_alloc(void *alloc_ctx, unsigned long size, int 
> write,
> +  gfp_t gfp_flags)

I agree with Laurent that "write" is confusing, this could be a
direction flag, but the dma direction allows bidirectional, which we
would not be using. So I would personally prefer a binary flag or
enum. So perhaps we should keep this, only documenting it please.

-- 
Best regards,
Pawel Osciak
--
To unsubscribe from this list: send the line "unsubscribe linux-media" in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [PATCH v3 2/2] V4L: uvcvideo: Add support for pan/tilt speed controls

2014-09-03 Thread Pawel Osciak
On Thu, Sep 4, 2014 at 4:40 AM, Vincent Palatin  wrote:
> Map V4L2_CID_TILT_SPEED and V4L2_CID_PAN_SPEED to the standard UVC
> CT_PANTILT_RELATIVE_CONTROL terminal control request.
>
> Tested by plugging a Logitech ConferenceCam C3000e USB camera
> and controlling pan/tilt from the userspace using the VIDIOC_S_CTRL ioctl.
> Verified that it can pan and tilt at the same time in both directions.
>
> Signed-off-by: Vincent Palatin 
>
> Change-Id: I7b70b228e5c0126683f5f0be34ffd2807f5783dc

Sorry, forgot to mention this previously, please remove gerrit ids
from the patches.
Thanks,
P.

> ---
> Changes from v1/v2:
> - rebased
>
>  drivers/media/usb/uvc/uvc_ctrl.c | 58 
> +---
>  1 file changed, 55 insertions(+), 3 deletions(-)
>
> diff --git a/drivers/media/usb/uvc/uvc_ctrl.c 
> b/drivers/media/usb/uvc/uvc_ctrl.c
> index 0eb82106..d703cb0 100644
> --- a/drivers/media/usb/uvc/uvc_ctrl.c
> +++ b/drivers/media/usb/uvc/uvc_ctrl.c
> @@ -309,9 +309,8 @@ static struct uvc_control_info uvc_ctrls[] = {
> .selector   = UVC_CT_PANTILT_RELATIVE_CONTROL,
> .index  = 12,
> .size   = 4,
> -   .flags  = UVC_CTRL_FLAG_SET_CUR | 
> UVC_CTRL_FLAG_GET_MIN
> -   | UVC_CTRL_FLAG_GET_MAX | 
> UVC_CTRL_FLAG_GET_RES
> -   | UVC_CTRL_FLAG_GET_DEF
> +   .flags  = UVC_CTRL_FLAG_SET_CUR
> +   | UVC_CTRL_FLAG_GET_RANGE
> | UVC_CTRL_FLAG_AUTO_UPDATE,
> },
> {
> @@ -391,6 +390,35 @@ static void uvc_ctrl_set_zoom(struct uvc_control_mapping 
> *mapping,
> data[2] = min((int)abs(value), 0xff);
>  }
>
> +static __s32 uvc_ctrl_get_rel_speed(struct uvc_control_mapping *mapping,
> +   __u8 query, const __u8 *data)
> +{
> +   int first = mapping->offset / 8;
> +   __s8 rel = (__s8)data[first];
> +
> +   switch (query) {
> +   case UVC_GET_CUR:
> +   return (rel == 0) ? 0 : (rel > 0 ? data[first+1]
> +: -data[first+1]);
> +   case UVC_GET_MIN:
> +   return -data[first+1];
> +   case UVC_GET_MAX:
> +   case UVC_GET_RES:
> +   case UVC_GET_DEF:
> +   default:
> +   return data[first+1];
> +   }
> +}
> +
> +static void uvc_ctrl_set_rel_speed(struct uvc_control_mapping *mapping,
> +   __s32 value, __u8 *data)
> +{
> +   int first = mapping->offset / 8;
> +
> +   data[first] = value == 0 ? 0 : (value > 0) ? 1 : 0xff;
> +   data[first+1] = min_t(int, abs(value), 0xff);
> +}
> +
>  static struct uvc_control_mapping uvc_ctrl_mappings[] = {
> {
> .id = V4L2_CID_BRIGHTNESS,
> @@ -677,6 +705,30 @@ static struct uvc_control_mapping uvc_ctrl_mappings[] = {
> .data_type  = UVC_CTRL_DATA_TYPE_SIGNED,
> },
> {
> +   .id = V4L2_CID_PAN_SPEED,
> +   .name   = "Pan (Speed)",
> +   .entity = UVC_GUID_UVC_CAMERA,
> +   .selector   = UVC_CT_PANTILT_RELATIVE_CONTROL,
> +   .size   = 16,
> +   .offset = 0,
> +   .v4l2_type  = V4L2_CTRL_TYPE_INTEGER,
> +   .data_type  = UVC_CTRL_DATA_TYPE_SIGNED,
> +   .get= uvc_ctrl_get_rel_speed,
> +   .set= uvc_ctrl_set_rel_speed,
> +   },
> +   {
> +   .id = V4L2_CID_TILT_SPEED,
> +   .name   = "Tilt (Speed)",
> +   .entity = UVC_GUID_UVC_CAMERA,
> +   .selector   = UVC_CT_PANTILT_RELATIVE_CONTROL,
> +   .size   = 16,
> +   .offset = 16,
> +   .v4l2_type  = V4L2_CTRL_TYPE_INTEGER,
> +   .data_type  = UVC_CTRL_DATA_TYPE_SIGNED,
> +   .get= uvc_ctrl_get_rel_speed,
> +   .set= uvc_ctrl_set_rel_speed,
> +   },
> +   {
> .id = V4L2_CID_PRIVACY,
> .name   = "Privacy",
> .entity = UVC_GUID_UVC_CAMERA,
> --
> 2.1.0.rc2.206.gedb03e5
>
--
To unsubscribe from this list: send the line "unsubscribe linux-media" in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [PATCH 2/2] V4L: uvcvideo: Add support for pan/tilt speed controls

2014-09-02 Thread Pawel Osciak
On Wed, Jul 9, 2014 at 8:49 AM, Vincent Palatin  wrote:
> Map V4L2_CID_TILT_SPEED and V4L2_CID_PAN_SPEED to the standard UVC
> CT_PANTILT_RELATIVE_CONTROL terminal control request.
>
> Tested by plugging a Logitech ConferenceCam C3000e USB camera
> and controlling pan/tilt from the userspace using the VIDIOC_S_CTRL ioctl.
> Verified that it can pan and tilt at the same time in both directions.
>
> Signed-off-by: Vincent Palatin 

Reviewed-by: Pawel Osciak 

> Change-Id: I7b70b228e5c0126683f5f0be34ffd2807f5783dc
> ---
>  drivers/media/usb/uvc/uvc_ctrl.c | 58 
> +---
>  1 file changed, 55 insertions(+), 3 deletions(-)
>
> diff --git a/drivers/media/usb/uvc/uvc_ctrl.c 
> b/drivers/media/usb/uvc/uvc_ctrl.c
> index 0eb82106..d703cb0 100644
> --- a/drivers/media/usb/uvc/uvc_ctrl.c
> +++ b/drivers/media/usb/uvc/uvc_ctrl.c
> @@ -309,9 +309,8 @@ static struct uvc_control_info uvc_ctrls[] = {
> .selector   = UVC_CT_PANTILT_RELATIVE_CONTROL,
> .index  = 12,
> .size   = 4,
> -   .flags  = UVC_CTRL_FLAG_SET_CUR | 
> UVC_CTRL_FLAG_GET_MIN
> -   | UVC_CTRL_FLAG_GET_MAX | 
> UVC_CTRL_FLAG_GET_RES
> -   | UVC_CTRL_FLAG_GET_DEF
> +   .flags  = UVC_CTRL_FLAG_SET_CUR
> +   | UVC_CTRL_FLAG_GET_RANGE
> | UVC_CTRL_FLAG_AUTO_UPDATE,
> },
> {
> @@ -391,6 +390,35 @@ static void uvc_ctrl_set_zoom(struct uvc_control_mapping 
> *mapping,
> data[2] = min((int)abs(value), 0xff);
>  }
>
> +static __s32 uvc_ctrl_get_rel_speed(struct uvc_control_mapping *mapping,
> +   __u8 query, const __u8 *data)
> +{
> +   int first = mapping->offset / 8;
> +   __s8 rel = (__s8)data[first];
> +
> +   switch (query) {
> +   case UVC_GET_CUR:
> +   return (rel == 0) ? 0 : (rel > 0 ? data[first+1]
> +: -data[first+1]);
> +   case UVC_GET_MIN:
> +   return -data[first+1];
> +   case UVC_GET_MAX:
> +   case UVC_GET_RES:
> +   case UVC_GET_DEF:
> +   default:
> +   return data[first+1];
> +   }
> +}
> +
> +static void uvc_ctrl_set_rel_speed(struct uvc_control_mapping *mapping,
> +   __s32 value, __u8 *data)
> +{
> +   int first = mapping->offset / 8;
> +
> +   data[first] = value == 0 ? 0 : (value > 0) ? 1 : 0xff;
> +   data[first+1] = min_t(int, abs(value), 0xff);
> +}
> +
>  static struct uvc_control_mapping uvc_ctrl_mappings[] = {
> {
> .id = V4L2_CID_BRIGHTNESS,
> @@ -677,6 +705,30 @@ static struct uvc_control_mapping uvc_ctrl_mappings[] = {
> .data_type  = UVC_CTRL_DATA_TYPE_SIGNED,
> },
> {
> +   .id = V4L2_CID_PAN_SPEED,
> +   .name   = "Pan (Speed)",
> +   .entity = UVC_GUID_UVC_CAMERA,
> +   .selector   = UVC_CT_PANTILT_RELATIVE_CONTROL,
> +   .size   = 16,
> +   .offset = 0,
> +   .v4l2_type  = V4L2_CTRL_TYPE_INTEGER,
> +   .data_type  = UVC_CTRL_DATA_TYPE_SIGNED,
> +   .get= uvc_ctrl_get_rel_speed,
> +   .set= uvc_ctrl_set_rel_speed,
> +   },
> +   {
> +   .id = V4L2_CID_TILT_SPEED,
> +   .name   = "Tilt (Speed)",
> +   .entity = UVC_GUID_UVC_CAMERA,
> +   .selector   = UVC_CT_PANTILT_RELATIVE_CONTROL,
> +   .size   = 16,
> +   .offset = 16,
> +   .v4l2_type  = V4L2_CTRL_TYPE_INTEGER,
> +   .data_type  = UVC_CTRL_DATA_TYPE_SIGNED,
> +   .get= uvc_ctrl_get_rel_speed,
> +   .set= uvc_ctrl_set_rel_speed,
> +   },
> +   {
> .id = V4L2_CID_PRIVACY,
> .name   = "Privacy",
> .entity = UVC_GUID_UVC_CAMERA,
> --
> 2.0.0.526.g5318336
>
--
To unsubscribe from this list: send the line "unsubscribe linux-media" in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [PATCH v2 1/2] [media] V4L: Add camera pan/tilt speed controls

2014-09-02 Thread Pawel Osciak
On Sat, Aug 16, 2014 at 4:08 AM, Vincent Palatin  wrote:
>
> The V4L2_CID_PAN_SPEED and V4L2_CID_TILT_SPEED controls allow to move the
> camera by setting its rotation speed around its axis.
>
> Signed-off-by: Vincent Palatin 

Reviewed-by: Pawel Osciak 

>
> ---
> Changes from v1:
> - update the documentation wording according to Pawel suggestion.
>
>  Documentation/DocBook/media/v4l/compat.xml   | 10 ++
>  Documentation/DocBook/media/v4l/controls.xml | 21 +
>  drivers/media/v4l2-core/v4l2-ctrls.c |  2 ++
>  include/uapi/linux/v4l2-controls.h   |  2 ++
>  4 files changed, 35 insertions(+)
>
> diff --git a/Documentation/DocBook/media/v4l/compat.xml 
> b/Documentation/DocBook/media/v4l/compat.xml
> index eee6f0f..21910e9 100644
> --- a/Documentation/DocBook/media/v4l/compat.xml
> +++ b/Documentation/DocBook/media/v4l/compat.xml
> @@ -2545,6 +2545,16 @@ fields changed from _s32 to _u32.
>
>  
>
> +
> +  V4L2 in Linux 3.17

This will need a bump.

>
> +  
> +   
> + Added V4L2_CID_PAN_SPEED and
> + V4L2_CID_TILT_SPEED camera controls.
> +   
> +  
> +
> +
>  
>Relation of V4L2 to other Linux multimedia APIs
>
> diff --git a/Documentation/DocBook/media/v4l/controls.xml 
> b/Documentation/DocBook/media/v4l/controls.xml
> index 47198ee..be88e64 100644
> --- a/Documentation/DocBook/media/v4l/controls.xml
> +++ b/Documentation/DocBook/media/v4l/controls.xml
> @@ -3914,6 +3914,27 @@ by exposure, white balance or focus controls.
>   
>   
>
> + 
> +spanname="id">V4L2_CID_PAN_SPEED 
> +   integer
> + This control turns the
> +camera horizontally at the specific speed. The unit is undefined. A
> +positive value moves the camera to the right (clockwise when viewed
> +from above), a negative value to the left. A value of zero stops the motion
> +if one is in progress and has no effect otherwise.
> + 
> + 
> +
> + 
> +spanname="id">V4L2_CID_TILT_SPEED 
> +   integer
> + This control turns the
> +camera vertically at the specified speed. The unit is undefined. A
> +positive value moves the camera up, a negative value down. A value of zero
> +stops the motion if one is in progress and has no effect otherwise.
> + 
> + 
> +
> 
>
>  
> diff --git a/drivers/media/v4l2-core/v4l2-ctrls.c 
> b/drivers/media/v4l2-core/v4l2-ctrls.c
> index 55c6832..57ddaf4 100644
> --- a/drivers/media/v4l2-core/v4l2-ctrls.c
> +++ b/drivers/media/v4l2-core/v4l2-ctrls.c
> @@ -787,6 +787,8 @@ const char *v4l2_ctrl_get_name(u32 id)
> case V4L2_CID_AUTO_FOCUS_STOP:  return "Auto Focus, Stop";
> case V4L2_CID_AUTO_FOCUS_STATUS:return "Auto Focus, Status";
> case V4L2_CID_AUTO_FOCUS_RANGE: return "Auto Focus, Range";
> +   case V4L2_CID_PAN_SPEED:return "Pan, Speed";
> +   case V4L2_CID_TILT_SPEED:   return "Tilt, Speed";
>
> /* FM Radio Modulator control */
> /* Keep the order of the 'case's the same as in videodev2.h! */
> diff --git a/include/uapi/linux/v4l2-controls.h 
> b/include/uapi/linux/v4l2-controls.h
> index 2ac5597..5576044 100644
> --- a/include/uapi/linux/v4l2-controls.h
> +++ b/include/uapi/linux/v4l2-controls.h
> @@ -745,6 +745,8 @@ enum v4l2_auto_focus_range {
> V4L2_AUTO_FOCUS_RANGE_INFINITY  = 3,
>  };
>
> +#define V4L2_CID_PAN_SPEED 
> (V4L2_CID_CAMERA_CLASS_BASE+32)
> +#define V4L2_CID_TILT_SPEED
> (V4L2_CID_CAMERA_CLASS_BASE+33)
>
>  /* FM Modulator class control IDs */
>
> --
> 2.1.0.rc2.206.gedb03e5
>
--
To unsubscribe from this list: send the line "unsubscribe linux-media" in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [ANNOUNCE] Linux Kernel Media mini-summit on Oct, 16-17 in Düsseldorf, Germany

2014-08-24 Thread Pawel Osciak
Hi Philipp,

On Fri, Aug 22, 2014 at 10:09 PM, Philipp Zabel  wrote:
> - Helping userspace to use mem2mem devices; clarification of
>   encoder/decoder handling, clarification of format/size setting
>   in case of dependencies between input and output formats,
>   possibly broad categorisation of mem2mem devices (encoder,
>   decoder, scaler, rotator, csc/filter, ...)

I'm planning a session on codec API, would like to specify it in
better detail and clear up ambiguities. If you'd have a list of issues
that should be clarified, it would be very useful to add to
discussion.

-- 
Thanks,
Pawel
--
To unsubscribe from this list: send the line "unsubscribe linux-media" in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [PATCH] videobuf2-core: modify the num of users

2014-08-14 Thread Pawel Osciak
On Thu, Aug 14, 2014 at 4:11 PM, panpan liu  wrote:
> If num_users returns 1 or more than 1, that means we are not the
> only user of the plane's memory.
>
> Signed-off-by: panpan liu 

NACK.

Please read the function documentation and how it is used. If the
number of users is 1, we are the only user and should be able to free
the queue. This will make us unable to do so.

> ---
>  drivers/media/v4l2-core/videobuf2-core.c |2 +-
>  1 file changed, 1 insertion(+), 1 deletion(-)
>
> diff --git a/drivers/media/v4l2-core/videobuf2-core.c 
> b/drivers/media/v4l2-core/videobuf2-core.c
> index c359006..d3a4b8f 100644
> --- a/drivers/media/v4l2-core/videobuf2-core.c
> +++ b/drivers/media/v4l2-core/videobuf2-core.c
> @@ -625,7 +625,7 @@ static bool __buffer_in_use(struct vb2_queue *q, struct 
> vb2_buffer *vb)
>  * case anyway. If num_users() returns more than 1,
>  * we are not the only user of the plane's memory.
>  */
> -   if (mem_priv && call_memop(vb, num_users, mem_priv) > 1)
> +   if (mem_priv && call_memop(vb, num_users, mem_priv) >= 1)
>         return true;
> }
> return false;
> --
> 1.7.9.5

-- 
Thanks,
Pawel Osciak
--
To unsubscribe from this list: send the line "unsubscribe linux-media" in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [PATCH 1/2] [media] V4L: Add camera pan/tilt speed controls

2014-08-06 Thread Pawel Osciak
On Thu, Aug 7, 2014 at 12:10 AM, Vincent Palatin  wrote:
>
> On Sun, Aug 3, 2014 at 10:52 PM, Pawel Osciak  wrote:
> > This looks good to me in general (with one comment below). I don't think we
> > can easily implement current V4L2 pan and tilt controls that are for
> > movement by a specified amount in terms of UVC pan/tilt speed controls,
> > which only let us set speed and direction...
> >
> > On Wed, Jul 9, 2014 at 8:49 AM, Vincent Palatin 
> > wrote:
> >>
> >> The V4L2_CID_PAN_SPEED and V4L2_CID_TILT_SPEED controls allow to move the
> >> camera by setting its rotation speed around its axis.
> >>
> >> Signed-off-by: Vincent Palatin 
> >>
> >> ---
> >>  Documentation/DocBook/media/v4l/compat.xml   | 10 ++
> >>  Documentation/DocBook/media/v4l/controls.xml | 21 +
> >>  drivers/media/v4l2-core/v4l2-ctrls.c |  2 ++
> >>  include/uapi/linux/v4l2-controls.h   |  2 ++
> >>  4 files changed, 35 insertions(+)
> >>
> >> diff --git a/Documentation/DocBook/media/v4l/compat.xml
> >> b/Documentation/DocBook/media/v4l/compat.xml
> >> index eee6f0f..21910e9 100644
> >> --- a/Documentation/DocBook/media/v4l/compat.xml
> >> +++ b/Documentation/DocBook/media/v4l/compat.xml
> >> @@ -2545,6 +2545,16 @@ fields changed from _s32 to _u32.
> >>
> >>  
> >>
> >> +
> >> +  V4L2 in Linux 3.17
> >> +  
> >> +   
> >> + Added V4L2_CID_PAN_SPEED and
> >> + V4L2_CID_TILT_SPEED camera controls.
> >> +   
> >> +  
> >> +
> >> +
> >>  
> >>Relation of V4L2 to other Linux multimedia APIs
> >>
> >> diff --git a/Documentation/DocBook/media/v4l/controls.xml
> >> b/Documentation/DocBook/media/v4l/controls.xml
> >> index 47198ee..cdf97f0 100644
> >> --- a/Documentation/DocBook/media/v4l/controls.xml
> >> +++ b/Documentation/DocBook/media/v4l/controls.xml
> >> @@ -3914,6 +3914,27 @@ by exposure, white balance or focus
> >> controls.
> >>   
> >>   
> >>
> >> + 
> >> +>> spanname="id">V4L2_CID_PAN_SPEED 
> >> +   integer
> >> + This control turns the
> >> +camera horizontally at the specific speed. The unit is undefined. A
> >> +positive value moves the camera to the right (clockwise when viewed
> >> +from above), a negative value to the left. A value of zero does not
> >> +cause or stop the motion.
> >
> >
> > How do we stop/start?
>
> As mentioned in the last sentence of the paragraph above, setting 0
> stops the movement.
> setting non-zero value starts it if needed.
>

The sentence says "A value of zero does *not* cause or stop the
motion.". Perhaps "not" is a typo then?
--
To unsubscribe from this list: send the line "unsubscribe linux-media" in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [PATCH for v3.17] videobuf2-core: add comments before the WARN_ON

2014-08-03 Thread Pawel Osciak
On Mon, Aug 4, 2014 at 2:36 PM, Hans Verkuil  wrote:
> Recently WARN_ON() calls have been added to warn if the driver is not
> properly returning buffers to vb2 in start_streaming (if it fails) or
> stop_streaming(). Add comments before those WARN_ON calls that refer
> to the videobuf2-core.h header that explains what drivers are supposed
> to do in these situations. That should help point developers in the
> right direction if they see these warnings.
>
> Signed-off-by: Hans Verkuil 

Acked-by: Pawel Osciak 

> ---
>  drivers/media/v4l2-core/videobuf2-core.c | 12 
>  1 file changed, 12 insertions(+)
>
> diff --git a/drivers/media/v4l2-core/videobuf2-core.c 
> b/drivers/media/v4l2-core/videobuf2-core.c
> index c359006..d3f2a22 100644
> --- a/drivers/media/v4l2-core/videobuf2-core.c
> +++ b/drivers/media/v4l2-core/videobuf2-core.c
> @@ -1762,6 +1762,12 @@ static int vb2_start_streaming(struct vb2_queue *q)
> q->start_streaming_called = 0;
>
> dprintk(1, "driver refused to start streaming\n");
> +   /*
> +* If you see this warning, then the driver isn't cleaning up properly
> +* after a failed start_streaming(). See the start_streaming()
> +* documentation in videobuf2-core.h for more information how buffers
> +* should be returned to vb2 in start_streaming().
> +*/
> if (WARN_ON(atomic_read(&q->owned_by_drv_count))) {
> unsigned i;
>
> @@ -2123,6 +2129,12 @@ static void __vb2_queue_cancel(struct vb2_queue *q)
> if (q->start_streaming_called)
> call_void_qop(q, stop_streaming, q);
>
> +   /*
> +* If you see this warning, then the driver isn't cleaning up properly
> +* in stop_streaming(). See the stop_streaming() documentation in
> +* videobuf2-core.h for more information how buffers should be 
> returned
> +* to vb2 in stop_streaming().
> +*/
> if (WARN_ON(atomic_read(&q->owned_by_drv_count))) {
>     for (i = 0; i < q->num_buffers; ++i)
> if (q->bufs[i]->state == VB2_BUF_STATE_ACTIVE)
> --
> 2.0.1
>



-- 
Best regards,
Pawel Osciak
--
To unsubscribe from this list: send the line "unsubscribe linux-media" in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [PATCH/RFC v2 2/2] v4l: vb2: Add fatal error condition flag

2014-06-05 Thread Pawel Osciak
Hi Laurent,
Thanks for the patch. Did you test this to work in fileio mode? Looks
like it should, but would like to make sure.
Thanks,
Pawel

On Thu, Jun 5, 2014 at 9:23 PM, Laurent Pinchart
 wrote:
> When a fatal error occurs that render the device unusable, the only
> options for a driver to signal the error condition to userspace is to
> set the V4L2_BUF_FLAG_ERROR flag when dequeuing buffers and to return an
> error from the buffer prepare handler when queuing buffers.
>
> The buffer error flag indicates a transient error and can't be used by
> applications to detect fatal errors. Returning an error from vb2_qbuf()
> is thus the only real indication that a fatal error occurred. However,
> this is difficult to handle for multithreaded applications that requeue
> buffers from a thread other than the control thread. In particular the
> poll() call in the control thread will not notify userspace of the
> error.
>
> This patch adds an explicit mechanism to report fatal errors to
> userspace. Applications can call the vb2_queue_error() function to
> signal a fatal error. From this moment on, buffer preparation will
> return -EIO to userspace, and vb2_poll() will set the POLLERR flag and
> return immediately. The error flag is cleared when cancelling the queue,
> either at stream off time (through vb2_streamoff) or when releasing the
> queue with vb2_queue_release().
>
> Signed-off-by: Laurent Pinchart 
> ---
>  drivers/media/v4l2-core/videobuf2-core.c | 40 
> +---
>  include/media/videobuf2-core.h   |  3 +++
>  2 files changed, 40 insertions(+), 3 deletions(-)
>
> diff --git a/drivers/media/v4l2-core/videobuf2-core.c 
> b/drivers/media/v4l2-core/videobuf2-core.c
> index fd428e0..c7aa07d 100644
> --- a/drivers/media/v4l2-core/videobuf2-core.c
> +++ b/drivers/media/v4l2-core/videobuf2-core.c
> @@ -1582,6 +1582,11 @@ static int __buf_prepare(struct vb2_buffer *vb, const 
> struct v4l2_buffer *b)
> return -EINVAL;
> }
>
> +   if (q->error) {
> +   dprintk(1, "fatal error occurred on queue\n");
> +   return -EIO;
> +   }
> +
> vb->state = VB2_BUF_STATE_PREPARING;
> vb->v4l2_buf.timestamp.tv_sec = 0;
> vb->v4l2_buf.timestamp.tv_usec = 0;
> @@ -1877,6 +1882,11 @@ static int __vb2_wait_for_done_vb(struct vb2_queue *q, 
> int nonblocking)
> return -EINVAL;
> }
>
> +   if (q->error) {
> +   dprintk(1, "Queue in error state, will not wait for 
> buffers\n");
> +   return -EIO;
> +   }
> +
> if (!list_empty(&q->done_list)) {
> /*
>  * Found a buffer that we were waiting for.
> @@ -1902,7 +1912,8 @@ static int __vb2_wait_for_done_vb(struct vb2_queue *q, 
> int nonblocking)
>  */
> dprintk(3, "will sleep waiting for buffers\n");
> ret = wait_event_interruptible(q->done_wq,
> -   !list_empty(&q->done_list) || !q->streaming);
> +   !list_empty(&q->done_list) || !q->streaming ||
> +   q->error);
>
> /*
>  * We need to reevaluate both conditions again after 
> reacquiring
> @@ -2099,6 +2110,7 @@ static void __vb2_queue_cancel(struct vb2_queue *q)
> q->streaming = 0;
> q->start_streaming_called = 0;
> q->queued_count = 0;
> +   q->error = 0;
>
> /*
>  * Remove all buffers from videobuf's list...
> @@ -2176,6 +2188,27 @@ static int vb2_internal_streamon(struct vb2_queue *q, 
> enum v4l2_buf_type type)
>  }
>
>  /**
> + * vb2_queue_error() - signal a fatal error on the queue
> + * @q: videobuf2 queue
> + *
> + * Flag that a fatal unrecoverable error has occurred and wake up all 
> processes
> + * waiting on the queue. Polling will now set POLLERR and queuing and 
> dequeuing
> + * buffers will return -EIO.
> + *
> + * The error flag will be cleared when cancelling the queue, either from
> + * vb2_streamoff or vb2_queue_release. Drivers should thus not call this
> + * function before starting the stream, otherwise the error flag will remain 
> set
> + * until the queue is released when closing the device node.
> + */
> +void vb2_queue_error(struct vb2_queue *q)
> +{
> +   q->error = 1;
> +
> +   wake_up_all(&q->done_wq);
> +}
> +EXPORT_SYMBOL_GPL(vb2_queue_error);
> +
> +/**
>   * vb2_streamon - start streaming
>   * @q: videobuf2 queue
>   * @type:  type argument passed from userspace to vidioc_streamon handler
> @@ -2533,9 +2566,10 @@ unsigned int vb2_poll(struct vb2_queue *q, struct file 
> *file, poll_table *wait)
> }
>
> /*
> -* There is nothing to wait for if the queue isn't streaming.
> +* There is nothing to wait for if the queue isn't streaming or if the
> +* error flag i

Re: [PATCH/RFC v2 1/2] v4l: vb2: Don't return POLLERR during transient buffer underruns

2014-06-05 Thread Pawel Osciak
On Thu, Jun 5, 2014 at 9:23 PM, Laurent Pinchart
 wrote:
> The V4L2 specification states that
>
> "When the application did not call VIDIOC_QBUF or VIDIOC_STREAMON yet
> the poll() function succeeds, but sets the POLLERR flag in the revents
> field."
>
> The vb2_poll() function sets POLLERR when the queued buffers list is
> empty, regardless of whether this is caused by the stream not being
> active yet, or by a transient buffer underrun.
>
> Bring the implementation in line with the specification by returning
> POLLERR only when the queue is not streaming. Buffer underruns during
> streaming are not treated specially anymore and just result in poll()
> blocking until the next event.
>
> Signed-off-by: Laurent Pinchart 
> Acked-by: Hans Verkuil 

Acked-by: Pawel Osciak 

> ---
>  drivers/media/v4l2-core/videobuf2-core.c | 4 ++--
>  1 file changed, 2 insertions(+), 2 deletions(-)
>
> diff --git a/drivers/media/v4l2-core/videobuf2-core.c 
> b/drivers/media/v4l2-core/videobuf2-core.c
> index 349e659..fd428e0 100644
> --- a/drivers/media/v4l2-core/videobuf2-core.c
> +++ b/drivers/media/v4l2-core/videobuf2-core.c
> @@ -2533,9 +2533,9 @@ unsigned int vb2_poll(struct vb2_queue *q, struct file 
> *file, poll_table *wait)
> }
>
> /*
> -* There is nothing to wait for if no buffers have already been 
> queued.
> +* There is nothing to wait for if the queue isn't streaming.
>  */
> -   if (list_empty(&q->queued_list))
> +   if (!vb2_is_streaming(q))
> return res | POLLERR;
>
> if (list_empty(&q->done_list))
> --
> 1.8.5.5
>
--
To unsubscribe from this list: send the line "unsubscribe linux-media" in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [PATCH 2/2] v4l: s5p-mfc: Limit enum_fmt to output formats of current version

2014-05-19 Thread Pawel Osciak
Hi Kamil,
I like the solution as well. Two suggestions to consider below.

On Fri, May 16, 2014 at 9:03 PM, Kamil Debski  wrote:
> MFC versions support a different set of formats, this specially applies
> to the raw YUV formats. This patch changes enum_fmt, so that it only
> reports formats that are supported by the used MFC version.
>
> Signed-off-by: Kamil Debski 
> ---

> diff --git a/drivers/media/platform/s5p-mfc/s5p_mfc_common.h 
> b/drivers/media/platform/s5p-mfc/s5p_mfc_common.h
> index 9370c34..d5efb10 100644
> --- a/drivers/media/platform/s5p-mfc/s5p_mfc_common.h
> +++ b/drivers/media/platform/s5p-mfc/s5p_mfc_common.h
> @@ -223,6 +223,7 @@ struct s5p_mfc_buf_align {
>  struct s5p_mfc_variant {
> unsigned int version;
> unsigned int port_num;
> +   u32 version_bit;
> struct s5p_mfc_buf_size *buf_size;
> struct s5p_mfc_buf_align *buf_align;
> char*fw_name;
> @@ -666,6 +667,7 @@ struct s5p_mfc_fmt {
> u32 codec_mode;
> enum s5p_mfc_fmt_type type;
> u32 num_planes;
> +   u32 versions;
>  };
>
>  /**
> @@ -705,4 +707,9 @@ void set_work_bit_irqsave(struct s5p_mfc_ctx *ctx);
>  #define IS_MFCV6_PLUS(dev) (dev->variant->version >= 0x60 ? 1 : 0)
>  #define IS_MFCV7_PLUS(dev) (dev->variant->version >= 0x70 ? 1 : 0)
>
> +#define MFC_V5 BIT(0)
> +#define MFC_V6 BIT(1)
> +#define MFC_V7 BIT(2)

These may be confusing. I'd suggest at least suffixing those macros with _BIT.
Or better yet, please make this into an enum and also make
variant->versions of size BITS_TO_LONGS() with max enum value.

>  /* Get format */
> @@ -384,11 +402,9 @@ static int vidioc_try_fmt(struct file *file, void *priv, 
> struct v4l2_format *f)
> mfc_err("Unknown codec\n");
> return -EINVAL;
> }
> -   if (!IS_MFCV6_PLUS(dev)) {
> -   if (fmt->fourcc == V4L2_PIX_FMT_VP8) {
> -   mfc_err("Not supported format.\n");
> -   return -EINVAL;
> -   }
> +   if ((dev->variant->version_bit & fmt->versions) == 0) {
> +   mfc_err("Unsupported format by this MFC version.\n");
> +   return -EINVAL;

What do you think of moving this check to find_format()? You wouldn't
have to duplicate it across enum_fmt and try_fmt then...
--
To unsubscribe from this list: send the line "unsubscribe linux-media" in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [PATCH] [media] s5p-mfc: Add a control for IVF format for VP8 encoder

2014-05-14 Thread Pawel Osciak
On Wed, May 14, 2014 at 11:12 PM, Kamil Debski  wrote:
> Hi Pawel, Hans,
>
> I think we talked some time ago on IRC about this patch.
> If I remember correctly, the conclusion was that it would be better to use
> a specific pixel formats for this kind of out codec output.
>
> Akin to:
> V4L2_PIX_FMT_H264   'H264'  H264 video elementary stream
> with start codes.
> V4L2_PIX_FMT_H264_NO_SC 'AVC1'  H264 video elementary stream without
> start codes.
>
> Could you confirm this?

Hi Kamil.
Yes, that was the conclusion.
Pawel

>
> Best wishes,
> --
> Kamil Debski
> Samsung R&D Institute Poland
>
>
>> -Original Message-
>> From: Arun Kumar K [mailto:arunkk.sams...@gmail.com] On Behalf Of Arun
>> Kumar K
>> Sent: Thursday, March 06, 2014 7:04 AM
>> To: linux-media@vger.kernel.org; linux-samsung-...@vger.kernel.org
>> Cc: k.deb...@samsung.com; s.nawro...@samsung.com; posc...@chromium.org;
>> arunkk.sams...@gmail.com
>> Subject: [PATCH] [media] s5p-mfc: Add a control for IVF format for VP8
>> encoder
>>
>> From: Pawel Osciak 
>>
>> Add a control to enable/disable IVF output stream format for VP8 encode.
>> Set the IVF format output to disabled as default.
>>
>> Signed-off-by: Pawel Osciak 
>> Signed-off-by: Arun Kumar K 
>> ---
>>  Documentation/DocBook/media/v4l/controls.xml|8 
>>  drivers/media/platform/s5p-mfc/s5p_mfc_common.h |1 +
>>  drivers/media/platform/s5p-mfc/s5p_mfc_enc.c|   11 +++
>>  drivers/media/platform/s5p-mfc/s5p_mfc_opr_v6.c |2 ++
>>  drivers/media/v4l2-core/v4l2-ctrls.c|1 +
>>  include/uapi/linux/v4l2-controls.h  |1 +
>>  6 files changed, 24 insertions(+)
>>
>> diff --git a/Documentation/DocBook/media/v4l/controls.xml
>> b/Documentation/DocBook/media/v4l/controls.xml
>> index 0e1770c..07fb64a 100644
>> --- a/Documentation/DocBook/media/v4l/controls.xml
>> +++ b/Documentation/DocBook/media/v4l/controls.xml
>> @@ -3222,6 +3222,14 @@ V4L2_CID_MPEG_VIDEO_VPX_GOLDEN_FRAME_REF_PERIOD
>> as a golden frame.  Acceptable values are 0, 1, 2 and 3
>> corresponding to encoder profiles 0, 1, 2 and 3.
>> 
>>
>> +   
>> +   
>> + > spanname="id">V4L2_CID_MPEG_VIDEO_VPX_IVF_FORMAT&n
>> bsp;
>> + boolean
>> +   
>> +   Outputs the VP8 encoded stream
>> in IVF file format.
>> +   
>> +
>>
>>  
>>
>> diff --git a/drivers/media/platform/s5p-mfc/s5p_mfc_common.h
>> b/drivers/media/platform/s5p-mfc/s5p_mfc_common.h
>> index 5c28cc3..4d17df9 100644
>> --- a/drivers/media/platform/s5p-mfc/s5p_mfc_common.h
>> +++ b/drivers/media/platform/s5p-mfc/s5p_mfc_common.h
>> @@ -418,6 +418,7 @@ struct s5p_mfc_vp8_enc_params {
>>   u8 rc_frame_qp;
>>   u8 rc_p_frame_qp;
>>   u8 profile;
>> + bool ivf;
>>  };
>>
>>  /**
>> diff --git a/drivers/media/platform/s5p-mfc/s5p_mfc_enc.c
>> b/drivers/media/platform/s5p-mfc/s5p_mfc_enc.c
>> index df83cd1..a67913e 100644
>> --- a/drivers/media/platform/s5p-mfc/s5p_mfc_enc.c
>> +++ b/drivers/media/platform/s5p-mfc/s5p_mfc_enc.c
>> @@ -676,6 +676,14 @@ static struct mfc_control controls[] = {
>>   .step = 1,
>>   .default_value = 0,
>>   },
>> + {
>> + .id = V4L2_CID_MPEG_VIDEO_VPX_IVF_FORMAT,
>> + .type = V4L2_CTRL_TYPE_BOOLEAN,
>> + .minimum = 0,
>> + .maximum = 1,
>> + .step = 1,
>> + .default_value = 0,
>> + },
>>  };
>>
>>  #define NUM_CTRLS ARRAY_SIZE(controls)
>> @@ -1636,6 +1644,9 @@ static int s5p_mfc_enc_s_ctrl(struct v4l2_ctrl
>> *ctrl)
>>   case V4L2_CID_MPEG_VIDEO_VPX_PROFILE:
>>   p->codec.vp8.profile = ctrl->val;
>>   break;
>> + case V4L2_CID_MPEG_VIDEO_VPX_IVF_FORMAT:
>> + p->codec.vp8.ivf = ctrl->val;
>> + break;
>>   default:
>>   v4l2_err(&dev->v4l2_dev, "Invalid control, id=%d, val=%d\n",
>>   ctrl->id,
> ctrl->val);
>> diff --git a/drivers/media/platform/s5p-mfc/s5p_mfc_opr_v6.c
>> b/drivers/media/platform/s5p-mfc/s5p_mfc_opr_v6.c
>> index f64621a..90edb19 100644
>> --- a/drivers/media/platform/s5p-mfc/s5p_mfc_opr_

Re: [PATCH 3/3] [media] s5p-mfc: Don't allocate codec buffers on STREAMON.

2014-05-08 Thread Pawel Osciak
Hi Kamil,

On Fri, May 9, 2014 at 1:22 AM, Kamil Debski  wrote:
> Hi,
>
>> From: Arun Kumar K [mailto:arunkk.sams...@gmail.com] On Behalf Of Arun
>> Kumar K
>> Sent: Friday, March 21, 2014 9:37 AM
>>
>> From: Pawel Osciak 
>>
>> Currently, we allocate private codec buffers on STREAMON, which may
>> fail if we are out of memory. We don't check for failure though, which
>> will make us crash with the codec accessing random memory.
>>
>> We shouldn't be failing STREAMON with out of memory errors though. So
>> move the allocation of private codec buffers to REQBUFS for OUTPUT
>> queue. Also, move MFC instance opening and closing to REQBUFS as well,
>> as it's tied to allocation and deallocation of private codec buffers.
>>
>> Signed-off-by: Pawel Osciak 
>> Signed-off-by: Arun Kumar K 
>> ---
>>  drivers/media/platform/s5p-mfc/s5p_mfc.c  |   10 -
>>  drivers/media/platform/s5p-mfc/s5p_mfc_ctrl.c |1 +
>>  drivers/media/platform/s5p-mfc/s5p_mfc_dec.c  |   30 +++--
>> 
>>  3 files changed, 19 insertions(+), 22 deletions(-)
>>
>> diff --git a/drivers/media/platform/s5p-mfc/s5p_mfc.c
>> b/drivers/media/platform/s5p-mfc/s5p_mfc.c
>> index 04030f5..4ee5a02 100644
>> --- a/drivers/media/platform/s5p-mfc/s5p_mfc.c
>> +++ b/drivers/media/platform/s5p-mfc/s5p_mfc.c
>> @@ -637,8 +637,9 @@ static irqreturn_t s5p_mfc_irq(int irq, void *priv)
>>   goto irq_cleanup_hw;
>>
>>   case S5P_MFC_R2H_CMD_CLOSE_INSTANCE_RET:
>> - clear_work_bit(ctx);
>> + ctx->inst_no = MFC_NO_INSTANCE_SET;
>>   ctx->state = MFCINST_FREE;
>> + clear_work_bit(ctx);
>>   wake_up(&ctx->queue);
>
> I have the impression that work bit first should be cleared and then
> changes made to the context.

While I agree it's probably a good idea, it shouldn't matter here.
This irq comes
after processing with hw_lock being held. clear_work_bit() influences
the decision
made under the same lock in try_run when choosing the next instance to run.

>
> clear_work_bit(ctx);
> +   ctx->inst_no = MFC_NO_INSTANCE_SET;
> ctx->state = MFCINST_FREE;
>
>>   goto irq_cleanup_hw;
>>
>> @@ -758,7 +759,7 @@ static int s5p_mfc_open(struct file *file)
>>   goto err_bad_node;
>>   }
>>   ctx->fh.ctrl_handler = &ctx->ctrl_handler;
>> - ctx->inst_no = -1;
>> + ctx->inst_no = MFC_NO_INSTANCE_SET;
>>   /* Load firmware if this is the first instance */
>>   if (dev->num_inst == 1) {
>>   dev->watchdog_timer.expires = jiffies + @@ -868,12 +869,11
>> @@ static int s5p_mfc_release(struct file *file)
>>   vb2_queue_release(&ctx->vq_dst);
>>   /* Mark context as idle */
>>   clear_work_bit_irqsave(ctx);
>> - /* If instance was initialised then
>> + /* If instance was initialised and not yet freed,
>>* return instance and free resources */
>> - if (ctx->inst_no != MFC_NO_INSTANCE_SET) {
>> + if (ctx->state != MFCINST_FREE && ctx->state != MFCINST_INIT) {
>>   mfc_debug(2, "Has to free instance\n");
>>   s5p_mfc_close_mfc_inst(dev, ctx);
>> - ctx->inst_no = MFC_NO_INSTANCE_SET;
>>   }
>>   /* hardware locking scheme */
>>   if (dev->curr_ctx == ctx->num)
>> diff --git a/drivers/media/platform/s5p-mfc/s5p_mfc_ctrl.c
>> b/drivers/media/platform/s5p-mfc/s5p_mfc_ctrl.c
>> index ccbfcb3..865e9e0 100644
>> --- a/drivers/media/platform/s5p-mfc/s5p_mfc_ctrl.c
>> +++ b/drivers/media/platform/s5p-mfc/s5p_mfc_ctrl.c
>> @@ -461,5 +461,6 @@ void s5p_mfc_close_mfc_inst(struct s5p_mfc_dev *dev,
>> struct s5p_mfc_ctx *ctx)
>>   if (ctx->type == MFCINST_DECODER)
>>   s5p_mfc_hw_call(dev->mfc_ops, release_dec_desc_buffer, ctx);
>>
>> + ctx->inst_no = MFC_NO_INSTANCE_SET;
>>   ctx->state = MFCINST_FREE;
>>  }
>> diff --git a/drivers/media/platform/s5p-mfc/s5p_mfc_dec.c
>> b/drivers/media/platform/s5p-mfc/s5p_mfc_dec.c
>> index efc78ae..4586186 100644
>> --- a/drivers/media/platform/s5p-mfc/s5p_mfc_dec.c
>> +++ b/drivers/media/platform/s5p-mfc/s5p_mfc_dec.c
>> @@ -475,11 +475,11 @@ static int reqbufs_output(struct s5p_mfc_dev *dev,
>> struct s5p_mfc_ctx *ctx,
>>   ret = vb2_reqbufs(&ctx->vq_src, reqbufs);
>> 

Re: [REVIEWv2 PATCH 12/13] vb2: start messages with a lower-case for consistency.

2014-04-09 Thread Pawel Osciak
On Mon, Apr 7, 2014 at 10:11 PM, Hans Verkuil  wrote:
> From: Hans Verkuil 
>
> The kernel debug messages produced by vb2 started either with a
> lower or an upper case character. Switched all to use lower-case
> which seemed to be what was used in the majority of the messages.
>
> Signed-off-by: Hans Verkuil 

Acked-by: Pawel Osciak 

> ---
>  drivers/media/v4l2-core/videobuf2-core.c | 58 
> 
>  1 file changed, 29 insertions(+), 29 deletions(-)
>
> diff --git a/drivers/media/v4l2-core/videobuf2-core.c 
> b/drivers/media/v4l2-core/videobuf2-core.c
> index d33c69b..e79d70c 100644
> --- a/drivers/media/v4l2-core/videobuf2-core.c
> +++ b/drivers/media/v4l2-core/videobuf2-core.c
> @@ -151,7 +151,7 @@ static void __vb2_buf_mem_free(struct vb2_buffer *vb)
> for (plane = 0; plane < vb->num_planes; ++plane) {
> call_memop(vb, put, vb->planes[plane].mem_priv);
> vb->planes[plane].mem_priv = NULL;
> -   dprintk(3, "Freed plane %d of buffer %d\n", plane,
> +   dprintk(3, "freed plane %d of buffer %d\n", plane,
> vb->v4l2_buf.index);
> }
>  }
> @@ -246,7 +246,7 @@ static void __setup_offsets(struct vb2_queue *q, unsigned 
> int n)
> for (plane = 0; plane < vb->num_planes; ++plane) {
> vb->v4l2_planes[plane].m.mem_offset = off;
>
> -   dprintk(3, "Buffer %d, plane %d offset 0x%08lx\n",
> +   dprintk(3, "buffer %d, plane %d offset 0x%08lx\n",
> buffer, plane, off);
>
> off += vb->v4l2_planes[plane].length;
> @@ -273,7 +273,7 @@ static int __vb2_queue_alloc(struct vb2_queue *q, enum 
> v4l2_memory memory,
> /* Allocate videobuf buffer structures */
> vb = kzalloc(q->buf_struct_size, GFP_KERNEL);
> if (!vb) {
> -   dprintk(1, "Memory alloc for buffer struct failed\n");
> +   dprintk(1, "memory alloc for buffer struct failed\n");
> break;
> }
>
> @@ -292,7 +292,7 @@ static int __vb2_queue_alloc(struct vb2_queue *q, enum 
> v4l2_memory memory,
> if (memory == V4L2_MEMORY_MMAP) {
> ret = __vb2_buf_mem_alloc(vb);
> if (ret) {
> -   dprintk(1, "Failed allocating memory for "
> +   dprintk(1, "failed allocating memory for "
> "buffer %d\n", buffer);
> kfree(vb);
> break;
> @@ -304,7 +304,7 @@ static int __vb2_queue_alloc(struct vb2_queue *q, enum 
> v4l2_memory memory,
>  */
> ret = call_vb_qop(vb, buf_init, vb);
> if (ret) {
> -   dprintk(1, "Buffer %d %p initialization"
> +   dprintk(1, "buffer %d %p initialization"
> " failed\n", buffer, vb);
> fail_vb_qop(vb, buf_init);
> __vb2_buf_mem_free(vb);
> @@ -320,7 +320,7 @@ static int __vb2_queue_alloc(struct vb2_queue *q, enum 
> v4l2_memory memory,
> if (memory == V4L2_MEMORY_MMAP)
> __setup_offsets(q, buffer);
>
> -   dprintk(1, "Allocated %d buffers, %d plane(s) each\n",
> +   dprintk(1, "allocated %d buffers, %d plane(s) each\n",
> buffer, num_planes);
>
> return buffer;
> @@ -477,13 +477,13 @@ static int __verify_planes_array(struct vb2_buffer *vb, 
> const struct v4l2_buffer
>
> /* Is memory for copying plane information present? */
> if (NULL == b->m.planes) {
> -   dprintk(1, "Multi-planar buffer passed but "
> +   dprintk(1, "multi-planar buffer passed but "
>"planes array not provided\n");
> return -EINVAL;
> }
>
> if (b->length < vb->num_planes || b->length > VIDEO_MAX_PLANES) {
> -   dprintk(1, "Incorrect planes array length, "
> +   dprintk(1, "incorrect planes array length, "
>"expected %d, got %d\n", vb->num_planes, 
> b->length);
> return -EINVAL;
> 

Re: [REVIEWv2 PATCH 10/13] vb2: set v4l2_buffer.bytesused to 0 for mp buffers

2014-04-09 Thread Pawel Osciak
Ah, alas, Sakari is right. This should not be needed, since we memcpy
vb->v4l2_buf to this, also overwriting bytesused.

On Thu, Apr 10, 2014 at 10:08 AM, Pawel Osciak  wrote:
> On Mon, Apr 7, 2014 at 10:11 PM, Hans Verkuil  wrote:
>> From: Hans Verkuil 
>>
>> The bytesused field of struct v4l2_buffer is not used for multiplanar
>> formats, so just zero it to prevent it from having some random value.
>>
>> Signed-off-by: Hans Verkuil 
>
> Acked-by: Pawel Osciak 
>
>> ---
>>  drivers/media/v4l2-core/videobuf2-core.c | 1 +
>>  1 file changed, 1 insertion(+)
>>
>> diff --git a/drivers/media/v4l2-core/videobuf2-core.c 
>> b/drivers/media/v4l2-core/videobuf2-core.c
>> index 08152dd..ef7ef82 100644
>> --- a/drivers/media/v4l2-core/videobuf2-core.c
>> +++ b/drivers/media/v4l2-core/videobuf2-core.c
>> @@ -582,6 +582,7 @@ static void __fill_v4l2_buffer(struct vb2_buffer *vb, 
>> struct v4l2_buffer *b)
>>  * for it. The caller has already verified memory and size.
>>  */
>> b->length = vb->num_planes;
>> +   b->bytesused = 0;
>> memcpy(b->m.planes, vb->v4l2_planes,
>>         b->length * sizeof(struct v4l2_plane));
>> } else {
>> --
>> 1.9.1
>>
>
>
>
> --
> Best regards,
> Pawel Osciak



-- 
Best regards,
Pawel Osciak
--
To unsubscribe from this list: send the line "unsubscribe linux-media" in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [REVIEWv2 PATCH 10/13] vb2: set v4l2_buffer.bytesused to 0 for mp buffers

2014-04-09 Thread Pawel Osciak
On Mon, Apr 7, 2014 at 10:11 PM, Hans Verkuil  wrote:
> From: Hans Verkuil 
>
> The bytesused field of struct v4l2_buffer is not used for multiplanar
> formats, so just zero it to prevent it from having some random value.
>
> Signed-off-by: Hans Verkuil 

Acked-by: Pawel Osciak 

> ---
>  drivers/media/v4l2-core/videobuf2-core.c | 1 +
>  1 file changed, 1 insertion(+)
>
> diff --git a/drivers/media/v4l2-core/videobuf2-core.c 
> b/drivers/media/v4l2-core/videobuf2-core.c
> index 08152dd..ef7ef82 100644
> --- a/drivers/media/v4l2-core/videobuf2-core.c
> +++ b/drivers/media/v4l2-core/videobuf2-core.c
> @@ -582,6 +582,7 @@ static void __fill_v4l2_buffer(struct vb2_buffer *vb, 
> struct v4l2_buffer *b)
>  * for it. The caller has already verified memory and size.
>  */
> b->length = vb->num_planes;
> +   b->bytesused = 0;
> memcpy(b->m.planes, vb->v4l2_planes,
> b->length * sizeof(struct v4l2_plane));
> } else {
> --
> 1.9.1
>



-- 
Best regards,
Pawel Osciak
--
To unsubscribe from this list: send the line "unsubscribe linux-media" in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [REVIEWv2 PATCH 09/13] vb2: add vb2_fileio_is_active and check it more often

2014-04-09 Thread Pawel Osciak
On Mon, Apr 7, 2014 at 10:11 PM, Hans Verkuil  wrote:
> From: Hans Verkuil 
>
> Added a vb2_fileio_is_active inline function that returns true if fileio
> is in progress. Check for this too in mmap() (you don't want apps mmap()ing
> buffers used by fileio) and expbuf() (same reason).
>
> In addition drivers should be able to check for this in queue_setup() to
> return an error if an attempt is made to read() or write() with
> V4L2_FIELD_ALTERNATE being configured. This is illegal (there is no way
> to pass the TOP/BOTTOM information around using file I/O).
>
> However, in order to be able to check for this the init_fileio function
> needs to set q->fileio early on, before the buffers are allocated. So switch
> to using internal functions (__reqbufs, vb2_internal_qbuf and
> vb2_internal_streamon) to skip the fileio check. Well, that's why the internal
> functions were created...
>
> Signed-off-by: Hans Verkuil 

Acked-by: Pawel Osciak 

> ---
>  drivers/media/v4l2-core/videobuf2-core.c | 39 
> 
>  include/media/videobuf2-core.h   | 17 ++
>  2 files changed, 41 insertions(+), 15 deletions(-)
>
> diff --git a/drivers/media/v4l2-core/videobuf2-core.c 
> b/drivers/media/v4l2-core/videobuf2-core.c
> index 89147d2..08152dd 100644
> --- a/drivers/media/v4l2-core/videobuf2-core.c
> +++ b/drivers/media/v4l2-core/videobuf2-core.c
> @@ -755,7 +755,7 @@ static int __verify_memory_type(struct vb2_queue *q,
>  * create_bufs is called with count == 0, but count == 0 should still
>  * do the memory and type validation.
>  */
> -   if (q->fileio) {
> +   if (vb2_fileio_is_active(q)) {
> dprintk(1, "file io in progress\n");
> return -EBUSY;
> }
> @@ -1617,7 +1617,7 @@ int vb2_prepare_buf(struct vb2_queue *q, struct 
> v4l2_buffer *b)
> struct vb2_buffer *vb;
> int ret;
>
> -   if (q->fileio) {
> +   if (vb2_fileio_is_active(q)) {
> dprintk(1, "file io in progress\n");
> return -EBUSY;
> }
> @@ -1786,7 +1786,7 @@ static int vb2_internal_qbuf(struct vb2_queue *q, 
> struct v4l2_buffer *b)
>   */
>  int vb2_qbuf(struct vb2_queue *q, struct v4l2_buffer *b)
>  {
> -   if (q->fileio) {
> +   if (vb2_fileio_is_active(q)) {
> dprintk(1, "file io in progress\n");
> return -EBUSY;
> }
> @@ -2006,7 +2006,7 @@ static int vb2_internal_dqbuf(struct vb2_queue *q, 
> struct v4l2_buffer *b, bool n
>   */
>  int vb2_dqbuf(struct vb2_queue *q, struct v4l2_buffer *b, bool nonblocking)
>  {
> -   if (q->fileio) {
> +   if (vb2_fileio_is_active(q)) {
> dprintk(1, "file io in progress\n");
> return -EBUSY;
> }
> @@ -2136,7 +2136,7 @@ static int vb2_internal_streamon(struct vb2_queue *q, 
> enum v4l2_buf_type type)
>   */
>  int vb2_streamon(struct vb2_queue *q, enum v4l2_buf_type type)
>  {
> -   if (q->fileio) {
> +   if (vb2_fileio_is_active(q)) {
> dprintk(1, "file io in progress\n");
> return -EBUSY;
> }
> @@ -2183,7 +2183,7 @@ static int vb2_internal_streamoff(struct vb2_queue *q, 
> enum v4l2_buf_type type)
>   */
>  int vb2_streamoff(struct vb2_queue *q, enum v4l2_buf_type type)
>  {
> -   if (q->fileio) {
> +   if (vb2_fileio_is_active(q)) {
> dprintk(1, "file io in progress\n");
> return -EBUSY;
> }
> @@ -2268,6 +2268,11 @@ int vb2_expbuf(struct vb2_queue *q, struct 
> v4l2_exportbuffer *eb)
> return -EINVAL;
> }
>
> +   if (vb2_fileio_is_active(q)) {
> +   dprintk(1, "expbuf: file io in progress\n");
> +   return -EBUSY;
> +   }
> +
> vb_plane = &vb->planes[eb->plane];
>
> dbuf = call_memop(vb, get_dmabuf, vb_plane->mem_priv, eb->flags & 
> O_ACCMODE);
> @@ -2344,6 +2349,10 @@ int vb2_mmap(struct vb2_queue *q, struct 
> vm_area_struct *vma)
> return -EINVAL;
> }
> }
> +   if (vb2_fileio_is_active(q)) {
> +   dprintk(1, "mmap: file io in progress\n");
> +   return -EBUSY;
> +   }
>
> /*
>  * Find the plane corresponding to the offset passed by userspace.
> @@ -2455,7 +2464,7 @@ unsigned int vb2_poll(struct vb2_queue *q, struct file 
> *file, poll_table *wait)
> /*
>  * Start file I/O emulator 

Re: [REVIEWv2 PATCH 07/13] vb2: reject output buffers with V4L2_FIELD_ALTERNATE

2014-04-09 Thread Pawel Osciak
On Mon, Apr 7, 2014 at 10:11 PM, Hans Verkuil  wrote:
> From: Hans Verkuil 
>
> This is not allowed by the spec and does in fact not make any sense.
> Return -EINVAL if this is the case.
>
> Signed-off-by: Hans Verkuil 

Acked-by: Pawel Osciak 

> ---
>  drivers/media/v4l2-core/videobuf2-core.c | 13 +
>  1 file changed, 13 insertions(+)
>
> diff --git a/drivers/media/v4l2-core/videobuf2-core.c 
> b/drivers/media/v4l2-core/videobuf2-core.c
> index b7de6be..c662ad9 100644
> --- a/drivers/media/v4l2-core/videobuf2-core.c
> +++ b/drivers/media/v4l2-core/videobuf2-core.c
> @@ -1511,6 +1511,19 @@ static int __buf_prepare(struct vb2_buffer *vb, const 
> struct v4l2_buffer *b)
> dprintk(1, "plane parameters verification failed: %d\n", ret);
> return ret;
> }
> +   if (b->field == V4L2_FIELD_ALTERNATE && V4L2_TYPE_IS_OUTPUT(q->type)) 
> {
> +   /*
> +* If the format's field is ALTERNATE, then the buffer's field
> +* should be either TOP or BOTTOM, not ALTERNATE since that
> +* makes no sense. The driver has to know whether the
> +* buffer represents a top or a bottom field in order to
> +* program any DMA correctly. Using ALTERNATE is wrong, since
> +* that just says that it is either a top or a bottom field,
> +* but not which of the two it is.
> +*/
> +   dprintk(1, "the field is incorrectly set to ALTERNATE for an 
> output buffer\n");
> +   return -EINVAL;
> +   }
>
> vb->state = VB2_BUF_STATE_PREPARING;
> vb->v4l2_buf.timestamp.tv_sec = 0;
> --
> 1.9.1
>



-- 
Best regards,
Pawel Osciak
--
To unsubscribe from this list: send the line "unsubscribe linux-media" in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [REVIEWv2 PATCH 04/13] vb2: use correct prefix

2014-04-09 Thread Pawel Osciak
_queue *q, 
> struct v4l2_buffer *b, bool n
>  int vb2_dqbuf(struct vb2_queue *q, struct v4l2_buffer *b, bool nonblocking)
>  {
> if (q->fileio) {
> -   dprintk(1, "dqbuf: file io in progress\n");
> +   dprintk(1, "file io in progress\n");
> return -EBUSY;
> }
> return vb2_internal_dqbuf(q, b, nonblocking);
> @@ -2069,26 +2066,26 @@ static int vb2_internal_streamon(struct vb2_queue *q, 
> enum v4l2_buf_type type)
> int ret;
>
> if (type != q->type) {
> -   dprintk(1, "streamon: invalid stream type\n");
> +   dprintk(1, "invalid stream type\n");
> return -EINVAL;
> }
>
> if (q->streaming) {
> -   dprintk(3, "streamon successful: already streaming\n");
> +   dprintk(3, "already streaming\n");
> return 0;
> }
>
> if (!q->num_buffers) {
> -   dprintk(1, "streamon: no buffers have been allocated\n");
> +   dprintk(1, "no buffers have been allocated\n");
> return -EINVAL;
> }
>
> if (!q->num_buffers) {
> -   dprintk(1, "streamon: no buffers have been allocated\n");
> +   dprintk(1, "no buffers have been allocated\n");
> return -EINVAL;
> }
> if (q->num_buffers < q->min_buffers_needed) {
> -   dprintk(1, "streamon: need at least %u allocated buffers\n",
> +   dprintk(1, "need at least %u allocated buffers\n",
> q->min_buffers_needed);
> return -EINVAL;
> }
> @@ -2107,7 +2104,7 @@ static int vb2_internal_streamon(struct vb2_queue *q, 
> enum v4l2_buf_type type)
>
> q->streaming = 1;
>
> -   dprintk(3, "Streamon successful\n");
> +   dprintk(3, "successful\n");
> return 0;
>  }
>
> @@ -2127,7 +2124,7 @@ static int vb2_internal_streamon(struct vb2_queue *q, 
> enum v4l2_buf_type type)
>  int vb2_streamon(struct vb2_queue *q, enum v4l2_buf_type type)
>  {
> if (q->fileio) {
> -   dprintk(1, "streamon: file io in progress\n");
> +   dprintk(1, "file io in progress\n");
> return -EBUSY;
> }
> return vb2_internal_streamon(q, type);
> @@ -2137,7 +2134,7 @@ EXPORT_SYMBOL_GPL(vb2_streamon);
>  static int vb2_internal_streamoff(struct vb2_queue *q, enum v4l2_buf_type 
> type)
>  {
> if (type != q->type) {
> -   dprintk(1, "streamoff: invalid stream type\n");
> +   dprintk(1, "invalid stream type\n");
> return -EINVAL;
> }
>
> @@ -2152,7 +2149,7 @@ static int vb2_internal_streamoff(struct vb2_queue *q, 
> enum v4l2_buf_type type)
>  */
> __vb2_queue_cancel(q);
>
> -   dprintk(3, "Streamoff successful\n");
> +   dprintk(3, "successful\n");
> return 0;
>  }
>
> @@ -2174,7 +2171,7 @@ static int vb2_internal_streamoff(struct vb2_queue *q, 
> enum v4l2_buf_type type)
>  int vb2_streamoff(struct vb2_queue *q, enum v4l2_buf_type type)
>  {
> if (q->fileio) {
> -   dprintk(1, "streamoff: file io in progress\n");
> +   dprintk(1, "file io in progress\n");
> return -EBUSY;
> }
> return vb2_internal_streamoff(q, type);
> @@ -2242,7 +2239,7 @@ int vb2_expbuf(struct vb2_queue *q, struct 
> v4l2_exportbuffer *eb)
> }
>
> if (eb->type != q->type) {
> -   dprintk(1, "qbuf: invalid buffer type\n");
> +   dprintk(1, "invalid buffer type\n");
> return -EINVAL;
> }
>
> @@ -2756,7 +2753,7 @@ static size_t __vb2_perform_fileio(struct vb2_queue *q, 
> char __user *data, size_
> struct vb2_fileio_buf *buf;
> int ret, index;
>
> -   dprintk(3, "file io: mode %s, offset %ld, count %zd, %sblocking\n",
> +   dprintk(3, "mode %s, offset %ld, count %zd, %sblocking\n",
> read ? "read" : "write", (long)*ppos, count,
> nonblock ? "non" : "");
>
> @@ -2768,7 +2765,7 @@ static size_t __vb2_perform_fileio(struct vb2_queue *q, 
> char __user *data, size_
>  */
> if (!q->fileio) {
> ret = __vb2_init_fileio(q, read);
> -   dprintk(3, "file io: vb2_init_fileio result: %d\n", ret);
> +   dprintk(3, "vb2_init_fileio result: %d\n", ret);
> if (ret)
> return ret;
> }
> @@ -2786,7 +2783,7 @@ static size_t __vb2_perform_fileio(struct vb2_queue *q, 
> char __user *data, size_
> fileio->b.type = q->type;
> fileio->b.memory = q->memory;
> ret = vb2_internal_dqbuf(q, &fileio->b, nonblock);
> -   dprintk(5, "file io: vb2_dqbuf result: %d\n", ret);
> +   dprintk(5, "vb2_dqbuf result: %d\n", ret);
> if (ret)
> return ret;
> fileio->dq_count += 1;
> @@ -2816,14 +2813,14 @@ static size_t __vb2_perform_fileio(struct vb2_queue 
> *q, char __user *data, size_
> /*
>  * Transfer data to userspace.
>  */
> -   dprintk(3, "file io: copying %zd bytes - buffer %d, offset %u\n",
> +   dprintk(3, "copying %zd bytes - buffer %d, offset %u\n",
> count, index, buf->pos);
> if (read)
> ret = copy_to_user(data, buf->vaddr + buf->pos, count);
> else
> ret = copy_from_user(buf->vaddr + buf->pos, data, count);
> if (ret) {
> -   dprintk(3, "file io: error copying data\n");
> +   dprintk(3, "error copying data\n");
> return -EFAULT;
> }
>
> @@ -2843,7 +2840,7 @@ static size_t __vb2_perform_fileio(struct vb2_queue *q, 
> char __user *data, size_
>  */
> if (read && (fileio->flags & VB2_FILEIO_READ_ONCE) &&
> fileio->dq_count == 1) {
> -   dprintk(3, "file io: read limit reached\n");
> +   dprintk(3, "read limit reached\n");
> return __vb2_cleanup_fileio(q);
> }
>
> @@ -2856,7 +2853,7 @@ static size_t __vb2_perform_fileio(struct vb2_queue *q, 
> char __user *data, size_
> fileio->b.index = index;
> fileio->b.bytesused = buf->pos;
> ret = vb2_internal_qbuf(q, &fileio->b);
> -   dprintk(5, "file io: vb2_dbuf result: %d\n", ret);
> +   dprintk(5, "vb2_dbuf result: %d\n", ret);
> if (ret)
> return ret;
>
> --
> 1.9.1
>



-- 
Best regards,
Pawel Osciak
--
To unsubscribe from this list: send the line "unsubscribe linux-media" in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [REVIEWv2 PATCH 06/13] vb2: set timestamp when using write()

2014-04-09 Thread Pawel Osciak
I see. Ack, but please add a comment about this in the code.

On Mon, Apr 7, 2014 at 10:11 PM, Hans Verkuil  wrote:
> From: Hans Verkuil 
>
> When using write() to write data to an output video node the vb2 core
> should set timestamps if V4L2_BUF_FLAG_TIMESTAMP_COPY is set. Nobody
> else is able to provide this information with the write() operation.
>
> Signed-off-by: Hans Verkuil 

Acked-by: Pawel Osciak 

> ---
>  drivers/media/v4l2-core/videobuf2-core.c | 6 ++
>  1 file changed, 6 insertions(+)
>
> diff --git a/drivers/media/v4l2-core/videobuf2-core.c 
> b/drivers/media/v4l2-core/videobuf2-core.c
> index 2e448a7..b7de6be 100644
> --- a/drivers/media/v4l2-core/videobuf2-core.c
> +++ b/drivers/media/v4l2-core/videobuf2-core.c
> @@ -22,6 +22,7 @@
>  #include 
>  #include 
>  #include 
> +#include 
>  #include 
>
>  static int debug;
> @@ -2751,6 +2752,9 @@ static size_t __vb2_perform_fileio(struct vb2_queue *q, 
> char __user *data, size_
>  {
> struct vb2_fileio_data *fileio;
> struct vb2_fileio_buf *buf;
> +   bool set_timestamp = !read &&
> +   (q->timestamp_flags & V4L2_BUF_FLAG_TIMESTAMP_MASK) ==
> +   V4L2_BUF_FLAG_TIMESTAMP_COPY;

Please add an explicit comment why we are doing this here in the code.

> int ret, index;
>
> dprintk(3, "mode %s, offset %ld, count %zd, %sblocking\n",
> @@ -2852,6 +2856,8 @@ static size_t __vb2_perform_fileio(struct vb2_queue *q, 
> char __user *data, size_
> fileio->b.memory = q->memory;
> fileio->b.index = index;
> fileio->b.bytesused = buf->pos;
> +   if (set_timestamp)
> +   v4l2_get_timestamp(&fileio->b.timestamp);
>     ret = vb2_internal_qbuf(q, &fileio->b);
> dprintk(5, "vb2_dbuf result: %d\n", ret);
> if (ret)
> --
> 1.9.1
>



-- 
Best regards,
Pawel Osciak
--
To unsubscribe from this list: send the line "unsubscribe linux-media" in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [REVIEWv2 PATCH 02/13] vb2: fix handling of data_offset and v4l2_plane.reserved[]

2014-04-09 Thread Pawel Osciak
Looks good to me, just a small nit below.


On Mon, Apr 7, 2014 at 10:11 PM, Hans Verkuil  wrote:
> From: Hans Verkuil 
>
> The videobuf2-core did not zero the 'planes' array in __qbuf_userptr()
> and __qbuf_dmabuf(). That's now memset to 0. Without this the reserved
> array in struct v4l2_plane would be non-zero, causing v4l2-compliance
> errors.
>
> More serious is the fact that data_offset was not handled correctly:
>
> - for capture devices it was never zeroed, which meant that it was
>   uninitialized. Unless the driver sets it it was a completely random
>   number. With the memset above this is now fixed.
>
> - __qbuf_dmabuf had a completely incorrect length check that included
>   data_offset.
>
> - in __fill_vb2_buffer in the DMABUF case the data_offset field was
>   unconditionally copied from v4l2_buffer to v4l2_plane when this
>   should only happen in the output case.
>
> - in the single-planar case data_offset was never correctly set to 0.
>   The single-planar API doesn't support data_offset, so setting it
>   to 0 is the right thing to do. This too is now solved by the memset.
>
> All these issues were found with v4l2-compliance.
>
> Signed-off-by: Hans Verkuil 

Acked-by: Pawel Osciak 

> ---
>  drivers/media/v4l2-core/videobuf2-core.c | 13 -
>  1 file changed, 4 insertions(+), 9 deletions(-)
>
> diff --git a/drivers/media/v4l2-core/videobuf2-core.c 
> b/drivers/media/v4l2-core/videobuf2-core.c
> index f9059bb..596998e 100644
> --- a/drivers/media/v4l2-core/videobuf2-core.c
> +++ b/drivers/media/v4l2-core/videobuf2-core.c
> @@ -1169,8 +1169,6 @@ static void __fill_vb2_buffer(struct vb2_buffer *vb, 
> const struct v4l2_buffer *b
> b->m.planes[plane].m.fd;
> v4l2_planes[plane].length =
> b->m.planes[plane].length;
> -   v4l2_planes[plane].data_offset =
> -   b->m.planes[plane].data_offset;
> }
> }
> } else {
> @@ -1180,10 +1178,8 @@ static void __fill_vb2_buffer(struct vb2_buffer *vb, 
> const struct v4l2_buffer *b
>  * In videobuf we use our internal V4l2_planes struct for
>  * single-planar buffers as well, for simplicity.
>  */
> -   if (V4L2_TYPE_IS_OUTPUT(b->type)) {
> +   if (V4L2_TYPE_IS_OUTPUT(b->type))
> v4l2_planes[0].bytesused = b->bytesused;
> -   v4l2_planes[0].data_offset = 0;
> -   }
>
> if (b->memory == V4L2_MEMORY_USERPTR) {
> v4l2_planes[0].m.userptr = b->m.userptr;
> @@ -1193,9 +1189,7 @@ static void __fill_vb2_buffer(struct vb2_buffer *vb, 
> const struct v4l2_buffer *b
> if (b->memory == V4L2_MEMORY_DMABUF) {
> v4l2_planes[0].m.fd = b->m.fd;
> v4l2_planes[0].length = b->length;
> -   v4l2_planes[0].data_offset = 0;
> }
> -
> }
>
> /* Zero flags that the vb2 core handles */
> @@ -1238,6 +1232,7 @@ static int __qbuf_userptr(struct vb2_buffer *vb, const 
> struct v4l2_buffer *b)
> int write = !V4L2_TYPE_IS_OUTPUT(q->type);
> bool reacquired = vb->planes[0].mem_priv == NULL;
>
> +   memset(planes, 0, sizeof(planes[0]) * vb->num_planes);

memset(planes, 0, sizeof(planes));

> /* Copy relevant information provided by the userspace */
> __fill_vb2_buffer(vb, b, planes);
>
> @@ -1357,6 +1352,7 @@ static int __qbuf_dmabuf(struct vb2_buffer *vb, const 
> struct v4l2_buffer *b)
> int write = !V4L2_TYPE_IS_OUTPUT(q->type);
> bool reacquired = vb->planes[0].mem_priv == NULL;
>
> +   memset(planes, 0, sizeof(planes[0]) * vb->num_planes);

memset(planes, 0, sizeof(planes));

> /* Copy relevant information provided by the userspace */
> __fill_vb2_buffer(vb, b, planes);
>
> @@ -1374,8 +1370,7 @@ static int __qbuf_dmabuf(struct vb2_buffer *vb, const 
> struct v4l2_buffer *b)
> if (planes[plane].length == 0)
> planes[plane].length = dbuf->size;
>
> -   if (planes[plane].length < planes[plane].data_offset +
> -   q->plane_sizes[plane]) {
> +   if (planes[plane].length < q->plane_sizes[plane]) {
> dprintk(1, "qbuf: invalid dmabuf length for plane 
> %d\n",
> plane);
> ret = -EINVAL;
> --
> 1.9.1
>



-- 
Best regards,
Pawel Osciak
--
To unsubscribe from this list: send the line "unsubscribe linux-media" in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [REVIEWv2 PATCH 04/13] vb2: use correct prefix

2014-04-09 Thread Pawel Osciak
On Mon, Apr 7, 2014 at 10:11 PM, Hans Verkuil  wrote:
> From: Hans Verkuil 
>
> Many dprintk's in vb2 use a hardcoded prefix with the function name. In
> many cases that is now outdated. To keep things consistent the dprintk
> macro has been changed to print the function name in addition to the "vb2:"
> prefix. Superfluous prefixes elsewhere in the code have been removed.
>
> Signed-off-by: Hans Verkuil 

Acked-by: Pawel Osciak 

> ---
>  drivers/media/v4l2-core/videobuf2-core.c | 133 
> +++
>  1 file changed, 65 insertions(+), 68 deletions(-)
>
> diff --git a/drivers/media/v4l2-core/videobuf2-core.c 
> b/drivers/media/v4l2-core/videobuf2-core.c
> index b2582cb..1421075 100644
> --- a/drivers/media/v4l2-core/videobuf2-core.c
> +++ b/drivers/media/v4l2-core/videobuf2-core.c
> @@ -27,10 +27,10 @@
>  static int debug;
>  module_param(debug, int, 0644);
>
> -#define dprintk(level, fmt, arg...)\
> -   do {\
> -   if (debug >= level) \
> -   printk(KERN_DEBUG "vb2: " fmt, ## arg); \
> +#define dprintk(level, fmt, arg...)  
> \
> +   do {  
> \
> +   if (debug >= level)   
> \
> +   pr_debug("vb2: %s: " fmt, __func__, ## arg); \
> } while (0)
>
>  #ifdef CONFIG_VIDEO_ADV_DEBUG
> @@ -371,7 +371,7 @@ static int __vb2_queue_free(struct vb2_queue *q, unsigned 
> int buffers)
> if (q->bufs[buffer] == NULL)
> continue;
> if (q->bufs[buffer]->state == VB2_BUF_STATE_PREPARING) {
> -   dprintk(1, "reqbufs: preparing buffers, cannot 
> free\n");
> +   dprintk(1, "preparing buffers, cannot free\n");
> return -EAGAIN;
> }
> }
> @@ -656,12 +656,12 @@ int vb2_querybuf(struct vb2_queue *q, struct 
> v4l2_buffer *b)
> int ret;
>
> if (b->type != q->type) {
> -   dprintk(1, "querybuf: wrong buffer type\n");
> +   dprintk(1, "wrong buffer type\n");
> return -EINVAL;
> }
>
> if (b->index >= q->num_buffers) {
> -   dprintk(1, "querybuf: buffer index out of range\n");
> +   dprintk(1, "buffer index out of range\n");
> return -EINVAL;
> }
> vb = q->bufs[b->index];
> @@ -721,12 +721,12 @@ static int __verify_memory_type(struct vb2_queue *q,
>  {
> if (memory != V4L2_MEMORY_MMAP && memory != V4L2_MEMORY_USERPTR &&
> memory != V4L2_MEMORY_DMABUF) {
> -   dprintk(1, "reqbufs: unsupported memory type\n");
> +   dprintk(1, "unsupported memory type\n");
> return -EINVAL;
> }
>
> if (type != q->type) {
> -   dprintk(1, "reqbufs: requested type is incorrect\n");
> +   dprintk(1, "requested type is incorrect\n");
> return -EINVAL;
> }
>
> @@ -735,17 +735,17 @@ static int __verify_memory_type(struct vb2_queue *q,
>  * are available.
>  */
> if (memory == V4L2_MEMORY_MMAP && __verify_mmap_ops(q)) {
> -   dprintk(1, "reqbufs: MMAP for current setup unsupported\n");
> +   dprintk(1, "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");
> +   dprintk(1, "USERPTR for current setup unsupported\n");
> return -EINVAL;
> }
>
> if (memory == V4L2_MEMORY_DMABUF && __verify_dmabuf_ops(q)) {
> -   dprintk(1, "reqbufs: DMABUF for current setup unsupported\n");
> +   dprintk(1, "DMABUF for current setup unsupported\n");
> return -EINVAL;
> }
>
> @@ -755,7 +755,7 @@ static int __verify_memory_type(struct vb2_queue *q,
>  * do the memory and type validation.
>  */
> if (q->fileio) {
> -   dprintk(1, "reqbufs: file io in 

Re: videobuf2-vmalloc suspect for corrupted data

2014-04-07 Thread Pawel Osciak
Hi Divneil,

On Mon, Apr 7, 2014 at 6:56 PM, Divneil Wadhawan  wrote:
> Hi,
>
> I have a V4L2 capture driver accepting a malloc'ed buffer.
> The driver is using vb2_vmalloc_memops 
> (../drivers/media/v4l2-core/videobuf2-vmalloc.c) for user-space to kvaddr 
> translation.
> Randomly, corrupted data is received by user-app.
>
> So, the question is regarding the handling of get_userptr, put_userptr by 
> v4l2-core:
>
> const struct vb2_mem_ops vb2_vmalloc_memops = {
>  
>  .get_userptr= vb2_vmalloc_get_userptr, (get_user_pages() and 
> vm_map_ram())
>  .put_userptr= vb2_vmalloc_put_userptr, (set_page_dirty_lock() 
> and put_page())
>   .
> };
>
> The driver prepares for the transaction by virtue of v4l2-core calling 
> get_userptr (QBUF)
> After data is filled, driver puts on a done list (DQBUF)
>
> We never mark the pages as dirty (or put_userptr) after a transaction is 
> complete.
> Here, in v4l2 core (videobuf2-core.c) , we conditionally put_userptr - when a 
> QBUF with a different userptr on same index, or releasing buffers.
>
> Is it correct? Probably seems to be the reason for corrupted data.

This is an optimization and requires the mapping of userspace buffer
to v4l2_buffer index to not change.
Is it possible that your userspace is not always queuing the same
userptr memory areas with the same v4l2_buffer index values?
In other words, if you have 2 buffers in use, under userspace mapping
at addr1 and addr2, if you queue addr1 with index=0 and addr2 with
index=1 initially,
you should always keep queuing addr1 with index=0 and never 1, etc.

Also, what architecture are you running this on?

> Regards,
> Divneil   --
> To unsubscribe from this list: send the line "unsubscribe linux-media" in
> the body of a message to majord...@vger.kernel.org
> More majordomo info at  http://vger.kernel.org/majordomo-info.html

-- 
Best regards,
Pawel Osciak
--
To unsubscribe from this list: send the line "unsubscribe linux-media" in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [REVIEW PATCH 08/11] vb2: simplify a confusing condition.

2014-04-07 Thread Pawel Osciak
On Tue, Mar 11, 2014 at 6:20 AM, Hans Verkuil  wrote:
> From: Hans Verkuil 
>
> q->start_streaming_called is always true, so the WARN_ON check against
> it being false can be dropped.
>
> Signed-off-by: Hans Verkuil 

Acked-by: Pawel Osciak 

> ---
>  drivers/media/v4l2-core/videobuf2-core.c | 5 ++---
>  1 file changed, 2 insertions(+), 3 deletions(-)
>
> diff --git a/drivers/media/v4l2-core/videobuf2-core.c 
> b/drivers/media/v4l2-core/videobuf2-core.c
> index 8984187..2ae316b 100644
> --- a/drivers/media/v4l2-core/videobuf2-core.c
> +++ b/drivers/media/v4l2-core/videobuf2-core.c
> @@ -1099,9 +1099,8 @@ void vb2_buffer_done(struct vb2_buffer *vb, enum 
> vb2_buffer_state state)
> if (!q->start_streaming_called) {
> if (WARN_ON(state != VB2_BUF_STATE_QUEUED))
> state = VB2_BUF_STATE_QUEUED;
> -   } else if (!WARN_ON(!q->start_streaming_called)) {
> -   if (WARN_ON(state != VB2_BUF_STATE_DONE &&
> -   state != VB2_BUF_STATE_ERROR))
> +   } else if (WARN_ON(state != VB2_BUF_STATE_DONE &&
> +  state != VB2_BUF_STATE_ERROR)) {
>     state = VB2_BUF_STATE_ERROR;
> }
>
> --
> 1.9.0
>



-- 
Best regards,
Pawel Osciak
--
To unsubscribe from this list: send the line "unsubscribe linux-media" in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [REVIEW PATCH 07/11] vb2: reject output buffers with V4L2_FIELD_ALTERNATE

2014-04-07 Thread Pawel Osciak
On Tue, Mar 11, 2014 at 6:20 AM, Hans Verkuil  wrote:
> From: Hans Verkuil 
>
> This is not allowed by the spec and does in fact not make any sense.
> Return -EINVAL if this is the case.
>
> Signed-off-by: Hans Verkuil 
> ---
>  drivers/media/v4l2-core/videobuf2-core.c | 9 +
>  1 file changed, 9 insertions(+)
>
> diff --git a/drivers/media/v4l2-core/videobuf2-core.c 
> b/drivers/media/v4l2-core/videobuf2-core.c
> index afd1268..8984187 100644
> --- a/drivers/media/v4l2-core/videobuf2-core.c
> +++ b/drivers/media/v4l2-core/videobuf2-core.c
> @@ -1526,6 +1526,15 @@ static int __buf_prepare(struct vb2_buffer *vb, const 
> struct v4l2_buffer *b)
> __func__, ret);
> return ret;
> }
> +   if (V4L2_TYPE_IS_OUTPUT(q->type) && b->field == V4L2_FIELD_ALTERNATE) 
> {

Checking for field first would probably eliminate the additional
OUTPUT check most of the time.
I'd swap them.

> +   /*
> +* If field is ALTERNATE, then we return an error.

I'd drop this line, doesn't really add anything.

> +* If the format's field is ALTERNATE, then the buffer's field
> +* should be either TOP or BOTTOM, but using ALTERNATE here as
> +* well makes no sense.

This doesn't really explain why this is an error and is confusing,
since we don't check TOP/BOTTOM
anyway. I think it would be better to say why ALTERNATE doesn't make
sense instead.

> +*/
> +   return -EINVAL;
> +   }
>
> vb->state = VB2_BUF_STATE_PREPARING;
> vb->v4l2_buf.timestamp.tv_sec = 0;
> --
> 1.9.0
>



-- 
Best regards,
Pawel Osciak
--
To unsubscribe from this list: send the line "unsubscribe linux-media" in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [REVIEW PATCH 06/11] vb2: set timestamp when using write()

2014-04-07 Thread Pawel Osciak
On Tue, Mar 11, 2014 at 6:20 AM, Hans Verkuil  wrote:
> From: Hans Verkuil 
>
> When using write() to write data to an output video node the vb2 core
> should set timestamps if V4L2_BUF_FLAG_TIMESTAMP_COPY is set. Nobody

I'm confused. Shouldn't we be saving the existing timestamp from the buffer if
V4L2_BUF_FLAG_TIMESTAMP_COPY is true, instead of getting it from
v4l2_get_timestamp()?

> else is able to provide this information with the write() operation.
>
> Signed-off-by: Hans Verkuil 
> ---
>  drivers/media/v4l2-core/videobuf2-core.c | 6 ++
>  1 file changed, 6 insertions(+)
>
> diff --git a/drivers/media/v4l2-core/videobuf2-core.c 
> b/drivers/media/v4l2-core/videobuf2-core.c
> index e38b45e..afd1268 100644
> --- a/drivers/media/v4l2-core/videobuf2-core.c
> +++ b/drivers/media/v4l2-core/videobuf2-core.c
> @@ -22,6 +22,7 @@
>  #include 
>  #include 
>  #include 
> +#include 
>  #include 
>
>  static int debug;
> @@ -2767,6 +2768,9 @@ static size_t __vb2_perform_fileio(struct vb2_queue *q, 
> char __user *data, size_
>  {
> struct vb2_fileio_data *fileio;
> struct vb2_fileio_buf *buf;
> +   bool set_timestamp = !read &&
> +   (q->timestamp_flags & V4L2_BUF_FLAG_TIMESTAMP_MASK) ==
> +   V4L2_BUF_FLAG_TIMESTAMP_COPY;
> int ret, index;
>
> dprintk(3, "file io: mode %s, offset %ld, count %zd, %sblocking\n",
> @@ -2868,6 +2872,8 @@ static size_t __vb2_perform_fileio(struct vb2_queue *q, 
> char __user *data, size_
> fileio->b.memory = q->memory;
> fileio->b.index = index;
> fileio->b.bytesused = buf->pos;
> +   if (set_timestamp)
> +   v4l2_get_timestamp(&fileio->b.timestamp);
> ret = vb2_internal_qbuf(q, &fileio->b);
> dprintk(5, "file io: vb2_internal_qbuf result: %d\n", ret);
> if (ret)
> --
> 1.9.0
>



-- 
Best regards,
Pawel Osciak
--
To unsubscribe from this list: send the line "unsubscribe linux-media" in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [REVIEW PATCH 05/11] vb2: move __qbuf_mmap before __qbuf_userptr

2014-04-07 Thread Pawel Osciak
On Tue, Mar 11, 2014 at 6:20 AM, Hans Verkuil  wrote:
> From: Hans Verkuil 
>
> __qbuf_mmap was sort of hidden in between the much larger __qbuf_userptr
> and __qbuf_dmabuf functions. Move it before __qbuf_userptr which is
> also conform the usual order these memory models are implemented: first
> mmap, then userptr, then dmabuf.
>
> Signed-off-by: Hans Verkuil 

Acked-by: Pawel Osciak 

> ---
>  drivers/media/v4l2-core/videobuf2-core.c | 28 ++--
>  1 file changed, 14 insertions(+), 14 deletions(-)
>
> diff --git a/drivers/media/v4l2-core/videobuf2-core.c 
> b/drivers/media/v4l2-core/videobuf2-core.c
> index 71be247..e38b45e 100644
> --- a/drivers/media/v4l2-core/videobuf2-core.c
> +++ b/drivers/media/v4l2-core/videobuf2-core.c
> @@ -1254,6 +1254,20 @@ static void __fill_vb2_buffer(struct vb2_buffer *vb, 
> const struct v4l2_buffer *b
>  }
>
>  /**
> + * __qbuf_mmap() - handle qbuf of an MMAP buffer
> + */
> +static int __qbuf_mmap(struct vb2_buffer *vb, const struct v4l2_buffer *b)
> +{
> +   int ret;
> +
> +   __fill_vb2_buffer(vb, b, vb->v4l2_planes);
> +   ret = call_vb_qop(vb, buf_prepare, vb);
> +   if (ret)
> +   fail_vb_qop(vb, buf_prepare);
> +   return ret;
> +}
> +
> +/**
>   * __qbuf_userptr() - handle qbuf of a USERPTR buffer
>   */
>  static int __qbuf_userptr(struct vb2_buffer *vb, const struct v4l2_buffer *b)
> @@ -1359,20 +1373,6 @@ err:
>  }
>
>  /**
> - * __qbuf_mmap() - handle qbuf of an MMAP buffer
> - */
> -static int __qbuf_mmap(struct vb2_buffer *vb, const struct v4l2_buffer *b)
> -{
> -   int ret;
> -
> -   __fill_vb2_buffer(vb, b, vb->v4l2_planes);
> -   ret = call_vb_qop(vb, buf_prepare, vb);
> -   if (ret)
> -   fail_vb_qop(vb, buf_prepare);
> -   return ret;
> -}
> -
> -/**
>   * __qbuf_dmabuf() - handle qbuf of a DMABUF buffer
>   */
>  static int __qbuf_dmabuf(struct vb2_buffer *vb, const struct v4l2_buffer *b)
> --
> 1.9.0
>



-- 
Best regards,
Pawel Osciak
--
To unsubscribe from this list: send the line "unsubscribe linux-media" in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [REVIEW PATCH 03/11] vb2: if bytesused is 0, then fill with output buffer length

2014-04-07 Thread Pawel Osciak
On Mon, Apr 7, 2014 at 4:39 PM, Hans Verkuil  wrote:
> On 04/07/2014 09:20 AM, Pawel Osciak wrote:
>> I'm thinking, that if we are doing this, perhaps we should just update
>> the API to allow this case, i.e. say that if the bytesused is not set
>
> With 'not set' you mean 'is 0', right?

Yes, correct.

>
>> for any planes, length will be used by default?
>> This would be backwards-compatible.
>
> I agree with that. I'll update the doc.
>
> Regards,
>
> Hans
>
--
To unsubscribe from this list: send the line "unsubscribe linux-media" in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [REVIEW PATCH 04/11] vb2: use correct prefix

2014-04-07 Thread Pawel Osciak
q, &vb, b, nonblocking);
> @@ -1954,13 +1960,13 @@ static int vb2_internal_dqbuf(struct vb2_queue *q, 
> struct v4l2_buffer *b, bool n
>
> switch (vb->state) {
> case VB2_BUF_STATE_DONE:
> -   dprintk(3, "dqbuf: Returning done buffer\n");
> +   dprintk(3, "%s: Returning done buffer\n", __func__);
> break;
> case VB2_BUF_STATE_ERROR:
> -   dprintk(3, "dqbuf: Returning done buffer with errors\n");
> +   dprintk(3, "%s: Returning done buffer with errors\n", 
> __func__);
> break;
> default:
> -   dprintk(1, "dqbuf: Invalid buffer state\n");
> +   dprintk(1, "%s: Invalid buffer state\n", __func__);
> return -EINVAL;
> }
>
> @@ -2004,7 +2010,7 @@ static int vb2_internal_dqbuf(struct vb2_queue *q, 
> struct v4l2_buffer *b, bool n
>  int vb2_dqbuf(struct vb2_queue *q, struct v4l2_buffer *b, bool nonblocking)
>  {
> if (q->fileio) {
> -   dprintk(1, "dqbuf: file io in progress\n");
> +   dprintk(1, "%s: file io in progress\n", __func__);
> return -EBUSY;
> }
> return vb2_internal_dqbuf(q, b, nonblocking);
> @@ -2076,7 +2082,7 @@ static int vb2_internal_streamon(struct vb2_queue *q, 
> enum v4l2_buf_type type)
> int ret;
>
> if (type != q->type) {
> -   dprintk(1, "streamon: invalid stream type\n");
> +   dprintk(1, "%s: invalid stream type\n", __func__);
> return -EINVAL;
> }
>
> @@ -2086,17 +2092,17 @@ static int vb2_internal_streamon(struct vb2_queue *q, 
> enum v4l2_buf_type type)
> }
>
> if (!q->num_buffers) {
> -   dprintk(1, "streamon: no buffers have been allocated\n");
> +   dprintk(1, "%s: no buffers have been allocated\n", __func__);
> return -EINVAL;
> }
>
> if (!q->num_buffers) {
> -   dprintk(1, "streamon: no buffers have been allocated\n");
> +   dprintk(1, "%s: no buffers have been allocated\n", __func__);
> return -EINVAL;
> }
> if (q->num_buffers < q->min_buffers_needed) {
> -   dprintk(1, "streamon: need at least %u allocated buffers\n",
> -   q->min_buffers_needed);
> +   dprintk(1, "%s: need at least %u allocated buffers\n",
> +   __func__, q->min_buffers_needed);
> return -EINVAL;
> }
>
> @@ -2134,7 +2140,7 @@ static int vb2_internal_streamon(struct vb2_queue *q, 
> enum v4l2_buf_type type)
>  int vb2_streamon(struct vb2_queue *q, enum v4l2_buf_type type)
>  {
> if (q->fileio) {
> -   dprintk(1, "streamon: file io in progress\n");
> +   dprintk(1, "%s: file io in progress\n", __func__);
> return -EBUSY;
> }
> return vb2_internal_streamon(q, type);
> @@ -2144,7 +2150,7 @@ EXPORT_SYMBOL_GPL(vb2_streamon);
>  static int vb2_internal_streamoff(struct vb2_queue *q, enum v4l2_buf_type 
> type)
>  {
> if (type != q->type) {
> -   dprintk(1, "streamoff: invalid stream type\n");
> +   dprintk(1, "%s: invalid stream type\n", __func__);
> return -EINVAL;
> }
>
> @@ -2181,7 +2187,7 @@ static int vb2_internal_streamoff(struct vb2_queue *q, 
> enum v4l2_buf_type type)
>  int vb2_streamoff(struct vb2_queue *q, enum v4l2_buf_type type)
>  {
> if (q->fileio) {
> -   dprintk(1, "streamoff: file io in progress\n");
> +   dprintk(1, "%s: file io in progress\n", __func__);
> return -EBUSY;
> }
> return vb2_internal_streamoff(q, type);
> @@ -2249,7 +2255,7 @@ int vb2_expbuf(struct vb2_queue *q, struct 
> v4l2_exportbuffer *eb)
> }
>
> if (eb->type != q->type) {
> -   dprintk(1, "qbuf: invalid buffer type\n");
> +   dprintk(1, "%s: invalid buffer type\n", __func__);
> return -EINVAL;
> }
>
> @@ -2863,7 +2869,7 @@ static size_t __vb2_perform_fileio(struct vb2_queue *q, 
> char __user *data, size_
> fileio->b.index = index;
> fileio->b.bytesused = buf->pos;
> ret = vb2_internal_qbuf(q, &fileio->b);
> -   dprintk(5, "file io: vb2_dbuf result: %d\n", ret);
> +   dprintk(5, "file io: vb2_internal_qbuf result: %d\n", ret);
> if (ret)
> return ret;
>
> --
> 1.9.0
>



-- 
Best regards,
Pawel Osciak
--
To unsubscribe from this list: send the line "unsubscribe linux-media" in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [REVIEW PATCH 03/11] vb2: if bytesused is 0, then fill with output buffer length

2014-04-07 Thread Pawel Osciak
I'm thinking, that if we are doing this, perhaps we should just update
the API to allow this case, i.e. say that if the bytesused is not set
for any planes, length will be used by default?
This would be backwards-compatible.

On Tue, Mar 11, 2014 at 6:20 AM, Hans Verkuil  wrote:
> From: Hans Verkuil 
>
> The application should really always fill in bytesused for output
> buffers, unfortunately the vb2 framework never checked for that.
>
> So for single planar formats replace a bytesused of 0 by the length
> of the buffer, and for multiplanar format do the same if bytesused is
> 0 for ALL planes.
>
> This seems to be what the user really intended if v4l2_buffer was
> just memset to 0.
>
> I'm afraid that just checking for this and returning an error would
> break too many applications. Quite a few drivers never check for bytesused
> at all and just use the buffer length instead.
>
> Signed-off-by: Hans Verkuil 

Acked-by: Pawel Osciak 

> ---
>  drivers/media/v4l2-core/videobuf2-core.c | 32 
> +++-
>  1 file changed, 27 insertions(+), 5 deletions(-)
>
> diff --git a/drivers/media/v4l2-core/videobuf2-core.c 
> b/drivers/media/v4l2-core/videobuf2-core.c
> index 1a09442..83e78e9 100644
> --- a/drivers/media/v4l2-core/videobuf2-core.c
> +++ b/drivers/media/v4l2-core/videobuf2-core.c
> @@ -1145,19 +1145,35 @@ static void __fill_vb2_buffer(struct vb2_buffer *vb, 
> const struct v4l2_buffer *b
> memset(v4l2_planes[plane].reserved, 0,
>sizeof(v4l2_planes[plane].reserved));
> v4l2_planes[plane].data_offset = 0;
> +   v4l2_planes[plane].bytesused = 0;
> }
>
> /* Fill in driver-provided information for OUTPUT types */
> if (V4L2_TYPE_IS_OUTPUT(b->type)) {
> +   bool bytesused_is_used;
> +
> +   /* Check if bytesused == 0 for all planes */
> +   for (plane = 0; plane < vb->num_planes; ++plane)
> +   if (b->m.planes[plane].bytesused)
> +   break;
> +   bytesused_is_used = plane < vb->num_planes;
> +
> /*
>  * Will have to go up to b->length when API starts
>  * accepting variable number of planes.
> +*
> +* If bytesused_is_used is false, then fall back to 
> the
> +* full buffer size. In that case userspace clearly
> +* never bothered to set it and it's a safe assumption
> +* that they really meant to use the full plane sizes.
>  */
> for (plane = 0; plane < vb->num_planes; ++plane) {
> -   v4l2_planes[plane].bytesused =
> -   b->m.planes[plane].bytesused;
> -   v4l2_planes[plane].data_offset =
> -   b->m.planes[plane].data_offset;
> +   struct v4l2_plane *pdst = &v4l2_planes[plane];
> +   struct v4l2_plane *psrc = &b->m.planes[plane];
> +
> +   pdst->bytesused = bytesused_is_used ?
> +   psrc->bytesused : psrc->length;
> +   pdst->data_offset = psrc->data_offset;
> }
> }
>
> @@ -1183,9 +1199,15 @@ static void __fill_vb2_buffer(struct vb2_buffer *vb, 
> const struct v4l2_buffer *b
>  * so fill in relevant v4l2_buffer struct fields instead.
>  * In videobuf we use our internal V4l2_planes struct for
>  * single-planar buffers as well, for simplicity.
> +*
> +* If bytesused == 0, then fall back to the full buffer size
> +* as that's a sensible default.
>  */
> if (V4L2_TYPE_IS_OUTPUT(b->type))
> -   v4l2_planes[0].bytesused = b->bytesused;
> +   v4l2_planes[0].bytesused =
> +   b->bytesused ? b->bytesused : b->length;
> +   else
> +   v4l2_planes[0].bytesused = 0;
> /* Single-planar buffers never use data_offset */
> v4l2_planes[0].data_offset = 0;
>
> --
> 1.9.0
>



-- 
Best regards,
Pawel Osciak
--
To unsubscribe from this list: send the line "unsubscribe linux-media" in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [REVIEW PATCH 02/11] vb2: fix handling of data_offset and v4l2_plane.reserved[]

2014-04-06 Thread Pawel Osciak
On Tue, Mar 11, 2014 at 6:20 AM, Hans Verkuil  wrote:
> From: Hans Verkuil 
>
> The videobuf2-core did not zero the reserved array of v4l2_plane as it
> should.
>
> More serious is the fact that data_offset was not handled correctly:
>
> - for capture devices it was never zeroed, which meant that it was
>   uninitialized. Unless the driver sets it it was a completely random
>   number.
>
> - __qbuf_dmabuf had a completely incorrect length check that included
>   data_offset.
>
> - in the single-planar case data_offset was never correctly set to 0.
>   The single-planar API doesn't support data_offset, so setting it
>   to 0 is the right thing to do.
>
> All these issues were found with v4l2-compliance.
>
> Signed-off-by: Hans Verkuil 
> ---
>  drivers/media/v4l2-core/videobuf2-core.c | 19 ++-
>  1 file changed, 10 insertions(+), 9 deletions(-)
>
> diff --git a/drivers/media/v4l2-core/videobuf2-core.c 
> b/drivers/media/v4l2-core/videobuf2-core.c
> index f9059bb..1a09442 100644
> --- a/drivers/media/v4l2-core/videobuf2-core.c
> +++ b/drivers/media/v4l2-core/videobuf2-core.c
> @@ -1141,6 +1141,12 @@ static void __fill_vb2_buffer(struct vb2_buffer *vb, 
> const struct v4l2_buffer *b
> unsigned int plane;
>
> if (V4L2_TYPE_IS_MULTIPLANAR(b->type)) {
> +   for (plane = 0; plane < vb->num_planes; ++plane) {
> +   memset(v4l2_planes[plane].reserved, 0,
> +  sizeof(v4l2_planes[plane].reserved));
> +   v4l2_planes[plane].data_offset = 0;
> +   }
> +

Perhaps we should just memset the whole v4l2_planes array to 0 over
all elements (ARRAY_SIZE)?
Also I would extract this above the if and zero out everything for
both multi and singleplanar.
You shouldn't need to zero it out below then.

> /* Fill in driver-provided information for OUTPUT types */
> if (V4L2_TYPE_IS_OUTPUT(b->type)) {
> /*
> @@ -1169,8 +1175,6 @@ static void __fill_vb2_buffer(struct vb2_buffer *vb, 
> const struct v4l2_buffer *b
> b->m.planes[plane].m.fd;
> v4l2_planes[plane].length =
> b->m.planes[plane].length;
> -   v4l2_planes[plane].data_offset =
> -   b->m.planes[plane].data_offset;
> }
> }
> } else {
> @@ -1180,10 +1184,10 @@ static void __fill_vb2_buffer(struct vb2_buffer *vb, 
> const struct v4l2_buffer *b
>  * In videobuf we use our internal V4l2_planes struct for
>  * single-planar buffers as well, for simplicity.
>  */
> -   if (V4L2_TYPE_IS_OUTPUT(b->type)) {
> +   if (V4L2_TYPE_IS_OUTPUT(b->type))
> v4l2_planes[0].bytesused = b->bytesused;
> -   v4l2_planes[0].data_offset = 0;
> -   }
> +   /* Single-planar buffers never use data_offset */
> +   v4l2_planes[0].data_offset = 0;
>
> if (b->memory == V4L2_MEMORY_USERPTR) {
> v4l2_planes[0].m.userptr = b->m.userptr;
> @@ -1193,9 +1197,7 @@ static void __fill_vb2_buffer(struct vb2_buffer *vb, 
> const struct v4l2_buffer *b
> if (b->memory == V4L2_MEMORY_DMABUF) {
> v4l2_planes[0].m.fd = b->m.fd;
> v4l2_planes[0].length = b->length;
> -   v4l2_planes[0].data_offset = 0;
> }
> -
> }
>
> /* Zero flags that the vb2 core handles */
> @@ -1374,8 +1376,7 @@ static int __qbuf_dmabuf(struct vb2_buffer *vb, const 
> struct v4l2_buffer *b)
> if (planes[plane].length == 0)
> planes[plane].length = dbuf->size;
>
> -   if (planes[plane].length < planes[plane].data_offset +
> -       q->plane_sizes[plane]) {
> +   if (planes[plane].length < q->plane_sizes[plane]) {

Good catch!

> dprintk(1, "qbuf: invalid dmabuf length for plane 
> %d\n",
> plane);
> ret = -EINVAL;
> --
> 1.9.0
>



-- 
Best regards,
Pawel Osciak
--
To unsubscribe from this list: send the line "unsubscribe linux-media" in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [REVIEW PATCH 01/11] vb2: stop_streaming should return void

2014-04-06 Thread Pawel Osciak
On Tue, Mar 11, 2014 at 6:20 AM, Hans Verkuil  wrote:
> From: Hans Verkuil 
>
> The vb2 core ignores any return code from the stop_streaming op.
> And there really isn't anything it can do anyway in case of an error.
> So change the return type to void and update any drivers that implement it.
>
> The int return gave drivers the idea that this operation could actually
> fail, but that's really not the case.
>
> The pwc amd sdr-msi3101 drivers both had this construction:
>
> if (mutex_lock_interruptible(&s->v4l2_lock))
> return -ERESTARTSYS;
>
> This has been updated to just call mutex_lock(). The stop_streaming op
> expects this to really stop streaming and I very much doubt this will
> work reliably if stop_streaming just returns without really stopping the
> DMA.
>
> Signed-off-by: Hans Verkuil 

Acked-by: Pawel Osciak 

> ---
>  drivers/media/pci/sta2x11/sta2x11_vip.c  | 3 +--
>  drivers/media/platform/blackfin/bfin_capture.c   | 6 +-
>  drivers/media/platform/coda.c| 4 +---
>  drivers/media/platform/exynos-gsc/gsc-m2m.c  | 4 +---
>  drivers/media/platform/exynos4-is/fimc-capture.c | 6 +++---
>  drivers/media/platform/exynos4-is/fimc-lite.c| 6 +++---
>  drivers/media/platform/exynos4-is/fimc-m2m.c | 3 +--
>  drivers/media/platform/marvell-ccic/mcam-core.c  | 7 +++
>  drivers/media/platform/s3c-camif/camif-capture.c | 4 ++--
>  drivers/media/platform/s5p-jpeg/jpeg-core.c  | 4 +---
>  drivers/media/platform/s5p-mfc/s5p_mfc_dec.c | 3 +--
>  drivers/media/platform/s5p-mfc/s5p_mfc_enc.c | 3 +--
>  drivers/media/platform/s5p-tv/mixer_video.c  | 3 +--
>  drivers/media/platform/soc_camera/atmel-isi.c| 6 ++
>  drivers/media/platform/soc_camera/mx2_camera.c   | 4 +---
>  drivers/media/platform/soc_camera/mx3_camera.c   | 4 +---
>  drivers/media/platform/soc_camera/rcar_vin.c | 4 +---
>  drivers/media/platform/soc_camera/sh_mobile_ceu_camera.c | 4 ++--
>  drivers/media/platform/vivi.c| 3 +--
>  drivers/media/platform/vsp1/vsp1_video.c | 4 +---
>  drivers/media/usb/em28xx/em28xx-v4l.h| 2 +-
>  drivers/media/usb/em28xx/em28xx-video.c  | 8 ++--
>  drivers/media/usb/pwc/pwc-if.c   | 7 ++-
>  drivers/media/usb/s2255/s2255drv.c   | 5 ++---
>  drivers/media/usb/stk1160/stk1160-v4l.c  | 4 ++--
>  drivers/media/usb/usbtv/usbtv-video.c| 9 +++--
>  drivers/staging/media/davinci_vpfe/vpfe_video.c  | 3 +--
>  drivers/staging/media/dt3155v4l/dt3155v4l.c  | 3 +--
>  drivers/staging/media/go7007/go7007-v4l2.c   | 3 +--
>  drivers/staging/media/msi3101/sdr-msi3101.c  | 7 ++-
>  drivers/staging/media/solo6x10/solo6x10-v4l2-enc.c   | 3 +--
>  drivers/staging/media/solo6x10/solo6x10-v4l2.c   | 3 +--
>  include/media/videobuf2-core.h   | 2 +-
>  33 files changed, 49 insertions(+), 95 deletions(-)
>
> diff --git a/drivers/media/pci/sta2x11/sta2x11_vip.c 
> b/drivers/media/pci/sta2x11/sta2x11_vip.c
> index bb11443..7559951 100644
> --- a/drivers/media/pci/sta2x11/sta2x11_vip.c
> +++ b/drivers/media/pci/sta2x11/sta2x11_vip.c
> @@ -357,7 +357,7 @@ static int start_streaming(struct vb2_queue *vq, unsigned 
> int count)
>  }
>
>  /* abort streaming and wait for last buffer */
> -static int stop_streaming(struct vb2_queue *vq)
> +static void stop_streaming(struct vb2_queue *vq)
>  {
> struct sta2x11_vip *vip = vb2_get_drv_priv(vq);
> struct vip_buffer *vip_buf, *node;
> @@ -374,7 +374,6 @@ static int stop_streaming(struct vb2_queue *vq)
> list_del(&vip_buf->list);
> }
> spin_unlock(&vip->lock);
> -   return 0;
>  }
>
>  static struct vb2_ops vip_video_qops = {
> diff --git a/drivers/media/platform/blackfin/bfin_capture.c 
> b/drivers/media/platform/blackfin/bfin_capture.c
> index 200bec9..16f643c 100644
> --- a/drivers/media/platform/blackfin/bfin_capture.c
> +++ b/drivers/media/platform/blackfin/bfin_capture.c
> @@ -427,15 +427,12 @@ static int bcap_start_streaming(struct vb2_queue *vq, 
> unsigned int count)
> return 0;
>  }
>
> -static int bcap_stop_streaming(struct vb2_queue *vq)
> +static void bcap_stop_streaming(struct vb2_queue *vq)
>  {
> struct bcap_device *bcap_dev = vb2_get_drv_priv(vq);
> struct ppi_if *ppi = bcap_dev->ppi;
>

Re: [REVIEW PATCH for v3.15 2/4] videobuf2-core: fix sparse errors.

2014-03-17 Thread Pawel Osciak
Hi Hans,
No issues with the patch, apart from one typo in a comment, but it may
not be worth the reupload.

On Sat, Mar 15, 2014 at 10:08 PM, Hans Verkuil  wrote:
> From: Hans Verkuil 
>
> Sparse generated a bunch of errors like this:
>
> drivers/media/v4l2-core/videobuf2-core.c:2045:25: error: incompatible types 
> in conditional expression (different base types)
> drivers/media/v4l2-core/videobuf2-core.c:136:17: error: incompatible types in 
> conditional expression (different base types)
> drivers/media/v4l2-core/videobuf2-core.c:151:17: error: incompatible types in 
> conditional expression (different base types)
> drivers/media/v4l2-core/videobuf2-core.c:168:25: error: incompatible types in 
> conditional expression (different base types)
> drivers/media/v4l2-core/videobuf2-core.c:183:17: error: incompatible types in 
> conditional expression (different base types)
> drivers/media/v4l2-core/videobuf2-core.c:185:9: error: incompatible types in 
> conditional expression (different base types)
> drivers/media/v4l2-core/videobuf2-core.c:385:25: error: incompatible types in 
> conditional expression (different base types)
> drivers/media/v4l2-core/videobuf2-core.c:1115:17: error: incompatible types 
> in conditional expression (different base types)
> drivers/media/v4l2-core/videobuf2-core.c:1268:33: error: incompatible types 
> in conditional expression (different base types)
> drivers/media/v4l2-core/videobuf2-core.c:1270:25: error: incompatible types 
> in conditional expression (different base types)
> drivers/media/v4l2-core/videobuf2-core.c:1315:17: error: incompatible types 
> in conditional expression (different base types)
> drivers/media/v4l2-core/videobuf2-core.c:1324:25: error: incompatible types 
> in conditional expression (different base types)
> drivers/media/v4l2-core/videobuf2-core.c:1396:25: error: incompatible types 
> in conditional expression (different base types)
> drivers/media/v4l2-core/videobuf2-core.c:1457:17: error: incompatible types 
> in conditional expression (different base types)
> drivers/media/v4l2-core/videobuf2-core.c:1482:17: error: incompatible types 
> in conditional expression (different base types)
> drivers/media/v4l2-core/videobuf2-core.c:1484:9: error: incompatible types in 
> conditional expression (different base types)
> drivers/media/v4l2-core/videobuf2-core.c:1523:17: error: incompatible types 
> in conditional expression (different base types)
> drivers/media/v4l2-core/videobuf2-core.c:1525:17: error: incompatible types 
> in conditional expression (different base types)
> drivers/media/v4l2-core/videobuf2-core.c:1815:17: error: incompatible types 
> in conditional expression (different base types)
> drivers/media/v4l2-core/videobuf2-core.c:1828:17: error: incompatible types 
> in conditional expression (different base types)
> drivers/media/v4l2-core/videobuf2-core.c:1914:25: error: incompatible types 
> in conditional expression (different base types)
> drivers/media/v4l2-core/videobuf2-core.c:1944:9: error: incompatible types in 
> conditional expression (different base types)
>
> These are caused by the call*op defines which do something like this:
>
> (ops->op) ? ops->op(args) : 0
>
> which is OK as long as op is not a void function, because in that case one 
> part
> of the conditional expression returns void, the other an integer. Hence the 
> sparse
> errors.
>
> I've replaced this by introducing three variants of the call_ macros:
> call_*op for int returns, call_void_*op for void returns and call_ptr_*op for
> pointer returns.
>
> That's the bad news. The good news is that the fail_*op macros could be 
> removed
> since the call_*op macros now have enough information to determine if the op
> succeeded or not and can increment the op counter only on success. This at 
> least
> makes it more robust w.r.t. future changes.
>
> Signed-off-by: Hans Verkuil 

Acked-by: Pawel Osciak 

> ---
>  drivers/media/v4l2-core/videobuf2-core.c | 211 
> +++
>  1 file changed, 130 insertions(+), 81 deletions(-)
>
> diff --git a/drivers/media/v4l2-core/videobuf2-core.c 
> b/drivers/media/v4l2-core/videobuf2-core.c
> index f9059bb..61149eb 100644
> --- a/drivers/media/v4l2-core/videobuf2-core.c
> +++ b/drivers/media/v4l2-core/videobuf2-core.c
> @@ -36,58 +36,133 @@ module_param(debug, int, 0644);
>  #ifdef CONFIG_VIDEO_ADV_DEBUG
>
>  /*
> - * If advanced debugging is on, then count how often each op is called,
> - * which can either be per-buffer or per-queue.
> + * If advanced debugging is on, then count how often each op is called
> + * sucessfully, which can either be per-buffer or per-queue.

s/sucessfully/successfully/

>   *
> - 

Re: [REVIEWv3 PATCH 03/17] vb2: fix PREPARE_BUF regression

2014-03-02 Thread Pawel Osciak
On Sat, Mar 1, 2014 at 2:42 AM, Hans Verkuil  wrote:
> Fix an incorrect test in vb2_internal_qbuf() where only DEQUEUED buffers
> are allowed. But PREPARED buffers are also OK.
>
> Introduced by commit 4138111a27859dcc56a5592c804dd16bb12a23d1
> ("vb2: simplify qbuf/prepare_buf by removing callback").
>
> Signed-off-by: Hans Verkuil 
> Acked-by: Laurent Pinchart 

Acked-by: Pawel Osciak 

> ---
>  drivers/media/v4l2-core/videobuf2-core.c | 8 ++--
>  1 file changed, 2 insertions(+), 6 deletions(-)
>
> diff --git a/drivers/media/v4l2-core/videobuf2-core.c 
> b/drivers/media/v4l2-core/videobuf2-core.c
> index f1a2857c..909f367 100644
> --- a/drivers/media/v4l2-core/videobuf2-core.c
> +++ b/drivers/media/v4l2-core/videobuf2-core.c
> @@ -1420,11 +1420,6 @@ static int vb2_internal_qbuf(struct vb2_queue *q, 
> struct v4l2_buffer *b)
> return ret;
>
> vb = q->bufs[b->index];
> -   if (vb->state != VB2_BUF_STATE_DEQUEUED) {
> -   dprintk(1, "%s(): invalid buffer state %d\n", __func__,
> -   vb->state);
> -   return -EINVAL;
> -   }
>
> switch (vb->state) {
> case VB2_BUF_STATE_DEQUEUED:
> @@ -1438,7 +1433,8 @@ static int vb2_internal_qbuf(struct vb2_queue *q, 
> struct v4l2_buffer *b)
> dprintk(1, "qbuf: buffer still being prepared\n");
> return -EINVAL;
> default:
> -   dprintk(1, "qbuf: buffer already in use\n");
> +   dprintk(1, "%s(): invalid buffer state %d\n", __func__,
> +   vb->state);
> return -EINVAL;
> }
>
> --
> 1.9.rc1
>



-- 
Best regards,
Pawel Osciak
--
To unsubscribe from this list: send the line "unsubscribe linux-media" in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [REVIEWv3 PATCH 01/17] vb2: Check if there are buffers before streamon

2014-03-02 Thread Pawel Osciak
On Sat, Mar 1, 2014 at 2:41 AM, Hans Verkuil  wrote:
> From: Ricardo Ribalda Delgado 
>
> This patch adds a test preventing streamon() if there is no buffer
> ready.
>
> Without this patch, a user could call streamon() before
> preparing any buffer. This leads to a situation where if he calls
> close() before calling streamoff() the device is kept streaming.
>
> Signed-off-by: Ricardo Ribalda Delgado 
> Signed-off-by: Hans Verkuil 

Acked-by: Pawel Osciak 

> ---
>  drivers/media/v4l2-core/videobuf2-core.c | 5 +
>  1 file changed, 5 insertions(+)
>
> diff --git a/drivers/media/v4l2-core/videobuf2-core.c 
> b/drivers/media/v4l2-core/videobuf2-core.c
> index 5a5fb7f..a127925 100644
> --- a/drivers/media/v4l2-core/videobuf2-core.c
> +++ b/drivers/media/v4l2-core/videobuf2-core.c
> @@ -1776,6 +1776,11 @@ static int vb2_internal_streamon(struct vb2_queue *q, 
> enum v4l2_buf_type type)
> return 0;
> }
>
> +   if (!q->num_buffers) {
> +   dprintk(1, "streamon: no buffers have been allocated\n");
> +   return -EINVAL;
> +   }
> +
> /*
>  * If any buffers were queued before streamon,
>  * we can now pass them to driver for processing.
> --
> 1.9.rc1
>



-- 
Best regards,
Pawel Osciak
--
To unsubscribe from this list: send the line "unsubscribe linux-media" in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [RFCv3 PATCH 08/10] vb2: only call start_streaming if sufficient buffers are queued

2014-02-13 Thread Pawel Osciak
atic int vpfe_reqbufs(struct file *file, void *priv,
> q->type = req_buf->type;
> q->io_modes = VB2_MMAP | VB2_USERPTR;
> q->drv_priv = fh;
> +   q->min_buffers_needed = 1;
> q->ops = &video_qops;
> q->mem_ops = &vb2_dma_contig_memops;
> q->buf_struct_size = sizeof(struct vpfe_cap_buffer);
> diff --git a/include/media/videobuf2-core.h b/include/media/videobuf2-core.h
> index adaffed..2ada71b 100644
> --- a/include/media/videobuf2-core.h
> +++ b/include/media/videobuf2-core.h
> @@ -348,20 +348,24 @@ struct v4l2_fh;
>   * @gfp_flags: additional gfp flags used when allocating the buffers.
>   * Typically this is 0, but it may be e.g. GFP_DMA or __GFP_DMA32
>   * to force the buffer allocation to a specific memory zone.
> + * @min_buffers_needed: the minimum number of buffers needed before
> + * start_streaming() can be called. Used when a DMA engine
> + * cannot be started unless at least this number of buffers
> + * have been queued into the driver.
>   *
>   * @memory:current memory type used
>   * @bufs:  videobuf buffer structures
>   * @num_buffers: number of allocated/used buffers
>   * @queued_list: list of buffers currently queued from userspace
> + * @queued_count: number of buffers queued and ready for streaming.
>   * @owned_by_drv_count: number of buffers owned by the driver
>   * @done_list: list of buffers ready to be dequeued to userspace
>   * @done_lock: lock to protect done_list list
>   * @done_wq:   waitqueue for processes waiting for buffers ready to be 
> dequeued
>   * @alloc_ctx: memory type/allocator-specific contexts for each plane
>   * @streaming: current streaming state
> - * @retry_start_streaming: start_streaming() was called, but there were not 
> enough
> - * buffers queued. If set, then retry calling start_streaming 
> when
> - * queuing a new buffer.
> + * @start_streaming_called: start_streaming() was called successfully and we
> + * started streaming.
>   * @fileio:file io emulator internal data, used only if emulator is 
> active
>   */
>  struct vb2_queue {
> @@ -377,6 +381,7 @@ struct vb2_queue {
> unsigned intbuf_struct_size;
> u32 timestamp_type;
> gfp_t   gfp_flags;
> +   u32 min_buffers_needed;

Perhaps add a WARN_ON or even clamp this if queue_setup requests less
buffers than this?

>
>  /* private: internal use only */
> enum v4l2_memorymemory;
> @@ -384,6 +389,7 @@ struct vb2_queue {
> unsigned intnum_buffers;
>
> struct list_headqueued_list;
> +   unsigned intqueued_count;
>
> atomic_towned_by_drv_count;
> struct list_headdone_list;
> @@ -394,7 +400,7 @@ struct vb2_queue {
> unsigned intplane_sizes[VIDEO_MAX_PLANES];
>
> unsigned intstreaming:1;
> -   unsigned intretry_start_streaming:1;
> +   unsigned intstart_streaming_called:1;
>
> struct vb2_fileio_data  *fileio;
>
> --
> 1.8.4.rc3
>



-- 
Best regards,
Pawel Osciak
--
To unsubscribe from this list: send the line "unsubscribe linux-media" in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [RFCv3 PATCH 06/10] vb2: fix read/write regression

2014-02-13 Thread Pawel Osciak
On Thu, Feb 13, 2014 at 6:40 PM, Hans Verkuil  wrote:
> From: Hans Verkuil 
>
> Commit 88e268702bfba78448abd20a31129458707383aa ("vb2: Improve file I/O
> emulation to handle buffers in any order") broke read/write support if
> the size of the buffer being read/written is less than the size of the
> image.
>
> When the commit was tested originally I used qv4l2, which call read()
> with exactly the size of the image. But if you try 'cat /dev/video0'
> then it will fail and typically hang after reading two buffers.
>
> This patch fixes the behavior by adding a new buf_index field that
> contains the index of the field currently being filled/read, or it
> is num_buffers in which case a new buffer needs to be dequeued.
>
> Signed-off-by: Hans Verkuil 
> Cc: Andy Walls 
> ---
>  drivers/media/v4l2-core/videobuf2-core.c | 7 +--
>  1 file changed, 5 insertions(+), 2 deletions(-)
>
> diff --git a/drivers/media/v4l2-core/videobuf2-core.c 
> b/drivers/media/v4l2-core/videobuf2-core.c
> index 7766bf5..a3b4b4c 100644
> --- a/drivers/media/v4l2-core/videobuf2-core.c
> +++ b/drivers/media/v4l2-core/videobuf2-core.c
> @@ -2418,6 +2418,7 @@ struct vb2_fileio_data {
> struct v4l2_requestbuffers req;
> struct v4l2_buffer b;
> struct vb2_fileio_buf bufs[VIDEO_MAX_FRAME];
> +   unsigned int buf_index;
> unsigned int index;

The two index fields are now confusing, especially because there is no
documentation. Perhaps we could call index "cur_index" and also add
documentation please?

> unsigned int q_count;
> unsigned int dq_count;
> @@ -2519,6 +2520,7 @@ static int __vb2_init_fileio(struct vb2_queue *q, int 
> read)
> fileio->bufs[i].queued = 1;
> }
> fileio->index = q->num_buffers;
> +   fileio->buf_index = q->num_buffers;
> }
>
> /*
> @@ -2597,7 +2599,7 @@ static size_t __vb2_perform_fileio(struct vb2_queue *q, 
> char __user *data, size_
> /*
>  * Check if we need to dequeue the buffer.
>  */
> -   index = fileio->index;
> +   index = fileio->buf_index;
> if (index >= q->num_buffers) {
> /*
>  * Call vb2_dqbuf to get buffer back.
> @@ -2611,7 +2613,7 @@ static size_t __vb2_perform_fileio(struct vb2_queue *q, 
> char __user *data, size_
> return ret;
> fileio->dq_count += 1;
>
> -   index = fileio->b.index;
> +   fileio->buf_index = index = fileio->b.index;
> buf = &fileio->bufs[index];
>
> /*
> @@ -2689,6 +2691,7 @@ static size_t __vb2_perform_fileio(struct vb2_queue *q, 
> char __user *data, size_
> fileio->q_count += 1;
> if (fileio->index < q->num_buffers)
> fileio->index++;
> +   fileio->buf_index = fileio->index;
> }
>
> /*
> --
> 1.8.4.rc3
>



-- 
Best regards,
Pawel Osciak
--
To unsubscribe from this list: send the line "unsubscribe linux-media" in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [RFCv3 PATCH 07/10] vb2: rename queued_count to owned_by_drv_count

2014-02-13 Thread Pawel Osciak
On Thu, Feb 13, 2014 at 6:40 PM, Hans Verkuil  wrote:
> From: Hans Verkuil 
>
> 'queued_count' is a bit vague since it is not clear to which queue it
> refers to: the vb2 internal list of buffers or the driver-owned list
> of buffers.
>
> Rename to make it explicit.
>
> Signed-off-by: Hans Verkuil 

Acked-by: Pawel Osciak 

> ---
>  drivers/media/v4l2-core/videobuf2-core.c | 10 +-
>  include/media/videobuf2-core.h   |  4 ++--
>  2 files changed, 7 insertions(+), 7 deletions(-)
>
> diff --git a/drivers/media/v4l2-core/videobuf2-core.c 
> b/drivers/media/v4l2-core/videobuf2-core.c
> index a3b4b4c..6af76ee 100644
> --- a/drivers/media/v4l2-core/videobuf2-core.c
> +++ b/drivers/media/v4l2-core/videobuf2-core.c
> @@ -1071,7 +1071,7 @@ void vb2_buffer_done(struct vb2_buffer *vb, enum 
> vb2_buffer_state state)
> spin_lock_irqsave(&q->done_lock, flags);
> vb->state = state;
> list_add_tail(&vb->done_entry, &q->done_list);
> -   atomic_dec(&q->queued_count);
> +   atomic_dec(&q->owned_by_drv_count);
> spin_unlock_irqrestore(&q->done_lock, flags);
>
> /* Inform any processes that may be waiting for buffers */
> @@ -1402,7 +1402,7 @@ static void __enqueue_in_driver(struct vb2_buffer *vb)
> unsigned int plane;
>
> vb->state = VB2_BUF_STATE_ACTIVE;
> -   atomic_inc(&q->queued_count);
> +   atomic_inc(&q->owned_by_drv_count);
>
> /* sync buffers */
> for (plane = 0; plane < vb->num_planes; ++plane)
> @@ -1554,7 +1554,7 @@ static int vb2_start_streaming(struct vb2_queue *q)
> int ret;
>
> /* Tell the driver to start streaming */
> -   ret = call_qop(q, start_streaming, q, atomic_read(&q->queued_count));
> +   ret = call_qop(q, start_streaming, q, 
> atomic_read(&q->owned_by_drv_count));
> if (ret)
> fail_qop(q, start_streaming);
>
> @@ -1779,7 +1779,7 @@ int vb2_wait_for_all_buffers(struct vb2_queue *q)
> }
>
> if (!q->retry_start_streaming)
> -   wait_event(q->done_wq, !atomic_read(&q->queued_count));
> +   wait_event(q->done_wq, !atomic_read(&q->owned_by_drv_count));
> return 0;
>  }
>  EXPORT_SYMBOL_GPL(vb2_wait_for_all_buffers);
> @@ -1911,7 +1911,7 @@ static void __vb2_queue_cancel(struct vb2_queue *q)
>  * has not already dequeued before initiating cancel.
>  */
> INIT_LIST_HEAD(&q->done_list);
> -   atomic_set(&q->queued_count, 0);
> +   atomic_set(&q->owned_by_drv_count, 0);
> wake_up_all(&q->done_wq);
>
> /*
> diff --git a/include/media/videobuf2-core.h b/include/media/videobuf2-core.h
> index 82b7f0f..adaffed 100644
> --- a/include/media/videobuf2-core.h
> +++ b/include/media/videobuf2-core.h
> @@ -353,7 +353,7 @@ struct v4l2_fh;
>   * @bufs:  videobuf buffer structures
>   * @num_buffers: number of allocated/used buffers
>   * @queued_list: list of buffers currently queued from userspace
> - * @queued_count: number of buffers owned by the driver
> + * @owned_by_drv_count: number of buffers owned by the driver
>   * @done_list: list of buffers ready to be dequeued to userspace
>   * @done_lock: lock to protect done_list list
>   * @done_wq:   waitqueue for processes waiting for buffers ready to be 
> dequeued
> @@ -385,7 +385,7 @@ struct vb2_queue {
>
> struct list_headqueued_list;
>
> -   atomic_tqueued_count;
> +   atomic_towned_by_drv_count;
> struct list_headdone_list;
> spinlock_t  done_lock;
> wait_queue_head_t   done_wq;
> --
> 1.8.4.rc3
>



-- 
Best regards,
Pawel Osciak
--
To unsubscribe from this list: send the line "unsubscribe linux-media" in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [RFCv3 PATCH 05/10] vb2: fix buf_init/buf_cleanup call sequences

2014-02-13 Thread Pawel Osciak
d\n");
> +   fail_vb_qop(vb, buf_prepare);
> +   call_vb_qop(vb, buf_cleanup, vb);

Should we explicitly set mem_priv to NULL here? This is one the issues
I have with using mem_priv, it's hard to reason if it's ok to do
buf_cleanup and expect mem_priv to be NULL here always.
Could we please add that inited bool into vb2_buffer to make it simpler?

> +   goto err;
> +   }
> +
> return 0;
>  err:
> /* In case of errors, release planes that were already acquired */
> @@ -1420,11 +1459,6 @@ static int __buf_prepare(struct vb2_buffer *vb, const 
> struct v4l2_buffer *b)
> ret = -EINVAL;
> }
>
> -   if (!ret) {
> -   ret = call_vb_qop(vb, buf_prepare, vb);
> -   if (ret)
> -   fail_vb_qop(vb, buf_prepare);
> -   }
> if (ret)
> dprintk(1, "qbuf: buffer preparation failed: %d\n", ret);
> vb->state = ret ? VB2_BUF_STATE_DEQUEUED : VB2_BUF_STATE_PREPARED;
> --
> 1.8.4.rc3
>



-- 
Best regards,
Pawel Osciak
--
To unsubscribe from this list: send the line "unsubscribe linux-media" in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [RFCv3 PATCH 04/10] vb2: call buf_finish from __dqbuf

2014-02-13 Thread Pawel Osciak
On Thu, Feb 13, 2014 at 6:40 PM, Hans Verkuil  wrote:
> From: Hans Verkuil 
>
> This ensures that it is also called from queue_cancel, which also calls
> __dqbuf(). Without this change any time queue_cancel is called while
> streaming the buf_finish op will not be called and any driver cleanup
> will not happen.
>
> Signed-off-by: Hans Verkuil 

Acked-by: Pawel Osciak 

> ---
>  drivers/media/v4l2-core/videobuf2-core.c | 4 ++--
>  1 file changed, 2 insertions(+), 2 deletions(-)
>
> diff --git a/drivers/media/v4l2-core/videobuf2-core.c 
> b/drivers/media/v4l2-core/videobuf2-core.c
> index 1f037de..3756378 100644
> --- a/drivers/media/v4l2-core/videobuf2-core.c
> +++ b/drivers/media/v4l2-core/videobuf2-core.c
> @@ -1762,6 +1762,8 @@ static void __vb2_dqbuf(struct vb2_buffer *vb)
> if (vb->state == VB2_BUF_STATE_DEQUEUED)
> return;
>
> +   call_vb_qop(vb, buf_finish, vb);
> +
> vb->state = VB2_BUF_STATE_DEQUEUED;
>
> /* unmap DMABUF buffer */
> @@ -1787,8 +1789,6 @@ static int vb2_internal_dqbuf(struct vb2_queue *q, 
> struct v4l2_buffer *b, bool n
> if (ret < 0)
> return ret;
>
> -   call_vb_qop(vb, buf_finish, vb);
> -
> switch (vb->state) {
> case VB2_BUF_STATE_DONE:
> dprintk(3, "dqbuf: Returning done buffer\n");
> --
> 1.8.4.rc3
>



-- 
Best regards,
Pawel Osciak
--
To unsubscribe from this list: send the line "unsubscribe linux-media" in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [RFCv3 PATCH 03/10] vb2: add note that buf_finish can be called with !vb2_is_streaming()

2014-02-13 Thread Pawel Osciak
Thanks Hans.

Acked-by: Pawel Osciak 

On Thu, Feb 13, 2014 at 6:40 PM, Hans Verkuil  wrote:
> From: Hans Verkuil 
>
> Drivers need to be aware that buf_finish can be called when there is no
> streaming going on, so make a note of that.
>
> Also add a bunch of missing periods at the end of sentences.
>
> Signed-off-by: Hans Verkuil 
> ---
>  include/media/videobuf2-core.h | 44 
> ++
>  1 file changed, 23 insertions(+), 21 deletions(-)
>
> diff --git a/include/media/videobuf2-core.h b/include/media/videobuf2-core.h
> index f443ce0..82b7f0f 100644
> --- a/include/media/videobuf2-core.h
> +++ b/include/media/videobuf2-core.h
> @@ -34,49 +34,49 @@ struct vb2_fileio_data;
>   * usually will result in the allocator freeing the buffer (if
>   * no other users of this buffer are present); the buf_priv
>   * argument is the allocator private per-buffer structure
> - * previously returned from the alloc callback
> + * previously returned from the alloc callback.
>   * @get_userptr: acquire userspace memory for a hardware operation; used for
>   *  USERPTR memory types; vaddr is the address passed to the
>   *  videobuf layer when queuing a video buffer of USERPTR type;
>   *  should return an allocator private per-buffer structure
>   *  associated with the buffer on success, NULL on failure;
>   *  the returned private structure will then be passed as 
> buf_priv
> - *  argument to other ops in this structure
> + *  argument to other ops in this structure.
>   * @put_userptr: inform the allocator that a USERPTR buffer will no longer
> - *  be used
> + *  be used.
>   * @attach_dmabuf: attach a shared struct dma_buf for a hardware operation;
>   *used for DMABUF memory types; alloc_ctx is the alloc 
> context
>   *dbuf is the shared dma_buf; returns NULL on failure;
>   *allocator private per-buffer structure on success;
> - *this needs to be used for further accesses to the buffer
> + *this needs to be used for further accesses to the buffer.
>   * @detach_dmabuf: inform the exporter of the buffer that the current DMABUF
>   *buffer is no longer used; the buf_priv argument is the
>   *allocator private per-buffer structure previously returned
> - *from the attach_dmabuf callback
> + *from the attach_dmabuf callback.
>   * @map_dmabuf: request for access to the dmabuf from allocator; the 
> allocator
>   * of dmabuf is informed that this driver is going to use the
> - * dmabuf
> + * dmabuf.
>   * @unmap_dmabuf: releases access control to the dmabuf - allocator is 
> notified
> - *   that this driver is done using the dmabuf for now
> + *   that this driver is done using the dmabuf for now.
>   * @prepare:   called every time the buffer is passed from userspace to the
> - * driver, useful for cache synchronisation, optional
> + * driver, useful for cache synchronisation, optional.
>   * @finish:called every time the buffer is passed back from the driver
> - * to the userspace, also optional
> + * to the userspace, also optional.
>   * @vaddr: return a kernel virtual address to a given memory buffer
>   * associated with the passed private structure or NULL if no
> - * such mapping exists
> + * such mapping exists.
>   * @cookie:return allocator specific cookie for a given memory buffer
>   * associated with the passed private structure or NULL if not
> - * available
> + * available.
>   * @num_users: return the current number of users of a memory buffer;
>   * return 1 if the videobuf layer (or actually the driver using
> - * it) is the only user
> + * it) is the only user.
>   * @mmap:  setup a userspace mapping for a given memory buffer under
> - * the provided virtual memory region
> + * the provided virtual memory region.
>   *
>   * Required ops for USERPTR types: get_userptr, put_userptr.
>   * Required ops for MMAP types: alloc, put, num_users, mmap.
> - * Required ops for read/write access types: alloc, put, num_users, vaddr
> + * Required ops for read/write access types: alloc, put, num_users, vaddr.
>   * Required ops for DMABUF types: attach_dmabuf, detach_dmabuf, map_dmabuf,
>   *   unmap_dmabuf.
>   */
> @@ -258,27 +258,2

Re: [RFCv3 PATCH 02/10] vb2: change result code of buf_finish to void.

2014-02-13 Thread Pawel Osciak
Thanks!

vb2 parts:
Acked-by: Pawel Osciak 

others:
Reviewed-by: Pawel Osciak 

On Thu, Feb 13, 2014 at 6:40 PM, Hans Verkuil  wrote:
> From: Hans Verkuil 
>
> The buf_finish op should always work, so change the return type to void.
> Update the few drivers that use it. Note that buf_finish can be called
> both when the DMA is streaming and when it isn't (during queue_cancel).
> Update drivers to check that where appropriate.
>
> Signed-off-by: Hans Verkuil 
> ---
>  drivers/media/parport/bw-qcam.c |  6 --
>  drivers/media/pci/sta2x11/sta2x11_vip.c |  7 +++
>  drivers/media/platform/marvell-ccic/mcam-core.c |  3 +--
>  drivers/media/usb/pwc/pwc-if.c  | 16 +---
>  drivers/media/usb/uvc/uvc_queue.c   |  6 +++---
>  drivers/media/v4l2-core/videobuf2-core.c|  6 +-
>  drivers/staging/media/go7007/go7007-v4l2.c  |  3 +--
>  include/media/videobuf2-core.h  |  2 +-
>  8 files changed, 23 insertions(+), 26 deletions(-)
>
> diff --git a/drivers/media/parport/bw-qcam.c b/drivers/media/parport/bw-qcam.c
> index d12bd33..8d69bfb 100644
> --- a/drivers/media/parport/bw-qcam.c
> +++ b/drivers/media/parport/bw-qcam.c
> @@ -667,13 +667,16 @@ static void buffer_queue(struct vb2_buffer *vb)
> vb2_buffer_done(vb, VB2_BUF_STATE_DONE);
>  }
>
> -static int buffer_finish(struct vb2_buffer *vb)
> +static void buffer_finish(struct vb2_buffer *vb)
>  {
> struct qcam *qcam = vb2_get_drv_priv(vb->vb2_queue);
> void *vbuf = vb2_plane_vaddr(vb, 0);
> int size = vb->vb2_queue->plane_sizes[0];
> int len;
>
> +   if (!vb2_is_streaming(vb->vb2_queue))
> +   return;
> +
> mutex_lock(&qcam->lock);
> parport_claim_or_block(qcam->pdev);
>
> @@ -691,7 +694,6 @@ static int buffer_finish(struct vb2_buffer *vb)
> if (len != size)
> vb->state = VB2_BUF_STATE_ERROR;
> vb2_set_plane_payload(vb, 0, len);
> -   return 0;
>  }
>
>  static struct vb2_ops qcam_video_qops = {
> diff --git a/drivers/media/pci/sta2x11/sta2x11_vip.c 
> b/drivers/media/pci/sta2x11/sta2x11_vip.c
> index e5cfb6c..bb11443 100644
> --- a/drivers/media/pci/sta2x11/sta2x11_vip.c
> +++ b/drivers/media/pci/sta2x11/sta2x11_vip.c
> @@ -327,7 +327,7 @@ static void buffer_queue(struct vb2_buffer *vb)
> }
> spin_unlock(&vip->lock);
>  }
> -static int buffer_finish(struct vb2_buffer *vb)
> +static void buffer_finish(struct vb2_buffer *vb)
>  {
> struct sta2x11_vip *vip = vb2_get_drv_priv(vb->vb2_queue);
> struct vip_buffer *vip_buf = to_vip_buffer(vb);
> @@ -337,9 +337,8 @@ static int buffer_finish(struct vb2_buffer *vb)
> list_del_init(&vip_buf->list);
> spin_unlock(&vip->lock);
>
> -   vip_active_buf_next(vip);
> -
> -   return 0;
> +   if (vb2_is_streaming(vb->vb2_queue))
> +   vip_active_buf_next(vip);
>  }
>
>  static int start_streaming(struct vb2_queue *vq, unsigned int count)
> diff --git a/drivers/media/platform/marvell-ccic/mcam-core.c 
> b/drivers/media/platform/marvell-ccic/mcam-core.c
> index 32fab30..8b34c48 100644
> --- a/drivers/media/platform/marvell-ccic/mcam-core.c
> +++ b/drivers/media/platform/marvell-ccic/mcam-core.c
> @@ -1238,7 +1238,7 @@ static int mcam_vb_sg_buf_prepare(struct vb2_buffer *vb)
> return 0;
>  }
>
> -static int mcam_vb_sg_buf_finish(struct vb2_buffer *vb)
> +static void mcam_vb_sg_buf_finish(struct vb2_buffer *vb)
>  {
> struct mcam_camera *cam = vb2_get_drv_priv(vb->vb2_queue);
> struct sg_table *sg_table = vb2_dma_sg_plane_desc(vb, 0);
> @@ -1246,7 +1246,6 @@ static int mcam_vb_sg_buf_finish(struct vb2_buffer *vb)
> if (sg_table)
> dma_unmap_sg(cam->dev, sg_table->sgl,
> sg_table->nents, DMA_FROM_DEVICE);
> -   return 0;
>  }
>
>  static void mcam_vb_sg_buf_cleanup(struct vb2_buffer *vb)
> diff --git a/drivers/media/usb/pwc/pwc-if.c b/drivers/media/usb/pwc/pwc-if.c
> index abf365a..b9c9f10 100644
> --- a/drivers/media/usb/pwc/pwc-if.c
> +++ b/drivers/media/usb/pwc/pwc-if.c
> @@ -614,17 +614,19 @@ static int buffer_prepare(struct vb2_buffer *vb)
> return 0;
>  }
>
> -static int buffer_finish(struct vb2_buffer *vb)
> +static void buffer_finish(struct vb2_buffer *vb)
>  {
> struct pwc_device *pdev = vb2_get_drv_priv(vb->vb2_queue);
> struct pwc_frame_buf *buf = container_of(vb, struct pwc_frame_buf, 
> vb);
>
> -   /*
> -* Application has call

Re: [RFCv2 PATCH 01/10] vb2: add debugging code to check for unbalanced ops.

2014-02-13 Thread Pawel Osciak
Hi Hans,
Thanks for the patch. I'm really happy to see this, it's a great idea
and it will be very useful.

Two comments:
- What do you think about moving the debug stuff to something like
videobuf2-debug.{c,h} instead?
- At this point vb2_buffer_done() shouldn't be required to be balanced
with buf_queue(). I know later patches in this series will require it,
but at this point it's not true. Perhaps we should move this to the
8th patch or after it? I don't feel too strong about this though.

One more nit inline.

But in general:

Acked-by: Pawel Osciak 


On Thu, Feb 6, 2014 at 8:02 PM, Hans Verkuil  wrote:
> From: Hans Verkuil 
>
> When a vb2_queue is freed check if all the mem_ops and queue ops were 
> balanced.
> So the number of calls to e.g. buf_finish has to match the number of calls to
> buf_prepare, etc.
>
> This code is only enabled if CONFIG_VIDEO_ADV_DEBUG is set.
>
> Signed-off-by: Hans Verkuil 
> ---
>  drivers/media/v4l2-core/videobuf2-core.c | 233 
> ---
>  include/media/videobuf2-core.h   |  43 ++
>  2 files changed, 226 insertions(+), 50 deletions(-)
>
> diff --git a/drivers/media/v4l2-core/videobuf2-core.c 
> b/drivers/media/v4l2-core/videobuf2-core.c
> index 5a5fb7f..07b58bd 100644
> --- a/drivers/media/v4l2-core/videobuf2-core.c
> +++ b/drivers/media/v4l2-core/videobuf2-core.c
> @@ -33,12 +33,63 @@ module_param(debug, int, 0644);
> printk(KERN_DEBUG "vb2: " fmt, ## arg); \
> } while (0)
>
> -#define call_memop(q, op, args...) \
> -   (((q)->mem_ops->op) ?   \
> -   ((q)->mem_ops->op(args)) : 0)
> +#ifdef CONFIG_VIDEO_ADV_DEBUG
> +
> +/*
> + * If advanced debugging is on, then count how often each op is called,
> + * which can either be per-buffer or per-queue.
> + *
> + * If the op failed then the 'fail_' variant is called to decrease the
> + * counter. That makes it easy to check that the 'init' and 'cleanup'
> + * (and variations thereof) stay balanced.
> + */
> +
> +#define call_memop(vb, op, args...)\
> +({ \
> +   struct vb2_queue *_q = (vb)->vb2_queue; \
> +   dprintk(2, "call_memop(%p, %d, %s)%s\n",\
> +   _q, (vb)->v4l2_buf.index, #op,  \
> +   _q->mem_ops->op ? "" : " (nop)");   \
> +   (vb)->cnt_mem_ ## op++; \
> +   _q->mem_ops->op ? _q->mem_ops->op(args) : 0;\
> +})
> +#define fail_memop(vb, op) ((vb)->cnt_mem_ ## op--)
> +
> +#define call_qop(q, op, args...)   \
> +({ \
> +   dprintk(2, "call_qop(%p, %s)%s\n", q, #op,  \
> +   (q)->ops->op ? "" : " (nop)");  \
> +   (q)->cnt_ ## op++;  \
> +   (q)->ops->op ? (q)->ops->op(args) : 0;  \
> +})
> +#define fail_qop(q, op) ((q)->cnt_ ## op--)
> +
> +#define call_vb_qop(vb, op, args...)   \
> +({ \
> +   struct vb2_queue *_q = (vb)->vb2_queue; \
> +   dprintk(2, "call_vb_qop(%p, %d, %s)%s\n",   \
> +   _q, (vb)->v4l2_buf.index, #op,  \
> +   _q->ops->op ? "" : " (nop)");   \
> +   (vb)->cnt_ ## op++; \
> +   _q->ops->op ? _q->ops->op(args) : 0;\
> +})
> +#define fail_vb_qop(vb, op) ((vb)->cnt_ ## op--)
> +
> +#else
> +
> +#define call_memop(vb, op, args...)\
> +   ((vb)->vb2_queue->mem_ops->op ? (vb)->vb2_queue->mem_ops->op(args) : 
> 0)
> +#define fail_memop(vb, op)
>
>  #define call_qop(q, op, args...)   \
> -   (((q)->ops->op) ? ((q)->ops->op(args)) : 0)
> +   ((q)->ops->op ? (q)->ops->op(args) : 0)
> +#define fail_qop(q, op)
> +
> +#define call_vb_qop(vb, op, args...)   \
> +  

Re: [PATCH] CHROMIUM: s5p-mfc: add controls to set vp8 enc profile

2013-12-09 Thread Pawel Osciak
Hi Arun,

On Mon, Dec 9, 2013 at 10:16 PM, Arun Kumar K  wrote:
> Add v4l2 controls to set desired profile for VP8 encoder.
> Acceptable levels for VP8 encoder are
> 0: Version 0
> 1: Version 1
> 2: Version 2
> 3: Version 3
>
> Signed-off-by: Pawel Osciak 

Sorry, but I'm not the author of this patch, Kiran is. I think the
confusion comes from the fact that I committed it to Chromium tree. I
think Kiran's sign-off should go first and the patch should contain:
"From: Kiran AVND "

Thanks,
Pawel

> Signed-off-by: Kiran AVND 
> Signed-off-by: Arun Kumar K 
> ---
> This patch is rebased over another VP8 control patch from me:
> https://linuxtv.org/patch/20733/
> ---
>  Documentation/DocBook/media/v4l/controls.xml|9 +
>  drivers/media/platform/s5p-mfc/s5p_mfc_common.h |1 +
>  drivers/media/platform/s5p-mfc/s5p_mfc_enc.c|   11 +++
>  drivers/media/platform/s5p-mfc/s5p_mfc_opr_v6.c |6 ++
>  drivers/media/v4l2-core/v4l2-ctrls.c|8 
>  include/uapi/linux/v4l2-controls.h  |1 +
>  6 files changed, 32 insertions(+), 4 deletions(-)
>
> diff --git a/Documentation/DocBook/media/v4l/controls.xml 
> b/Documentation/DocBook/media/v4l/controls.xml
> index e4db4ac..c1f7544 100644
> --- a/Documentation/DocBook/media/v4l/controls.xml
> +++ b/Documentation/DocBook/media/v4l/controls.xml
> @@ -3193,6 +3193,15 @@ V4L2_CID_MPEG_VIDEO_VPX_GOLDEN_FRAME_REF_PERIOD as a 
> golden frame.
>   Quantization parameter for a P 
> frame for VP8.
>   
>
> + 
> + 
> +spanname="id">V4L2_CID_MPEG_VIDEO_VPX_PROFILE 
> +   integer
> + 
> + Select the desired profile for VP8 
> encoder.
> +Acceptable values are 0, 1, 2 and 3 corresponding to encoder versions 0, 1, 
> 2 and 3.
> + 
> +
>
>  
>
> diff --git a/drivers/media/platform/s5p-mfc/s5p_mfc_common.h 
> b/drivers/media/platform/s5p-mfc/s5p_mfc_common.h
> index d91f757..797e61d 100644
> --- a/drivers/media/platform/s5p-mfc/s5p_mfc_common.h
> +++ b/drivers/media/platform/s5p-mfc/s5p_mfc_common.h
> @@ -426,6 +426,7 @@ struct s5p_mfc_vp8_enc_params {
> u8 rc_max_qp;
> u8 rc_frame_qp;
> u8 rc_p_frame_qp;
> +   u8 profile;
>  };
>
>  /**
> diff --git a/drivers/media/platform/s5p-mfc/s5p_mfc_enc.c 
> b/drivers/media/platform/s5p-mfc/s5p_mfc_enc.c
> index 33e8ae3..ec0581c 100644
> --- a/drivers/media/platform/s5p-mfc/s5p_mfc_enc.c
> +++ b/drivers/media/platform/s5p-mfc/s5p_mfc_enc.c
> @@ -650,6 +650,14 @@ static struct mfc_control controls[] = {
> .step = 1,
> .default_value = 10,
> },
> +   {
> +   .id = V4L2_CID_MPEG_VIDEO_VPX_PROFILE,
> +   .type = V4L2_CTRL_TYPE_INTEGER_MENU,
> +   .minimum = 0,
> +   .maximum = 3,
> +   .step = 1,
> +   .default_value = 0,
> +   },
>  };
>
>  #define NUM_CTRLS ARRAY_SIZE(controls)
> @@ -1601,6 +1609,9 @@ static int s5p_mfc_enc_s_ctrl(struct v4l2_ctrl *ctrl)
> case V4L2_CID_MPEG_VIDEO_VPX_P_FRAME_QP:
> p->codec.vp8.rc_p_frame_qp = ctrl->val;
> break;
> +   case V4L2_CID_MPEG_VIDEO_VPX_PROFILE:
> +   p->codec.vp8.profile = ctrl->val;
> +   break;
> default:
> v4l2_err(&dev->v4l2_dev, "Invalid control, id=%d, val=%d\n",
> ctrl->id, ctrl->val);
> diff --git a/drivers/media/platform/s5p-mfc/s5p_mfc_opr_v6.c 
> b/drivers/media/platform/s5p-mfc/s5p_mfc_opr_v6.c
> index b4886d6..f6ff2db 100644
> --- a/drivers/media/platform/s5p-mfc/s5p_mfc_opr_v6.c
> +++ b/drivers/media/platform/s5p-mfc/s5p_mfc_opr_v6.c
> @@ -1197,10 +1197,8 @@ static int s5p_mfc_set_enc_params_vp8(struct 
> s5p_mfc_ctx *ctx)
> reg |= ((p->num_b_frame & 0x3) << 16);
> WRITEL(reg, S5P_FIMV_E_GOP_CONFIG_V6);
>
> -   /* profile & level */
> -   reg = 0;
> -   /** profile */
> -   reg |= (0x1 << 4);
> +   /* profile - 0 ~ 3 */
> +   reg = p_vp8->profile & 0x3;
> WRITEL(reg, S5P_FIMV_E_PICTURE_PROFILE_V6);
>
> /* rate control config. */
> diff --git a/drivers/media/v4l2-core/v4l2-ctrls.c 
> b/drivers/media/v4l2-core/v4l2-ctrls.c
> index 20840df..5069dd2 100644
> --- a/drivers/media/v4l2-core/v4l2-ctrls.c
> +++ b/drivers/media/v4l2-core/v4l2-ctrls.c
> @@ -575,11 +575,17 @@ const s64 *v4l2_c

Re: [media-workshop] Kernel Summit Media Mini-summit attendees on Oct 23 in Edinburgh

2013-10-10 Thread Pawel Osciak
I'm sorry everyone, I unfortunately won't be able to make it after all
due to schedule conflicts.
Best regards,
Pawel

On Fri, Sep 20, 2013 at 7:50 PM, Mauro Carvalho Chehab
 wrote:
> Em Fri, 20 Sep 2013 09:59:28 +0200
> Hans de Goede  escreveu:
>
>> Hi,
>>
>> Sorry for replying in the midst of the thread I deleted
>> the beginning before realizing I should respond.
>>
>> >>>>> On 09/17/13 19:08, Mauro Carvalho Chehab wrote:
>> >>>>>> Hi,
>> >>>>>>
>> >>>>>> I'm trying to consolidate the list of interested people on
>> >>>>>> participating at this year's the media mini-summit. From what I got
>> >>>>>> from the discussions, we have, so far:
>> >>>>>>
>> >>>>>>Benjamin Gaignard 
>> >>>>>>Guennadi Liakhovetski 
>> >>>>>>Hans Verkuil 
>> >>>>>>Hugues FRUCHET 
>> >>>>>>Laurent Pinchart 
>> >>>>>>Mauro Carvalho Chehab 
>> >>>>>>Michael Krufky 
>> >>>>>>Oliver Schinagl 
>> >>>>>>Pawel Osciak 
>> >>>>>>Peter Senna Tschudin 
>> >>>>>>Ricardo Ribalda Delgado 
>> >>>>>>Sakari Ailus 
>> >>>>>>
>> >>>>>> Please let me know if I'm missing someone, or if one of the above
>> >>>>>> won't be able to go to the meeting, as my plan is to send the
>> >>>>>> invitations tomorrow.
>>
>> I'll be in Edinburgh for kvm-forum and I would like to attend the meeting,
>> at least the parts about the userspace libraries.
>
> Ok.
>
> I'll add your name to the list of atendees.
>
> Regards,
> Mauro
>
>>
>> Regards,
>>
>> Hans (de Goede)
>>
>> ___
>> media-workshop mailing list
>> media-works...@linuxtv.org
>> http://www.linuxtv.org/cgi-bin/mailman/listinfo/media-workshop
>
>
>
>
> Cheers,
> Mauro
> --
> To unsubscribe from this list: send the line "unsubscribe linux-media" in
> the body of a message to majord...@vger.kernel.org
> More majordomo info at  http://vger.kernel.org/majordomo-info.html
--
To unsubscribe from this list: send the line "unsubscribe linux-media" in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [PATCH] [media] videobuf2-core: call __setup_offsets only for mmap memory type

2013-09-29 Thread Pawel Osciak
Thanks Philipp.

Acked-by: Pawel Osciak 


On Thu, Sep 19, 2013 at 5:30 PM, Philipp Zabel  wrote:
> Hi Pawel,
>
> Am Donnerstag, den 19.09.2013, 16:54 +0900 schrieb Pawel Osciak:
>> On Thu, Sep 19, 2013 at 4:37 PM, Philipp Zabel  
>> wrote:
>> > __setup_offsets fills the v4l2_planes' mem_offset fields, which is only 
>> > valid
>> > for V4L2_MEMORY_MMAP type buffers. For V4L2_MEMORY_DMABUF and _USERPTR 
>> > buffers,
>> > this incorrectly overwrites the fd and userptr fields.
>>
>> I'm not particularly against this change, but I'm curious if anything
>> that you were doing was broken by this call? The buffers are created
>> here, so their fields don't contain anything that could be overwritten
>> (although keeping them at 0 is preferable).
>
> nothing was actually broken, but even though the spec doesn't say
> anything about the QUERYBUF return values in the DMABUF/USERPTR cases,
> setting them to some random initial value doesn't seem right.
>
> Maybe the documentation could be amended to mention fd and userptr,
> although in this case the fd should probably be set to -1 initially.
> QUERYBUF could then be used to find free slots.
>
> regards
> Philipp
>



-- 
Best regards,
Pawel Osciak
--
To unsubscribe from this list: send the line "unsubscribe linux-media" in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [PATCH] [media] videobuf2-core: call __setup_offsets only for mmap memory type

2013-09-19 Thread Pawel Osciak
On Thu, Sep 19, 2013 at 4:37 PM, Philipp Zabel  wrote:
> __setup_offsets fills the v4l2_planes' mem_offset fields, which is only valid
> for V4L2_MEMORY_MMAP type buffers. For V4L2_MEMORY_DMABUF and _USERPTR 
> buffers,
> this incorrectly overwrites the fd and userptr fields.

I'm not particularly against this change, but I'm curious if anything
that you were doing was broken by this call? The buffers are created
here, so their fields don't contain anything that could be overwritten
(although keeping them at 0 is preferable).

>
> Reported-by: Michael Olbrich 
> Signed-off-by: Philipp Zabel 
> ---
>  drivers/media/v4l2-core/videobuf2-core.c | 3 ++-
>  1 file changed, 2 insertions(+), 1 deletion(-)
>
> diff --git a/drivers/media/v4l2-core/videobuf2-core.c 
> b/drivers/media/v4l2-core/videobuf2-core.c
> index 9c865da..95a798e 100644
> --- a/drivers/media/v4l2-core/videobuf2-core.c
> +++ b/drivers/media/v4l2-core/videobuf2-core.c
> @@ -241,7 +241,8 @@ static int __vb2_queue_alloc(struct vb2_queue *q, enum 
> v4l2_memory memory,
> q->bufs[q->num_buffers + buffer] = vb;
> }
>
> -   __setup_offsets(q, buffer);
> +   if (memory == V4L2_MEMORY_MMAP)
> +   __setup_offsets(q, buffer);
>
> dprintk(1, "Allocated %d buffers, %d plane(s) each\n",
> buffer, num_planes);
> --
> 1.8.4.rc3
>



-- 
Best regards,
Pawel Osciak
--
To unsubscribe from this list: send the line "unsubscribe linux-media" in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [PATCH v1 16/19] v4l: Add encoding camera controls.

2013-09-11 Thread Pawel Osciak
On Tue, Sep 10, 2013 at 6:17 PM, Hans Verkuil  wrote:
> On Mon 9 September 2013 11:09:57 Sylwester Nawrocki wrote:
>> On 09/09/2013 11:00 AM, Kamil Debski wrote:
>> [...]
>>  We have QP controls separately for H264, H263 and MPEG4. Why is that?
>>  Which one should I use for VP8? Shouldn't we unify them instead?
>> >>>
>> >>> I can't quite remember the details, so I've CCed Kamil since he added
>> >> those controls.
>> >>> At least the H264 QP controls are different from the others as they
>> >>> have a different range. What's the range for VP8?
>> >>
>> >> Yes, it differs, 0-127.
>> >> But I feel this is pretty unfortunate, is it a good idea to multiply
>> >> controls to have one per format when they have different ranges
>> >> depending on the selected format in general? Perhaps a custom handler
>> >> would be better?
>> >>
>> >>> I'm not sure why the H263/MPEG4 controls weren't unified: it might be
>> >>> that since the
>> >>> H264 range was different we decided to split it up per codec. But I
>> >>> seem to remember that there was another reason as well.
>> >
>> > We had a discussion about this on linux-media mailing list. It can be found
>> > here:
>> > http://comments.gmane.org/gmane.linux.drivers.video-input-infrastructure/32606
>> > In short, it is a mix of two reasons: one - the valid range is different 
>> > for
>> > different formats and second - implementing controls which have different
>> > min/max values depending on format was not easy.
>>
>> Hmm, these seem pretty vague reasons. And since some time we have support
>> for dynamic control range update [1].
>
> I don't think we should change this. We chose to go with separate controls,
> and we should stick with that. We might do it differently today, but it's
> not a big deal.

I guess I can't reuse MPEG controls as you suggested then. But I could
either create a new VPX class, or keep these ones in camera class and
create separate VPX class later for codecs. It's technically possible
for UVC to have different constraints on some controls though, even if
the codec is the same, potentially creating more confusion...


>
> Regards,
>
> Hans
>
>>
>> > On the one hand I am thinking that now, when we have more codecs, it would
>> > be better
>> > to have a single control, on the other hand what about backward
>> > compatibility?
>> > Is there a graceful way to merge H263 and H264 QP controls?
>>
>> [1] https://patchwork.linuxtv.org/patch/16436/
>>
>> --
>> Regards,
>> Sylwester
>> --
>> To unsubscribe from this list: send the line "unsubscribe linux-media" in
>> the body of a message to majord...@vger.kernel.org
>> More majordomo info at  http://vger.kernel.org/majordomo-info.html
>>
--
To unsubscribe from this list: send the line "unsubscribe linux-media" in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [PATCH v1 16/19] v4l: Add encoding camera controls.

2013-09-09 Thread Pawel Osciak
On Mon, Sep 9, 2013 at 4:52 PM, Hans Verkuil  wrote:
> On 09/09/2013 05:48 AM, Pawel Osciak wrote:
>> Hi Hans,
>> Thanks for the comments, one question inline.
>>
>> On Fri, Aug 30, 2013 at 3:48 PM, Hans Verkuil  wrote:
>>> On 08/30/2013 04:17 AM, Pawel Osciak wrote:
>>>> Add defines for controls found in UVC 1.5 encoding cameras.
>>>>
>>>> Signed-off-by: Pawel Osciak 
>>>> ---
>>>>  drivers/media/v4l2-core/v4l2-ctrls.c | 29 +
>>>>  include/uapi/linux/v4l2-controls.h   | 31 +++
>>>>  2 files changed, 60 insertions(+)
>>>>
>>>> diff --git a/drivers/media/v4l2-core/v4l2-ctrls.c 
>>>> b/drivers/media/v4l2-core/v4l2-ctrls.c
>>>> index c3f0803..0b3a632 100644
>>>> --- a/drivers/media/v4l2-core/v4l2-ctrls.c
>>>> +++ b/drivers/media/v4l2-core/v4l2-ctrls.c
>>>> @@ -781,6 +781,35 @@ const char *v4l2_ctrl_get_name(u32 id)
>>>>   case V4L2_CID_AUTO_FOCUS_STATUS:return "Auto Focus, Status";
>>>>   case V4L2_CID_AUTO_FOCUS_RANGE: return "Auto Focus, Range";
>>>>
>>>> + case V4L2_CID_ENCODER_MIN_FRAME_INTERVAL: return "Encoder, min. 
>>>> frame interval";
>>>> + case V4L2_CID_ENCODER_RATE_CONTROL_MODE: return "Encoder, rate 
>>>> control mode";
>>>> + case V4L2_CID_ENCODER_AVERAGE_BITRATE:  return "Encoder, average 
>>>> bitrate";
>>>> + case V4L2_CID_ENCODER_CPB_SIZE: return "Encoder, CPB size";
>>>> + case V4L2_CID_ENCODER_PEAK_BIT_RATE:return "Encoder, peak bit 
>>>> rate";
>>>> + case V4L2_CID_ENCODER_QP_PARAM_I:   return "Encoder, QP param 
>>>> for I frames";
>>>> + case V4L2_CID_ENCODER_QP_PARAM_P:   return "Encoder, QP param 
>>>> for P frames";
>>>> + case V4L2_CID_ENCODER_QP_PARAM_BG:  return "Encoder, QP param 
>>>> for B/G frames";
>>>
>>> A lot of these exist already. E.g. V4L2_CID_MPEG_VIDEO_MPEG4_I/P/B_FRAME_QP.
>>>
>>> Samsung added support for many of these parameters for their MFC encoder 
>>> (including
>>> VP8 support) so you should use them as well. As mentioned in 
>>> v4l2-controls.h the
>>> MPEG part of the control name is historical. Interpret it as 'CODEC', not 
>>> MPEG.
>>>
>>
>> We have QP controls separately for H264, H263 and MPEG4. Why is that?
>> Which one should I use for VP8? Shouldn't we unify them instead?
>
> I can't quite remember the details, so I've CCed Kamil since he added those 
> controls.
> At least the H264 QP controls are different from the others as they have a 
> different
> range. What's the range for VP8?
>

Yes, it differs, 0-127.
But I feel this is pretty unfortunate, is it a good idea to multiply
controls to have one per format when they have different ranges
depending on the selected format in general? Perhaps a custom handler
would be better?

> I'm not sure why the H263/MPEG4 controls weren't unified: it might be that 
> since the
> H264 range was different we decided to split it up per codec. But I seem to 
> remember
> that there was another reason as well.
>
> Regards,
>
> Hans
--
To unsubscribe from this list: send the line "unsubscribe linux-media" in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [PATCH v1 16/19] v4l: Add encoding camera controls.

2013-09-08 Thread Pawel Osciak
Hi Hans,
Thanks for the comments, one question inline.

On Fri, Aug 30, 2013 at 3:48 PM, Hans Verkuil  wrote:
> On 08/30/2013 04:17 AM, Pawel Osciak wrote:
>> Add defines for controls found in UVC 1.5 encoding cameras.
>>
>> Signed-off-by: Pawel Osciak 
>> ---
>>  drivers/media/v4l2-core/v4l2-ctrls.c | 29 +
>>  include/uapi/linux/v4l2-controls.h   | 31 +++
>>  2 files changed, 60 insertions(+)
>>
>> diff --git a/drivers/media/v4l2-core/v4l2-ctrls.c 
>> b/drivers/media/v4l2-core/v4l2-ctrls.c
>> index c3f0803..0b3a632 100644
>> --- a/drivers/media/v4l2-core/v4l2-ctrls.c
>> +++ b/drivers/media/v4l2-core/v4l2-ctrls.c
>> @@ -781,6 +781,35 @@ const char *v4l2_ctrl_get_name(u32 id)
>>   case V4L2_CID_AUTO_FOCUS_STATUS:return "Auto Focus, Status";
>>   case V4L2_CID_AUTO_FOCUS_RANGE: return "Auto Focus, Range";
>>
>> + case V4L2_CID_ENCODER_MIN_FRAME_INTERVAL: return "Encoder, min. frame 
>> interval";
>> + case V4L2_CID_ENCODER_RATE_CONTROL_MODE: return "Encoder, rate control 
>> mode";
>> + case V4L2_CID_ENCODER_AVERAGE_BITRATE:  return "Encoder, average 
>> bitrate";
>> + case V4L2_CID_ENCODER_CPB_SIZE: return "Encoder, CPB size";
>> + case V4L2_CID_ENCODER_PEAK_BIT_RATE:return "Encoder, peak bit 
>> rate";
>> + case V4L2_CID_ENCODER_QP_PARAM_I:   return "Encoder, QP param for 
>> I frames";
>> + case V4L2_CID_ENCODER_QP_PARAM_P:   return "Encoder, QP param for 
>> P frames";
>> + case V4L2_CID_ENCODER_QP_PARAM_BG:  return "Encoder, QP param for 
>> B/G frames";
>
> A lot of these exist already. E.g. V4L2_CID_MPEG_VIDEO_MPEG4_I/P/B_FRAME_QP.
>
> Samsung added support for many of these parameters for their MFC encoder 
> (including
> VP8 support) so you should use them as well. As mentioned in v4l2-controls.h 
> the
> MPEG part of the control name is historical. Interpret it as 'CODEC', not 
> MPEG.
>

We have QP controls separately for H264, H263 and MPEG4. Why is that?
Which one should I use for VP8? Shouldn't we unify them instead?


>> + case V4L2_CID_ENCODER_NUM_GDR_FRAMES:   return "Encoder, number of GDR 
>> frames";
>> + case V4L2_CID_ENCODER_LTR_BUFFER_CONTROL: return "Encoder, LTR buffer 
>> control";
>> + case V4L2_CID_ENCODER_LTR_BUFFER_TRUST_MODE: return "Encoder, LTR 
>> buffer trust mode";
>> + case V4L2_CID_ENCODER_LTR_PICTURE_POSITION: return "Encoder, LTR 
>> picture position";
>> + case V4L2_CID_ENCODER_LTR_PICTURE_MODE: return "Encoder, LTR picture 
>> mode";
>> + case V4L2_CID_ENCODER_LTR_VALIDATION:   return "Encoder, LTR 
>> validation";
>> + case V4L2_CID_ENCODER_MIN_QP:   return "Encoder, minimum QP 
>> param";
>> + case V4L2_CID_ENCODER_MAX_QP:   return "Encoder, maximum QP 
>> param";
>> + case V4L2_CID_ENCODER_SYNC_FRAME_INTERVAL: return "Encoder, sync frame 
>> interval";
>> + case V4L2_CID_ENCODER_ERROR_RESILIENCY: return "Encoder, error 
>> resiliency";
>> + case V4L2_CID_ENCODER_TEMPORAL_LAYER_ENABLE: return "Encoder, temporal 
>> layer enable";
>> +
>> + case V4L2_CID_ENCODER_VP8_SLICE_MODE:   return "Encoder, VP8 slice 
>> mode";
>> + case V4L2_CID_ENCODER_VP8_SYNC_FRAME_TYPE: return "Encoder, VP8 sync 
>> frame type";
>> + case V4L2_CID_ENCODER_VP8_DCT_PARTS_PER_FRAME: return "Encoder, VP8, 
>> DCT partitions per frame";
>> +
>> + case V4L2_CID_ENCODER_H264_PROFILE_TOOLSET: return "Encoder, H.264 
>> profile and toolset";
>> + case V4L2_CID_ENCODER_H264_LEVEL_IDC_LIMIT: return "Encoder, H.264 
>> level IDC limit";
>> + case V4L2_CID_ENCODER_H264_SEI_PAYLOAD_TYPE: return "Encoder, H.264 
>> SEI payload type";
>> + case V4L2_CID_ENCODER_H264_LAYER_PRIORITY: return "Encoder, H.264 
>> layer priority";
>> +
>>   /* FM Radio Modulator control */
>>   /* Keep the order of the 'case's the same as in videodev2.h! */
>>   case V4L2_CID_FM_TX_CLASS:  return "FM Radio Modulator 
>> Controls";
>> diff --git a/include/uapi/linux/v4l2-controls.h 
>> b/include/uapi/linux/v4l2-controls.h
>> index 083bb5a..ef3a30d 100644
>> --- a/incl

Re: [media-workshop] Agenda for the Edinburgh mini-summit

2013-09-07 Thread Pawel Osciak
On Fri, Sep 6, 2013 at 10:45 PM, Laurent Pinchart
 wrote:
>
> Hi Hugues,
>
> On Thursday 05 September 2013 13:37:49 Hugues FRUCHET wrote:
> > Hi Mauro,
> >
> > For floating point issue, we have not encountered such issue while
> > integrating various codec (currently H264, MPEG4, VP8 of both Google G1 IP &
> > ST IPs), could you precise which codec you experienced which required FP
> > support ?
> >
> > For user-space library, problem we encountered is that interface between
> > parsing side (for ex. H264 SPS/PPS decoding, slice header decoding,
> > references frame list management, ...moreover all that is needed to prepare
> > hardware IPs call) and decoder side (hardware IPs handling) is not
> > standardized and differs largely regarding IPs or CPU/copro partitioning.
> > This means that even if we use the standard V4L2 capture interface to inject
> > video bitstream (H264 access units for ex), some proprietary meta are needed
> > to be attached to each buffers, making de facto "un-standard" the V4L2
> > interface for this driver.
>
> We're working on APIs to pass meta data from/to the kernel. The necessary
> infrastructure is more or less there already, we "just" need to agree on
> guidelines and standardize the process. One option that will likely be
> implemented is to store meta-data in a plane, using the multiplanar API.


What API is that? Is there an RFC somewhere?

> The resulting plane format will be driver-specific, so we'll loose part of the
> benefits that the V4L2 API provides. We could try to solve this by writing a
> libv4l plugin, specific to your driver, that would handle bitstream parsing
> and fill the meta-data planes correctly. Applications using libv4l would thus
> only need to pass encoded frames to the library, which would create
> multiplanar buffers with video data and meta-data, and pass them to the
> driver. This would be fully transparent for the application.

If V4L2 API is not hardware-independent, it's a big loss. If this
happens, there will be need for another, middleware API, like OMX IL.
This makes V4L2 by itself impractical for real world applications. And
the incentives of using V4L2 are gone, because it's much easier to
write a custom DRM driver and add any userspace API on top of it.
Perhaps this is inevitable, given differences in hardware, but a
plugin approach would be a way to keep V4L2 abstract and retain the
ability to do the bulk of processing in userspace...
--
To unsubscribe from this list: send the line "unsubscribe linux-media" in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


[PATCH v1 06/19] uvcvideo: Recognize UVC 1.5 encoding units.

2013-08-29 Thread Pawel Osciak
Add encoding unit definitions and descriptor parsing code and allow them to
be added to chains.

Signed-off-by: Pawel Osciak 
---
 drivers/media/usb/uvc/uvc_ctrl.c   | 37 ++---
 drivers/media/usb/uvc/uvc_driver.c | 67 +-
 drivers/media/usb/uvc/uvcvideo.h   | 14 +++-
 include/uapi/linux/usb/video.h |  1 +
 4 files changed, 105 insertions(+), 14 deletions(-)

diff --git a/drivers/media/usb/uvc/uvc_ctrl.c b/drivers/media/usb/uvc/uvc_ctrl.c
index ba159a4..72d6724 100644
--- a/drivers/media/usb/uvc/uvc_ctrl.c
+++ b/drivers/media/usb/uvc/uvc_ctrl.c
@@ -777,6 +777,7 @@ static const __u8 uvc_processing_guid[16] = 
UVC_GUID_UVC_PROCESSING;
 static const __u8 uvc_camera_guid[16] = UVC_GUID_UVC_CAMERA;
 static const __u8 uvc_media_transport_input_guid[16] =
UVC_GUID_UVC_MEDIA_TRANSPORT_INPUT;
+static const __u8 uvc_encoding_guid[16] = UVC_GUID_UVC_ENCODING;
 
 static int uvc_entity_match_guid(const struct uvc_entity *entity,
const __u8 guid[16])
@@ -795,6 +796,9 @@ static int uvc_entity_match_guid(const struct uvc_entity 
*entity,
return memcmp(entity->extension.guidExtensionCode,
  guid, 16) == 0;
 
+   case UVC_VC_ENCODING_UNIT:
+   return memcmp(uvc_encoding_guid, guid, 16) == 0;
+
default:
return 0;
}
@@ -2105,12 +2109,13 @@ int uvc_ctrl_init_device(struct uvc_device *dev)
 {
struct uvc_entity *entity;
unsigned int i;
+   int num_found;
 
/* Walk the entities list and instantiate controls */
list_for_each_entry(entity, &dev->entities, list) {
struct uvc_control *ctrl;
-   unsigned int bControlSize = 0, ncontrols;
-   __u8 *bmControls = NULL;
+   unsigned int bControlSize = 0, ncontrols = 0;
+   __u8 *bmControls = NULL, *bmControlsRuntime = NULL;
 
if (UVC_ENTITY_TYPE(entity) == UVC_VC_EXTENSION_UNIT) {
bmControls = entity->extension.bmControls;
@@ -2121,13 +2126,25 @@ int uvc_ctrl_init_device(struct uvc_device *dev)
} else if (UVC_ENTITY_TYPE(entity) == UVC_ITT_CAMERA) {
bmControls = entity->camera.bmControls;
bControlSize = entity->camera.bControlSize;
+   } else if (UVC_ENTITY_TYPE(entity) == UVC_VC_ENCODING_UNIT) {
+   bmControls = entity->encoding.bmControls;
+   bmControlsRuntime = entity->encoding.bmControlsRuntime;
+   bControlSize = entity->encoding.bControlSize;
}
 
/* Remove bogus/blacklisted controls */
uvc_ctrl_prune_entity(dev, entity);
 
/* Count supported controls and allocate the controls array */
-   ncontrols = memweight(bmControls, bControlSize);
+   for (i = 0; i < bControlSize; ++i) {
+   if (bmControlsRuntime) {
+   ncontrols += hweight8(bmControls[i]
+ | bmControlsRuntime[i]);
+   } else {
+   ncontrols += hweight8(bmControls[i]);
+   }
+   }
+
if (ncontrols == 0)
continue;
 
@@ -2139,8 +2156,17 @@ int uvc_ctrl_init_device(struct uvc_device *dev)
 
/* Initialize all supported controls */
ctrl = entity->controls;
-   for (i = 0; i < bControlSize * 8; ++i) {
-   if (uvc_test_bit(bmControls, i) == 0)
+   for (i = 0, num_found = 0;
+   i < bControlSize * 8 && num_found < ncontrols; ++i) {
+   if (uvc_test_bit(bmControls, i) == 1)
+   ctrl->on_init = 1;
+   if (bmControlsRuntime &&
+   uvc_test_bit(bmControlsRuntime, i) == 1)
+   ctrl->in_runtime = 1;
+   else if (!bmControlsRuntime)
+   ctrl->in_runtime = ctrl->on_init;
+
+   if (ctrl->on_init == 0 && ctrl->in_runtime == 0)
continue;
 
ctrl->entity = entity;
@@ -2148,6 +2174,7 @@ int uvc_ctrl_init_device(struct uvc_device *dev)
 
uvc_ctrl_init_ctrl(dev, ctrl);
ctrl++;
+   num_found++;
}
}
 
diff --git a/drivers/media/usb/uvc/uvc_driver.c 
b/drivers/media/usb/uvc/uvc_driver.c
index d7ff707..d950b40 100644
--- a/drivers/media/usb/uvc/uvc_driver.c
+++ b/drivers/media/usb/uvc/uvc_driver.c
@@ -1155,6 +1155,37 @@ static int uvc_parse_standard_control(struct uvc_device 
*dev,
 

[PATCH v1 11/19] uvcvideo: Support V4L2_CTRL_TYPE_BITMASK controls.

2013-08-29 Thread Pawel Osciak
Signed-off-by: Pawel Osciak 
---
 drivers/media/usb/uvc/uvc_ctrl.c | 18 ++
 1 file changed, 18 insertions(+)

diff --git a/drivers/media/usb/uvc/uvc_ctrl.c b/drivers/media/usb/uvc/uvc_ctrl.c
index b0a19b9..a0493d6 100644
--- a/drivers/media/usb/uvc/uvc_ctrl.c
+++ b/drivers/media/usb/uvc/uvc_ctrl.c
@@ -1550,6 +1550,24 @@ int uvc_ctrl_set(struct uvc_video_chain *chain, struct 
v4l2_ext_control *xctrl,
 
break;
 
+   case V4L2_CTRL_TYPE_BITMASK:
+   value = xctrl->value;
+
+   /* If GET_RES is supported, it will return a bitmask of bits
+* that can be set. If it isn't, allow any value.
+*/
+   if (ctrl->info.flags & UVC_CTRL_FLAG_GET_RES) {
+   if (!ctrl->cached) {
+   ret = uvc_ctrl_populate_cache(chain, ctrl);
+   if (ret < 0)
+   return ret;
+   }
+   step = mapping->get(mapping, UVC_GET_RES,
+   uvc_ctrl_data(ctrl, UVC_CTRL_DATA_RES));
+   if (value & ~step)
+   return -ERANGE;
+   }
+
default:
value = xctrl->value;
break;
-- 
1.8.4

--
To unsubscribe from this list: send the line "unsubscribe linux-media" in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


[PATCH v1 00/19] UVC 1.5 VP8 support for uvcvideo

2013-08-29 Thread Pawel Osciak
Hello everyone,

This series adds support for UVC 1.5 and VP8 encoding cameras to the uvcvideo
driver. The official specification for the new standard can be found here:
http://www.usb.org/developers/devclass_docs.

The main change in 1.5 is support for encoding cameras. Those cameras contain
additional UVC entities, called Encoding Units, with their own set of controls
governing encode parameters. Typical encoding cameras (see examples in class
spec) expose two USB Video Streaming Interfaces (VSIs): one for raw stream
formats and one for encoded streams. Typically, both get their source stream
from a single sensor, producing raw and encoded versions of the video feed
simultaneously.
Encoding Units may also support the so-called "simulcast" formats, which allow
additional sub-streams, or layers, used to achieve temporal scalability.
The spec allows up to 4 simulcast layers. Those layers are encoded in the same
format, but encoding parameters, such as resolution, bitrate, etc., may,
depending on the camera capabilities, be changed independently for each layer,
and their streaming state may also be controlled independently as well. The
layers are streamed from the same USB VSI, and the information which layer
a frame belongs to is contained in its payload header.

In V4L2 API, a separate video node is created for each VSI: one for raw formats
VSI and another for the encoded formats VSI. Both can operate completely
independently from each other. In addition, if the Encoding Unit supports
simulcast, one V4L2 node is created for each stream layer instead, and each
can be controlled independently, including streamon/streamoff state, setting
resolution and controls. Once a simulcast format is successfully set for one
of the simulcast video nodes however, it cannot be changed, unless all connected
nodes are idle, i.e. they are not streaming and their buffers are freed.

The userspace can discover if a set of nodes belongs to one encoding unit
by traversing media controller topology of the camera.


I will be gradually posting documentation changes for new features after initial
rounds of reviews. This is a relatively major change to the UVC driver and
although I tried to keep the existing logic for UVC <1.5 cameras intact as much
as possible, I would very much appreciate it if these patches could get some
testing from you as well, on your own devices/systems.

Thanks,
Pawel Osciak


Pawel Osciak (19):
  uvcvideo: Add UVC query tracing.
  uvcvideo: Return 0 when setting probe control succeeds.
  uvcvideo: Add support for multiple chains with common roots.
  uvcvideo: Create separate debugfs entries for each streaming interface.
  uvcvideo: Add support for UVC1.5 P&C control.
  uvcvideo: Recognize UVC 1.5 encoding units.
  uvcvideo: Unify error reporting during format descriptor parsing.
  uvcvideo: Add UVC1.5 VP8 format support.
  uvcvideo: Reorganize uvc_{get,set}_le_value.
  uvcvideo: Support UVC 1.5 runtime control property.
  uvcvideo: Support V4L2_CTRL_TYPE_BITMASK controls.
  uvcvideo: Reorganize next buffer handling.
  uvcvideo: Unify UVC payload header parsing.
  v4l: Add v4l2_buffer flags for VP8-specific special frames.
  uvcvideo: Add support for VP8 special frame flags.
  v4l: Add encoding camera controls.
  uvcvideo: Add UVC 1.5 Encoding Unit controls.
  v4l: Add V4L2_PIX_FMT_VP8_SIMULCAST format.
  uvcvideo: Add support for UVC 1.5 VP8 simulcast.

 drivers/media/usb/uvc/uvc_ctrl.c | 960 ---
 drivers/media/usb/uvc/uvc_debugfs.c  |   3 +-
 drivers/media/usb/uvc/uvc_driver.c   | 604 ++
 drivers/media/usb/uvc/uvc_entity.c   | 129 -
 drivers/media/usb/uvc/uvc_isight.c   |  12 +-
 drivers/media/usb/uvc/uvc_queue.c|  25 +-
 drivers/media/usb/uvc/uvc_v4l2.c | 284 +--
 drivers/media/usb/uvc/uvc_video.c| 704 -
 drivers/media/usb/uvc/uvcvideo.h | 214 +++-
 drivers/media/v4l2-core/v4l2-ctrls.c |  29 ++
 include/uapi/linux/usb/video.h   |  45 ++
 include/uapi/linux/v4l2-controls.h   |  31 ++
 include/uapi/linux/videodev2.h   |   8 +
 13 files changed, 2421 insertions(+), 627 deletions(-)
--
To unsubscribe from this list: send the line "unsubscribe linux-media" in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


[PATCH v1 08/19] uvcvideo: Add UVC1.5 VP8 format support.

2013-08-29 Thread Pawel Osciak
Add detection and parsing of VP8 format and frame descriptors and
reorganize format parsing code.

Signed-off-by: Pawel Osciak 
---
 drivers/media/usb/uvc/uvc_driver.c | 120 -
 drivers/media/usb/uvc/uvcvideo.h   |   4 +-
 include/uapi/linux/usb/video.h |   8 +++
 3 files changed, 104 insertions(+), 28 deletions(-)

diff --git a/drivers/media/usb/uvc/uvc_driver.c 
b/drivers/media/usb/uvc/uvc_driver.c
index 936ddc7..27a7a11 100644
--- a/drivers/media/usb/uvc/uvc_driver.c
+++ b/drivers/media/usb/uvc/uvc_driver.c
@@ -312,7 +312,7 @@ static int uvc_parse_format(struct uvc_device *dev,
struct uvc_frame *frame;
const unsigned char *start = buffer;
unsigned int interval;
-   unsigned int i, n;
+   unsigned int i, n, intervals_off;
__u8 ftype;
 
format->type = buffer[2];
@@ -401,6 +401,18 @@ static int uvc_parse_format(struct uvc_device *dev,
format->nframes = 1;
break;
 
+   case UVC_VS_FORMAT_VP8:
+   if (buflen < 13)
+   goto format_error;
+
+   format->bpp = 0;
+   format->flags = UVC_FMT_FLAG_COMPRESSED;
+   ftype = UVC_VS_FRAME_VP8;
+   strlcpy(format->name, "VP8", sizeof(format->name));
+   format->fcc = V4L2_PIX_FMT_VP8;
+
+   break;
+
case UVC_VS_FORMAT_MPEG2TS:
case UVC_VS_FORMAT_STREAM_BASED:
/* Not supported yet. */
@@ -417,44 +429,83 @@ static int uvc_parse_format(struct uvc_device *dev,
buflen -= buffer[0];
buffer += buffer[0];
 
-   /* Parse the frame descriptors. Only uncompressed, MJPEG and frame
-* based formats have frame descriptors.
+   /* Parse the frame descriptors. Only uncompressed, MJPEG, temporally
+* encoded and frame based formats have frame descriptors.
 */
while (buflen > 2 && buffer[1] == USB_DT_CS_INTERFACE &&
   buffer[2] == ftype) {
frame = &format->frame[format->nframes];
-   if (ftype != UVC_VS_FRAME_FRAME_BASED)
-   n = buflen > 25 ? buffer[25] : 0;
-   else
-   n = buflen > 21 ? buffer[21] : 0;
-
-   n = n ? n : 3;
 
-   if (buflen < 26 + 4*n) {
-   uvc_trace(UVC_TRACE_DESCR, "device %d videostreaming "
-  "interface %d FRAME error\n", dev->udev->devnum,
-  alts->desc.bInterfaceNumber);
-   return -EINVAL;
-   }
-
-   frame->bFrameIndex = buffer[3];
-   frame->bmCapabilities = buffer[4];
-   frame->wWidth = get_unaligned_le16(&buffer[5]);
-   frame->wHeight = get_unaligned_le16(&buffer[7]);
-   frame->dwMinBitRate = get_unaligned_le32(&buffer[9]);
-   frame->dwMaxBitRate = get_unaligned_le32(&buffer[13]);
-   if (ftype != UVC_VS_FRAME_FRAME_BASED) {
+   switch (ftype) {
+   case UVC_VS_FRAME_UNCOMPRESSED:
+   case UVC_VS_FRAME_MJPEG:
+   intervals_off = 26;
+   if (buflen < intervals_off)
+   goto frame_error;
+
+   frame->bFrameIndex = buffer[3];
+   frame->bmCapabilities = buffer[4];
+   frame->wWidth = get_unaligned_le16(&buffer[5]);
+   frame->wHeight = get_unaligned_le16(&buffer[7]);
+   frame->dwMinBitRate = get_unaligned_le32(&buffer[9]);
+   frame->dwMaxBitRate = get_unaligned_le32(&buffer[13]);
frame->dwMaxVideoFrameBufferSize =
get_unaligned_le32(&buffer[17]);
frame->dwDefaultFrameInterval =
get_unaligned_le32(&buffer[21]);
-   frame->bFrameIntervalType = buffer[25];
-   } else {
+   frame->bFrameIntervalType = n = buffer[25];
+   break;
+
+   case UVC_VS_FRAME_FRAME_BASED:
+   intervals_off = 26;
+   if (buflen < intervals_off)
+   goto frame_error;
+
+   frame->bFrameIndex = buffer[3];
+   frame->bmCapabilities = buffer[4];
+   frame->wWidth = get_unaligned_le16(&buffer[5]);
+   frame->wHeight = get_unaligned_le16(&buffer[7]);
+   frame->dwMinBitRate = get_unaligned_le32(&buffer[9]);
+   frame->dwMaxBitRate = get_unaligned_le32(&

[PATCH v1 17/19] uvcvideo: Add UVC 1.5 Encoding Unit controls.

2013-08-29 Thread Pawel Osciak
These controls allow modifying encoding parameters.

Signed-off-by: Pawel Osciak 
---
 drivers/media/usb/uvc/uvc_ctrl.c | 445 +++
 include/uapi/linux/usb/video.h   |  23 ++
 2 files changed, 468 insertions(+)

diff --git a/drivers/media/usb/uvc/uvc_ctrl.c b/drivers/media/usb/uvc/uvc_ctrl.c
index a0493d6..cd02c99 100644
--- a/drivers/media/usb/uvc/uvc_ctrl.c
+++ b/drivers/media/usb/uvc/uvc_ctrl.c
@@ -351,6 +351,167 @@ static struct uvc_control_info uvc_ctrls[] = {
| UVC_CTRL_FLAG_RESTORE
| UVC_CTRL_FLAG_AUTO_UPDATE,
},
+   /*
+* All EU controls are marked as AUTO_UPDATE, because many are, and also
+* we can't cache all of them as they are stream/layer dependent, which
+* would be too slow/too much to cache.
+*/
+   {
+   .entity = UVC_GUID_UVC_ENCODING,
+   .selector   = UVC_EU_PROFILE_TOOLSET_CONTROL,
+   .index  = 1,
+   .size   = 6,
+   .flags  = UVC_CTRL_FLAG_SET_CUR | UVC_CTRL_FLAG_GET_CUR
+   | UVC_CTRL_FLAG_GET_DEF
+   | UVC_CTRL_FLAG_AUTO_UPDATE,
+   },
+   {
+   .entity = UVC_GUID_UVC_ENCODING,
+   .selector   = UVC_EU_MIN_FRAME_INTERVAL_CONTROL,
+   .index  = 3,
+   .size   = 4,
+   .flags  = UVC_CTRL_FLAG_SET_CUR | UVC_CTRL_FLAG_GET_CUR
+   | UVC_CTRL_FLAG_GET_MIN | UVC_CTRL_FLAG_GET_MAX
+   | UVC_CTRL_FLAG_GET_DEF
+   | UVC_CTRL_FLAG_AUTO_UPDATE,
+   },
+   {
+   .entity = UVC_GUID_UVC_ENCODING,
+   .selector   = UVC_EU_SLICE_MODE_CONTROL,
+   .index  = 4,
+   .size   = 4,
+   .flags  = UVC_CTRL_FLAG_SET_CUR | UVC_CTRL_FLAG_GET_CUR
+   | UVC_CTRL_FLAG_GET_MIN | UVC_CTRL_FLAG_GET_MAX
+   | UVC_CTRL_FLAG_GET_DEF
+   | UVC_CTRL_FLAG_AUTO_UPDATE,
+   },
+   {
+   .entity = UVC_GUID_UVC_ENCODING,
+   .selector   = UVC_EU_RATE_CONTROL_MODE_CONTROL,
+   .index  = 5,
+   .size   = 1,
+   .flags  = UVC_CTRL_FLAG_SET_CUR | UVC_CTRL_FLAG_GET_CUR
+   | UVC_CTRL_FLAG_GET_DEF
+   | UVC_CTRL_FLAG_AUTO_UPDATE,
+   },
+   {
+   .entity = UVC_GUID_UVC_ENCODING,
+   .selector   = UVC_EU_AVERAGE_BITRATE_CONTROL,
+   .index  = 6,
+   .size   = 4,
+   .flags  = UVC_CTRL_FLAG_SET_CUR
+   | UVC_CTRL_FLAG_GET_RANGE
+   | UVC_CTRL_FLAG_AUTO_UPDATE,
+   },
+   {
+   .entity = UVC_GUID_UVC_ENCODING,
+   .selector   = UVC_EU_CPB_SIZE_CONTROL,
+   .index  = 7,
+   .size   = 4,
+   .flags  = UVC_CTRL_FLAG_SET_CUR
+   | UVC_CTRL_FLAG_GET_RANGE
+   | UVC_CTRL_FLAG_AUTO_UPDATE,
+   },
+   {
+   .entity = UVC_GUID_UVC_ENCODING,
+   .selector   = UVC_EU_PEAK_BIT_RATE_CONTROL,
+   .index  = 8,
+   .size   = 4,
+   .flags  = UVC_CTRL_FLAG_SET_CUR
+   | UVC_CTRL_FLAG_GET_RANGE
+   | UVC_CTRL_FLAG_AUTO_UPDATE,
+   },
+   {
+   .entity = UVC_GUID_UVC_ENCODING,
+   .selector   = UVC_EU_QUANTIZATION_PARAMS_CONTROL,
+   .index  = 9,
+   .size   = 6,
+   .flags  = UVC_CTRL_FLAG_SET_CUR | UVC_CTRL_FLAG_GET_CUR
+   | UVC_CTRL_FLAG_GET_MIN | UVC_CTRL_FLAG_GET_MAX
+   | UVC_CTRL_FLAG_GET_DEF
+   | UVC_CTRL_FLAG_AUTO_UPDATE,
+   },
+   {
+   .entity = UVC_GUID_UVC_ENCODING,
+   .selector   = UVC_EU_SYNC_REF_FRAME_CONTROL,
+   .index  = 10,
+   .size   = 4,
+   .flags  = UVC_CTRL_FLAG_SET_CUR | UVC_CTRL_FLAG_GET_CUR
+   | UVC_CTRL_FLAG_GET_MIN | UVC_CTRL_FLAG_GET_MAX
+   | UVC_CTRL_FLAG_AUTO_UPDATE,
+   },
+   {
+   .entity = UVC_GUID_UVC_ENCODING,
+   .selector   = UVC_EU_LTR_BUFFER_CONTROL,
+   .index  = 11,
+   .size 

[PATCH v1 15/19] uvcvideo: Add support for VP8 special frame flags.

2013-08-29 Thread Pawel Osciak
Signed-off-by: Pawel Osciak 
---
 drivers/media/usb/uvc/uvc_video.c | 18 +-
 drivers/media/usb/uvc/uvcvideo.h  | 10 ++
 2 files changed, 27 insertions(+), 1 deletion(-)

diff --git a/drivers/media/usb/uvc/uvc_video.c 
b/drivers/media/usb/uvc/uvc_video.c
index 59f57a2..0291817 100644
--- a/drivers/media/usb/uvc/uvc_video.c
+++ b/drivers/media/usb/uvc/uvc_video.c
@@ -1136,6 +1136,8 @@ static int uvc_video_parse_header(struct uvc_streaming 
*stream,
if (header->has_scr)
header->length += 6;
 
+   header->buf_flags = 0;
+
if (stream->cur_format->fcc == V4L2_PIX_FMT_VP8) {
/* VP8 payload has 2 additional bytes of BFH. */
header->length += 2;
@@ -1147,6 +1149,16 @@ static int uvc_video_parse_header(struct uvc_streaming 
*stream,
header->has_sli = data[1] & UVC_STREAM_SLI;
if (header->has_sli)
header->length += 2;
+
+   /* Codec-specific flags for v4l2_buffer. */
+   header->buf_flags |= (data[1] & UVC_STREAM_STI) ?
+   V4L2_BUF_FLAG_KEYFRAME : 0;
+   header->buf_flags |= (data[2] & UVC_STREAM_VP8_PRF) ?
+   V4L2_BUF_FLAG_PREV_FRAME : 0;
+   header->buf_flags |= (data[2] & UVC_STREAM_VP8_ARF) ?
+   V4L2_BUF_FLAG_ALTREF_FRAME : 0;
+   header->buf_flags |= (data[2] & UVC_STREAM_VP8_GRF) ?
+   V4L2_BUF_FLAG_GOLDEN_FRAME : 0;
}
 
/* - bHeaderLength value can't be larger than the packet size. */
@@ -1222,6 +1234,8 @@ static void uvc_video_decode_isoc(struct urb *urb, struct 
uvc_streaming *stream)
if (ret < 0)
continue;
 
+   buf->buf.v4l2_buf.flags |= header.buf_flags;
+
/* Decode the payload data. */
uvc_video_decode_data(stream, buf, mem + header.length,
urb->iso_frame_desc[i].actual_length - header.length);
@@ -1293,8 +1307,10 @@ static void uvc_video_decode_bulk(struct urb *urb, 
struct uvc_streaming *stream)
 */
 
/* Process video data. */
-   if (!stream->bulk.skip_payload && buf != NULL)
+   if (!stream->bulk.skip_payload && buf != NULL) {
uvc_video_decode_data(stream, buf, mem, len);
+   buf->buf.v4l2_buf.flags |= header.buf_flags;
+   }
 
/* Detect the payload end by a URB smaller than the maximum size (or
 * a payload size equal to the maximum) and process the header again.
diff --git a/drivers/media/usb/uvc/uvcvideo.h b/drivers/media/usb/uvc/uvcvideo.h
index b355b2c..fb21459 100644
--- a/drivers/media/usb/uvc/uvcvideo.h
+++ b/drivers/media/usb/uvc/uvcvideo.h
@@ -145,6 +145,14 @@
 #define UVC_FMT_FLAG_COMPRESSED0x0001
 #define UVC_FMT_FLAG_STREAM0x0002
 
+/* v4l2_buffer codec flags */
+#define UVC_V4L2_BUFFER_CODEC_FLAGS(V4L2_BUF_FLAG_KEYFRAME | \
+V4L2_BUF_FLAG_PFRAME | \
+V4L2_BUF_FLAG_BFRAME | \
+V4L2_BUF_FLAG_PREV_FRAME | \
+V4L2_BUF_FLAG_GOLDEN_FRAME | \
+V4L2_BUF_FLAG_ALTREF_FRAME)
+
 /* 
  * Structures.
  */
@@ -472,6 +480,8 @@ struct uvc_payload_header {
 
int length;
int payload_size;
+
+   __u32 buf_flags; /* v4l2_buffer flags */
 };
 
 struct uvc_streaming {
-- 
1.8.4

--
To unsubscribe from this list: send the line "unsubscribe linux-media" in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


[PATCH v1 03/19] uvcvideo: Add support for multiple chains with common roots.

2013-08-29 Thread Pawel Osciak
This adds support for pipelines that fork into branches consisting of more
than one entity, creating a chain for each fork and putting common entities
on all chains that share them.

This requires us to share the ctrl_mutex across forked chains. Whenever we
discover a shared part of a chain, we assign the pointer to an existing
mutex to the sharing chain instead of creating a new one.

The "forward scan" is not needed anymore, as after scanning back from OTs,
we go over all entities which are not on a path from an OT and accept
single-XU branches, adding them to the existing chains.

Also extract control locking into __uvc_ctrl_{lock,unlock} functions.

Signed-off-by: Pawel Osciak 
---
 drivers/media/usb/uvc/uvc_ctrl.c   |  70 -
 drivers/media/usb/uvc/uvc_driver.c | 210 +
 drivers/media/usb/uvc/uvc_entity.c |  15 ++-
 drivers/media/usb/uvc/uvc_v4l2.c   |   9 +-
 drivers/media/usb/uvc/uvcvideo.h   |  20 +++-
 5 files changed, 199 insertions(+), 125 deletions(-)

diff --git a/drivers/media/usb/uvc/uvc_ctrl.c b/drivers/media/usb/uvc/uvc_ctrl.c
index a2f4501..ba159a4 100644
--- a/drivers/media/usb/uvc/uvc_ctrl.c
+++ b/drivers/media/usb/uvc/uvc_ctrl.c
@@ -841,6 +841,7 @@ static struct uvc_control *uvc_find_control(struct 
uvc_video_chain *chain,
 {
struct uvc_control *ctrl = NULL;
struct uvc_entity *entity;
+   struct uvc_chain_entry *entry;
int next = v4l2_id & V4L2_CTRL_FLAG_NEXT_CTRL;
 
*mapping = NULL;
@@ -849,7 +850,8 @@ static struct uvc_control *uvc_find_control(struct 
uvc_video_chain *chain,
v4l2_id &= V4L2_CTRL_ID_MASK;
 
/* Find the control. */
-   list_for_each_entry(entity, &chain->entities, chain) {
+   list_for_each_entry(entry, &chain->entities, chain_entry) {
+   entity = entry->entity;
__uvc_find_control(entity, v4l2_id, mapping, &ctrl, next);
if (ctrl && !next)
return ctrl;
@@ -1048,6 +1050,16 @@ static int __uvc_query_v4l2_ctrl(struct uvc_video_chain 
*chain,
return 0;
 }
 
+int __uvc_ctrl_lock(struct uvc_video_chain *chain)
+{
+   return mutex_lock_interruptible(&chain->pipeline->ctrl_mutex) ?
+   -ERESTARTSYS : 0;
+}
+void __uvc_ctrl_unlock(struct uvc_video_chain *chain)
+{
+   mutex_unlock(&chain->pipeline->ctrl_mutex);
+}
+
 int uvc_query_v4l2_ctrl(struct uvc_video_chain *chain,
struct v4l2_queryctrl *v4l2_ctrl)
 {
@@ -1055,9 +1067,9 @@ int uvc_query_v4l2_ctrl(struct uvc_video_chain *chain,
struct uvc_control_mapping *mapping;
int ret;
 
-   ret = mutex_lock_interruptible(&chain->ctrl_mutex);
+   ret = __uvc_ctrl_lock(chain);
if (ret < 0)
-   return -ERESTARTSYS;
+   return ret;
 
ctrl = uvc_find_control(chain, v4l2_ctrl->id, &mapping);
if (ctrl == NULL) {
@@ -1067,7 +1079,7 @@ int uvc_query_v4l2_ctrl(struct uvc_video_chain *chain,
 
ret = __uvc_query_v4l2_ctrl(chain, ctrl, mapping, v4l2_ctrl);
 done:
-   mutex_unlock(&chain->ctrl_mutex);
+   __uvc_ctrl_unlock(chain);
return ret;
 }
 
@@ -1094,9 +1106,9 @@ int uvc_query_v4l2_menu(struct uvc_video_chain *chain,
query_menu->id = id;
query_menu->index = index;
 
-   ret = mutex_lock_interruptible(&chain->ctrl_mutex);
+   ret = __uvc_ctrl_lock(chain);
if (ret < 0)
-   return -ERESTARTSYS;
+   return ret;
 
ctrl = uvc_find_control(chain, query_menu->id, &mapping);
if (ctrl == NULL || mapping->v4l2_type != V4L2_CTRL_TYPE_MENU) {
@@ -1132,7 +1144,7 @@ int uvc_query_v4l2_menu(struct uvc_video_chain *chain,
strlcpy(query_menu->name, menu_info->name, sizeof query_menu->name);
 
 done:
-   mutex_unlock(&chain->ctrl_mutex);
+   __uvc_ctrl_unlock(chain);
return ret;
 }
 
@@ -1257,9 +1269,9 @@ static int uvc_ctrl_add_event(struct 
v4l2_subscribed_event *sev, unsigned elems)
struct uvc_control *ctrl;
int ret;
 
-   ret = mutex_lock_interruptible(&handle->chain->ctrl_mutex);
+   ret = __uvc_ctrl_lock(handle->chain);
if (ret < 0)
-   return -ERESTARTSYS;
+   return ret;
 
ctrl = uvc_find_control(handle->chain, sev->id, &mapping);
if (ctrl == NULL) {
@@ -1285,7 +1297,7 @@ static int uvc_ctrl_add_event(struct 
v4l2_subscribed_event *sev, unsigned elems)
}
 
 done:
-   mutex_unlock(&handle->chain->ctrl_mutex);
+   __uvc_ctrl_unlock(handle->chain);
return ret;
 }
 
@@ -1293,9 +1305,9 @@ static void uvc_ctrl_del_event(struct 
v4l2_subscribed_event *sev)
 {
struct uvc_fh *handle = container_of(sev->fh, struct uvc_fh, vfh);
 
-   mutex_lock(&handle-&

[PATCH v1 07/19] uvcvideo: Unify error reporting during format descriptor parsing.

2013-08-29 Thread Pawel Osciak
Add common error handling paths for format parsing failures.

Signed-off-by: Pawel Osciak 
---
 drivers/media/usb/uvc/uvc_driver.c | 35 ++-
 1 file changed, 14 insertions(+), 21 deletions(-)

diff --git a/drivers/media/usb/uvc/uvc_driver.c 
b/drivers/media/usb/uvc/uvc_driver.c
index d950b40..936ddc7 100644
--- a/drivers/media/usb/uvc/uvc_driver.c
+++ b/drivers/media/usb/uvc/uvc_driver.c
@@ -322,13 +322,8 @@ static int uvc_parse_format(struct uvc_device *dev,
case UVC_VS_FORMAT_UNCOMPRESSED:
case UVC_VS_FORMAT_FRAME_BASED:
n = buffer[2] == UVC_VS_FORMAT_UNCOMPRESSED ? 27 : 28;
-   if (buflen < n) {
-   uvc_trace(UVC_TRACE_DESCR, "device %d videostreaming "
-  "interface %d FORMAT error\n",
-  dev->udev->devnum,
-  alts->desc.bInterfaceNumber);
-   return -EINVAL;
-   }
+   if (buflen < n)
+   goto format_error;
 
/* Find the format descriptor from its GUID. */
fmtdesc = uvc_format_by_guid(&buffer[5]);
@@ -356,13 +351,8 @@ static int uvc_parse_format(struct uvc_device *dev,
break;
 
case UVC_VS_FORMAT_MJPEG:
-   if (buflen < 11) {
-   uvc_trace(UVC_TRACE_DESCR, "device %d videostreaming "
-  "interface %d FORMAT error\n",
-  dev->udev->devnum,
-  alts->desc.bInterfaceNumber);
-   return -EINVAL;
-   }
+   if (buflen < 11)
+   goto format_error;
 
strlcpy(format->name, "MJPEG", sizeof format->name);
format->fcc = V4L2_PIX_FMT_MJPEG;
@@ -372,13 +362,8 @@ static int uvc_parse_format(struct uvc_device *dev,
break;
 
case UVC_VS_FORMAT_DV:
-   if (buflen < 9) {
-   uvc_trace(UVC_TRACE_DESCR, "device %d videostreaming "
-  "interface %d FORMAT error\n",
-  dev->udev->devnum,
-  alts->desc.bInterfaceNumber);
-   return -EINVAL;
-   }
+   if (buflen < 9)
+   goto format_error;
 
switch (buffer[8] & 0x7f) {
case 0:
@@ -542,6 +527,14 @@ static int uvc_parse_format(struct uvc_device *dev,
}
 
return buffer - start;
+
+format_error:
+   uvc_trace(UVC_TRACE_DESCR, "device %d videostreaming "
+   "interface %d FORMAT error\n",
+   dev->udev->devnum,
+   alts->desc.bInterfaceNumber);
+   return -EINVAL;
+
 }
 
 static int uvc_parse_streaming(struct uvc_device *dev,
-- 
1.8.4

--
To unsubscribe from this list: send the line "unsubscribe linux-media" in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


[PATCH v1 14/19] v4l: Add v4l2_buffer flags for VP8-specific special frames.

2013-08-29 Thread Pawel Osciak
Add bits for previous, golden and altref frame types.

Signed-off-by: Pawel Osciak 
---
 include/uapi/linux/videodev2.h | 4 
 1 file changed, 4 insertions(+)

diff --git a/include/uapi/linux/videodev2.h b/include/uapi/linux/videodev2.h
index 437f1b0..c011ee0 100644
--- a/include/uapi/linux/videodev2.h
+++ b/include/uapi/linux/videodev2.h
@@ -687,6 +687,10 @@ struct v4l2_buffer {
 #define V4L2_BUF_FLAG_TIMESTAMP_UNKNOWN0x
 #define V4L2_BUF_FLAG_TIMESTAMP_MONOTONIC  0x2000
 #define V4L2_BUF_FLAG_TIMESTAMP_COPY   0x4000
+/* VP8 special frames */
+#define V4L2_BUF_FLAG_PREV_FRAME   0x1  /* VP8 prev frame */
+#define V4L2_BUF_FLAG_GOLDEN_FRAME 0x2  /* VP8 golden frame */
+#define V4L2_BUF_FLAG_ALTREF_FRAME 0x4  /* VP8 altref frame */
 
 /**
  * struct v4l2_exportbuffer - export of video buffer as DMABUF file descriptor
-- 
1.8.4

--
To unsubscribe from this list: send the line "unsubscribe linux-media" in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


[PATCH v1 02/19] uvcvideo: Return 0 when setting probe control succeeds.

2013-08-29 Thread Pawel Osciak
Return 0 instead of returning size of the probe control on successful set.

Signed-off-by: Pawel Osciak 
---
 drivers/media/usb/uvc/uvc_video.c | 2 ++
 1 file changed, 2 insertions(+)

diff --git a/drivers/media/usb/uvc/uvc_video.c 
b/drivers/media/usb/uvc/uvc_video.c
index 695f6d9..1198989 100644
--- a/drivers/media/usb/uvc/uvc_video.c
+++ b/drivers/media/usb/uvc/uvc_video.c
@@ -296,6 +296,8 @@ static int uvc_set_video_ctrl(struct uvc_streaming *stream,
"%d (exp. %u).\n", probe ? "probe" : "commit",
ret, size);
ret = -EIO;
+   } else {
+   ret = 0;
}
 
kfree(data);
-- 
1.8.4

--
To unsubscribe from this list: send the line "unsubscribe linux-media" in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


[PATCH v1 13/19] uvcvideo: Unify UVC payload header parsing.

2013-08-29 Thread Pawel Osciak
Create a separate function for parsing UVC payload headers and extract code
from other functions into it. Store the parsed values in a header struct.

Signed-off-by: Pawel Osciak 
---
 drivers/media/usb/uvc/uvc_video.c | 270 +++---
 drivers/media/usb/uvc/uvcvideo.h  |  21 +++
 2 files changed, 157 insertions(+), 134 deletions(-)

diff --git a/drivers/media/usb/uvc/uvc_video.c 
b/drivers/media/usb/uvc/uvc_video.c
index 2f9a5fa..59f57a2 100644
--- a/drivers/media/usb/uvc/uvc_video.c
+++ b/drivers/media/usb/uvc/uvc_video.c
@@ -422,40 +422,14 @@ static int uvc_commit_video(struct uvc_streaming *stream,
 
 static void
 uvc_video_clock_decode(struct uvc_streaming *stream, struct uvc_buffer *buf,
-  const __u8 *data, int len)
+   struct uvc_payload_header *header)
 {
struct uvc_clock_sample *sample;
-   unsigned int header_size;
-   bool has_pts = false;
-   bool has_scr = false;
unsigned long flags;
struct timespec ts;
u16 host_sof;
u16 dev_sof;
 
-   switch (data[1] & (UVC_STREAM_PTS | UVC_STREAM_SCR)) {
-   case UVC_STREAM_PTS | UVC_STREAM_SCR:
-   header_size = 12;
-   has_pts = true;
-   has_scr = true;
-   break;
-   case UVC_STREAM_PTS:
-   header_size = 6;
-   has_pts = true;
-   break;
-   case UVC_STREAM_SCR:
-   header_size = 8;
-   has_scr = true;
-   break;
-   default:
-   header_size = 2;
-   break;
-   }
-
-   /* Check for invalid headers. */
-   if (len < header_size)
-   return;
-
/* Extract the timestamps:
 *
 * - store the frame PTS in the buffer structure
@@ -463,17 +437,17 @@ uvc_video_clock_decode(struct uvc_streaming *stream, 
struct uvc_buffer *buf,
 *   kernel timestamps and store them with the SCR STC and SOF fields
 *   in the ring buffer
 */
-   if (has_pts && buf != NULL)
-   buf->pts = get_unaligned_le32(&data[2]);
+   if (header->has_pts && buf != NULL)
+   buf->pts = header->pts;
 
-   if (!has_scr)
+   if (!header->has_scr)
return;
 
/* To limit the amount of data, drop SCRs with an SOF identical to the
 * previous one.
 */
-   dev_sof = get_unaligned_le16(&data[header_size - 2]);
-   if (dev_sof == stream->clock.last_sof)
+   dev_sof = header->sof;
+   if (dev_sof <= stream->clock.last_sof)
return;
 
stream->clock.last_sof = dev_sof;
@@ -513,7 +487,7 @@ uvc_video_clock_decode(struct uvc_streaming *stream, struct 
uvc_buffer *buf,
spin_lock_irqsave(&stream->clock.lock, flags);
 
sample = &stream->clock.samples[stream->clock.head];
-   sample->dev_stc = get_unaligned_le32(&data[header_size - 6]);
+   sample->dev_stc = header->stc;
sample->dev_sof = dev_sof;
sample->host_sof = host_sof;
sample->host_ts = ts;
@@ -756,114 +730,74 @@ done:
  */
 
 static void uvc_video_stats_decode(struct uvc_streaming *stream,
-   const __u8 *data, int len)
+   struct uvc_payload_header *header)
 {
-   unsigned int header_size;
-   bool has_pts = false;
-   bool has_scr = false;
-   u16 uninitialized_var(scr_sof);
-   u32 uninitialized_var(scr_stc);
-   u32 uninitialized_var(pts);
-
if (stream->stats.stream.nb_frames == 0 &&
stream->stats.frame.nb_packets == 0)
ktime_get_ts(&stream->stats.stream.start_ts);
 
-   switch (data[1] & (UVC_STREAM_PTS | UVC_STREAM_SCR)) {
-   case UVC_STREAM_PTS | UVC_STREAM_SCR:
-   header_size = 12;
-   has_pts = true;
-   has_scr = true;
-   break;
-   case UVC_STREAM_PTS:
-   header_size = 6;
-   has_pts = true;
-   break;
-   case UVC_STREAM_SCR:
-   header_size = 8;
-   has_scr = true;
-   break;
-   default:
-   header_size = 2;
-   break;
-   }
-
-   /* Check for invalid headers. */
-   if (len < header_size || data[0] < header_size) {
-   stream->stats.frame.nb_invalid++;
-   return;
-   }
-
-   /* Extract the timestamps. */
-   if (has_pts)
-   pts = get_unaligned_le32(&data[2]);
-
-   if (has_scr) {
-   scr_stc = get_unaligned_le32(&data[header_size - 6]);
-   scr_sof = get_unaligned_le16(&data[header_size - 2]);
-   }
-
/* Is PTS constant through the whole frame ? */
-   if (has_pts && stream->stats.frame.nb_pts) {
-

[PATCH v1 09/19] uvcvideo: Reorganize uvc_{get,set}_le_value.

2013-08-29 Thread Pawel Osciak
Signed-off-by: Pawel Osciak 
---
 drivers/media/usb/uvc/uvc_ctrl.c | 62 
 1 file changed, 37 insertions(+), 25 deletions(-)

diff --git a/drivers/media/usb/uvc/uvc_ctrl.c b/drivers/media/usb/uvc/uvc_ctrl.c
index 72d6724..d735c88 100644
--- a/drivers/media/usb/uvc/uvc_ctrl.c
+++ b/drivers/media/usb/uvc/uvc_ctrl.c
@@ -707,18 +707,12 @@ static inline void uvc_clear_bit(__u8 *data, int bit)
data[bit >> 3] &= ~(1 << (bit & 7));
 }
 
-/* Extract the bit string specified by mapping->offset and mapping->size
- * from the little-endian data stored at 'data' and return the result as
- * a signed 32bit integer. Sign extension will be performed if the mapping
- * references a signed data type.
- */
-static __s32 uvc_get_le_value(struct uvc_control_mapping *mapping,
-   __u8 query, const __u8 *data)
+static int __uvc_get_le_value(int bits, int offset, const __u8 *data,
+   __u32 data_type)
 {
-   int bits = mapping->size;
-   int offset = mapping->offset;
__s32 value = 0;
__u8 mask;
+   int size = bits;
 
data += offset / 8;
offset &= 7;
@@ -733,22 +727,49 @@ static __s32 uvc_get_le_value(struct uvc_control_mapping 
*mapping,
}
 
/* Sign-extend the value if needed. */
-   if (mapping->data_type == UVC_CTRL_DATA_TYPE_SIGNED)
-   value |= -(value & (1 << (mapping->size - 1)));
+   if (data_type == UVC_CTRL_DATA_TYPE_SIGNED)
+   value |= -(value & (1 << (size - 1)));
 
return value;
 }
 
+/* Extract the bit string specified by mapping->offset and mapping->size
+ * from the little-endian data stored at 'data' and return the result as
+ * a signed 32bit integer. Sign extension will be performed if the mapping
+ * references a signed data type.
+ */
+static __s32 uvc_get_le_value(struct uvc_control_mapping *mapping,
+   __u8 query, const __u8 *data)
+{
+   return __uvc_get_le_value(mapping->size, mapping->offset, data,
+   mapping->data_type);
+}
+
+static void __uvc_set_le_value(int bits, int offset, __s32 value, __u8 *data,
+   bool keep_existing)
+{
+   __u8 mask;
+
+   data += offset / 8;
+   offset &= 7;
+
+   for (; bits > 0; data++) {
+   mask = ((1LL << bits) - 1) << offset;
+   if (!keep_existing)
+   *data = (*data & ~mask);
+   *data |= ((value << offset) & mask);
+   value >>= (8 - offset);
+   bits -= 8 - offset;
+   offset = 0;
+   }
+}
+
 /* Set the bit string specified by mapping->offset and mapping->size
  * in the little-endian data stored at 'data' to the value 'value'.
  */
 static void uvc_set_le_value(struct uvc_control_mapping *mapping,
__s32 value, __u8 *data)
 {
-   int bits = mapping->size;
-   int offset = mapping->offset;
-   __u8 mask;
-
/* According to the v4l2 spec, writing any value to a button control
 * should result in the action belonging to the button control being
 * triggered. UVC devices however want to see a 1 written -> override
@@ -757,16 +778,7 @@ static void uvc_set_le_value(struct uvc_control_mapping 
*mapping,
if (mapping->v4l2_type == V4L2_CTRL_TYPE_BUTTON)
value = -1;
 
-   data += offset / 8;
-   offset &= 7;
-
-   for (; bits > 0; data++) {
-   mask = ((1LL << bits) - 1) << offset;
-   *data = (*data & ~mask) | ((value << offset) & mask);
-   value >>= offset ? offset : 8;
-   bits -= 8 - offset;
-   offset = 0;
-   }
+   __uvc_set_le_value(mapping->size, mapping->offset, value, data, false);
 }
 
 /* 
-- 
1.8.4

--
To unsubscribe from this list: send the line "unsubscribe linux-media" in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


[PATCH v1 01/19] uvcvideo: Add UVC query tracing.

2013-08-29 Thread Pawel Osciak
Add a new trace argument enabling UVC query details and contents logging.

Signed-off-by: Pawel Osciak 
---
 drivers/media/usb/uvc/uvc_video.c | 45 +--
 drivers/media/usb/uvc/uvcvideo.h  |  9 
 2 files changed, 38 insertions(+), 16 deletions(-)

diff --git a/drivers/media/usb/uvc/uvc_video.c 
b/drivers/media/usb/uvc/uvc_video.c
index 3394c34..695f6d9 100644
--- a/drivers/media/usb/uvc/uvc_video.c
+++ b/drivers/media/usb/uvc/uvc_video.c
@@ -29,22 +29,6 @@
 /* 
  * UVC Controls
  */
-
-static int __uvc_query_ctrl(struct uvc_device *dev, __u8 query, __u8 unit,
-   __u8 intfnum, __u8 cs, void *data, __u16 size,
-   int timeout)
-{
-   __u8 type = USB_TYPE_CLASS | USB_RECIP_INTERFACE;
-   unsigned int pipe;
-
-   pipe = (query & 0x80) ? usb_rcvctrlpipe(dev->udev, 0)
- : usb_sndctrlpipe(dev->udev, 0);
-   type |= (query & 0x80) ? USB_DIR_IN : USB_DIR_OUT;
-
-   return usb_control_msg(dev->udev, pipe, query, type, cs << 8,
-   unit << 8 | intfnum, data, size, timeout);
-}
-
 static const char *uvc_query_name(__u8 query)
 {
switch (query) {
@@ -69,6 +53,35 @@ static const char *uvc_query_name(__u8 query)
}
 }
 
+static int __uvc_query_ctrl(struct uvc_device *dev, __u8 query, __u8 unit,
+   __u8 intfnum, __u8 cs, void *data, __u16 size,
+   int timeout)
+{
+   __u8 type = USB_TYPE_CLASS | USB_RECIP_INTERFACE;
+   unsigned int pipe;
+   int ret;
+
+   pipe = (query & 0x80) ? usb_rcvctrlpipe(dev->udev, 0)
+ : usb_sndctrlpipe(dev->udev, 0);
+   type |= (query & 0x80) ? USB_DIR_IN : USB_DIR_OUT;
+
+   uvc_trace(UVC_TRACE_QUERY,
+   "%s (%d): size=%d, unit=%d, cs=%d, intf=%d\n",
+   uvc_query_name(query), query, size, unit, cs, intfnum);
+   uvc_trace(UVC_TRACE_QUERY, "Sent:\n");
+   uvc_print_hex_dump(UVC_TRACE_QUERY, data, size);
+
+   ret = usb_control_msg(dev->udev, pipe, query, type, cs << 8,
+   unit << 8 | intfnum, data, size, timeout);
+   if (ret == -EPIPE)
+   uvc_trace(UVC_TRACE_QUERY, "Got device STALL on query!\n");
+
+   uvc_trace(UVC_TRACE_QUERY, "Received:\n");
+   uvc_print_hex_dump(UVC_TRACE_QUERY, data, size);
+
+   return ret;
+}
+
 int uvc_query_ctrl(struct uvc_device *dev, __u8 query, __u8 unit,
__u8 intfnum, __u8 cs, void *data, __u16 size)
 {
diff --git a/drivers/media/usb/uvc/uvcvideo.h b/drivers/media/usb/uvc/uvcvideo.h
index 9e35982..75e0153 100644
--- a/drivers/media/usb/uvc/uvcvideo.h
+++ b/drivers/media/usb/uvc/uvcvideo.h
@@ -574,6 +574,7 @@ struct uvc_driver {
 #define UVC_TRACE_VIDEO(1 << 10)
 #define UVC_TRACE_STATS(1 << 11)
 #define UVC_TRACE_CLOCK(1 << 12)
+#define UVC_TRACE_QUERY(1 << 13)
 
 #define UVC_WARN_MINMAX0
 #define UVC_WARN_PROBE_DEF 1
@@ -599,6 +600,14 @@ extern unsigned int uvc_timeout_param;
 #define uvc_printk(level, msg...) \
printk(level "uvcvideo: " msg)
 
+#define uvc_print_hex_dump(flag, buf, len) \
+   do { \
+   if (uvc_trace_param & flag) { \
+   print_hex_dump(KERN_DEBUG, "uvcvideo: ", \
+   DUMP_PREFIX_NONE, 16, 1, buf, len, false); \
+   } \
+   } while (0)
+
 /* --
  * Internal functions.
  */
-- 
1.8.4

--
To unsubscribe from this list: send the line "unsubscribe linux-media" in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


[PATCH v1 05/19] uvcvideo: Add support for UVC1.5 P&C control.

2013-08-29 Thread Pawel Osciak
Add support for UVC 1.5 Probe & Commit control.

Signed-off-by: Pawel Osciak 
---
 drivers/media/usb/uvc/uvc_video.c | 52 ---
 include/uapi/linux/usb/video.h|  7 ++
 2 files changed, 55 insertions(+), 4 deletions(-)

diff --git a/drivers/media/usb/uvc/uvc_video.c 
b/drivers/media/usb/uvc/uvc_video.c
index 1198989..b4ebccd 100644
--- a/drivers/media/usb/uvc/uvc_video.c
+++ b/drivers/media/usb/uvc/uvc_video.c
@@ -168,14 +168,25 @@ static void uvc_fixup_video_ctrl(struct uvc_streaming 
*stream,
}
 }
 
+int uvc_get_probe_ctrl_size(struct uvc_streaming *stream)
+{
+   if (stream->dev->uvc_version < 0x0110)
+   return 26;
+   else if (stream->dev->uvc_version < 0x0150)
+   return 34;
+   else
+   return 48;
+}
+
 static int uvc_get_video_ctrl(struct uvc_streaming *stream,
struct uvc_streaming_control *ctrl, int probe, __u8 query)
 {
__u8 *data;
__u16 size;
int ret;
+   int i;
 
-   size = stream->dev->uvc_version >= 0x0110 ? 34 : 26;
+   size = uvc_get_probe_ctrl_size(stream);
if ((stream->dev->quirks & UVC_QUIRK_PROBE_DEF) &&
query == UVC_GET_DEF)
return -EIO;
@@ -230,7 +241,7 @@ static int uvc_get_video_ctrl(struct uvc_streaming *stream,
ctrl->dwMaxVideoFrameSize = get_unaligned_le32(&data[18]);
ctrl->dwMaxPayloadTransferSize = get_unaligned_le32(&data[22]);
 
-   if (size == 34) {
+   if (size >= 34) {
ctrl->dwClockFrequency = get_unaligned_le32(&data[26]);
ctrl->bmFramingInfo = data[30];
ctrl->bPreferedVersion = data[31];
@@ -244,6 +255,26 @@ static int uvc_get_video_ctrl(struct uvc_streaming *stream,
ctrl->bMaxVersion = 0;
}
 
+   if (size >= 48) {
+   ctrl->bUsage = data[34];
+   ctrl->bBitDepthLuma = data[35];
+   ctrl->bmSetting = data[36];
+   ctrl->bMaxNumberOfRefFramesPlus1 = data[37];
+   ctrl->bmRateControlModes = get_unaligned_le16(&data[38]);
+   for (i = 0; i < ARRAY_SIZE(ctrl->bmLayoutPerStream); ++i) {
+   ctrl->bmLayoutPerStream[i] =
+   get_unaligned_le16(&data[40 + i * 2]);
+   }
+   } else {
+   ctrl->bUsage = 0;
+   ctrl->bBitDepthLuma = 0;
+   ctrl->bmSetting = 0;
+   ctrl->bMaxNumberOfRefFramesPlus1 = 0;
+   ctrl->bmRateControlModes = 0;
+   for (i = 0; i < ARRAY_SIZE(ctrl->bmLayoutPerStream); ++i)
+   ctrl->bmLayoutPerStream[i] = 0;
+   }
+
/* Some broken devices return null or wrong dwMaxVideoFrameSize and
 * dwMaxPayloadTransferSize fields. Try to get the value from the
 * format and frame descriptors.
@@ -262,8 +293,9 @@ static int uvc_set_video_ctrl(struct uvc_streaming *stream,
__u8 *data;
__u16 size;
int ret;
+   int i;
 
-   size = stream->dev->uvc_version >= 0x0110 ? 34 : 26;
+   size = uvc_get_probe_ctrl_size(stream);
data = kzalloc(size, GFP_KERNEL);
if (data == NULL)
return -ENOMEM;
@@ -280,7 +312,7 @@ static int uvc_set_video_ctrl(struct uvc_streaming *stream,
put_unaligned_le32(ctrl->dwMaxVideoFrameSize, &data[18]);
put_unaligned_le32(ctrl->dwMaxPayloadTransferSize, &data[22]);
 
-   if (size == 34) {
+   if (size >= 34) {
put_unaligned_le32(ctrl->dwClockFrequency, &data[26]);
data[30] = ctrl->bmFramingInfo;
data[31] = ctrl->bPreferedVersion;
@@ -288,6 +320,18 @@ static int uvc_set_video_ctrl(struct uvc_streaming *stream,
data[33] = ctrl->bMaxVersion;
}
 
+   if (size >= 48) {
+   data[34] = ctrl->bUsage;
+   data[35] = ctrl->bBitDepthLuma;
+   data[36] = ctrl->bmSetting;
+   data[37] = ctrl->bMaxNumberOfRefFramesPlus1;
+   *(__le16 *)&data[38] = cpu_to_le16(ctrl->bmRateControlModes);
+   for (i = 0; i < ARRAY_SIZE(ctrl->bmLayoutPerStream); ++i) {
+   *(__le16 *)&data[40 + i * 2] =
+   cpu_to_le16(ctrl->bmLayoutPerStream[i]);
+   }
+   }
+
ret = __uvc_query_ctrl(stream->dev, UVC_SET_CUR, 0, stream->intfnum,
probe ? UVC_VS_PROBE_CONTROL : UVC_VS_COMMIT_CONTROL, data,
size, uvc_timeout_param);
diff --git a/include/uapi/linux/usb/video.h b/include/uapi/linux/usb/video.h
index 3b3b95e..331c071 100644
--- a/include/uapi/linux/usb/video.h
+++ b/include/uapi/linux/usb/video.h
@@ -432,

[PATCH v1 18/19] v4l: Add V4L2_PIX_FMT_VP8_SIMULCAST format.

2013-08-29 Thread Pawel Osciak
This format is used by UVC 1.5 VP8-encoding cameras. When it is used, the camera
may encode captured frames into one or more streams, each of which may
be configured differently. This allows simultaneous capture of streams
with different resolutions, bitrates, and other settings, depending on the
camera capabilities.

Signed-off-by: Pawel Osciak 
---
 include/uapi/linux/videodev2.h | 4 
 1 file changed, 4 insertions(+)

diff --git a/include/uapi/linux/videodev2.h b/include/uapi/linux/videodev2.h
index c011ee0..8b0d4ad 100644
--- a/include/uapi/linux/videodev2.h
+++ b/include/uapi/linux/videodev2.h
@@ -402,6 +402,7 @@ struct v4l2_pix_format {
 #define V4L2_PIX_FMT_VC1_ANNEX_G v4l2_fourcc('V', 'C', '1', 'G') /* SMPTE 421M 
Annex G compliant stream */
 #define V4L2_PIX_FMT_VC1_ANNEX_L v4l2_fourcc('V', 'C', '1', 'L') /* SMPTE 421M 
Annex L compliant stream */
 #define V4L2_PIX_FMT_VP8  v4l2_fourcc('V', 'P', '8', '0') /* VP8 */
+#define V4L2_PIX_FMT_VP8_SIMULCAST v4l2_fourcc('V', 'P', '8', 'S') /* VP8 
simulcast */
 
 /*  Vendor-specific formats   */
 #define V4L2_PIX_FMT_CPIA1v4l2_fourcc('C', 'P', 'I', 'A') /* cpia1 YUV */
@@ -691,6 +692,9 @@ struct v4l2_buffer {
 #define V4L2_BUF_FLAG_PREV_FRAME   0x1  /* VP8 prev frame */
 #define V4L2_BUF_FLAG_GOLDEN_FRAME 0x2  /* VP8 golden frame */
 #define V4L2_BUF_FLAG_ALTREF_FRAME 0x4  /* VP8 altref frame */
+/* Simulcast layer structure. */
+#define V4L2_BUF_FLAG_LAYER_STRUCTURE_SHIFT19  /* Bits 19-20 for layer */
+#define V4L2_BUF_FLAG_LAYER_STRUCTURE_MASK 0x3 /* structure information. */
 
 /**
  * struct v4l2_exportbuffer - export of video buffer as DMABUF file descriptor
-- 
1.8.4

--
To unsubscribe from this list: send the line "unsubscribe linux-media" in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


[PATCH v1 10/19] uvcvideo: Support UVC 1.5 runtime control property.

2013-08-29 Thread Pawel Osciak
UVC 1.5 introduces the concept of runtime controls, which can be set during
streaming. Non-runtime controls can only be changed while device is idle.

Signed-off-by: Pawel Osciak 
---
 drivers/media/usb/uvc/uvc_ctrl.c | 45 +---
 drivers/media/usb/uvc/uvc_v4l2.c | 18 ++--
 drivers/media/usb/uvc/uvcvideo.h | 12 +++
 3 files changed, 57 insertions(+), 18 deletions(-)

diff --git a/drivers/media/usb/uvc/uvc_ctrl.c b/drivers/media/usb/uvc/uvc_ctrl.c
index d735c88..b0a19b9 100644
--- a/drivers/media/usb/uvc/uvc_ctrl.c
+++ b/drivers/media/usb/uvc/uvc_ctrl.c
@@ -1076,8 +1076,19 @@ void __uvc_ctrl_unlock(struct uvc_video_chain *chain)
mutex_unlock(&chain->pipeline->ctrl_mutex);
 }
 
+static int uvc_check_ctrl_runtime(struct uvc_control *ctrl, bool streaming)
+{
+   if (streaming && !ctrl->in_runtime) {
+   uvc_trace(UVC_TRACE_CONTROL,
+   "Control disabled while streaming\n");
+   return -EBUSY;
+   }
+
+   return 0;
+}
+
 int uvc_query_v4l2_ctrl(struct uvc_video_chain *chain,
-   struct v4l2_queryctrl *v4l2_ctrl)
+   struct v4l2_queryctrl *v4l2_ctrl, bool streaming)
 {
struct uvc_control *ctrl;
struct uvc_control_mapping *mapping;
@@ -1093,6 +1104,10 @@ int uvc_query_v4l2_ctrl(struct uvc_video_chain *chain,
goto done;
}
 
+   ret = uvc_check_ctrl_runtime(ctrl, streaming);
+   if (ret < 0)
+   goto done;
+
ret = __uvc_query_v4l2_ctrl(chain, ctrl, mapping, v4l2_ctrl);
 done:
__uvc_ctrl_unlock(chain);
@@ -1109,7 +1124,7 @@ done:
  * manually.
  */
 int uvc_query_v4l2_menu(struct uvc_video_chain *chain,
-   struct v4l2_querymenu *query_menu)
+   struct v4l2_querymenu *query_menu, bool streaming)
 {
struct uvc_menu_info *menu_info;
struct uvc_control_mapping *mapping;
@@ -1132,6 +1147,10 @@ int uvc_query_v4l2_menu(struct uvc_video_chain *chain,
goto done;
}
 
+   ret = uvc_check_ctrl_runtime(ctrl, streaming);
+   if (ret < 0)
+   goto done;
+
if (query_menu->index >= mapping->menu_count) {
ret = -EINVAL;
goto done;
@@ -1436,21 +1455,26 @@ done:
return ret;
 }
 
-int uvc_ctrl_get(struct uvc_video_chain *chain,
-   struct v4l2_ext_control *xctrl)
+int uvc_ctrl_get(struct uvc_video_chain *chain, struct v4l2_ext_control *xctrl,
+bool streaming)
 {
struct uvc_control *ctrl;
struct uvc_control_mapping *mapping;
+   int ret;
 
ctrl = uvc_find_control(chain, xctrl->id, &mapping);
if (ctrl == NULL)
return -EINVAL;
 
+   ret = uvc_check_ctrl_runtime(ctrl, streaming);
+   if (ret < 0)
+   return ret;
+
return __uvc_ctrl_get(chain, ctrl, mapping, &xctrl->value);
 }
 
-int uvc_ctrl_set(struct uvc_video_chain *chain,
-   struct v4l2_ext_control *xctrl)
+int uvc_ctrl_set(struct uvc_video_chain *chain, struct v4l2_ext_control *xctrl,
+bool streaming)
 {
struct uvc_control *ctrl;
struct uvc_control_mapping *mapping;
@@ -1466,6 +1490,10 @@ int uvc_ctrl_set(struct uvc_video_chain *chain,
if (!(ctrl->info.flags & UVC_CTRL_FLAG_SET_CUR))
return -EACCES;
 
+   ret = uvc_check_ctrl_runtime(ctrl, streaming);
+   if (ret < 0)
+   return ret;
+
/* Clamp out of range values. */
switch (mapping->v4l2_type) {
case V4L2_CTRL_TYPE_INTEGER:
@@ -1885,8 +1913,9 @@ static int uvc_ctrl_add_info(struct uvc_device *dev, 
struct uvc_control *ctrl,
ctrl->initialized = 1;
 
uvc_trace(UVC_TRACE_CONTROL, "Added control %pUl/%u to device %s "
-   "entity %u\n", ctrl->info.entity, ctrl->info.selector,
-   dev->udev->devpath, ctrl->entity->id);
+   "entity %u, init/runtime %d/%d\n", ctrl->info.entity,
+   ctrl->info.selector, dev->udev->devpath, ctrl->entity->id,
+   ctrl->on_init, ctrl->in_runtime);
 
 done:
if (ret < 0)
diff --git a/drivers/media/usb/uvc/uvc_v4l2.c b/drivers/media/usb/uvc/uvc_v4l2.c
index a899159..decd65f 100644
--- a/drivers/media/usb/uvc/uvc_v4l2.c
+++ b/drivers/media/usb/uvc/uvc_v4l2.c
@@ -597,7 +597,8 @@ static long uvc_v4l2_do_ioctl(struct file *file, unsigned 
int cmd, void *arg)
 
/* Get, Set & Query control */
case VIDIOC_QUERYCTRL:
-   return uvc_query_v4l2_ctrl(chain, arg);
+   return uvc_query_v4l2_ctrl(chain, arg,
+   uvc_is_stream_streaming(stream));
 
case VIDIOC_G_CTRL:
{
@@ -611,7 +612,8 @@ static long uvc_v4l2_do_ioctl(struct file *file, unsigned 
int cmd, void 

[PATCH v1 16/19] v4l: Add encoding camera controls.

2013-08-29 Thread Pawel Osciak
Add defines for controls found in UVC 1.5 encoding cameras.

Signed-off-by: Pawel Osciak 
---
 drivers/media/v4l2-core/v4l2-ctrls.c | 29 +
 include/uapi/linux/v4l2-controls.h   | 31 +++
 2 files changed, 60 insertions(+)

diff --git a/drivers/media/v4l2-core/v4l2-ctrls.c 
b/drivers/media/v4l2-core/v4l2-ctrls.c
index c3f0803..0b3a632 100644
--- a/drivers/media/v4l2-core/v4l2-ctrls.c
+++ b/drivers/media/v4l2-core/v4l2-ctrls.c
@@ -781,6 +781,35 @@ const char *v4l2_ctrl_get_name(u32 id)
case V4L2_CID_AUTO_FOCUS_STATUS:return "Auto Focus, Status";
case V4L2_CID_AUTO_FOCUS_RANGE: return "Auto Focus, Range";
 
+   case V4L2_CID_ENCODER_MIN_FRAME_INTERVAL: return "Encoder, min. frame 
interval";
+   case V4L2_CID_ENCODER_RATE_CONTROL_MODE: return "Encoder, rate control 
mode";
+   case V4L2_CID_ENCODER_AVERAGE_BITRATE:  return "Encoder, average 
bitrate";
+   case V4L2_CID_ENCODER_CPB_SIZE: return "Encoder, CPB size";
+   case V4L2_CID_ENCODER_PEAK_BIT_RATE:return "Encoder, peak bit rate";
+   case V4L2_CID_ENCODER_QP_PARAM_I:   return "Encoder, QP param for I 
frames";
+   case V4L2_CID_ENCODER_QP_PARAM_P:   return "Encoder, QP param for P 
frames";
+   case V4L2_CID_ENCODER_QP_PARAM_BG:  return "Encoder, QP param for 
B/G frames";
+   case V4L2_CID_ENCODER_NUM_GDR_FRAMES:   return "Encoder, number of GDR 
frames";
+   case V4L2_CID_ENCODER_LTR_BUFFER_CONTROL: return "Encoder, LTR buffer 
control";
+   case V4L2_CID_ENCODER_LTR_BUFFER_TRUST_MODE: return "Encoder, LTR 
buffer trust mode";
+   case V4L2_CID_ENCODER_LTR_PICTURE_POSITION: return "Encoder, LTR 
picture position";
+   case V4L2_CID_ENCODER_LTR_PICTURE_MODE: return "Encoder, LTR picture 
mode";
+   case V4L2_CID_ENCODER_LTR_VALIDATION:   return "Encoder, LTR 
validation";
+   case V4L2_CID_ENCODER_MIN_QP:   return "Encoder, minimum QP 
param";
+   case V4L2_CID_ENCODER_MAX_QP:   return "Encoder, maximum QP 
param";
+   case V4L2_CID_ENCODER_SYNC_FRAME_INTERVAL: return "Encoder, sync frame 
interval";
+   case V4L2_CID_ENCODER_ERROR_RESILIENCY: return "Encoder, error 
resiliency";
+   case V4L2_CID_ENCODER_TEMPORAL_LAYER_ENABLE: return "Encoder, temporal 
layer enable";
+
+   case V4L2_CID_ENCODER_VP8_SLICE_MODE:   return "Encoder, VP8 slice 
mode";
+   case V4L2_CID_ENCODER_VP8_SYNC_FRAME_TYPE: return "Encoder, VP8 sync 
frame type";
+   case V4L2_CID_ENCODER_VP8_DCT_PARTS_PER_FRAME: return "Encoder, VP8, 
DCT partitions per frame";
+
+   case V4L2_CID_ENCODER_H264_PROFILE_TOOLSET: return "Encoder, H.264 
profile and toolset";
+   case V4L2_CID_ENCODER_H264_LEVEL_IDC_LIMIT: return "Encoder, H.264 
level IDC limit";
+   case V4L2_CID_ENCODER_H264_SEI_PAYLOAD_TYPE: return "Encoder, H.264 SEI 
payload type";
+   case V4L2_CID_ENCODER_H264_LAYER_PRIORITY: return "Encoder, H.264 layer 
priority";
+
/* FM Radio Modulator control */
/* Keep the order of the 'case's the same as in videodev2.h! */
case V4L2_CID_FM_TX_CLASS:  return "FM Radio Modulator 
Controls";
diff --git a/include/uapi/linux/v4l2-controls.h 
b/include/uapi/linux/v4l2-controls.h
index 083bb5a..ef3a30d 100644
--- a/include/uapi/linux/v4l2-controls.h
+++ b/include/uapi/linux/v4l2-controls.h
@@ -729,6 +729,37 @@ enum v4l2_auto_focus_range {
V4L2_AUTO_FOCUS_RANGE_INFINITY  = 3,
 };
 
+/* Controls found in UVC 1.5 encoding cameras */
+#define V4L2_CID_ENCODER_MIN_FRAME_INTERVAL(V4L2_CID_CAMERA_CLASS_BASE+32)
+#define V4L2_CID_ENCODER_RATE_CONTROL_MODE (V4L2_CID_CAMERA_CLASS_BASE+33)
+#define V4L2_CID_ENCODER_AVERAGE_BITRATE   (V4L2_CID_CAMERA_CLASS_BASE+34)
+#define V4L2_CID_ENCODER_CPB_SIZE  (V4L2_CID_CAMERA_CLASS_BASE+35)
+#define V4L2_CID_ENCODER_PEAK_BIT_RATE (V4L2_CID_CAMERA_CLASS_BASE+36)
+#define V4L2_CID_ENCODER_QP_PARAM_I(V4L2_CID_CAMERA_CLASS_BASE+37)
+#define V4L2_CID_ENCODER_QP_PARAM_P(V4L2_CID_CAMERA_CLASS_BASE+38)
+#define V4L2_CID_ENCODER_QP_PARAM_BG   (V4L2_CID_CAMERA_CLASS_BASE+39)
+#define V4L2_CID_ENCODER_NUM_GDR_FRAMES
(V4L2_CID_CAMERA_CLASS_BASE+40)
+#define V4L2_CID_ENCODER_LTR_BUFFER_CONTROL(V4L2_CID_CAMERA_CLASS_BASE+41)
+#define V4L2_CID_ENCODER_LTR_BUFFER_TRUST_MODE (V4L2_CID_CAMERA_CLASS_BASE+42)
+#define V4L2_CID_ENCODER_LTR_PICTURE_POSITION  (V4L2_CID_CAMERA_CLASS_BASE+43)
+#define V4L2_CID_ENCODER_LTR_PICTURE_MODE  (V4L2_CID_CAMERA_CLASS_BASE+44)
+#define V4L2_CID_ENCODER_LTR_VALIDATION   

[PATCH v1 04/19] uvcvideo: Create separate debugfs entries for each streaming interface.

2013-08-29 Thread Pawel Osciak
Add interface number to debugfs entry name to be able to create separate
entries for each streaming interface for devices exposing more than one,
instead of failing to create more than one.

Signed-off-by: Pawel Osciak 
---
 drivers/media/usb/uvc/uvc_debugfs.c | 3 ++-
 1 file changed, 2 insertions(+), 1 deletion(-)

diff --git a/drivers/media/usb/uvc/uvc_debugfs.c 
b/drivers/media/usb/uvc/uvc_debugfs.c
index 14561a5..0663fbd 100644
--- a/drivers/media/usb/uvc/uvc_debugfs.c
+++ b/drivers/media/usb/uvc/uvc_debugfs.c
@@ -84,7 +84,8 @@ int uvc_debugfs_init_stream(struct uvc_streaming *stream)
if (uvc_debugfs_root_dir == NULL)
return -ENODEV;
 
-   sprintf(dir_name, "%u-%u", udev->bus->busnum, udev->devnum);
+   sprintf(dir_name, "%u-%u-%u", udev->bus->busnum, udev->devnum,
+   stream->intfnum);
 
dent = debugfs_create_dir(dir_name, uvc_debugfs_root_dir);
if (IS_ERR_OR_NULL(dent)) {
-- 
1.8.4

--
To unsubscribe from this list: send the line "unsubscribe linux-media" in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


[PATCH v1 12/19] uvcvideo: Reorganize next buffer handling.

2013-08-29 Thread Pawel Osciak
Move getting the first buffer from the current queue to a uvc_queue function
and out of the USB completion handler.

Signed-off-by: Pawel Osciak 
---
 drivers/media/usb/uvc/uvc_isight.c |  6 --
 drivers/media/usb/uvc/uvc_queue.c  | 14 ++
 drivers/media/usb/uvc/uvc_video.c  | 29 -
 drivers/media/usb/uvc/uvcvideo.h   |  7 +++
 4 files changed, 33 insertions(+), 23 deletions(-)

diff --git a/drivers/media/usb/uvc/uvc_isight.c 
b/drivers/media/usb/uvc/uvc_isight.c
index 8510e72..ab01286 100644
--- a/drivers/media/usb/uvc/uvc_isight.c
+++ b/drivers/media/usb/uvc/uvc_isight.c
@@ -99,10 +99,12 @@ static int isight_decode(struct uvc_video_queue *queue, 
struct uvc_buffer *buf,
return 0;
 }
 
-void uvc_video_decode_isight(struct urb *urb, struct uvc_streaming *stream,
-   struct uvc_buffer *buf)
+void uvc_video_decode_isight(struct urb *urb, struct uvc_streaming *stream)
 {
int ret, i;
+   struct uvc_buffer *buf;
+
+   buf = uvc_queue_get_first_buf(&stream->queue);
 
for (i = 0; i < urb->number_of_packets; ++i) {
if (urb->iso_frame_desc[i].status < 0) {
diff --git a/drivers/media/usb/uvc/uvc_queue.c 
b/drivers/media/usb/uvc/uvc_queue.c
index cd962be..55d2670 100644
--- a/drivers/media/usb/uvc/uvc_queue.c
+++ b/drivers/media/usb/uvc/uvc_queue.c
@@ -352,6 +352,20 @@ void uvc_queue_cancel(struct uvc_video_queue *queue, int 
disconnect)
spin_unlock_irqrestore(&queue->irqlock, flags);
 }
 
+struct uvc_buffer *uvc_queue_get_first_buf(struct uvc_video_queue *queue)
+{
+   struct uvc_buffer *buf = NULL;
+   unsigned long flags;
+
+   spin_lock_irqsave(&queue->irqlock, flags);
+   if (!list_empty(&queue->irqqueue))
+   buf = list_first_entry(&queue->irqqueue, struct uvc_buffer,
+   queue);
+   spin_unlock_irqrestore(&queue->irqlock, flags);
+
+   return buf;
+}
+
 struct uvc_buffer *uvc_queue_next_buffer(struct uvc_video_queue *queue,
struct uvc_buffer *buf)
 {
diff --git a/drivers/media/usb/uvc/uvc_video.c 
b/drivers/media/usb/uvc/uvc_video.c
index b4ebccd..2f9a5fa 100644
--- a/drivers/media/usb/uvc/uvc_video.c
+++ b/drivers/media/usb/uvc/uvc_video.c
@@ -1193,11 +1193,11 @@ static int uvc_video_encode_data(struct uvc_streaming 
*stream,
 /*
  * Completion handler for video URBs.
  */
-static void uvc_video_decode_isoc(struct urb *urb, struct uvc_streaming 
*stream,
-   struct uvc_buffer *buf)
+static void uvc_video_decode_isoc(struct urb *urb, struct uvc_streaming 
*stream)
 {
u8 *mem;
int ret, i;
+   struct uvc_buffer *buf = NULL;
 
for (i = 0; i < urb->number_of_packets; ++i) {
if (urb->iso_frame_desc[i].status < 0) {
@@ -1211,6 +1211,7 @@ static void uvc_video_decode_isoc(struct urb *urb, struct 
uvc_streaming *stream,
 
/* Decode the payload header. */
mem = urb->transfer_buffer + urb->iso_frame_desc[i].offset;
+   buf = uvc_queue_get_first_buf(&stream->queue);
do {
ret = uvc_video_decode_start(stream, buf, mem,
urb->iso_frame_desc[i].actual_length);
@@ -1241,11 +1242,11 @@ static void uvc_video_decode_isoc(struct urb *urb, 
struct uvc_streaming *stream,
}
 }
 
-static void uvc_video_decode_bulk(struct urb *urb, struct uvc_streaming 
*stream,
-   struct uvc_buffer *buf)
+static void uvc_video_decode_bulk(struct urb *urb, struct uvc_streaming 
*stream)
 {
u8 *mem;
int len, ret;
+   struct uvc_buffer *buf;
 
/*
 * Ignore ZLPs if they're not part of a frame, otherwise process them
@@ -1258,6 +1259,8 @@ static void uvc_video_decode_bulk(struct urb *urb, struct 
uvc_streaming *stream,
len = urb->actual_length;
stream->bulk.payload_size += len;
 
+   buf = uvc_queue_get_first_buf(&stream->queue);
+
/* If the URB is the first of its payload, decode and save the
 * header.
 */
@@ -1309,12 +1312,13 @@ static void uvc_video_decode_bulk(struct urb *urb, 
struct uvc_streaming *stream,
}
 }
 
-static void uvc_video_encode_bulk(struct urb *urb, struct uvc_streaming 
*stream,
-   struct uvc_buffer *buf)
+static void uvc_video_encode_bulk(struct urb *urb, struct uvc_streaming 
*stream)
 {
u8 *mem = urb->transfer_buffer;
int len = stream->urb_size, ret;
+   struct uvc_buffer *buf;
 
+   buf = uvc_queue_get_first_buf(&stream->queue);
if (buf == NULL) {
urb->transfer_buffer_length = 0;
return;
@@ -1355,9 +1359,6 @@ static void uvc_video_encode_bulk(struct urb *urb, struct 
uvc_streaming *stream,
 static void uvc_video_complete(struct urb *urb)
 {
struct uvc_streaming *stream = urb->c

Re: [PATCH] [media] v4l2: mem2mem: save irq flags correctly

2013-05-28 Thread Pawel Osciak
John, thanks for the patch.

On Thu, May 23, 2013 at 5:41 PM, John Sheu  wrote:
> Save flags correctly when taking spinlocks in v4l2_m2m_try_schedule.
>
> Signed-off-by: John Sheu 

Acked-by: Pawel Osciak 


> ---
>  drivers/media/v4l2-core/v4l2-mem2mem.c | 19 +++
>  1 file changed, 11 insertions(+), 8 deletions(-)
>
> diff --git a/drivers/media/v4l2-core/v4l2-mem2mem.c 
> b/drivers/media/v4l2-core/v4l2-mem2mem.c
> index 66f599f..3606ff2 100644
> --- a/drivers/media/v4l2-core/v4l2-mem2mem.c
> +++ b/drivers/media/v4l2-core/v4l2-mem2mem.c
> @@ -205,7 +205,7 @@ static void v4l2_m2m_try_run(struct v4l2_m2m_dev *m2m_dev)
>  static void v4l2_m2m_try_schedule(struct v4l2_m2m_ctx *m2m_ctx)
>  {
> struct v4l2_m2m_dev *m2m_dev;
> -   unsigned long flags_job, flags;
> +   unsigned long flags_job, flags_out, flags_cap;
>
> m2m_dev = m2m_ctx->m2m_dev;
> dprintk("Trying to schedule a job for m2m_ctx: %p\n", m2m_ctx);
> @@ -223,23 +223,26 @@ static void v4l2_m2m_try_schedule(struct v4l2_m2m_ctx 
> *m2m_ctx)
> return;
> }
>
> -   spin_lock_irqsave(&m2m_ctx->out_q_ctx.rdy_spinlock, flags);
> +   spin_lock_irqsave(&m2m_ctx->out_q_ctx.rdy_spinlock, flags_out);
> if (list_empty(&m2m_ctx->out_q_ctx.rdy_queue)) {
> -   spin_unlock_irqrestore(&m2m_ctx->out_q_ctx.rdy_spinlock, 
> flags);
> +   spin_unlock_irqrestore(&m2m_ctx->out_q_ctx.rdy_spinlock,
> +   flags_out);
> spin_unlock_irqrestore(&m2m_dev->job_spinlock, flags_job);
> dprintk("No input buffers available\n");
> return;
> }
> -   spin_lock_irqsave(&m2m_ctx->cap_q_ctx.rdy_spinlock, flags);
> +   spin_lock_irqsave(&m2m_ctx->cap_q_ctx.rdy_spinlock, flags_cap);
> if (list_empty(&m2m_ctx->cap_q_ctx.rdy_queue)) {
> -   spin_unlock_irqrestore(&m2m_ctx->cap_q_ctx.rdy_spinlock, 
> flags);
> -   spin_unlock_irqrestore(&m2m_ctx->out_q_ctx.rdy_spinlock, 
> flags);
> +   spin_unlock_irqrestore(&m2m_ctx->cap_q_ctx.rdy_spinlock,
> +   flags_cap);
> +   spin_unlock_irqrestore(&m2m_ctx->out_q_ctx.rdy_spinlock,
> +   flags_out);
> spin_unlock_irqrestore(&m2m_dev->job_spinlock, flags_job);
> dprintk("No output buffers available\n");
> return;
> }
> -   spin_unlock_irqrestore(&m2m_ctx->cap_q_ctx.rdy_spinlock, flags);
> -   spin_unlock_irqrestore(&m2m_ctx->out_q_ctx.rdy_spinlock, flags);
> +   spin_unlock_irqrestore(&m2m_ctx->cap_q_ctx.rdy_spinlock, flags_cap);
> +   spin_unlock_irqrestore(&m2m_ctx->out_q_ctx.rdy_spinlock, flags_out);
>
> if (m2m_dev->m2m_ops->job_ready
> && (!m2m_dev->m2m_ops->job_ready(m2m_ctx->priv))) {
> --
> 1.8.2.1
>



--
Best regards,
Pawel Osciak
--
To unsubscribe from this list: send the line "unsubscribe linux-media" in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


  1   2   3   4   >