diff options
author | Hans Verkuil <hans.verkuil@cisco.com> | 2018-05-12 10:44:00 -0400 |
---|---|---|
committer | Mauro Carvalho Chehab <mchehab+samsung@kernel.org> | 2018-05-28 15:57:17 -0400 |
commit | 1f5965c4dfd7665f2914a1f1095dcc6020656b04 (patch) | |
tree | 531462341750f55ef66498336b08a07c5b9de454 /drivers/media/usb/gspca | |
parent | 90b2da89a083e1395cb322521a42397c49ae4500 (diff) |
media: gspca: convert to vb2
The gspca core has its own buffere implementation. Use the
core VB 2 instead.
Signed-off-by: Hans Verkuil <hans.verkuil@cisco.com>
Reviewed-by: Hans de Goede <hdegoede@redhat.com>
Signed-off-by: Mauro Carvalho Chehab <mchehab+samsung@kernel.org>
Diffstat (limited to 'drivers/media/usb/gspca')
-rw-r--r-- | drivers/media/usb/gspca/Kconfig | 1 | ||||
-rw-r--r-- | drivers/media/usb/gspca/gspca.c | 906 | ||||
-rw-r--r-- | drivers/media/usb/gspca/gspca.h | 38 | ||||
-rw-r--r-- | drivers/media/usb/gspca/m5602/m5602_core.c | 4 | ||||
-rw-r--r-- | drivers/media/usb/gspca/vc032x.c | 2 |
5 files changed, 182 insertions, 769 deletions
diff --git a/drivers/media/usb/gspca/Kconfig b/drivers/media/usb/gspca/Kconfig index bc9a439745aa..d3b6665c342d 100644 --- a/drivers/media/usb/gspca/Kconfig +++ b/drivers/media/usb/gspca/Kconfig | |||
@@ -2,6 +2,7 @@ menuconfig USB_GSPCA | |||
2 | tristate "GSPCA based webcams" | 2 | tristate "GSPCA based webcams" |
3 | depends on VIDEO_V4L2 | 3 | depends on VIDEO_V4L2 |
4 | depends on INPUT || INPUT=n | 4 | depends on INPUT || INPUT=n |
5 | select VIDEOBUF2_VMALLOC | ||
5 | default m | 6 | default m |
6 | ---help--- | 7 | ---help--- |
7 | Say Y here if you want to enable selecting webcams based | 8 | Say Y here if you want to enable selecting webcams based |
diff --git a/drivers/media/usb/gspca/gspca.c b/drivers/media/usb/gspca/gspca.c index d29773b8f696..ff229d3aae0f 100644 --- a/drivers/media/usb/gspca/gspca.c +++ b/drivers/media/usb/gspca/gspca.c | |||
@@ -82,32 +82,6 @@ static void PDEBUG_MODE(struct gspca_dev *gspca_dev, int debug, char *txt, | |||
82 | #define GSPCA_MEMORY_NO 0 /* V4L2_MEMORY_xxx starts from 1 */ | 82 | #define GSPCA_MEMORY_NO 0 /* V4L2_MEMORY_xxx starts from 1 */ |
83 | #define GSPCA_MEMORY_READ 7 | 83 | #define GSPCA_MEMORY_READ 7 |
84 | 84 | ||
85 | #define BUF_ALL_FLAGS (V4L2_BUF_FLAG_QUEUED | V4L2_BUF_FLAG_DONE) | ||
86 | |||
87 | /* | ||
88 | * VMA operations. | ||
89 | */ | ||
90 | static void gspca_vm_open(struct vm_area_struct *vma) | ||
91 | { | ||
92 | struct gspca_frame *frame = vma->vm_private_data; | ||
93 | |||
94 | frame->vma_use_count++; | ||
95 | frame->v4l2_buf.flags |= V4L2_BUF_FLAG_MAPPED; | ||
96 | } | ||
97 | |||
98 | static void gspca_vm_close(struct vm_area_struct *vma) | ||
99 | { | ||
100 | struct gspca_frame *frame = vma->vm_private_data; | ||
101 | |||
102 | if (--frame->vma_use_count <= 0) | ||
103 | frame->v4l2_buf.flags &= ~V4L2_BUF_FLAG_MAPPED; | ||
104 | } | ||
105 | |||
106 | static const struct vm_operations_struct gspca_vm_ops = { | ||
107 | .open = gspca_vm_open, | ||
108 | .close = gspca_vm_close, | ||
109 | }; | ||
110 | |||
111 | /* | 85 | /* |
112 | * Input and interrupt endpoint handling functions | 86 | * Input and interrupt endpoint handling functions |
113 | */ | 87 | */ |
@@ -356,7 +330,7 @@ static void isoc_irq(struct urb *urb) | |||
356 | struct gspca_dev *gspca_dev = (struct gspca_dev *) urb->context; | 330 | struct gspca_dev *gspca_dev = (struct gspca_dev *) urb->context; |
357 | 331 | ||
358 | gspca_dbg(gspca_dev, D_PACK, "isoc irq\n"); | 332 | gspca_dbg(gspca_dev, D_PACK, "isoc irq\n"); |
359 | if (!gspca_dev->streaming) | 333 | if (!vb2_start_streaming_called(&gspca_dev->queue)) |
360 | return; | 334 | return; |
361 | fill_frame(gspca_dev, urb); | 335 | fill_frame(gspca_dev, urb); |
362 | } | 336 | } |
@@ -370,7 +344,7 @@ static void bulk_irq(struct urb *urb) | |||
370 | int st; | 344 | int st; |
371 | 345 | ||
372 | gspca_dbg(gspca_dev, D_PACK, "bulk irq\n"); | 346 | gspca_dbg(gspca_dev, D_PACK, "bulk irq\n"); |
373 | if (!gspca_dev->streaming) | 347 | if (!vb2_start_streaming_called(&gspca_dev->queue)) |
374 | return; | 348 | return; |
375 | switch (urb->status) { | 349 | switch (urb->status) { |
376 | case 0: | 350 | case 0: |
@@ -417,25 +391,24 @@ void gspca_frame_add(struct gspca_dev *gspca_dev, | |||
417 | const u8 *data, | 391 | const u8 *data, |
418 | int len) | 392 | int len) |
419 | { | 393 | { |
420 | struct gspca_frame *frame; | 394 | struct gspca_buffer *buf; |
421 | int i, j; | 395 | unsigned long flags; |
422 | 396 | ||
423 | gspca_dbg(gspca_dev, D_PACK, "add t:%d l:%d\n", packet_type, len); | 397 | gspca_dbg(gspca_dev, D_PACK, "add t:%d l:%d\n", packet_type, len); |
424 | 398 | ||
425 | if (packet_type == FIRST_PACKET) { | 399 | spin_lock_irqsave(&gspca_dev->qlock, flags); |
426 | i = atomic_read(&gspca_dev->fr_i); | 400 | buf = list_first_entry_or_null(&gspca_dev->buf_list, |
401 | typeof(*buf), list); | ||
402 | spin_unlock_irqrestore(&gspca_dev->qlock, flags); | ||
427 | 403 | ||
428 | /* if there are no queued buffer, discard the whole frame */ | 404 | if (packet_type == FIRST_PACKET) { |
429 | if (i == atomic_read(&gspca_dev->fr_q)) { | 405 | /* if there is no queued buffer, discard the whole frame */ |
406 | if (!buf) { | ||
430 | gspca_dev->last_packet_type = DISCARD_PACKET; | 407 | gspca_dev->last_packet_type = DISCARD_PACKET; |
431 | gspca_dev->sequence++; | 408 | gspca_dev->sequence++; |
432 | return; | 409 | return; |
433 | } | 410 | } |
434 | j = gspca_dev->fr_queue[i]; | 411 | gspca_dev->image = vb2_plane_vaddr(&buf->vb.vb2_buf, 0); |
435 | frame = &gspca_dev->frame[j]; | ||
436 | v4l2_get_timestamp(&frame->v4l2_buf.timestamp); | ||
437 | frame->v4l2_buf.sequence = gspca_dev->sequence++; | ||
438 | gspca_dev->image = frame->data; | ||
439 | gspca_dev->image_len = 0; | 412 | gspca_dev->image_len = 0; |
440 | } else { | 413 | } else { |
441 | switch (gspca_dev->last_packet_type) { | 414 | switch (gspca_dev->last_packet_type) { |
@@ -453,10 +426,10 @@ void gspca_frame_add(struct gspca_dev *gspca_dev, | |||
453 | 426 | ||
454 | /* append the packet to the frame buffer */ | 427 | /* append the packet to the frame buffer */ |
455 | if (len > 0) { | 428 | if (len > 0) { |
456 | if (gspca_dev->image_len + len > gspca_dev->frsz) { | 429 | if (gspca_dev->image_len + len > gspca_dev->pixfmt.sizeimage) { |
457 | gspca_err(gspca_dev, "frame overflow %d > %d\n", | 430 | gspca_err(gspca_dev, "frame overflow %d > %d\n", |
458 | gspca_dev->image_len + len, | 431 | gspca_dev->image_len + len, |
459 | gspca_dev->frsz); | 432 | gspca_dev->pixfmt.sizeimage); |
460 | packet_type = DISCARD_PACKET; | 433 | packet_type = DISCARD_PACKET; |
461 | } else { | 434 | } else { |
462 | /* !! image is NULL only when last pkt is LAST or DISCARD | 435 | /* !! image is NULL only when last pkt is LAST or DISCARD |
@@ -476,80 +449,23 @@ void gspca_frame_add(struct gspca_dev *gspca_dev, | |||
476 | * next first packet, wake up the application and advance | 449 | * next first packet, wake up the application and advance |
477 | * in the queue */ | 450 | * in the queue */ |
478 | if (packet_type == LAST_PACKET) { | 451 | if (packet_type == LAST_PACKET) { |
479 | i = atomic_read(&gspca_dev->fr_i); | 452 | spin_lock_irqsave(&gspca_dev->qlock, flags); |
480 | j = gspca_dev->fr_queue[i]; | 453 | list_del(&buf->list); |
481 | frame = &gspca_dev->frame[j]; | 454 | spin_unlock_irqrestore(&gspca_dev->qlock, flags); |
482 | frame->v4l2_buf.bytesused = gspca_dev->image_len; | 455 | buf->vb.vb2_buf.timestamp = ktime_get_ns(); |
483 | frame->v4l2_buf.flags = (frame->v4l2_buf.flags | 456 | vb2_set_plane_payload(&buf->vb.vb2_buf, 0, |
484 | | V4L2_BUF_FLAG_DONE) | 457 | gspca_dev->image_len); |
485 | & ~V4L2_BUF_FLAG_QUEUED; | 458 | buf->vb.sequence = gspca_dev->sequence++; |
486 | i = (i + 1) % GSPCA_MAX_FRAMES; | 459 | buf->vb.field = V4L2_FIELD_NONE; |
487 | atomic_set(&gspca_dev->fr_i, i); | ||
488 | wake_up_interruptible(&gspca_dev->wq); /* event = new frame */ | ||
489 | gspca_dbg(gspca_dev, D_FRAM, "frame complete len:%d\n", | 460 | gspca_dbg(gspca_dev, D_FRAM, "frame complete len:%d\n", |
490 | frame->v4l2_buf.bytesused); | 461 | gspca_dev->image_len); |
462 | vb2_buffer_done(&buf->vb.vb2_buf, VB2_BUF_STATE_DONE); | ||
491 | gspca_dev->image = NULL; | 463 | gspca_dev->image = NULL; |
492 | gspca_dev->image_len = 0; | 464 | gspca_dev->image_len = 0; |
493 | } | 465 | } |
494 | } | 466 | } |
495 | EXPORT_SYMBOL(gspca_frame_add); | 467 | EXPORT_SYMBOL(gspca_frame_add); |
496 | 468 | ||
497 | static int frame_alloc(struct gspca_dev *gspca_dev, struct file *file, | ||
498 | enum v4l2_memory memory, unsigned int count) | ||
499 | { | ||
500 | struct gspca_frame *frame; | ||
501 | unsigned int frsz; | ||
502 | int i; | ||
503 | |||
504 | frsz = gspca_dev->pixfmt.sizeimage; | ||
505 | gspca_dbg(gspca_dev, D_STREAM, "frame alloc frsz: %d\n", frsz); | ||
506 | frsz = PAGE_ALIGN(frsz); | ||
507 | if (count >= GSPCA_MAX_FRAMES) | ||
508 | count = GSPCA_MAX_FRAMES - 1; | ||
509 | gspca_dev->frbuf = vmalloc_32(frsz * count); | ||
510 | if (!gspca_dev->frbuf) { | ||
511 | pr_err("frame alloc failed\n"); | ||
512 | return -ENOMEM; | ||
513 | } | ||
514 | gspca_dev->capt_file = file; | ||
515 | gspca_dev->memory = memory; | ||
516 | gspca_dev->frsz = frsz; | ||
517 | gspca_dev->nframes = count; | ||
518 | for (i = 0; i < count; i++) { | ||
519 | frame = &gspca_dev->frame[i]; | ||
520 | frame->v4l2_buf.index = i; | ||
521 | frame->v4l2_buf.type = V4L2_BUF_TYPE_VIDEO_CAPTURE; | ||
522 | frame->v4l2_buf.flags = V4L2_BUF_FLAG_TIMESTAMP_MONOTONIC; | ||
523 | frame->v4l2_buf.field = V4L2_FIELD_NONE; | ||
524 | frame->v4l2_buf.length = frsz; | ||
525 | frame->v4l2_buf.memory = memory; | ||
526 | frame->v4l2_buf.sequence = 0; | ||
527 | frame->data = gspca_dev->frbuf + i * frsz; | ||
528 | frame->v4l2_buf.m.offset = i * frsz; | ||
529 | } | ||
530 | atomic_set(&gspca_dev->fr_q, 0); | ||
531 | atomic_set(&gspca_dev->fr_i, 0); | ||
532 | gspca_dev->fr_o = 0; | ||
533 | return 0; | ||
534 | } | ||
535 | |||
536 | static void frame_free(struct gspca_dev *gspca_dev) | ||
537 | { | ||
538 | int i; | ||
539 | |||
540 | gspca_dbg(gspca_dev, D_STREAM, "frame free\n"); | ||
541 | if (gspca_dev->frbuf != NULL) { | ||
542 | vfree(gspca_dev->frbuf); | ||
543 | gspca_dev->frbuf = NULL; | ||
544 | for (i = 0; i < gspca_dev->nframes; i++) | ||
545 | gspca_dev->frame[i].data = NULL; | ||
546 | } | ||
547 | gspca_dev->nframes = 0; | ||
548 | gspca_dev->frsz = 0; | ||
549 | gspca_dev->capt_file = NULL; | ||
550 | gspca_dev->memory = GSPCA_MEMORY_NO; | ||
551 | } | ||
552 | |||
553 | static void destroy_urbs(struct gspca_dev *gspca_dev) | 469 | static void destroy_urbs(struct gspca_dev *gspca_dev) |
554 | { | 470 | { |
555 | struct urb *urb; | 471 | struct urb *urb; |
@@ -583,22 +499,6 @@ static int gspca_set_alt0(struct gspca_dev *gspca_dev) | |||
583 | return ret; | 499 | return ret; |
584 | } | 500 | } |
585 | 501 | ||
586 | /* Note: both the queue and the usb locks should be held when calling this */ | ||
587 | static void gspca_stream_off(struct gspca_dev *gspca_dev) | ||
588 | { | ||
589 | gspca_dev->streaming = 0; | ||
590 | gspca_dev->usb_err = 0; | ||
591 | if (gspca_dev->sd_desc->stopN) | ||
592 | gspca_dev->sd_desc->stopN(gspca_dev); | ||
593 | destroy_urbs(gspca_dev); | ||
594 | gspca_input_destroy_urb(gspca_dev); | ||
595 | gspca_set_alt0(gspca_dev); | ||
596 | gspca_input_create_urb(gspca_dev); | ||
597 | if (gspca_dev->sd_desc->stop0) | ||
598 | gspca_dev->sd_desc->stop0(gspca_dev); | ||
599 | gspca_dbg(gspca_dev, D_STREAM, "stream off OK\n"); | ||
600 | } | ||
601 | |||
602 | /* | 502 | /* |
603 | * look for an input transfer endpoint in an alternate setting. | 503 | * look for an input transfer endpoint in an alternate setting. |
604 | * | 504 | * |
@@ -829,6 +729,23 @@ static int create_urbs(struct gspca_dev *gspca_dev, | |||
829 | return 0; | 729 | return 0; |
830 | } | 730 | } |
831 | 731 | ||
732 | /* Note: both the queue and the usb locks should be held when calling this */ | ||
733 | static void gspca_stream_off(struct gspca_dev *gspca_dev) | ||
734 | { | ||
735 | gspca_dev->streaming = false; | ||
736 | gspca_dev->usb_err = 0; | ||
737 | if (gspca_dev->sd_desc->stopN) | ||
738 | gspca_dev->sd_desc->stopN(gspca_dev); | ||
739 | destroy_urbs(gspca_dev); | ||
740 | gspca_input_destroy_urb(gspca_dev); | ||
741 | gspca_set_alt0(gspca_dev); | ||
742 | if (gspca_dev->present) | ||
743 | gspca_input_create_urb(gspca_dev); | ||
744 | if (gspca_dev->sd_desc->stop0) | ||
745 | gspca_dev->sd_desc->stop0(gspca_dev); | ||
746 | gspca_dbg(gspca_dev, D_STREAM, "stream off OK\n"); | ||
747 | } | ||
748 | |||
832 | /* | 749 | /* |
833 | * start the USB transfer | 750 | * start the USB transfer |
834 | */ | 751 | */ |
@@ -844,7 +761,6 @@ static int gspca_init_transfer(struct gspca_dev *gspca_dev) | |||
844 | gspca_dev->image = NULL; | 761 | gspca_dev->image = NULL; |
845 | gspca_dev->image_len = 0; | 762 | gspca_dev->image_len = 0; |
846 | gspca_dev->last_packet_type = DISCARD_PACKET; | 763 | gspca_dev->last_packet_type = DISCARD_PACKET; |
847 | gspca_dev->sequence = 0; | ||
848 | 764 | ||
849 | gspca_dev->usb_err = 0; | 765 | gspca_dev->usb_err = 0; |
850 | 766 | ||
@@ -924,8 +840,8 @@ static int gspca_init_transfer(struct gspca_dev *gspca_dev) | |||
924 | destroy_urbs(gspca_dev); | 840 | destroy_urbs(gspca_dev); |
925 | goto out; | 841 | goto out; |
926 | } | 842 | } |
927 | gspca_dev->streaming = 1; | ||
928 | v4l2_ctrl_handler_setup(gspca_dev->vdev.ctrl_handler); | 843 | v4l2_ctrl_handler_setup(gspca_dev->vdev.ctrl_handler); |
844 | gspca_dev->streaming = true; | ||
929 | 845 | ||
930 | /* some bulk transfers are started by the subdriver */ | 846 | /* some bulk transfers are started by the subdriver */ |
931 | if (gspca_dev->cam.bulk && gspca_dev->cam.bulk_nurbs == 0) | 847 | if (gspca_dev->cam.bulk && gspca_dev->cam.bulk_nurbs == 0) |
@@ -1165,11 +1081,9 @@ static int vidioc_try_fmt_vid_cap(struct file *file, | |||
1165 | struct v4l2_format *fmt) | 1081 | struct v4l2_format *fmt) |
1166 | { | 1082 | { |
1167 | struct gspca_dev *gspca_dev = video_drvdata(file); | 1083 | struct gspca_dev *gspca_dev = video_drvdata(file); |
1168 | int ret; | ||
1169 | 1084 | ||
1170 | ret = try_fmt_vid_cap(gspca_dev, fmt); | 1085 | if (try_fmt_vid_cap(gspca_dev, fmt) < 0) |
1171 | if (ret < 0) | 1086 | return -EINVAL; |
1172 | return ret; | ||
1173 | return 0; | 1087 | return 0; |
1174 | } | 1088 | } |
1175 | 1089 | ||
@@ -1177,36 +1091,22 @@ static int vidioc_s_fmt_vid_cap(struct file *file, void *priv, | |||
1177 | struct v4l2_format *fmt) | 1091 | struct v4l2_format *fmt) |
1178 | { | 1092 | { |
1179 | struct gspca_dev *gspca_dev = video_drvdata(file); | 1093 | struct gspca_dev *gspca_dev = video_drvdata(file); |
1180 | int ret; | 1094 | int mode; |
1181 | |||
1182 | if (mutex_lock_interruptible(&gspca_dev->queue_lock)) | ||
1183 | return -ERESTARTSYS; | ||
1184 | 1095 | ||
1185 | ret = try_fmt_vid_cap(gspca_dev, fmt); | 1096 | if (vb2_is_busy(&gspca_dev->queue)) |
1186 | if (ret < 0) | 1097 | return -EBUSY; |
1187 | goto out; | ||
1188 | 1098 | ||
1189 | if (gspca_dev->nframes != 0 | 1099 | mode = try_fmt_vid_cap(gspca_dev, fmt); |
1190 | && fmt->fmt.pix.sizeimage > gspca_dev->frsz) { | 1100 | if (mode < 0) |
1191 | ret = -EINVAL; | 1101 | return -EINVAL; |
1192 | goto out; | ||
1193 | } | ||
1194 | 1102 | ||
1195 | if (gspca_dev->streaming) { | 1103 | gspca_dev->curr_mode = mode; |
1196 | ret = -EBUSY; | ||
1197 | goto out; | ||
1198 | } | ||
1199 | gspca_dev->curr_mode = ret; | ||
1200 | if (gspca_dev->sd_desc->try_fmt) | 1104 | if (gspca_dev->sd_desc->try_fmt) |
1201 | /* subdriver try_fmt can modify format parameters */ | 1105 | /* subdriver try_fmt can modify format parameters */ |
1202 | gspca_dev->pixfmt = fmt->fmt.pix; | 1106 | gspca_dev->pixfmt = fmt->fmt.pix; |
1203 | else | 1107 | else |
1204 | gspca_dev->pixfmt = gspca_dev->cam.cam_mode[ret]; | 1108 | gspca_dev->pixfmt = gspca_dev->cam.cam_mode[mode]; |
1205 | 1109 | return 0; | |
1206 | ret = 0; | ||
1207 | out: | ||
1208 | mutex_unlock(&gspca_dev->queue_lock); | ||
1209 | return ret; | ||
1210 | } | 1110 | } |
1211 | 1111 | ||
1212 | static int vidioc_enum_framesizes(struct file *file, void *priv, | 1112 | static int vidioc_enum_framesizes(struct file *file, void *priv, |
@@ -1281,53 +1181,6 @@ static void gspca_release(struct v4l2_device *v4l2_device) | |||
1281 | kfree(gspca_dev); | 1181 | kfree(gspca_dev); |
1282 | } | 1182 | } |
1283 | 1183 | ||
1284 | static int dev_open(struct file *file) | ||
1285 | { | ||
1286 | struct gspca_dev *gspca_dev = video_drvdata(file); | ||
1287 | int ret; | ||
1288 | |||
1289 | gspca_dbg(gspca_dev, D_STREAM, "[%s] open\n", current->comm); | ||
1290 | |||
1291 | /* protect the subdriver against rmmod */ | ||
1292 | if (!try_module_get(gspca_dev->module)) | ||
1293 | return -ENODEV; | ||
1294 | |||
1295 | ret = v4l2_fh_open(file); | ||
1296 | if (ret) | ||
1297 | module_put(gspca_dev->module); | ||
1298 | return ret; | ||
1299 | } | ||
1300 | |||
1301 | static int dev_close(struct file *file) | ||
1302 | { | ||
1303 | struct gspca_dev *gspca_dev = video_drvdata(file); | ||
1304 | |||
1305 | gspca_dbg(gspca_dev, D_STREAM, "[%s] close\n", current->comm); | ||
1306 | |||
1307 | /* Needed for gspca_stream_off, always lock before queue_lock! */ | ||
1308 | if (mutex_lock_interruptible(&gspca_dev->usb_lock)) | ||
1309 | return -ERESTARTSYS; | ||
1310 | |||
1311 | if (mutex_lock_interruptible(&gspca_dev->queue_lock)) { | ||
1312 | mutex_unlock(&gspca_dev->usb_lock); | ||
1313 | return -ERESTARTSYS; | ||
1314 | } | ||
1315 | |||
1316 | /* if the file did the capture, free the streaming resources */ | ||
1317 | if (gspca_dev->capt_file == file) { | ||
1318 | if (gspca_dev->streaming) | ||
1319 | gspca_stream_off(gspca_dev); | ||
1320 | frame_free(gspca_dev); | ||
1321 | } | ||
1322 | module_put(gspca_dev->module); | ||
1323 | mutex_unlock(&gspca_dev->queue_lock); | ||
1324 | mutex_unlock(&gspca_dev->usb_lock); | ||
1325 | |||
1326 | gspca_dbg(gspca_dev, D_STREAM, "close done\n"); | ||
1327 | |||
1328 | return v4l2_fh_release(file); | ||
1329 | } | ||
1330 | |||
1331 | static int vidioc_querycap(struct file *file, void *priv, | 1184 | static int vidioc_querycap(struct file *file, void *priv, |
1332 | struct v4l2_capability *cap) | 1185 | struct v4l2_capability *cap) |
1333 | { | 1186 | { |
@@ -1377,167 +1230,9 @@ static int vidioc_s_input(struct file *file, void *priv, unsigned int i) | |||
1377 | { | 1230 | { |
1378 | if (i > 0) | 1231 | if (i > 0) |
1379 | return -EINVAL; | 1232 | return -EINVAL; |
1380 | return (0); | ||
1381 | } | ||
1382 | |||
1383 | static int vidioc_reqbufs(struct file *file, void *priv, | ||
1384 | struct v4l2_requestbuffers *rb) | ||
1385 | { | ||
1386 | struct gspca_dev *gspca_dev = video_drvdata(file); | ||
1387 | int i, ret = 0, streaming; | ||
1388 | |||
1389 | i = rb->memory; /* (avoid compilation warning) */ | ||
1390 | switch (i) { | ||
1391 | case GSPCA_MEMORY_READ: /* (internal call) */ | ||
1392 | case V4L2_MEMORY_MMAP: | ||
1393 | case V4L2_MEMORY_USERPTR: | ||
1394 | break; | ||
1395 | default: | ||
1396 | return -EINVAL; | ||
1397 | } | ||
1398 | if (mutex_lock_interruptible(&gspca_dev->queue_lock)) | ||
1399 | return -ERESTARTSYS; | ||
1400 | |||
1401 | if (gspca_dev->memory != GSPCA_MEMORY_NO | ||
1402 | && gspca_dev->memory != GSPCA_MEMORY_READ | ||
1403 | && gspca_dev->memory != rb->memory) { | ||
1404 | ret = -EBUSY; | ||
1405 | goto out; | ||
1406 | } | ||
1407 | |||
1408 | /* only one file may do the capture */ | ||
1409 | if (gspca_dev->capt_file != NULL | ||
1410 | && gspca_dev->capt_file != file) { | ||
1411 | ret = -EBUSY; | ||
1412 | goto out; | ||
1413 | } | ||
1414 | |||
1415 | /* if allocated, the buffers must not be mapped */ | ||
1416 | for (i = 0; i < gspca_dev->nframes; i++) { | ||
1417 | if (gspca_dev->frame[i].vma_use_count) { | ||
1418 | ret = -EBUSY; | ||
1419 | goto out; | ||
1420 | } | ||
1421 | } | ||
1422 | |||
1423 | /* stop streaming */ | ||
1424 | streaming = gspca_dev->streaming; | ||
1425 | if (streaming) { | ||
1426 | gspca_stream_off(gspca_dev); | ||
1427 | |||
1428 | /* Don't restart the stream when switching from read | ||
1429 | * to mmap mode */ | ||
1430 | if (gspca_dev->memory == GSPCA_MEMORY_READ) | ||
1431 | streaming = 0; | ||
1432 | } | ||
1433 | |||
1434 | /* free the previous allocated buffers, if any */ | ||
1435 | if (gspca_dev->nframes != 0) | ||
1436 | frame_free(gspca_dev); | ||
1437 | if (rb->count == 0) /* unrequest */ | ||
1438 | goto out; | ||
1439 | ret = frame_alloc(gspca_dev, file, rb->memory, rb->count); | ||
1440 | if (ret == 0) { | ||
1441 | rb->count = gspca_dev->nframes; | ||
1442 | if (streaming) | ||
1443 | ret = gspca_init_transfer(gspca_dev); | ||
1444 | } | ||
1445 | out: | ||
1446 | mutex_unlock(&gspca_dev->queue_lock); | ||
1447 | gspca_dbg(gspca_dev, D_STREAM, "reqbufs st:%d c:%d\n", ret, rb->count); | ||
1448 | return ret; | ||
1449 | } | ||
1450 | |||
1451 | static int vidioc_querybuf(struct file *file, void *priv, | ||
1452 | struct v4l2_buffer *v4l2_buf) | ||
1453 | { | ||
1454 | struct gspca_dev *gspca_dev = video_drvdata(file); | ||
1455 | struct gspca_frame *frame; | ||
1456 | |||
1457 | if (v4l2_buf->index >= gspca_dev->nframes) | ||
1458 | return -EINVAL; | ||
1459 | |||
1460 | frame = &gspca_dev->frame[v4l2_buf->index]; | ||
1461 | memcpy(v4l2_buf, &frame->v4l2_buf, sizeof *v4l2_buf); | ||
1462 | return 0; | 1233 | return 0; |
1463 | } | 1234 | } |
1464 | 1235 | ||
1465 | static int vidioc_streamon(struct file *file, void *priv, | ||
1466 | enum v4l2_buf_type buf_type) | ||
1467 | { | ||
1468 | struct gspca_dev *gspca_dev = video_drvdata(file); | ||
1469 | int ret; | ||
1470 | |||
1471 | if (buf_type != V4L2_BUF_TYPE_VIDEO_CAPTURE) | ||
1472 | return -EINVAL; | ||
1473 | if (mutex_lock_interruptible(&gspca_dev->queue_lock)) | ||
1474 | return -ERESTARTSYS; | ||
1475 | |||
1476 | /* check the capture file */ | ||
1477 | if (gspca_dev->capt_file != file) { | ||
1478 | ret = -EBUSY; | ||
1479 | goto out; | ||
1480 | } | ||
1481 | |||
1482 | if (gspca_dev->nframes == 0 | ||
1483 | || !(gspca_dev->frame[0].v4l2_buf.flags & V4L2_BUF_FLAG_QUEUED)) { | ||
1484 | ret = -EINVAL; | ||
1485 | goto out; | ||
1486 | } | ||
1487 | if (!gspca_dev->streaming) { | ||
1488 | ret = gspca_init_transfer(gspca_dev); | ||
1489 | if (ret < 0) | ||
1490 | goto out; | ||
1491 | } | ||
1492 | PDEBUG_MODE(gspca_dev, D_STREAM, "stream on OK", | ||
1493 | gspca_dev->pixfmt.pixelformat, | ||
1494 | gspca_dev->pixfmt.width, gspca_dev->pixfmt.height); | ||
1495 | ret = 0; | ||
1496 | out: | ||
1497 | mutex_unlock(&gspca_dev->queue_lock); | ||
1498 | return ret; | ||
1499 | } | ||
1500 | |||
1501 | static int vidioc_streamoff(struct file *file, void *priv, | ||
1502 | enum v4l2_buf_type buf_type) | ||
1503 | { | ||
1504 | struct gspca_dev *gspca_dev = video_drvdata(file); | ||
1505 | int i, ret; | ||
1506 | |||
1507 | if (buf_type != V4L2_BUF_TYPE_VIDEO_CAPTURE) | ||
1508 | return -EINVAL; | ||
1509 | |||
1510 | if (mutex_lock_interruptible(&gspca_dev->queue_lock)) | ||
1511 | return -ERESTARTSYS; | ||
1512 | |||
1513 | if (!gspca_dev->streaming) { | ||
1514 | ret = 0; | ||
1515 | goto out; | ||
1516 | } | ||
1517 | |||
1518 | /* check the capture file */ | ||
1519 | if (gspca_dev->capt_file != file) { | ||
1520 | ret = -EBUSY; | ||
1521 | goto out; | ||
1522 | } | ||
1523 | |||
1524 | /* stop streaming */ | ||
1525 | gspca_stream_off(gspca_dev); | ||
1526 | /* In case another thread is waiting in dqbuf */ | ||
1527 | wake_up_interruptible(&gspca_dev->wq); | ||
1528 | |||
1529 | /* empty the transfer queues */ | ||
1530 | for (i = 0; i < gspca_dev->nframes; i++) | ||
1531 | gspca_dev->frame[i].v4l2_buf.flags &= ~BUF_ALL_FLAGS; | ||
1532 | atomic_set(&gspca_dev->fr_q, 0); | ||
1533 | atomic_set(&gspca_dev->fr_i, 0); | ||
1534 | gspca_dev->fr_o = 0; | ||
1535 | ret = 0; | ||
1536 | out: | ||
1537 | mutex_unlock(&gspca_dev->queue_lock); | ||
1538 | return ret; | ||
1539 | } | ||
1540 | |||
1541 | static int vidioc_g_jpegcomp(struct file *file, void *priv, | 1236 | static int vidioc_g_jpegcomp(struct file *file, void *priv, |
1542 | struct v4l2_jpegcompression *jpegcomp) | 1237 | struct v4l2_jpegcompression *jpegcomp) |
1543 | { | 1238 | { |
@@ -1561,7 +1256,7 @@ static int vidioc_g_parm(struct file *filp, void *priv, | |||
1561 | { | 1256 | { |
1562 | struct gspca_dev *gspca_dev = video_drvdata(filp); | 1257 | struct gspca_dev *gspca_dev = video_drvdata(filp); |
1563 | 1258 | ||
1564 | parm->parm.capture.readbuffers = gspca_dev->nbufread; | 1259 | parm->parm.capture.readbuffers = 2; |
1565 | 1260 | ||
1566 | if (gspca_dev->sd_desc->get_streamparm) { | 1261 | if (gspca_dev->sd_desc->get_streamparm) { |
1567 | gspca_dev->usb_err = 0; | 1262 | gspca_dev->usb_err = 0; |
@@ -1575,13 +1270,8 @@ static int vidioc_s_parm(struct file *filp, void *priv, | |||
1575 | struct v4l2_streamparm *parm) | 1270 | struct v4l2_streamparm *parm) |
1576 | { | 1271 | { |
1577 | struct gspca_dev *gspca_dev = video_drvdata(filp); | 1272 | struct gspca_dev *gspca_dev = video_drvdata(filp); |
1578 | unsigned int n; | ||
1579 | 1273 | ||
1580 | n = parm->parm.capture.readbuffers; | 1274 | parm->parm.capture.readbuffers = 2; |
1581 | if (n == 0 || n >= GSPCA_MAX_FRAMES) | ||
1582 | parm->parm.capture.readbuffers = gspca_dev->nbufread; | ||
1583 | else | ||
1584 | gspca_dev->nbufread = n; | ||
1585 | 1275 | ||
1586 | if (gspca_dev->sd_desc->set_streamparm) { | 1276 | if (gspca_dev->sd_desc->set_streamparm) { |
1587 | gspca_dev->usb_err = 0; | 1277 | gspca_dev->usb_err = 0; |
@@ -1592,418 +1282,138 @@ static int vidioc_s_parm(struct file *filp, void *priv, | |||
1592 | return 0; | 1282 | return 0; |
1593 | } | 1283 | } |
1594 | 1284 | ||
1595 | static int dev_mmap(struct file *file, struct vm_area_struct *vma) | 1285 | static int gspca_queue_setup(struct vb2_queue *vq, |
1596 | { | 1286 | unsigned int *nbuffers, unsigned int *nplanes, |
1597 | struct gspca_dev *gspca_dev = video_drvdata(file); | 1287 | unsigned int sizes[], struct device *alloc_devs[]) |
1598 | struct gspca_frame *frame; | ||
1599 | struct page *page; | ||
1600 | unsigned long addr, start, size; | ||
1601 | int i, ret; | ||
1602 | |||
1603 | start = vma->vm_start; | ||
1604 | size = vma->vm_end - vma->vm_start; | ||
1605 | gspca_dbg(gspca_dev, D_STREAM, "mmap start:%08x size:%d\n", | ||
1606 | (int) start, (int)size); | ||
1607 | |||
1608 | if (mutex_lock_interruptible(&gspca_dev->queue_lock)) | ||
1609 | return -ERESTARTSYS; | ||
1610 | if (gspca_dev->capt_file != file) { | ||
1611 | ret = -EINVAL; | ||
1612 | goto out; | ||
1613 | } | ||
1614 | |||
1615 | frame = NULL; | ||
1616 | for (i = 0; i < gspca_dev->nframes; ++i) { | ||
1617 | if (gspca_dev->frame[i].v4l2_buf.memory != V4L2_MEMORY_MMAP) { | ||
1618 | gspca_dbg(gspca_dev, D_STREAM, "mmap bad memory type\n"); | ||
1619 | break; | ||
1620 | } | ||
1621 | if ((gspca_dev->frame[i].v4l2_buf.m.offset >> PAGE_SHIFT) | ||
1622 | == vma->vm_pgoff) { | ||
1623 | frame = &gspca_dev->frame[i]; | ||
1624 | break; | ||
1625 | } | ||
1626 | } | ||
1627 | if (frame == NULL) { | ||
1628 | gspca_dbg(gspca_dev, D_STREAM, "mmap no frame buffer found\n"); | ||
1629 | ret = -EINVAL; | ||
1630 | goto out; | ||
1631 | } | ||
1632 | if (size != frame->v4l2_buf.length) { | ||
1633 | gspca_dbg(gspca_dev, D_STREAM, "mmap bad size\n"); | ||
1634 | ret = -EINVAL; | ||
1635 | goto out; | ||
1636 | } | ||
1637 | |||
1638 | /* | ||
1639 | * - VM_IO marks the area as being a mmaped region for I/O to a | ||
1640 | * device. It also prevents the region from being core dumped. | ||
1641 | */ | ||
1642 | vma->vm_flags |= VM_IO; | ||
1643 | |||
1644 | addr = (unsigned long) frame->data; | ||
1645 | while (size > 0) { | ||
1646 | page = vmalloc_to_page((void *) addr); | ||
1647 | ret = vm_insert_page(vma, start, page); | ||
1648 | if (ret < 0) | ||
1649 | goto out; | ||
1650 | start += PAGE_SIZE; | ||
1651 | addr += PAGE_SIZE; | ||
1652 | size -= PAGE_SIZE; | ||
1653 | } | ||
1654 | |||
1655 | vma->vm_ops = &gspca_vm_ops; | ||
1656 | vma->vm_private_data = frame; | ||
1657 | gspca_vm_open(vma); | ||
1658 | ret = 0; | ||
1659 | out: | ||
1660 | mutex_unlock(&gspca_dev->queue_lock); | ||
1661 | return ret; | ||
1662 | } | ||
1663 | |||
1664 | static int frame_ready_nolock(struct gspca_dev *gspca_dev, struct file *file, | ||
1665 | enum v4l2_memory memory) | ||
1666 | { | 1288 | { |
1667 | if (!gspca_dev->present) | 1289 | struct gspca_dev *gspca_dev = vb2_get_drv_priv(vq); |
1668 | return -ENODEV; | ||
1669 | if (gspca_dev->capt_file != file || gspca_dev->memory != memory || | ||
1670 | !gspca_dev->streaming) | ||
1671 | return -EINVAL; | ||
1672 | 1290 | ||
1673 | /* check if a frame is ready */ | 1291 | if (*nplanes) |
1674 | return gspca_dev->fr_o != atomic_read(&gspca_dev->fr_i); | 1292 | return sizes[0] < gspca_dev->pixfmt.sizeimage ? -EINVAL : 0; |
1293 | *nplanes = 1; | ||
1294 | sizes[0] = gspca_dev->pixfmt.sizeimage; | ||
1295 | return 0; | ||
1675 | } | 1296 | } |
1676 | 1297 | ||
1677 | static int frame_ready(struct gspca_dev *gspca_dev, struct file *file, | 1298 | static int gspca_buffer_prepare(struct vb2_buffer *vb) |
1678 | enum v4l2_memory memory) | ||
1679 | { | 1299 | { |
1680 | int ret; | 1300 | struct gspca_dev *gspca_dev = vb2_get_drv_priv(vb->vb2_queue); |
1301 | unsigned long size = gspca_dev->pixfmt.sizeimage; | ||
1681 | 1302 | ||
1682 | if (mutex_lock_interruptible(&gspca_dev->queue_lock)) | 1303 | if (vb2_plane_size(vb, 0) < size) { |
1683 | return -ERESTARTSYS; | 1304 | gspca_err(gspca_dev, "buffer too small (%lu < %lu)\n", |
1684 | ret = frame_ready_nolock(gspca_dev, file, memory); | 1305 | vb2_plane_size(vb, 0), size); |
1685 | mutex_unlock(&gspca_dev->queue_lock); | 1306 | return -EINVAL; |
1686 | return ret; | 1307 | } |
1308 | return 0; | ||
1687 | } | 1309 | } |
1688 | 1310 | ||
1689 | /* | 1311 | static void gspca_buffer_finish(struct vb2_buffer *vb) |
1690 | * dequeue a video buffer | ||
1691 | * | ||
1692 | * If nonblock_ing is false, block until a buffer is available. | ||
1693 | */ | ||
1694 | static int vidioc_dqbuf(struct file *file, void *priv, | ||
1695 | struct v4l2_buffer *v4l2_buf) | ||
1696 | { | 1312 | { |
1697 | struct gspca_dev *gspca_dev = video_drvdata(file); | 1313 | struct gspca_dev *gspca_dev = vb2_get_drv_priv(vb->vb2_queue); |
1698 | struct gspca_frame *frame; | ||
1699 | int i, j, ret; | ||
1700 | |||
1701 | gspca_dbg(gspca_dev, D_FRAM, "dqbuf\n"); | ||
1702 | |||
1703 | if (mutex_lock_interruptible(&gspca_dev->queue_lock)) | ||
1704 | return -ERESTARTSYS; | ||
1705 | |||
1706 | for (;;) { | ||
1707 | ret = frame_ready_nolock(gspca_dev, file, v4l2_buf->memory); | ||
1708 | if (ret < 0) | ||
1709 | goto out; | ||
1710 | if (ret > 0) | ||
1711 | break; | ||
1712 | |||
1713 | mutex_unlock(&gspca_dev->queue_lock); | ||
1714 | |||
1715 | if (file->f_flags & O_NONBLOCK) | ||
1716 | return -EAGAIN; | ||
1717 | |||
1718 | /* wait till a frame is ready */ | ||
1719 | ret = wait_event_interruptible_timeout(gspca_dev->wq, | ||
1720 | frame_ready(gspca_dev, file, v4l2_buf->memory), | ||
1721 | msecs_to_jiffies(3000)); | ||
1722 | if (ret < 0) | ||
1723 | return ret; | ||
1724 | if (ret == 0) | ||
1725 | return -EIO; | ||
1726 | |||
1727 | if (mutex_lock_interruptible(&gspca_dev->queue_lock)) | ||
1728 | return -ERESTARTSYS; | ||
1729 | } | ||
1730 | |||
1731 | i = gspca_dev->fr_o; | ||
1732 | j = gspca_dev->fr_queue[i]; | ||
1733 | frame = &gspca_dev->frame[j]; | ||
1734 | 1314 | ||
1735 | gspca_dev->fr_o = (i + 1) % GSPCA_MAX_FRAMES; | 1315 | if (!gspca_dev->sd_desc->dq_callback) |
1736 | 1316 | return; | |
1737 | frame->v4l2_buf.flags &= ~V4L2_BUF_FLAG_DONE; | ||
1738 | memcpy(v4l2_buf, &frame->v4l2_buf, sizeof *v4l2_buf); | ||
1739 | gspca_dbg(gspca_dev, D_FRAM, "dqbuf %d\n", j); | ||
1740 | ret = 0; | ||
1741 | |||
1742 | if (gspca_dev->memory == V4L2_MEMORY_USERPTR) { | ||
1743 | if (copy_to_user((__u8 __user *) frame->v4l2_buf.m.userptr, | ||
1744 | frame->data, | ||
1745 | frame->v4l2_buf.bytesused)) { | ||
1746 | gspca_err(gspca_dev, "dqbuf cp to user failed\n"); | ||
1747 | ret = -EFAULT; | ||
1748 | } | ||
1749 | } | ||
1750 | out: | ||
1751 | mutex_unlock(&gspca_dev->queue_lock); | ||
1752 | |||
1753 | if (ret == 0 && gspca_dev->sd_desc->dq_callback) { | ||
1754 | mutex_lock(&gspca_dev->usb_lock); | ||
1755 | gspca_dev->usb_err = 0; | ||
1756 | if (gspca_dev->present) | ||
1757 | gspca_dev->sd_desc->dq_callback(gspca_dev); | ||
1758 | mutex_unlock(&gspca_dev->usb_lock); | ||
1759 | } | ||
1760 | 1317 | ||
1761 | return ret; | 1318 | gspca_dev->usb_err = 0; |
1319 | if (gspca_dev->present) | ||
1320 | gspca_dev->sd_desc->dq_callback(gspca_dev); | ||
1762 | } | 1321 | } |
1763 | 1322 | ||
1764 | /* | 1323 | static void gspca_buffer_queue(struct vb2_buffer *vb) |
1765 | * queue a video buffer | ||
1766 | * | ||
1767 | * Attempting to queue a buffer that has already been | ||
1768 | * queued will return -EINVAL. | ||
1769 | */ | ||
1770 | static int vidioc_qbuf(struct file *file, void *priv, | ||
1771 | struct v4l2_buffer *v4l2_buf) | ||
1772 | { | 1324 | { |
1773 | struct gspca_dev *gspca_dev = video_drvdata(file); | 1325 | struct gspca_dev *gspca_dev = vb2_get_drv_priv(vb->vb2_queue); |
1774 | struct gspca_frame *frame; | 1326 | struct gspca_buffer *buf = to_gspca_buffer(vb); |
1775 | int i, index, ret; | 1327 | unsigned long flags; |
1776 | |||
1777 | gspca_dbg(gspca_dev, D_FRAM, "qbuf %d\n", v4l2_buf->index); | ||
1778 | |||
1779 | if (mutex_lock_interruptible(&gspca_dev->queue_lock)) | ||
1780 | return -ERESTARTSYS; | ||
1781 | |||
1782 | index = v4l2_buf->index; | ||
1783 | if ((unsigned) index >= gspca_dev->nframes) { | ||
1784 | gspca_dbg(gspca_dev, D_FRAM, | ||
1785 | "qbuf idx %d >= %d\n", index, gspca_dev->nframes); | ||
1786 | ret = -EINVAL; | ||
1787 | goto out; | ||
1788 | } | ||
1789 | if (v4l2_buf->memory != gspca_dev->memory) { | ||
1790 | gspca_dbg(gspca_dev, D_FRAM, "qbuf bad memory type\n"); | ||
1791 | ret = -EINVAL; | ||
1792 | goto out; | ||
1793 | } | ||
1794 | |||
1795 | frame = &gspca_dev->frame[index]; | ||
1796 | if (frame->v4l2_buf.flags & BUF_ALL_FLAGS) { | ||
1797 | gspca_dbg(gspca_dev, D_FRAM, "qbuf bad state\n"); | ||
1798 | ret = -EINVAL; | ||
1799 | goto out; | ||
1800 | } | ||
1801 | 1328 | ||
1802 | frame->v4l2_buf.flags |= V4L2_BUF_FLAG_QUEUED; | 1329 | spin_lock_irqsave(&gspca_dev->qlock, flags); |
1803 | 1330 | list_add_tail(&buf->list, &gspca_dev->buf_list); | |
1804 | if (frame->v4l2_buf.memory == V4L2_MEMORY_USERPTR) { | 1331 | spin_unlock_irqrestore(&gspca_dev->qlock, flags); |
1805 | frame->v4l2_buf.m.userptr = v4l2_buf->m.userptr; | ||
1806 | frame->v4l2_buf.length = v4l2_buf->length; | ||
1807 | } | ||
1808 | |||
1809 | /* put the buffer in the 'queued' queue */ | ||
1810 | i = atomic_read(&gspca_dev->fr_q); | ||
1811 | gspca_dev->fr_queue[i] = index; | ||
1812 | atomic_set(&gspca_dev->fr_q, (i + 1) % GSPCA_MAX_FRAMES); | ||
1813 | |||
1814 | v4l2_buf->flags |= V4L2_BUF_FLAG_QUEUED; | ||
1815 | v4l2_buf->flags &= ~V4L2_BUF_FLAG_DONE; | ||
1816 | ret = 0; | ||
1817 | out: | ||
1818 | mutex_unlock(&gspca_dev->queue_lock); | ||
1819 | return ret; | ||
1820 | } | 1332 | } |
1821 | 1333 | ||
1822 | /* | 1334 | static void gspca_return_all_buffers(struct gspca_dev *gspca_dev, |
1823 | * allocate the resources for read() | 1335 | enum vb2_buffer_state state) |
1824 | */ | ||
1825 | static int read_alloc(struct gspca_dev *gspca_dev, | ||
1826 | struct file *file) | ||
1827 | { | 1336 | { |
1828 | struct v4l2_buffer v4l2_buf; | 1337 | struct gspca_buffer *buf, *node; |
1829 | int i, ret; | 1338 | unsigned long flags; |
1830 | |||
1831 | gspca_dbg(gspca_dev, D_STREAM, "read alloc\n"); | ||
1832 | |||
1833 | if (mutex_lock_interruptible(&gspca_dev->usb_lock)) | ||
1834 | return -ERESTARTSYS; | ||
1835 | 1339 | ||
1836 | if (gspca_dev->nframes == 0) { | 1340 | spin_lock_irqsave(&gspca_dev->qlock, flags); |
1837 | struct v4l2_requestbuffers rb; | 1341 | list_for_each_entry_safe(buf, node, &gspca_dev->buf_list, list) { |
1838 | 1342 | vb2_buffer_done(&buf->vb.vb2_buf, state); | |
1839 | memset(&rb, 0, sizeof rb); | 1343 | list_del(&buf->list); |
1840 | rb.count = gspca_dev->nbufread; | ||
1841 | rb.type = V4L2_BUF_TYPE_VIDEO_CAPTURE; | ||
1842 | rb.memory = GSPCA_MEMORY_READ; | ||
1843 | ret = vidioc_reqbufs(file, gspca_dev, &rb); | ||
1844 | if (ret != 0) { | ||
1845 | gspca_dbg(gspca_dev, D_STREAM, "read reqbuf err %d\n", | ||
1846 | ret); | ||
1847 | goto out; | ||
1848 | } | ||
1849 | memset(&v4l2_buf, 0, sizeof v4l2_buf); | ||
1850 | v4l2_buf.type = V4L2_BUF_TYPE_VIDEO_CAPTURE; | ||
1851 | v4l2_buf.memory = GSPCA_MEMORY_READ; | ||
1852 | for (i = 0; i < gspca_dev->nbufread; i++) { | ||
1853 | v4l2_buf.index = i; | ||
1854 | ret = vidioc_qbuf(file, gspca_dev, &v4l2_buf); | ||
1855 | if (ret != 0) { | ||
1856 | gspca_dbg(gspca_dev, D_STREAM, "read qbuf err: %d\n", | ||
1857 | ret); | ||
1858 | goto out; | ||
1859 | } | ||
1860 | } | ||
1861 | } | 1344 | } |
1862 | 1345 | spin_unlock_irqrestore(&gspca_dev->qlock, flags); | |
1863 | /* start streaming */ | ||
1864 | ret = vidioc_streamon(file, gspca_dev, V4L2_BUF_TYPE_VIDEO_CAPTURE); | ||
1865 | if (ret != 0) | ||
1866 | gspca_dbg(gspca_dev, D_STREAM, "read streamon err %d\n", ret); | ||
1867 | out: | ||
1868 | mutex_unlock(&gspca_dev->usb_lock); | ||
1869 | return ret; | ||
1870 | } | 1346 | } |
1871 | 1347 | ||
1872 | static __poll_t dev_poll(struct file *file, poll_table *wait) | 1348 | static int gspca_start_streaming(struct vb2_queue *vq, unsigned int count) |
1873 | { | 1349 | { |
1874 | struct gspca_dev *gspca_dev = video_drvdata(file); | 1350 | struct gspca_dev *gspca_dev = vb2_get_drv_priv(vq); |
1875 | __poll_t req_events = poll_requested_events(wait); | 1351 | int ret; |
1876 | __poll_t ret = 0; | ||
1877 | |||
1878 | gspca_dbg(gspca_dev, D_FRAM, "poll\n"); | ||
1879 | |||
1880 | if (req_events & EPOLLPRI) | ||
1881 | ret |= v4l2_ctrl_poll(file, wait); | ||
1882 | |||
1883 | if (req_events & (EPOLLIN | EPOLLRDNORM)) { | ||
1884 | /* if reqbufs is not done, the user would use read() */ | ||
1885 | if (gspca_dev->memory == GSPCA_MEMORY_NO) { | ||
1886 | if (read_alloc(gspca_dev, file) != 0) { | ||
1887 | ret |= EPOLLERR; | ||
1888 | goto out; | ||
1889 | } | ||
1890 | } | ||
1891 | |||
1892 | poll_wait(file, &gspca_dev->wq, wait); | ||
1893 | |||
1894 | /* check if an image has been received */ | ||
1895 | if (mutex_lock_interruptible(&gspca_dev->queue_lock) != 0) { | ||
1896 | ret |= EPOLLERR; | ||
1897 | goto out; | ||
1898 | } | ||
1899 | if (gspca_dev->fr_o != atomic_read(&gspca_dev->fr_i)) | ||
1900 | ret |= EPOLLIN | EPOLLRDNORM; | ||
1901 | mutex_unlock(&gspca_dev->queue_lock); | ||
1902 | } | ||
1903 | 1352 | ||
1904 | out: | 1353 | gspca_dev->sequence = 0; |
1905 | if (!gspca_dev->present) | ||
1906 | ret |= EPOLLHUP; | ||
1907 | 1354 | ||
1355 | ret = gspca_init_transfer(gspca_dev); | ||
1356 | if (ret) | ||
1357 | gspca_return_all_buffers(gspca_dev, VB2_BUF_STATE_QUEUED); | ||
1908 | return ret; | 1358 | return ret; |
1909 | } | 1359 | } |
1910 | 1360 | ||
1911 | static ssize_t dev_read(struct file *file, char __user *data, | 1361 | static void gspca_stop_streaming(struct vb2_queue *vq) |
1912 | size_t count, loff_t *ppos) | ||
1913 | { | 1362 | { |
1914 | struct gspca_dev *gspca_dev = video_drvdata(file); | 1363 | struct gspca_dev *gspca_dev = vb2_get_drv_priv(vq); |
1915 | struct gspca_frame *frame; | ||
1916 | struct v4l2_buffer v4l2_buf; | ||
1917 | struct timeval timestamp; | ||
1918 | int n, ret, ret2; | ||
1919 | |||
1920 | gspca_dbg(gspca_dev, D_FRAM, "read (%zd)\n", count); | ||
1921 | if (gspca_dev->memory == GSPCA_MEMORY_NO) { /* first time ? */ | ||
1922 | ret = read_alloc(gspca_dev, file); | ||
1923 | if (ret != 0) | ||
1924 | return ret; | ||
1925 | } | ||
1926 | |||
1927 | /* get a frame */ | ||
1928 | v4l2_get_timestamp(×tamp); | ||
1929 | timestamp.tv_sec--; | ||
1930 | n = 2; | ||
1931 | for (;;) { | ||
1932 | memset(&v4l2_buf, 0, sizeof v4l2_buf); | ||
1933 | v4l2_buf.type = V4L2_BUF_TYPE_VIDEO_CAPTURE; | ||
1934 | v4l2_buf.memory = GSPCA_MEMORY_READ; | ||
1935 | ret = vidioc_dqbuf(file, gspca_dev, &v4l2_buf); | ||
1936 | if (ret != 0) { | ||
1937 | gspca_dbg(gspca_dev, D_STREAM, "read dqbuf err %d\n", | ||
1938 | ret); | ||
1939 | return ret; | ||
1940 | } | ||
1941 | 1364 | ||
1942 | /* if the process slept for more than 1 second, | 1365 | gspca_stream_off(gspca_dev); |
1943 | * get a newer frame */ | ||
1944 | frame = &gspca_dev->frame[v4l2_buf.index]; | ||
1945 | if (--n < 0) | ||
1946 | break; /* avoid infinite loop */ | ||
1947 | if (frame->v4l2_buf.timestamp.tv_sec >= timestamp.tv_sec) | ||
1948 | break; | ||
1949 | ret = vidioc_qbuf(file, gspca_dev, &v4l2_buf); | ||
1950 | if (ret != 0) { | ||
1951 | gspca_dbg(gspca_dev, D_STREAM, "read qbuf err %d\n", | ||
1952 | ret); | ||
1953 | return ret; | ||
1954 | } | ||
1955 | } | ||
1956 | 1366 | ||
1957 | /* copy the frame */ | 1367 | /* Release all active buffers */ |
1958 | if (count > frame->v4l2_buf.bytesused) | 1368 | gspca_return_all_buffers(gspca_dev, VB2_BUF_STATE_ERROR); |
1959 | count = frame->v4l2_buf.bytesused; | ||
1960 | ret = copy_to_user(data, frame->data, count); | ||
1961 | if (ret != 0) { | ||
1962 | gspca_err(gspca_dev, "read cp to user lack %d / %zd\n", | ||
1963 | ret, count); | ||
1964 | ret = -EFAULT; | ||
1965 | goto out; | ||
1966 | } | ||
1967 | ret = count; | ||
1968 | out: | ||
1969 | /* in each case, requeue the buffer */ | ||
1970 | ret2 = vidioc_qbuf(file, gspca_dev, &v4l2_buf); | ||
1971 | if (ret2 != 0) | ||
1972 | return ret2; | ||
1973 | return ret; | ||
1974 | } | 1369 | } |
1975 | 1370 | ||
1371 | static const struct vb2_ops gspca_qops = { | ||
1372 | .queue_setup = gspca_queue_setup, | ||
1373 | .buf_prepare = gspca_buffer_prepare, | ||
1374 | .buf_finish = gspca_buffer_finish, | ||
1375 | .buf_queue = gspca_buffer_queue, | ||
1376 | .start_streaming = gspca_start_streaming, | ||
1377 | .stop_streaming = gspca_stop_streaming, | ||
1378 | .wait_prepare = vb2_ops_wait_prepare, | ||
1379 | .wait_finish = vb2_ops_wait_finish, | ||
1380 | }; | ||
1381 | |||
1976 | static const struct v4l2_file_operations dev_fops = { | 1382 | static const struct v4l2_file_operations dev_fops = { |
1977 | .owner = THIS_MODULE, | 1383 | .owner = THIS_MODULE, |
1978 | .open = dev_open, | 1384 | .open = v4l2_fh_open, |
1979 | .release = dev_close, | 1385 | .release = vb2_fop_release, |
1980 | .read = dev_read, | ||
1981 | .mmap = dev_mmap, | ||
1982 | .unlocked_ioctl = video_ioctl2, | 1386 | .unlocked_ioctl = video_ioctl2, |
1983 | .poll = dev_poll, | 1387 | .read = vb2_fop_read, |
1388 | .mmap = vb2_fop_mmap, | ||
1389 | .poll = vb2_fop_poll, | ||
1984 | }; | 1390 | }; |
1985 | 1391 | ||
1986 | static const struct v4l2_ioctl_ops dev_ioctl_ops = { | 1392 | static const struct v4l2_ioctl_ops dev_ioctl_ops = { |
1987 | .vidioc_querycap = vidioc_querycap, | 1393 | .vidioc_querycap = vidioc_querycap, |
1988 | .vidioc_dqbuf = vidioc_dqbuf, | ||
1989 | .vidioc_qbuf = vidioc_qbuf, | ||
1990 | .vidioc_enum_fmt_vid_cap = vidioc_enum_fmt_vid_cap, | 1394 | .vidioc_enum_fmt_vid_cap = vidioc_enum_fmt_vid_cap, |
1991 | .vidioc_try_fmt_vid_cap = vidioc_try_fmt_vid_cap, | 1395 | .vidioc_try_fmt_vid_cap = vidioc_try_fmt_vid_cap, |
1992 | .vidioc_g_fmt_vid_cap = vidioc_g_fmt_vid_cap, | 1396 | .vidioc_g_fmt_vid_cap = vidioc_g_fmt_vid_cap, |
1993 | .vidioc_s_fmt_vid_cap = vidioc_s_fmt_vid_cap, | 1397 | .vidioc_s_fmt_vid_cap = vidioc_s_fmt_vid_cap, |
1994 | .vidioc_streamon = vidioc_streamon, | ||
1995 | .vidioc_enum_input = vidioc_enum_input, | 1398 | .vidioc_enum_input = vidioc_enum_input, |
1996 | .vidioc_g_input = vidioc_g_input, | 1399 | .vidioc_g_input = vidioc_g_input, |
1997 | .vidioc_s_input = vidioc_s_input, | 1400 | .vidioc_s_input = vidioc_s_input, |
1998 | .vidioc_reqbufs = vidioc_reqbufs, | ||
1999 | .vidioc_querybuf = vidioc_querybuf, | ||
2000 | .vidioc_streamoff = vidioc_streamoff, | ||
2001 | .vidioc_g_jpegcomp = vidioc_g_jpegcomp, | 1401 | .vidioc_g_jpegcomp = vidioc_g_jpegcomp, |
2002 | .vidioc_s_jpegcomp = vidioc_s_jpegcomp, | 1402 | .vidioc_s_jpegcomp = vidioc_s_jpegcomp, |
2003 | .vidioc_g_parm = vidioc_g_parm, | 1403 | .vidioc_g_parm = vidioc_g_parm, |
2004 | .vidioc_s_parm = vidioc_s_parm, | 1404 | .vidioc_s_parm = vidioc_s_parm, |
2005 | .vidioc_enum_framesizes = vidioc_enum_framesizes, | 1405 | .vidioc_enum_framesizes = vidioc_enum_framesizes, |
2006 | .vidioc_enum_frameintervals = vidioc_enum_frameintervals, | 1406 | .vidioc_enum_frameintervals = vidioc_enum_frameintervals, |
1407 | |||
1408 | .vidioc_reqbufs = vb2_ioctl_reqbufs, | ||
1409 | .vidioc_create_bufs = vb2_ioctl_create_bufs, | ||
1410 | .vidioc_querybuf = vb2_ioctl_querybuf, | ||
1411 | .vidioc_qbuf = vb2_ioctl_qbuf, | ||
1412 | .vidioc_dqbuf = vb2_ioctl_dqbuf, | ||
1413 | .vidioc_expbuf = vb2_ioctl_expbuf, | ||
1414 | .vidioc_streamon = vb2_ioctl_streamon, | ||
1415 | .vidioc_streamoff = vb2_ioctl_streamoff, | ||
1416 | |||
2007 | #ifdef CONFIG_VIDEO_ADV_DEBUG | 1417 | #ifdef CONFIG_VIDEO_ADV_DEBUG |
2008 | .vidioc_g_chip_info = vidioc_g_chip_info, | 1418 | .vidioc_g_chip_info = vidioc_g_chip_info, |
2009 | .vidioc_g_register = vidioc_g_register, | 1419 | .vidioc_g_register = vidioc_g_register, |
@@ -2034,6 +1444,7 @@ int gspca_dev_probe2(struct usb_interface *intf, | |||
2034 | { | 1444 | { |
2035 | struct gspca_dev *gspca_dev; | 1445 | struct gspca_dev *gspca_dev; |
2036 | struct usb_device *dev = interface_to_usbdev(intf); | 1446 | struct usb_device *dev = interface_to_usbdev(intf); |
1447 | struct vb2_queue *q; | ||
2037 | int ret; | 1448 | int ret; |
2038 | 1449 | ||
2039 | pr_info("%s-" GSPCA_VERSION " probing %04x:%04x\n", | 1450 | pr_info("%s-" GSPCA_VERSION " probing %04x:%04x\n", |
@@ -2078,20 +1489,37 @@ int gspca_dev_probe2(struct usb_interface *intf, | |||
2078 | ret = v4l2_device_register(&intf->dev, &gspca_dev->v4l2_dev); | 1489 | ret = v4l2_device_register(&intf->dev, &gspca_dev->v4l2_dev); |
2079 | if (ret) | 1490 | if (ret) |
2080 | goto out; | 1491 | goto out; |
1492 | gspca_dev->present = true; | ||
2081 | gspca_dev->sd_desc = sd_desc; | 1493 | gspca_dev->sd_desc = sd_desc; |
2082 | gspca_dev->nbufread = 2; | ||
2083 | gspca_dev->empty_packet = -1; /* don't check the empty packets */ | 1494 | gspca_dev->empty_packet = -1; /* don't check the empty packets */ |
2084 | gspca_dev->vdev = gspca_template; | 1495 | gspca_dev->vdev = gspca_template; |
2085 | gspca_dev->vdev.v4l2_dev = &gspca_dev->v4l2_dev; | 1496 | gspca_dev->vdev.v4l2_dev = &gspca_dev->v4l2_dev; |
2086 | video_set_drvdata(&gspca_dev->vdev, gspca_dev); | 1497 | video_set_drvdata(&gspca_dev->vdev, gspca_dev); |
2087 | gspca_dev->module = module; | 1498 | gspca_dev->module = module; |
2088 | gspca_dev->present = 1; | ||
2089 | 1499 | ||
2090 | mutex_init(&gspca_dev->usb_lock); | 1500 | mutex_init(&gspca_dev->usb_lock); |
2091 | gspca_dev->vdev.lock = &gspca_dev->usb_lock; | 1501 | gspca_dev->vdev.lock = &gspca_dev->usb_lock; |
2092 | mutex_init(&gspca_dev->queue_lock); | ||
2093 | init_waitqueue_head(&gspca_dev->wq); | 1502 | init_waitqueue_head(&gspca_dev->wq); |
2094 | 1503 | ||
1504 | /* Initialize the vb2 queue */ | ||
1505 | q = &gspca_dev->queue; | ||
1506 | q->type = V4L2_BUF_TYPE_VIDEO_CAPTURE; | ||
1507 | q->io_modes = VB2_MMAP | VB2_USERPTR | VB2_DMABUF | VB2_READ; | ||
1508 | q->drv_priv = gspca_dev; | ||
1509 | q->buf_struct_size = sizeof(struct gspca_buffer); | ||
1510 | q->ops = &gspca_qops; | ||
1511 | q->mem_ops = &vb2_vmalloc_memops; | ||
1512 | q->timestamp_flags = V4L2_BUF_FLAG_TIMESTAMP_MONOTONIC; | ||
1513 | q->min_buffers_needed = 2; | ||
1514 | q->lock = &gspca_dev->usb_lock; | ||
1515 | ret = vb2_queue_init(q); | ||
1516 | if (ret) | ||
1517 | goto out; | ||
1518 | gspca_dev->vdev.queue = q; | ||
1519 | |||
1520 | INIT_LIST_HEAD(&gspca_dev->buf_list); | ||
1521 | spin_lock_init(&gspca_dev->qlock); | ||
1522 | |||
2095 | /* configure the subdriver and initialize the USB device */ | 1523 | /* configure the subdriver and initialize the USB device */ |
2096 | ret = sd_desc->config(gspca_dev, id); | 1524 | ret = sd_desc->config(gspca_dev, id); |
2097 | if (ret < 0) | 1525 | if (ret < 0) |
@@ -2109,14 +1537,6 @@ int gspca_dev_probe2(struct usb_interface *intf, | |||
2109 | if (ret) | 1537 | if (ret) |
2110 | goto out; | 1538 | goto out; |
2111 | 1539 | ||
2112 | /* | ||
2113 | * Don't take usb_lock for these ioctls. This improves latency if | ||
2114 | * usb_lock is taken for a long time, e.g. when changing a control | ||
2115 | * value, and a new frame is ready to be dequeued. | ||
2116 | */ | ||
2117 | v4l2_disable_ioctl_locking(&gspca_dev->vdev, VIDIOC_DQBUF); | ||
2118 | v4l2_disable_ioctl_locking(&gspca_dev->vdev, VIDIOC_QBUF); | ||
2119 | v4l2_disable_ioctl_locking(&gspca_dev->vdev, VIDIOC_QUERYBUF); | ||
2120 | #ifdef CONFIG_VIDEO_ADV_DEBUG | 1540 | #ifdef CONFIG_VIDEO_ADV_DEBUG |
2121 | if (!gspca_dev->sd_desc->get_register) | 1541 | if (!gspca_dev->sd_desc->get_register) |
2122 | v4l2_disable_ioctl(&gspca_dev->vdev, VIDIOC_DBG_G_REGISTER); | 1542 | v4l2_disable_ioctl(&gspca_dev->vdev, VIDIOC_DBG_G_REGISTER); |
@@ -2198,24 +1618,17 @@ void gspca_disconnect(struct usb_interface *intf) | |||
2198 | video_device_node_name(&gspca_dev->vdev)); | 1618 | video_device_node_name(&gspca_dev->vdev)); |
2199 | 1619 | ||
2200 | mutex_lock(&gspca_dev->usb_lock); | 1620 | mutex_lock(&gspca_dev->usb_lock); |
1621 | gspca_dev->present = false; | ||
2201 | 1622 | ||
2202 | gspca_dev->present = 0; | 1623 | vb2_queue_error(&gspca_dev->queue); |
2203 | destroy_urbs(gspca_dev); | ||
2204 | 1624 | ||
2205 | #if IS_ENABLED(CONFIG_INPUT) | 1625 | #if IS_ENABLED(CONFIG_INPUT) |
2206 | gspca_input_destroy_urb(gspca_dev); | ||
2207 | input_dev = gspca_dev->input_dev; | 1626 | input_dev = gspca_dev->input_dev; |
2208 | if (input_dev) { | 1627 | if (input_dev) { |
2209 | gspca_dev->input_dev = NULL; | 1628 | gspca_dev->input_dev = NULL; |
2210 | input_unregister_device(input_dev); | 1629 | input_unregister_device(input_dev); |
2211 | } | 1630 | } |
2212 | #endif | 1631 | #endif |
2213 | /* Free subdriver's streaming resources / stop sd workqueue(s) */ | ||
2214 | if (gspca_dev->sd_desc->stop0 && gspca_dev->streaming) | ||
2215 | gspca_dev->sd_desc->stop0(gspca_dev); | ||
2216 | gspca_dev->streaming = 0; | ||
2217 | gspca_dev->dev = NULL; | ||
2218 | wake_up_interruptible(&gspca_dev->wq); | ||
2219 | 1632 | ||
2220 | v4l2_device_disconnect(&gspca_dev->v4l2_dev); | 1633 | v4l2_device_disconnect(&gspca_dev->v4l2_dev); |
2221 | video_unregister_device(&gspca_dev->vdev); | 1634 | video_unregister_device(&gspca_dev->vdev); |
@@ -2234,7 +1647,7 @@ int gspca_suspend(struct usb_interface *intf, pm_message_t message) | |||
2234 | 1647 | ||
2235 | gspca_input_destroy_urb(gspca_dev); | 1648 | gspca_input_destroy_urb(gspca_dev); |
2236 | 1649 | ||
2237 | if (!gspca_dev->streaming) | 1650 | if (!vb2_start_streaming_called(&gspca_dev->queue)) |
2238 | return 0; | 1651 | return 0; |
2239 | 1652 | ||
2240 | mutex_lock(&gspca_dev->usb_lock); | 1653 | mutex_lock(&gspca_dev->usb_lock); |
@@ -2266,8 +1679,7 @@ int gspca_resume(struct usb_interface *intf) | |||
2266 | * only write to the device registers on s_ctrl when streaming -> | 1679 | * only write to the device registers on s_ctrl when streaming -> |
2267 | * Clear streaming to avoid setting all ctrls twice. | 1680 | * Clear streaming to avoid setting all ctrls twice. |
2268 | */ | 1681 | */ |
2269 | streaming = gspca_dev->streaming; | 1682 | streaming = vb2_start_streaming_called(&gspca_dev->queue); |
2270 | gspca_dev->streaming = 0; | ||
2271 | if (streaming) | 1683 | if (streaming) |
2272 | ret = gspca_init_transfer(gspca_dev); | 1684 | ret = gspca_init_transfer(gspca_dev); |
2273 | else | 1685 | else |
diff --git a/drivers/media/usb/gspca/gspca.h b/drivers/media/usb/gspca/gspca.h index 249cb38a542f..b0ced2e14006 100644 --- a/drivers/media/usb/gspca/gspca.h +++ b/drivers/media/usb/gspca/gspca.h | |||
@@ -9,6 +9,8 @@ | |||
9 | #include <media/v4l2-common.h> | 9 | #include <media/v4l2-common.h> |
10 | #include <media/v4l2-ctrls.h> | 10 | #include <media/v4l2-ctrls.h> |
11 | #include <media/v4l2-device.h> | 11 | #include <media/v4l2-device.h> |
12 | #include <media/videobuf2-v4l2.h> | ||
13 | #include <media/videobuf2-vmalloc.h> | ||
12 | #include <linux/mutex.h> | 14 | #include <linux/mutex.h> |
13 | 15 | ||
14 | 16 | ||
@@ -138,19 +140,22 @@ enum gspca_packet_type { | |||
138 | LAST_PACKET | 140 | LAST_PACKET |
139 | }; | 141 | }; |
140 | 142 | ||
141 | struct gspca_frame { | 143 | struct gspca_buffer { |
142 | __u8 *data; /* frame buffer */ | 144 | struct vb2_v4l2_buffer vb; |
143 | int vma_use_count; | 145 | struct list_head list; |
144 | struct v4l2_buffer v4l2_buf; | ||
145 | }; | 146 | }; |
146 | 147 | ||
148 | static inline struct gspca_buffer *to_gspca_buffer(struct vb2_buffer *vb2) | ||
149 | { | ||
150 | return container_of(vb2, struct gspca_buffer, vb.vb2_buf); | ||
151 | } | ||
152 | |||
147 | struct gspca_dev { | 153 | struct gspca_dev { |
148 | struct video_device vdev; /* !! must be the first item */ | 154 | struct video_device vdev; /* !! must be the first item */ |
149 | struct module *module; /* subdriver handling the device */ | 155 | struct module *module; /* subdriver handling the device */ |
150 | struct v4l2_device v4l2_dev; | 156 | struct v4l2_device v4l2_dev; |
151 | struct usb_device *dev; | 157 | struct usb_device *dev; |
152 | struct file *capt_file; /* file doing video capture */ | 158 | |
153 | /* protected by queue_lock */ | ||
154 | #if IS_ENABLED(CONFIG_INPUT) | 159 | #if IS_ENABLED(CONFIG_INPUT) |
155 | struct input_dev *input_dev; | 160 | struct input_dev *input_dev; |
156 | char phys[64]; /* physical device path */ | 161 | char phys[64]; /* physical device path */ |
@@ -176,34 +181,29 @@ struct gspca_dev { | |||
176 | struct urb *int_urb; | 181 | struct urb *int_urb; |
177 | #endif | 182 | #endif |
178 | 183 | ||
179 | __u8 *frbuf; /* buffer for nframes */ | 184 | u8 *image; /* image being filled */ |
180 | struct gspca_frame frame[GSPCA_MAX_FRAMES]; | ||
181 | u8 *image; /* image beeing filled */ | ||
182 | __u32 frsz; /* frame size */ | ||
183 | u32 image_len; /* current length of image */ | 185 | u32 image_len; /* current length of image */ |
184 | atomic_t fr_q; /* next frame to queue */ | ||
185 | atomic_t fr_i; /* frame being filled */ | ||
186 | signed char fr_queue[GSPCA_MAX_FRAMES]; /* frame queue */ | ||
187 | char nframes; /* number of frames */ | ||
188 | u8 fr_o; /* next frame to dequeue */ | ||
189 | __u8 last_packet_type; | 186 | __u8 last_packet_type; |
190 | __s8 empty_packet; /* if (-1) don't check empty packets */ | 187 | __s8 empty_packet; /* if (-1) don't check empty packets */ |
191 | __u8 streaming; /* protected by both mutexes (*) */ | 188 | bool streaming; |
192 | 189 | ||
193 | __u8 curr_mode; /* current camera mode */ | 190 | __u8 curr_mode; /* current camera mode */ |
194 | struct v4l2_pix_format pixfmt; /* current mode parameters */ | 191 | struct v4l2_pix_format pixfmt; /* current mode parameters */ |
195 | __u32 sequence; /* frame sequence number */ | 192 | __u32 sequence; /* frame sequence number */ |
196 | 193 | ||
194 | struct vb2_queue queue; | ||
195 | |||
196 | spinlock_t qlock; | ||
197 | struct list_head buf_list; | ||
198 | |||
197 | wait_queue_head_t wq; /* wait queue */ | 199 | wait_queue_head_t wq; /* wait queue */ |
198 | struct mutex usb_lock; /* usb exchange protection */ | 200 | struct mutex usb_lock; /* usb exchange protection */ |
199 | struct mutex queue_lock; /* ISOC queue protection */ | ||
200 | int usb_err; /* USB error - protected by usb_lock */ | 201 | int usb_err; /* USB error - protected by usb_lock */ |
201 | u16 pkt_size; /* ISOC packet size */ | 202 | u16 pkt_size; /* ISOC packet size */ |
202 | #ifdef CONFIG_PM | 203 | #ifdef CONFIG_PM |
203 | char frozen; /* suspend - resume */ | 204 | char frozen; /* suspend - resume */ |
204 | #endif | 205 | #endif |
205 | char present; /* device connected */ | 206 | bool present; |
206 | char nbufread; /* number of buffers for read() */ | ||
207 | char memory; /* memory type (V4L2_MEMORY_xxx) */ | 207 | char memory; /* memory type (V4L2_MEMORY_xxx) */ |
208 | __u8 iface; /* USB interface number */ | 208 | __u8 iface; /* USB interface number */ |
209 | __u8 alt; /* USB alternate setting */ | 209 | __u8 alt; /* USB alternate setting */ |
diff --git a/drivers/media/usb/gspca/m5602/m5602_core.c b/drivers/media/usb/gspca/m5602/m5602_core.c index b83ec4285a0b..30b7cf1feedd 100644 --- a/drivers/media/usb/gspca/m5602/m5602_core.c +++ b/drivers/media/usb/gspca/m5602/m5602_core.c | |||
@@ -342,7 +342,7 @@ static void m5602_urb_complete(struct gspca_dev *gspca_dev, | |||
342 | data += 4; | 342 | data += 4; |
343 | len -= 4; | 343 | len -= 4; |
344 | 344 | ||
345 | if (cur_frame_len + len <= gspca_dev->frsz) { | 345 | if (cur_frame_len + len <= gspca_dev->pixfmt.sizeimage) { |
346 | gspca_dbg(gspca_dev, D_FRAM, "Continuing frame %d copying %d bytes\n", | 346 | gspca_dbg(gspca_dev, D_FRAM, "Continuing frame %d copying %d bytes\n", |
347 | sd->frame_count, len); | 347 | sd->frame_count, len); |
348 | 348 | ||
@@ -351,7 +351,7 @@ static void m5602_urb_complete(struct gspca_dev *gspca_dev, | |||
351 | } else { | 351 | } else { |
352 | /* Add the remaining data up to frame size */ | 352 | /* Add the remaining data up to frame size */ |
353 | gspca_frame_add(gspca_dev, INTER_PACKET, data, | 353 | gspca_frame_add(gspca_dev, INTER_PACKET, data, |
354 | gspca_dev->frsz - cur_frame_len); | 354 | gspca_dev->pixfmt.sizeimage - cur_frame_len); |
355 | } | 355 | } |
356 | } | 356 | } |
357 | } | 357 | } |
diff --git a/drivers/media/usb/gspca/vc032x.c b/drivers/media/usb/gspca/vc032x.c index 6b11597977c9..52d071659634 100644 --- a/drivers/media/usb/gspca/vc032x.c +++ b/drivers/media/usb/gspca/vc032x.c | |||
@@ -3642,7 +3642,7 @@ static void sd_pkt_scan(struct gspca_dev *gspca_dev, | |||
3642 | int size, l; | 3642 | int size, l; |
3643 | 3643 | ||
3644 | l = gspca_dev->image_len; | 3644 | l = gspca_dev->image_len; |
3645 | size = gspca_dev->frsz; | 3645 | size = gspca_dev->pixfmt.sizeimage; |
3646 | if (len > size - l) | 3646 | if (len > size - l) |
3647 | len = size - l; | 3647 | len = size - l; |
3648 | } | 3648 | } |