Merge "WindowInfo: Merge InputConfig and Feature flags" into tm-dev
diff --git a/libs/gui/WindowInfo.cpp b/libs/gui/WindowInfo.cpp
index 80bd638..b02bae4 100644
--- a/libs/gui/WindowInfo.cpp
+++ b/libs/gui/WindowInfo.cpp
@@ -51,11 +51,11 @@
 }
 
 bool WindowInfo::isSpy() const {
-    return inputFeatures.test(Feature::SPY);
+    return inputConfig.test(InputConfig::SPY);
 }
 
 bool WindowInfo::interceptsStylus() const {
-    return inputFeatures.test(Feature::INTERCEPTS_STYLUS);
+    return inputConfig.test(InputConfig::INTERCEPTS_STYLUS);
 }
 
 bool WindowInfo::overlaps(const WindowInfo* other) const {
@@ -73,8 +73,7 @@
             info.touchableRegion.hasSameRects(touchableRegion) &&
             info.touchOcclusionMode == touchOcclusionMode && info.ownerPid == ownerPid &&
             info.ownerUid == ownerUid && info.packageName == packageName &&
-            info.inputFeatures == inputFeatures && info.inputConfig == inputConfig &&
-            info.displayId == displayId &&
+            info.inputConfig == inputConfig && info.displayId == displayId &&
             info.replaceTouchableRegionWithCrop == replaceTouchableRegionWithCrop &&
             info.applicationInfo == applicationInfo && info.layoutParamsType == layoutParamsType &&
             info.layoutParamsFlags == layoutParamsFlags;
@@ -92,7 +91,6 @@
     parcel->writeInt32(1);
 
     // Ensure that the size of the flags that we use is 32 bits for writing into the parcel.
-    static_assert(sizeof(inputFeatures) == 4u);
     static_assert(sizeof(inputConfig) == 4u);
 
     // clang-format off
@@ -120,7 +118,6 @@
         parcel->writeInt32(ownerPid) ?:
         parcel->writeInt32(ownerUid) ?:
         parcel->writeUtf8AsUtf16(packageName) ?:
-        parcel->writeInt32(inputFeatures.get()) ?:
         parcel->writeInt32(inputConfig.get()) ?:
         parcel->writeInt32(displayId) ?:
         applicationInfo.writeToParcel(parcel) ?:
@@ -178,7 +175,6 @@
 
     touchOcclusionMode = static_cast<TouchOcclusionMode>(touchOcclusionModeInt);
 
-    inputFeatures = Flags<Feature>(parcel->readInt32());
     inputConfig = Flags<InputConfig>(parcel->readInt32());
     // clang-format off
     status = parcel->readInt32(&displayId) ?:
diff --git a/libs/gui/include/gui/WindowInfo.h b/libs/gui/include/gui/WindowInfo.h
index b9bffaa..ef0b98b 100644
--- a/libs/gui/include/gui/WindowInfo.h
+++ b/libs/gui/include/gui/WindowInfo.h
@@ -17,7 +17,7 @@
 #pragma once
 
 #include <android/gui/TouchOcclusionMode.h>
-#include <android/os/IInputConstants.h>
+#include <android/os/InputConfig.h>
 #include <binder/Parcel.h>
 #include <binder/Parcelable.h>
 #include <ftl/Flags.h>
@@ -132,49 +132,45 @@
         ftl_last = FIRST_SYSTEM_WINDOW + 15
     };
 
-    // This is a conversion of os::IInputConstants::InputFeature to an enum backed by an unsigned
-    // type. This indicates that they are flags, so it can be used with ftl/enum.h.
-    enum class Feature : uint32_t {
-        // clang-format off
-        NO_INPUT_CHANNEL =
-                static_cast<uint32_t>(os::IInputConstants::InputFeature::NO_INPUT_CHANNEL),
-        DISABLE_USER_ACTIVITY =
-                static_cast<uint32_t>(os::IInputConstants::InputFeature::DISABLE_USER_ACTIVITY),
-        DROP_INPUT =
-                static_cast<uint32_t>(os::IInputConstants::InputFeature::DROP_INPUT),
-        DROP_INPUT_IF_OBSCURED =
-                static_cast<uint32_t>(os::IInputConstants::InputFeature::DROP_INPUT_IF_OBSCURED),
-        SPY =
-                static_cast<uint32_t>(os::IInputConstants::InputFeature::SPY),
-        INTERCEPTS_STYLUS =
-                static_cast<uint32_t>(os::IInputConstants::InputFeature::INTERCEPTS_STYLUS),
-        // clang-format on
-    };
-
     // Flags used to determine configuration of this input window.
-    // Input windows can be configured with two sets of flags: InputFeature (WindowInfo::Feature
-    // defined above), and InputConfig. When adding a new configuration for an input window:
-    //   - If you are adding a new flag that's visible and accessible to apps, it should be added
-    //   as an InputFeature.
-    //   - If you are adding an internal behaviour that is used within the system or shell and is
-    //   not exposed to apps, it should be added as an InputConfig.
+    // This is a conversion of os::InputConfig to an enum backed by an unsigned
+    // type. This indicates that they are flags, so it can be used with ftl/enum.h.
     enum class InputConfig : uint32_t {
         // clang-format off
-        NONE                         = 0,
-        NOT_VISIBLE                  = 1 << 0,
-        NOT_FOCUSABLE                = 1 << 1,
-        NOT_TOUCHABLE                = 1 << 2,
-        PREVENT_SPLITTING            = 1 << 3,
-        DUPLICATE_TOUCH_TO_WALLPAPER = 1 << 4,
-        IS_WALLPAPER                 = 1 << 5,
-        PAUSE_DISPATCHING            = 1 << 6,
-        // This flag is set when the window is of a trusted type that is allowed to silently
-        // overlay other windows for the purpose of implementing the secure views feature.
-        // Trusted overlays, such as IME windows, can partly obscure other windows without causing
-        // motion events to be delivered to them with AMOTION_EVENT_FLAG_WINDOW_IS_OBSCURED.
-        TRUSTED_OVERLAY              = 1 << 7,
-        WATCH_OUTSIDE_TOUCH          = 1 << 8,
-        SLIPPERY                     = 1 << 9,
+        DEFAULT =
+                static_cast<uint32_t>(os::InputConfig::DEFAULT),
+        NO_INPUT_CHANNEL =
+                static_cast<uint32_t>(os::InputConfig::NO_INPUT_CHANNEL),
+        NOT_VISIBLE =
+                static_cast<uint32_t>(os::InputConfig::NOT_VISIBLE),
+        NOT_FOCUSABLE =
+                static_cast<uint32_t>(os::InputConfig::NOT_FOCUSABLE),
+        NOT_TOUCHABLE =
+                static_cast<uint32_t>(os::InputConfig::NOT_TOUCHABLE),
+        PREVENT_SPLITTING =
+                static_cast<uint32_t>(os::InputConfig::PREVENT_SPLITTING),
+        DUPLICATE_TOUCH_TO_WALLPAPER =
+                static_cast<uint32_t>(os::InputConfig::DUPLICATE_TOUCH_TO_WALLPAPER),
+        IS_WALLPAPER =
+                static_cast<uint32_t>(os::InputConfig::IS_WALLPAPER),
+        PAUSE_DISPATCHING =
+                static_cast<uint32_t>(os::InputConfig::PAUSE_DISPATCHING),
+        TRUSTED_OVERLAY =
+                static_cast<uint32_t>(os::InputConfig::TRUSTED_OVERLAY),
+        WATCH_OUTSIDE_TOUCH =
+                static_cast<uint32_t>(os::InputConfig::WATCH_OUTSIDE_TOUCH),
+        SLIPPERY =
+                static_cast<uint32_t>(os::InputConfig::SLIPPERY),
+        DISABLE_USER_ACTIVITY =
+                static_cast<uint32_t>(os::InputConfig::DISABLE_USER_ACTIVITY),
+        DROP_INPUT =
+                static_cast<uint32_t>(os::InputConfig::DROP_INPUT),
+        DROP_INPUT_IF_OBSCURED =
+                static_cast<uint32_t>(os::InputConfig::DROP_INPUT_IF_OBSCURED),
+        SPY =
+                static_cast<uint32_t>(os::InputConfig::SPY),
+        INTERCEPTS_STYLUS =
+                static_cast<uint32_t>(os::InputConfig::INTERCEPTS_STYLUS),
         // clang-format on
     };
 
@@ -228,7 +224,6 @@
     int32_t ownerPid = -1;
     int32_t ownerUid = -1;
     std::string packageName;
-    Flags<Feature> inputFeatures;
     Flags<InputConfig> inputConfig;
     int32_t displayId = ADISPLAY_ID_NONE;
     InputApplicationInfo applicationInfo;
diff --git a/libs/gui/tests/WindowInfo_test.cpp b/libs/gui/tests/WindowInfo_test.cpp
index ff9bae2..c51b244 100644
--- a/libs/gui/tests/WindowInfo_test.cpp
+++ b/libs/gui/tests/WindowInfo_test.cpp
@@ -64,7 +64,6 @@
     i.ownerPid = 19;
     i.ownerUid = 24;
     i.packageName = "com.example.package";
-    i.inputFeatures = WindowInfo::Feature::DISABLE_USER_ACTIVITY;
     i.inputConfig = WindowInfo::InputConfig::NOT_FOCUSABLE;
     i.displayId = 34;
     i.replaceTouchableRegionWithCrop = true;
@@ -97,7 +96,6 @@
     ASSERT_EQ(i.ownerPid, i2.ownerPid);
     ASSERT_EQ(i.ownerUid, i2.ownerUid);
     ASSERT_EQ(i.packageName, i2.packageName);
-    ASSERT_EQ(i.inputFeatures, i2.inputFeatures);
     ASSERT_EQ(i.inputConfig, i2.inputConfig);
     ASSERT_EQ(i.displayId, i2.displayId);
     ASSERT_EQ(i.replaceTouchableRegionWithCrop, i2.replaceTouchableRegionWithCrop);
diff --git a/libs/input/Android.bp b/libs/input/Android.bp
index 930d819..606fe2a 100644
--- a/libs/input/Android.bp
+++ b/libs/input/Android.bp
@@ -30,6 +30,7 @@
         "android/os/IInputConstants.aidl",
         "android/os/InputEventInjectionResult.aidl",
         "android/os/InputEventInjectionSync.aidl",
+        "android/os/InputConfig.aidl",
     ],
 }
 
@@ -79,11 +80,8 @@
         android: {
             srcs: [
                 "InputTransport.cpp",
-                "android/os/BlockUntrustedTouchesMode.aidl",
-                "android/os/IInputConstants.aidl",
                 "android/os/IInputFlinger.aidl",
-                "android/os/InputEventInjectionResult.aidl",
-                "android/os/InputEventInjectionSync.aidl",
+                ":inputconstants_aidl",
             ],
 
             export_shared_lib_headers: ["libbinder"],
@@ -119,6 +117,7 @@
                 "InputTransport.cpp",
                 "android/os/IInputConstants.aidl",
                 "android/os/IInputFlinger.aidl",
+                "android/os/InputConfig.aidl",
             ],
             static_libs: [
                 "libhostgraphics",
diff --git a/libs/input/android/os/IInputConstants.aidl b/libs/input/android/os/IInputConstants.aidl
index 265cbf0..5ce10a4 100644
--- a/libs/input/android/os/IInputConstants.aidl
+++ b/libs/input/android/os/IInputConstants.aidl
@@ -47,55 +47,6 @@
      */
     const int INPUT_EVENT_FLAG_IS_ACCESSIBILITY_EVENT = 0x800;
 
-    @Backing(type="int")
-    enum InputFeature {
-        /**
-         * Does not construct an input channel for this window.  The channel will therefore
-         * be incapable of receiving input.
-         */
-        NO_INPUT_CHANNEL = 0x00000002,
-
-        /**
-         * When this window has focus, does not call user activity for all input events so
-         * the application will have to do it itself.  Should only be used by
-         * the keyguard and phone app.
-         *
-         * Should only be used by the keyguard and phone app.
-         */
-        DISABLE_USER_ACTIVITY = 0x00000004,
-
-        /**
-         * Internal flag used to indicate that input should be dropped on this window.
-         */
-        DROP_INPUT = 0x00000008,
-
-        /**
-         * Internal flag used to indicate that input should be dropped on this window if this window
-         * is obscured.
-         */
-        DROP_INPUT_IF_OBSCURED = 0x00000010,
-
-        /**
-         * An input spy window. This window will receive all pointer events within its touchable
-         * area, but will will not stop events from being sent to other windows below it in z-order.
-         * An input event will be dispatched to all spy windows above the top non-spy window at the
-         * event's coordinates.
-         */
-        SPY = 0x00000020,
-
-        /**
-         * When used with the window flag {@link #FLAG_NOT_TOUCHABLE}, this window will continue
-         * to receive events from a stylus device within its touchable region. All other pointer
-         * events, such as from a mouse or touchscreen, will be dispatched to the windows behind it.
-         *
-         * This input feature has no effect when the window flag {@link #FLAG_NOT_TOUCHABLE} is
-         * not set.
-         *
-         * The window must be a trusted overlay to use this input feature.
-         */
-        INTERCEPTS_STYLUS = 0x00000040,
-    }
-
     /* The default pointer acceleration value. */
     const int DEFAULT_POINTER_ACCELERATION = 3;
 }
diff --git a/libs/input/android/os/InputConfig.aidl b/libs/input/android/os/InputConfig.aidl
new file mode 100644
index 0000000..6d1b396
--- /dev/null
+++ b/libs/input/android/os/InputConfig.aidl
@@ -0,0 +1,147 @@
+/**
+ * Copyright (c) 2022, The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package android.os;
+
+
+/**
+ * Input configurations flags used to determine the behavior of input windows.
+ * @hide
+ */
+@Backing(type="int")
+enum InputConfig {
+
+    /**
+     * The default InputConfig value with no flags set.
+     */
+    DEFAULT                      = 0,
+
+    /**
+     * Does not construct an input channel for this window.  The channel will therefore
+     * be incapable of receiving input.
+     */
+    NO_INPUT_CHANNEL             = 1 << 0,
+
+    /**
+     * Indicates that this input window is not visible, and thus will not be considered as
+     * an input target and will not obscure other windows.
+     */
+    NOT_VISIBLE                  = 1 << 1,
+
+    /**
+     * Indicates that this input window cannot be a focus target, and this will not
+     * receive any input events that can only be directed for the focused window, such
+     * as key events.
+     */
+    NOT_FOCUSABLE                = 1 << 2,
+
+    /**
+     * Indicates that this input window cannot receive any events directed at a
+     * specific location on the screen, such as touchscreen, mouse, and stylus events.
+     * The window will not be considered as a touch target, but can still obscure other
+     * windows.
+     */
+    NOT_TOUCHABLE                = 1 << 3,
+
+    /**
+     * Indicates that this window will not accept a touch event that is split between
+     * more than one window. When set:
+     *  - If this window receives a DOWN event with the first pointer, all successive
+     *    pointers that go down, regardless of their location on the screen, will be
+     *    directed to this window;
+     *  - If the DOWN event lands outside the touchable bounds of this window, no
+     *    successive pointers that go down, regardless of their location on the screen,
+     *    will be directed to this window.
+     */
+    PREVENT_SPLITTING            = 1 << 4,
+
+    /**
+     * Indicates that this window shows the wallpaper behind it, so all touch events
+     * that it receives should also be sent to the wallpaper.
+     */
+    DUPLICATE_TOUCH_TO_WALLPAPER = 1 << 5,
+
+    /** Indicates that this the wallpaper's input window. */
+    IS_WALLPAPER                 = 1 << 6,
+
+    /**
+     * Indicates that input events should not be dispatched to this window. When set,
+     * input events directed towards this window will simply be dropped, and will not
+     * be dispatched to windows behind it.
+     */
+    PAUSE_DISPATCHING            = 1 << 7,
+
+    /**
+     * This flag is set when the window is of a trusted type that is allowed to silently
+     * overlay other windows for the purpose of implementing the secure views feature.
+     * Trusted overlays, such as IME windows, can partly obscure other windows without causing
+     * motion events to be delivered to them with AMOTION_EVENT_FLAG_WINDOW_IS_OBSCURED.
+     */
+    TRUSTED_OVERLAY              = 1 << 8,
+
+    /**
+     * Indicates that this window wants to listen for when there is a touch DOWN event
+     * that occurs outside its touchable bounds. When such an event occurs, this window
+     * will receive a MotionEvent with ACTION_OUTSIDE.
+     */
+    WATCH_OUTSIDE_TOUCH          = 1 << 9,
+
+    /**
+     * When set, this flag allows touches to leave the current window whenever the finger
+     * moves above another window. When this happens, the window that touch has just left
+     * (the current window) will receive ACTION_CANCEL, and the window that touch has entered
+     * will receive ACTION_DOWN, and the remainder of the touch gesture will only go to the
+     * new window. Without this flag, the entire gesture is sent to the current window, even
+     * if the touch leaves the window's bounds.
+     */
+    SLIPPERY                     = 1 << 10,
+
+    /**
+     * When this window has focus, does not call user activity for all input events so
+     * the application will have to do it itself.
+     */
+    DISABLE_USER_ACTIVITY        = 1 << 11,
+
+    /**
+     * Internal flag used to indicate that input should be dropped on this window.
+     */
+    DROP_INPUT                   = 1 << 12,
+
+    /**
+     * Internal flag used to indicate that input should be dropped on this window if this window
+     * is obscured.
+     */
+    DROP_INPUT_IF_OBSCURED       = 1 << 13,
+
+    /**
+     * An input spy window. This window will receive all pointer events within its touchable
+     * area, but will not stop events from being sent to other windows below it in z-order.
+     * An input event will be dispatched to all spy windows above the top non-spy window at the
+     * event's coordinates.
+     */
+    SPY                          = 1 << 14,
+
+    /**
+     * When used with {@link #NOT_TOUCHABLE}, this window will continue to receive events from
+     * a stylus device within its touchable region. All other pointer events, such as from a
+     * mouse or touchscreen, will be dispatched to the windows behind it.
+     *
+     * This configuration has no effect when the config {@link #NOT_TOUCHABLE} is not set.
+     *
+     * It is not valid to set this configuration if {@link #TRUSTED_OVERLAY} is not set.
+     */
+    INTERCEPTS_STYLUS            = 1 << 15,
+}
diff --git a/services/inputflinger/dispatcher/InputDispatcher.cpp b/services/inputflinger/dispatcher/InputDispatcher.cpp
index 32c3a12..7a00222 100644
--- a/services/inputflinger/dispatcher/InputDispatcher.cpp
+++ b/services/inputflinger/dispatcher/InputDispatcher.cpp
@@ -2698,18 +2698,16 @@
 
 std::string InputDispatcher::dumpWindowForTouchOcclusion(const WindowInfo* info,
                                                          bool isTouchedWindow) const {
-    return StringPrintf(INDENT2
-                        "* %spackage=%s/%" PRId32 ", id=%" PRId32 ", mode=%s, alpha=%.2f, "
-                        "frame=[%" PRId32 ",%" PRId32 "][%" PRId32 ",%" PRId32
-                        "], touchableRegion=%s, window={%s}, inputConfig={%s}, inputFeatures={%s}, "
-                        "hasToken=%s, applicationInfo.name=%s, applicationInfo.token=%s\n",
+    return StringPrintf(INDENT2 "* %spackage=%s/%" PRId32 ", id=%" PRId32 ", mode=%s, alpha=%.2f, "
+                                "frame=[%" PRId32 ",%" PRId32 "][%" PRId32 ",%" PRId32
+                                "], touchableRegion=%s, window={%s}, inputConfig={%s}, "
+                                "hasToken=%s, applicationInfo.name=%s, applicationInfo.token=%s\n",
                         isTouchedWindow ? "[TOUCHED] " : "", info->packageName.c_str(),
                         info->ownerUid, info->id, toString(info->touchOcclusionMode).c_str(),
                         info->alpha, info->frameLeft, info->frameTop, info->frameRight,
                         info->frameBottom, dumpRegion(info->touchableRegion).c_str(),
                         info->name.c_str(), info->inputConfig.string().c_str(),
-                        info->inputFeatures.string().c_str(), toString(info->token != nullptr),
-                        info->applicationInfo.name.c_str(),
+                        toString(info->token != nullptr), info->applicationInfo.name.c_str(),
                         toString(info->applicationInfo.token).c_str());
 }
 
@@ -2787,7 +2785,7 @@
     sp<WindowInfoHandle> focusedWindowHandle = getFocusedWindowHandleLocked(displayId);
     if (focusedWindowHandle != nullptr) {
         const WindowInfo* info = focusedWindowHandle->getInfo();
-        if (info->inputFeatures.test(WindowInfo::Feature::DISABLE_USER_ACTIVITY)) {
+        if (info->inputConfig.test(WindowInfo::InputConfig::DISABLE_USER_ACTIVITY)) {
             if (DEBUG_DISPATCH_CYCLE) {
                 ALOGD("Not poking user activity: disabled by window '%s'.", info->name.c_str());
             }
@@ -4516,7 +4514,7 @@
 bool InputDispatcher::hasResponsiveConnectionLocked(WindowInfoHandle& windowHandle) const {
     sp<Connection> connection = getConnectionLocked(windowHandle.getToken());
     const bool noInputChannel =
-            windowHandle.getInfo()->inputFeatures.test(WindowInfo::Feature::NO_INPUT_CHANNEL);
+            windowHandle.getInfo()->inputConfig.test(WindowInfo::InputConfig::NO_INPUT_CHANNEL);
     if (connection != nullptr && noInputChannel) {
         ALOGW("%s has feature NO_INPUT_CHANNEL, but it matched to connection %s",
               windowHandle.getName().c_str(), connection->inputChannel->getName().c_str());
@@ -4566,7 +4564,7 @@
         const WindowInfo* info = handle->getInfo();
         if (getInputChannelLocked(handle->getToken()) == nullptr) {
             const bool noInputChannel =
-                    info->inputFeatures.test(WindowInfo::Feature::NO_INPUT_CHANNEL);
+                    info->inputConfig.test(WindowInfo::InputConfig::NO_INPUT_CHANNEL);
             const bool canReceiveInput =
                     !info->inputConfig.test(WindowInfo::InputConfig::NOT_TOUCHABLE) ||
                     !info->inputConfig.test(WindowInfo::InputConfig::NOT_FOCUSABLE);
@@ -4632,7 +4630,7 @@
         const WindowInfo& info = *window->getInfo();
 
         // Ensure all tokens are null if the window has feature NO_INPUT_CHANNEL
-        const bool noInputWindow = info.inputFeatures.test(WindowInfo::Feature::NO_INPUT_CHANNEL);
+        const bool noInputWindow = info.inputConfig.test(WindowInfo::InputConfig::NO_INPUT_CHANNEL);
         if (noInputWindow && window->getToken() != nullptr) {
             ALOGE("%s has feature NO_INPUT_WINDOW, but a non-null token. Clearing",
                   window->getName().c_str());
@@ -5209,8 +5207,6 @@
                                          windowInfo->applicationInfo.name.c_str(),
                                          toString(windowInfo->applicationInfo.token).c_str());
                     dump += dumpRegion(windowInfo->touchableRegion);
-                    dump += StringPrintf(", inputFeatures=%s",
-                                         windowInfo->inputFeatures.string().c_str());
                     dump += StringPrintf(", ownerPid=%d, ownerUid=%d, dispatchingTimeout=%" PRId64
                                          "ms, hasToken=%s, "
                                          "touchOcclusionMode=%s\n",
@@ -6248,13 +6244,14 @@
 
 bool InputDispatcher::shouldDropInput(
         const EventEntry& entry, const sp<android::gui::WindowInfoHandle>& windowHandle) const {
-    if (windowHandle->getInfo()->inputFeatures.test(WindowInfo::Feature::DROP_INPUT) ||
-        (windowHandle->getInfo()->inputFeatures.test(WindowInfo::Feature::DROP_INPUT_IF_OBSCURED) &&
+    if (windowHandle->getInfo()->inputConfig.test(WindowInfo::InputConfig::DROP_INPUT) ||
+        (windowHandle->getInfo()->inputConfig.test(
+                 WindowInfo::InputConfig::DROP_INPUT_IF_OBSCURED) &&
          isWindowObscuredLocked(windowHandle))) {
-        ALOGW("Dropping %s event targeting %s as requested by input feature %s on display "
-              "%" PRId32 ".",
+        ALOGW("Dropping %s event targeting %s as requested by the input configuration {%s} on "
+              "display %" PRId32 ".",
               ftl::enum_string(entry.type).c_str(), windowHandle->getName().c_str(),
-              windowHandle->getInfo()->inputFeatures.string().c_str(),
+              windowHandle->getInfo()->inputConfig.string().c_str(),
               windowHandle->getInfo()->displayId);
         return true;
     }
diff --git a/services/inputflinger/tests/InputDispatcher_test.cpp b/services/inputflinger/tests/InputDispatcher_test.cpp
index b3f51ee..b3fea74 100644
--- a/services/inputflinger/tests/InputDispatcher_test.cpp
+++ b/services/inputflinger/tests/InputDispatcher_test.cpp
@@ -991,7 +991,7 @@
         mInfo.ownerPid = INJECTOR_PID;
         mInfo.ownerUid = INJECTOR_UID;
         mInfo.displayId = displayId;
-        mInfo.inputConfig = WindowInfo::InputConfig::NONE;
+        mInfo.inputConfig = WindowInfo::InputConfig::DEFAULT;
     }
 
     sp<FakeWindowHandle> clone(
@@ -1035,6 +1035,24 @@
         mInfo.setInputConfig(WindowInfo::InputConfig::WATCH_OUTSIDE_TOUCH, watchOutside);
     }
 
+    void setSpy(bool spy) { mInfo.setInputConfig(WindowInfo::InputConfig::SPY, spy); }
+
+    void setInterceptsStylus(bool interceptsStylus) {
+        mInfo.setInputConfig(WindowInfo::InputConfig::INTERCEPTS_STYLUS, interceptsStylus);
+    }
+
+    void setDropInput(bool dropInput) {
+        mInfo.setInputConfig(WindowInfo::InputConfig::DROP_INPUT, dropInput);
+    }
+
+    void setDropInputIfObscured(bool dropInputIfObscured) {
+        mInfo.setInputConfig(WindowInfo::InputConfig::DROP_INPUT_IF_OBSCURED, dropInputIfObscured);
+    }
+
+    void setNoInputChannel(bool noInputChannel) {
+        mInfo.setInputConfig(WindowInfo::InputConfig::NO_INPUT_CHANNEL, noInputChannel);
+    }
+
     void setAlpha(float alpha) { mInfo.alpha = alpha; }
 
     void setTouchOcclusionMode(TouchOcclusionMode mode) { mInfo.touchOcclusionMode = mode; }
@@ -1065,8 +1083,6 @@
         mInfo.setInputConfig(WindowInfo::InputConfig::DUPLICATE_TOUCH_TO_WALLPAPER, hasWallpaper);
     }
 
-    void setInputFeatures(Flags<WindowInfo::Feature> features) { mInfo.inputFeatures = features; }
-
     void setTrustedOverlay(bool trustedOverlay) {
         mInfo.setInputConfig(WindowInfo::InputConfig::TRUSTED_OVERLAY, trustedOverlay);
     }
@@ -1219,7 +1235,7 @@
 
     void assertNoEvents() {
         if (mInputReceiver == nullptr &&
-            mInfo.inputFeatures.test(WindowInfo::Feature::NO_INPUT_CHANNEL)) {
+            mInfo.inputConfig.test(WindowInfo::InputConfig::NO_INPUT_CHANNEL)) {
             return; // Can't receive events if the window does not have input channel
         }
         ASSERT_NE(nullptr, mInputReceiver)
@@ -4301,7 +4317,7 @@
                 new FakeWindowHandle(mApplication, mDispatcher, "Spy", ADISPLAY_ID_DEFAULT);
         spy->setTrustedOverlay(true);
         spy->setFocusable(false);
-        spy->setInputFeatures(WindowInfo::Feature::SPY);
+        spy->setSpy(true);
         spy->setDispatchingTimeout(30ms);
         mDispatcher->setInputWindows({{ADISPLAY_ID_DEFAULT, {spy, mWindow}}});
         return spy;
@@ -5094,7 +5110,7 @@
                                               "Window without input channel", ADISPLAY_ID_DEFAULT,
                                               std::make_optional<sp<IBinder>>(nullptr) /*token*/);
 
-        mNoInputWindow->setInputFeatures(WindowInfo::Feature::NO_INPUT_CHANNEL);
+        mNoInputWindow->setNoInputChannel(true);
         mNoInputWindow->setFrame(Rect(0, 0, 100, 100));
         // It's perfectly valid for this window to not have an associated input channel
 
@@ -5136,7 +5152,7 @@
                                           "Window with input channel and NO_INPUT_CHANNEL",
                                           ADISPLAY_ID_DEFAULT);
 
-    mNoInputWindow->setInputFeatures(WindowInfo::Feature::NO_INPUT_CHANNEL);
+    mNoInputWindow->setNoInputChannel(true);
     mNoInputWindow->setFrame(Rect(0, 0, 100, 100));
     mDispatcher->setInputWindows({{ADISPLAY_ID_DEFAULT, {mNoInputWindow, mBottomWindow}}});
 
@@ -6051,7 +6067,7 @@
     std::shared_ptr<FakeApplicationHandle> application = std::make_shared<FakeApplicationHandle>();
     sp<FakeWindowHandle> window =
             new FakeWindowHandle(application, mDispatcher, "Test window", ADISPLAY_ID_DEFAULT);
-    window->setInputFeatures(WindowInfo::Feature::DROP_INPUT);
+    window->setDropInput(true);
     mDispatcher->setFocusedApplication(ADISPLAY_ID_DEFAULT, application);
     window->setFocusable(true);
     mDispatcher->setInputWindows({{ADISPLAY_ID_DEFAULT, {window}}});
@@ -6070,7 +6086,7 @@
     window->assertNoEvents();
 
     // With the flag cleared, the window should get input
-    window->setInputFeatures({});
+    window->setDropInput(false);
     mDispatcher->setInputWindows({{ADISPLAY_ID_DEFAULT, {window}}});
 
     keyArgs = generateKeyArgs(AKEY_EVENT_ACTION_UP, ADISPLAY_ID_DEFAULT);
@@ -6096,7 +6112,7 @@
     std::shared_ptr<FakeApplicationHandle> application = std::make_shared<FakeApplicationHandle>();
     sp<FakeWindowHandle> window =
             new FakeWindowHandle(application, mDispatcher, "Test window", ADISPLAY_ID_DEFAULT);
-    window->setInputFeatures(WindowInfo::Feature::DROP_INPUT_IF_OBSCURED);
+    window->setDropInputIfObscured(true);
     window->setOwnerInfo(222, 222);
     mDispatcher->setFocusedApplication(ADISPLAY_ID_DEFAULT, application);
     window->setFocusable(true);
@@ -6116,7 +6132,7 @@
     window->assertNoEvents();
 
     // With the flag cleared, the window should get input
-    window->setInputFeatures({});
+    window->setDropInputIfObscured(false);
     mDispatcher->setInputWindows({{ADISPLAY_ID_DEFAULT, {obscuringWindow, window}}});
 
     keyArgs = generateKeyArgs(AKEY_EVENT_ACTION_UP, ADISPLAY_ID_DEFAULT);
@@ -6142,7 +6158,7 @@
     std::shared_ptr<FakeApplicationHandle> application = std::make_shared<FakeApplicationHandle>();
     sp<FakeWindowHandle> window =
             new FakeWindowHandle(application, mDispatcher, "Test window", ADISPLAY_ID_DEFAULT);
-    window->setInputFeatures(WindowInfo::Feature::DROP_INPUT_IF_OBSCURED);
+    window->setDropInputIfObscured(true);
     window->setOwnerInfo(222, 222);
     mDispatcher->setFocusedApplication(ADISPLAY_ID_DEFAULT, application);
     window->setFocusable(true);
@@ -6251,7 +6267,7 @@
         name += std::to_string(mSpyCount++);
         sp<FakeWindowHandle> spy =
                 new FakeWindowHandle(application, mDispatcher, name.c_str(), ADISPLAY_ID_DEFAULT);
-        spy->setInputFeatures(WindowInfo::Feature::SPY);
+        spy->setSpy(true);
         spy->setTrustedOverlay(true);
         return spy;
     }
@@ -6699,7 +6715,7 @@
         overlay->setFocusable(false);
         overlay->setOwnerInfo(111, 111);
         overlay->setTouchable(false);
-        overlay->setInputFeatures(WindowInfo::Feature::INTERCEPTS_STYLUS);
+        overlay->setInterceptsStylus(true);
         overlay->setTrustedOverlay(true);
 
         std::shared_ptr<FakeApplicationHandle> application =
@@ -6765,7 +6781,7 @@
 
 TEST_F(InputDispatcherStylusInterceptorTest, SpyWindowStylusInterceptor) {
     auto [overlay, window] = setupStylusOverlayScenario();
-    overlay->setInputFeatures(overlay->getInfo()->inputFeatures | WindowInfo::Feature::SPY);
+    overlay->setSpy(true);
     mDispatcher->setInputWindows({{ADISPLAY_ID_DEFAULT, {overlay, window}}});
 
     sendStylusEvent(AMOTION_EVENT_ACTION_DOWN);
diff --git a/services/surfaceflinger/Layer.cpp b/services/surfaceflinger/Layer.cpp
index 4de8dc2..aeaf1e1 100644
--- a/services/surfaceflinger/Layer.cpp
+++ b/services/surfaceflinger/Layer.cpp
@@ -2266,14 +2266,14 @@
 }
 
 void Layer::handleDropInputMode(gui::WindowInfo& info) const {
-    if (mDrawingState.inputInfo.inputFeatures.test(WindowInfo::Feature::NO_INPUT_CHANNEL)) {
+    if (mDrawingState.inputInfo.inputConfig.test(WindowInfo::InputConfig::NO_INPUT_CHANNEL)) {
         return;
     }
 
     // Check if we need to drop input unconditionally
     gui::DropInputMode dropInputMode = getDropInputMode();
     if (dropInputMode == gui::DropInputMode::ALL) {
-        info.inputFeatures |= WindowInfo::Feature::DROP_INPUT;
+        info.inputConfig |= WindowInfo::InputConfig::DROP_INPUT;
         ALOGV("Dropping input for %s as requested by policy.", getDebugName());
         return;
     }
@@ -2286,7 +2286,7 @@
     // Check if the parent has set an alpha on the layer
     sp<Layer> parent = mDrawingParent.promote();
     if (parent && parent->getAlpha() != 1.0_hf) {
-        info.inputFeatures |= WindowInfo::Feature::DROP_INPUT;
+        info.inputConfig |= WindowInfo::InputConfig::DROP_INPUT;
         ALOGV("Dropping input for %s as requested by policy because alpha=%f", getDebugName(),
               static_cast<float>(getAlpha()));
     }
@@ -2294,7 +2294,7 @@
     // Check if the parent has cropped the buffer
     Rect bufferSize = getCroppedBufferSize(getDrawingState());
     if (!bufferSize.isValid()) {
-        info.inputFeatures |= WindowInfo::Feature::DROP_INPUT_IF_OBSCURED;
+        info.inputConfig |= WindowInfo::InputConfig::DROP_INPUT_IF_OBSCURED;
         return;
     }
 
@@ -2306,7 +2306,7 @@
     bool croppedByParent = bufferInScreenSpace != Rect{mScreenBounds};
 
     if (croppedByParent) {
-        info.inputFeatures |= WindowInfo::Feature::DROP_INPUT;
+        info.inputConfig |= WindowInfo::InputConfig::DROP_INPUT;
         ALOGV("Dropping input for %s as requested by policy because buffer is cropped by parent",
               getDebugName());
     } else {
@@ -2314,7 +2314,7 @@
         // input if the window is obscured. This check should be done in surfaceflinger but the
         // logic currently resides in inputflinger. So pass the if_obscured check to input to only
         // drop input events if the window is obscured.
-        info.inputFeatures |= WindowInfo::Feature::DROP_INPUT_IF_OBSCURED;
+        info.inputConfig |= WindowInfo::InputConfig::DROP_INPUT_IF_OBSCURED;
     }
 }
 
@@ -2323,7 +2323,7 @@
         mDrawingState.inputInfo.name = getName();
         mDrawingState.inputInfo.ownerUid = mOwnerUid;
         mDrawingState.inputInfo.ownerPid = mOwnerPid;
-        mDrawingState.inputInfo.inputFeatures = WindowInfo::Feature::NO_INPUT_CHANNEL;
+        mDrawingState.inputInfo.inputConfig |= WindowInfo::InputConfig::NO_INPUT_CHANNEL;
         mDrawingState.inputInfo.displayId = getLayerStack().id;
     }
 
@@ -2351,7 +2351,7 @@
     // If the window will be blacked out on a display because the display does not have the secure
     // flag and the layer has the secure flag set, then drop input.
     if (!displayIsSecure && isSecure()) {
-        info.inputFeatures |= WindowInfo::Feature::DROP_INPUT;
+        info.inputConfig |= WindowInfo::InputConfig::DROP_INPUT;
     }
 
     auto cropLayer = mDrawingState.touchableRegionCrop.promote();