SurfaceFlinger: add DISPLAY_EVENT_CONFIG_CHANGED

Add a new event to DisplayEventReceiver for display
configuration change. This event is sent by SF when display config
is changed.

Test: adb shell /data/nativetest64/libsurfaceflinger_unittest/libsurfaceflinger_unittest
Bug: 122905403
Change-Id: Ibb7e0ce7b83b91259ccb0e9c982f5e378b0ebfaf
diff --git a/services/surfaceflinger/Scheduler/EventThread.cpp b/services/surfaceflinger/Scheduler/EventThread.cpp
index 4b500f1..78bf7c5 100644
--- a/services/surfaceflinger/Scheduler/EventThread.cpp
+++ b/services/surfaceflinger/Scheduler/EventThread.cpp
@@ -97,6 +97,13 @@
     return event;
 }
 
+DisplayEventReceiver::Event makeConfigChanged(uint32_t displayId, int32_t configId) {
+    DisplayEventReceiver::Event event;
+    event.header = {DisplayEventReceiver::DISPLAY_EVENT_CONFIG_CHANGED, displayId, systemTime()};
+    event.config.configId = configId;
+    return event;
+}
+
 } // namespace
 
 EventThreadConnection::EventThreadConnection(EventThread* eventThread,
@@ -307,6 +314,13 @@
     mCondition.notify_all();
 }
 
+void EventThread::onConfigChanged(PhysicalDisplayId displayId, int32_t configId) {
+    std::lock_guard<std::mutex> lock(mMutex);
+
+    mPendingEvents.push_back(makeConfigChanged(displayId, configId));
+    mCondition.notify_all();
+}
+
 void EventThread::threadMain(std::unique_lock<std::mutex>& lock) {
     DisplayEventConsumers consumers;
 
@@ -404,6 +418,7 @@
                                      const sp<EventThreadConnection>& connection) const {
     switch (event.header.type) {
         case DisplayEventReceiver::DISPLAY_EVENT_HOTPLUG:
+        case DisplayEventReceiver::DISPLAY_EVENT_CONFIG_CHANGED:
             return true;
 
         case DisplayEventReceiver::DISPLAY_EVENT_VSYNC:
diff --git a/services/surfaceflinger/Scheduler/EventThread.h b/services/surfaceflinger/Scheduler/EventThread.h
index 3411438..d5e3349 100644
--- a/services/surfaceflinger/Scheduler/EventThread.h
+++ b/services/surfaceflinger/Scheduler/EventThread.h
@@ -112,6 +112,9 @@
 
     virtual void onHotplugReceived(PhysicalDisplayId displayId, bool connected) = 0;
 
+    // called when SF changes the active config and apps needs to be notified about the change
+    virtual void onConfigChanged(PhysicalDisplayId displayId, int32_t configId) = 0;
+
     virtual void dump(std::string& result) const = 0;
 
     virtual void setPhaseOffset(nsecs_t phaseOffset) = 0;
@@ -153,6 +156,8 @@
 
     void onHotplugReceived(PhysicalDisplayId displayId, bool connected) override;
 
+    void onConfigChanged(PhysicalDisplayId displayId, int32_t configId) override;
+
     void dump(std::string& result) const override;
 
     void setPhaseOffset(nsecs_t phaseOffset) override;
diff --git a/services/surfaceflinger/Scheduler/Scheduler.cpp b/services/surfaceflinger/Scheduler/Scheduler.cpp
index 4f846db..990318a 100644
--- a/services/surfaceflinger/Scheduler/Scheduler.cpp
+++ b/services/surfaceflinger/Scheduler/Scheduler.cpp
@@ -153,6 +153,12 @@
     mConnections[handle->id]->thread->onScreenReleased();
 }
 
+void Scheduler::onConfigChanged(const sp<ConnectionHandle>& handle, PhysicalDisplayId displayId,
+                                int32_t configId) {
+    RETURN_IF_INVALID();
+    mConnections[handle->id]->thread->onConfigChanged(displayId, configId);
+}
+
 void Scheduler::dump(const sp<Scheduler::ConnectionHandle>& handle, std::string& result) const {
     RETURN_IF_INVALID();
     mConnections.at(handle->id)->thread->dump(result);
diff --git a/services/surfaceflinger/Scheduler/Scheduler.h b/services/surfaceflinger/Scheduler/Scheduler.h
index c566922..7f113e7 100644
--- a/services/surfaceflinger/Scheduler/Scheduler.h
+++ b/services/surfaceflinger/Scheduler/Scheduler.h
@@ -105,6 +105,10 @@
     // Should be called before the screen is turned off.
     void onScreenReleased(const sp<ConnectionHandle>& handle);
 
+    // Should be called when display config changed
+    void onConfigChanged(const sp<ConnectionHandle>& handle, PhysicalDisplayId displayId,
+                         int32_t configId);
+
     // Should be called when dumpsys command is received.
     void dump(const sp<ConnectionHandle>& handle, std::string& result) const;