diff options
author | Chris Ye <lzye@google.com> | 2020-09-22 15:36:28 -0700 |
---|---|---|
committer | Chris Ye <lzye@google.com> | 2020-10-08 11:12:36 -0700 |
commit | 181353f5c41609b3c969f10595a2379da427183f (patch) | |
tree | aded8660f00b8c00de9a127c72161e1c413cebae | |
parent | fdc9ff756c7c6a6df851ae078eb128d96dfcb5a5 (diff) | |
download | native-181353f5c41609b3c969f10595a2379da427183f.tar.gz |
Fix InputDevice listener notification for merged controller.
Merged game controllers report unique device id combined from multiple
input devices, when notifying device listener input manager will send
a list of devices unique to each other.
When an event hub device is added to a input device, the generation Id
must be bumped to generate a device changed event for input device
listener.
Fixed the Sony game controller connection failure.
Fixed the duplicate device listing in input service dump.
Bug: 168338098
Test: atest inputflinger_tests
Change-Id: Ie4f57215880ff06264a7c4f80c505cf4acc6bca5
-rw-r--r-- | services/inputflinger/reader/InputDevice.cpp | 6 | ||||
-rw-r--r-- | services/inputflinger/reader/InputReader.cpp | 36 | ||||
-rw-r--r-- | services/inputflinger/reader/include/InputDevice.h | 2 | ||||
-rw-r--r-- | services/inputflinger/reader/include/InputReader.h | 5 |
4 files changed, 41 insertions, 8 deletions
diff --git a/services/inputflinger/reader/InputDevice.cpp b/services/inputflinger/reader/InputDevice.cpp index 4b19e5e353..3347ba6ad7 100644 --- a/services/inputflinger/reader/InputDevice.cpp +++ b/services/inputflinger/reader/InputDevice.cpp @@ -84,12 +84,13 @@ void InputDevice::setEnabled(bool enabled, nsecs_t when) { bumpGeneration(); } -void InputDevice::dump(std::string& dump) { +void InputDevice::dump(std::string& dump, const std::string& eventHubDevStr) { InputDeviceInfo deviceInfo; getDeviceInfo(&deviceInfo); dump += StringPrintf(INDENT "Device %d: %s\n", deviceInfo.getId(), deviceInfo.getDisplayName().c_str()); + dump += StringPrintf(INDENT "%s", eventHubDevStr.c_str()); dump += StringPrintf(INDENT2 "Generation: %d\n", mGeneration); dump += StringPrintf(INDENT2 "IsExternal: %s\n", toString(mIsExternal)); dump += StringPrintf(INDENT2 "AssociatedDisplayPort: "); @@ -101,6 +102,7 @@ void InputDevice::dump(std::string& dump) { dump += StringPrintf(INDENT2 "HasMic: %s\n", toString(mHasMic)); dump += StringPrintf(INDENT2 "Sources: 0x%08x\n", deviceInfo.getSources()); dump += StringPrintf(INDENT2 "KeyboardType: %d\n", deviceInfo.getKeyboardType()); + dump += StringPrintf(INDENT2 "ControllerNum: %d\n", deviceInfo.getControllerNumber()); const std::vector<InputDeviceInfo::MotionRange>& ranges = deviceInfo.getMotionRanges(); if (!ranges.empty()) { @@ -200,6 +202,8 @@ void InputDevice::addEventHubDevice(int32_t eventHubId, bool populateMappers) { // insert the context into the devices set mDevices.insert({eventHubId, std::make_pair(std::move(contextPtr), std::move(mappers))}); + // Must change generation to flag this device as changed + bumpGeneration(); } void InputDevice::removeEventHubDevice(int32_t eventHubId) { diff --git a/services/inputflinger/reader/InputReader.cpp b/services/inputflinger/reader/InputReader.cpp index 657a134865..fc063f97ab 100644 --- a/services/inputflinger/reader/InputReader.cpp +++ b/services/inputflinger/reader/InputReader.cpp @@ -206,6 +206,14 @@ void InputReader::addDeviceLocked(nsecs_t when, int32_t eventHubId) { } mDevices.emplace(eventHubId, device); + // Add device to device to EventHub ids map. + const auto mapIt = mDeviceToEventHubIdsMap.find(device); + if (mapIt == mDeviceToEventHubIdsMap.end()) { + std::vector<int32_t> ids = {eventHubId}; + mDeviceToEventHubIdsMap.emplace(device, ids); + } else { + mapIt->second.push_back(eventHubId); + } bumpGenerationLocked(); if (device->getClasses() & INPUT_DEVICE_CLASS_EXTERNAL_STYLUS) { @@ -222,6 +230,17 @@ void InputReader::removeDeviceLocked(nsecs_t when, int32_t eventHubId) { std::shared_ptr<InputDevice> device = std::move(deviceIt->second); mDevices.erase(deviceIt); + // Erase device from device to EventHub ids map. + auto mapIt = mDeviceToEventHubIdsMap.find(device); + if (mapIt != mDeviceToEventHubIdsMap.end()) { + std::vector<int32_t>& eventHubIds = mapIt->second; + eventHubIds.erase(std::remove_if(eventHubIds.begin(), eventHubIds.end(), + [eventHubId](int32_t eId) { return eId == eventHubId; }), + eventHubIds.end()); + if (eventHubIds.size() == 0) { + mDeviceToEventHubIdsMap.erase(mapIt); + } + } bumpGenerationLocked(); if (device->isIgnored()) { @@ -449,8 +468,7 @@ void InputReader::getInputDevices(std::vector<InputDeviceInfo>& outInputDevices) void InputReader::getInputDevicesLocked(std::vector<InputDeviceInfo>& outInputDevices) { outInputDevices.clear(); - for (auto& devicePair : mDevices) { - std::shared_ptr<InputDevice>& device = devicePair.second; + for (const auto& [device, eventHubIds] : mDeviceToEventHubIdsMap) { if (!device->isIgnored()) { InputDeviceInfo info; device->getDeviceInfo(&info); @@ -621,11 +639,17 @@ void InputReader::dump(std::string& dump) { mEventHub->dump(dump); dump += "\n"; - dump += "Input Reader State:\n"; + dump += StringPrintf("Input Reader State (Nums of device: %zu):\n", + mDeviceToEventHubIdsMap.size()); - for (const auto& devicePair : mDevices) { - const std::shared_ptr<InputDevice>& device = devicePair.second; - device->dump(dump); + for (const auto& devicePair : mDeviceToEventHubIdsMap) { + const std::shared_ptr<InputDevice>& device = devicePair.first; + std::string eventHubDevStr = INDENT "EventHub Devices: [ "; + for (const auto& eId : devicePair.second) { + eventHubDevStr += StringPrintf("%d ", eId); + } + eventHubDevStr += "] \n"; + device->dump(dump, eventHubDevStr); } dump += INDENT "Configuration:\n"; diff --git a/services/inputflinger/reader/include/InputDevice.h b/services/inputflinger/reader/include/InputDevice.h index 71313fc86f..a08062adef 100644 --- a/services/inputflinger/reader/include/InputDevice.h +++ b/services/inputflinger/reader/include/InputDevice.h @@ -66,7 +66,7 @@ public: bool isEnabled(); void setEnabled(bool enabled, nsecs_t when); - void dump(std::string& dump); + void dump(std::string& dump, const std::string& eventHubDevStr); void addEventHubDevice(int32_t eventHubId, bool populateMappers = true); void removeEventHubDevice(int32_t eventHubId); void configure(nsecs_t when, const InputReaderConfiguration* config, uint32_t changes); diff --git a/services/inputflinger/reader/include/InputReader.h b/services/inputflinger/reader/include/InputReader.h index 693ec30b7d..d46ec1a783 100644 --- a/services/inputflinger/reader/include/InputReader.h +++ b/services/inputflinger/reader/include/InputReader.h @@ -141,6 +141,11 @@ private: // to lookup the input device instance from the EventHub device id. std::unordered_map<int32_t /*eventHubId*/, std::shared_ptr<InputDevice>> mDevices; + // An input device contains one or more eventHubId, this map provides a way to lookup the + // EventHubIds contained in the input device from the input device instance. + std::unordered_map<std::shared_ptr<InputDevice>, std::vector<int32_t> /*eventHubId*/> + mDeviceToEventHubIdsMap; + // low-level input event decoding and device management void processEventsLocked(const RawEvent* rawEvents, size_t count); |