On Friday 07 March 2008 16:43:10 Elvis Chen wrote:
> greetings,
>
> I have 2 pauppauge pvr-150 on a ubuntu 7.10 amd64 system.  They show
> up as /dev/video32 and /dev/video33.  I'm trying to grab images from
> these 2 cards via s-video but ran into problem.  I seek your help. 
> My code that generates corrupted images is attached below.
>
> What works:
>
> 1) grab 1 image from each video device individually,
> 2) grab 1 image from both devices individually, but one after the
> other, 3) grab images from 1 video device continuously,
>
> what does NOT work:
>
> grab 1 image from tuner-1, grab 1 image from tuner-2 (works so far),
> then grab 1 more image from tuner-1.  At this point the images grabed
> from tuner-1 is corrupted:  it looks like the pixels are quadrupled,
> and the images is duplicated/shifted.  The following code segment
> demonstrate the problem:
>
>
>   int i = 1, j = 1;
>   int iwidth = 720, iheight = 480;
>
>   struct v4l2_format vf, vf1;
>   int fd = open( "/dev/video32", O_RDWR);
>   ioctl( fd, VIDIOC_S_INPUT, &i );
>   memset(&vf,0,sizeof(vf));
>   vf.type=V4L2_BUF_TYPE_VIDEO_CAPTURE;
>   vf.fmt.pix.width=iwidth;
>   vf.fmt.pix.height=iheight;
>   vf.fmt.pix.pixelformat=V4L2_PIX_FMT_HM12;
>   vf.fmt.pix.field=V4L2_FIELD_INTERLACED;
>   vf.fmt.pix.bytesperline=vf.fmt.pix.width;
>   ioctl(fd,VIDIOC_S_FMT,&vf);
>
>   int fd1 = open( "/dev/video33", O_RDWR);
>   ioctl( fd1, VIDIOC_S_INPUT, &j );
>   memset(&vf1,0,sizeof(vf1));
>   vf1.type=V4L2_BUF_TYPE_VIDEO_CAPTURE;
>   vf1.fmt.pix.width=iwidth;
>   vf1.fmt.pix.height=iheight;
>   vf1.fmt.pix.pixelformat=V4L2_PIX_FMT_HM12;
>   vf1.fmt.pix.field=V4L2_FIELD_INTERLACED;
>   vf1.fmt.pix.bytesperline=vf1.fmt.pix.width;
>   ioctl(fd1,VIDIOC_S_FMT,&vf1);
>
>   uint8_t *image, *imagey, *imageu, *imagev, *imageRGB;
>   image    = new uint8_t[ iwidth * iheight * 3 / 2 ];
>   imagey   = new uint8_t[ iwidth * iheight  ];
>   imageu   = new uint8_t[ iwidth * iheight / 4 ];
>   imagev   = new uint8_t[ iwidth * iheight / 4 ];
>   imageRGB = new uint8_t[ iwidth * iheight * 3 ];
>
> // read from tuner 1
>   if ( read( fd, image, iwidth*iheight*3/2 ) == -1 ) {
>     std::cerr << "error grabbing YUV image" << std::endl;
>     exit(1);
>   }
>
> // read from tuner 2
>   if ( read( fd1, image, iwidth*iheight*3/2 ) == -1 ) {
>     std::cerr << "error grabbing YUV image" << std::endl;
>     exit(1);
>   }
>
> // read from tuner 1 again
>   if ( read( fd, image, iwidth*iheight*3/2 ) == -1 ) {
>     std::cerr << "error grabbing YUV image" << std::endl;
>     exit(1);
>   }
>
>   // decrypt the microblocks
>   de_macro_y( imagey, image, iwidth, iwidth, iheight );
>   de_macro_uv( imageu, imagev, image+(iwidth*iheight),
>            iwidth/2, iwidth/2, iheight/2 );
>   // convert the YUV image to RGB
>   YUV2RGB( imageRGB, imagey, imageu, imagev, iwidth, iheight );
>
> if one displays the RGB array (imageRGB), the image stored in it is
> corrupted.  It loos like all pixels are quadruple in both x/y
> direction; the image also appear to be duplicated/shifted.
>
>
> if one *DOES NOT* read from tuner 2, then the image is fine.
>
> Any idea how I can fix this problem?
>
> any help is very much appreciated,

There is a bug in the ivtv driver that was only fixed in kernel 2.6.24. 
What happens is that if the application cannot quite keep up with the 
video stream the internal buffers will become full. At that moment 
buffers will be dropped (you probably get some message about that in 
the kernel log) and in kernels < 2.6.24 the YUV frames would become 
misaligned. This bug is fixed in kernel 2.6.24.

I suspect this is what your problem is. Check your kernel log: if you 
capture from two video3x devices then you probably see "Dropping data" 
messages.


Regards,

         Hans

_______________________________________________
ivtv-users mailing list
[email protected]
http://ivtvdriver.org/mailman/listinfo/ivtv-users

Reply via email to