static void ext_connect(GIOChannel *io, GError *err, gpointer user_data) { struct ext_io *conn = user_data; struct ext_profile *ext = conn->ext; struct btd_device *device; bdaddr_t src; char addr[18]; if (!bt_io_get(io, NULL, BT_IO_OPT_SOURCE_BDADDR, &src, BT_IO_OPT_DEST, addr, BT_IO_OPT_INVALID)) { error("Unable to get connect data for %s", ext->name); goto drop; } if (err != NULL) { error("%s failed to connect to %s: %s", ext->name, addr, err->message); goto drop; } DBG("%s connected to %s", ext->name, addr); device = get_btd_dev(&src, addr); if (!device) { error("%s: Unable to get dev object for %s", ext->name, addr); goto drop; } if (conn->io_id == 0) { GIOCondition cond = G_IO_HUP | G_IO_ERR | G_IO_NVAL; conn->io_id = g_io_add_watch(io, cond, ext_io_disconnected, conn); } if (send_new_connection(ext, conn, device)) return; drop: ext->conns = g_slist_remove(ext->conns, conn); ext_io_destroy(conn); }
static gboolean sco_connect_cb(GIOChannel *io, GIOCondition cond, gpointer user_data) { struct ofono_handsfree_card *card = user_data; DBusMessage *reply; int sk; if (agent == NULL) { /* There's no agent, so there's no one to reply to */ reply = NULL; goto done; } if (cond & (G_IO_ERR | G_IO_HUP | G_IO_NVAL)) { if (card->msg) reply = __ofono_error_failed(card->msg); goto done; } sk = g_io_channel_unix_get_fd(io); send_new_connection(card->path, sk, card->selected_codec); close(sk); if (card->msg) reply = dbus_message_new_method_return(card->msg); done: if (card->msg == NULL) return FALSE; if (reply) g_dbus_send_message(ofono_dbus_get_connection(), reply); dbus_message_unref(card->msg); card->msg = NULL; return FALSE; }
static gboolean sco_accept(GIOChannel *io, GIOCondition cond, gpointer user_data) { struct ofono_handsfree_card *card; struct sockaddr_sco saddr; socklen_t alen; int sk, nsk; char local[18], remote[18]; if (cond & (G_IO_ERR | G_IO_HUP | G_IO_NVAL)) return FALSE; sk = g_io_channel_unix_get_fd(io); memset(&saddr, 0, sizeof(saddr)); alen = sizeof(saddr); nsk = accept(sk, (struct sockaddr *) &saddr, &alen); if (nsk < 0) return TRUE; if (agent == NULL) { ofono_error("Reject SCO: Agent not registered"); close(nsk); return TRUE; } bt_ba2str(&saddr.sco_bdaddr, remote); memset(&saddr, 0, sizeof(saddr)); alen = sizeof(saddr); if (getsockname(nsk, (struct sockaddr *) &saddr, &alen) < 0) { ofono_error("SCO getsockname(): %s (%d)", strerror(errno), errno); close(nsk); return TRUE; } bt_ba2str(&saddr.sco_bdaddr, local); card = card_find(remote, local); if (card == NULL || card->path == NULL) { ofono_error("Rejecting SCO: Audio Card not found!"); close(nsk); return TRUE; } if (apply_settings_from_codec(nsk, card->selected_codec) == FALSE) { close(nsk); return TRUE; } DBG("SCO connection setup between local: %s and remote: %s", local, remote); send_new_connection(card->path, nsk, card->selected_codec); close(nsk); if (card->driver->sco_connected_hint) card->driver->sco_connected_hint(card); return TRUE; }