diff --git a/src/core/linux/SDL_udev.c b/src/core/linux/SDL_udev.c index 3aaa0fb4e9..111e362f6c 100644 --- a/src/core/linux/SDL_udev.c +++ b/src/core/linux/SDL_udev.c @@ -464,6 +464,7 @@ static int device_class(struct udev_device *dev) { const char *subsystem; const char *val = NULL; + const char *attr = NULL; int devclass = 0; subsystem = _this->syms.udev_device_get_subsystem(dev); @@ -475,8 +476,18 @@ static int device_class(struct udev_device *dev) devclass = SDL_UDEV_DEVICE_SOUND; } else if (SDL_strcmp(subsystem, "video4linux") == 0) { val = _this->syms.udev_device_get_property_value(dev, "ID_V4L_CAPABILITIES"); - if (val && SDL_strcasestr(val, "capture")) { - devclass = SDL_UDEV_DEVICE_VIDEO_CAPTURE; + if (val) { + if (SDL_strcasestr(val, "capture")) { + devclass = SDL_UDEV_DEVICE_VIDEO_CAPTURE; + } + // v4l2loopback may report output caps before reporting capture caps + // and ID_V4L_CAPABILITIES is never updated + else if (SDL_strcasestr(val, "video_output")) { + attr = _this->syms.udev_device_get_sysattr_value(dev, "state"); + if (attr && SDL_strcmp(attr, "capture") == 0) { + devclass = SDL_UDEV_DEVICE_VIDEO_CAPTURE; + } + } } } else if (SDL_strcmp(subsystem, "input") == 0) { // udev rules reference: http://cgit.freedesktop.org/systemd/systemd/tree/src/udev/udev-builtin-input_id.c