diff options
Diffstat (limited to 'drivers/media/video/em28xx/em28xx-video.c')
-rw-r--r-- | drivers/media/video/em28xx/em28xx-video.c | 66 |
1 files changed, 42 insertions, 24 deletions
diff --git a/drivers/media/video/em28xx/em28xx-video.c b/drivers/media/video/em28xx/em28xx-video.c index 0fe20110bfd6..20090e34173a 100644 --- a/drivers/media/video/em28xx/em28xx-video.c +++ b/drivers/media/video/em28xx/em28xx-video.c | |||
@@ -203,12 +203,6 @@ static void em28xx_copy_video(struct em28xx *dev, | |||
203 | if (dma_q->pos + len > buf->vb.size) | 203 | if (dma_q->pos + len > buf->vb.size) |
204 | len = buf->vb.size - dma_q->pos; | 204 | len = buf->vb.size - dma_q->pos; |
205 | 205 | ||
206 | if (p[0] != 0x88 && p[0] != 0x22) { | ||
207 | em28xx_isocdbg("frame is not complete\n"); | ||
208 | len += 4; | ||
209 | } else | ||
210 | p += 4; | ||
211 | |||
212 | startread = p; | 206 | startread = p; |
213 | remain = len; | 207 | remain = len; |
214 | 208 | ||
@@ -309,14 +303,6 @@ static void em28xx_copy_vbi(struct em28xx *dev, | |||
309 | if (dma_q->pos + len > buf->vb.size) | 303 | if (dma_q->pos + len > buf->vb.size) |
310 | len = buf->vb.size - dma_q->pos; | 304 | len = buf->vb.size - dma_q->pos; |
311 | 305 | ||
312 | if ((p[0] == 0x33 && p[1] == 0x95) || | ||
313 | (p[0] == 0x88 && p[1] == 0x88)) { | ||
314 | /* Header field, advance past it */ | ||
315 | p += 4; | ||
316 | } else { | ||
317 | len += 4; | ||
318 | } | ||
319 | |||
320 | startread = p; | 306 | startread = p; |
321 | 307 | ||
322 | startwrite = outp + dma_q->pos; | 308 | startwrite = outp + dma_q->pos; |
@@ -507,8 +493,15 @@ static inline int em28xx_isoc_copy(struct em28xx *dev, struct urb *urb) | |||
507 | 493 | ||
508 | dma_q->pos = 0; | 494 | dma_q->pos = 0; |
509 | } | 495 | } |
510 | if (buf != NULL) | 496 | if (buf != NULL) { |
497 | if (p[0] != 0x88 && p[0] != 0x22) { | ||
498 | em28xx_isocdbg("frame is not complete\n"); | ||
499 | len += 4; | ||
500 | } else { | ||
501 | p += 4; | ||
502 | } | ||
511 | em28xx_copy_video(dev, dma_q, buf, p, outp, len); | 503 | em28xx_copy_video(dev, dma_q, buf, p, outp, len); |
504 | } | ||
512 | } | 505 | } |
513 | return rc; | 506 | return rc; |
514 | } | 507 | } |
@@ -555,8 +548,7 @@ static inline int em28xx_isoc_copy_vbi(struct em28xx *dev, struct urb *urb) | |||
555 | continue; | 548 | continue; |
556 | } | 549 | } |
557 | 550 | ||
558 | len = urb->iso_frame_desc[i].actual_length - 4; | 551 | len = urb->iso_frame_desc[i].actual_length; |
559 | |||
560 | if (urb->iso_frame_desc[i].actual_length <= 0) { | 552 | if (urb->iso_frame_desc[i].actual_length <= 0) { |
561 | /* em28xx_isocdbg("packet %d is empty",i); - spammy */ | 553 | /* em28xx_isocdbg("packet %d is empty",i); - spammy */ |
562 | continue; | 554 | continue; |
@@ -577,6 +569,17 @@ static inline int em28xx_isoc_copy_vbi(struct em28xx *dev, struct urb *urb) | |||
577 | dev->vbi_read = 0; | 569 | dev->vbi_read = 0; |
578 | em28xx_isocdbg("VBI START HEADER!!!\n"); | 570 | em28xx_isocdbg("VBI START HEADER!!!\n"); |
579 | dev->cur_field = p[2]; | 571 | dev->cur_field = p[2]; |
572 | p += 4; | ||
573 | len -= 4; | ||
574 | } else if (p[0] == 0x88 && p[1] == 0x88 && | ||
575 | p[2] == 0x88 && p[3] == 0x88) { | ||
576 | /* continuation */ | ||
577 | p += 4; | ||
578 | len -= 4; | ||
579 | } else if (p[0] == 0x22 && p[1] == 0x5a) { | ||
580 | /* start video */ | ||
581 | p += 4; | ||
582 | len -= 4; | ||
580 | } | 583 | } |
581 | 584 | ||
582 | vbi_size = dev->vbi_width * dev->vbi_height; | 585 | vbi_size = dev->vbi_width * dev->vbi_height; |
@@ -631,9 +634,6 @@ static inline int em28xx_isoc_copy_vbi(struct em28xx *dev, struct urb *urb) | |||
631 | 634 | ||
632 | if (dev->capture_type == 1) { | 635 | if (dev->capture_type == 1) { |
633 | dev->capture_type = 2; | 636 | dev->capture_type = 2; |
634 | em28xx_isocdbg("Video frame %d, length=%i, %s\n", p[2], | ||
635 | len, (p[2] & 1) ? "odd" : "even"); | ||
636 | |||
637 | if (dev->progressive || !(dev->cur_field & 1)) { | 637 | if (dev->progressive || !(dev->cur_field & 1)) { |
638 | if (buf != NULL) | 638 | if (buf != NULL) |
639 | buffer_filled(dev, dma_q, buf); | 639 | buffer_filled(dev, dma_q, buf); |
@@ -652,8 +652,25 @@ static inline int em28xx_isoc_copy_vbi(struct em28xx *dev, struct urb *urb) | |||
652 | 652 | ||
653 | dma_q->pos = 0; | 653 | dma_q->pos = 0; |
654 | } | 654 | } |
655 | if (buf != NULL && dev->capture_type == 2) | 655 | |
656 | em28xx_copy_video(dev, dma_q, buf, p, outp, len); | 656 | if (buf != NULL && dev->capture_type == 2) { |
657 | if (len > 4 && p[0] == 0x88 && p[1] == 0x88 && | ||
658 | p[2] == 0x88 && p[3] == 0x88) { | ||
659 | p += 4; | ||
660 | len -= 4; | ||
661 | } | ||
662 | if (len > 4 && p[0] == 0x22 && p[1] == 0x5a) { | ||
663 | em28xx_isocdbg("Video frame %d, len=%i, %s\n", | ||
664 | p[2], len, (p[2] & 1) ? | ||
665 | "odd" : "even"); | ||
666 | p += 4; | ||
667 | len -= 4; | ||
668 | } | ||
669 | |||
670 | if (len > 0) | ||
671 | em28xx_copy_video(dev, dma_q, buf, p, outp, | ||
672 | len); | ||
673 | } | ||
657 | } | 674 | } |
658 | return rc; | 675 | return rc; |
659 | } | 676 | } |
@@ -1483,6 +1500,7 @@ static int vidioc_g_tuner(struct file *file, void *priv, | |||
1483 | return -EINVAL; | 1500 | return -EINVAL; |
1484 | 1501 | ||
1485 | strcpy(t->name, "Tuner"); | 1502 | strcpy(t->name, "Tuner"); |
1503 | t->type = V4L2_TUNER_ANALOG_TV; | ||
1486 | 1504 | ||
1487 | mutex_lock(&dev->lock); | 1505 | mutex_lock(&dev->lock); |
1488 | v4l2_device_call_all(&dev->v4l2_dev, 0, tuner, g_tuner, t); | 1506 | v4l2_device_call_all(&dev->v4l2_dev, 0, tuner, g_tuner, t); |
@@ -1814,7 +1832,7 @@ static int vidioc_g_fmt_sliced_vbi_cap(struct file *file, void *priv, | |||
1814 | mutex_lock(&dev->lock); | 1832 | mutex_lock(&dev->lock); |
1815 | 1833 | ||
1816 | f->fmt.sliced.service_set = 0; | 1834 | f->fmt.sliced.service_set = 0; |
1817 | v4l2_device_call_all(&dev->v4l2_dev, 0, video, g_fmt, f); | 1835 | v4l2_device_call_all(&dev->v4l2_dev, 0, vbi, g_sliced_fmt, &f->fmt.sliced); |
1818 | 1836 | ||
1819 | if (f->fmt.sliced.service_set == 0) | 1837 | if (f->fmt.sliced.service_set == 0) |
1820 | rc = -EINVAL; | 1838 | rc = -EINVAL; |
@@ -1836,7 +1854,7 @@ static int vidioc_try_set_sliced_vbi_cap(struct file *file, void *priv, | |||
1836 | return rc; | 1854 | return rc; |
1837 | 1855 | ||
1838 | mutex_lock(&dev->lock); | 1856 | mutex_lock(&dev->lock); |
1839 | v4l2_device_call_all(&dev->v4l2_dev, 0, video, g_fmt, f); | 1857 | v4l2_device_call_all(&dev->v4l2_dev, 0, vbi, g_sliced_fmt, &f->fmt.sliced); |
1840 | mutex_unlock(&dev->lock); | 1858 | mutex_unlock(&dev->lock); |
1841 | 1859 | ||
1842 | if (f->fmt.sliced.service_set == 0) | 1860 | if (f->fmt.sliced.service_set == 0) |