summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorJeff Brown <jeffbrown@google.com>2010-10-11 17:26:51 -0700
committerAndroid Git Automerger <android-git-automerger@android.com>2010-10-11 17:26:51 -0700
commitf2e0681ada3ffe1de994a51dcebd6ef045d27434 (patch)
treec6f8e837d2091a890fb3d9d2882b3a534b190625
parentd965724fdcc63a070657518542559a8b1a35a70d (diff)
parent1da8d4d1697cec871dea8c30dad67e90db10bde6 (diff)
downloadframeworks_base-f2e0681ada3ffe1de994a51dcebd6ef045d27434.zip
frameworks_base-f2e0681ada3ffe1de994a51dcebd6ef045d27434.tar.gz
frameworks_base-f2e0681ada3ffe1de994a51dcebd6ef045d27434.tar.bz2
am 1da8d4d1: Merge "Fix an event injection bug when the policy is bypassed." into gingerbread
Merge commit '1da8d4d1697cec871dea8c30dad67e90db10bde6' into gingerbread-plus-aosp * commit '1da8d4d1697cec871dea8c30dad67e90db10bde6': Fix an event injection bug when the policy is bypassed.
-rw-r--r--core/java/android/view/WindowManagerPolicy.java1
-rw-r--r--include/ui/Input.h4
-rw-r--r--include/ui/InputDispatcher.h5
-rw-r--r--libs/ui/InputDispatcher.cpp63
-rwxr-xr-xpolicy/src/com/android/internal/policy/impl/PhoneWindowManager.java15
-rw-r--r--services/java/com/android/server/InputManager.java5
-rw-r--r--services/java/com/android/server/WindowManagerService.java7
-rw-r--r--services/jni/com_android_server_InputManager.cpp250
8 files changed, 149 insertions, 201 deletions
diff --git a/core/java/android/view/WindowManagerPolicy.java b/core/java/android/view/WindowManagerPolicy.java
index ef7716e..1fd31a3 100644
--- a/core/java/android/view/WindowManagerPolicy.java
+++ b/core/java/android/view/WindowManagerPolicy.java
@@ -77,6 +77,7 @@ public interface WindowManagerPolicy {
public final static int FLAG_VIRTUAL = 0x00000100;
public final static int FLAG_INJECTED = 0x01000000;
+ public final static int FLAG_TRUSTED = 0x02000000;
public final static int FLAG_WOKE_HERE = 0x10000000;
public final static int FLAG_BRIGHT_HERE = 0x20000000;
diff --git a/include/ui/Input.h b/include/ui/Input.h
index 66061fd..8c6018b 100644
--- a/include/ui/Input.h
+++ b/include/ui/Input.h
@@ -95,6 +95,10 @@ enum {
// Indicates that the input event was injected.
POLICY_FLAG_INJECTED = 0x01000000,
+ // Indicates that the input event is from a trusted source such as a directly attached
+ // input device or an application with system-wide event injection permission.
+ POLICY_FLAG_TRUSTED = 0x02000000,
+
/* These flags are set by the input reader policy as it intercepts each event. */
// Indicates that the screen was off when the event was received and the event
diff --git a/include/ui/InputDispatcher.h b/include/ui/InputDispatcher.h
index 0834e86..3599163 100644
--- a/include/ui/InputDispatcher.h
+++ b/include/ui/InputDispatcher.h
@@ -913,7 +913,6 @@ private:
void drainInboundQueueLocked();
void releasePendingEventLocked();
void releaseInboundEventLocked(EventEntry* entry);
- bool isEventFromTrustedSourceLocked(EventEntry* entry);
// Dispatch state.
bool mDispatchEnabled;
@@ -960,10 +959,10 @@ private:
nsecs_t currentTime, ConfigurationChangedEntry* entry);
bool dispatchKeyLocked(
nsecs_t currentTime, KeyEntry* entry, nsecs_t keyRepeatTimeout,
- bool dropEvent, nsecs_t* nextWakeupTime);
+ DropReason* dropReason, nsecs_t* nextWakeupTime);
bool dispatchMotionLocked(
nsecs_t currentTime, MotionEntry* entry,
- bool dropEvent, nsecs_t* nextWakeupTime);
+ DropReason* dropReason, nsecs_t* nextWakeupTime);
void dispatchEventToCurrentInputTargetsLocked(
nsecs_t currentTime, EventEntry* entry, bool resumeWithAppendedMotionSample);
diff --git a/libs/ui/InputDispatcher.cpp b/libs/ui/InputDispatcher.cpp
index 58c2cdf..41b6ff3 100644
--- a/libs/ui/InputDispatcher.cpp
+++ b/libs/ui/InputDispatcher.cpp
@@ -370,7 +370,7 @@ void InputDispatcher::dispatchOnceInnerLocked(nsecs_t keyRepeatTimeout,
}
}
done = dispatchKeyLocked(currentTime, typedEntry, keyRepeatTimeout,
- dropReason != DROP_REASON_NOT_DROPPED, nextWakeupTime);
+ &dropReason, nextWakeupTime);
break;
}
@@ -380,7 +380,7 @@ void InputDispatcher::dispatchOnceInnerLocked(nsecs_t keyRepeatTimeout,
dropReason = DROP_REASON_APP_SWITCH;
}
done = dispatchMotionLocked(currentTime, typedEntry,
- dropReason != DROP_REASON_NOT_DROPPED, nextWakeupTime);
+ &dropReason, nextWakeupTime);
break;
}
@@ -431,6 +431,9 @@ void InputDispatcher::dropInboundEventLocked(EventEntry* entry, DropReason dropR
const char* reason;
switch (dropReason) {
case DROP_REASON_POLICY:
+#if DEBUG_INBOUND_EVENT_DETAILS
+ LOGD("Dropped event because policy requested that it not be delivered to the application.");
+#endif
reason = "inbound event was dropped because the policy requested that it not be "
"delivered to the application";
break;
@@ -473,7 +476,7 @@ bool InputDispatcher::isAppSwitchKeyCode(int32_t keyCode) {
bool InputDispatcher::isAppSwitchKeyEventLocked(KeyEntry* keyEntry) {
return ! (keyEntry->flags & AKEY_EVENT_FLAG_CANCELED)
&& isAppSwitchKeyCode(keyEntry->keyCode)
- && isEventFromTrustedSourceLocked(keyEntry)
+ && (keyEntry->policyFlags & POLICY_FLAG_TRUSTED)
&& (keyEntry->policyFlags & POLICY_FLAG_PASS_TO_USER);
}
@@ -541,12 +544,6 @@ void InputDispatcher::releaseInboundEventLocked(EventEntry* entry) {
mAllocator.releaseEventEntry(entry);
}
-bool InputDispatcher::isEventFromTrustedSourceLocked(EventEntry* entry) {
- InjectionState* injectionState = entry->injectionState;
- return ! injectionState
- || hasInjectionPermission(injectionState->injectorPid, injectionState->injectorUid);
-}
-
void InputDispatcher::resetKeyRepeatLocked() {
if (mKeyRepeatState.lastKeyEntry) {
mAllocator.releaseKeyEntry(mKeyRepeatState.lastKeyEntry);
@@ -559,7 +556,8 @@ InputDispatcher::KeyEntry* InputDispatcher::synthesizeKeyRepeatLocked(
KeyEntry* entry = mKeyRepeatState.lastKeyEntry;
// Reuse the repeated key entry if it is otherwise unreferenced.
- uint32_t policyFlags = entry->policyFlags & (POLICY_FLAG_RAW_MASK | POLICY_FLAG_PASS_TO_USER);
+ uint32_t policyFlags = (entry->policyFlags & POLICY_FLAG_RAW_MASK)
+ | POLICY_FLAG_PASS_TO_USER | POLICY_FLAG_TRUSTED;
if (entry->refCount == 1) {
mAllocator.recycleKeyEntry(entry);
entry->eventTime = currentTime;
@@ -608,19 +606,13 @@ bool InputDispatcher::dispatchConfigurationChangedLocked(
bool InputDispatcher::dispatchKeyLocked(
nsecs_t currentTime, KeyEntry* entry, nsecs_t keyRepeatTimeout,
- bool dropEvent, nsecs_t* nextWakeupTime) {
+ DropReason* dropReason, nsecs_t* nextWakeupTime) {
// Give the policy a chance to intercept the key.
if (entry->interceptKeyResult == KeyEntry::INTERCEPT_KEY_RESULT_UNKNOWN) {
- bool trusted;
- if (! dropEvent && mFocusedWindow) {
- trusted = checkInjectionPermission(mFocusedWindow, entry->injectionState);
- } else {
- trusted = isEventFromTrustedSourceLocked(entry);
- }
- if (trusted) {
+ if (entry->policyFlags & POLICY_FLAG_PASS_TO_USER) {
CommandEntry* commandEntry = postCommandLocked(
& InputDispatcher::doInterceptKeyBeforeDispatchingLockedInterruptible);
- if (! dropEvent && mFocusedWindow) {
+ if (mFocusedWindow) {
commandEntry->inputChannel = mFocusedWindow->inputChannel;
}
commandEntry->keyEntry = entry;
@@ -630,13 +622,16 @@ bool InputDispatcher::dispatchKeyLocked(
entry->interceptKeyResult = KeyEntry::INTERCEPT_KEY_RESULT_CONTINUE;
}
} else if (entry->interceptKeyResult == KeyEntry::INTERCEPT_KEY_RESULT_SKIP) {
+ if (*dropReason == DROP_REASON_NOT_DROPPED) {
+ *dropReason = DROP_REASON_POLICY;
+ }
resetTargetsLocked();
setInjectionResultLocked(entry, INPUT_EVENT_INJECTION_SUCCEEDED);
return true;
}
// Clean up if dropping the event.
- if (dropEvent) {
+ if (*dropReason != DROP_REASON_NOT_DROPPED) {
resetTargetsLocked();
setInjectionResultLocked(entry, INPUT_EVENT_INJECTION_FAILED);
return true;
@@ -648,7 +643,8 @@ bool InputDispatcher::dispatchKeyLocked(
if (entry->repeatCount == 0
&& entry->action == AKEY_EVENT_ACTION_DOWN
- && ! entry->isInjected()) {
+ && (entry->policyFlags & POLICY_FLAG_TRUSTED)
+ && !entry->isInjected()) {
if (mKeyRepeatState.lastKeyEntry
&& mKeyRepeatState.lastKeyEntry->keyCode == entry->keyCode) {
// We have seen two identical key downs in a row which indicates that the device
@@ -713,9 +709,9 @@ void InputDispatcher::logOutboundKeyDetailsLocked(const char* prefix, const KeyE
}
bool InputDispatcher::dispatchMotionLocked(
- nsecs_t currentTime, MotionEntry* entry, bool dropEvent, nsecs_t* nextWakeupTime) {
+ nsecs_t currentTime, MotionEntry* entry, DropReason* dropReason, nsecs_t* nextWakeupTime) {
// Clean up if dropping the event.
- if (dropEvent) {
+ if (*dropReason != DROP_REASON_NOT_DROPPED) {
resetTargetsLocked();
setInjectionResultLocked(entry, INPUT_EVENT_INJECTION_FAILED);
return true;
@@ -2085,6 +2081,7 @@ void InputDispatcher::notifyKey(nsecs_t eventTime, int32_t deviceId, int32_t sou
return;
}
+ policyFlags |= POLICY_FLAG_TRUSTED;
mPolicy->interceptKeyBeforeQueueing(eventTime, deviceId, action, /*byref*/ flags,
keyCode, scanCode, /*byref*/ policyFlags);
@@ -2130,6 +2127,7 @@ void InputDispatcher::notifyMotion(nsecs_t eventTime, int32_t deviceId, int32_t
return;
}
+ policyFlags |= POLICY_FLAG_TRUSTED;
mPolicy->interceptGenericBeforeQueueing(eventTime, /*byref*/ policyFlags);
bool needWake;
@@ -2263,6 +2261,7 @@ void InputDispatcher::notifySwitch(nsecs_t when, int32_t switchCode, int32_t swi
switchCode, switchValue, policyFlags);
#endif
+ policyFlags |= POLICY_FLAG_TRUSTED;
mPolicy->notifySwitch(when, switchCode, switchValue, policyFlags);
}
@@ -2275,7 +2274,11 @@ int32_t InputDispatcher::injectInputEvent(const InputEvent* event,
#endif
nsecs_t endTime = now() + milliseconds_to_nanoseconds(timeoutMillis);
- bool trusted = hasInjectionPermission(injectorPid, injectorUid);
+
+ uint32_t policyFlags = POLICY_FLAG_INJECTED;
+ if (hasInjectionPermission(injectorPid, injectorUid)) {
+ policyFlags |= POLICY_FLAG_TRUSTED;
+ }
EventEntry* injectedEntry;
switch (event->getType()) {
@@ -2291,11 +2294,8 @@ int32_t InputDispatcher::injectInputEvent(const InputEvent* event,
int32_t flags = keyEvent->getFlags();
int32_t keyCode = keyEvent->getKeyCode();
int32_t scanCode = keyEvent->getScanCode();
- uint32_t policyFlags = POLICY_FLAG_INJECTED;
- if (trusted) {
- mPolicy->interceptKeyBeforeQueueing(eventTime, deviceId, action, /*byref*/ flags,
- keyCode, scanCode, /*byref*/ policyFlags);
- }
+ mPolicy->interceptKeyBeforeQueueing(eventTime, deviceId, action, /*byref*/ flags,
+ keyCode, scanCode, /*byref*/ policyFlags);
mLock.lock();
injectedEntry = mAllocator.obtainKeyEntry(eventTime, deviceId, keyEvent->getSource(),
@@ -2314,10 +2314,7 @@ int32_t InputDispatcher::injectInputEvent(const InputEvent* event,
}
nsecs_t eventTime = motionEvent->getEventTime();
- uint32_t policyFlags = POLICY_FLAG_INJECTED;
- if (trusted) {
- mPolicy->interceptGenericBeforeQueueing(eventTime, /*byref*/ policyFlags);
- }
+ mPolicy->interceptGenericBeforeQueueing(eventTime, /*byref*/ policyFlags);
mLock.lock();
const nsecs_t* sampleEventTimes = motionEvent->getSampleEventTimes();
diff --git a/policy/src/com/android/internal/policy/impl/PhoneWindowManager.java b/policy/src/com/android/internal/policy/impl/PhoneWindowManager.java
index f21d357..d9bceec 100755
--- a/policy/src/com/android/internal/policy/impl/PhoneWindowManager.java
+++ b/policy/src/com/android/internal/policy/impl/PhoneWindowManager.java
@@ -1057,6 +1057,10 @@ public class PhoneWindowManager implements WindowManagerPolicy {
@Override
public boolean interceptKeyBeforeDispatching(WindowState win, int action, int flags,
int keyCode, int metaState, int repeatCount, int policyFlags) {
+ if ((policyFlags & WindowManagerPolicy.FLAG_TRUSTED) == 0) {
+ return false;
+ }
+
final boolean keyguardOn = keyguardOn();
final boolean down = (action == KeyEvent.ACTION_DOWN);
final boolean canceled = ((flags & KeyEvent.FLAG_CANCELED) != 0);
@@ -1083,7 +1087,7 @@ public class PhoneWindowManager implements WindowManagerPolicy {
if (!down) {
mHomePressed = false;
- if (! canceled) {
+ if (!canceled) {
// If an incoming call is ringing, HOME is totally disabled.
// (The user is already on the InCallScreen at this point,
// and his ONLY options are to answer or reject the call.)
@@ -1735,7 +1739,14 @@ public class PhoneWindowManager implements WindowManagerPolicy {
public int interceptKeyBeforeQueueing(long whenNanos, int keyCode, boolean down,
int policyFlags, boolean isScreenOn) {
int result = ACTION_PASS_TO_USER;
-
+ if ((policyFlags & WindowManagerPolicy.FLAG_TRUSTED) == 0) {
+ return result;
+ }
+
+ if (down && (policyFlags & WindowManagerPolicy.FLAG_VIRTUAL) != 0) {
+ performHapticFeedbackLw(null, HapticFeedbackConstants.VIRTUAL_KEY, false);
+ }
+
final boolean isWakeKey = (policyFlags
& (WindowManagerPolicy.FLAG_WAKE | WindowManagerPolicy.FLAG_WAKE_DROPPED)) != 0;
diff --git a/services/java/com/android/server/InputManager.java b/services/java/com/android/server/InputManager.java
index ed1243a..df41264 100644
--- a/services/java/com/android/server/InputManager.java
+++ b/services/java/com/android/server/InputManager.java
@@ -359,11 +359,6 @@ public class InputManager {
private static final String CALIBRATION_DIR_PATH = "usr/idc/";
@SuppressWarnings("unused")
- public void virtualKeyDownFeedback() {
- mWindowManagerService.mInputMonitor.virtualKeyDownFeedback();
- }
-
- @SuppressWarnings("unused")
public void notifyConfigurationChanged(long whenNanos) {
mWindowManagerService.sendNewConfiguration();
}
diff --git a/services/java/com/android/server/WindowManagerService.java b/services/java/com/android/server/WindowManagerService.java
index a23737b..abf848c 100644
--- a/services/java/com/android/server/WindowManagerService.java
+++ b/services/java/com/android/server/WindowManagerService.java
@@ -5244,13 +5244,6 @@ public class WindowManagerService extends IWindowManager.Stub
mTempInputWindows.clear();
}
- /* Provides feedback for a virtual key down. */
- public void virtualKeyDownFeedback() {
- synchronized (mWindowMap) {
- mPolicy.performHapticFeedbackLw(null, HapticFeedbackConstants.VIRTUAL_KEY, false);
- }
- }
-
/* Notifies that the lid switch changed state. */
public void notifyLidSwitchChanged(long whenNanos, boolean lidOpen) {
mPolicy.notifyLidSwitchChanged(whenNanos, lidOpen);
diff --git a/services/jni/com_android_server_InputManager.cpp b/services/jni/com_android_server_InputManager.cpp
index 18037e4..a0b0aba 100644
--- a/services/jni/com_android_server_InputManager.cpp
+++ b/services/jni/com_android_server_InputManager.cpp
@@ -50,7 +50,6 @@ static struct {
jmethodID notifyLidSwitchChanged;
jmethodID notifyInputChannelBroken;
jmethodID notifyANR;
- jmethodID virtualKeyDownFeedback;
jmethodID interceptKeyBeforeQueueing;
jmethodID interceptKeyBeforeDispatching;
jmethodID checkInjectEventsPermission;
@@ -192,6 +191,8 @@ public:
/* --- InputDispatcherPolicyInterface implementation --- */
+ virtual void notifySwitch(nsecs_t when, int32_t switchCode, int32_t switchValue,
+ uint32_t policyFlags);
virtual void notifyConfigurationChanged(nsecs_t when);
virtual nsecs_t notifyANR(const sp<InputApplicationHandle>& inputApplicationHandle,
const sp<InputChannel>& inputChannel);
@@ -205,8 +206,6 @@ public:
virtual void interceptGenericBeforeQueueing(nsecs_t when, uint32_t& policyFlags);
virtual bool interceptKeyBeforeDispatching(const sp<InputChannel>& inputChannel,
const KeyEvent* keyEvent, uint32_t policyFlags);
- virtual void notifySwitch(nsecs_t when, int32_t switchCode, int32_t switchValue,
- uint32_t policyFlags);
virtual void pokeUserActivity(nsecs_t eventTime, int32_t eventType);
virtual bool checkInjectEventsPermissionNonReentrant(
int32_t injectorPid, int32_t injectorUid);
@@ -255,7 +254,6 @@ private:
static bool populateWindow(JNIEnv* env, jobject windowObj, InputWindow& outWindow);
- static bool isPolicyKey(int32_t keyCode, bool isScreenOn);
static bool checkAndClearExceptionFromCallback(JNIEnv* env, const char* methodName);
static inline JNIEnv* jniEnv() {
@@ -291,37 +289,6 @@ void NativeInputManager::dump(String8& dump) {
dump.append("\n");
}
-bool NativeInputManager::isPolicyKey(int32_t keyCode, bool isScreenOn) {
- // Special keys that the WindowManagerPolicy might care about.
- switch (keyCode) {
- case AKEYCODE_VOLUME_UP:
- case AKEYCODE_VOLUME_DOWN:
- case AKEYCODE_ENDCALL:
- case AKEYCODE_POWER:
- case AKEYCODE_CALL:
- case AKEYCODE_HOME:
- case AKEYCODE_MENU:
- case AKEYCODE_SEARCH:
- // media keys
- case AKEYCODE_HEADSETHOOK:
- case AKEYCODE_MEDIA_PLAY_PAUSE:
- case AKEYCODE_MEDIA_STOP:
- case AKEYCODE_MEDIA_NEXT:
- case AKEYCODE_MEDIA_PREVIOUS:
- case AKEYCODE_MEDIA_REWIND:
- case AKEYCODE_MEDIA_FAST_FORWARD:
- // The policy always cares about these keys.
- return true;
- default:
- // We need to pass all keys to the policy in the following cases:
- // - screen is off
- // - keyguard is visible
- // - policy is performing key chording
- //return ! isScreenOn || keyguardVisible || chording;
- return true; // XXX stubbed out for now
- }
-}
-
bool NativeInputManager::checkAndClearExceptionFromCallback(JNIEnv* env, const char* methodName) {
if (env->ExceptionCheck()) {
LOGE("An exception was thrown by callback '%s'.", methodName);
@@ -454,115 +421,6 @@ bool NativeInputManager::getDisplayInfo(int32_t displayId,
return result;
}
-bool NativeInputManager::isScreenOn() {
- return android_server_PowerManagerService_isScreenOn();
-}
-
-bool NativeInputManager::isScreenBright() {
- return android_server_PowerManagerService_isScreenBright();
-}
-
-void NativeInputManager::interceptKeyBeforeQueueing(nsecs_t when,
- int32_t deviceId, int32_t action, int32_t &flags,
- int32_t keyCode, int32_t scanCode, uint32_t& policyFlags) {
-#if DEBUG_INPUT_DISPATCHER_POLICY
- LOGD("interceptKeyBeforeQueueing - when=%lld, deviceId=%d, action=%d, flags=%d, "
- "keyCode=%d, scanCode=%d, policyFlags=0x%x",
- when, deviceId, action, flags, keyCode, scanCode, policyFlags);
-#endif
-
- bool down = action == AKEY_EVENT_ACTION_DOWN;
- if ((policyFlags & POLICY_FLAG_VIRTUAL) || (flags & AKEY_EVENT_FLAG_VIRTUAL_HARD_KEY)) {
- policyFlags |= POLICY_FLAG_VIRTUAL;
- flags |= AKEY_EVENT_FLAG_VIRTUAL_HARD_KEY;
-
- if (down) {
- JNIEnv* env = jniEnv();
- env->CallVoidMethod(mCallbacksObj, gCallbacksClassInfo.virtualKeyDownFeedback);
- checkAndClearExceptionFromCallback(env, "virtualKeyDownFeedback");
- }
- }
-
- const int32_t WM_ACTION_PASS_TO_USER = 1;
- const int32_t WM_ACTION_POKE_USER_ACTIVITY = 2;
- const int32_t WM_ACTION_GO_TO_SLEEP = 4;
-
- bool isScreenOn = this->isScreenOn();
- bool isScreenBright = this->isScreenBright();
-
- jint wmActions = 0;
- if (isPolicyKey(keyCode, isScreenOn)) {
- JNIEnv* env = jniEnv();
-
- wmActions = env->CallIntMethod(mCallbacksObj,
- gCallbacksClassInfo.interceptKeyBeforeQueueing,
- when, keyCode, down, policyFlags, isScreenOn);
- if (checkAndClearExceptionFromCallback(env, "interceptKeyBeforeQueueing")) {
- wmActions = 0;
- }
- } else {
- wmActions = WM_ACTION_PASS_TO_USER;
- }
-
- if (! isScreenOn) {
- // Key presses and releases wake the device.
- policyFlags |= POLICY_FLAG_WOKE_HERE;
- flags |= AKEY_EVENT_FLAG_WOKE_HERE;
- }
-
- if (! isScreenBright) {
- // Key presses and releases brighten the screen if dimmed.
- policyFlags |= POLICY_FLAG_BRIGHT_HERE;
- }
-
- if (wmActions & WM_ACTION_GO_TO_SLEEP) {
- android_server_PowerManagerService_goToSleep(when);
- }
-
- if (wmActions & WM_ACTION_POKE_USER_ACTIVITY) {
- android_server_PowerManagerService_userActivity(when, POWER_MANAGER_BUTTON_EVENT);
- }
-
- if (wmActions & WM_ACTION_PASS_TO_USER) {
- policyFlags |= POLICY_FLAG_PASS_TO_USER;
- }
-}
-
-void NativeInputManager::interceptGenericBeforeQueueing(nsecs_t when, uint32_t& policyFlags) {
-#if DEBUG_INPUT_DISPATCHER_POLICY
- LOGD("interceptGenericBeforeQueueing - when=%lld, policyFlags=0x%x", when, policyFlags);
-#endif
-
- if (isScreenOn()) {
- // Only dispatch events when the device is awake.
- // Do not wake the device.
- policyFlags |= POLICY_FLAG_PASS_TO_USER;
-
- if (! isScreenBright()) {
- // Brighten the screen if dimmed.
- policyFlags |= POLICY_FLAG_BRIGHT_HERE;
- }
- }
-}
-
-void NativeInputManager::notifySwitch(nsecs_t when, int32_t switchCode,
- int32_t switchValue, uint32_t policyFlags) {
-#if DEBUG_INPUT_DISPATCHER_POLICY
- LOGD("notifySwitch - when=%lld, switchCode=%d, switchValue=%d, policyFlags=0x%x",
- when, switchCode, switchValue, policyFlags);
-#endif
-
- JNIEnv* env = jniEnv();
-
- switch (switchCode) {
- case SW_LID:
- env->CallVoidMethod(mCallbacksObj, gCallbacksClassInfo.notifyLidSwitchChanged,
- when, switchValue == 0);
- checkAndClearExceptionFromCallback(env, "notifyLidSwitchChanged");
- break;
- }
-}
-
bool NativeInputManager::filterTouchEvents() {
if (mFilterTouchEvents < 0) {
JNIEnv* env = jniEnv();
@@ -692,6 +550,24 @@ void NativeInputManager::getExcludedDeviceNames(Vector<String8>& outExcludedDevi
}
}
+void NativeInputManager::notifySwitch(nsecs_t when, int32_t switchCode,
+ int32_t switchValue, uint32_t policyFlags) {
+#if DEBUG_INPUT_DISPATCHER_POLICY
+ LOGD("notifySwitch - when=%lld, switchCode=%d, switchValue=%d, policyFlags=0x%x",
+ when, switchCode, switchValue, policyFlags);
+#endif
+
+ JNIEnv* env = jniEnv();
+
+ switch (switchCode) {
+ case SW_LID:
+ env->CallVoidMethod(mCallbacksObj, gCallbacksClassInfo.notifyLidSwitchChanged,
+ when, switchValue == 0);
+ checkAndClearExceptionFromCallback(env, "notifyLidSwitchChanged");
+ break;
+ }
+}
+
void NativeInputManager::notifyConfigurationChanged(nsecs_t when) {
#if DEBUG_INPUT_DISPATCHER_POLICY
LOGD("notifyConfigurationChanged - when=%lld", when);
@@ -944,13 +820,88 @@ void NativeInputManager::setInputDispatchMode(bool enabled, bool frozen) {
mInputManager->getDispatcher()->setInputDispatchMode(enabled, frozen);
}
-bool NativeInputManager::interceptKeyBeforeDispatching(const sp<InputChannel>& inputChannel,
- const KeyEvent* keyEvent, uint32_t policyFlags) {
+bool NativeInputManager::isScreenOn() {
+ return android_server_PowerManagerService_isScreenOn();
+}
+
+bool NativeInputManager::isScreenBright() {
+ return android_server_PowerManagerService_isScreenBright();
+}
+
+void NativeInputManager::interceptKeyBeforeQueueing(nsecs_t when,
+ int32_t deviceId, int32_t action, int32_t &flags,
+ int32_t keyCode, int32_t scanCode, uint32_t& policyFlags) {
+#if DEBUG_INPUT_DISPATCHER_POLICY
+ LOGD("interceptKeyBeforeQueueing - when=%lld, deviceId=%d, action=%d, flags=%d, "
+ "keyCode=%d, scanCode=%d, policyFlags=0x%x",
+ when, deviceId, action, flags, keyCode, scanCode, policyFlags);
+#endif
+
+ if ((policyFlags & POLICY_FLAG_VIRTUAL) || (flags & AKEY_EVENT_FLAG_VIRTUAL_HARD_KEY)) {
+ policyFlags |= POLICY_FLAG_VIRTUAL;
+ flags |= AKEY_EVENT_FLAG_VIRTUAL_HARD_KEY;
+ }
+
+ const int32_t WM_ACTION_PASS_TO_USER = 1;
+ const int32_t WM_ACTION_POKE_USER_ACTIVITY = 2;
+ const int32_t WM_ACTION_GO_TO_SLEEP = 4;
+
bool isScreenOn = this->isScreenOn();
- if (! isPolicyKey(keyEvent->getKeyCode(), isScreenOn)) {
- return false;
+ bool isScreenBright = this->isScreenBright();
+
+ JNIEnv* env = jniEnv();
+ jint wmActions = env->CallIntMethod(mCallbacksObj,
+ gCallbacksClassInfo.interceptKeyBeforeQueueing,
+ when, keyCode, action == AKEY_EVENT_ACTION_DOWN, policyFlags, isScreenOn);
+ if (checkAndClearExceptionFromCallback(env, "interceptKeyBeforeQueueing")) {
+ wmActions = 0;
+ }
+
+ if (policyFlags & POLICY_FLAG_TRUSTED) {
+ if (! isScreenOn) {
+ // Key presses and releases wake the device.
+ policyFlags |= POLICY_FLAG_WOKE_HERE;
+ flags |= AKEY_EVENT_FLAG_WOKE_HERE;
+ }
+
+ if (! isScreenBright) {
+ // Key presses and releases brighten the screen if dimmed.
+ policyFlags |= POLICY_FLAG_BRIGHT_HERE;
+ }
+
+ if (wmActions & WM_ACTION_GO_TO_SLEEP) {
+ android_server_PowerManagerService_goToSleep(when);
+ }
+
+ if (wmActions & WM_ACTION_POKE_USER_ACTIVITY) {
+ android_server_PowerManagerService_userActivity(when, POWER_MANAGER_BUTTON_EVENT);
+ }
}
+ if (wmActions & WM_ACTION_PASS_TO_USER) {
+ policyFlags |= POLICY_FLAG_PASS_TO_USER;
+ }
+}
+
+void NativeInputManager::interceptGenericBeforeQueueing(nsecs_t when, uint32_t& policyFlags) {
+#if DEBUG_INPUT_DISPATCHER_POLICY
+ LOGD("interceptGenericBeforeQueueing - when=%lld, policyFlags=0x%x", when, policyFlags);
+#endif
+
+ if (isScreenOn()) {
+ // Only dispatch events when the device is awake.
+ // Do not wake the device.
+ policyFlags |= POLICY_FLAG_PASS_TO_USER;
+
+ if ((policyFlags & POLICY_FLAG_TRUSTED) && !isScreenBright()) {
+ // Brighten the screen if dimmed.
+ policyFlags |= POLICY_FLAG_BRIGHT_HERE;
+ }
+ }
+}
+
+bool NativeInputManager::interceptKeyBeforeDispatching(const sp<InputChannel>& inputChannel,
+ const KeyEvent* keyEvent, uint32_t policyFlags) {
JNIEnv* env = jniEnv();
// Note: inputChannel may be null.
@@ -1365,9 +1316,6 @@ int register_android_server_InputManager(JNIEnv* env) {
GET_METHOD_ID(gCallbacksClassInfo.notifyANR, gCallbacksClassInfo.clazz,
"notifyANR", "(Ljava/lang/Object;Landroid/view/InputChannel;)J");
- GET_METHOD_ID(gCallbacksClassInfo.virtualKeyDownFeedback, gCallbacksClassInfo.clazz,
- "virtualKeyDownFeedback", "()V");
-
GET_METHOD_ID(gCallbacksClassInfo.interceptKeyBeforeQueueing, gCallbacksClassInfo.clazz,
"interceptKeyBeforeQueueing", "(JIZIZ)I");