NetBSD video(4) support, patch 2 of 3
authorPatrick Welche <prlw1@cam.ac.uk>
Mon, 17 Sep 2012 10:03:35 +0000 (12:03 +0200)
committerAndrey Kamaev <andrey.kamaev@itseez.com>
Mon, 28 Jan 2013 13:11:41 +0000 (17:11 +0400)
* Decouple Video4Linux2 support from Video4Linux as existence of
  v4l2 on a system does not imply support for v4l.
* Don't use V4L's struct video_window in V4L2 code.
* Removed __USE_GNU as comment says:
      /* support for MJPEG is only available with libjpeg and gcc,
         because it's use libjepg and fmemopen()
  so replace with test for fmemopen() if found necessary.

modules/highgui/src/cap.cpp
modules/highgui/src/cap_v4l.cpp

index 821478f..13475f2 100644 (file)
@@ -172,7 +172,8 @@ CV_IMPL CvCapture * cvCreateCameraCapture (int index)
     defined(HAVE_TYZX)         || \
     defined(HAVE_VFW)          || \
     defined(HAVE_LIBV4L)       || \
-    (defined(HAVE_CAMV4L) && defined(HAVE_CAMV4L2)) || \
+    defined(HAVE_CAMV4L)       || \
+    defined(HAVE_CAMV4L2)      || \
     defined(HAVE_VIDEOIO)      || \
     defined(HAVE_GSTREAMER)    || \
     defined(HAVE_DC1394_2)     || \
@@ -217,7 +218,7 @@ CV_IMPL CvCapture * cvCreateCameraCapture (int index)
                 return capture;
 #endif
 
-#if defined HAVE_LIBV4L || (defined (HAVE_CAMV4L) && defined (HAVE_CAMV4L2)) || defined HAVE_VIDEOIO
+#if defined HAVE_LIBV4L || defined HAVE_CAMV4L || defined HAVE_CAMV4L2 || defined HAVE_VIDEOIO
             capture = cvCreateCameraCapture_V4L (index);
             if (capture)
                 return capture;
index 33e0f38..a0d51e8 100644 (file)
@@ -202,7 +202,7 @@ make & enjoy!
 
 #include "precomp.hpp"
 
-#if !defined WIN32 && ((defined HAVE_CAMV4L && defined HAVE_CAMV4L2) || defined HAVE_VIDEOIO)
+#if !defined WIN32 && (defined HAVE_CAMV4L || defined HAVE_CAMV4L2 || defined HAVE_VIDEOIO)
 
 #define CLEAR(x) memset (&(x), 0, sizeof (x))
 
@@ -214,16 +214,18 @@ make & enjoy!
 #include <sys/types.h>
 #include <sys/mman.h>
 
+#ifdef HAVE_CAMVAL
 #include <linux/videodev.h>
+#endif
 
 #include <string.h>
 #include <stdlib.h>
-#include <asm/types.h>          /* for videodev2.h */
 #include <assert.h>
 #include <sys/stat.h>
 #include <sys/ioctl.h>
 
 #ifdef HAVE_CAMV4L2
+#include <asm/types.h>          /* for videodev2.h */
 #include <linux/videodev2.h>
 #endif
 
@@ -293,11 +295,13 @@ typedef struct CvCaptureCAM_V4L
     int deviceHandle;
     int bufferIndex;
     int FirstCapture;
+#ifdef HAVE_CAMV4L
     struct video_capability capability;
     struct video_window     captureWindow;
     struct video_picture    imageProperties;
     struct video_mbuf       memoryBuffer;
     struct video_mmap       *mmaps;
+#endif /* HAVE_CAMV4L */
     char *memoryMap;
     IplImage frame;
 
@@ -350,9 +354,6 @@ static int icvSetVideoSize( CvCaptureCAM_V4L* capture, int w, int h);
 static int numCameras = 0;
 static int indexList = 0;
 
-#ifdef HAVE_CAMV4L2
-
-// IOCTL handling for V4L2
 static int xioctl( int fd, int request, void *arg)
 {
 
@@ -366,8 +367,6 @@ static int xioctl( int fd, int request, void *arg)
 
 }
 
-#endif /* HAVE_CAMV4L2 */
-
 /* Simple test program: Find number of Video Sources available.
    Start from 0 and go to MAX_CAMERAS while checking for the device with that name.
    If it fails on the first attempt of /dev/video0, then check if /dev/video is valid.
@@ -398,6 +397,8 @@ static void icvInitCapture_V4L() {
 
 }; /* End icvInitCapture_V4L */
 
+#ifdef HAVE_CAMV4L
+
 static int
 try_palette(int fd,
             struct video_picture *cam_pic,
@@ -415,6 +416,8 @@ try_palette(int fd,
   return 0;
 }
 
+#endif /* HAVE_CAMV4L */
+
 #ifdef HAVE_CAMV4L2
 
 static int try_palette_v4l2(CvCaptureCAM_V4L* capture, unsigned long colorspace)
@@ -439,6 +442,8 @@ static int try_palette_v4l2(CvCaptureCAM_V4L* capture, unsigned long colorspace)
 
 #endif /* HAVE_CAMV4L2 */
 
+#ifdef HAVE_CAMV4L
+
 static int try_init_v4l(CvCaptureCAM_V4L* capture, char *deviceName)
 {
 
@@ -454,7 +459,6 @@ static int try_init_v4l(CvCaptureCAM_V4L* capture, char *deviceName)
   /* No matter what the name - it still must be opened! */
   capture->deviceHandle = open(deviceName, O_RDWR);
 
-
   if (capture->deviceHandle == 0)
   {
     detect = -1;
@@ -468,7 +472,6 @@ static int try_init_v4l(CvCaptureCAM_V4L* capture, char *deviceName)
     if (ioctl(capture->deviceHandle, VIDIOCGCAP, &capture->capability) < 0)
     {
       detect = 0;
-
       icvCloseCAM_V4L(capture);
     }
       else
@@ -481,54 +484,64 @@ static int try_init_v4l(CvCaptureCAM_V4L* capture, char *deviceName)
 
 }
 
+#endif /* HAVE_CAMV4L */
+
 #ifdef HAVE_CAMV4L2
 
 static int try_init_v4l2(CvCaptureCAM_V4L* capture, char *deviceName)
 {
-
-  // if detect = -1 then unable to open device
-  // if detect = 0 then detected nothing
-  // if detect = 1 then V4L2 device
-  int detect = 0;
-
-
   // Test device for V4L2 compability
+  // Return value:
+  // -1 then unable to open device
+  //  0 then detected nothing
+  //  1 then V4L2 device
+
+  int deviceIndex;
 
   /* Open and test V4L2 device */
   capture->deviceHandle = open (deviceName, O_RDWR /* required */ | O_NONBLOCK, 0);
-
-
-
-  if (capture->deviceHandle == 0)
+  if (-1 == capture->deviceHandle)
   {
-    detect = -1;
-
+#ifndef NDEBUG
+    fprintf(stderr, "(DEBUG) try_init_v4l2 open \"%s\": %s\n", deviceName, strerror(errno));
+#endif
     icvCloseCAM_V4L(capture);
+    return -1;
   }
 
-  if (detect == 0)
+  CLEAR (capture->cap);
+  if (-1 == xioctl (capture->deviceHandle, VIDIOC_QUERYCAP, &capture->cap))
   {
-    CLEAR (capture->cap);
-    if (-1 == xioctl (capture->deviceHandle, VIDIOC_QUERYCAP, &capture->cap))
-    {
-      detect = 0;
+#ifndef NDEBUG
+    fprintf(stderr, "(DEBUG) try_init_v4l2 VIDIOC_QUERYCAP \"%s\": %s\n", deviceName, strerror(errno));
+#endif
+    icvCloseCAM_V4L(capture);
+    return 0;
+  }
 
-      icvCloseCAM_V4L(capture);
-    }
-      else
-    {
-      CLEAR (capture->capability);
-      capture->capability.type = capture->cap.capabilities;
+  /* Query channels number */
+  if (-1 == xioctl (capture->deviceHandle, VIDIOC_G_INPUT, &deviceIndex))
+  {
+#ifndef NDEBUG
+    fprintf(stderr, "(DEBUG) try_init_v4l2 VIDIOC_G_INPUT \"%s\": %s\n", deviceName, strerror(errno));
+#endif
+    icvCloseCAM_V4L(capture);
+    return 0;
+  }
 
-      /* Query channels number */
-      if (-1 != xioctl (capture->deviceHandle, VIDIOC_G_INPUT, &capture->capability.channels))
-      {
-        detect = 1;
-      }
-    }
+  /* Query information about current input */
+  CLEAR (capture->inp);
+  capture->inp.index = deviceIndex;
+  if (-1 == xioctl (capture->deviceHandle, VIDIOC_ENUMINPUT, &capture->inp))
+  {
+#ifndef NDEBUG
+    fprintf(stderr, "(DEBUG) try_init_v4l2 VIDIOC_ENUMINPUT \"%s\": %s\n", deviceName, strerror(errno));
+#endif
+    icvCloseCAM_V4L(capture);
+    return 0;
   }
 
-  return detect;
+  return 1;
 
 }
 
@@ -551,10 +564,6 @@ static int autosetup_capture_mode_v4l2(CvCaptureCAM_V4L* capture)
   else
 
 #ifdef HAVE_JPEG
-#ifdef __USE_GNU
-      /* support for MJPEG is only available with libjpeg and gcc,
-     because it's use libjepg and fmemopen()
-      */
   if (try_palette_v4l2(capture, V4L2_PIX_FMT_MJPEG) == 0 ||
       try_palette_v4l2(capture, V4L2_PIX_FMT_JPEG) == 0)
   {
@@ -562,7 +571,6 @@ static int autosetup_capture_mode_v4l2(CvCaptureCAM_V4L* capture)
   }
   else
 #endif
-#endif
 
   if (try_palette_v4l2(capture, V4L2_PIX_FMT_YUYV) == 0)
   {
@@ -598,6 +606,8 @@ static int autosetup_capture_mode_v4l2(CvCaptureCAM_V4L* capture)
 
 #endif /* HAVE_CAMV4L2 */
 
+#ifdef HAVE_CAMV4L
+
 static int autosetup_capture_mode_v4l(CvCaptureCAM_V4L* capture)
 {
 
@@ -631,6 +641,8 @@ static int autosetup_capture_mode_v4l(CvCaptureCAM_V4L* capture)
 
 }
 
+#endif /* HAVE_CAMV4L */
+
 #ifdef HAVE_CAMV4L2
 
 static void v4l2_scan_controls_enumerate_menu(CvCaptureCAM_V4L* capture)
@@ -981,8 +993,8 @@ static int _capture_V4L2 (CvCaptureCAM_V4L *capture, char *deviceName)
 
    /* Set up Image data */
    cvInitImageHeader( &capture->frame,
-                      cvSize( capture->captureWindow.width,
-                              capture->captureWindow.height ),
+                      cvSize( capture->form.fmt.pix.width,
+                              capture->form.fmt.pix.height ),
                       IPL_DEPTH_8U, 3, IPL_ORIGIN_TL, 4 );
    /* Allocate space for RGBA data */
    capture->frame.imageData = (char *)cvAlloc(capture->frame.imageSize);
@@ -992,6 +1004,8 @@ static int _capture_V4L2 (CvCaptureCAM_V4L *capture, char *deviceName)
 
 #endif /* HAVE_CAMV4L2 */
 
+#ifdef HAVE_CAMV4L
+
 static int _capture_V4L (CvCaptureCAM_V4L *capture, char *deviceName)
 {
    int detect_v4l = 0;
@@ -1110,6 +1124,8 @@ static int _capture_V4L (CvCaptureCAM_V4L *capture, char *deviceName)
    return 1;
 }; /* End _capture_V4L */
 
+#endif /* HAVE_CAMV4L */
+
 static CvCaptureCAM_V4L * icvCaptureFromCAM_V4L (int index)
 {
    static int autoindex;
@@ -1159,10 +1175,12 @@ static CvCaptureCAM_V4L * icvCaptureFromCAM_V4L (int index)
        icvCloseCAM_V4L(capture);
        V4L2_SUPPORT = 0;
 #endif  /* HAVE_CAMV4L2 */
+#ifdef HAVE_CAMV4L
        if (_capture_V4L (capture, deviceName) == -1) {
            icvCloseCAM_V4L(capture);
            return NULL;
        }
+#endif  /* HAVE_CAMV4L */
 #ifdef HAVE_CAMV4L2
    } else {
        V4L2_SUPPORT = 1;
@@ -1271,7 +1289,9 @@ static int icvGrabFrameCAM_V4L(CvCaptureCAM_V4L* capture) {
 
 #ifdef HAVE_CAMV4L2
 
+#ifdef HAVE_CAMV4L
       if (V4L2_SUPPORT == 1)
+#endif
       {
 
         for (capture->bufferIndex = 0;
@@ -1301,8 +1321,12 @@ static int icvGrabFrameCAM_V4L(CvCaptureCAM_V4L* capture) {
             perror ("VIDIOC_STREAMON");
             return 0;
         }
-      } else
+      }
 #endif /* HAVE_CAMV4L2 */
+#if defined(HAVE_CAMV4L) && defined(HAVE_CAMV4L2)
+      else
+#endif /* HAVE_CAMV4L && HAVE_CAMV4L2 */
+#ifdef HAVE_CAMV4L
       {
 
         for (capture->bufferIndex = 0;
@@ -1321,6 +1345,7 @@ static int icvGrabFrameCAM_V4L(CvCaptureCAM_V4L* capture) {
         }
 
       }
+#endif /* HAVE_CAMV4L */
 
 #if defined(V4L_ABORT_BADJPEG) && defined(HAVE_CAMV4L2)
      if (V4L2_SUPPORT == 1)
@@ -1342,8 +1367,12 @@ static int icvGrabFrameCAM_V4L(CvCaptureCAM_V4L* capture) {
 
      mainloop_v4l2(capture);
 
-   } else
+   }
 #endif /* HAVE_CAMV4L2 */
+#if defined(HAVE_CAMV4L) && defined(HAVE_CAMV4L2)
+     else
+#endif /* HAVE_CAMV4L && HAVE_CAMV4L2 */
+#ifdef HAVE_CAMV4L
    {
 
      capture->mmaps[capture->bufferIndex].frame  = capture->bufferIndex;
@@ -1363,6 +1392,7 @@ static int icvGrabFrameCAM_V4L(CvCaptureCAM_V4L* capture) {
      }
 
    }
+#endif /* HAVE_CAMV4L */
 
    return(1);
 }
@@ -2080,6 +2110,7 @@ static IplImage* icvRetrieveFrameCAM_V4L( CvCaptureCAM_V4L* capture, int) {
 #ifdef HAVE_CAMV4L2
   if (V4L2_SUPPORT == 0)
 #endif /* HAVE_CAMV4L2 */
+#ifdef HAVE_CAMV4L
   {
 
     /* [FD] this really belongs here */
@@ -2088,6 +2119,7 @@ static IplImage* icvRetrieveFrameCAM_V4L( CvCaptureCAM_V4L* capture, int) {
     }
 
   }
+#endif /* HAVE_CAMV4L */
 
    /* Now get what has already been captured as a IplImage return */
 
@@ -2108,8 +2140,12 @@ static IplImage* icvRetrieveFrameCAM_V4L( CvCaptureCAM_V4L* capture, int) {
        capture->frame.imageData = (char *)cvAlloc(capture->frame.imageSize);
     }
 
-  } else
+  }
 #endif /* HAVE_CAMV4L2 */
+#if defined(HAVE_CAMV4L) && defined(HAVE_CAMV4L2)
+    else
+#endif /* HAVE_CAMV4L && HAVE_CAMV4L2 */
+#ifdef HAVE_CAMV4L
   {
 
     if((capture->frame.width != capture->mmaps[capture->bufferIndex].width)
@@ -2123,6 +2159,7 @@ static IplImage* icvRetrieveFrameCAM_V4L( CvCaptureCAM_V4L* capture, int) {
     }
 
   }
+#endif /* HAVE_CAMV4L */
 
 #ifdef HAVE_CAMV4L2
 
@@ -2150,10 +2187,6 @@ static IplImage* icvRetrieveFrameCAM_V4L( CvCaptureCAM_V4L* capture, int) {
              (unsigned char*)capture->frame.imageData);
     break;
 #ifdef HAVE_JPEG
-#ifdef __USE_GNU
-    /* support for MJPEG is only available with libjpeg and gcc,
-       because it's use libjepg and fmemopen()
-    */
       case PALETTE_MJPEG:
     if (!mjpeg_to_rgb24(capture->form.fmt.pix.width,
                 capture->form.fmt.pix.height,
@@ -2164,7 +2197,6 @@ static IplImage* icvRetrieveFrameCAM_V4L( CvCaptureCAM_V4L* capture, int) {
       return 0;
     break;
 #endif
-#endif
 
       case PALETTE_YUYV:
     yuyv_to_rgb24(capture->form.fmt.pix.width,
@@ -2206,8 +2238,12 @@ static IplImage* icvRetrieveFrameCAM_V4L( CvCaptureCAM_V4L* capture, int) {
             (unsigned char*)capture->frame.imageData);
     break;
       }
-  } else
+  }
 #endif /* HAVE_CAMV4L2 */
+#if defined(HAVE_CAMV4L) && defined(HAVE_CAMV4L2)
+    else
+#endif /* HAVE_CAMV4L && HAVE_CAMV4L2 */
+#ifdef HAVE_CAMV4L
   {
 
     switch(capture->imageProperties.palette) {
@@ -2243,6 +2279,7 @@ static IplImage* icvRetrieveFrameCAM_V4L( CvCaptureCAM_V4L* capture, int) {
     }
 
   }
+#endif /* HAVE_CAMV4L */
 
    return(&capture->frame);
 }
@@ -2252,7 +2289,9 @@ static double icvGetPropertyCAM_V4L (CvCaptureCAM_V4L* capture,
 
 #ifdef HAVE_CAMV4L2
 
+#ifdef HAVE_CAMV4L
   if (V4L2_SUPPORT == 1)
+#endif
   {
 
       /* default value for min and max */
@@ -2363,8 +2402,12 @@ static double icvGetPropertyCAM_V4L (CvCaptureCAM_V4L* capture,
       /* all was OK, so convert to 0.0 - 1.0 range, and return the value */
       return ((float)capture->control.value - v4l2_min + 1) / (v4l2_max - v4l2_min);
 
-  } else
+  }
 #endif /* HAVE_CAMV4L2 */
+#if defined(HAVE_CAMV4L) && defined(HAVE_CAMV4L2)
+    else
+#endif /* HAVE_CAMV4L && HAVE_CAMV4L2 */
+#ifdef HAVE_CAMV4L
   {
 
     int retval = -1;
@@ -2422,6 +2465,7 @@ static double icvGetPropertyCAM_V4L (CvCaptureCAM_V4L* capture,
     return float (retval) / 0xFFFF;
 
   }
+#endif /* HAVE_CAMV4L */
 
 };
 
@@ -2494,8 +2538,12 @@ static int icvSetVideoSize( CvCaptureCAM_V4L* capture, int w, int h) {
 
     return 0;
 
-  } else
+  }
 #endif /* HAVE_CAMV4L2 */
+#if defined(HAVE_CAMV4L) && defined(HAVE_CAMV4L2)
+    else
+#endif /* HAVE_CAMV4L && HAVE_CAMV4L2 */
+#ifdef HAVE_CAMV4L
   {
 
     if (capture==0) return 0;
@@ -2522,6 +2570,7 @@ static int icvSetVideoSize( CvCaptureCAM_V4L* capture, int w, int h) {
      capture->FirstCapture = 1;
 
   }
+#endif /* HAVE_CAMV4L */
 
   return 0;
 
@@ -2653,8 +2702,12 @@ static int icvSetControl (CvCaptureCAM_V4L* capture,
         perror ("VIDIOC_S_CTRL");
         return -1;
     }
-  } else
+  }
 #endif /* HAVE_CAMV4L2 */
+#if defined(HAVE_CAMV4L) && defined(HAVE_CAMV4L2)
+    else
+#endif /* HAVE_CAMV4L && HAVE_CAMV4L2 */
+#ifdef HAVE_CAMV4L
   {
 
     int v4l_value;
@@ -2699,6 +2752,7 @@ static int icvSetControl (CvCaptureCAM_V4L* capture,
        return -1;
     }
   }
+#endif /* HAVE_CAMV4L */
 
   /* all was OK */
   return 0;
@@ -2759,6 +2813,7 @@ static void icvCloseCAM_V4L( CvCaptureCAM_V4L* capture ){
 #ifdef HAVE_CAMV4L2
      if (V4L2_SUPPORT == 0)
 #endif /* HAVE_CAMV4L2 */
+#ifdef HAVE_CAMV4L
      {
 
        if (capture->mmaps)
@@ -2767,10 +2822,14 @@ static void icvCloseCAM_V4L( CvCaptureCAM_V4L* capture ){
          munmap(capture->memoryMap, capture->memoryBuffer.size);
 
      }
+#endif /* HAVE_CAMV4L */
+#if defined(HAVE_CAMV4L) && defined(HAVE_CAMV4L2)
+     else
+#endif /* HAVE_CAMV4L && HAVE_CAMV4L2 */
 #ifdef HAVE_CAMV4L2
-     else {
+       {
        capture->type = V4L2_BUF_TYPE_VIDEO_CAPTURE;
-       if (ioctl(capture->deviceHandle, VIDIOC_STREAMOFF, &capture->type) < 0) {
+       if (-1 == ioctl(capture->deviceHandle, VIDIOC_STREAMOFF, &capture->type)) {
            perror ("Unable to stop the stream.");
        }