blob: c58ae23cc56d82af295fd23ec0f4e320a089079e [file] [log] [blame]
Garfield Tane84e6f92019-08-29 17:28:41 -07001/*
2 * Copyright (C) 2019 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 */
16
17#ifndef _UI_INPUT_INPUTDISPATCHER_ENTRY_H
18#define _UI_INPUT_INPUTDISPATCHER_ENTRY_H
19
20#include "InjectionState.h"
21#include "InputTarget.h"
22
23#include <input/Input.h>
24#include <input/InputApplication.h>
25#include <stdint.h>
26#include <utils/Timers.h>
27#include <functional>
28#include <string>
29
30namespace android::inputdispatcher {
31
Siarhei Vishniakoude4bf152019-08-16 11:12:52 -050032// Sequence number for synthesized or injected events.
Garfield Tan6a5a14e2020-01-28 13:24:04 -080033constexpr int32_t SYNTHESIZED_EVENT_ID = 0;
Siarhei Vishniakoude4bf152019-08-16 11:12:52 -050034
Garfield Tane84e6f92019-08-29 17:28:41 -070035struct EventEntry {
Siarhei Vishniakouf1035d42019-09-20 16:32:01 +010036 enum class Type {
37 CONFIGURATION_CHANGED,
38 DEVICE_RESET,
39 FOCUS,
40 KEY,
41 MOTION,
42 };
Siarhei Vishniakou49483272019-10-22 13:13:47 -070043
44 static const char* typeToString(Type type) {
45 switch (type) {
46 case Type::CONFIGURATION_CHANGED:
47 return "CONFIGURATION_CHANGED";
48 case Type::DEVICE_RESET:
49 return "DEVICE_RESET";
Siarhei Vishniakouf1035d42019-09-20 16:32:01 +010050 case Type::FOCUS:
51 return "FOCUS";
Siarhei Vishniakou49483272019-10-22 13:13:47 -070052 case Type::KEY:
53 return "KEY";
54 case Type::MOTION:
55 return "MOTION";
56 }
57 }
Garfield Tane84e6f92019-08-29 17:28:41 -070058
Garfield Tan6a5a14e2020-01-28 13:24:04 -080059 int32_t id;
Garfield Tane84e6f92019-08-29 17:28:41 -070060 mutable int32_t refCount;
Siarhei Vishniakou49483272019-10-22 13:13:47 -070061 Type type;
Garfield Tane84e6f92019-08-29 17:28:41 -070062 nsecs_t eventTime;
63 uint32_t policyFlags;
64 InjectionState* injectionState;
65
66 bool dispatchInProgress; // initially false, set to true while dispatching
67
Siarhei Vishniakoude4bf152019-08-16 11:12:52 -050068 /**
69 * Injected keys are events from an external (probably untrusted) application
70 * and are not related to real hardware state. They come in via
71 * InputDispatcher::injectInputEvent, which sets policy flag POLICY_FLAG_INJECTED.
72 */
Garfield Tane84e6f92019-08-29 17:28:41 -070073 inline bool isInjected() const { return injectionState != nullptr; }
74
Siarhei Vishniakoude4bf152019-08-16 11:12:52 -050075 /**
76 * Synthesized events are either injected events, or events that come
77 * from real hardware, but aren't directly attributable to a specific hardware event.
78 * Key repeat is a synthesized event, because it is related to an actual hardware state
79 * (a key is currently pressed), but the repeat itself is generated by the framework.
80 */
Garfield Tan6a5a14e2020-01-28 13:24:04 -080081 inline bool isSynthesized() const { return isInjected() || id == SYNTHESIZED_EVENT_ID; }
Siarhei Vishniakoude4bf152019-08-16 11:12:52 -050082
Garfield Tane84e6f92019-08-29 17:28:41 -070083 void release();
84
85 virtual void appendDescription(std::string& msg) const = 0;
86
87protected:
Garfield Tan6a5a14e2020-01-28 13:24:04 -080088 EventEntry(int32_t id, Type type, nsecs_t eventTime, uint32_t policyFlags);
Garfield Tane84e6f92019-08-29 17:28:41 -070089 virtual ~EventEntry();
90 void releaseInjectionState();
91};
92
93struct ConfigurationChangedEntry : EventEntry {
Garfield Tan6a5a14e2020-01-28 13:24:04 -080094 explicit ConfigurationChangedEntry(int32_t id, nsecs_t eventTime);
Garfield Tane84e6f92019-08-29 17:28:41 -070095 virtual void appendDescription(std::string& msg) const;
96
97protected:
98 virtual ~ConfigurationChangedEntry();
99};
100
101struct DeviceResetEntry : EventEntry {
102 int32_t deviceId;
103
Garfield Tan6a5a14e2020-01-28 13:24:04 -0800104 DeviceResetEntry(int32_t id, nsecs_t eventTime, int32_t deviceId);
Garfield Tane84e6f92019-08-29 17:28:41 -0700105 virtual void appendDescription(std::string& msg) const;
106
107protected:
108 virtual ~DeviceResetEntry();
109};
110
Siarhei Vishniakouf1035d42019-09-20 16:32:01 +0100111struct FocusEntry : EventEntry {
112 sp<IBinder> connectionToken;
113 bool hasFocus;
114
Garfield Tan6a5a14e2020-01-28 13:24:04 -0800115 FocusEntry(int32_t id, nsecs_t eventTime, sp<IBinder> connectionToken, bool hasFocus);
Siarhei Vishniakouf1035d42019-09-20 16:32:01 +0100116 virtual void appendDescription(std::string& msg) const;
117
118protected:
119 virtual ~FocusEntry();
120};
121
Garfield Tane84e6f92019-08-29 17:28:41 -0700122struct KeyEntry : EventEntry {
123 int32_t deviceId;
124 uint32_t source;
125 int32_t displayId;
126 int32_t action;
127 int32_t flags;
128 int32_t keyCode;
129 int32_t scanCode;
130 int32_t metaState;
131 int32_t repeatCount;
132 nsecs_t downTime;
133
134 bool syntheticRepeat; // set to true for synthetic key repeats
135
136 enum InterceptKeyResult {
137 INTERCEPT_KEY_RESULT_UNKNOWN,
138 INTERCEPT_KEY_RESULT_SKIP,
139 INTERCEPT_KEY_RESULT_CONTINUE,
140 INTERCEPT_KEY_RESULT_TRY_AGAIN_LATER,
141 };
142 InterceptKeyResult interceptKeyResult; // set based on the interception result
143 nsecs_t interceptKeyWakeupTime; // used with INTERCEPT_KEY_RESULT_TRY_AGAIN_LATER
144
Garfield Tan6a5a14e2020-01-28 13:24:04 -0800145 KeyEntry(int32_t id, nsecs_t eventTime, int32_t deviceId, uint32_t source, int32_t displayId,
146 uint32_t policyFlags, int32_t action, int32_t flags, int32_t keyCode, int32_t scanCode,
147 int32_t metaState, int32_t repeatCount, nsecs_t downTime);
Garfield Tane84e6f92019-08-29 17:28:41 -0700148 virtual void appendDescription(std::string& msg) const;
149 void recycle();
150
151protected:
152 virtual ~KeyEntry();
153};
154
155struct MotionEntry : EventEntry {
156 nsecs_t eventTime;
157 int32_t deviceId;
158 uint32_t source;
159 int32_t displayId;
160 int32_t action;
161 int32_t actionButton;
162 int32_t flags;
163 int32_t metaState;
164 int32_t buttonState;
165 MotionClassification classification;
166 int32_t edgeFlags;
167 float xPrecision;
168 float yPrecision;
169 float xCursorPosition;
170 float yCursorPosition;
171 nsecs_t downTime;
172 uint32_t pointerCount;
173 PointerProperties pointerProperties[MAX_POINTERS];
174 PointerCoords pointerCoords[MAX_POINTERS];
175
Garfield Tan6a5a14e2020-01-28 13:24:04 -0800176 MotionEntry(int32_t id, nsecs_t eventTime, int32_t deviceId, uint32_t source, int32_t displayId,
177 uint32_t policyFlags, int32_t action, int32_t actionButton, int32_t flags,
178 int32_t metaState, int32_t buttonState, MotionClassification classification,
179 int32_t edgeFlags, float xPrecision, float yPrecision, float xCursorPosition,
180 float yCursorPosition, nsecs_t downTime, uint32_t pointerCount,
181 const PointerProperties* pointerProperties, const PointerCoords* pointerCoords,
182 float xOffset, float yOffset);
Garfield Tane84e6f92019-08-29 17:28:41 -0700183 virtual void appendDescription(std::string& msg) const;
184
185protected:
186 virtual ~MotionEntry();
187};
188
189// Tracks the progress of dispatching a particular event to a particular connection.
190struct DispatchEntry {
191 const uint32_t seq; // unique sequence number, never 0
192
193 EventEntry* eventEntry; // the event to dispatch
194 int32_t targetFlags;
195 float xOffset;
196 float yOffset;
197 float globalScaleFactor;
198 float windowXScale = 1.0f;
199 float windowYScale = 1.0f;
200 nsecs_t deliveryTime; // time when the event was actually delivered
201
202 // Set to the resolved action and flags when the event is enqueued.
203 int32_t resolvedAction;
204 int32_t resolvedFlags;
205
206 DispatchEntry(EventEntry* eventEntry, int32_t targetFlags, float xOffset, float yOffset,
207 float globalScaleFactor, float windowXScale, float windowYScale);
208 ~DispatchEntry();
209
210 inline bool hasForegroundTarget() const { return targetFlags & InputTarget::FLAG_FOREGROUND; }
211
212 inline bool isSplit() const { return targetFlags & InputTarget::FLAG_SPLIT; }
213
214private:
215 static volatile int32_t sNextSeqAtomic;
216
217 static uint32_t nextSeq();
218};
219
Gang Wange9087892020-01-07 12:17:14 -0500220VerifiedKeyEvent verifiedKeyEventFromKeyEntry(const KeyEntry& entry);
221VerifiedMotionEvent verifiedMotionEventFromMotionEntry(const MotionEntry& entry);
222
Garfield Tane84e6f92019-08-29 17:28:41 -0700223class InputDispatcher;
224// A command entry captures state and behavior for an action to be performed in the
225// dispatch loop after the initial processing has taken place. It is essentially
226// a kind of continuation used to postpone sensitive policy interactions to a point
227// in the dispatch loop where it is safe to release the lock (generally after finishing
228// the critical parts of the dispatch cycle).
229//
230// The special thing about commands is that they can voluntarily release and reacquire
231// the dispatcher lock at will. Initially when the command starts running, the
232// dispatcher lock is held. However, if the command needs to call into the policy to
233// do some work, it can release the lock, do the work, then reacquire the lock again
234// before returning.
235//
236// This mechanism is a bit clunky but it helps to preserve the invariant that the dispatch
237// never calls into the policy while holding its lock.
238//
239// Commands are implicitly 'LockedInterruptible'.
240struct CommandEntry;
241typedef std::function<void(InputDispatcher&, CommandEntry*)> Command;
242
243class Connection;
244struct CommandEntry {
245 explicit CommandEntry(Command command);
246 ~CommandEntry();
247
248 Command command;
249
250 // parameters for the command (usage varies by command)
251 sp<Connection> connection;
252 nsecs_t eventTime;
253 KeyEntry* keyEntry;
254 sp<InputApplicationHandle> inputApplicationHandle;
255 std::string reason;
256 int32_t userActivityEventType;
257 uint32_t seq;
258 bool handled;
259 sp<InputChannel> inputChannel;
260 sp<IBinder> oldToken;
261 sp<IBinder> newToken;
262};
263
264} // namespace android::inputdispatcher
265
266#endif // _UI_INPUT_INPUTDISPATCHER_ENTRY_H