avicap32 patch
Maarten Lankhorst
m.b.lankhorst at gmail.com
Mon Apr 25 12:14:08 CDT 2005
This patch implements capGetDriverDescription, I wrote it so i could use
it in devenum to implement vfwcapture
it checks for linux/videodev.h and if it's found, it can be used in
avicap32..
linux/videodev.h also includes videodev2.h if V4L2 is available, and if
it is, it defines HAVE_V4L2, which I also use in the patch
-------------- next part --------------
Index: configure.ac
===================================================================
RCS file: /home/wine/wine/configure.ac,v
retrieving revision 1.347
diff -u -p -r1.347 configure.ac
--- configure.ac 20 Apr 2005 19:15:31 -0000 1.347
+++ configure.ac 25 Apr 2005 17:08:11 -0000
@@ -1211,6 +1211,9 @@ AC_CHECK_HEADERS([resolv.h],,,
AC_CHECK_HEADERS(ucontext.h,,,[#include <signal.h>])
+dnl **** Check for v4l headers ****
+AC_CHECK_HEADERS(linux/videodev.h,,,[#include <asm/types.h>])
+
dnl **** Check for IPX headers (currently Linux only) ****
AC_CACHE_CHECK([for GNU style IPX support], ac_cv_c_ipx_gnu,
Index: configure
===================================================================
RCS file: /home/wine/wine/configure,v
retrieving revision 1.643
diff -u -p -r1.643 configure
--- configure 20 Apr 2005 19:15:31 -0000 1.643
+++ configure 25 Apr 2005 17:08:22 -0000
@@ -16809,6 +16809,67 @@ done
+for ac_header in linux/videodev.h
+do
+as_ac_Header=`echo "ac_cv_header_$ac_header" | $as_tr_sh`
+echo "$as_me:$LINENO: checking for $ac_header" >&5
+echo $ECHO_N "checking for $ac_header... $ECHO_C" >&6
+if eval "test \"\${$as_ac_Header+set}\" = set"; then
+ echo $ECHO_N "(cached) $ECHO_C" >&6
+else
+ cat >conftest.$ac_ext <<_ACEOF
+/* confdefs.h. */
+_ACEOF
+cat confdefs.h >>conftest.$ac_ext
+cat >>conftest.$ac_ext <<_ACEOF
+/* end confdefs.h. */
+#include <asm/types.h>
+
+#include <$ac_header>
+_ACEOF
+rm -f conftest.$ac_objext
+if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5
+ (eval $ac_compile) 2>conftest.er1
+ ac_status=$?
+ grep -v '^ *+' conftest.er1 >conftest.err
+ rm -f conftest.er1
+ cat conftest.err >&5
+ echo "$as_me:$LINENO: \$? = $ac_status" >&5
+ (exit $ac_status); } &&
+ { ac_try='test -z "$ac_c_werror_flag" || test ! -s conftest.err'
+ { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5
+ (eval $ac_try) 2>&5
+ ac_status=$?
+ echo "$as_me:$LINENO: \$? = $ac_status" >&5
+ (exit $ac_status); }; } &&
+ { ac_try='test -s conftest.$ac_objext'
+ { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5
+ (eval $ac_try) 2>&5
+ ac_status=$?
+ echo "$as_me:$LINENO: \$? = $ac_status" >&5
+ (exit $ac_status); }; }; then
+ eval "$as_ac_Header=yes"
+else
+ echo "$as_me: failed program was:" >&5
+sed 's/^/| /' conftest.$ac_ext >&5
+
+eval "$as_ac_Header=no"
+fi
+rm -f conftest.err conftest.$ac_objext conftest.$ac_ext
+fi
+echo "$as_me:$LINENO: result: `eval echo '${'$as_ac_Header'}'`" >&5
+echo "${ECHO_T}`eval echo '${'$as_ac_Header'}'`" >&6
+if test `eval echo '${'$as_ac_Header'}'` = yes; then
+ cat >>confdefs.h <<_ACEOF
+#define `echo "HAVE_$ac_header" | $as_tr_cpp` 1
+_ACEOF
+
+fi
+
+done
+
+
+
echo "$as_me:$LINENO: checking for GNU style IPX support" >&5
echo $ECHO_N "checking for GNU style IPX support... $ECHO_C" >&6
if test "${ac_cv_c_ipx_gnu+set}" = set; then
Index: include/config.h.in
===================================================================
RCS file: /home/wine/wine/include/config.h.in,v
retrieving revision 1.214
diff -u -p -r1.214 config.h.in
--- include/config.h.in 4 Mar 2005 12:38:37 -0000 1.214
+++ include/config.h.in 25 Apr 2005 17:08:22 -0000
@@ -335,6 +335,9 @@
/* Define to 1 if you have the <linux/ucdrom.h> header file. */
#undef HAVE_LINUX_UCDROM_H
+/* Define to 1 if you have the <linux/videodev.h> header file. */
+#undef HAVE_LINUX_VIDEODEV_H
+
/* Define to 1 if the system has the type `long long'. */
#undef HAVE_LONG_LONG
Index: dlls/avicap32/Makefile.in
===================================================================
RCS file: /home/wine/wine/dlls/avicap32/Makefile.in,v
retrieving revision 1.7
diff -u -p -r1.7 Makefile.in
--- dlls/avicap32/Makefile.in 11 Oct 2003 01:09:21 -0000 1.7
+++ dlls/avicap32/Makefile.in 25 Apr 2005 17:09:02 -0000
@@ -3,7 +3,7 @@ TOPOBJDIR = ../..
SRCDIR = @srcdir@
VPATH = @srcdir@
MODULE = avicap32.dll
-IMPORTS = ntdll
+IMPORTS = ntdll unicows kernel32
C_SRCS = avicap32_main.c
Index: dlls/avicap32/avicap32_main.c
===================================================================
RCS file: /home/wine/wine/dlls/avicap32/avicap32_main.c,v
retrieving revision 1.11
diff -u -p -r1.11 avicap32_main.c
--- dlls/avicap32/avicap32_main.c 9 Sep 2003 19:39:32 -0000 1.11
+++ dlls/avicap32/avicap32_main.c 25 Apr 2005 17:09:03 -0000
@@ -17,6 +17,7 @@
*/
#define COM_NO_WINDOWS_H
+#include "config.h"
#include <stdarg.h>
#include "windef.h"
@@ -28,6 +29,18 @@
#include "winternl.h"
#include "wine/debug.h"
+#ifdef HAVE_LINUX_VIDEODEV_H
+#include <stdio.h>
+#include <sys/ioctl.h>
+#include <sys/stat.h>
+#include <errno.h>
+#include <asm/types.h>
+#include <linux/videodev.h>
+#include <fcntl.h>
+#include <unistd.h>
+#include "winnls.h"
+#endif
+
WINE_DEFAULT_DEBUG_CHANNEL(avicap);
@@ -63,15 +76,102 @@ HWND VFWAPI capCreateCaptureWindowA(LPCS
return retW;
}
+#ifdef HAVE_LINUX_VIDEODEV_H
+static int xioctl(int fd, int request, void * arg)
+{
+ int r;
+
+ do r = ioctl (fd, request, arg);
+ while (-1 == r && EINTR == errno);
+
+ return r;
+}
+
+static BOOL queryvideodevice(int devnum, char *name, char *version)
+{
+ int fd = -1;
+ char device[16];
+ struct stat st;
+ struct video_capability capa;
+#ifdef HAVE_V4L2
+ struct v4l2_capability caps;
+#endif
+
+ sprintf(device, "/dev/video%i", devnum);
+
+ if (stat (device, &st) == -1) {
+ /* This is probably because the device does not exist */
+ WARN("%s: %s\n", device, strerror(errno));
+ return 0;
+ }
+
+ if (!S_ISCHR (st.st_mode)) {
+ ERR("%s: Not a device\n", device);
+ return 0;
+ }
+
+ fd = open(device, O_RDWR | O_NONBLOCK);
+ if (fd == 0) {
+ ERR("%s: Failed to open: %s\n", device, strerror(errno));
+ return 0;
+ }
+
+#ifdef HAVE_V4L2
+ memset(&caps, 0, sizeof(caps));
+ if (xioctl(fd, VIDIOC_QUERYCAP, &caps) != -1) {
+ strcpy(name, caps.card);
+ name[sizeof(caps.card) - 1] = 0;
+ sprintf(version, "%s v%u.%u.%u", caps.driver, (caps.version >> 16) & 0xFF,
+ (caps.version >> 8) & 0xFF, caps.version & 0xFF);
+ close(fd);
+ return 1;
+ }
+
+ if (errno != EINVAL && errno != 515)
+ WARN("%s: ioctl failed: %s -- Falling back to V4L\n", device, strerror(errno));
+ else WARN("%s: Not a V4L2 compatible device, trying V4l 1\n", device);
+#endif /* HAVE_V4L2 */
+
+ memset(&capa, 0, sizeof(capa));
+ if (xioctl(fd, VIDIOCGCAP, &capa) == -1) {
+/* errno 515 is used by some webcam drivers for unknown IOICTL command */
+ if (errno != EINVAL && errno != 515)
+ ERR("%s: Querying failed: %s\n", device, strerror(errno));
+ else ERR("%s: Querying failed: Not a V4L compatible device", device);
+ close(fd);
+ return 0;
+ }
+
+ strcpy(name, capa.name);
+ strcpy(version, device);
+ close(fd);
+ return 1;
+}
+
+#else /* HAVE_LINUX_VIDEODEV_H */
+
+static int queryvideodevice(int devnum, char *name, char *version)
+{
+ ERR("Video 4 Linux support not enabled\n");
+ return 0;
+}
+
+#endif /* HAVE_LINUX_VIDEODEV_H */
+
/***********************************************************************
* capGetDriverDescriptionA (AVICAP32.@)
*/
BOOL VFWAPI capGetDriverDescriptionA(WORD wDriverIndex, LPSTR lpszName,
INT cbName, LPSTR lpszVer, INT cbVer)
{
- FIXME("(%d, %p, %d, %p, %d) stub!\n", wDriverIndex, lpszName, cbName,
- lpszVer, cbVer);
- return FALSE;
+ char devname[32], devver[32];
+
+ if (!queryvideodevice(wDriverIndex, devname, devver)) return FALSE;
+
+ strncpy(lpszName, devname, cbName);
+ strncpy(lpszVer, devver, cbVer);
+ TRACE("Version: %s - Name: %s\n", lpszVer, lpszName);
+ return TRUE;
}
/***********************************************************************
@@ -80,7 +180,13 @@ BOOL VFWAPI capGetDriverDescriptionA(WOR
BOOL VFWAPI capGetDriverDescriptionW(WORD wDriverIndex, LPWSTR lpszName,
INT cbName, LPWSTR lpszVer, INT cbVer)
{
- FIXME("(%d, %p, %d, %p, %d) stub!\n", wDriverIndex, lpszName, cbName,
- lpszVer, cbVer);
- return FALSE;
+ char devname[32], devver[32];
+
+ if (!queryvideodevice(wDriverIndex, devname, devver)) return FALSE;
+
+ MultiByteToWideChar(CP_UTF8, 0, devname, -1, lpszName, cbName);
+ MultiByteToWideChar(CP_UTF8, 0, devver, -1, lpszVer, cbVer);
+ TRACE("Version: %s - Name: %s\n", debugstr_w(lpszVer), debugstr_w(lpszName));
+ return TRUE;
}
+
More information about the wine-patches
mailing list