aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorMarek Szyprowski <m.szyprowski@samsung.com>2011-08-24 05:49:35 -0400
committerMauro Carvalho Chehab <mchehab@redhat.com>2011-09-06 14:04:09 -0400
commit25a27d91006091e28532053c95fa36b70b79d3ad (patch)
tree9012e2126e118b5579b149e99320c4e7ccea9ba8
parentc1426bc727b78808fb956f7402b689144c1506ee (diff)
[media] media: vb2: fix handling MAPPED buffer flag
MAPPED flag was set for the buffer only if all it's planes were mapped and relied on a simple mapping counter. This assumption is really bogus, especially because the buffers may be mapped multiple times. Also the meaning of this flag for muliplane buffers was not really useful. This patch fixes this issue by setting the MAPPED flag for the buffer if any of it's planes is in use (what means that has been mapped at least once), so MAPPED flag can be used as 'in_use' indicator. Reported-by: Hans Verkuil <hverkuil@xs4all.nl> Signed-off-by: Marek Szyprowski <m.szyprowski@samsung.com> Signed-off-by: Kyungmin Park <kyungmin.park@samsung.com> CC: Pawel Osciak <pawel@osciak.com> Tested-by: Hans Verkuil <hans.verkuil@cisco.com> Signed-off-by: Mauro Carvalho Chehab <mchehab@redhat.com>
-rw-r--r--drivers/media/video/videobuf2-core.c67
-rw-r--r--include/media/videobuf2-core.h3
2 files changed, 36 insertions, 34 deletions
diff --git a/drivers/media/video/videobuf2-core.c b/drivers/media/video/videobuf2-core.c
index c3606276607e..e89fd53a021a 100644
--- a/drivers/media/video/videobuf2-core.c
+++ b/drivers/media/video/videobuf2-core.c
@@ -277,6 +277,41 @@ static int __verify_planes_array(struct vb2_buffer *vb, struct v4l2_buffer *b)
277} 277}
278 278
279/** 279/**
280 * __buffer_in_use() - return true if the buffer is in use and
281 * the queue cannot be freed (by the means of REQBUFS(0)) call
282 */
283static bool __buffer_in_use(struct vb2_queue *q, struct vb2_buffer *vb)
284{
285 unsigned int plane;
286 for (plane = 0; plane < vb->num_planes; ++plane) {
287 /*
288 * If num_users() has not been provided, call_memop
289 * will return 0, apparently nobody cares about this
290 * case anyway. If num_users() returns more than 1,
291 * we are not the only user of the plane's memory.
292 */
293 if (call_memop(q, plane, num_users,
294 vb->planes[plane].mem_priv) > 1)
295 return true;
296 }
297 return false;
298}
299
300/**
301 * __buffers_in_use() - return true if any buffers on the queue are in use and
302 * the queue cannot be freed (by the means of REQBUFS(0)) call
303 */
304static bool __buffers_in_use(struct vb2_queue *q)
305{
306 unsigned int buffer;
307 for (buffer = 0; buffer < q->num_buffers; ++buffer) {
308 if (__buffer_in_use(q, q->bufs[buffer]))
309 return true;
310 }
311 return false;
312}
313
314/**
280 * __fill_v4l2_buffer() - fill in a struct v4l2_buffer with information to be 315 * __fill_v4l2_buffer() - fill in a struct v4l2_buffer with information to be
281 * returned to userspace 316 * returned to userspace
282 */ 317 */
@@ -335,7 +370,7 @@ static int __fill_v4l2_buffer(struct vb2_buffer *vb, struct v4l2_buffer *b)
335 break; 370 break;
336 } 371 }
337 372
338 if (vb->num_planes_mapped == vb->num_planes) 373 if (__buffer_in_use(q, vb))
339 b->flags |= V4L2_BUF_FLAG_MAPPED; 374 b->flags |= V4L2_BUF_FLAG_MAPPED;
340 375
341 return ret; 376 return ret;
@@ -400,33 +435,6 @@ static int __verify_mmap_ops(struct vb2_queue *q)
400} 435}
401 436
402/** 437/**
403 * __buffers_in_use() - return true if any buffers on the queue are in use and
404 * the queue cannot be freed (by the means of REQBUFS(0)) call
405 */
406static bool __buffers_in_use(struct vb2_queue *q)
407{
408 unsigned int buffer, plane;
409 struct vb2_buffer *vb;
410
411 for (buffer = 0; buffer < q->num_buffers; ++buffer) {
412 vb = q->bufs[buffer];
413 for (plane = 0; plane < vb->num_planes; ++plane) {
414 /*
415 * If num_users() has not been provided, call_memop
416 * will return 0, apparently nobody cares about this
417 * case anyway. If num_users() returns more than 1,
418 * we are not the only user of the plane's memory.
419 */
420 if (call_memop(q, plane, num_users,
421 vb->planes[plane].mem_priv) > 1)
422 return true;
423 }
424 }
425
426 return false;
427}
428
429/**
430 * vb2_reqbufs() - Initiate streaming 438 * vb2_reqbufs() - Initiate streaming
431 * @q: videobuf2 queue 439 * @q: videobuf2 queue
432 * @req: struct passed from userspace to vidioc_reqbufs handler in driver 440 * @req: struct passed from userspace to vidioc_reqbufs handler in driver
@@ -1343,9 +1351,6 @@ int vb2_mmap(struct vb2_queue *q, struct vm_area_struct *vma)
1343 if (ret) 1351 if (ret)
1344 return ret; 1352 return ret;
1345 1353
1346 vb_plane->mapped = 1;
1347 vb->num_planes_mapped++;
1348
1349 dprintk(3, "Buffer %d, plane %d successfully mapped\n", buffer, plane); 1354 dprintk(3, "Buffer %d, plane %d successfully mapped\n", buffer, plane);
1350 return 0; 1355 return 0;
1351} 1356}
diff --git a/include/media/videobuf2-core.h b/include/media/videobuf2-core.h
index 496d6e548ef5..984f2bae2578 100644
--- a/include/media/videobuf2-core.h
+++ b/include/media/videobuf2-core.h
@@ -75,7 +75,6 @@ struct vb2_mem_ops {
75 75
76struct vb2_plane { 76struct vb2_plane {
77 void *mem_priv; 77 void *mem_priv;
78 int mapped:1;
79}; 78};
80 79
81/** 80/**
@@ -147,7 +146,6 @@ struct vb2_queue;
147 * @done_entry: entry on the list that stores all buffers ready to 146 * @done_entry: entry on the list that stores all buffers ready to
148 * be dequeued to userspace 147 * be dequeued to userspace
149 * @planes: private per-plane information; do not change 148 * @planes: private per-plane information; do not change
150 * @num_planes_mapped: number of mapped planes; do not change
151 */ 149 */
152struct vb2_buffer { 150struct vb2_buffer {
153 struct v4l2_buffer v4l2_buf; 151 struct v4l2_buffer v4l2_buf;
@@ -164,7 +162,6 @@ struct vb2_buffer {
164 struct list_head done_entry; 162 struct list_head done_entry;
165 163
166 struct vb2_plane planes[VIDEO_MAX_PLANES]; 164 struct vb2_plane planes[VIDEO_MAX_PLANES];
167 unsigned int num_planes_mapped;
168}; 165};
169 166
170/** 167/**