diff options
author | Andrew Duggan <aduggan@synaptics.com> | 2017-03-27 19:53:45 -0700 |
---|---|---|
committer | Andrew Duggan <aduggan@synaptics.com> | 2017-03-30 09:53:39 -0700 |
commit | 1db0d35356ff384a4114f6b30aad9a9d0e89f4dc (patch) | |
tree | 2b6a89d436a80cadef6f79e308fe50347c08d9f3 | |
parent | 3781959e23f79fec610e87cfbc3a43c6b24ea7ba (diff) | |
download | rmi4utils-1db0d35356ff384a4114f6b30aad9a9d0e89f4dc.tar.gz |
For HID devices restore the original operating mode on close
-rw-r--r-- | rmidevice/hiddevice.cpp | 48 | ||||
-rw-r--r-- | rmidevice/hiddevice.h | 14 |
2 files changed, 51 insertions, 11 deletions
diff --git a/rmidevice/hiddevice.cpp b/rmidevice/hiddevice.cpp index 7476f06..808751c 100644 --- a/rmidevice/hiddevice.cpp +++ b/rmidevice/hiddevice.cpp @@ -41,12 +41,6 @@ #define RMI_ATTN_REPORT_ID 0xc // Input Report #define RMI_SET_RMI_MODE_REPORT_ID 0xf // Feature Report -enum rmi_hid_mode_type { - HID_RMI4_MODE_MOUSE = 0, - HID_RMI4_MODE_ATTN_REPORTS = 1, - HID_RMI4_MODE_NO_PACKED_ATTN_REPORTS = 2, -}; - enum hid_report_type { HID_REPORT_TYPE_UNKNOWN = 0x0, HID_REPORT_TYPE_INPUT = 0x81, @@ -72,6 +66,8 @@ int HIDDevice::Open(const char * filename) { int rc; int desc_size; + std::string hidDeviceName; + std::string hidDriverName; if (!filename) return -EINVAL; @@ -134,10 +130,21 @@ int HIDDevice::Open(const char * filename) m_deviceOpen = true; - rc = SetMode(HID_RMI4_MODE_ATTN_REPORTS); - if (rc) { - rc = -1; - goto error; + // Determine which mode the device is currently running in based on the current HID driver + // hid-rmi indicated RMI Mode 1 all others would be Mode 0 + if (LookupHidDeviceName(m_info.bustype, m_info.vendor, m_info.product, hidDeviceName)) { + if (LookupHidDriverName(hidDeviceName, hidDriverName)) { + if (hidDriverName == "hid-rmi") + m_initialMode = HID_RMI4_MODE_ATTN_REPORTS; + } + } + + if (m_initialMode != m_mode) { + rc = SetMode(m_mode); + if (rc) { + rc = -1; + goto error; + } } return 0; @@ -401,6 +408,9 @@ void HIDDevice::Close() if (!m_deviceOpen) return; + if (m_initialMode != m_mode) + SetMode(m_initialMode); + m_deviceOpen = false; close(m_fd); m_fd = -1; @@ -762,6 +772,24 @@ bool HIDDevice::LookupHidDeviceName(int bus, int vendorId, int productId, std::s return ret; } +bool HIDDevice::LookupHidDriverName(std::string &deviceName, std::string &driverName) +{ + bool ret = false; + ssize_t sz; + char link[PATH_MAX]; + std::string driverLink = "/sys/bus/hid/devices/" + deviceName + "/driver"; + + sz = readlink(driverLink.c_str(), link, PATH_MAX); + if (sz == -1) + return ret; + + link[sz] = 0; + + driverName = std::string(StripPath(link, PATH_MAX)); + + return true; +} + bool HIDDevice::WaitForHidRawDevice(int notifyFd, std::string & deviceName, std::string & hidrawFile) { diff --git a/rmidevice/hiddevice.h b/rmidevice/hiddevice.h index f3a88f0..2c794c7 100644 --- a/rmidevice/hiddevice.h +++ b/rmidevice/hiddevice.h @@ -22,6 +22,12 @@ #include <string> #include "rmidevice.h" +enum rmi_hid_mode_type { + HID_RMI4_MODE_MOUSE = 0, + HID_RMI4_MODE_ATTN_REPORTS = 1, + HID_RMI4_MODE_NO_PACKED_ATTN_REPORTS = 2, +}; + class HIDDevice : public RMIDevice { public: @@ -30,7 +36,9 @@ public: m_inputReportSize(0), m_outputReportSize(0), m_featureReportSize(0), - m_deviceOpen(false) + m_deviceOpen(false), + m_mode(HID_RMI4_MODE_ATTN_REPORTS), + m_initialMode(HID_RMI4_MODE_MOUSE) {} virtual int Open(const char * filename); virtual int Read(unsigned short addr, unsigned char *buf, @@ -69,12 +77,16 @@ private: bool m_deviceOpen; + rmi_hid_mode_type m_mode; + rmi_hid_mode_type m_initialMode; + int GetReport(int *reportId, struct timeval * timeout = NULL); void PrintReport(const unsigned char *report); void ParseReportDescriptor(); // static HID utility functions static bool LookupHidDeviceName(int bus, int vendorId, int productId, std::string &deviceName); + static bool LookupHidDriverName(std::string &deviceName, std::string &driverName); static bool FindTransportDevice(int bus, std::string & hidDeviceName, std::string & transportDeviceName, std::string & driverPath); static bool WaitForHidRawDevice(int notifyFd, std::string & deviceName, std::string & hidraw); |