[pulseaudio-discuss] [PATCH 3/5] bluetooth: fix set_volume_cb on sco over pcm

Tanu Kaskinen tanu.kaskinen at digia.com
Mon Mar 28 05:35:16 PDT 2011


From: Marc-André Lureau <marc-andre.lureau at nokia.com>

The current implementation is totally bogus, it cast the over_sink
userdata to the bluetooth-device userdata... It was failing nicely
because the previous code had a gentle safe-guard in u->profile ==
PROFILE_HSP, and u->profile was just random.

There is no easy way to associate additional data to a sink or
source. Two solutions seems possible: looking up loaded modules and
check which one was handling the sink/source, or using pa_shared. I
went for the second solution.
---
 src/modules/bluetooth/module-bluetooth-device.c |   59 +++++++++++++++++++----
 1 files changed, 50 insertions(+), 9 deletions(-)

diff --git a/src/modules/bluetooth/module-bluetooth-device.c b/src/modules/bluetooth/module-bluetooth-device.c
index 10fb5ed..455a53a 100644
--- a/src/modules/bluetooth/module-bluetooth-device.c
+++ b/src/modules/bluetooth/module-bluetooth-device.c
@@ -39,6 +39,7 @@
 #include <pulsecore/core-rtclock.h>
 #include <pulsecore/core-util.h>
 #include <pulsecore/core-error.h>
+#include <pulsecore/shared.h>
 #include <pulsecore/socket-util.h>
 #include <pulsecore/thread.h>
 #include <pulsecore/thread-mq.h>
@@ -1798,14 +1799,21 @@ fail:
 
 /* Run from main thread */
 static void sink_set_volume_cb(pa_sink *s) {
-    struct userdata *u = s->userdata;
     DBusMessage *m;
     dbus_uint16_t gain;
+    struct userdata *u;
+    char *k;
 
-    pa_assert(u);
+    pa_assert(s);
+    pa_assert(s->core);
 
-    if (u->profile != PROFILE_HSP)
-        return;
+    k = pa_sprintf_malloc("bluetooth-device@%p", (void*) s);
+    u = pa_shared_get(s->core, k);
+    pa_xfree(k);
+
+    pa_assert(u);
+    pa_assert(u->sink == s);
+    pa_assert(u->profile == PROFILE_HSP);
 
     gain = (pa_cvolume_max(&s->real_volume) * 15) / PA_VOLUME_NORM;
 
@@ -1822,14 +1830,21 @@ static void sink_set_volume_cb(pa_sink *s) {
 
 /* Run from main thread */
 static void source_set_volume_cb(pa_source *s) {
-    struct userdata *u = s->userdata;
     DBusMessage *m;
     dbus_uint16_t gain;
+    struct userdata *u;
+    char *k;
 
-    pa_assert(u);
+    pa_assert(s);
+    pa_assert(s->core);
 
-    if (u->profile != PROFILE_HSP)
-        return;
+    k = pa_sprintf_malloc("bluetooth-device@%p", (void*) s);
+    u = pa_shared_get(s->core, k);
+    pa_xfree(k);
+
+    pa_assert(u);
+    pa_assert(u->source == s);
+    pa_assert(u->profile == PROFILE_HSP);
 
     gain = (pa_cvolume_max(&s->volume) * 15) / PA_VOLUME_NORM;
 
@@ -2687,7 +2702,7 @@ int pa__init(pa_module* m) {
     struct userdata *u;
     const char *address, *path;
     DBusError err;
-    char *mike, *speaker, *transport;
+    char *mike, *speaker, *transport, *k;
     const pa_bluetooth_device *device;
 
     pa_assert(m);
@@ -2788,6 +2803,18 @@ int pa__init(pa_module* m) {
     /* Connect to the BT service */
     init_bt(u);
 
+    if (u->hsp.sco_sink) {
+        k = pa_sprintf_malloc("bluetooth-device@%p", (void*) u->hsp.sco_sink);
+        pa_shared_set(u->core, k, u);
+        pa_xfree(k);
+    }
+
+    if (u->hsp.sco_source) {
+        k = pa_sprintf_malloc("bluetooth-device@%p", (void*) u->hsp.sco_source);
+        pa_shared_set(u->core, k, u);
+        pa_xfree(k);
+    }
+
     if (u->profile != PROFILE_OFF)
         if (init_profile(u) < 0)
             goto fail;
@@ -2820,6 +2847,8 @@ int pa__get_n_used(pa_module *m) {
 
 void pa__done(pa_module *m) {
     struct userdata *u;
+    char *k;
+
     pa_assert(m);
 
     if (!(u = m->userdata))
@@ -2860,6 +2889,18 @@ void pa__done(pa_module *m) {
 
     shutdown_bt(u);
 
+    if (u->hsp.sco_sink) {
+        k = pa_sprintf_malloc("bluetooth-device@%p", (void*) u->hsp.sco_sink);
+        pa_shared_remove(u->core, k);
+        pa_xfree(k);
+    }
+
+    if (u->hsp.sco_source) {
+        k = pa_sprintf_malloc("bluetooth-device@%p", (void*) u->hsp.sco_source);
+        pa_shared_remove(u->core, k);
+        pa_xfree(k);
+    }
+
     if (u->a2dp.buffer)
         pa_xfree(u->a2dp.buffer);
 
-- 
1.7.4.1




More information about the pulseaudio-discuss mailing list