diff --git a/services/inputflinger/tests/Android.bp b/services/inputflinger/tests/Android.bp
index 58a5c31..af40fed 100644
--- a/services/inputflinger/tests/Android.bp
+++ b/services/inputflinger/tests/Android.bp
@@ -55,6 +55,7 @@
         "LatencyTracker_test.cpp",
         "NotifyArgs_test.cpp",
         "PreferStylusOverTouch_test.cpp",
+        "PropertyProvider_test.cpp",
         "TestInputListener.cpp",
         "UinputDevice.cpp",
         "UnwantedInteractionBlocker_test.cpp",
diff --git a/services/inputflinger/tests/PropertyProvider_test.cpp b/services/inputflinger/tests/PropertyProvider_test.cpp
new file mode 100644
index 0000000..42a6a9f
--- /dev/null
+++ b/services/inputflinger/tests/PropertyProvider_test.cpp
@@ -0,0 +1,286 @@
+/*
+ * Copyright 2023 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.
+ */
+
+#include <gestures/PropertyProvider.h>
+#include <gmock/gmock.h>
+#include <gtest/gtest.h>
+
+#include "include/gestures.h"
+
+namespace android {
+
+using testing::ElementsAre;
+
+class PropertyProviderTest : public testing::Test {
+protected:
+    PropertyProvider mProvider;
+};
+
+TEST_F(PropertyProviderTest, Int_Create) {
+    const size_t COUNT = 4;
+    int intData[COUNT] = {0, 0, 0, 0};
+    int initialValues[COUNT] = {1, 2, 3, 4};
+    gesturePropProvider.create_int_fn(&mProvider, "Some Integers", intData, COUNT, initialValues);
+
+    ASSERT_TRUE(mProvider.hasProperty("Some Integers"));
+    GesturesProp& prop = mProvider.getProperty("Some Integers");
+    EXPECT_EQ(prop.getName(), "Some Integers");
+    EXPECT_EQ(prop.getCount(), COUNT);
+    EXPECT_THAT(intData, ElementsAre(1, 2, 3, 4));
+}
+
+TEST_F(PropertyProviderTest, Int_Get) {
+    const size_t COUNT = 4;
+    int intData[COUNT] = {0, 0, 0, 0};
+    int initialValues[COUNT] = {9, 9, 9, 9};
+    GesturesProp* propPtr = gesturePropProvider.create_int_fn(&mProvider, "Some Integers", intData,
+                                                              COUNT, initialValues);
+
+    // Get handlers are supposed to be called before the property's data is accessed, so they can
+    // update it if necessary. This getter updates the values, so that the ordering can be checked.
+    GesturesPropGetHandler getter{[](void* handlerData) -> GesturesPropBool {
+        int* array = static_cast<int*>(handlerData);
+        array[0] = 1;
+        array[1] = 2;
+        array[2] = 3;
+        array[3] = 4;
+        return true;
+    }};
+    gesturePropProvider.register_handlers_fn(&mProvider, propPtr, /* handler_data= */ intData,
+                                             getter, nullptr);
+
+    ASSERT_TRUE(mProvider.hasProperty("Some Integers"));
+    GesturesProp& prop = mProvider.getProperty("Some Integers");
+    EXPECT_THAT(prop.getIntValues(), ElementsAre(1, 2, 3, 4));
+}
+
+TEST_F(PropertyProviderTest, Int_Set) {
+    const size_t COUNT = 4;
+    int intData[COUNT] = {0, 0, 0, 0};
+    int initialValues[COUNT] = {9, 9, 9, 9};
+    GesturesProp* propPtr = gesturePropProvider.create_int_fn(&mProvider, "Some Integers", intData,
+                                                              COUNT, initialValues);
+
+    struct SetterData {
+        bool setterCalled;
+        int* propertyData;
+    };
+    SetterData setterData = {false, intData};
+    GesturesPropSetHandler setter{[](void* handlerData) {
+        SetterData* data = static_cast<SetterData*>(handlerData);
+        // Set handlers should be called after the property's data has changed, so check the data.
+        EXPECT_EQ(data->propertyData[0], 1);
+        EXPECT_EQ(data->propertyData[1], 2);
+        EXPECT_EQ(data->propertyData[2], 3);
+        EXPECT_EQ(data->propertyData[3], 4);
+        data->setterCalled = true;
+    }};
+    gesturePropProvider.register_handlers_fn(&mProvider, propPtr, /* handler_data= */ &setterData,
+                                             nullptr, setter);
+
+    ASSERT_TRUE(mProvider.hasProperty("Some Integers"));
+    GesturesProp& prop = mProvider.getProperty("Some Integers");
+    prop.setIntValues({1, 2, 3, 4});
+    EXPECT_THAT(intData, ElementsAre(1, 2, 3, 4));
+    EXPECT_TRUE(setterData.setterCalled);
+    EXPECT_THAT(prop.getIntValues(), ElementsAre(1, 2, 3, 4));
+}
+
+TEST_F(PropertyProviderTest, Bool_Create) {
+    const size_t COUNT = 3;
+    GesturesPropBool boolData[COUNT] = {false, false, false};
+    GesturesPropBool initialValues[COUNT] = {true, false, false};
+    gesturePropProvider.create_bool_fn(&mProvider, "Some Booleans", boolData, COUNT, initialValues);
+
+    ASSERT_TRUE(mProvider.hasProperty("Some Booleans"));
+    GesturesProp& prop = mProvider.getProperty("Some Booleans");
+    EXPECT_EQ(prop.getName(), "Some Booleans");
+    EXPECT_EQ(prop.getCount(), COUNT);
+    EXPECT_THAT(boolData, ElementsAre(true, false, false));
+}
+
+TEST_F(PropertyProviderTest, Bool_Get) {
+    const size_t COUNT = 3;
+    GesturesPropBool boolData[COUNT] = {false, false, false};
+    GesturesPropBool initialValues[COUNT] = {true, false, false};
+    GesturesProp* propPtr = gesturePropProvider.create_bool_fn(&mProvider, "Some Booleans",
+                                                               boolData, COUNT, initialValues);
+
+    // Get handlers are supposed to be called before the property's data is accessed, so they can
+    // update it if necessary. This getter updates the values, so that the ordering can be checked.
+    GesturesPropGetHandler getter{[](void* handlerData) -> GesturesPropBool {
+        GesturesPropBool* array = static_cast<GesturesPropBool*>(handlerData);
+        array[0] = false;
+        array[1] = true;
+        array[2] = true;
+        return true;
+    }};
+    gesturePropProvider.register_handlers_fn(&mProvider, propPtr, /* handler_data= */ boolData,
+                                             getter, nullptr);
+
+    ASSERT_TRUE(mProvider.hasProperty("Some Booleans"));
+    GesturesProp& prop = mProvider.getProperty("Some Booleans");
+    EXPECT_THAT(prop.getBoolValues(), ElementsAre(false, true, true));
+}
+
+TEST_F(PropertyProviderTest, Bool_Set) {
+    const size_t COUNT = 3;
+    GesturesPropBool boolData[COUNT] = {false, false, false};
+    GesturesPropBool initialValues[COUNT] = {true, false, false};
+    GesturesProp* propPtr = gesturePropProvider.create_bool_fn(&mProvider, "Some Booleans",
+                                                               boolData, COUNT, initialValues);
+
+    struct SetterData {
+        bool setterCalled;
+        GesturesPropBool* propertyData;
+    };
+    SetterData setterData = {false, boolData};
+    GesturesPropSetHandler setter{[](void* handlerData) {
+        SetterData* data = static_cast<SetterData*>(handlerData);
+        // Set handlers should be called after the property's data has changed, so check the data.
+        EXPECT_EQ(data->propertyData[0], false);
+        EXPECT_EQ(data->propertyData[1], true);
+        EXPECT_EQ(data->propertyData[2], true);
+        data->setterCalled = true;
+    }};
+    gesturePropProvider.register_handlers_fn(&mProvider, propPtr, /* handler_data= */ &setterData,
+                                             nullptr, setter);
+
+    ASSERT_TRUE(mProvider.hasProperty("Some Booleans"));
+    GesturesProp& prop = mProvider.getProperty("Some Booleans");
+    prop.setBoolValues({false, true, true});
+    EXPECT_THAT(boolData, ElementsAre(false, true, true));
+    EXPECT_TRUE(setterData.setterCalled);
+    EXPECT_THAT(prop.getBoolValues(), ElementsAre(false, true, true));
+}
+
+TEST_F(PropertyProviderTest, Real_Create) {
+    const size_t COUNT = 3;
+    double realData[COUNT] = {0.0, 0.0, 0.0};
+    double initialValues[COUNT] = {3.14, 0.7, -5.0};
+    gesturePropProvider.create_real_fn(&mProvider, "Some Reals", realData, COUNT, initialValues);
+
+    ASSERT_TRUE(mProvider.hasProperty("Some Reals"));
+    GesturesProp& prop = mProvider.getProperty("Some Reals");
+    EXPECT_EQ(prop.getName(), "Some Reals");
+    EXPECT_EQ(prop.getCount(), COUNT);
+    EXPECT_THAT(realData, ElementsAre(3.14, 0.7, -5.0));
+}
+
+TEST_F(PropertyProviderTest, Real_Get) {
+    const size_t COUNT = 3;
+    double realData[COUNT] = {0.0, 0.0, 0.0};
+    double initialValues[COUNT] = {-1.0, -1.0, -1.0};
+    GesturesProp* propPtr = gesturePropProvider.create_real_fn(&mProvider, "Some Reals", realData,
+                                                               COUNT, initialValues);
+
+    // Get handlers are supposed to be called before the property's data is accessed, so they can
+    // update it if necessary. This getter updates the values, so that the ordering can be checked.
+    GesturesPropGetHandler getter{[](void* handlerData) -> GesturesPropBool {
+        double* array = static_cast<double*>(handlerData);
+        array[0] = 3.14;
+        array[1] = 0.7;
+        array[2] = -5.0;
+        return true;
+    }};
+    gesturePropProvider.register_handlers_fn(&mProvider, propPtr, /* handler_data= */ realData,
+                                             getter, nullptr);
+
+    ASSERT_TRUE(mProvider.hasProperty("Some Reals"));
+    GesturesProp& prop = mProvider.getProperty("Some Reals");
+    EXPECT_THAT(prop.getRealValues(), ElementsAre(3.14, 0.7, -5.0));
+}
+
+TEST_F(PropertyProviderTest, Real_Set) {
+    const size_t COUNT = 3;
+    double realData[COUNT] = {0.0, 0.0, 0.0};
+    double initialValues[COUNT] = {-1.0, -1.0, -1.0};
+    GesturesProp* propPtr = gesturePropProvider.create_real_fn(&mProvider, "Some Reals", realData,
+                                                               COUNT, initialValues);
+
+    struct SetterData {
+        bool setterCalled;
+        double* propertyData;
+    };
+    SetterData setterData = {false, realData};
+    GesturesPropSetHandler setter{[](void* handlerData) {
+        SetterData* data = static_cast<SetterData*>(handlerData);
+        // Set handlers should be called after the property's data has changed, so check the data.
+        EXPECT_EQ(data->propertyData[0], 3.14);
+        EXPECT_EQ(data->propertyData[1], 0.7);
+        EXPECT_EQ(data->propertyData[2], -5.0);
+        data->setterCalled = true;
+    }};
+    gesturePropProvider.register_handlers_fn(&mProvider, propPtr, /* handler_data= */ &setterData,
+                                             nullptr, setter);
+
+    ASSERT_TRUE(mProvider.hasProperty("Some Reals"));
+    GesturesProp& prop = mProvider.getProperty("Some Reals");
+    prop.setRealValues({3.14, 0.7, -5.0});
+    EXPECT_THAT(realData, ElementsAre(3.14, 0.7, -5.0));
+    EXPECT_TRUE(setterData.setterCalled);
+    EXPECT_THAT(prop.getRealValues(), ElementsAre(3.14, 0.7, -5.0));
+}
+
+TEST_F(PropertyProviderTest, String_Create) {
+    const char* str = nullptr;
+    std::string initialValue = "Foo";
+    gesturePropProvider.create_string_fn(&mProvider, "A String", &str, initialValue.c_str());
+
+    ASSERT_TRUE(mProvider.hasProperty("A String"));
+    GesturesProp& prop = mProvider.getProperty("A String");
+    EXPECT_EQ(prop.getName(), "A String");
+    EXPECT_EQ(prop.getCount(), 1u);
+    EXPECT_STREQ(str, "Foo");
+}
+
+TEST_F(PropertyProviderTest, String_Get) {
+    const char* str = nullptr;
+    std::string initialValue = "Foo";
+    GesturesProp* propPtr = gesturePropProvider.create_string_fn(&mProvider, "A String", &str,
+                                                                 initialValue.c_str());
+
+    // Get handlers are supposed to be called before the property's data is accessed, so they can
+    // update it if necessary. This getter updates the values, so that the ordering can be checked.
+    struct GetterData {
+        const char** strPtr;
+        std::string newValue; // Have to store the new value outside getter so it stays allocated.
+    };
+    GetterData getterData = {&str, "Bar"};
+    GesturesPropGetHandler getter{[](void* handlerData) -> GesturesPropBool {
+        GetterData* data = static_cast<GetterData*>(handlerData);
+        *data->strPtr = data->newValue.c_str();
+        return true;
+    }};
+    gesturePropProvider.register_handlers_fn(&mProvider, propPtr, /* handler_data= */ &getterData,
+                                             getter, nullptr);
+
+    ASSERT_TRUE(mProvider.hasProperty("A String"));
+    GesturesProp& prop = mProvider.getProperty("A String");
+    EXPECT_EQ(prop.getStringValue(), "Bar");
+}
+
+TEST_F(PropertyProviderTest, Free) {
+    int intData = 0;
+    int initialValue = 42;
+    GesturesProp* propPtr =
+            gesturePropProvider.create_int_fn(&mProvider, "Foo", &intData, 1, &initialValue);
+    gesturePropProvider.free_fn(&mProvider, propPtr);
+
+    EXPECT_FALSE(mProvider.hasProperty("Foo"));
+}
+
+} // namespace android
