diff options
author | Vasyl Vavrychuk <vasyl.vavrychuk@opensynergy.com> | 2021-09-14 07:08:22 +0200 |
---|---|---|
committer | Jan-Simon Moeller <jsmoeller@linuxfoundation.org> | 2021-12-07 22:54:14 +0000 |
commit | 3c3a41eb2b33ba2253eb7439ff6290c414143416 (patch) | |
tree | 9b50276b3be903de04fb82467638fb37d5a5d27d | |
parent | 88fde6fd98c0c4330cd91af267efa2f5492da180 (diff) |
Automatically detect camera capable v4l2 device.
Bug-AGL: SPEC-4148
Change-Id: I42cf0adf9e55679069992d73f079b916684f8e8b
Signed-off-by: Vasyl Vavrychuk <vasyl.vavrychuk@opensynergy.com>
-rw-r--r-- | app/main.cpp | 4 | ||||
-rw-r--r-- | app/utils.cpp | 47 | ||||
-rw-r--r-- | app/utils.h | 3 |
3 files changed, 51 insertions, 3 deletions
diff --git a/app/main.cpp b/app/main.cpp index fff9c4c..182489e 100644 --- a/app/main.cpp +++ b/app/main.cpp @@ -23,8 +23,6 @@ #include <gst/video/videooverlay.h> #include <gst/wayland/wayland.h> -#define DEFAULT_VIDEO_DEVICE "/dev/video0" - // these only applies if the window is a dialog/pop-up one // by default the compositor make the window maximized #define WINDOW_WIDTH_SIZE 640 @@ -669,7 +667,7 @@ int main(int argc, char *argv[]) memset(pipeline_str, 0, sizeof(pipeline_str)); snprintf(pipeline_str, sizeof(pipeline_str), "v4l2src device=%s ! video/x-raw,width=%d,height=%d ! waylandsink", - DEFAULT_VIDEO_DEVICE, WINDOW_WIDTH_SIZE, WINDOW_HEIGHT_SIZE); + get_camera_device(), WINDOW_WIDTH_SIZE, WINDOW_HEIGHT_SIZE); gst_init(&gargc, &gargv); setbuf(stdout, NULL); diff --git a/app/utils.cpp b/app/utils.cpp index f1c3eae..1cf71f2 100644 --- a/app/utils.cpp +++ b/app/utils.cpp @@ -1,10 +1,16 @@ #include <sys/mman.h> +#include <sys/types.h> +#include <sys/ioctl.h> #include <unistd.h> #include <fcntl.h> +#include <dirent.h> #include <assert.h> #include <cstdlib> #include <cstring> #include <cerrno> +#include <cstdio> +#include <cctype> +#include <linux/videodev2.h> #include "utils.h" @@ -148,3 +154,44 @@ os_create_anonymous_file(off_t size) return fd; } + +const char* +get_camera_device(void) +{ + DIR *dir = opendir("/dev"); + if (!dir) { + perror("Couldn't open the '/dev' directory"); + return NULL; + } + + static char device[PATH_MAX]; + bool found = false; + while (struct dirent *dirent = readdir(dir)) { + if (strncmp(dirent->d_name, "video", strlen("video"))) + continue; + if (!isdigit(dirent->d_name[strlen("video")])) + continue; + + strcpy(device, "/dev/"); + strncat(device, dirent->d_name, sizeof(device) - 1); + + int fd = open(device, O_RDWR); + if (fd == -1) + continue; + struct v4l2_capability vid_cap; + if (ioctl(fd, VIDIOC_QUERYCAP, &vid_cap) < 0) { + close(fd); + continue; + } + close(fd); + + if ((vid_cap.capabilities & V4L2_CAP_VIDEO_CAPTURE) || + (vid_cap.capabilities & V4L2_CAP_VIDEO_CAPTURE_MPLANE)) { + found = true; + break; + } + } + + closedir(dir); + return found ? device : NULL; +} diff --git a/app/utils.h b/app/utils.h index 99b2e30..8d6f0fd 100644 --- a/app/utils.h +++ b/app/utils.h @@ -8,6 +8,9 @@ extern "C" { int os_create_anonymous_file(off_t size); +const char* +get_camera_device(void); + #ifdef __cplusplus } #endif |