blob: 969c03268ef8394219888d0a0a0f892f11d7fc7a [file] [log] [blame]
Michael Ensingb8d93262020-05-12 00:41:30 -07001/*
2 * Copyright 2022 The Android Open Source Project
3 *
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
7 *
8 * http://www.apache.org/licenses/LICENSE-2.0
9 *
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
15 */
Michael Ensingb8d93262020-05-12 00:41:30 -070016#pragma once
17
Harry Cuttsccb75e82023-06-23 14:08:06 +000018#include <map>
Harry Cuttsf61c0472023-07-10 14:45:15 +000019#include <memory>
Harry Cutts207674d2024-06-06 18:53:41 +000020#include <optional>
Harry Cuttsccb75e82023-06-23 14:08:06 +000021
22#include <EventHub.h>
Michael Ensingb8d93262020-05-12 00:41:30 -070023#include <InputDevice.h>
24#include <InputMapper.h>
25#include <InputReader.h>
Aditya Wazireea5be02022-10-31 12:40:10 +053026#include <ThreadSafeFuzzedDataProvider.h>
Michael Ensingb8d93262020-05-12 00:41:30 -070027
28constexpr size_t kValidTypes[] = {EV_SW,
29 EV_SYN,
Michael Ensingb8d93262020-05-12 00:41:30 -070030 EV_ABS,
31 EV_KEY,
32 EV_MSC,
33 EV_REL,
34 android::EventHubInterface::DEVICE_ADDED,
35 android::EventHubInterface::DEVICE_REMOVED,
36 android::EventHubInterface::FINISHED_DEVICE_SCAN};
37
38constexpr size_t kValidCodes[] = {
39 SYN_REPORT,
40 ABS_MT_SLOT,
41 SYN_MT_REPORT,
42 ABS_MT_POSITION_X,
43 ABS_MT_POSITION_Y,
44 ABS_MT_TOUCH_MAJOR,
45 ABS_MT_TOUCH_MINOR,
46 ABS_MT_WIDTH_MAJOR,
47 ABS_MT_WIDTH_MINOR,
48 ABS_MT_ORIENTATION,
49 ABS_MT_TRACKING_ID,
50 ABS_MT_PRESSURE,
51 ABS_MT_DISTANCE,
52 ABS_MT_TOOL_TYPE,
Michael Ensingb8d93262020-05-12 00:41:30 -070053 MSC_SCAN,
54 REL_X,
55 REL_Y,
56 REL_WHEEL,
57 REL_HWHEEL,
58 BTN_LEFT,
59 BTN_RIGHT,
60 BTN_MIDDLE,
61 BTN_BACK,
62 BTN_SIDE,
63 BTN_FORWARD,
64 BTN_EXTRA,
65 BTN_TASK,
66};
67
Michael Ensingb8d93262020-05-12 00:41:30 -070068constexpr size_t kMaxSize = 256;
69
70namespace android {
71
Siarhei Vishniakou6d73f832022-07-21 17:27:03 -070072template<class Fdp>
73ToolType getFuzzedToolType(Fdp& fdp) {
74 const int32_t toolType = fdp.template ConsumeIntegralInRange<int32_t>(
75 static_cast<int32_t>(ToolType::ftl_first),
76 static_cast<int32_t>(ToolType::ftl_last));
77 return static_cast<ToolType>(toolType);
78}
79
Harry Cutts656e0ad2023-06-16 16:39:55 +000080template <class Fdp>
81RawEvent getFuzzedRawEvent(Fdp& fdp) {
82 const int32_t type = fdp.ConsumeBool() ? fdp.PickValueInArray(kValidTypes)
83 : fdp.template ConsumeIntegral<int32_t>();
84 const int32_t code = fdp.ConsumeBool() ? fdp.PickValueInArray(kValidCodes)
85 : fdp.template ConsumeIntegral<int32_t>();
86 return RawEvent{
87 .when = fdp.template ConsumeIntegral<nsecs_t>(),
88 .readTime = fdp.template ConsumeIntegral<nsecs_t>(),
89 .deviceId = fdp.template ConsumeIntegral<int32_t>(),
90 .type = type,
91 .code = code,
92 .value = fdp.template ConsumeIntegral<int32_t>(),
93 };
94}
95
Michael Ensingb8d93262020-05-12 00:41:30 -070096class FuzzEventHub : public EventHubInterface {
97 InputDeviceIdentifier mIdentifier;
98 std::vector<TouchVideoFrame> mVideoFrames;
99 PropertyMap mFuzzConfig;
Harry Cuttsccb75e82023-06-23 14:08:06 +0000100 std::map<int32_t /* deviceId */, std::map<int /* axis */, RawAbsoluteAxisInfo>> mAxes;
Aditya Wazireea5be02022-10-31 12:40:10 +0530101 std::shared_ptr<ThreadSafeFuzzedDataProvider> mFdp;
Michael Ensingb8d93262020-05-12 00:41:30 -0700102
103public:
Aditya Wazireea5be02022-10-31 12:40:10 +0530104 FuzzEventHub(std::shared_ptr<ThreadSafeFuzzedDataProvider> fdp) : mFdp(std::move(fdp)) {}
Michael Ensingb8d93262020-05-12 00:41:30 -0700105 ~FuzzEventHub() {}
106 void addProperty(std::string key, std::string value) { mFuzzConfig.addProperty(key, value); }
Michael Ensingb8d93262020-05-12 00:41:30 -0700107
108 ftl::Flags<InputDeviceClass> getDeviceClasses(int32_t deviceId) const override {
109 return ftl::Flags<InputDeviceClass>(mFdp->ConsumeIntegral<uint32_t>());
110 }
111 InputDeviceIdentifier getDeviceIdentifier(int32_t deviceId) const override {
112 return mIdentifier;
113 }
114 int32_t getDeviceControllerNumber(int32_t deviceId) const override {
115 return mFdp->ConsumeIntegral<int32_t>();
116 }
Harry Cuttsc34f7582023-03-07 16:23:30 +0000117 std::optional<PropertyMap> getConfiguration(int32_t deviceId) const override {
118 return mFuzzConfig;
Michael Ensingb8d93262020-05-12 00:41:30 -0700119 }
Harry Cuttsccb75e82023-06-23 14:08:06 +0000120 void setAbsoluteAxisInfo(int32_t deviceId, int axis, const RawAbsoluteAxisInfo& axisInfo) {
121 mAxes[deviceId][axis] = axisInfo;
122 }
Harry Cutts207674d2024-06-06 18:53:41 +0000123 std::optional<RawAbsoluteAxisInfo> getAbsoluteAxisInfo(int32_t deviceId,
124 int axis) const override {
Harry Cuttsccb75e82023-06-23 14:08:06 +0000125 if (auto deviceAxesIt = mAxes.find(deviceId); deviceAxesIt != mAxes.end()) {
126 const std::map<int, RawAbsoluteAxisInfo>& deviceAxes = deviceAxesIt->second;
127 if (auto axisInfoIt = deviceAxes.find(axis); axisInfoIt != deviceAxes.end()) {
Harry Cutts207674d2024-06-06 18:53:41 +0000128 return axisInfoIt->second;
Harry Cuttsccb75e82023-06-23 14:08:06 +0000129 }
130 }
Harry Cutts207674d2024-06-06 18:53:41 +0000131 if (mFdp->ConsumeBool()) {
132 return std::optional<RawAbsoluteAxisInfo>({
Harry Cutts207674d2024-06-06 18:53:41 +0000133 .minValue = mFdp->ConsumeIntegral<int32_t>(),
134 .maxValue = mFdp->ConsumeIntegral<int32_t>(),
135 .flat = mFdp->ConsumeIntegral<int32_t>(),
136 .fuzz = mFdp->ConsumeIntegral<int32_t>(),
137 .resolution = mFdp->ConsumeIntegral<int32_t>(),
138 });
139 } else {
140 return std::nullopt;
141 }
Michael Ensingb8d93262020-05-12 00:41:30 -0700142 }
143 bool hasRelativeAxis(int32_t deviceId, int axis) const override { return mFdp->ConsumeBool(); }
144 bool hasInputProperty(int32_t deviceId, int property) const override {
145 return mFdp->ConsumeBool();
146 }
147 bool hasMscEvent(int32_t deviceId, int mscEvent) const override { return mFdp->ConsumeBool(); }
148 status_t mapKey(int32_t deviceId, int32_t scanCode, int32_t usageCode, int32_t metaState,
149 int32_t* outKeycode, int32_t* outMetaState, uint32_t* outFlags) const override {
150 return mFdp->ConsumeIntegral<status_t>();
151 }
152 status_t mapAxis(int32_t deviceId, int32_t scanCode, AxisInfo* outAxisInfo) const override {
153 return mFdp->ConsumeIntegral<status_t>();
154 }
155 void setExcludedDevices(const std::vector<std::string>& devices) override {}
Siarhei Vishniakou7b3ea0b2022-09-16 14:23:20 -0700156 std::vector<RawEvent> getEvents(int timeoutMillis) override {
157 std::vector<RawEvent> events;
158 const size_t count = mFdp->ConsumeIntegralInRange<size_t>(0, kMaxSize);
159 for (size_t i = 0; i < count; ++i) {
Harry Cutts656e0ad2023-06-16 16:39:55 +0000160 events.push_back(getFuzzedRawEvent(*mFdp));
Siarhei Vishniakou7b3ea0b2022-09-16 14:23:20 -0700161 }
162 return events;
Michael Ensingb8d93262020-05-12 00:41:30 -0700163 }
164 std::vector<TouchVideoFrame> getVideoFrames(int32_t deviceId) override { return mVideoFrames; }
165
166 base::Result<std::pair<InputDeviceSensorType, int32_t>> mapSensor(
167 int32_t deviceId, int32_t absCode) const override {
168 return base::ResultError("Fuzzer", UNKNOWN_ERROR);
169 };
170 // Raw batteries are sysfs power_supply nodes we found from the EventHub device sysfs node,
171 // containing the raw info of the sysfs node structure.
172 std::vector<int32_t> getRawBatteryIds(int32_t deviceId) const override { return {}; }
173 std::optional<RawBatteryInfo> getRawBatteryInfo(int32_t deviceId,
174 int32_t BatteryId) const override {
175 return std::nullopt;
176 };
177
178 std::vector<int32_t> getRawLightIds(int32_t deviceId) const override { return {}; };
179 std::optional<RawLightInfo> getRawLightInfo(int32_t deviceId, int32_t lightId) const override {
180 return std::nullopt;
181 };
182 std::optional<int32_t> getLightBrightness(int32_t deviceId, int32_t lightId) const override {
183 return std::nullopt;
184 };
185 void setLightBrightness(int32_t deviceId, int32_t lightId, int32_t brightness) override{};
186 std::optional<std::unordered_map<LightColor, int32_t>> getLightIntensities(
187 int32_t deviceId, int32_t lightId) const override {
188 return std::nullopt;
189 };
190 void setLightIntensities(int32_t deviceId, int32_t lightId,
191 std::unordered_map<LightColor, int32_t> intensities) override{};
192
Vaibhav Devmurari7fb41132023-01-02 13:30:26 +0000193 std::optional<RawLayoutInfo> getRawLayoutInfo(int32_t deviceId) const override {
194 return std::nullopt;
Michael Ensingb8d93262020-05-12 00:41:30 -0700195 };
196
197 int32_t getScanCodeState(int32_t deviceId, int32_t scanCode) const override {
198 return mFdp->ConsumeIntegral<int32_t>();
199 }
200 int32_t getKeyCodeState(int32_t deviceId, int32_t keyCode) const override {
201 return mFdp->ConsumeIntegral<int32_t>();
202 }
203 int32_t getSwitchState(int32_t deviceId, int32_t sw) const override {
204 return mFdp->ConsumeIntegral<int32_t>();
205 }
Vaibhav Devmuraricbba14c2022-10-10 16:54:49 +0000206 void addKeyRemapping(int32_t deviceId, int32_t fromKeyCode, int32_t toKeyCode) const override {}
Michael Ensingb8d93262020-05-12 00:41:30 -0700207 int32_t getKeyCodeForKeyLocation(int32_t deviceId, int32_t locationKeyCode) const override {
208 return mFdp->ConsumeIntegral<int32_t>();
209 }
Harry Cuttse2c5e202024-06-21 17:08:48 +0000210 std::optional<int32_t> getAbsoluteAxisValue(int32_t deviceId, int32_t axis) const override {
211 if (mFdp->ConsumeBool()) {
212 return mFdp->ConsumeIntegral<int32_t>();
213 } else {
214 return std::nullopt;
215 }
Michael Ensingb8d93262020-05-12 00:41:30 -0700216 }
Arpit Singh4b4a4572023-11-24 18:19:56 +0000217 base::Result<std::vector<int32_t>> getMtSlotValues(int32_t deviceId, int32_t axis,
218 size_t slotCount) const override {
219 if (mFdp->ConsumeBool()) {
220 std::vector<int32_t> outValues(slotCount + 1);
221 for (size_t i = 0; i < outValues.size(); i++) {
222 outValues.push_back(mFdp->ConsumeIntegral<int32_t>());
223 }
224 return std::move(outValues);
225 } else {
226 return base::ResultError("Fuzzer", UNKNOWN_ERROR);
227 }
228 }
Michael Ensingb8d93262020-05-12 00:41:30 -0700229 bool markSupportedKeyCodes(int32_t deviceId, const std::vector<int32_t>& keyCodes,
230 uint8_t* outFlags) const override {
231 return mFdp->ConsumeBool();
232 }
233 bool hasScanCode(int32_t deviceId, int32_t scanCode) const override {
234 return mFdp->ConsumeBool();
235 }
236 bool hasKeyCode(int32_t deviceId, int32_t keyCode) const override {
237 return mFdp->ConsumeBool();
238 }
239 bool hasLed(int32_t deviceId, int32_t led) const override { return mFdp->ConsumeBool(); }
240 void setLedState(int32_t deviceId, int32_t led, bool on) override {}
241 void getVirtualKeyDefinitions(
242 int32_t deviceId, std::vector<VirtualKeyDefinition>& outVirtualKeys) const override {}
243 const std::shared_ptr<KeyCharacterMap> getKeyCharacterMap(int32_t deviceId) const override {
244 return nullptr;
245 }
246 bool setKeyboardLayoutOverlay(int32_t deviceId, std::shared_ptr<KeyCharacterMap> map) override {
247 return mFdp->ConsumeBool();
248 }
249 void vibrate(int32_t deviceId, const VibrationElement& effect) override {}
250 void cancelVibrate(int32_t deviceId) override {}
251
252 std::vector<int32_t> getVibratorIds(int32_t deviceId) const override { return {}; };
253
254 /* Query battery level. */
255 std::optional<int32_t> getBatteryCapacity(int32_t deviceId, int32_t batteryId) const override {
256 return std::nullopt;
257 };
258
259 /* Query battery status. */
260 std::optional<int32_t> getBatteryStatus(int32_t deviceId, int32_t batteryId) const override {
261 return std::nullopt;
262 };
263
264 void requestReopenDevices() override {}
265 void wake() override {}
266 void dump(std::string& dump) const override {}
267 void monitor() const override {}
268 bool isDeviceEnabled(int32_t deviceId) const override { return mFdp->ConsumeBool(); }
269 status_t enableDevice(int32_t deviceId) override { return mFdp->ConsumeIntegral<status_t>(); }
270 status_t disableDevice(int32_t deviceId) override { return mFdp->ConsumeIntegral<status_t>(); }
Vaibhav Devmurari5fc7d852023-03-17 18:43:33 +0000271 void sysfsNodeChanged(const std::string& sysfsNodePath) override {}
Michael Ensingb8d93262020-05-12 00:41:30 -0700272};
273
Michael Ensingb8d93262020-05-12 00:41:30 -0700274class FuzzInputReaderPolicy : public InputReaderPolicyInterface {
275 TouchAffineTransformation mTransform;
Aditya Wazireea5be02022-10-31 12:40:10 +0530276 std::shared_ptr<ThreadSafeFuzzedDataProvider> mFdp;
Michael Ensingb8d93262020-05-12 00:41:30 -0700277
278protected:
279 ~FuzzInputReaderPolicy() {}
280
281public:
Prabir Pradhan2120b9e2024-05-04 00:06:37 +0000282 FuzzInputReaderPolicy(std::shared_ptr<ThreadSafeFuzzedDataProvider> mFdp) : mFdp(mFdp) {}
Michael Ensingb8d93262020-05-12 00:41:30 -0700283 void getReaderConfiguration(InputReaderConfiguration* outConfig) override {}
Michael Ensingb8d93262020-05-12 00:41:30 -0700284 void notifyInputDevicesChanged(const std::vector<InputDeviceInfo>& inputDevices) override {}
285 std::shared_ptr<KeyCharacterMap> getKeyboardLayoutOverlay(
Vaibhav Devmuraridec30802023-07-11 15:02:03 +0000286 const InputDeviceIdentifier& identifier,
287 const std::optional<KeyboardLayoutInfo> layoutInfo) override {
Michael Ensingb8d93262020-05-12 00:41:30 -0700288 return nullptr;
289 }
290 std::string getDeviceAlias(const InputDeviceIdentifier& identifier) {
291 return mFdp->ConsumeRandomLengthString(32);
292 }
293 TouchAffineTransformation getTouchAffineTransformation(const std::string& inputDeviceDescriptor,
Michael Wrighta9cf4192022-12-01 23:46:39 +0000294 ui::Rotation surfaceRotation) override {
Michael Ensingb8d93262020-05-12 00:41:30 -0700295 return mTransform;
296 }
297 void setTouchAffineTransformation(const TouchAffineTransformation t) { mTransform = t; }
Prabir Pradhanda20b172022-09-26 17:01:18 +0000298 void notifyStylusGestureStarted(int32_t, nsecs_t) {}
Arpit Singhb3b3f732023-07-04 14:30:05 +0000299 bool isInputMethodConnectionActive() override { return mFdp->ConsumeBool(); }
Prabir Pradhan19767602023-11-03 16:53:31 +0000300 std::optional<DisplayViewport> getPointerViewportForAssociatedDisplay(
Linnan Li13bf76a2024-05-05 19:18:02 +0800301 ui::LogicalDisplayId associatedDisplayId) override {
Byoungho Jungda10dd32023-10-06 17:03:45 +0900302 return {};
303 }
Michael Ensingb8d93262020-05-12 00:41:30 -0700304};
305
306class FuzzInputListener : public virtual InputListenerInterface {
307public:
Prabir Pradhane3da4bb2023-04-05 23:51:23 +0000308 void notifyInputDevicesChanged(const NotifyInputDevicesChangedArgs& args) override {}
Prabir Pradhanc392d8f2023-04-13 19:32:51 +0000309 void notifyConfigurationChanged(const NotifyConfigurationChangedArgs& args) override {}
310 void notifyKey(const NotifyKeyArgs& args) override {}
311 void notifyMotion(const NotifyMotionArgs& args) override {}
312 void notifySwitch(const NotifySwitchArgs& args) override {}
313 void notifySensor(const NotifySensorArgs& args) override{};
314 void notifyVibratorState(const NotifyVibratorStateArgs& args) override{};
315 void notifyDeviceReset(const NotifyDeviceResetArgs& args) override {}
316 void notifyPointerCaptureChanged(const NotifyPointerCaptureChangedArgs& args) override{};
Michael Ensingb8d93262020-05-12 00:41:30 -0700317};
318
319class FuzzInputReaderContext : public InputReaderContext {
320 std::shared_ptr<EventHubInterface> mEventHub;
321 sp<InputReaderPolicyInterface> mPolicy;
Aditya Wazireea5be02022-10-31 12:40:10 +0530322 std::shared_ptr<ThreadSafeFuzzedDataProvider> mFdp;
Michael Ensingb8d93262020-05-12 00:41:30 -0700323
324public:
325 FuzzInputReaderContext(std::shared_ptr<EventHubInterface> eventHub,
Harry Cuttsf61c0472023-07-10 14:45:15 +0000326 std::shared_ptr<ThreadSafeFuzzedDataProvider> fdp)
327 : mEventHub(eventHub), mPolicy(sp<FuzzInputReaderPolicy>::make(fdp)), mFdp(fdp) {}
Michael Ensingb8d93262020-05-12 00:41:30 -0700328 ~FuzzInputReaderContext() {}
329 void updateGlobalMetaState() override {}
330 int32_t getGlobalMetaState() { return mFdp->ConsumeIntegral<int32_t>(); }
331 void disableVirtualKeysUntil(nsecs_t time) override {}
332 bool shouldDropVirtualKey(nsecs_t now, int32_t keyCode, int32_t scanCode) override {
333 return mFdp->ConsumeBool();
334 }
Michael Ensingb8d93262020-05-12 00:41:30 -0700335 void requestTimeoutAtTime(nsecs_t when) override {}
336 int32_t bumpGeneration() override { return mFdp->ConsumeIntegral<int32_t>(); }
337 void getExternalStylusDevices(std::vector<InputDeviceInfo>& outDevices) override {}
Siarhei Vishniakou2935db72022-09-22 13:35:22 -0700338 std::list<NotifyArgs> dispatchExternalStylusState(const StylusState& outState) override {
339 return {};
340 }
Michael Ensingb8d93262020-05-12 00:41:30 -0700341 InputReaderPolicyInterface* getPolicy() override { return mPolicy.get(); }
Michael Ensingb8d93262020-05-12 00:41:30 -0700342 EventHubInterface* getEventHub() override { return mEventHub.get(); }
343 int32_t getNextId() override { return mFdp->ConsumeIntegral<int32_t>(); }
344
345 void updateLedMetaState(int32_t metaState) override{};
346 int32_t getLedMetaState() override { return mFdp->ConsumeIntegral<int32_t>(); };
Prabir Pradhanda20b172022-09-26 17:01:18 +0000347 void notifyStylusGestureStarted(int32_t, nsecs_t) {}
Arpit Singha5ea7c12023-07-05 15:39:25 +0000348
349 void setPreventingTouchpadTaps(bool prevent) {}
350 bool isPreventingTouchpadTaps() { return mFdp->ConsumeBool(); };
Arpit Singh82e413e2023-10-10 19:30:58 +0000351
352 void setLastKeyDownTimestamp(nsecs_t when) { mLastKeyDownTimestamp = when; };
353 nsecs_t getLastKeyDownTimestamp() { return mLastKeyDownTimestamp; };
Vaibhav Devmurarie58ffb92024-05-22 17:38:25 +0000354 KeyboardClassifier& getKeyboardClassifier() override { return *mClassifier; }
Arpit Singh82e413e2023-10-10 19:30:58 +0000355
356private:
357 nsecs_t mLastKeyDownTimestamp;
Vaibhav Devmurarie58ffb92024-05-22 17:38:25 +0000358 std::unique_ptr<KeyboardClassifier> mClassifier = std::make_unique<KeyboardClassifier>();
Michael Ensingb8d93262020-05-12 00:41:30 -0700359};
360
Harry Cuttsf61c0472023-07-10 14:45:15 +0000361template <class Fdp>
362InputDevice getFuzzedInputDevice(Fdp& fdp, FuzzInputReaderContext* context) {
363 InputDeviceIdentifier identifier;
364 identifier.name = fdp.ConsumeRandomLengthString(16);
365 identifier.location = fdp.ConsumeRandomLengthString(12);
366 int32_t deviceID = fdp.ConsumeIntegralInRange(0, 5);
367 int32_t deviceGeneration = fdp.ConsumeIntegralInRange(0, 5);
368 return InputDevice(context, deviceID, deviceGeneration, identifier);
369}
370
371template <class Fdp>
372void configureAndResetDevice(Fdp& fdp, InputDevice& device) {
373 nsecs_t arbitraryTime = fdp.template ConsumeIntegral<nsecs_t>();
374 std::list<NotifyArgs> out;
375 out += device.configure(arbitraryTime, /*readerConfig=*/{}, /*changes=*/{});
376 out += device.reset(arbitraryTime);
377}
378
379template <class Fdp, class T, typename... Args>
380T& getMapperForDevice(Fdp& fdp, InputDevice& device, Args... args) {
381 int32_t eventhubId = fdp.template ConsumeIntegral<int32_t>();
382 // ensure a device entry exists for this eventHubId
383 device.addEmptyEventHubDevice(eventhubId);
384 configureAndResetDevice(fdp, device);
385
386 return device.template constructAndAddMapper<T>(eventhubId, args...);
387}
388
Michael Ensingb8d93262020-05-12 00:41:30 -0700389} // namespace android