We should not autoswitch to the off profile in case things go wrong. In particular we should not switch to the off profile on startup just because we haven't got the right callbacks from bluez yet, because then the profile will always change from a2dp to off. Signed-off-by: David Henningsson <david.henningsson at canonical.com> --- This is an attempt to fix https://bugs.freedesktop.org/show_bug.cgi?id=87081 but it's probably wrong, because I had to disable what looks like some type of remote "hang up" feature. I don't know anything about this feature and could use some help/feedback/review on how to re-enable it without it being triggered. Anyhow, from a quick test, it seems to be working. src/modules/bluetooth/module-bluez5-device.c | 29 +++++++++++----------------- 1 file changed, 11 insertions(+), 18 deletions(-) diff --git a/src/modules/bluetooth/module-bluez5-device.c b/src/modules/bluetooth/module-bluez5-device.c index e6a8071..a16f9ba 100644 --- a/src/modules/bluetooth/module-bluez5-device.c +++ b/src/modules/bluetooth/module-bluez5-device.c @@ -1857,7 +1857,7 @@ static int set_profile_cb(pa_card *c, pa_card_profile *new_profile) { const pa_bluetooth_device *d = u->device; if (!d->transports[*p] || d->transports[*p]->state <= PA_BLUETOOTH_TRANSPORT_STATE_DISCONNECTED) { - pa_log_warn("Refused to switch profile to %s: Not connected", new_profile->name); + pa_log_info("Refused to switch profile to %s: Not connected", new_profile->name); return -PA_ERR_IO; } } @@ -1879,7 +1879,7 @@ static int set_profile_cb(pa_card *c, pa_card_profile *new_profile) { off: stop_thread(u); - pa_assert_se(pa_card_set_profile(u->card, pa_hashmap_get(u->card->profiles, "off"), false) >= 0); +// pa_assert_se(pa_card_set_profile(u->card, pa_hashmap_get(u->card->profiles, "off"), false) >= 0); return -PA_ERR_IO; } @@ -1968,12 +1968,18 @@ static void handle_transport_state_change(struct userdata *u, struct pa_bluetoot bool release = false; pa_card_profile *cp; pa_device_port *port; + pa_available_t oldavail, newavail; pa_assert(u); pa_assert(t); pa_assert_se(cp = pa_hashmap_get(u->card->profiles, pa_bluetooth_profile_to_string(t->profile))); - pa_card_profile_set_available(cp, transport_state_to_availability(t->state)); + /* Update profile availability and reinitialize profile if necessary */ + oldavail = cp->available; + newavail = transport_state_to_availability(t->state); + pa_card_profile_set_available(cp, newavail); + if (oldavail == PA_AVAILABLE_NO && newavail != PA_AVAILABLE_NO) + set_profile_cb(u->card, cp); /* Update port availability */ pa_assert_se(port = pa_hashmap_get(u->card->ports, u->output_port_name)); @@ -1983,7 +1989,7 @@ static void handle_transport_state_change(struct userdata *u, struct pa_bluetoot /* Acquire or release transport as needed */ acquire = (t->state == PA_BLUETOOTH_TRANSPORT_STATE_PLAYING && u->profile == t->profile); - release = (t->state != PA_BLUETOOTH_TRANSPORT_STATE_PLAYING && u->profile == t->profile); + release = (false && t->state != PA_BLUETOOTH_TRANSPORT_STATE_PLAYING && u->profile == t->profile); if (acquire && transport_acquire(u, true) >= 0) { if (u->source) { @@ -2182,20 +2188,7 @@ int pa__init(pa_module* m) { u->msg->parent.process_msg = device_process_msg; u->msg->card = u->card; - if (u->profile != PA_BLUETOOTH_PROFILE_OFF) - if (init_profile(u) < 0) - goto off; - - if (u->sink || u->source) - if (start_thread(u) < 0) - goto off; - - return 0; - -off: - stop_thread(u); - - pa_assert_se(pa_card_set_profile(u->card, pa_hashmap_get(u->card->profiles, "off"), false) >= 0); + set_profile_cb(u->card, u->card->active_profile); return 0; -- 2.1.3