| Index: ui/events/ozone/evdev/event_factory.cc
|
| diff --git a/ui/events/ozone/evdev/event_factory.cc b/ui/events/ozone/evdev/event_factory.cc
|
| index cc928197d7eaec071d270182d7a3c9efffb3d2ac..a458eab9bedd9c511ed9706e3da0c5020f5113f4 100644
|
| --- a/ui/events/ozone/evdev/event_factory.cc
|
| +++ b/ui/events/ozone/evdev/event_factory.cc
|
| @@ -4,26 +4,19 @@
|
|
|
| #include "ui/events/ozone/evdev/event_factory.h"
|
|
|
| -#include <errno.h>
|
| #include <fcntl.h>
|
| #include <linux/input.h>
|
| -#include <poll.h>
|
| -#include <unistd.h>
|
|
|
| -#if defined(USE_UDEV)
|
| -#include <libudev.h>
|
| -#endif
|
| -
|
| -#include "base/callback.h"
|
| #include "base/debug/trace_event.h"
|
| #include "base/files/file_enumerator.h"
|
| #include "base/stl_util.h"
|
| -#include "base/strings/stringprintf.h"
|
| -#include "base/threading/thread_restrictions.h"
|
| #include "ui/events/ozone/evdev/event_device_info.h"
|
| #include "ui/events/ozone/evdev/key_event_converter.h"
|
| #include "ui/events/ozone/evdev/touch_event_converter.h"
|
| -#include "ui/events/ozone/event_factory_ozone.h"
|
| +
|
| +#if defined(USE_UDEV)
|
| +#include "ui/events/ozone/evdev/device_manager_udev.h"
|
| +#endif
|
|
|
| namespace ui {
|
|
|
| @@ -41,86 +34,29 @@ bool IsTouchScreen(const EventDeviceInfo& devinfo) {
|
| return devinfo.HasEventType(EV_ABS) && !IsTouchPad(devinfo);
|
| }
|
|
|
| -#if defined(USE_UDEV)
|
| -
|
| -// Severity levels from syslog.h. We can't include it directly as it
|
| -// conflicts with base/logging.h
|
| -enum {
|
| - SYS_LOG_EMERG = 0,
|
| - SYS_LOG_ALERT = 1,
|
| - SYS_LOG_CRIT = 2,
|
| - SYS_LOG_ERR = 3,
|
| - SYS_LOG_WARNING = 4,
|
| - SYS_LOG_NOTICE = 5,
|
| - SYS_LOG_INFO = 6,
|
| - SYS_LOG_DEBUG = 7,
|
| -};
|
| -
|
| -// Log handler for messages generated from libudev.
|
| -void UdevLog(struct udev* udev,
|
| - int priority,
|
| - const char* file,
|
| - int line,
|
| - const char* fn,
|
| - const char* format,
|
| - va_list args) {
|
| - std::string message = base::StringPrintf("libudev: %s: ", fn);
|
| - base::StringAppendV(&message, format, args);
|
| - if (priority <= SYS_LOG_ERR)
|
| - LOG(ERROR) << message;
|
| - else if (priority <= SYS_LOG_INFO)
|
| - VLOG(1) << message;
|
| - else // SYS_LOG_DEBUG
|
| - VLOG(2) << message;
|
| -}
|
| -
|
| -// Connect to the udev daemon.
|
| -scoped_udev UdevConnect() {
|
| - struct udev* udev = udev_new();
|
| - if (udev) {
|
| - udev_set_log_fn(udev, UdevLog);
|
| - udev_set_log_priority(udev, SYS_LOG_DEBUG);
|
| +class DeviceManagerManual : public DeviceManagerEvdev {
|
| + public:
|
| + DeviceManagerManual() {}
|
| + virtual ~DeviceManagerManual() {}
|
| +
|
| + // Enumerate existing devices & start watching for device changes.
|
| + virtual void ScanAndStartMonitoring(const EvdevDeviceCallback& device_added,
|
| + const EvdevDeviceCallback& device_removed)
|
| + OVERRIDE {
|
| + base::FileEnumerator file_enum(base::FilePath("/dev/input"),
|
| + false,
|
| + base::FileEnumerator::FILES,
|
| + "event*[0-9]");
|
| + for (base::FilePath path = file_enum.Next(); !path.empty();
|
| + path = file_enum.Next())
|
| + device_added.Run(path);
|
| }
|
| - return scoped_udev(udev);
|
| -}
|
| -
|
| -// Enumerate all input devices using udev. Calls device_callback per device.
|
| -bool UdevEnumerateInputDevices(
|
| - struct udev* udev,
|
| - base::Callback<void(const base::FilePath&)> device_callback) {
|
| - scoped_udev_enumerate enumerate(udev_enumerate_new(udev));
|
| - if (!enumerate)
|
| - return false;
|
| -
|
| - udev_enumerate_add_match_subsystem(enumerate.get(), "input");
|
| - udev_enumerate_scan_devices(enumerate.get());
|
| -
|
| - struct udev_list_entry* devices =
|
| - udev_enumerate_get_list_entry(enumerate.get());
|
| - struct udev_list_entry* entry;
|
| -
|
| - udev_list_entry_foreach(entry, devices) {
|
| - const char* name = udev_list_entry_get_name(entry);
|
| -
|
| - scoped_udev_device device(udev_device_new_from_syspath(udev, name));
|
| - if (!device)
|
| - continue;
|
| -
|
| - const char* path = udev_device_get_devnode(device.get());
|
| - if (!path)
|
| - continue;
|
| -
|
| - // Found input device node; attach.
|
| - device_callback.Run(base::FilePath(path));
|
| - }
|
| -
|
| - return true;
|
| -}
|
| -
|
| -#endif // defined(USE_UDEV)
|
| +};
|
|
|
| } // namespace
|
|
|
| +DeviceManagerEvdev::~DeviceManagerEvdev() {}
|
| +
|
| EventFactoryEvdev::EventFactoryEvdev() {}
|
|
|
| EventFactoryEvdev::~EventFactoryEvdev() { STLDeleteValues(&converters_); }
|
| @@ -147,7 +83,7 @@ void EventFactoryEvdev::AttachInputDevice(const base::FilePath& path) {
|
| return;
|
| }
|
|
|
| - // TODO(spang) Add more device types. Support hot-plugging.
|
| + // TODO(spang) Add more device types.
|
| scoped_ptr<EventConverterEvdev> converter;
|
| if (IsTouchScreen(devinfo))
|
| converter.reset(new TouchEventConverterEvdev(fd, path));
|
| @@ -155,47 +91,32 @@ void EventFactoryEvdev::AttachInputDevice(const base::FilePath& path) {
|
| converter.reset(new KeyEventConverterEvdev(fd, path, &modifiers_));
|
|
|
| if (converter) {
|
| + delete converters_[path];
|
| converters_[path] = converter.release();
|
| } else {
|
| close(fd);
|
| }
|
| }
|
|
|
| -void EventFactoryEvdev::StartProcessingEvents() {
|
| - base::ThreadRestrictions::AssertIOAllowed();
|
| +void EventFactoryEvdev::DetachInputDevice(const base::FilePath& path) {
|
| + TRACE_EVENT1("ozone", "DetachInputDevice", "path", path.value());
|
| + delete converters_[path];
|
| + converters_.erase(path);
|
| +}
|
|
|
| +void EventFactoryEvdev::StartProcessingEvents() {
|
| #if defined(USE_UDEV)
|
| // Scan for input devices using udev.
|
| - StartProcessingEventsUdev();
|
| + device_manager_ = CreateDeviceManagerUdev();
|
| #else
|
| // No udev support. Scan devices manually in /dev/input.
|
| - StartProcessingEventsManual();
|
| + device_manager_.reset(new DeviceManagerManual);
|
| #endif
|
| -}
|
|
|
| -void EventFactoryEvdev::StartProcessingEventsManual() {
|
| - base::FileEnumerator file_enum(base::FilePath("/dev/input"),
|
| - false,
|
| - base::FileEnumerator::FILES,
|
| - "event*[0-9]");
|
| - for (base::FilePath path = file_enum.Next(); !path.empty();
|
| - path = file_enum.Next())
|
| - AttachInputDevice(path);
|
| + device_manager_->ScanAndStartMonitoring(
|
| + base::Bind(&EventFactoryEvdev::AttachInputDevice, base::Unretained(this)),
|
| + base::Bind(&EventFactoryEvdev::DetachInputDevice,
|
| + base::Unretained(this)));
|
| }
|
|
|
| -#if defined(USE_UDEV)
|
| -void EventFactoryEvdev::StartProcessingEventsUdev() {
|
| - udev_ = UdevConnect();
|
| - if (!udev_) {
|
| - LOG(ERROR) << "failed to connect to udev";
|
| - return;
|
| - }
|
| - if (!UdevEnumerateInputDevices(
|
| - udev_.get(),
|
| - base::Bind(&EventFactoryEvdev::AttachInputDevice,
|
| - base::Unretained(this))))
|
| - LOG(ERROR) << "failed to enumerate input devices via udev";
|
| -}
|
| -#endif
|
| -
|
| } // namespace ui
|
|
|