InputManagerService由SystemServer启动,整体流程如下:
代码如下:
//frameworks/base/core/java/com/android/server/SystemServer.java
public final class SystemServer implements Dumpable {
private void startOtherServices() {
........
//调用构造函数
inputManager = new InputManagerService(context);
......
//将InputManagerService添加到servicemanager中
ServiceManager.addService(Context.INPUT_SERVICE, inputManager,
/* allowIsolated= */ false, DUMP_FLAG_PRIORITY_CRITICAL);
......
//将InputMonitor注册到IMS中,用于对事件筛选和派发的处理
inputManager.setWindowManagerCallbacks(wm.getInputMonitor());
......
//调用到Native层,启动InputReader和InputDispatcher的线程循环
inputManager.start();
......
}
}
上面方法主要处理如下:
1、通过new的方式创建InputManagerService对象。
2、调用inputManager的setWindowManagerCallbacks方法,将InputMonitor注册到IMS中,用于对事件筛选和派发的处理。
3、调用inputManager的start方法,启动InputReader和InputDispatcher的线程循环。
下面分别进行分析:
new InputManagerService
通过new的方式创建InputManagerService对象,InputManagerService构造方法如下:
//frameworks/base/service/core/java/android/server/input/InputManagerService.java
public class InputManagerService extends IInputManager.Stub implements Watchdog.Monitor {
InputManagerService(Injector injector) {
// The static association map is accessed by both java and native code, so it must be
// initialized before initializing the native service.
mStaticAssociations = loadStaticInputPortAssociations();
mContext = injector.getContext();
mHandler = new InputManagerHandler(injector.getLooper());
mNative = injector.getNativeService(this);
mUseDevInputEventForAudioJack =
mContext.getResources().getBoolean(R.bool.config_useDevInputEventForAudioJack);
Slog.i(TAG, "Initializing input manager, mUseDevInputEventForAudioJack="
+ mUseDevInputEventForAudioJack);
String doubleTouchGestureEnablePath = mContext.getResources().getString(
R.string.config_doubleTouchGestureEnableFile);
mDoubleTouchGestureEnableFile = TextUtils.isEmpty(doubleTouchGestureEnablePath) ? null :
new File(doubleTouchGestureEnablePath);
injector.registerLocalService(new LocalService());
}
}
调用Injector的getNativeService方法:
//frameworks/base/service/core/java/android/server/input/InputManagerService.java
public class InputManagerService extends IInputManager.Stub implements Watchdog.Monitor {
static class Injector {
NativeInputManagerService getNativeService(InputManagerService service) {
return new NativeInputManagerService.NativeImpl(service, mContext, mLooper.getQueue());
}
}
}
通过new的方式创建NativeInputManagerService.NativeImpl对象,NativeImpl的构造方法如下:
public interface NativeInputManagerService {
class NativeImpl implements NativeInputManagerService {
/** Pointer to native input manager service object, used by native code. */
@SuppressWarnings({"unused", "FieldCanBeLocal"})
private final long mPtr;
NativeImpl(InputManagerService service, Context context, MessageQueue messageQueue) {
mPtr = init(service, context, messageQueue);
}
private native long init(InputManagerService service, Context context,
MessageQueue messageQueue);
}
调用init方法,该方法是native方法,在中com_android_server_inputManagerService.cpp实现:
//frameworks/base/services/core/jni/com_android_server_inputManagerService.cpp
static jlong nativeInit(JNIEnv* env, jclass /* clazz */,
jobject serviceObj, jobject contextObj, jobject messageQueueObj) {
sp<MessageQueue> messageQueue = android_os_MessageQueue_getMessageQueue(env, messageQueueObj);
if (messageQueue == nullptr) {
jniThrowRuntimeException(env, "MessageQueue is not initialized.");
return 0;
}
NativeInputManager* im = new NativeInputManager(contextObj, serviceObj,
messageQueue->getLooper());
im->incStrong(0);
return reinterpret_cast<jlong>(im);
}
通过new的方式创建NativeInputManager对象,NativeInputManager的构造方法如下:
//frameworks/base/services/core/jni/com_android_server_inputManagerService.cpp
NativeInputManager::NativeInputManager(jobject contextObj,
jobject serviceObj, const sp<Looper>& looper) :
mLooper(looper), mInteractive(true) {
JNIEnv* env = jniEnv();
mServiceObj = env->NewGlobalRef(serviceObj);
{
AutoMutex _l(mLock);
mLocked.systemUiLightsOut = false;
mLocked.pointerSpeed = 0;
mLocked.pointerAcceleration = android::os::IInputConstants::DEFAULT_POINTER_ACCELERATION;
mLocked.pointerGesturesEnabled = true;
mLocked.showTouches = false;
mLocked.pointerDisplayId = ADISPLAY_ID_DEFAULT;
}
mInteractive = true;
InputManager* im = new InputManager(this, this);
mInputManager = im;
defaultServiceManager()->addService(String16("inputflinger"), im);
}
new InputManager
通过new的方式创建InputManager对象:
//frameworks/native/services/inputflinger/InputManager.cpp
InputManager::InputManager(
const sp<InputReaderPolicyInterface>& readerPolicy,
const sp<InputDispatcherPolicyInterface>& dispatcherPolicy) {
mDispatcher = createInputDispatcher(dispatcherPolicy);
mClassifier = std::make_unique<InputClassifier>(*mDispatcher);
mBlocker = std::make_unique<UnwantedInteractionBlocker>(*mClassifier);
mReader = createInputReader(readerPolicy, *mBlocker);
}
上面方法的主要处理如下:
1、调用createInputDispatcher方法,创建InputDispatcher对象。
2、调用createInputReader方法,创建InputReader对象。
下面分别进行分析:
createInputDispatcher
调用createInputDispatcher方法,创建InputDispatcher对象:
//frameworks/native/services/inputflinger/dispatcher/inputDispatcherFactory.cpp
std::unique_ptr<InputDispatcherInterface> createInputDispatcher(
const sp<InputDispatcherPolicyInterface>& policy) {
return std::make_unique<android::inputdispatcher::InputDispatcher>(policy);
}
InputDispatcher::InputDispatcher
创建InputDispatcher对象,InputDispatcher的构造方法如下:
//frameworks/native/services/inputflinger/dispatcher/InputDispatcher.cpp
InputDispatcher::InputDispatcher(const sp<InputDispatcherPolicyInterface>& policy,
std::chrono::nanoseconds staleEventTimeout)
: mPolicy(policy),
mPendingEvent(nullptr),
mLastDropReason(DropReason::NOT_DROPPED),
mIdGenerator(IdGenerator::Source::INPUT_DISPATCHER),
mAppSwitchSawKeyDown(false),
mAppSwitchDueTime(LONG_LONG_MAX),
mNextUnblockedEvent(nullptr),
mMonitorDispatchingTimeout(DEFAULT_INPUT_DISPATCHING_TIMEOUT),
mDispatchEnabled(false),
mDispatchFrozen(false),
mInputFilterEnabled(false),
// mInTouchMode will be initialized by the WindowManager to the default device config.
// To avoid leaking stack in case that call never comes, and for tests,
// initialize it here anyways.
mInTouchMode(kDefaultInTouchMode),
mMaximumObscuringOpacityForTouch(1.0f),
mFocusedDisplayId(ADISPLAY_ID_DEFAULT),
mWindowTokenWithPointerCapture(nullptr),
mStaleEventTimeout(staleEventTimeout),
mLatencyAggregator(),
mLatencyTracker(&mLatencyAggregator) {
mLooper = new Looper(false); //创建一个循环
mReporter = createInputReporter();
mWindowInfoListener = new DispatcherWindowListener(*this);
SurfaceComposerClient::getDefault()->addWindowInfosListener(mWindowInfoListener);
mKeyRepeatState.lastKeyEntry = nullptr;
policy->getDispatcherConfiguration(&mConfig);
}
createInputReader
调用createInputReader方法,创建InputReader对象:
//frameworks/native/services/inputflinger/reader/InputReaderFactory.cpp
std::unique_ptr<InputReaderInterface> createInputReader(
const sp<InputReaderPolicyInterface>& policy, InputListenerInterface& listener) {
return std::make_unique<InputReader>(std::make_unique<EventHub>(), policy, listener);
}
InputReader::InputReader
创建InputReader对象,InputReader的构造方法如下:
//frameworks/native/services/inputflinger/reader/InputReader.cpp
InputReader::InputReader(std::shared_ptr<EventHubInterface> eventHub,
const sp<InputReaderPolicyInterface>& policy,
InputListenerInterface& listener)
: mContext(this),
mEventHub(eventHub),
mPolicy(policy),
mQueuedListener(listener),
mGlobalMetaState(AMETA_NONE),
mLedMetaState(AMETA_NONE),
mGeneration(1),
mNextInputDeviceId(END_RESERVED_ID),
mDisableVirtualKeysTimeout(LLONG_MIN),
mNextTimeout(LLONG_MAX),
mConfigurationChangesToRefresh(0) {
refreshConfigurationLocked(0);
updateGlobalMetaStateLocked();
}
EventHub::EventHub
创建EventHub对象,EventHub的构造方法如下:
//frameworks/native/services/inputflinger/reader/EventHub.cpp
EventHub::EventHub(void)
: mBuiltInKeyboardId(NO_BUILT_IN_KEYBOARD),
mNextDeviceId(1),
mControllerNumbers(),
mNeedToSendFinishedDeviceScan(false),
mNeedToReopenDevices(false),
mNeedToScanDevices(true),
mPendingEventCount(0),
mPendingEventIndex(0),
mPendingINotify(false) {
ensureProcessCanBlockSuspend();
// 1.创建一个新的epoll实例
mEpollFd = epoll_create1(EPOLL_CLOEXEC);
LOG_ALWAYS_FATAL_IF(mEpollFd < 0, "Could not create epoll instance: %s", strerror(errno));
// 2.创建一个新的inotify实例,Inotify API用于检测文件系统变化的机制。Inotify可用于检测单个文件,也可以检测整个目录。
// 当目录下的设备节点发生增删事件时,可已通过 read(fd) 获取事件的详细信息
mINotifyFd = inotify_init1(IN_CLOEXEC);
std::error_code errorCode;
bool isDeviceInotifyAdded = false;
// 3.添加 /dev/input 或者 /dev 目录的Inotify
if (std::filesystem::exists(DEVICE_INPUT_PATH, errorCode)) {
addDeviceInputInotify();
} else {
addDeviceInotify();
isDeviceInotifyAdded = true;
if (errorCode) {
ALOGW("Could not run filesystem::exists() due to error %d : %s.", errorCode.value(),
errorCode.message().c_str());
}
}
if (isV4lScanningEnabled() && !isDeviceInotifyAdded) {
addDeviceInotify();
} else {
ALOGI("Video device scanning disabled");
}
struct epoll_event eventItem = {};
eventItem.events = EPOLLIN | EPOLLWAKEUP;
eventItem.data.fd = mINotifyFd;
// 4. 把 inotify 添加到 epoll 监听队列中,当 inotify 事件到来时,epoll_wait() 会立即返回,EventHub 可以从 fd 中读取设备节点的增删信息并进行处理
int result = epoll_ctl(mEpollFd, EPOLL_CTL_ADD, mINotifyFd, &eventItem);
LOG_ALWAYS_FATAL_IF(result != 0, "Could not add INotify to epoll instance. errno=%d", errno);
// 5. 创建管道,fds[0] 表示管道的读端,fds[1] 表示管道的写端
int wakeFds[2];
result = pipe2(wakeFds, O_CLOEXEC);
LOG_ALWAYS_FATAL_IF(result != 0, "Could not create wake pipe. errno=%d", errno);
mWakeReadPipeFd = wakeFds[0];
mWakeWritePipeFd = wakeFds[1];
result = fcntl(mWakeReadPipeFd, F_SETFL, O_NONBLOCK); // 设置唤醒读端为非阻塞式
LOG_ALWAYS_FATAL_IF(result != 0, "Could not make wake read pipe non-blocking. errno=%d",
errno);
result = fcntl(mWakeWritePipeFd, F_SETFL, O_NONBLOCK); // 设置唤醒写端为非阻塞式
LOG_ALWAYS_FATAL_IF(result != 0, "Could not make wake write pipe non-blocking. errno=%d",
errno);
//6. 把唤醒读端的 fd 添加到 epoll 监听队列中,目的是在必要时唤醒 reader 线程
eventItem.data.fd = mWakeReadPipeFd;
result = epoll_ctl(mEpollFd, EPOLL_CTL_ADD, mWakeReadPipeFd, &eventItem);
LOG_ALWAYS_FATAL_IF(result != 0, "Could not add wake read pipe to epoll instance. errno=%d",
errno);
}
inputManager setWindowManagerCallbacks
调用InputManagerService的setWindowManagerCallbacks方法,将InputMonitor注册到IMS中,用于对事件筛选和派发的处理:
//frameworks/base/service/core/java/android/server/input/InputManagerService.java
public class InputManagerService extends IInputManager.Stub implements Watchdog.Monitor {
public void setWindowManagerCallbacks(WindowManagerCallbacks callbacks) {
if (mWindowManagerCallbacks != null) {
unregisterLidSwitchCallbackInternal(mWindowManagerCallbacks);
}
mWindowManagerCallbacks = callbacks;
registerLidSwitchCallbackInternal(mWindowManagerCallbacks);
}
}
调用InputManagerService的registerLidSwitchCallbackInternal方法:
//frameworks/base/service/core/java/android/server/input/InputManagerService.java
public class InputManagerService extends IInputManager.Stub implements Watchdog.Monitor {
void registerLidSwitchCallbackInternal(@NonNull LidSwitchCallback callback) {
synchronized (mLidSwitchLock) {
mLidSwitchCallbacks.add(callback);
// Skip triggering the initial callback if the system is not yet ready as the switch
// state will be reported as KEY_STATE_UNKNOWN. The callback will be triggered in
// systemRunning().
if (mSystemReady) {
boolean lidOpen = getSwitchState(-1 /* deviceId */, InputDevice.SOURCE_ANY, SW_LID)
== KEY_STATE_UP;
callback.notifyLidSwitchChanged(0 /* whenNanos */, lidOpen);
}
}
}
}
InputManagerService start
调用InputManagerService 的start方法:
//frameworks/base/service/core/java/android/server/input/InputManagerService.java
public class InputManagerService extends IInputManager.Stub implements Watchdog.Monitor {
private final NativeInputManagerService mNative;
public void start() {
Slog.i(TAG, "Starting input manager");
mNative.start();
// Add ourselves to the Watchdog monitors.
Watchdog.getInstance().addMonitor(this);
registerPointerSpeedSettingObserver();
registerShowTouchesSettingObserver();
registerAccessibilityLargePointerSettingObserver();
registerLongPressTimeoutObserver();
registerMaximumObscuringOpacityForTouchSettingObserver();
registerBlockUntrustedTouchesModeSettingObserver();
mContext.registerReceiver(new BroadcastReceiver() {
@Override
public void onReceive(Context context, Intent intent) {
updatePointerSpeedFromSettings();
updateShowTouchesFromSettings();
updateAccessibilityLargePointerFromSettings();
updateDeepPressStatusFromSettings("user switched");
}
}, new IntentFilter(Intent.ACTION_USER_SWITCHED), null, mHandler);
updatePointerSpeedFromSettings();
updateShowTouchesFromSettings();
updateAccessibilityLargePointerFromSettings();
updateDeepPressStatusFromSettings("just booted");
updateMaximumObscuringOpacityForTouchFromSettings();
updateBlockUntrustedTouchesModeFromSettings();
}
}
调用mNative(NativeInputManagerService)的start方法,NativeInputManagerService是一个接口,start是一个Native方法,在com_android_server_input_inputManagerService.cpp中实现:
//frameworks/base/services/core/jni/com_android_server_input_inputManagerService.cpp
static void nativeStart(JNIEnv* env, jobject nativeImplObj) {
NativeInputManager* im = getNativeInputManager(env, nativeImplObj);
status_t result = im->getInputManager()->start();
if (result) {
jniThrowRuntimeException(env, "Input manager could not be started.");
}
}
InputManager start
调用getInputManager获取InputManagerInterface对象,然后调用InputManagerInterface的start方法,InputManagerInterface是一个接口,由InputManager实现:
//frameworks/native/services/inputflinger/InputManager.cpp
std::unique_ptr<InputDispatcherInterface> mDispatcher;
std::unique_ptr<InputReaderInterface> mReader;
status_t InputManager::start() {
status_t result = mDispatcher->start();
if (result) {
ALOGE("Could not start InputDispatcher thread due to error %d.", result);
return result;
}
result = mReader->start();
if (result) {
ALOGE("Could not start InputReader due to error %d.", result);
mDispatcher->stop();
return result;
}
return OK;
}
上面方法的主要处理如下:
1、调用mDispatcher(InputDispatcherInterface)的start方法。
2、调用mReader(InputReaderInterface)的start方法。
下面分别进行分析:
InputDispatcher start
调用mDispatcher(InputDispatcherInterface)的start方法,InputDispatcherInterface是一个接口,由InputDispatcher实现,InputDispatcher的start方法会创建一个线程,然后开启线程Loop,循环处理输入事件:
//frameworks/native/services/inputflinger/dispatcher/InputDispatcher.java
status_t InputDispatcher::start() {
if (mThread) {
return ALREADY_EXISTS;
}
mThread = std::make_unique<InputThread>(
"InputDispatcher", [this]() { dispatchOnce(); }, [this]() { mLooper->wake(); });
return OK;
}
InputDispatcher dispatchOnce
InputDispatcher在start() 方法中会启动一个线程,在被唤醒后会调用到dispatchOnce 方法,在该方法中,通过调用dispatchOnceInnerLocked来分发事件:
Android13 InputDispatcher dispatchOnce流程分析-CSDN博客
InputReader start
调用mReader(InputReaderInterface)的start方法,InputReaderInterface是一个接口,由InputReader实现,