Log fatal if transaction callbacks are called more than once

Bug: 288781573
Test: presubmits
Change-Id: I424bf89cc3fd52df2460a6028f71b2a988b783b4
diff --git a/libs/gui/SurfaceComposerClient.cpp b/libs/gui/SurfaceComposerClient.cpp
index 5bc05ef..dcadf07 100644
--- a/libs/gui/SurfaceComposerClient.cpp
+++ b/libs/gui/SurfaceComposerClient.cpp
@@ -1901,8 +1901,29 @@
         CallbackId::Type callbackType) {
     auto listener = TransactionCompletedListener::getInstance();
 
-    auto callbackWithContext = std::bind(callback, callbackContext, std::placeholders::_1,
-                                         std::placeholders::_2, std::placeholders::_3);
+    TransactionCompletedCallback callbackWithContext =
+            [called = false, callback,
+             callbackContext](nsecs_t latchTime, const sp<Fence>& presentFence,
+                              const std::vector<SurfaceControlStats>& stats) mutable {
+                if (called) {
+                    std::stringstream stream;
+                    auto it = stats.begin();
+                    if (it != stats.end()) {
+                        stream << it->surfaceControl->getName();
+                        it++;
+                    }
+                    while (it != stats.end()) {
+                        stream << ", " << it->surfaceControl->getName();
+                        it++;
+                    }
+                    LOG_ALWAYS_FATAL("Transaction callback called more than once. SurfaceControls: "
+                                     "%s",
+                                     stream.str().c_str());
+                }
+                callback(callbackContext, latchTime, presentFence, stats);
+                called = true;
+            };
+
     const auto& surfaceControls =
             mListenerCallbacks[TransactionCompletedListener::getIInstance()].surfaceControls;