[TV Audio] Remove deadlock
authorPrzemyslaw Ciezkowski <p.ciezkowski@samsung.com>
Mon, 16 Feb 2015 11:35:29 +0000 (12:35 +0100)
committerPawel Andruszkiewicz <p.andruszkie@samsung.com>
Wed, 18 Feb 2015 14:44:23 +0000 (23:44 +0900)
When JS tries to call unsetVolumeChangeListener() in VolumeChangeListener
callback, deadlock appears in sound manager.
Solution: call JS callback not from sound_manager callback, but
from g_idle_add() callback.

[Verification]
TCT AudioControlManager_setVolumeChangeListener now doesn't block

Change-Id: I0c1f2b1d0a77b440aa60c376b69daafd9e1be50a
Signed-off-by: Przemyslaw Ciezkowski <p.ciezkowski@samsung.com>
src/tvaudio/tvaudio_manager.cc
src/tvaudio/tvaudio_manager.h

index 63764ef293e1ab92f753b30012d6a192f235e213..bec083aad9037614a2f9408d788f9195189072a3 100755 (executable)
@@ -10,8 +10,6 @@
 #include <sound_manager.h>
 #include <sound_manager_product.h>
 
-#include <glib.h>
-
 #include <fstream> // NOLINT (readability/streams)
 // this flag is no longer enforced in the newest cpplint.py
 
@@ -175,10 +173,17 @@ void AudioControlManager::volumeChangeCallback(
         unsigned int /*volume*/,
         void* /*user_data*/) {
     LOGD("Enter");
+    if (!g_idle_add(onVolumeChange, NULL)) {
+        LOGW("Failed to add to g_idle");
+    }
+}
+
+gboolean AudioControlManager::onVolumeChange(gpointer /*user_data*/) {
+    LOGD("Enter");
     try {
         if (!getInstance().m_volume_change_listener) {
             LOGD("Listener is null. Ignoring");
-            return;
+            return G_SOURCE_REMOVE;
         }
         u_int16_t val;
         try {
@@ -190,6 +195,7 @@ void AudioControlManager::volumeChangeCallback(
     } catch (...) {
         LOGE("Failed to call callback");
     }
+    return G_SOURCE_REMOVE;
 }
 
 /**
index 38161e1d686d1017149d7b4ddc9bf982662f2d2b..2ba27c9d107c3efe36e4494277cf5c0735b91198 100755 (executable)
@@ -2,6 +2,7 @@
 // Use of this source code is governed by a BSD-style license that can be
 // found in the LICENSE file.
 
+#include <glib.h>
 #include <atomic>
 #include <map>
 #include <memory>
@@ -43,6 +44,7 @@ class AudioControlManager {
     void registerVolumeChangeListener(VolumeChangeListener* listener);
     void unregisterVolumeChangeListener();
     static void volumeChangeCallback(unsigned int volume, void* user_data);
+    static gboolean onVolumeChange(gpointer user_data);
 
     // Non-copyable, -assignable, -movable
     AudioControlManager(const AudioControlManager &) = delete;