Skip to content

Commit

Permalink
sfos: bluez5: Wait for NewConnection even if Connect fails.
Browse files Browse the repository at this point in the history
If the initial Connect call fails it is possible that the
headset in question is still starting up and doesn't want
connection from our end just yet. In that case say that we
are connecting and wait for possible NewConnection from
the starting device. In case there isn't going to be any
NewConnection set up a timer to update the backend state.
  • Loading branch information
jusa committed Mar 22, 2019
1 parent 9b2dc55 commit 758a06d
Showing 1 changed file with 56 additions and 0 deletions.
56 changes: 56 additions & 0 deletions src/modules/bluetooth/backend-ofono.c
Expand Up @@ -28,6 +28,8 @@
#include <pulsecore/dbus-shared.h>
#include <pulsecore/shared.h>
#include <pulsecore/core-error.h>
#include <pulse/timeval.h>
#include <pulse/rtclock.h>

#include "bluez5-util.h"

Expand Down Expand Up @@ -70,6 +72,7 @@ struct hf_audio_card {
char *path;
char *remote_address;
char *local_address;
pa_time_event *deferred_time_event;

enum hf_audio_card_state state;
int fd;
Expand All @@ -88,6 +91,8 @@ struct pa_bluetooth_backend {
PA_LLIST_HEAD(pa_dbus_pending, pending);
};

static void cancel_deferred_event(struct hf_audio_card *card);

static pa_dbus_pending* hf_dbus_send_and_add_to_pending(pa_bluetooth_backend *backend, DBusMessage *m,
DBusPendingCallNotifyFunction func, void *call_data) {
pa_dbus_pending *p;
Expand Down Expand Up @@ -118,6 +123,8 @@ static struct hf_audio_card *hf_audio_card_new(pa_bluetooth_backend *backend, co
static void hf_audio_card_free(struct hf_audio_card *card) {
pa_assert(card);

cancel_deferred_event(card);

if (card->transport)
pa_bluetooth_transport_free(card->transport);

Expand Down Expand Up @@ -156,6 +163,40 @@ static int socket_accept(int sock)
return 0;
}

#define DEFERRED_CONNECT_WAIT_TIME ((pa_usec_t) (5 * PA_USEC_PER_SEC))

static void cancel_deferred_event(struct hf_audio_card *card) {
pa_assert(card);

if (card->deferred_time_event) {
pa_log_debug("cancel deferred connect waiting");
card->backend->core->mainloop->time_free(card->deferred_time_event);
card->deferred_time_event = NULL;
}
}

static void deferred_event_cb(pa_mainloop_api *a, pa_time_event *e, const struct timeval *t, void *userdata) {
struct hf_audio_card *card = userdata;

pa_assert(card);

if (card->fd < 0) {
pa_log_debug("deferred event event timer up, card fd is not set");
cancel_deferred_event(card);
pa_bluetooth_transport_set_state(card->transport, PA_BLUETOOTH_TRANSPORT_STATE_DISCONNECTED);
}
}

static void setup_deferred_event(struct hf_audio_card *card) {
pa_assert(card);

cancel_deferred_event(card);
pa_log_debug("setup deferred connect waiting");
card->deferred_time_event = pa_core_rttime_new(card->backend->core,
pa_rtclock_now() + DEFERRED_CONNECT_WAIT_TIME,
deferred_event_cb, card);
}

static int hf_audio_agent_transport_acquire(pa_bluetooth_transport *t, bool optional, size_t *imtu, size_t *omtu) {
struct hf_audio_card *card = t->userdata;
int err;
Expand All @@ -179,6 +220,14 @@ static int hf_audio_agent_transport_acquire(pa_bluetooth_transport *t, bool opti

if (!r) {
pa_log_debug("transport acquire error: %s:%s",derr.name, derr.message);

if (pa_streq(derr.name, "org.ofono.Error.Failed")) {
pa_log_debug("wait for a while if other end will connect to us, return -EAGAIN");
dbus_error_free(&derr);
setup_deferred_event(card);
return -EAGAIN;
}

card->state = HF_AUDIO_CARD_DISCONNECTED;
dbus_error_free(&derr);
return -1;
Expand All @@ -192,6 +241,8 @@ static int hf_audio_agent_transport_acquire(pa_bluetooth_transport *t, bool opti
}
}

cancel_deferred_event(card);

/* The correct block size should take into account the SCO MTU from
* the Bluetooth adapter and (for adapters in the USB bus) the MxPS
* value from the Isoc USB endpoint in use by btusb and should be
Expand Down Expand Up @@ -221,6 +272,8 @@ static void hf_audio_agent_transport_release(pa_bluetooth_transport *t) {

pa_assert(card);

cancel_deferred_event(card);

if (card->fd < 0) {
pa_log_info("Transport %s already released", t->path);
return;
Expand Down Expand Up @@ -561,6 +614,9 @@ static DBusMessage *hf_audio_agent_new_connection(DBusConnection *c, DBusMessage

card = pa_hashmap_get(backend->cards, path);

if (card)
cancel_deferred_event(card);

if (card && card->state == HF_AUDIO_CARD_DISCONNECTED)
pa_log_debug("oFono initiated connection");

Expand Down

0 comments on commit 758a06d

Please sign in to comment.