Linux bluetooth development
 help / color / mirror / Atom feed
* [PATCH BlueZ 02/13] audio: Remove HFP option from audio.conf
From: Luiz Augusto von Dentz @ 2012-11-13 13:21 UTC (permalink / raw)
  To: linux-bluetooth
In-Reply-To: <1352812880-7306-1-git-send-email-luiz.dentz@gmail.com>

From: Luiz Augusto von Dentz <luiz.von.dentz@intel.com>

It is not in use anymore
---
 audio/audio.conf | 4 ----
 audio/manager.c  | 8 --------
 audio/manager.h  | 1 -
 3 files changed, 13 deletions(-)

diff --git a/audio/audio.conf b/audio/audio.conf
index d1c57d3..6bf4482 100644
--- a/audio/audio.conf
+++ b/audio/audio.conf
@@ -25,10 +25,6 @@
 # service interacts with remote headset devices)
 [Headset]
 
-# Set to true to support HFP, false means only HSP is supported
-# Defaults to true
-HFP=true
-
 # Maximum number of connected HSP/HFP devices per adapter. Defaults to 1
 MaxConnected=1
 
diff --git a/audio/manager.c b/audio/manager.c
index 26dde60..e949509 100644
--- a/audio/manager.c
+++ b/audio/manager.c
@@ -90,7 +90,6 @@ static GSList *adapters = NULL;
 static GSList *devices = NULL;
 
 static struct enabled_interfaces enabled = {
-	.hfp		= TRUE,
 	.gateway	= FALSE,
 	.sink		= TRUE,
 	.source		= FALSE,
@@ -674,13 +673,6 @@ int audio_manager_init(GKeyFile *conf, gboolean *enable_sco)
 	} else
 		auto_connect = b;
 
-	b = g_key_file_get_boolean(config, "Headset", "HFP",
-					&err);
-	if (err)
-		g_clear_error(&err);
-	else
-		enabled.hfp = b;
-
 	err = NULL;
 	i = g_key_file_get_integer(config, "Headset", "MaxConnected",
 					&err);
diff --git a/audio/manager.h b/audio/manager.h
index 08d814f..8fb208c 100644
--- a/audio/manager.h
+++ b/audio/manager.h
@@ -23,7 +23,6 @@
  */
 
 struct enabled_interfaces {
-	gboolean hfp;
 	gboolean headset;
 	gboolean gateway;
 	gboolean sink;
-- 
1.7.11.7


^ permalink raw reply related

* [PATCH BlueZ 2/3] avrcp: Fix dead assignments in ct_set_setting
From: Luiz Augusto von Dentz @ 2012-11-13 13:21 UTC (permalink / raw)
  To: linux-bluetooth
In-Reply-To: <1352812880-7306-1-git-send-email-luiz.dentz@gmail.com>

From: Szymon Janc <szymon.janc@tieto.com>

Value stored in val is never read before writing it again. After
fixing val same applies to attr variable.
---
 audio/avrcp.c | 4 ++--
 1 file changed, 2 insertions(+), 2 deletions(-)

diff --git a/audio/avrcp.c b/audio/avrcp.c
index e3ce2fb..2517df8 100644
--- a/audio/avrcp.c
+++ b/audio/avrcp.c
@@ -1944,8 +1944,8 @@ static bool ct_set_setting(struct media_player *mp, const char *key,
 					const char *value, void *user_data)
 {
 	struct avrcp_player *player = user_data;
-	int attr = attr_to_val(key);
-	int val = attrval_to_val(attr, value);
+	int attr;
+	int val;
 	struct avrcp *session;
 
 	session = player->sessions->data;
-- 
1.7.11.7


^ permalink raw reply related

* [PATCH BlueZ 03/13] audio: Remove code using headset
From: Luiz Augusto von Dentz @ 2012-11-13 13:21 UTC (permalink / raw)
  To: linux-bluetooth
In-Reply-To: <1352812880-7306-1-git-send-email-luiz.dentz@gmail.com>

From: Luiz Augusto von Dentz <luiz.von.dentz@intel.com>

This is to be replaced with external profile support.
---
 audio/device.c    | 191 +-----------------------------------------------
 audio/headset.c   |   3 -
 audio/main.c      |  28 +------
 audio/manager.c   |  48 +-----------
 audio/manager.h   |   3 -
 audio/media.c     |  74 +------------------
 audio/transport.c | 215 ------------------------------------------------------
 7 files changed, 9 insertions(+), 553 deletions(-)

diff --git a/audio/device.c b/audio/device.c
index aee4161..aaa666d 100644
--- a/audio/device.c
+++ b/audio/device.c
@@ -53,7 +53,6 @@
 #include "control.h"
 #include "avctp.h"
 #include "avrcp.h"
-#include "headset.h"
 #include "gateway.h"
 #include "sink.h"
 #include "source.h"
@@ -74,7 +73,6 @@ typedef enum {
 struct dev_priv {
 	audio_state_t state;
 
-	headset_state_t hs_state;
 	sink_state_t sink_state;
 	avctp_state_t avctp_state;
 
@@ -92,7 +90,6 @@ struct dev_priv {
 static unsigned int sink_callback_id = 0;
 static unsigned int avctp_callback_id = 0;
 static unsigned int avdtp_callback_id = 0;
-static unsigned int headset_callback_id = 0;
 
 static void device_free(struct audio_device *dev)
 {
@@ -208,8 +205,6 @@ static void disconnect_cb(struct btd_device *btd_dev, gboolean removal,
 
 	if (dev->sink && priv->sink_state != SINK_STATE_DISCONNECTED)
 		sink_shutdown(dev->sink);
-	else if (priv->hs_state != HEADSET_STATE_DISCONNECTED)
-		headset_shutdown(dev);
 	else
 		priv->disconnecting = FALSE;
 }
@@ -270,84 +265,6 @@ static void device_set_state(struct audio_device *dev, audio_state_t new_state)
 				DBUS_TYPE_STRING, &state_str);
 }
 
-static gboolean avdtp_connect_timeout(gpointer user_data)
-{
-	struct audio_device *dev = user_data;
-
-	dev->priv->avdtp_timer = 0;
-
-	if (dev->sink) {
-		struct avdtp *session = avdtp_get(&dev->src, &dev->dst);
-
-		if (!session)
-			return FALSE;
-
-		sink_setup_stream(dev->sink, session);
-		avdtp_unref(session);
-	}
-
-	return FALSE;
-}
-
-static gboolean device_set_avdtp_timer(struct audio_device *dev)
-{
-	struct dev_priv *priv = dev->priv;
-	guint timeout = AVDTP_CONNECT_TIMEOUT;
-
-	if (!dev->sink)
-		return FALSE;
-
-	if (priv->avdtp_timer)
-		return FALSE;
-
-	/* If the headset is the HSP/HFP RFCOMM initiator, give the headset
-	 * time to initiate AVDTP signalling (and avoid further racing) */
-	if (dev->headset && headset_get_rfcomm_initiator(dev))
-		timeout += AVDTP_CONNECT_TIMEOUT_BOOST;
-
-	priv->avdtp_timer = g_timeout_add_seconds(timeout,
-							avdtp_connect_timeout,
-							dev);
-
-	return TRUE;
-}
-
-static gboolean headset_connect_timeout(gpointer user_data)
-{
-	struct audio_device *dev = user_data;
-	struct dev_priv *priv = dev->priv;
-
-	dev->priv->headset_timer = 0;
-
-	if (dev->headset == NULL)
-		return FALSE;
-
-	if (headset_config_stream(dev, FALSE, NULL, NULL) == 0) {
-		if (priv->state != AUDIO_STATE_CONNECTED &&
-				(priv->sink_state == SINK_STATE_CONNECTED ||
-				priv->sink_state == SINK_STATE_PLAYING))
-			device_set_state(dev, AUDIO_STATE_CONNECTED);
-	}
-
-	return FALSE;
-}
-
-static gboolean device_set_headset_timer(struct audio_device *dev)
-{
-	struct dev_priv *priv = dev->priv;
-
-	if (!dev->headset)
-		return FALSE;
-
-	if (priv->headset_timer)
-		return FALSE;
-
-	priv->headset_timer = g_timeout_add_seconds(HEADSET_CONNECT_TIMEOUT,
-						headset_connect_timeout, dev);
-
-	return TRUE;
-}
-
 static void device_avdtp_cb(struct audio_device *dev, struct avdtp *session,
 				avdtp_session_state_t old_state,
 				avdtp_session_state_t new_state,
@@ -382,44 +299,17 @@ static void device_sink_cb(struct audio_device *dev,
 			device_remove_control_timer(dev);
 			avrcp_disconnect(dev);
 		}
-		if (priv->hs_state != HEADSET_STATE_DISCONNECTED &&
-				(priv->dc_req || priv->disconnecting)) {
-			headset_shutdown(dev);
-			break;
-		}
-		if (priv->hs_state == HEADSET_STATE_DISCONNECTED)
-			device_set_state(dev, AUDIO_STATE_DISCONNECTED);
-		else if (old_state == SINK_STATE_CONNECTING) {
-			switch (priv->hs_state) {
-			case HEADSET_STATE_CONNECTED:
-			case HEADSET_STATE_PLAY_IN_PROGRESS:
-			case HEADSET_STATE_PLAYING:
-				device_set_state(dev, AUDIO_STATE_CONNECTED);
-			default:
-				break;
-			}
-		}
+
+		device_set_state(dev, AUDIO_STATE_DISCONNECTED);
 		break;
 	case SINK_STATE_CONNECTING:
 		device_remove_avdtp_timer(dev);
-		if (priv->hs_state == HEADSET_STATE_DISCONNECTED)
-			device_set_state(dev, AUDIO_STATE_CONNECTING);
+		device_set_state(dev, AUDIO_STATE_CONNECTING);
 		break;
 	case SINK_STATE_CONNECTED:
 		if (old_state == SINK_STATE_PLAYING)
 			break;
-		if (dev->auto_connect) {
-			if (!dev->headset)
-				device_set_state(dev, AUDIO_STATE_CONNECTED);
-			else if (priv->hs_state == HEADSET_STATE_DISCONNECTED)
-				device_set_headset_timer(dev);
-			else if (priv->hs_state == HEADSET_STATE_CONNECTED ||
-					priv->hs_state == HEADSET_STATE_PLAY_IN_PROGRESS ||
-					priv->hs_state == HEADSET_STATE_PLAYING)
-				device_set_state(dev, AUDIO_STATE_CONNECTED);
-		} else if (priv->hs_state == HEADSET_STATE_DISCONNECTED ||
-				priv->hs_state == HEADSET_STATE_CONNECTING)
-			device_set_state(dev, AUDIO_STATE_CONNECTED);
+		device_set_state(dev, AUDIO_STATE_CONNECTED);
 		break;
 	case SINK_STATE_PLAYING:
 		break;
@@ -447,62 +337,6 @@ static void device_avctp_cb(struct audio_device *dev,
 	}
 }
 
-static void device_headset_cb(struct audio_device *dev,
-				headset_state_t old_state,
-				headset_state_t new_state,
-				void *user_data)
-{
-	struct dev_priv *priv = dev->priv;
-
-	if (!dev->headset)
-		return;
-
-	priv->hs_state = new_state;
-
-	switch (new_state) {
-	case HEADSET_STATE_DISCONNECTED:
-		device_remove_avdtp_timer(dev);
-		if (priv->sink_state != SINK_STATE_DISCONNECTED && dev->sink &&
-				(priv->dc_req || priv->disconnecting)) {
-			sink_shutdown(dev->sink);
-			break;
-		}
-		if (priv->sink_state == SINK_STATE_DISCONNECTED)
-			device_set_state(dev, AUDIO_STATE_DISCONNECTED);
-		else if (old_state == HEADSET_STATE_CONNECTING &&
-				(priv->sink_state == SINK_STATE_CONNECTED ||
-				priv->sink_state == SINK_STATE_PLAYING))
-			device_set_state(dev, AUDIO_STATE_CONNECTED);
-		break;
-	case HEADSET_STATE_CONNECTING:
-		device_remove_headset_timer(dev);
-		if (priv->sink_state == SINK_STATE_DISCONNECTED)
-			device_set_state(dev, AUDIO_STATE_CONNECTING);
-		break;
-	case HEADSET_STATE_CONNECTED:
-		if (old_state == HEADSET_STATE_CONNECTED ||
-				old_state == HEADSET_STATE_PLAY_IN_PROGRESS ||
-				old_state == HEADSET_STATE_PLAYING)
-			break;
-		if (dev->auto_connect) {
-			if (!dev->sink)
-				device_set_state(dev, AUDIO_STATE_CONNECTED);
-			else if (priv->sink_state == SINK_STATE_DISCONNECTED)
-				device_set_avdtp_timer(dev);
-			else if (priv->sink_state == SINK_STATE_CONNECTED ||
-					priv->sink_state == SINK_STATE_PLAYING)
-				device_set_state(dev, AUDIO_STATE_CONNECTED);
-		} else if (priv->sink_state == SINK_STATE_DISCONNECTED ||
-				priv->sink_state == SINK_STATE_CONNECTING)
-			device_set_state(dev, AUDIO_STATE_CONNECTED);
-		break;
-	case HEADSET_STATE_PLAY_IN_PROGRESS:
-		break;
-	case HEADSET_STATE_PLAYING:
-		break;
-	}
-}
-
 static DBusMessage *dev_connect(DBusConnection *conn, DBusMessage *msg,
 								void *data)
 {
@@ -516,9 +350,6 @@ static DBusMessage *dev_connect(DBusConnection *conn, DBusMessage *msg,
 
 	dev->auto_connect = TRUE;
 
-	if (dev->headset)
-		headset_config_stream(dev, FALSE, NULL, NULL);
-
 	if (priv->state != AUDIO_STATE_CONNECTING && dev->sink) {
 		struct avdtp *session = avdtp_get(&dev->src, &dev->dst);
 
@@ -561,8 +392,6 @@ static DBusMessage *dev_disconnect(DBusConnection *conn, DBusMessage *msg,
 
 	if (dev->sink && priv->sink_state != SINK_STATE_DISCONNECTED)
 		sink_shutdown(dev->sink);
-	else if (priv->hs_state != HEADSET_STATE_DISCONNECTED)
-		headset_shutdown(dev);
 	else {
 		dbus_message_unref(priv->dc_req);
 		priv->dc_req = NULL;
@@ -652,10 +481,6 @@ struct audio_device *audio_device_register(struct btd_device *device,
 	if (avctp_callback_id == 0)
 		avctp_callback_id = avctp_add_state_cb(device_avctp_cb, NULL);
 
-	if (headset_callback_id == 0)
-		headset_callback_id = headset_add_state_cb(device_headset_cb,
-									NULL);
-
 	return dev;
 }
 
@@ -666,17 +491,12 @@ gboolean audio_device_is_active(struct audio_device *dev,
 		if ((dev->sink || dev->source) &&
 				avdtp_is_connected(&dev->src, &dev->dst))
 			return TRUE;
-		if (dev->headset && headset_is_active(dev))
-			return TRUE;
 	} else if (!strcmp(interface, AUDIO_SINK_INTERFACE) && dev->sink &&
 				avdtp_is_connected(&dev->src, &dev->dst))
 		return TRUE;
 	else if (!strcmp(interface, AUDIO_SOURCE_INTERFACE) && dev->source &&
 				avdtp_is_connected(&dev->src, &dev->dst))
 		return TRUE;
-	else if (!strcmp(interface, AUDIO_HEADSET_INTERFACE) && dev->headset &&
-				headset_is_active(dev))
-		return TRUE;
 	else if (!strcmp(interface, AUDIO_CONTROL_INTERFACE) && dev->control &&
 				control_is_active(dev))
 		return TRUE;
@@ -694,9 +514,6 @@ void audio_device_unregister(struct audio_device *device)
 		device->hs_preauth_id = 0;
 	}
 
-	if (device->headset)
-		headset_unregister(device);
-
 	if (device->gateway)
 		gateway_unregister(device);
 
diff --git a/audio/headset.c b/audio/headset.c
index 5e42a61..fb660f5 100644
--- a/audio/headset.c
+++ b/audio/headset.c
@@ -1614,9 +1614,6 @@ static int rfcomm_connect(struct audio_device *dev, headset_stream_cb_t cb,
 	char address[18];
 	GError *err = NULL;
 
-	if (!manager_allow_headset_connection(dev))
-		return -ECONNREFUSED;
-
 	if (hs->rfcomm_ch < 0)
 		return get_records(dev, cb, user_data, cb_id);
 
diff --git a/audio/main.c b/audio/main.c
index f7bb32a..a423b79 100644
--- a/audio/main.c
+++ b/audio/main.c
@@ -42,7 +42,6 @@
 #include "plugin.h"
 #include "log.h"
 #include "device.h"
-#include "headset.h"
 #include "manager.h"
 #include "gateway.h"
 
@@ -89,36 +88,12 @@ static void sco_server_cb(GIOChannel *chan, GError *err, gpointer data)
 		goto drop;
 	}
 
-	device = manager_find_device(NULL, &src, &dst, AUDIO_HEADSET_INTERFACE,
-					FALSE);
-	if (!device)
-		device = manager_find_device(NULL, &src, &dst,
+	device = manager_find_device(NULL, &src, &dst,
 						AUDIO_GATEWAY_INTERFACE,
 						FALSE);
-
 	if (!device)
 		goto drop;
 
-	if (device->headset) {
-		if (headset_get_state(device) < HEADSET_STATE_CONNECTED) {
-			DBG("Refusing SCO from non-connected headset");
-			goto gateway;
-		}
-
-		if (!headset_get_hfp_active(device)) {
-			error("Refusing non-HFP SCO connect attempt from %s",
-									addr);
-			goto drop;
-		}
-
-		if (headset_connect_sco(device, chan) < 0)
-			goto drop;
-
-		headset_set_state(device, HEADSET_STATE_PLAYING);
-		goto connect;
-	}
-
-gateway:
 	if (device->gateway) {
 		if (!gateway_is_connected(device)) {
 			DBG("Refusing SCO from non-connected AG");
@@ -130,7 +105,6 @@ gateway:
 	} else
 		goto drop;
 
-connect:
 	sk = g_io_channel_unix_get_fd(chan);
 	fcntl(sk, F_SETFL, 0);
 
diff --git a/audio/manager.c b/audio/manager.c
index e949509..d151f16 100644
--- a/audio/manager.c
+++ b/audio/manager.c
@@ -61,7 +61,6 @@
 #include "avdtp.h"
 #include "media.h"
 #include "a2dp.h"
-#include "headset.h"
 #include "gateway.h"
 #include "sink.h"
 #include "source.h"
@@ -637,9 +636,7 @@ int audio_manager_init(GKeyFile *conf, gboolean *enable_sco)
 	list = g_key_file_get_string_list(config, "General", "Enable",
 						NULL, NULL);
 	for (i = 0; list && list[i] != NULL; i++) {
-		if (g_str_equal(list[i], "Headset"))
-			enabled.headset = TRUE;
-		else if (g_str_equal(list[i], "Gateway"))
+		if (g_str_equal(list[i], "Gateway"))
 			enabled.gateway = TRUE;
 		else if (g_str_equal(list[i], "Sink"))
 			enabled.sink = TRUE;
@@ -653,9 +650,7 @@ int audio_manager_init(GKeyFile *conf, gboolean *enable_sco)
 	list = g_key_file_get_string_list(config, "General", "Disable",
 						NULL, NULL);
 	for (i = 0; list && list[i] != NULL; i++) {
-		if (g_str_equal(list[i], "Headset"))
-			enabled.headset = FALSE;
-		else if (g_str_equal(list[i], "Gateway"))
+		if (g_str_equal(list[i], "Gateway"))
 			enabled.gateway = FALSE;
 		else if (g_str_equal(list[i], "Sink"))
 			enabled.sink = FALSE;
@@ -694,7 +689,7 @@ proceed:
 
 	btd_register_adapter_driver(&media_driver);
 
-	*enable_sco = (enabled.gateway || enabled.headset);
+	*enable_sco = enabled.gateway;
 
 	return 0;
 }
@@ -740,10 +735,6 @@ GSList *manager_find_devices(const char *path,
 		if ((dst && bacmp(dst, BDADDR_ANY)) && bacmp(&dev->dst, dst))
 			continue;
 
-		if (interface && !strcmp(AUDIO_HEADSET_INTERFACE, interface)
-				&& !dev->headset)
-			continue;
-
 		if (interface && !strcmp(AUDIO_GATEWAY_INTERFACE, interface)
 				&& !dev->gateway)
 			continue;
@@ -829,43 +820,10 @@ struct audio_device *manager_get_device(const bdaddr_t *src,
 	return dev;
 }
 
-gboolean manager_allow_headset_connection(struct audio_device *device)
-{
-	GSList *l;
-	int connected = 0;
-
-	for (l = devices; l != NULL; l = l->next) {
-		struct audio_device *dev = l->data;
-		struct headset *hs = dev->headset;
-
-		if (dev == device)
-			continue;
-
-		if (device && bacmp(&dev->src, &device->src) != 0)
-			continue;
-
-		if (!hs)
-			continue;
-
-		if (headset_get_state(dev) > HEADSET_STATE_DISCONNECTED)
-			connected++;
-
-		if (connected >= max_connected_headsets)
-			return FALSE;
-	}
-
-	return TRUE;
-}
-
 void manager_set_fast_connectable(gboolean enable)
 {
 	GSList *l;
 
-	if (enable && !manager_allow_headset_connection(NULL)) {
-		DBG("Refusing enabling fast connectable");
-		return;
-	}
-
 	for (l = adapters; l != NULL; l = l->next) {
 		struct audio_adapter *adapter = l->data;
 
diff --git a/audio/manager.h b/audio/manager.h
index 8fb208c..d3b5692 100644
--- a/audio/manager.h
+++ b/audio/manager.h
@@ -23,7 +23,6 @@
  */
 
 struct enabled_interfaces {
-	gboolean headset;
 	gboolean gateway;
 	gboolean sink;
 	gboolean source;
@@ -50,8 +49,6 @@ struct audio_device *manager_get_device(const bdaddr_t *src,
 					const bdaddr_t *dst,
 					gboolean create);
 
-gboolean manager_allow_headset_connection(struct audio_device *device);
-
 /* TRUE to enable fast connectable and FALSE to disable fast connectable for all
  * audio adapters. */
 void manager_set_fast_connectable(gboolean enable);
diff --git a/audio/media.c b/audio/media.c
index cec938a..ea0b44e 100644
--- a/audio/media.c
+++ b/audio/media.c
@@ -46,7 +46,6 @@
 #include "transport.h"
 #include "a2dp.h"
 #include "avrcp.h"
-#include "headset.h"
 #include "gateway.h"
 #include "manager.h"
 
@@ -141,9 +140,6 @@ static void media_endpoint_destroy(struct media_endpoint *endpoint)
 {
 	DBG("sender=%s path=%s", endpoint->sender, endpoint->path);
 
-	if (endpoint->hs_watch)
-		headset_remove_state_cb(endpoint->hs_watch);
-
 	if (endpoint->ag_watch)
 		gateway_remove_state_cb(endpoint->ag_watch);
 
@@ -185,17 +181,6 @@ static void media_endpoint_exit(DBusConnection *connection, void *user_data)
 	media_endpoint_remove(endpoint);
 }
 
-static void headset_setconf_cb(struct media_endpoint *endpoint, void *ret,
-						int size, void *user_data)
-{
-	struct audio_device *dev = user_data;
-
-	if (ret != NULL)
-		return;
-
-	headset_shutdown(dev);
-}
-
 static void clear_configuration(struct media_endpoint *endpoint,
 					struct media_transport *transport)
 {
@@ -449,41 +434,6 @@ done:
 	media_endpoint_remove(endpoint);
 }
 
-static void headset_state_changed(struct audio_device *dev,
-					headset_state_t old_state,
-					headset_state_t new_state,
-					void *user_data)
-{
-	struct media_endpoint *endpoint = user_data;
-	struct media_transport *transport;
-
-	DBG("");
-
-	if (bacmp(&endpoint->adapter->src, &dev->src) != 0)
-		return;
-
-	switch (new_state) {
-	case HEADSET_STATE_DISCONNECTED:
-		transport = find_device_transport(endpoint, dev);
-
-		if (transport != NULL) {
-			DBG("Clear endpoint %p", endpoint);
-			clear_configuration(endpoint, transport);
-		}
-		break;
-	case HEADSET_STATE_CONNECTING:
-		set_configuration(endpoint, dev, NULL, 0, headset_setconf_cb,
-								dev, NULL);
-		break;
-	case HEADSET_STATE_CONNECTED:
-		break;
-	case HEADSET_STATE_PLAY_IN_PROGRESS:
-		break;
-	case HEADSET_STATE_PLAYING:
-		break;
-	}
-}
-
 static const char *get_name(struct a2dp_sep *sep, void *user_data)
 {
 	struct media_endpoint *endpoint = user_data;
@@ -671,28 +621,6 @@ static gboolean endpoint_init_a2dp_sink(struct media_endpoint *endpoint,
 	return TRUE;
 }
 
-static gboolean endpoint_init_ag(struct media_endpoint *endpoint, int *err)
-{
-	GSList *list;
-	GSList *l;
-
-	endpoint->hs_watch = headset_add_state_cb(headset_state_changed,
-								endpoint);
-	list = manager_find_devices(NULL, &endpoint->adapter->src, BDADDR_ANY,
-						AUDIO_HEADSET_INTERFACE, TRUE);
-
-	for (l = list; l != NULL; l = l->next) {
-		struct audio_device *dev = l->data;
-
-		set_configuration(endpoint, dev, NULL, 0,
-						headset_setconf_cb, dev, NULL);
-	}
-
-	g_slist_free(list);
-
-	return TRUE;
-}
-
 static gboolean endpoint_init_hs(struct media_endpoint *endpoint, int *err)
 {
 	GSList *list;
@@ -750,7 +678,7 @@ static struct media_endpoint *media_endpoint_create(struct media_adapter *adapte
 							delay_reporting, err);
 	else if (strcasecmp(uuid, HFP_AG_UUID) == 0 ||
 					strcasecmp(uuid, HSP_AG_UUID) == 0)
-		succeeded = endpoint_init_ag(endpoint, err);
+		succeeded = TRUE;
 	else if (strcasecmp(uuid, HFP_HS_UUID) == 0 ||
 					strcasecmp(uuid, HSP_HS_UUID) == 0)
 		succeeded = endpoint_init_hs(endpoint, err);
diff --git a/audio/transport.c b/audio/transport.c
index 7ad7033..74562ea 100644
--- a/audio/transport.c
+++ b/audio/transport.c
@@ -44,7 +44,6 @@
 #include "media.h"
 #include "transport.h"
 #include "a2dp.h"
-#include "headset.h"
 #include "gateway.h"
 #include "sink.h"
 #include "source.h"
@@ -212,9 +211,6 @@ void media_transport_destroy(struct media_transport *transport)
 {
 	char *path;
 
-	if (transport->hs_watch)
-		headset_remove_state_cb(transport->hs_watch);
-
 	if (transport->ag_watch)
 		gateway_remove_state_cb(transport->ag_watch);
 
@@ -465,116 +461,6 @@ static void cancel_a2dp(struct media_transport *transport, guint id)
 	a2dp_cancel(transport->device, id);
 }
 
-static void headset_resume_complete(struct audio_device *dev, void *user_data)
-{
-	struct media_owner *owner = user_data;
-	struct media_request *req = owner->pending;
-	struct media_transport *transport = owner->transport;
-	int fd;
-	uint16_t imtu, omtu;
-	gboolean ret;
-
-	req->id = 0;
-
-	if (dev == NULL)
-		goto fail;
-
-	fd = headset_get_sco_fd(dev);
-	if (fd < 0)
-		goto fail;
-
-	imtu = 48;
-	omtu = 48;
-
-	media_transport_set_fd(transport, fd, imtu, omtu);
-
-	if ((owner->lock & TRANSPORT_LOCK_READ) == 0)
-		imtu = 0;
-
-	if ((owner->lock & TRANSPORT_LOCK_WRITE) == 0)
-		omtu = 0;
-
-	ret = g_dbus_send_reply(btd_get_dbus_connection(), req->msg,
-						DBUS_TYPE_UNIX_FD, &fd,
-						DBUS_TYPE_UINT16, &imtu,
-						DBUS_TYPE_UINT16, &omtu,
-						DBUS_TYPE_INVALID);
-	if (ret == FALSE)
-		goto fail;
-
-	media_owner_remove(owner);
-
-	transport_set_state(transport, TRANSPORT_STATE_ACTIVE);
-
-	return;
-
-fail:
-	media_transport_remove(transport, owner);
-}
-
-static guint resume_headset(struct media_transport *transport,
-				struct media_owner *owner)
-{
-	struct audio_device *device = transport->device;
-
-	if (state_in_use(transport->state))
-		goto done;
-
-	if (headset_lock(device, HEADSET_LOCK_READ |
-						HEADSET_LOCK_WRITE) == FALSE)
-		return 0;
-
-	if (transport->state == TRANSPORT_STATE_IDLE)
-		transport_set_state(transport, TRANSPORT_STATE_REQUESTING);
-
-done:
-	return headset_request_stream(device, headset_resume_complete,
-					owner);
-}
-
-static void headset_suspend_complete(struct audio_device *dev, void *user_data)
-{
-	struct media_owner *owner = user_data;
-	struct media_transport *transport = owner->transport;
-
-	/* Release always succeeds */
-	if (owner->pending) {
-		owner->pending->id = 0;
-		media_request_reply(owner->pending, 0);
-		media_owner_remove(owner);
-	}
-
-	headset_unlock(dev, HEADSET_LOCK_READ | HEADSET_LOCK_WRITE);
-	transport_set_state(transport, TRANSPORT_STATE_IDLE);
-	media_transport_remove(transport, owner);
-}
-
-static guint suspend_headset(struct media_transport *transport,
-						struct media_owner *owner)
-{
-	struct audio_device *device = transport->device;
-
-	if (!owner) {
-		headset_state_t state = headset_get_state(device);
-
-		headset_unlock(device, HEADSET_LOCK_READ | HEADSET_LOCK_WRITE);
-
-		if (state == HEADSET_STATE_PLAYING)
-			transport_set_state(transport, TRANSPORT_STATE_PENDING);
-		else
-			transport_set_state(transport, TRANSPORT_STATE_IDLE);
-
-		return 0;
-	}
-
-	return headset_suspend_stream(device, headset_suspend_complete, owner);
-}
-
-static void cancel_headset(struct media_transport *transport, guint id)
-{
-	headset_cancel_stream(transport->device, id);
-}
-
 static void gateway_resume_complete(struct audio_device *dev, GError *err,
 							void *user_data)
 {
@@ -920,33 +806,6 @@ static int set_property_a2dp(struct media_transport *transport,
 	return -EINVAL;
 }
 
-static int set_property_headset(struct media_transport *transport,
-						const char *property,
-						DBusMessageIter *value)
-{
-	if (g_strcmp0(property, "NREC") == 0) {
-		gboolean nrec;
-
-		if (dbus_message_iter_get_arg_type(value) != DBUS_TYPE_BOOLEAN)
-			return -EINVAL;
-		dbus_message_iter_get_basic(value, &nrec);
-
-		/* FIXME: set new nrec */
-		return 0;
-	} else if (g_strcmp0(property, "InbandRingtone") == 0) {
-		gboolean inband;
-
-		if (dbus_message_iter_get_arg_type(value) != DBUS_TYPE_BOOLEAN)
-			return -EINVAL;
-		dbus_message_iter_get_basic(value, &inband);
-
-		/* FIXME: set new inband */
-		return 0;
-	}
-
-	return -EINVAL;
-}
-
 static int set_property_gateway(struct media_transport *transport,
 						const char *property,
 						DBusMessageIter *value)
@@ -1012,22 +871,6 @@ static void get_properties_a2dp(struct media_transport *transport,
 							&a2dp->volume);
 }
 
-static void get_properties_headset(struct media_transport *transport,
-						DBusMessageIter *dict)
-{
-	gboolean nrec, inband;
-	const char *routing;
-
-	nrec = headset_get_nrec(transport->device);
-	dict_append_entry(dict, "NREC", DBUS_TYPE_BOOLEAN, &nrec);
-
-	inband = headset_get_inband(transport->device);
-	dict_append_entry(dict, "InbandRingtone", DBUS_TYPE_BOOLEAN, &inband);
-
-	routing = headset_get_sco_hci(transport->device) ? "HCI" : "PCM";
-	dict_append_entry(dict, "Routing", DBUS_TYPE_STRING, &routing);
-}
-
 static void get_properties_gateway(struct media_transport *transport,
 						DBusMessageIter *dict)
 {
@@ -1123,16 +966,6 @@ static void destroy_a2dp(void *data)
 	g_free(a2dp);
 }
 
-static void destroy_headset(void *data)
-{
-	struct headset_transport *headset = data;
-
-	if (headset->nrec_id > 0)
-		headset_remove_nrec_cb(headset->device, headset->nrec_id);
-
-	g_free(headset);
-}
-
 static void media_transport_free(void *data)
 {
 	struct media_transport *transport = data;
@@ -1154,18 +987,6 @@ static void media_transport_free(void *data)
 	g_free(transport);
 }
 
-static void headset_nrec_changed(struct audio_device *dev, gboolean nrec,
-							void *user_data)
-{
-	struct media_transport *transport = user_data;
-
-	DBG("");
-
-	emit_property_changed(transport->path,
-				MEDIA_TRANSPORT_INTERFACE, "NREC",
-				DBUS_TYPE_BOOLEAN, &nrec);
-}
-
 static void transport_update_playing(struct media_transport *transport,
 							gboolean playing)
 {
@@ -1188,22 +1009,6 @@ static void transport_update_playing(struct media_transport *transport,
 		transport_set_state(transport, TRANSPORT_STATE_PENDING);
 }
 
-static void headset_state_changed(struct audio_device *dev,
-						headset_state_t old_state,
-						headset_state_t new_state,
-						void *user_data)
-{
-	struct media_transport *transport = user_data;
-
-	if (dev != transport->device)
-		return;
-
-	if (new_state == HEADSET_STATE_PLAYING)
-		transport_update_playing(transport, TRUE);
-	else
-		transport_update_playing(transport, FALSE);
-}
-
 static void gateway_state_changed(struct audio_device *dev,
 						gateway_state_t old_state,
 						gateway_state_t new_state,
@@ -1295,26 +1100,6 @@ struct media_transport *media_transport_create(struct media_endpoint *endpoint,
 			transport->source_watch = source_add_state_cb(
 							source_state_changed,
 							transport);
-	} else if (strcasecmp(uuid, HFP_AG_UUID) == 0 ||
-			strcasecmp(uuid, HSP_AG_UUID) == 0) {
-		struct headset_transport *headset;
-
-		headset = g_new0(struct headset_transport, 1);
-		headset->device = device;
-		headset->nrec_id = headset_add_nrec_cb(device,
-							headset_nrec_changed,
-							transport);
-
-		transport->resume = resume_headset;
-		transport->suspend = suspend_headset;
-		transport->cancel = cancel_headset;
-		transport->get_properties = get_properties_headset;
-		transport->set_property = set_property_headset;
-		transport->data = headset;
-		transport->destroy = destroy_headset;
-		transport->hs_watch = headset_add_state_cb(
-							headset_state_changed,
-							transport);
 	} else if (strcasecmp(uuid, HFP_HS_UUID) == 0 ||
 			strcasecmp(uuid, HSP_HS_UUID) == 0) {
 		transport->resume = resume_gateway;
-- 
1.7.11.7


^ permalink raw reply related

* [PATCH BlueZ 3/3] network: Fix dead assignment in connect_cb
From: Luiz Augusto von Dentz @ 2012-11-13 13:21 UTC (permalink / raw)
  To: linux-bluetooth
In-Reply-To: <1352812880-7306-1-git-send-email-luiz.dentz@gmail.com>

From: Szymon Janc <szymon.janc@tieto.com>

Value stored to err_msg is never read in case err was not NULL.
Simply remove err_msg and pass strerror() directly where it is used.
---
 profiles/network/connection.c | 5 +----
 1 file changed, 1 insertion(+), 4 deletions(-)

diff --git a/profiles/network/connection.c b/profiles/network/connection.c
index abcbee8..1a1fb4d 100644
--- a/profiles/network/connection.c
+++ b/profiles/network/connection.c
@@ -371,19 +371,16 @@ static int bnep_connect(struct network_conn *nc)
 static void connect_cb(GIOChannel *chan, GError *err, gpointer data)
 {
 	struct network_conn *nc = data;
-	const char *err_msg;
 	int perr;
 
 	if (err) {
 		error("%s", err->message);
-		err_msg = err->message;
 		goto failed;
 	}
 
 	perr = bnep_connect(nc);
 	if (perr < 0) {
-		err_msg = strerror(-perr);
-		error("bnep connect(): %s (%d)", err_msg, -perr);
+		error("bnep connect(): %s (%d)", strerror(-perr), -perr);
 		goto failed;
 	}
 
-- 
1.7.11.7


^ permalink raw reply related

* [PATCH BlueZ 04/13] build: Remove telephony-maemo5.c
From: Luiz Augusto von Dentz @ 2012-11-13 13:21 UTC (permalink / raw)
  To: linux-bluetooth
In-Reply-To: <1352812880-7306-1-git-send-email-luiz.dentz@gmail.com>

From: Luiz Augusto von Dentz <luiz.von.dentz@intel.com>

---
 Makefile.am              |    4 +-
 audio/telephony-maemo5.c | 2102 ----------------------------------------------
 2 files changed, 2 insertions(+), 2104 deletions(-)
 delete mode 100644 audio/telephony-maemo5.c

diff --git a/Makefile.am b/Makefile.am
index c398e74..9b24589 100644
--- a/Makefile.am
+++ b/Makefile.am
@@ -126,7 +126,7 @@ builtin_nodist += audio/telephony.c
 noinst_LIBRARIES += audio/libtelephony.a
 
 audio_libtelephony_a_SOURCES = audio/telephony.h audio/telephony-dummy.c \
-				audio/telephony-maemo5.c audio/telephony-ofono.c \
+				audio/telephony-ofono.c \
 				audio/telephony-maemo6.c
 endif
 
@@ -315,7 +315,7 @@ EXTRA_DIST += src/genbuiltin src/bluetooth.conf src/org.bluez.service \
 			src/main.conf profiles/network/network.conf \
 			profiles/input/input.conf profiles/proximity/proximity.conf \
 			audio/audio.conf audio/telephony-dummy.c \
-			audio/telephony-maemo5.c audio/telephony-ofono.c \
+			audio/telephony-ofono.c \
 			audio/telephony-maemo6.c profiles/sap/sap-dummy.c \
 			profiles/sap/sap-u8500.c
 
diff --git a/audio/telephony-maemo5.c b/audio/telephony-maemo5.c
deleted file mode 100644
index deb64e4..0000000
--- a/audio/telephony-maemo5.c
+++ /dev/null
@@ -1,2102 +0,0 @@
-/*
- *
- *  BlueZ - Bluetooth protocol stack for Linux
- *
- *  Copyright (C) 2008-2010  Nokia Corporation
- *  Copyright (C) 2004-2010  Marcel Holtmann <marcel@holtmann.org>
- *
- *
- *  This program is free software; you can redistribute it and/or modify
- *  it under the terms of the GNU General Public License as published by
- *  the Free Software Foundation; either version 2 of the License, or
- *  (at your option) any later version.
- *
- *  This program is distributed in the hope that it will be useful,
- *  but WITHOUT ANY WARRANTY; without even the implied warranty of
- *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
- *  GNU General Public License for more details.
- *
- *  You should have received a copy of the GNU General Public License
- *  along with this program; if not, write to the Free Software
- *  Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
- *
- */
-
-#ifdef HAVE_CONFIG_H
-#include <config.h>
-#endif
-
-#include <stdlib.h>
-#include <stdio.h>
-#include <unistd.h>
-#include <fcntl.h>
-#include <stdint.h>
-#include <string.h>
-#include <glib.h>
-#include <dbus/dbus.h>
-#include <gdbus.h>
-
-#include "dbus-common.h"
-#include "log.h"
-#include "telephony.h"
-#include "error.h"
-
-/* SSC D-Bus definitions */
-#define SSC_DBUS_NAME  "com.nokia.phone.SSC"
-#define SSC_DBUS_IFACE "com.nokia.phone.SSC"
-#define SSC_DBUS_PATH  "/com/nokia/phone/SSC"
-
-/* libcsnet D-Bus definitions */
-#define NETWORK_BUS_NAME		"com.nokia.phone.net"
-#define NETWORK_INTERFACE		"Phone.Net"
-#define NETWORK_PATH			"/com/nokia/phone/net"
-
-/* Mask bits for supported services */
-#define NETWORK_MASK_GPRS_SUPPORT	0x01
-#define NETWORK_MASK_CS_SERVICES	0x02
-#define NETWORK_MASK_EGPRS_SUPPORT	0x04
-#define NETWORK_MASK_HSDPA_AVAIL	0x08
-#define NETWORK_MASK_HSUPA_AVAIL	0x10
-
-/* network get cell info: cell type */
-#define NETWORK_UNKNOWN_CELL		0
-#define NETWORK_GSM_CELL		1
-#define NETWORK_WCDMA_CELL		2
-
-enum net_registration_status {
-	NETWORK_REG_STATUS_HOME = 0x00,
-	NETWORK_REG_STATUS_ROAM,
-	NETWORK_REG_STATUS_ROAM_BLINK,
-	NETWORK_REG_STATUS_NOSERV,
-	NETWORK_REG_STATUS_NOSERV_SEARCHING,
-	NETWORK_REG_STATUS_NOSERV_NOTSEARCHING,
-	NETWORK_REG_STATUS_NOSERV_NOSIM,
-	NETWORK_REG_STATUS_POWER_OFF = 0x08,
-	NETWORK_REG_STATUS_NSPS,
-	NETWORK_REG_STATUS_NSPS_NO_COVERAGE,
-	NETWORK_REG_STATUS_NOSERV_SIM_REJECTED_BY_NW
-};
-
-enum network_types {
-	NETWORK_GSM_HOME_PLMN = 0,
-	NETWORK_GSM_PREFERRED_PLMN,
-	NETWORK_GSM_FORBIDDEN_PLMN,
-	NETWORK_GSM_OTHER_PLMN,
-	NETWORK_GSM_NO_PLMN_AVAIL
-};
-
-enum network_alpha_tag_name_type {
-	NETWORK_HARDCODED_LATIN_OPER_NAME = 0,
-	NETWORK_HARDCODED_USC2_OPER_NAME,
-	NETWORK_NITZ_SHORT_OPER_NAME,
-	NETWORK_NITZ_FULL_OPER_NAME,
-};
-
-#define TELEPHONY_MAEMO_PATH		"/com/nokia/MaemoTelephony"
-#define TELEPHONY_MAEMO_INTERFACE	"com.nokia.MaemoTelephony"
-
-#define CALLERID_BASE		"/var/lib/bluetooth/maemo-callerid-"
-#define ALLOWED_FLAG_FILE	"/var/lib/bluetooth/maemo-callerid-allowed"
-#define RESTRICTED_FLAG_FILE	"/var/lib/bluetooth/maemo-callerid-restricted"
-#define NONE_FLAG_FILE		"/var/lib/bluetooth/maemo-callerid-none"
-
-static uint32_t callerid = 0;
-
-/* CSD CALL plugin D-Bus definitions */
-#define CSD_CALL_BUS_NAME	"com.nokia.csd.Call"
-#define CSD_CALL_INTERFACE	"com.nokia.csd.Call"
-#define CSD_CALL_INSTANCE	"com.nokia.csd.Call.Instance"
-#define CSD_CALL_CONFERENCE	"com.nokia.csd.Call.Conference"
-#define CSD_CALL_PATH		"/com/nokia/csd/call"
-#define CSD_CALL_CONFERENCE_PATH "/com/nokia/csd/call/conference"
-
-/* Call status values as exported by the CSD CALL plugin */
-#define CSD_CALL_STATUS_IDLE			0
-#define CSD_CALL_STATUS_CREATE			1
-#define CSD_CALL_STATUS_COMING			2
-#define CSD_CALL_STATUS_PROCEEDING		3
-#define CSD_CALL_STATUS_MO_ALERTING		4
-#define CSD_CALL_STATUS_MT_ALERTING		5
-#define CSD_CALL_STATUS_WAITING			6
-#define CSD_CALL_STATUS_ANSWERED		7
-#define CSD_CALL_STATUS_ACTIVE			8
-#define CSD_CALL_STATUS_MO_RELEASE		9
-#define CSD_CALL_STATUS_MT_RELEASE		10
-#define CSD_CALL_STATUS_HOLD_INITIATED		11
-#define CSD_CALL_STATUS_HOLD			12
-#define CSD_CALL_STATUS_RETRIEVE_INITIATED	13
-#define CSD_CALL_STATUS_RECONNECT_PENDING	14
-#define CSD_CALL_STATUS_TERMINATED		15
-#define CSD_CALL_STATUS_SWAP_INITIATED		16
-
-#define CALL_FLAG_NONE				0
-#define CALL_FLAG_PRESENTATION_ALLOWED		0x01
-#define CALL_FLAG_PRESENTATION_RESTRICTED	0x02
-
-/* SIM Phonebook D-Bus definitions */
-#define SIM_PHONEBOOK_BUS_NAME			"com.nokia.phone.SIM"
-#define SIM_PHONEBOOK_INTERFACE			"Phone.Sim.Phonebook"
-#define SIM_PHONEBOOK_PATH			"/com/nokia/phone/SIM/phonebook"
-
-#define PHONEBOOK_INDEX_FIRST_ENTRY		0xFFFF
-#define PHONEBOOK_INDEX_NEXT_FREE_LOCATION	0xFFFE
-
-enum sim_phonebook_type {
-	SIM_PHONEBOOK_TYPE_ADN = 0x0,
-	SIM_PHONEBOOK_TYPE_SDN,
-	SIM_PHONEBOOK_TYPE_FDN,
-	SIM_PHONEBOOK_TYPE_VMBX,
-	SIM_PHONEBOOK_TYPE_MBDN,
-	SIM_PHONEBOOK_TYPE_EN,
-	SIM_PHONEBOOK_TYPE_MSISDN
-};
-
-enum sim_phonebook_location_type {
-	SIM_PHONEBOOK_LOCATION_EXACT = 0x0,
-	SIM_PHONEBOOK_LOCATION_NEXT
-};
-
-struct csd_call {
-	char *object_path;
-	int status;
-	gboolean originating;
-	gboolean emergency;
-	gboolean on_hold;
-	gboolean conference;
-	char *number;
-	gboolean setup;
-};
-
-static struct {
-	uint8_t status;
-	uint16_t lac;
-	uint32_t cell_id;
-	uint32_t operator_code;
-	uint32_t country_code;
-	uint8_t network_type;
-	uint8_t supported_services;
-	uint16_t signals_bar;
-	char *operator_name;
-} net = {
-	.status = NETWORK_REG_STATUS_NOSERV,
-	.lac = 0,
-	.cell_id = 0,
-	.operator_code = 0,
-	.country_code = 0,
-	.network_type = NETWORK_GSM_NO_PLMN_AVAIL,
-	.supported_services = 0,
-	.signals_bar = 0,
-	.operator_name = NULL,
-};
-
-static GSList *calls = NULL;
-
-/* Reference count for determining the call indicator status */
-static GSList *active_calls = NULL;
-
-static char *msisdn = NULL;	/* Subscriber number */
-static char *vmbx = NULL;	/* Voice mailbox number */
-
-/* HAL battery namespace key values */
-static int battchg_cur = -1;	/* "battery.charge_level.current" */
-static int battchg_last = -1;	/* "battery.charge_level.last_full" */
-static int battchg_design = -1;	/* "battery.charge_level.design" */
-
-static gboolean get_calls_active = FALSE;
-
-static gboolean events_enabled = FALSE;
-
-/* Supported set of call hold operations */
-static const char *chld_str = "0,1,1x,2,2x,3,4";
-
-static char *last_dialed_number = NULL;
-
-/* Timer for tracking call creation requests */
-static guint create_request_timer = 0;
-
-static struct indicator maemo_indicators[] =
-{
-	{ "battchg",	"0-5",	5,	TRUE },
-	{ "signal",	"0-5",	0,	TRUE },
-	{ "service",	"0,1",	0,	TRUE },
-	{ "call",	"0,1",	0,	TRUE },
-	{ "callsetup",	"0-3",	0,	TRUE },
-	{ "callheld",	"0-2",	0,	FALSE },
-	{ "roam",	"0,1",	0,	TRUE },
-	{ NULL }
-};
-
-static char *call_status_str[] = {
-	"IDLE",
-	"CREATE",
-	"COMING",
-	"PROCEEDING",
-	"MO_ALERTING",
-	"MT_ALERTING",
-	"WAITING",
-	"ANSWERED",
-	"ACTIVE",
-	"MO_RELEASE",
-	"MT_RELEASE",
-	"HOLD_INITIATED",
-	"HOLD",
-	"RETRIEVE_INITIATED",
-	"RECONNECT_PENDING",
-	"TERMINATED",
-	"SWAP_INITIATED",
-	"???"
-};
-
-static struct csd_call *find_call(const char *path)
-{
-	GSList *l;
-
-	for (l = calls; l != NULL; l = l->next) {
-		struct csd_call *call = l->data;
-
-		if (g_str_equal(call->object_path, path))
-			return call;
-	}
-
-	return NULL;
-}
-
-static struct csd_call *find_non_held_call(void)
-{
-	GSList *l;
-
-	for (l = calls; l != NULL; l = l->next) {
-		struct csd_call *call = l->data;
-
-		if (call->status == CSD_CALL_STATUS_IDLE)
-			continue;
-
-		if (call->status != CSD_CALL_STATUS_HOLD)
-			return call;
-	}
-
-	return NULL;
-}
-
-static struct csd_call *find_non_idle_call(void)
-{
-	GSList *l;
-
-	for (l = calls; l != NULL; l = l->next) {
-		struct csd_call *call = l->data;
-
-		if (call->status != CSD_CALL_STATUS_IDLE)
-			return call;
-	}
-
-	return NULL;
-}
-
-static struct csd_call *find_call_with_status(int status)
-{
-	GSList *l;
-
-	for (l = calls; l != NULL; l = l->next) {
-		struct csd_call *call = l->data;
-
-		if (call->status == status)
-			return call;
-	}
-
-	return NULL;
-}
-
-static int release_conference(void)
-{
-	DBusMessage *msg;
-
-	DBG("telephony-maemo: releasing conference call");
-
-	msg = dbus_message_new_method_call(CSD_CALL_BUS_NAME,
-						CSD_CALL_CONFERENCE_PATH,
-						CSD_CALL_INSTANCE,
-						"Release");
-	if (!msg) {
-		error("Unable to allocate new D-Bus message");
-		return -ENOMEM;
-	}
-
-	g_dbus_send_message(btd_get_dbus_connection(), msg);
-
-	return 0;
-}
-
-static int release_call(struct csd_call *call)
-{
-	DBusMessage *msg;
-
-	msg = dbus_message_new_method_call(CSD_CALL_BUS_NAME,
-						call->object_path,
-						CSD_CALL_INSTANCE,
-						"Release");
-	if (!msg) {
-		error("Unable to allocate new D-Bus message");
-		return -ENOMEM;
-	}
-
-	g_dbus_send_message(btd_get_dbus_connection(), msg);
-
-	return 0;
-}
-
-static int answer_call(struct csd_call *call)
-{
-	DBusMessage *msg;
-
-	msg = dbus_message_new_method_call(CSD_CALL_BUS_NAME,
-						call->object_path,
-						CSD_CALL_INSTANCE,
-						"Answer");
-	if (!msg) {
-		error("Unable to allocate new D-Bus message");
-		return -ENOMEM;
-	}
-
-	g_dbus_send_message(btd_get_dbus_connection(), msg);
-
-	return 0;
-}
-
-static int split_call(struct csd_call *call)
-{
-	DBusMessage *msg;
-
-	msg = dbus_message_new_method_call(CSD_CALL_BUS_NAME,
-						call->object_path,
-						CSD_CALL_INSTANCE,
-						"Split");
-	if (!msg) {
-		error("Unable to allocate new D-Bus message");
-		return -ENOMEM;
-	}
-
-	g_dbus_send_message(btd_get_dbus_connection(), msg);
-
-	return 0;
-}
-
-static int unhold_call(struct csd_call *call)
-{
-	DBusMessage *msg;
-
-	msg = dbus_message_new_method_call(CSD_CALL_BUS_NAME, CSD_CALL_PATH,
-						CSD_CALL_INTERFACE,
-						"Unhold");
-	if (!msg) {
-		error("Unable to allocate new D-Bus message");
-		return -ENOMEM;
-	}
-
-	g_dbus_send_message(btd_get_dbus_connection(), msg);
-
-	return 0;
-}
-
-static int hold_call(struct csd_call *call)
-{
-	DBusMessage *msg;
-
-	msg = dbus_message_new_method_call(CSD_CALL_BUS_NAME, CSD_CALL_PATH,
-						CSD_CALL_INTERFACE,
-						"Hold");
-	if (!msg) {
-		error("Unable to allocate new D-Bus message");
-		return -ENOMEM;
-	}
-
-	g_dbus_send_message(btd_get_dbus_connection(), msg);
-
-	return 0;
-}
-
-static int swap_calls(void)
-{
-	DBusMessage *msg;
-
-	msg = dbus_message_new_method_call(CSD_CALL_BUS_NAME, CSD_CALL_PATH,
-						CSD_CALL_INTERFACE,
-						"Swap");
-	if (!msg) {
-		error("Unable to allocate new D-Bus message");
-		return -ENOMEM;
-	}
-
-	g_dbus_send_message(btd_get_dbus_connection(), msg);
-
-	return 0;
-}
-
-static int create_conference(void)
-{
-	DBusMessage *msg;
-
-	msg = dbus_message_new_method_call(CSD_CALL_BUS_NAME, CSD_CALL_PATH,
-						CSD_CALL_INTERFACE,
-						"Conference");
-	if (!msg) {
-		error("Unable to allocate new D-Bus message");
-		return -ENOMEM;
-	}
-
-	g_dbus_send_message(btd_get_dbus_connection(), msg);
-
-	return 0;
-}
-
-static int call_transfer(void)
-{
-	DBusMessage *msg;
-
-	msg = dbus_message_new_method_call(CSD_CALL_BUS_NAME, CSD_CALL_PATH,
-						CSD_CALL_INTERFACE,
-						"Transfer");
-	if (!msg) {
-		error("Unable to allocate new D-Bus message");
-		return -ENOMEM;
-	}
-
-	g_dbus_send_message(btd_get_dbus_connection(), msg);
-
-	return 0;
-}
-
-static int number_type(const char *number)
-{
-	if (number == NULL)
-		return NUMBER_TYPE_TELEPHONY;
-
-	if (number[0] == '+' || strncmp(number, "00", 2) == 0)
-		return NUMBER_TYPE_INTERNATIONAL;
-
-	return NUMBER_TYPE_TELEPHONY;
-}
-
-void telephony_device_connected(void *telephony_device)
-{
-	struct csd_call *coming;
-
-	DBG("telephony-maemo: device %p connected", telephony_device);
-
-	coming = find_call_with_status(CSD_CALL_STATUS_MT_ALERTING);
-	if (coming) {
-		if (find_call_with_status(CSD_CALL_STATUS_ACTIVE))
-			telephony_call_waiting_ind(coming->number,
-						number_type(coming->number));
-		else
-			telephony_incoming_call_ind(coming->number,
-						number_type(coming->number));
-	}
-}
-
-void telephony_device_disconnected(void *telephony_device)
-{
-	DBG("telephony-maemo: device %p disconnected", telephony_device);
-	events_enabled = FALSE;
-}
-
-void telephony_event_reporting_req(void *telephony_device, int ind)
-{
-	events_enabled = ind == 1 ? TRUE : FALSE;
-
-	telephony_event_reporting_rsp(telephony_device, CME_ERROR_NONE);
-}
-
-void telephony_response_and_hold_req(void *telephony_device, int rh)
-{
-	telephony_response_and_hold_rsp(telephony_device,
-						CME_ERROR_NOT_SUPPORTED);
-}
-
-void telephony_last_dialed_number_req(void *telephony_device)
-{
-	DBG("telephony-maemo: last dialed number request");
-
-	if (last_dialed_number)
-		telephony_dial_number_req(telephony_device,
-						last_dialed_number);
-	else
-		telephony_last_dialed_number_rsp(telephony_device,
-						CME_ERROR_NOT_ALLOWED);
-}
-
-void telephony_terminate_call_req(void *telephony_device)
-{
-	struct csd_call *call;
-	int err;
-
-	call = find_call_with_status(CSD_CALL_STATUS_ACTIVE);
-	if (!call)
-		call = find_non_idle_call();
-
-	if (!call) {
-		error("No active call");
-		telephony_terminate_call_rsp(telephony_device,
-						CME_ERROR_NOT_ALLOWED);
-		return;
-	}
-
-	if (call->conference)
-		err = release_conference();
-	else
-		err = release_call(call);
-
-	if (err < 0)
-		telephony_terminate_call_rsp(telephony_device,
-						CME_ERROR_AG_FAILURE);
-	else
-		telephony_terminate_call_rsp(telephony_device, CME_ERROR_NONE);
-}
-
-void telephony_answer_call_req(void *telephony_device)
-{
-	struct csd_call *call;
-
-	call = find_call_with_status(CSD_CALL_STATUS_COMING);
-	if (!call)
-		call = find_call_with_status(CSD_CALL_STATUS_MT_ALERTING);
-
-	if (!call)
-		call = find_call_with_status(CSD_CALL_STATUS_PROCEEDING);
-
-	if (!call)
-		call = find_call_with_status(CSD_CALL_STATUS_WAITING);
-
-	if (!call) {
-		telephony_answer_call_rsp(telephony_device,
-						CME_ERROR_NOT_ALLOWED);
-		return;
-	}
-
-	if (answer_call(call) < 0)
-		telephony_answer_call_rsp(telephony_device,
-						CME_ERROR_AG_FAILURE);
-	else
-		telephony_answer_call_rsp(telephony_device, CME_ERROR_NONE);
-}
-
-static int send_method_call(const char *dest, const char *path,
-				const char *interface, const char *method,
-				DBusPendingCallNotifyFunction cb,
-				void *user_data, int type, ...)
-{
-	DBusConnection *conn = btd_get_dbus_connection();
-	DBusMessage *msg;
-	DBusPendingCall *call;
-	va_list args;
-
-	msg = dbus_message_new_method_call(dest, path, interface, method);
-	if (!msg) {
-		error("Unable to allocate new D-Bus %s message", method);
-		return -ENOMEM;
-	}
-
-	va_start(args, type);
-
-	if (!dbus_message_append_args_valist(msg, type, args)) {
-		dbus_message_unref(msg);
-		va_end(args);
-		return -EIO;
-	}
-
-	va_end(args);
-
-	if (!cb) {
-		g_dbus_send_message(conn, msg);
-		return 0;
-	}
-
-	if (!dbus_connection_send_with_reply(conn, msg, &call, -1)) {
-		error("Sending %s failed", method);
-		dbus_message_unref(msg);
-		return -EIO;
-	}
-
-	dbus_pending_call_set_notify(call, cb, user_data, NULL);
-	dbus_pending_call_unref(call);
-	dbus_message_unref(msg);
-
-	return 0;
-}
-
-static const char *memory_dial_lookup(int location)
-{
-	if (location == 1)
-		return vmbx;
-	else
-		return NULL;
-}
-
-void telephony_dial_number_req(void *telephony_device, const char *number)
-{
-	uint32_t flags = callerid;
-	int ret;
-
-	DBG("telephony-maemo: dial request to %s", number);
-
-	if (strncmp(number, "*31#", 4) == 0) {
-		number += 4;
-		flags = CALL_FLAG_PRESENTATION_ALLOWED;
-	} else if (strncmp(number, "#31#", 4) == 0) {
-		number += 4;
-		flags = CALL_FLAG_PRESENTATION_RESTRICTED;
-	} else if (number[0] == '>') {
-		const char *location = &number[1];
-
-		number = memory_dial_lookup(strtol(&number[1], NULL, 0));
-		if (!number) {
-			error("No number at memory location %s", location);
-			telephony_dial_number_rsp(telephony_device,
-						CME_ERROR_INVALID_INDEX);
-			return;
-		}
-	}
-
-	ret = send_method_call(CSD_CALL_BUS_NAME, CSD_CALL_PATH,
-				CSD_CALL_INTERFACE, "CreateWith",
-				NULL, NULL,
-				DBUS_TYPE_STRING, &number,
-				DBUS_TYPE_UINT32, &flags,
-				DBUS_TYPE_INVALID);
-	if (ret < 0) {
-		telephony_dial_number_rsp(telephony_device,
-						CME_ERROR_AG_FAILURE);
-		return;
-	}
-
-	telephony_dial_number_rsp(telephony_device, CME_ERROR_NONE);
-}
-
-void telephony_transmit_dtmf_req(void *telephony_device, char tone)
-{
-	int ret;
-	char buf[2] = { tone, '\0' }, *buf_ptr = buf;
-
-	DBG("telephony-maemo: transmit dtmf: %s", buf);
-
-	ret = send_method_call(CSD_CALL_BUS_NAME, CSD_CALL_PATH,
-				CSD_CALL_INTERFACE, "SendDTMF",
-				NULL, NULL,
-				DBUS_TYPE_STRING, &buf_ptr,
-				DBUS_TYPE_INVALID);
-	if (ret < 0) {
-		telephony_transmit_dtmf_rsp(telephony_device,
-						CME_ERROR_AG_FAILURE);
-		return;
-	}
-
-	telephony_transmit_dtmf_rsp(telephony_device, CME_ERROR_NONE);
-}
-
-void telephony_subscriber_number_req(void *telephony_device)
-{
-	DBG("telephony-maemo: subscriber number request");
-	if (msisdn)
-		telephony_subscriber_number_ind(msisdn,
-						number_type(msisdn),
-						SUBSCRIBER_SERVICE_VOICE);
-	telephony_subscriber_number_rsp(telephony_device, CME_ERROR_NONE);
-}
-
-static int csd_status_to_hfp(struct csd_call *call)
-{
-	switch (call->status) {
-	case CSD_CALL_STATUS_IDLE:
-	case CSD_CALL_STATUS_MO_RELEASE:
-	case CSD_CALL_STATUS_MT_RELEASE:
-	case CSD_CALL_STATUS_TERMINATED:
-		return -1;
-	case CSD_CALL_STATUS_CREATE:
-		return CALL_STATUS_DIALING;
-	case CSD_CALL_STATUS_WAITING:
-		return CALL_STATUS_WAITING;
-	case CSD_CALL_STATUS_PROCEEDING:
-		/* PROCEEDING can happen in outgoing/incoming */
-		if (call->originating)
-			return CALL_STATUS_DIALING;
-		else
-			return CALL_STATUS_INCOMING;
-	case CSD_CALL_STATUS_COMING:
-		return CALL_STATUS_INCOMING;
-	case CSD_CALL_STATUS_MO_ALERTING:
-		return CALL_STATUS_ALERTING;
-	case CSD_CALL_STATUS_MT_ALERTING:
-		return CALL_STATUS_INCOMING;
-	case CSD_CALL_STATUS_ANSWERED:
-	case CSD_CALL_STATUS_ACTIVE:
-	case CSD_CALL_STATUS_RECONNECT_PENDING:
-	case CSD_CALL_STATUS_SWAP_INITIATED:
-	case CSD_CALL_STATUS_HOLD_INITIATED:
-		return CALL_STATUS_ACTIVE;
-	case CSD_CALL_STATUS_RETRIEVE_INITIATED:
-	case CSD_CALL_STATUS_HOLD:
-		return CALL_STATUS_HELD;
-	default:
-		return -1;
-	}
-}
-
-void telephony_list_current_calls_req(void *telephony_device)
-{
-	GSList *l;
-	int i;
-
-	DBG("telephony-maemo: list current calls request");
-
-	for (l = calls, i = 1; l != NULL; l = l->next, i++) {
-		struct csd_call *call = l->data;
-		int status, direction, multiparty;
-
-		status = csd_status_to_hfp(call);
-		if (status < 0)
-			continue;
-
-		direction = call->originating ?
-				CALL_DIR_OUTGOING : CALL_DIR_INCOMING;
-
-		multiparty = call->conference ?
-				CALL_MULTIPARTY_YES : CALL_MULTIPARTY_NO;
-
-		telephony_list_current_call_ind(i, direction, status,
-						CALL_MODE_VOICE, multiparty,
-						call->number,
-						number_type(call->number));
-	}
-
-	telephony_list_current_calls_rsp(telephony_device, CME_ERROR_NONE);
-}
-
-void telephony_operator_selection_req(void *telephony_device)
-{
-	telephony_operator_selection_ind(OPERATOR_MODE_AUTO,
-				net.operator_name ? net.operator_name : "");
-	telephony_operator_selection_rsp(telephony_device, CME_ERROR_NONE);
-}
-
-static void foreach_call_with_status(int status,
-					int (*func)(struct csd_call *call))
-{
-	GSList *l;
-
-	for (l = calls; l != NULL; l = l->next) {
-		struct csd_call *call = l->data;
-
-		if (call->status == status)
-			func(call);
-	}
-}
-
-void telephony_call_hold_req(void *telephony_device, const char *cmd)
-{
-	const char *idx;
-	struct csd_call *call;
-	int err = 0;
-
-	DBG("telephony-maemo: got call hold request %s", cmd);
-
-	if (strlen(cmd) > 1)
-		idx = &cmd[1];
-	else
-		idx = NULL;
-
-	if (idx)
-		call = g_slist_nth_data(calls, strtol(idx, NULL, 0) - 1);
-	else
-		call = NULL;
-
-	switch (cmd[0]) {
-	case '0':
-		foreach_call_with_status(CSD_CALL_STATUS_HOLD, release_call);
-		foreach_call_with_status(CSD_CALL_STATUS_WAITING,
-								release_call);
-		break;
-	case '1':
-		if (idx) {
-			if (call)
-				err = release_call(call);
-			break;
-		}
-		foreach_call_with_status(CSD_CALL_STATUS_ACTIVE, release_call);
-		call = find_call_with_status(CSD_CALL_STATUS_WAITING);
-		if (call)
-			err = answer_call(call);
-		break;
-	case '2':
-		if (idx) {
-			if (call)
-				err = split_call(call);
-		} else {
-			struct csd_call *held, *wait;
-
-			call = find_call_with_status(CSD_CALL_STATUS_ACTIVE);
-			held = find_call_with_status(CSD_CALL_STATUS_HOLD);
-			wait = find_call_with_status(CSD_CALL_STATUS_WAITING);
-
-			if (wait)
-				err = answer_call(wait);
-			else if (call && held)
-				err = swap_calls();
-			else {
-				if (call)
-					err = hold_call(call);
-				if (held)
-					err = unhold_call(held);
-			}
-		}
-		break;
-	case '3':
-		if (find_call_with_status(CSD_CALL_STATUS_HOLD) ||
-				find_call_with_status(CSD_CALL_STATUS_WAITING))
-			err = create_conference();
-		break;
-	case '4':
-		err = call_transfer();
-		break;
-	default:
-		DBG("Unknown call hold request");
-		break;
-	}
-
-	if (err)
-		telephony_call_hold_rsp(telephony_device,
-					CME_ERROR_AG_FAILURE);
-	else
-		telephony_call_hold_rsp(telephony_device, CME_ERROR_NONE);
-}
-
-void telephony_nr_and_ec_req(void *telephony_device, gboolean enable)
-{
-	DBG("telephony-maemo: got %s NR and EC request",
-			enable ? "enable" : "disable");
-	telephony_nr_and_ec_rsp(telephony_device, CME_ERROR_NONE);
-}
-
-void telephony_key_press_req(void *telephony_device, const char *keys)
-{
-	struct csd_call *active, *waiting;
-	int err;
-
-	DBG("telephony-maemo: got key press request for %s", keys);
-
-	waiting = find_call_with_status(CSD_CALL_STATUS_COMING);
-	if (!waiting)
-		waiting = find_call_with_status(CSD_CALL_STATUS_MT_ALERTING);
-	if (!waiting)
-		waiting = find_call_with_status(CSD_CALL_STATUS_PROCEEDING);
-
-	active = find_call_with_status(CSD_CALL_STATUS_ACTIVE);
-
-	if (waiting)
-		err = answer_call(waiting);
-	else if (active)
-		err = release_call(active);
-	else
-		err = 0;
-
-	if (err < 0)
-		telephony_key_press_rsp(telephony_device,
-							CME_ERROR_AG_FAILURE);
-	else
-		telephony_key_press_rsp(telephony_device, CME_ERROR_NONE);
-}
-
-void telephony_voice_dial_req(void *telephony_device, gboolean enable)
-{
-	DBG("telephony-maemo: got %s voice dial request",
-			enable ? "enable" : "disable");
-
-	telephony_voice_dial_rsp(telephony_device, CME_ERROR_NOT_SUPPORTED);
-}
-
-static void handle_incoming_call(DBusMessage *msg)
-{
-	const char *number, *call_path;
-	struct csd_call *call;
-
-	if (!dbus_message_get_args(msg, NULL,
-					DBUS_TYPE_OBJECT_PATH, &call_path,
-					DBUS_TYPE_STRING, &number,
-					DBUS_TYPE_INVALID)) {
-		error("Unexpected parameters in Call.Coming() signal");
-		return;
-	}
-
-	call = find_call(call_path);
-	if (!call) {
-		error("Didn't find any matching call object for %s",
-				call_path);
-		return;
-	}
-
-	DBG("Incoming call to %s from number %s", call_path, number);
-
-	g_free(call->number);
-	call->number = g_strdup(number);
-
-	telephony_update_indicator(maemo_indicators, "callsetup",
-					EV_CALLSETUP_INCOMING);
-
-	if (find_call_with_status(CSD_CALL_STATUS_ACTIVE))
-		telephony_call_waiting_ind(call->number,
-						number_type(call->number));
-	else
-		telephony_incoming_call_ind(call->number,
-						number_type(call->number));
-}
-
-static void handle_outgoing_call(DBusMessage *msg)
-{
-	const char *number, *call_path;
-	struct csd_call *call;
-
-	if (!dbus_message_get_args(msg, NULL,
-					DBUS_TYPE_OBJECT_PATH, &call_path,
-					DBUS_TYPE_STRING, &number,
-					DBUS_TYPE_INVALID)) {
-		error("Unexpected parameters in Call.Created() signal");
-		return;
-	}
-
-	call = find_call(call_path);
-	if (!call) {
-		error("Didn't find any matching call object for %s",
-				call_path);
-		return;
-	}
-
-	DBG("Outgoing call from %s to number %s", call_path, number);
-
-	g_free(call->number);
-	call->number = g_strdup(number);
-
-	g_free(last_dialed_number);
-	last_dialed_number = g_strdup(number);
-
-	if (create_request_timer) {
-		g_source_remove(create_request_timer);
-		create_request_timer = 0;
-	}
-}
-
-static gboolean create_timeout(gpointer user_data)
-{
-	telephony_update_indicator(maemo_indicators, "callsetup",
-					EV_CALLSETUP_INACTIVE);
-	create_request_timer = 0;
-	return FALSE;
-}
-
-static void handle_create_requested(DBusMessage *msg)
-{
-	DBG("Call.CreateRequested()");
-
-	if (create_request_timer)
-		g_source_remove(create_request_timer);
-
-	create_request_timer = g_timeout_add_seconds(5, create_timeout, NULL);
-
-	telephony_update_indicator(maemo_indicators, "callsetup",
-					EV_CALLSETUP_OUTGOING);
-}
-
-static void handle_call_status(DBusMessage *msg, const char *call_path)
-{
-	struct csd_call *call;
-	dbus_uint32_t status, cause_type, cause;
-	int callheld = telephony_get_indicator(maemo_indicators, "callheld");
-
-	if (!dbus_message_get_args(msg, NULL,
-					DBUS_TYPE_UINT32, &status,
-					DBUS_TYPE_UINT32, &cause_type,
-					DBUS_TYPE_UINT32, &cause,
-					DBUS_TYPE_INVALID)) {
-		error("Unexpected parameters in Instance.CallStatus() signal");
-		return;
-	}
-
-	call = find_call(call_path);
-	if (!call) {
-		error("Didn't find any matching call object for %s",
-				call_path);
-		return;
-	}
-
-	if (status > 16) {
-		error("Invalid call status %u", status);
-		return;
-	}
-
-	DBG("Call %s changed from %s to %s", call_path,
-		call_status_str[call->status], call_status_str[status]);
-
-	if (call->status == (int) status) {
-		DBG("Ignoring CSD Call state change to existing state");
-		return;
-	}
-
-	call->status = (int) status;
-
-	switch (status) {
-	case CSD_CALL_STATUS_IDLE:
-		if (call->setup) {
-			telephony_update_indicator(maemo_indicators,
-							"callsetup",
-							EV_CALLSETUP_INACTIVE);
-			if (!call->originating)
-				telephony_calling_stopped_ind();
-		}
-
-		g_free(call->number);
-		call->number = NULL;
-		call->originating = FALSE;
-		call->emergency = FALSE;
-		call->on_hold = FALSE;
-		call->conference = FALSE;
-		call->setup = FALSE;
-		break;
-	case CSD_CALL_STATUS_CREATE:
-		call->originating = TRUE;
-		call->setup = TRUE;
-		break;
-	case CSD_CALL_STATUS_COMING:
-		call->originating = FALSE;
-		call->setup = TRUE;
-		break;
-	case CSD_CALL_STATUS_PROCEEDING:
-		break;
-	case CSD_CALL_STATUS_MO_ALERTING:
-		telephony_update_indicator(maemo_indicators, "callsetup",
-						EV_CALLSETUP_ALERTING);
-		break;
-	case CSD_CALL_STATUS_MT_ALERTING:
-		break;
-	case CSD_CALL_STATUS_WAITING:
-		break;
-	case CSD_CALL_STATUS_ANSWERED:
-		break;
-	case CSD_CALL_STATUS_ACTIVE:
-		if (call->on_hold) {
-			call->on_hold = FALSE;
-			if (find_call_with_status(CSD_CALL_STATUS_HOLD))
-				telephony_update_indicator(maemo_indicators,
-							"callheld",
-							EV_CALLHELD_MULTIPLE);
-			else
-				telephony_update_indicator(maemo_indicators,
-							"callheld",
-							EV_CALLHELD_NONE);
-		} else {
-			if (!g_slist_find(active_calls, call))
-				active_calls = g_slist_prepend(active_calls, call);
-			if (g_slist_length(active_calls) == 1)
-				telephony_update_indicator(maemo_indicators,
-								"call",
-								EV_CALL_ACTIVE);
-			/* Upgrade callheld status if necessary */
-			if (callheld == EV_CALLHELD_ON_HOLD)
-				telephony_update_indicator(maemo_indicators,
-							"callheld",
-							EV_CALLHELD_MULTIPLE);
-			telephony_update_indicator(maemo_indicators,
-							"callsetup",
-							EV_CALLSETUP_INACTIVE);
-			if (!call->originating)
-				telephony_calling_stopped_ind();
-			call->setup = FALSE;
-		}
-		break;
-	case CSD_CALL_STATUS_MO_RELEASE:
-	case CSD_CALL_STATUS_MT_RELEASE:
-		active_calls = g_slist_remove(active_calls, call);
-		if (g_slist_length(active_calls) == 0)
-			telephony_update_indicator(maemo_indicators, "call",
-							EV_CALL_INACTIVE);
-		break;
-	case CSD_CALL_STATUS_HOLD_INITIATED:
-		break;
-	case CSD_CALL_STATUS_HOLD:
-		call->on_hold = TRUE;
-		if (find_non_held_call())
-			telephony_update_indicator(maemo_indicators,
-							"callheld",
-							EV_CALLHELD_MULTIPLE);
-		else
-			telephony_update_indicator(maemo_indicators,
-							"callheld",
-							EV_CALLHELD_ON_HOLD);
-		break;
-	case CSD_CALL_STATUS_RETRIEVE_INITIATED:
-		break;
-	case CSD_CALL_STATUS_RECONNECT_PENDING:
-		break;
-	case CSD_CALL_STATUS_TERMINATED:
-		if (call->on_hold &&
-				!find_call_with_status(CSD_CALL_STATUS_HOLD))
-			telephony_update_indicator(maemo_indicators,
-							"callheld",
-							EV_CALLHELD_NONE);
-		else if (callheld == EV_CALLHELD_MULTIPLE &&
-				find_call_with_status(CSD_CALL_STATUS_HOLD))
-			telephony_update_indicator(maemo_indicators,
-							"callheld",
-							EV_CALLHELD_ON_HOLD);
-		break;
-	case CSD_CALL_STATUS_SWAP_INITIATED:
-		break;
-	default:
-		error("Unknown call status %u", status);
-		break;
-	}
-}
-
-static void handle_conference(DBusMessage *msg, gboolean joined)
-{
-	const char *path;
-	struct csd_call *call;
-
-	if (!dbus_message_get_args(msg, NULL,
-					DBUS_TYPE_OBJECT_PATH, &path,
-					DBUS_TYPE_INVALID)) {
-		error("Unexpected parameters in Conference.%s",
-					dbus_message_get_member(msg));
-		return;
-	}
-
-	call = find_call(path);
-	if (!call) {
-		error("Conference signal for unknown call %s", path);
-		return;
-	}
-
-	DBG("Call %s %s the conference", path, joined ? "joined" : "left");
-
-	call->conference = joined;
-}
-
-static void get_operator_name_reply(DBusPendingCall *pending_call,
-					void *user_data)
-{
-	DBusMessage *reply;
-	DBusError err;
-	const char *name;
-	dbus_int32_t net_err;
-
-	reply = dbus_pending_call_steal_reply(pending_call);
-
-	dbus_error_init(&err);
-	if (dbus_set_error_from_message(&err, reply)) {
-		error("get_operator_name failed: %s, %s",
-			err.name, err.message);
-		dbus_error_free(&err);
-		goto done;
-	}
-
-	dbus_error_init(&err);
-	if (!dbus_message_get_args(reply, &err,
-					DBUS_TYPE_STRING, &name,
-					DBUS_TYPE_INT32, &net_err,
-					DBUS_TYPE_INVALID)) {
-		error("Unexpected get_operator_name reply parameters: %s, %s",
-			err.name, err.message);
-		dbus_error_free(&err);
-		goto done;
-	}
-
-	if (net_err != 0) {
-		error("get_operator_name failed with code %d", net_err);
-		goto done;
-	}
-
-	if (strlen(name) == 0)
-		goto done;
-
-	g_free(net.operator_name);
-	net.operator_name = g_strdup(name);
-
-	DBG("telephony-maemo: operator name updated: %s", name);
-
-done:
-	dbus_message_unref(reply);
-}
-
-static void resolve_operator_name(uint32_t operator, uint32_t country)
-{
-	uint8_t name_type = NETWORK_HARDCODED_LATIN_OPER_NAME;
-
-	send_method_call(NETWORK_BUS_NAME, NETWORK_PATH,
-				NETWORK_INTERFACE, "get_operator_name",
-				get_operator_name_reply, NULL,
-				DBUS_TYPE_BYTE, &name_type,
-				DBUS_TYPE_UINT32, &operator,
-				DBUS_TYPE_UINT32, &country,
-				DBUS_TYPE_INVALID);
-}
-
-static void update_registration_status(uint8_t status, uint16_t lac,
-					uint32_t cell_id,
-					uint32_t operator_code,
-					uint32_t country_code,
-					uint8_t network_type,
-					uint8_t supported_services)
-{
-	if (net.status != status) {
-		switch (status) {
-		case NETWORK_REG_STATUS_HOME:
-			telephony_update_indicator(maemo_indicators, "roam",
-							EV_ROAM_INACTIVE);
-			if (net.status >= NETWORK_REG_STATUS_NOSERV)
-				telephony_update_indicator(maemo_indicators,
-							"service",
-							EV_SERVICE_PRESENT);
-			break;
-		case NETWORK_REG_STATUS_ROAM:
-		case NETWORK_REG_STATUS_ROAM_BLINK:
-			telephony_update_indicator(maemo_indicators, "roam",
-							EV_ROAM_ACTIVE);
-			if (net.status >= NETWORK_REG_STATUS_NOSERV)
-				telephony_update_indicator(maemo_indicators,
-							"service",
-							EV_SERVICE_PRESENT);
-			break;
-		case NETWORK_REG_STATUS_NOSERV:
-		case NETWORK_REG_STATUS_NOSERV_SEARCHING:
-		case NETWORK_REG_STATUS_NOSERV_NOTSEARCHING:
-		case NETWORK_REG_STATUS_NOSERV_NOSIM:
-		case NETWORK_REG_STATUS_POWER_OFF:
-		case NETWORK_REG_STATUS_NSPS:
-		case NETWORK_REG_STATUS_NSPS_NO_COVERAGE:
-		case NETWORK_REG_STATUS_NOSERV_SIM_REJECTED_BY_NW:
-			if (net.status < NETWORK_REG_STATUS_NOSERV)
-				telephony_update_indicator(maemo_indicators,
-							"service",
-							EV_SERVICE_NONE);
-			break;
-		}
-
-		net.status = status;
-	}
-
-	net.lac = lac;
-	net.cell_id = cell_id;
-
-	if (net.operator_code != operator_code ||
-			net.country_code != country_code) {
-		g_free(net.operator_name);
-		net.operator_name = NULL;
-		resolve_operator_name(operator_code, country_code);
-		net.operator_code = operator_code;
-		net.country_code = country_code;
-	}
-
-	net.network_type = network_type;
-	net.supported_services = supported_services;
-}
-
-static void handle_registration_status_change(DBusMessage *msg)
-{
-	uint8_t status;
-	dbus_uint16_t lac, network_type, supported_services;
-	dbus_uint32_t cell_id, operator_code, country_code;
-
-	if (!dbus_message_get_args(msg, NULL,
-					DBUS_TYPE_BYTE, &status,
-					DBUS_TYPE_UINT16, &lac,
-					DBUS_TYPE_UINT32, &cell_id,
-					DBUS_TYPE_UINT32, &operator_code,
-					DBUS_TYPE_UINT32, &country_code,
-					DBUS_TYPE_BYTE, &network_type,
-					DBUS_TYPE_BYTE, &supported_services,
-					DBUS_TYPE_INVALID)) {
-		error("Unexpected parameters in registration_status_change");
-		return;
-	}
-
-	update_registration_status(status, lac, cell_id, operator_code,
-					country_code, network_type,
-					supported_services);
-}
-
-static void update_signal_strength(uint8_t signals_bar)
-{
-	int signal;
-
-	if (signals_bar > 100) {
-		DBG("signals_bar greater than expected: %u", signals_bar);
-		signals_bar = 100;
-	}
-
-	if (net.signals_bar == signals_bar)
-		return;
-
-	/* A simple conversion from 0-100 to 0-5 (used by HFP) */
-	signal = (signals_bar + 20) / 21;
-
-	telephony_update_indicator(maemo_indicators, "signal", signal);
-
-	net.signals_bar = signals_bar;
-
-	DBG("Signal strength updated: %u/100, %d/5", signals_bar, signal);
-}
-
-static void handle_signal_strength_change(DBusMessage *msg)
-{
-	uint8_t signals_bar, rssi_in_dbm;
-
-	if (!dbus_message_get_args(msg, NULL,
-					DBUS_TYPE_BYTE, &signals_bar,
-					DBUS_TYPE_BYTE, &rssi_in_dbm,
-					DBUS_TYPE_INVALID)) {
-		error("Unexpected parameters in signal_strength_change");
-		return;
-	}
-
-	update_signal_strength(signals_bar);
-}
-
-static gboolean iter_get_basic_args(DBusMessageIter *iter,
-					int first_arg_type, ...)
-{
-	int type;
-	va_list ap;
-
-	va_start(ap, first_arg_type);
-
-	for (type = first_arg_type; type != DBUS_TYPE_INVALID;
-			type = va_arg(ap, int)) {
-		void *value = va_arg(ap, void *);
-		int real_type = dbus_message_iter_get_arg_type(iter);
-
-		if (real_type != type) {
-			error("iter_get_basic_args: expected %c but got %c",
-					(char) type, (char) real_type);
-			break;
-		}
-
-		dbus_message_iter_get_basic(iter, value);
-		dbus_message_iter_next(iter);
-	}
-
-	va_end(ap);
-
-	return type == DBUS_TYPE_INVALID ? TRUE : FALSE;
-}
-
-static void hal_battery_level_reply(DBusPendingCall *call, void *user_data)
-{
-	DBusError err;
-	DBusMessage *reply;
-	dbus_int32_t level;
-	int *value = user_data;
-
-	reply = dbus_pending_call_steal_reply(call);
-
-	dbus_error_init(&err);
-	if (dbus_set_error_from_message(&err, reply)) {
-		error("hald replied with an error: %s, %s",
-				err.name, err.message);
-		dbus_error_free(&err);
-		goto done;
-	}
-
-	dbus_error_init(&err);
-	if (dbus_message_get_args(reply, &err,
-				DBUS_TYPE_INT32, &level,
-				DBUS_TYPE_INVALID) == FALSE) {
-		error("Unable to parse GetPropertyInteger reply: %s, %s",
-							err.name, err.message);
-		dbus_error_free(&err);
-		goto done;
-	}
-
-	*value = (int) level;
-
-	if (value == &battchg_last)
-		DBG("telephony-maemo: battery.charge_level.last_full is %d",
-				*value);
-	else if (value == &battchg_design)
-		DBG("telephony-maemo: battery.charge_level.design is %d",
-				*value);
-	else
-		DBG("telephony-maemo: battery.charge_level.current is %d",
-				*value);
-
-	if ((battchg_design > 0 || battchg_last > 0) && battchg_cur >= 0) {
-		int new, max;
-
-		if (battchg_last > 0)
-			max = battchg_last;
-		else
-			max = battchg_design;
-
-		new = battchg_cur * 5 / max;
-
-		telephony_update_indicator(maemo_indicators, "battchg", new);
-	}
-done:
-	dbus_message_unref(reply);
-}
-
-static void hal_get_integer(const char *path, const char *key, void *user_data)
-{
-	send_method_call("org.freedesktop.Hal", path,
-				"org.freedesktop.Hal.Device",
-				"GetPropertyInteger",
-				hal_battery_level_reply, user_data,
-				DBUS_TYPE_STRING, &key,
-				DBUS_TYPE_INVALID);
-}
-
-static void handle_hal_property_modified(DBusMessage *msg)
-{
-	DBusMessageIter iter, array;
-	dbus_int32_t num_changes;
-	const char *path;
-
-	path = dbus_message_get_path(msg);
-
-	dbus_message_iter_init(msg, &iter);
-
-	if (dbus_message_iter_get_arg_type(&iter) != DBUS_TYPE_INT32) {
-		error("Unexpected signature in hal PropertyModified signal");
-		return;
-	}
-
-	dbus_message_iter_get_basic(&iter, &num_changes);
-	dbus_message_iter_next(&iter);
-
-	if (dbus_message_iter_get_arg_type(&iter) != DBUS_TYPE_ARRAY) {
-		error("Unexpected signature in hal PropertyModified signal");
-		return;
-	}
-
-	dbus_message_iter_recurse(&iter, &array);
-
-	while (dbus_message_iter_get_arg_type(&array) != DBUS_TYPE_INVALID) {
-		DBusMessageIter prop;
-		const char *name;
-		dbus_bool_t added, removed;
-
-		dbus_message_iter_recurse(&array, &prop);
-
-		if (!iter_get_basic_args(&prop,
-					DBUS_TYPE_STRING, &name,
-					DBUS_TYPE_BOOLEAN, &added,
-					DBUS_TYPE_BOOLEAN, &removed,
-					DBUS_TYPE_INVALID)) {
-			error("Invalid hal PropertyModified parameters");
-			break;
-		}
-
-		if (g_str_equal(name, "battery.charge_level.last_full"))
-			hal_get_integer(path, name, &battchg_last);
-		else if (g_str_equal(name, "battery.charge_level.current"))
-			hal_get_integer(path, name, &battchg_cur);
-		else if (g_str_equal(name, "battery.charge_level.design"))
-			hal_get_integer(path, name, &battchg_design);
-
-		dbus_message_iter_next(&array);
-	}
-}
-
-static void csd_call_free(struct csd_call *call)
-{
-	if (!call)
-		return;
-
-	g_free(call->object_path);
-	g_free(call->number);
-
-	g_free(call);
-}
-
-static void parse_call_list(DBusMessageIter *iter)
-{
-	do {
-		DBusMessageIter call_iter;
-		struct csd_call *call;
-		const char *object_path, *number;
-		dbus_uint32_t status;
-		dbus_bool_t originating, terminating, emerg, on_hold, conf;
-
-		if (dbus_message_iter_get_arg_type(iter) != DBUS_TYPE_STRUCT) {
-			error("Unexpected signature in GetCallInfoAll reply");
-			break;
-		}
-
-		dbus_message_iter_recurse(iter, &call_iter);
-
-		if (!iter_get_basic_args(&call_iter,
-					DBUS_TYPE_OBJECT_PATH, &object_path,
-					DBUS_TYPE_UINT32, &status,
-					DBUS_TYPE_BOOLEAN, &originating,
-					DBUS_TYPE_BOOLEAN, &terminating,
-					DBUS_TYPE_BOOLEAN, &emerg,
-					DBUS_TYPE_BOOLEAN, &on_hold,
-					DBUS_TYPE_BOOLEAN, &conf,
-					DBUS_TYPE_STRING, &number,
-					DBUS_TYPE_INVALID)) {
-			error("Parsing call D-Bus parameters failed");
-			break;
-		}
-
-		call = find_call(object_path);
-		if (!call) {
-			call = g_new0(struct csd_call, 1);
-			call->object_path = g_strdup(object_path);
-			call->status = (int) status;
-			calls = g_slist_append(calls, call);
-			DBG("telephony-maemo: new csd call instance at %s",
-								object_path);
-		}
-
-		if (call->status == CSD_CALL_STATUS_IDLE)
-			continue;
-
-		/* CSD gives incorrect call_hold property sometimes */
-		if ((call->status != CSD_CALL_STATUS_HOLD && on_hold) ||
-				(call->status == CSD_CALL_STATUS_HOLD &&
-								!on_hold)) {
-			error("Conflicting call status and on_hold property!");
-			on_hold = call->status == CSD_CALL_STATUS_HOLD;
-		}
-
-		call->originating = originating;
-		call->on_hold = on_hold;
-		call->conference = conf;
-		g_free(call->number);
-		call->number = g_strdup(number);
-
-	} while (dbus_message_iter_next(iter));
-}
-
-static void signal_strength_reply(DBusPendingCall *call, void *user_data)
-{
-	DBusError err;
-	DBusMessage *reply;
-	uint8_t signals_bar, rssi_in_dbm;
-	dbus_int32_t net_err;
-
-	reply = dbus_pending_call_steal_reply(call);
-
-	dbus_error_init(&err);
-	if (dbus_set_error_from_message(&err, reply)) {
-		error("Unable to get signal strength: %s, %s",
-			err.name, err.message);
-		dbus_error_free(&err);
-		goto done;
-	}
-
-	dbus_error_init(&err);
-	if (!dbus_message_get_args(reply, &err,
-					DBUS_TYPE_BYTE, &signals_bar,
-					DBUS_TYPE_BYTE, &rssi_in_dbm,
-					DBUS_TYPE_INT32, &net_err,
-					DBUS_TYPE_INVALID)) {
-		error("Unable to parse signal_strength reply: %s, %s",
-							err.name, err.message);
-		dbus_error_free(&err);
-		goto done;
-	}
-
-	if (net_err != 0) {
-		error("get_signal_strength failed with code %d", net_err);
-		goto done;
-	}
-
-	update_signal_strength(signals_bar);
-
-done:
-	dbus_message_unref(reply);
-}
-
-static int get_signal_strength(void)
-{
-	return send_method_call(NETWORK_BUS_NAME, NETWORK_PATH,
-				NETWORK_INTERFACE, "get_signal_strength",
-				signal_strength_reply, NULL,
-				DBUS_TYPE_INVALID);
-}
-
-static void registration_status_reply(DBusPendingCall *call, void *user_data)
-{
-	DBusError err;
-	DBusMessage *reply;
-	uint8_t status;
-	dbus_uint16_t lac, network_type, supported_services;
-	dbus_uint32_t cell_id, operator_code, country_code;
-	dbus_int32_t net_err;
-
-	reply = dbus_pending_call_steal_reply(call);
-
-	dbus_error_init(&err);
-	if (dbus_set_error_from_message(&err, reply)) {
-		error("Unable to get registration status: %s, %s",
-				err.name, err.message);
-		dbus_error_free(&err);
-		goto done;
-	}
-
-	dbus_error_init(&err);
-	if (!dbus_message_get_args(reply, &err,
-					DBUS_TYPE_BYTE, &status,
-					DBUS_TYPE_UINT16, &lac,
-					DBUS_TYPE_UINT32, &cell_id,
-					DBUS_TYPE_UINT32, &operator_code,
-					DBUS_TYPE_UINT32, &country_code,
-					DBUS_TYPE_BYTE, &network_type,
-					DBUS_TYPE_BYTE, &supported_services,
-					DBUS_TYPE_INT32, &net_err,
-					DBUS_TYPE_INVALID)) {
-		error("Unable to parse registration_status_change reply:"
-					" %s, %s", err.name, err.message);
-		dbus_error_free(&err);
-		goto done;
-	}
-
-	if (net_err != 0) {
-		error("get_registration_status failed with code %d", net_err);
-		goto done;
-	}
-
-	update_registration_status(status, lac, cell_id, operator_code,
-					country_code, network_type,
-					supported_services);
-
-	get_signal_strength();
-
-done:
-	dbus_message_unref(reply);
-}
-
-static int get_registration_status(void)
-{
-	return send_method_call(NETWORK_BUS_NAME, NETWORK_PATH,
-				NETWORK_INTERFACE, "get_registration_status",
-				registration_status_reply, NULL,
-				DBUS_TYPE_INVALID);
-}
-
-static void call_info_reply(DBusPendingCall *call, void *user_data)
-{
-	DBusError err;
-	DBusMessage *reply;
-	DBusMessageIter iter, sub;
-
-	get_calls_active = FALSE;
-
-	reply = dbus_pending_call_steal_reply(call);
-
-	dbus_error_init(&err);
-	if (dbus_set_error_from_message(&err, reply)) {
-		error("csd replied with an error: %s, %s",
-				err.name, err.message);
-		dbus_error_free(&err);
-		goto done;
-	}
-
-	dbus_message_iter_init(reply, &iter);
-
-	if (dbus_message_iter_get_arg_type(&iter) != DBUS_TYPE_ARRAY) {
-		error("Unexpected signature in GetCallInfoAll return");
-		goto done;
-	}
-
-	dbus_message_iter_recurse(&iter, &sub);
-
-	parse_call_list(&sub);
-
-	get_registration_status();
-
-done:
-	dbus_message_unref(reply);
-}
-
-static void hal_find_device_reply(DBusPendingCall *call, void *user_data)
-{
-	DBusError err;
-	DBusMessage *reply;
-	DBusMessageIter iter, sub;
-	const char *path;
-	char match_string[256];
-	int type;
-
-	reply = dbus_pending_call_steal_reply(call);
-
-	dbus_error_init(&err);
-	if (dbus_set_error_from_message(&err, reply)) {
-		error("hald replied with an error: %s, %s",
-				err.name, err.message);
-		dbus_error_free(&err);
-		goto done;
-	}
-
-	dbus_message_iter_init(reply, &iter);
-
-	if (dbus_message_iter_get_arg_type(&iter) != DBUS_TYPE_ARRAY) {
-		error("Unexpected signature in FindDeviceByCapability return");
-		goto done;
-	}
-
-	dbus_message_iter_recurse(&iter, &sub);
-
-	type = dbus_message_iter_get_arg_type(&sub);
-
-	if (type != DBUS_TYPE_OBJECT_PATH && type != DBUS_TYPE_STRING) {
-		error("No hal device with battery capability found");
-		goto done;
-	}
-
-	dbus_message_iter_get_basic(&sub, &path);
-
-	DBG("telephony-maemo: found battery device at %s", path);
-
-	snprintf(match_string, sizeof(match_string),
-			"type='signal',"
-			"path='%s',"
-			"interface='org.freedesktop.Hal.Device',"
-			"member='PropertyModified'", path);
-	dbus_bus_add_match(btd_get_dbus_connection(), match_string, NULL);
-
-	hal_get_integer(path, "battery.charge_level.last_full", &battchg_last);
-	hal_get_integer(path, "battery.charge_level.current", &battchg_cur);
-	hal_get_integer(path, "battery.charge_level.design", &battchg_design);
-
-done:
-	dbus_message_unref(reply);
-}
-
-static void phonebook_read_reply(DBusPendingCall *call, void *user_data)
-{
-	DBusError derr;
-	DBusMessage *reply;
-	const char *name, *number;
-	char **number_type = user_data;
-	dbus_int32_t current_location, err;
-
-	reply = dbus_pending_call_steal_reply(call);
-
-	dbus_error_init(&derr);
-	if (dbus_set_error_from_message(&derr, reply)) {
-		error("SIM.Phonebook replied with an error: %s, %s",
-				derr.name, derr.message);
-		dbus_error_free(&derr);
-		goto done;
-	}
-
-	dbus_error_init(&derr);
-	if (dbus_message_get_args(reply, &derr,
-				DBUS_TYPE_STRING, &name,
-				DBUS_TYPE_STRING, &number,
-				DBUS_TYPE_INT32, &current_location,
-				DBUS_TYPE_INT32, &err,
-				DBUS_TYPE_INVALID) == FALSE) {
-		error("Unable to parse SIM.Phonebook.read arguments: %s, %s",
-				derr.name, derr.message);
-		dbus_error_free(&derr);
-		goto done;
-	}
-
-	if (err != 0) {
-		error("SIM.Phonebook.read failed with error %d", err);
-		if (number_type == &vmbx)
-			vmbx = g_strdup(getenv("VMBX_NUMBER"));
-		goto done;
-	}
-
-	if (number_type == &msisdn) {
-		g_free(msisdn);
-		msisdn = g_strdup(number);
-		DBG("Got MSISDN %s (%s)", number, name);
-	} else {
-		g_free(vmbx);
-		vmbx = g_strdup(number);
-		DBG("Got voice mailbox number %s (%s)", number, name);
-	}
-
-done:
-	dbus_message_unref(reply);
-}
-
-static void csd_init(void)
-{
-	dbus_uint32_t location;
-	uint8_t pb_type, location_type;
-	int ret;
-
-	ret = send_method_call(CSD_CALL_BUS_NAME, CSD_CALL_PATH,
-				CSD_CALL_INTERFACE, "GetCallInfoAll",
-				call_info_reply, NULL, DBUS_TYPE_INVALID);
-	if (ret < 0) {
-		error("Unable to sent GetCallInfoAll method call");
-		return;
-	}
-
-	get_calls_active = TRUE;
-
-	pb_type = SIM_PHONEBOOK_TYPE_MSISDN;
-	location = PHONEBOOK_INDEX_FIRST_ENTRY;
-	location_type = SIM_PHONEBOOK_LOCATION_NEXT;
-
-	ret = send_method_call(SIM_PHONEBOOK_BUS_NAME, SIM_PHONEBOOK_PATH,
-				SIM_PHONEBOOK_INTERFACE, "read",
-				phonebook_read_reply, &msisdn,
-				DBUS_TYPE_BYTE, &pb_type,
-				DBUS_TYPE_INT32, &location,
-				DBUS_TYPE_BYTE, &location_type,
-				DBUS_TYPE_INVALID);
-	if (ret < 0) {
-		error("Unable to send " SIM_PHONEBOOK_INTERFACE ".read()");
-		return;
-	}
-
-	pb_type = SIM_PHONEBOOK_TYPE_MBDN;
-	location = PHONEBOOK_INDEX_FIRST_ENTRY;
-	location_type = SIM_PHONEBOOK_LOCATION_NEXT;
-
-	ret = send_method_call(SIM_PHONEBOOK_BUS_NAME, SIM_PHONEBOOK_PATH,
-				SIM_PHONEBOOK_INTERFACE, "read",
-				phonebook_read_reply, &vmbx,
-				DBUS_TYPE_BYTE, &pb_type,
-				DBUS_TYPE_INT32, &location,
-				DBUS_TYPE_BYTE, &location_type,
-				DBUS_TYPE_INVALID);
-	if (ret < 0) {
-		error("Unable to send " SIM_PHONEBOOK_INTERFACE ".read()");
-		return;
-	}
-}
-
-static uint32_t get_callflag(const char *callerid_setting)
-{
-	if (callerid_setting != NULL) {
-		if (g_str_equal(callerid_setting, "allowed"))
-			return CALL_FLAG_PRESENTATION_ALLOWED;
-		else if (g_str_equal(callerid_setting, "restricted"))
-			return CALL_FLAG_PRESENTATION_RESTRICTED;
-		else
-			return CALL_FLAG_NONE;
-	} else
-		return CALL_FLAG_NONE;
-}
-
-static void generate_flag_file(const char *filename)
-{
-	int fd;
-
-	if (g_file_test(ALLOWED_FLAG_FILE, G_FILE_TEST_EXISTS) ||
-			g_file_test(RESTRICTED_FLAG_FILE, G_FILE_TEST_EXISTS) ||
-			g_file_test(NONE_FLAG_FILE, G_FILE_TEST_EXISTS))
-		return;
-
-	fd = open(filename, O_WRONLY | O_CREAT, 0);
-	if (fd >= 0)
-		close(fd);
-}
-
-static void save_callerid_to_file(const char *callerid_setting)
-{
-	char callerid_file[FILENAME_MAX];
-
-	snprintf(callerid_file, sizeof(callerid_file), "%s%s",
-					CALLERID_BASE, callerid_setting);
-
-	if (g_file_test(ALLOWED_FLAG_FILE, G_FILE_TEST_EXISTS))
-		rename(ALLOWED_FLAG_FILE, callerid_file);
-	else if (g_file_test(RESTRICTED_FLAG_FILE, G_FILE_TEST_EXISTS))
-		rename(RESTRICTED_FLAG_FILE, callerid_file);
-	else if (g_file_test(NONE_FLAG_FILE, G_FILE_TEST_EXISTS))
-		rename(NONE_FLAG_FILE, callerid_file);
-	else
-		generate_flag_file(callerid_file);
-}
-
-static uint32_t callerid_from_file(void)
-{
-	if (g_file_test(ALLOWED_FLAG_FILE, G_FILE_TEST_EXISTS))
-		return CALL_FLAG_PRESENTATION_ALLOWED;
-	else if (g_file_test(RESTRICTED_FLAG_FILE, G_FILE_TEST_EXISTS))
-		return CALL_FLAG_PRESENTATION_RESTRICTED;
-	else if (g_file_test(NONE_FLAG_FILE, G_FILE_TEST_EXISTS))
-		return CALL_FLAG_NONE;
-	else
-		return CALL_FLAG_NONE;
-}
-
-static DBusMessage *set_callerid(DBusConnection *conn, DBusMessage *msg,
-					void *data)
-{
-	const char *callerid_setting;
-
-	if (dbus_message_get_args(msg, NULL, DBUS_TYPE_STRING,
-						&callerid_setting,
-						DBUS_TYPE_INVALID) == FALSE)
-		return btd_error_invalid_args(msg);
-
-	if (g_str_equal(callerid_setting, "allowed") ||
-			g_str_equal(callerid_setting, "restricted") ||
-			g_str_equal(callerid_setting, "none")) {
-		save_callerid_to_file(callerid_setting);
-		callerid = get_callflag(callerid_setting);
-		DBG("telephony-maemo setting callerid flag: %s",
-							callerid_setting);
-		return dbus_message_new_method_return(msg);
-	}
-
-	error("telephony-maemo: invalid argument %s for method call"
-					" SetCallerId", callerid_setting);
-		return btd_error_invalid_args(msg);
-}
-
-static const GDBusMethodTable telephony_maemo_methods[] = {
-	{ GDBUS_ASYNC_METHOD("SetCallerId",
-				GDBUS_ARGS({ "id", "s" }), NULL,
-				set_callerid) },
-	{ }
-};
-
-static void handle_modem_state(DBusMessage *msg)
-{
-	const char *state;
-
-	if (!dbus_message_get_args(msg, NULL, DBUS_TYPE_STRING, &state,
-							DBUS_TYPE_INVALID)) {
-		error("Unexpected modem state parameters");
-		return;
-	}
-
-	DBG("SSC modem state: %s", state);
-
-	if (calls != NULL || get_calls_active)
-		return;
-
-	if (g_str_equal(state, "cmt_ready") || g_str_equal(state, "online"))
-		csd_init();
-}
-
-static void modem_state_reply(DBusPendingCall *call, void *user_data)
-{
-	DBusMessage *reply = dbus_pending_call_steal_reply(call);
-	DBusError err;
-
-	dbus_error_init(&err);
-	if (dbus_set_error_from_message(&err, reply)) {
-		error("get_modem_status: %s, %s", err.name, err.message);
-		dbus_error_free(&err);
-	} else
-		handle_modem_state(reply);
-
-	dbus_message_unref(reply);
-}
-
-static DBusHandlerResult signal_filter(DBusConnection *conn,
-						DBusMessage *msg, void *data)
-{
-	const char *path = dbus_message_get_path(msg);
-
-	if (dbus_message_get_type(msg) != DBUS_MESSAGE_TYPE_SIGNAL)
-		return DBUS_HANDLER_RESULT_NOT_YET_HANDLED;
-
-	if (dbus_message_is_signal(msg, CSD_CALL_INTERFACE, "Coming"))
-		handle_incoming_call(msg);
-	else if (dbus_message_is_signal(msg, CSD_CALL_INTERFACE, "Created"))
-		handle_outgoing_call(msg);
-	else if (dbus_message_is_signal(msg, CSD_CALL_INTERFACE,
-							"CreateRequested"))
-		handle_create_requested(msg);
-	else if (dbus_message_is_signal(msg, CSD_CALL_INSTANCE, "CallStatus"))
-		handle_call_status(msg, path);
-	else if (dbus_message_is_signal(msg, CSD_CALL_CONFERENCE, "Joined"))
-		handle_conference(msg, TRUE);
-	else if (dbus_message_is_signal(msg, CSD_CALL_CONFERENCE, "Left"))
-		handle_conference(msg, FALSE);
-	else if (dbus_message_is_signal(msg, NETWORK_INTERFACE,
-					"registration_status_change"))
-		handle_registration_status_change(msg);
-	else if (dbus_message_is_signal(msg, NETWORK_INTERFACE,
-					"signal_strength_change"))
-		handle_signal_strength_change(msg);
-	else if (dbus_message_is_signal(msg, "org.freedesktop.Hal.Device",
-					"PropertyModified"))
-		handle_hal_property_modified(msg);
-	else if (dbus_message_is_signal(msg, SSC_DBUS_IFACE,
-						"modem_state_changed_ind"))
-		handle_modem_state(msg);
-
-	return DBUS_HANDLER_RESULT_NOT_YET_HANDLED;
-}
-
-int telephony_init(void)
-{
-	DBusConnection *conn = btd_get_dbus_connection();
-	const char *battery_cap = "battery";
-	uint32_t features = AG_FEATURE_EC_ANDOR_NR |
-				AG_FEATURE_INBAND_RINGTONE |
-				AG_FEATURE_REJECT_A_CALL |
-				AG_FEATURE_ENHANCED_CALL_STATUS |
-				AG_FEATURE_ENHANCED_CALL_CONTROL |
-				AG_FEATURE_EXTENDED_ERROR_RESULT_CODES |
-				AG_FEATURE_THREE_WAY_CALLING;
-
-	if (!dbus_connection_add_filter(conn, signal_filter,
-						NULL, NULL))
-		error("Can't add signal filter");
-
-	dbus_bus_add_match(conn,
-			"type=signal,interface=" CSD_CALL_INTERFACE, NULL);
-	dbus_bus_add_match(conn,
-			"type=signal,interface=" CSD_CALL_INSTANCE, NULL);
-	dbus_bus_add_match(conn,
-			"type=signal,interface=" CSD_CALL_CONFERENCE, NULL);
-	dbus_bus_add_match(conn,
-			"type=signal,interface=" NETWORK_INTERFACE, NULL);
-	dbus_bus_add_match(conn,
-				"type=signal,interface=" SSC_DBUS_IFACE
-				",member=modem_state_changed_ind", NULL);
-
-	if (send_method_call(SSC_DBUS_NAME, SSC_DBUS_PATH, SSC_DBUS_IFACE,
-					"get_modem_state", modem_state_reply,
-					NULL, DBUS_TYPE_INVALID) < 0)
-		error("Unable to send " SSC_DBUS_IFACE ".get_modem_state()");
-
-	generate_flag_file(NONE_FLAG_FILE);
-	callerid = callerid_from_file();
-
-	if (!g_dbus_register_interface(conn, TELEPHONY_MAEMO_PATH,
-			TELEPHONY_MAEMO_INTERFACE, telephony_maemo_methods,
-			NULL, NULL, NULL, NULL)) {
-		error("telephony-maemo interface %s init failed on path %s",
-			TELEPHONY_MAEMO_INTERFACE, TELEPHONY_MAEMO_PATH);
-	}
-
-	DBG("telephony-maemo registering %s interface on path %s",
-			TELEPHONY_MAEMO_INTERFACE, TELEPHONY_MAEMO_PATH);
-
-	telephony_ready_ind(features, maemo_indicators, BTRH_NOT_SUPPORTED,
-								chld_str);
-	if (send_method_call("org.freedesktop.Hal",
-				"/org/freedesktop/Hal/Manager",
-				"org.freedesktop.Hal.Manager",
-				"FindDeviceByCapability",
-				hal_find_device_reply, NULL,
-				DBUS_TYPE_STRING, &battery_cap,
-				DBUS_TYPE_INVALID) < 0)
-		error("Unable to send HAL method call");
-
-	return 0;
-}
-
-void telephony_exit(void)
-{
-	g_slist_foreach(calls, (GFunc) csd_call_free, NULL);
-	g_slist_free(calls);
-	calls = NULL;
-
-	dbus_connection_remove_filter(btd_get_dbus_connection(),
-							signal_filter, NULL);
-
-	telephony_deinit();
-}
-- 
1.7.11.7


^ permalink raw reply related

* [PATCH BlueZ 05/13] build: Remove telephony-maemo6.c
From: Luiz Augusto von Dentz @ 2012-11-13 13:21 UTC (permalink / raw)
  To: linux-bluetooth
In-Reply-To: <1352812880-7306-1-git-send-email-luiz.dentz@gmail.com>

From: Luiz Augusto von Dentz <luiz.von.dentz@intel.com>

---
 Makefile.am              |    6 +-
 audio/telephony-maemo6.c | 2196 ----------------------------------------------
 2 files changed, 2 insertions(+), 2200 deletions(-)
 delete mode 100644 audio/telephony-maemo6.c

diff --git a/Makefile.am b/Makefile.am
index 9b24589..b7e861b 100644
--- a/Makefile.am
+++ b/Makefile.am
@@ -126,8 +126,7 @@ builtin_nodist += audio/telephony.c
 noinst_LIBRARIES += audio/libtelephony.a
 
 audio_libtelephony_a_SOURCES = audio/telephony.h audio/telephony-dummy.c \
-				audio/telephony-ofono.c \
-				audio/telephony-maemo6.c
+				audio/telephony-ofono.c
 endif
 
 if SAPPLUGIN
@@ -316,8 +315,7 @@ EXTRA_DIST += src/genbuiltin src/bluetooth.conf src/org.bluez.service \
 			profiles/input/input.conf profiles/proximity/proximity.conf \
 			audio/audio.conf audio/telephony-dummy.c \
 			audio/telephony-ofono.c \
-			audio/telephony-maemo6.c profiles/sap/sap-dummy.c \
-			profiles/sap/sap-u8500.c
+			profiles/sap/sap-dummy.c profiles/sap/sap-u8500.c
 
 include Makefile.tools
 
diff --git a/audio/telephony-maemo6.c b/audio/telephony-maemo6.c
deleted file mode 100644
index ef997ca..0000000
--- a/audio/telephony-maemo6.c
+++ /dev/null
@@ -1,2196 +0,0 @@
-/*
- *
- *  BlueZ - Bluetooth protocol stack for Linux
- *
- *  Copyright (C) 2008-2010  Nokia Corporation
- *  Copyright (C) 2004-2010  Marcel Holtmann <marcel@holtmann.org>
- *
- *
- *  This program is free software; you can redistribute it and/or modify
- *  it under the terms of the GNU General Public License as published by
- *  the Free Software Foundation; either version 2 of the License, or
- *  (at your option) any later version.
- *
- *  This program is distributed in the hope that it will be useful,
- *  but WITHOUT ANY WARRANTY; without even the implied warranty of
- *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
- *  GNU General Public License for more details.
- *
- *  You should have received a copy of the GNU General Public License
- *  along with this program; if not, write to the Free Software
- *  Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
- *
- */
-
-#ifdef HAVE_CONFIG_H
-#include <config.h>
-#endif
-
-#include <stdlib.h>
-#include <stdio.h>
-#include <unistd.h>
-#include <fcntl.h>
-#include <stdint.h>
-#include <string.h>
-#include <glib.h>
-#include <dbus/dbus.h>
-#include <gdbus.h>
-
-#include <bluetooth/sdp.h>
-
-#include "dbus-common.h"
-#include "log.h"
-#include "telephony.h"
-#include "error.h"
-
-/* SSC D-Bus definitions */
-#define SSC_DBUS_NAME  "com.nokia.phone.SSC"
-#define SSC_DBUS_IFACE "com.nokia.phone.SSC"
-#define SSC_DBUS_PATH  "/com/nokia/phone/SSC"
-
-/* libcsnet D-Bus definitions */
-#define CSD_CSNET_BUS_NAME	"com.nokia.csd.CSNet"
-#define CSD_CSNET_PATH		"/com/nokia/csd/csnet"
-#define CSD_CSNET_IFACE		"com.nokia.csd.CSNet"
-#define CSD_CSNET_REGISTRATION	"com.nokia.csd.CSNet.NetworkRegistration"
-#define CSD_CSNET_OPERATOR	"com.nokia.csd.CSNet.NetworkOperator"
-#define CSD_CSNET_SIGNAL	"com.nokia.csd.CSNet.SignalStrength"
-
-enum net_registration_status {
-	NETWORK_REG_STATUS_HOME,
-	NETWORK_REG_STATUS_ROAMING,
-	NETWORK_REG_STATUS_OFFLINE,
-	NETWORK_REG_STATUS_SEARCHING,
-	NETWORK_REG_STATUS_NO_SIM,
-	NETWORK_REG_STATUS_POWEROFF,
-	NETWORK_REG_STATUS_POWERSAFE,
-	NETWORK_REG_STATUS_NO_COVERAGE,
-	NETWORK_REG_STATUS_REJECTED,
-	NETWORK_REG_STATUS_UNKOWN
-};
-
-/* CSD CALL plugin D-Bus definitions */
-#define CSD_CALL_BUS_NAME	"com.nokia.csd.Call"
-#define CSD_CALL_INTERFACE	"com.nokia.csd.Call"
-#define CSD_CALL_INSTANCE	"com.nokia.csd.Call.Instance"
-#define CSD_CALL_CONFERENCE	"com.nokia.csd.Call.Conference"
-#define CSD_CALL_PATH		"/com/nokia/csd/call"
-#define CSD_CALL_CONFERENCE_PATH "/com/nokia/csd/call/conference"
-
-/* Call status values as exported by the CSD CALL plugin */
-#define CSD_CALL_STATUS_IDLE			0
-#define CSD_CALL_STATUS_CREATE			1
-#define CSD_CALL_STATUS_COMING			2
-#define CSD_CALL_STATUS_PROCEEDING		3
-#define CSD_CALL_STATUS_MO_ALERTING		4
-#define CSD_CALL_STATUS_MT_ALERTING		5
-#define CSD_CALL_STATUS_WAITING			6
-#define CSD_CALL_STATUS_ANSWERED		7
-#define CSD_CALL_STATUS_ACTIVE			8
-#define CSD_CALL_STATUS_MO_RELEASE		9
-#define CSD_CALL_STATUS_MT_RELEASE		10
-#define CSD_CALL_STATUS_HOLD_INITIATED		11
-#define CSD_CALL_STATUS_HOLD			12
-#define CSD_CALL_STATUS_RETRIEVE_INITIATED	13
-#define CSD_CALL_STATUS_RECONNECT_PENDING	14
-#define CSD_CALL_STATUS_TERMINATED		15
-#define CSD_CALL_STATUS_SWAP_INITIATED		16
-
-#define CALL_FLAG_NONE				0
-#define CALL_FLAG_PRESENTATION_ALLOWED		0x01
-#define CALL_FLAG_PRESENTATION_RESTRICTED	0x02
-
-/* SIM Phonebook D-Bus definitions */
-#define CSD_SIMPB_BUS_NAME			"com.nokia.csd.SIM"
-#define CSD_SIMPB_INTERFACE			"com.nokia.csd.SIM.Phonebook"
-#define CSD_SIMPB_PATH				"/com/nokia/csd/sim/phonebook"
-
-#define CSD_SIMPB_TYPE_ADN			"ADN"
-#define CSD_SIMPB_TYPE_FDN			"FDN"
-#define CSD_SIMPB_TYPE_SDN			"SDN"
-#define CSD_SIMPB_TYPE_VMBX			"VMBX"
-#define CSD_SIMPB_TYPE_MBDN			"MBDN"
-#define CSD_SIMPB_TYPE_EN			"EN"
-#define CSD_SIMPB_TYPE_MSISDN			"MSISDN"
-
-/* OHM plugin D-Bus definitions */
-#define OHM_BUS_NAME		"com.nokia.NonGraphicFeedback1"
-#define OHM_INTERFACE		"com.nokia.NonGraphicFeedback1"
-#define OHM_PATH		"/com/nokia/NonGraphicFeedback1"
-
-/* tone-genenerator D-Bus definitions */
-#define TONEGEN_BUS_NAME	"com.Nokia.Telephony.Tones"
-#define TONEGEN_INTERFACE	"com.Nokia.Telephony.Tones"
-#define TONEGEN_PATH		"/com/Nokia/Telephony/Tones"
-
-/* tone-generator DTMF definitions */
-#define DTMF_ASTERISK   10
-#define DTMF_HASHMARK   11
-#define DTMF_A          12
-#define DTMF_B          13
-#define DTMF_C          14
-#define DTMF_D          15
-
-#define FEEDBACK_TONE_DURATION			200
-
-struct csd_call {
-	char *object_path;
-	int status;
-	gboolean originating;
-	gboolean emergency;
-	gboolean on_hold;
-	gboolean conference;
-	char *number;
-	gboolean setup;
-};
-
-static struct {
-	char *operator_name;
-	uint8_t status;
-	int32_t signal_bars;
-} net = {
-	.operator_name = NULL,
-	.status = NETWORK_REG_STATUS_UNKOWN,
-	/* Init as 0 meaning inactive mode. In modem power off state
-	 * can be be -1, but we treat all values as 0s regardless
-	 * inactive or power off. */
-	.signal_bars = 0,
-};
-
-struct pending_req {
-	DBusPendingCall *call;
-	void *user_data;
-};
-
-static int get_property(const char *iface, const char *prop);
-
-static GSList *calls = NULL;
-static GSList *watches = NULL;
-static GSList *pending = NULL;
-
-/* Reference count for determining the call indicator status */
-static GSList *active_calls = NULL;
-
-/* Queue of DTMF tones to play */
-static GSList *tones = NULL;
-static guint create_tones_timer = 0;
-
-static char *msisdn = NULL;	/* Subscriber number */
-static char *vmbx = NULL;	/* Voice mailbox number */
-
-/* HAL battery namespace key values */
-static int battchg_cur = -1;	/* "battery.charge_level.current" */
-static int battchg_last = -1;	/* "battery.charge_level.last_full" */
-static int battchg_design = -1;	/* "battery.charge_level.design" */
-
-static gboolean get_calls_active = FALSE;
-
-static gboolean events_enabled = FALSE;
-
-/* Supported set of call hold operations */
-static const char *chld_str = "0,1,1x,2,2x,3,4";
-
-/* Timer for tracking call creation requests */
-static guint create_request_timer = 0;
-
-static struct indicator maemo_indicators[] =
-{
-	{ "battchg",	"0-5",	5,	TRUE },
-	/* signal strength in terms of bars */
-	{ "signal",	"0-5",	0,	TRUE },
-	{ "service",	"0,1",	0,	TRUE },
-	{ "call",	"0,1",	0,	TRUE },
-	{ "callsetup",	"0-3",	0,	TRUE },
-	{ "callheld",	"0-2",	0,	FALSE },
-	{ "roam",	"0,1",	0,	TRUE },
-	{ NULL }
-};
-
-static char *call_status_str[] = {
-	"IDLE",
-	"CREATE",
-	"COMING",
-	"PROCEEDING",
-	"MO_ALERTING",
-	"MT_ALERTING",
-	"WAITING",
-	"ANSWERED",
-	"ACTIVE",
-	"MO_RELEASE",
-	"MT_RELEASE",
-	"HOLD_INITIATED",
-	"HOLD",
-	"RETRIEVE_INITIATED",
-	"RECONNECT_PENDING",
-	"TERMINATED",
-	"SWAP_INITIATED",
-	"???"
-};
-
-static int send_method_call(const char *dest, const char *path,
-				const char *interface, const char *method,
-				DBusPendingCallNotifyFunction cb,
-				void *user_data, int type, ...)
-{
-	DBusConnection *conn = btd_get_dbus_connection();
-	DBusMessage *msg;
-	DBusPendingCall *call;
-	va_list args;
-	struct pending_req *req;
-
-	msg = dbus_message_new_method_call(dest, path, interface, method);
-	if (!msg) {
-		error("Unable to allocate new D-Bus %s message", method);
-		return -ENOMEM;
-	}
-
-	va_start(args, type);
-
-	if (!dbus_message_append_args_valist(msg, type, args)) {
-		dbus_message_unref(msg);
-		va_end(args);
-		return -EIO;
-	}
-
-	va_end(args);
-
-	if (!cb) {
-		g_dbus_send_message(conn, msg);
-		return 0;
-	}
-
-	if (!dbus_connection_send_with_reply(conn, msg, &call, -1)) {
-		error("Sending %s failed", method);
-		dbus_message_unref(msg);
-		return -EIO;
-	}
-
-	dbus_pending_call_set_notify(call, cb, user_data, NULL);
-
-	req = g_new0(struct pending_req, 1);
-	req->call = call;
-	req->user_data = user_data;
-
-	pending = g_slist_prepend(pending, req);
-	dbus_message_unref(msg);
-
-	return 0;
-}
-
-static struct csd_call *find_call(const char *path)
-{
-	GSList *l;
-
-	for (l = calls; l != NULL; l = l->next) {
-		struct csd_call *call = l->data;
-
-		if (g_str_equal(call->object_path, path))
-			return call;
-	}
-
-	return NULL;
-}
-
-static struct csd_call *find_non_held_call(void)
-{
-	GSList *l;
-
-	for (l = calls; l != NULL; l = l->next) {
-		struct csd_call *call = l->data;
-
-		if (call->status == CSD_CALL_STATUS_IDLE)
-			continue;
-
-		if (call->status != CSD_CALL_STATUS_HOLD)
-			return call;
-	}
-
-	return NULL;
-}
-
-static struct csd_call *find_non_idle_call(void)
-{
-	GSList *l;
-
-	for (l = calls; l != NULL; l = l->next) {
-		struct csd_call *call = l->data;
-
-		if (call->status != CSD_CALL_STATUS_IDLE)
-			return call;
-	}
-
-	return NULL;
-}
-
-static struct csd_call *find_call_with_status(int status)
-{
-	GSList *l;
-
-	for (l = calls; l != NULL; l = l->next) {
-		struct csd_call *call = l->data;
-
-		if (call->status == status)
-			return call;
-	}
-
-	return NULL;
-}
-
-static int release_conference(void)
-{
-	DBusMessage *msg;
-
-	DBG("telephony-maemo6: releasing conference call");
-
-	msg = dbus_message_new_method_call(CSD_CALL_BUS_NAME,
-						CSD_CALL_CONFERENCE_PATH,
-						CSD_CALL_INSTANCE,
-						"Release");
-	if (!msg) {
-		error("Unable to allocate new D-Bus message");
-		return -ENOMEM;
-	}
-
-	g_dbus_send_message(btd_get_dbus_connection(), msg);
-
-	return 0;
-}
-
-static int release_call(struct csd_call *call)
-{
-	DBusMessage *msg;
-
-	msg = dbus_message_new_method_call(CSD_CALL_BUS_NAME,
-						call->object_path,
-						CSD_CALL_INSTANCE,
-						"Release");
-	if (!msg) {
-		error("Unable to allocate new D-Bus message");
-		return -ENOMEM;
-	}
-
-	g_dbus_send_message(btd_get_dbus_connection(), msg);
-
-	return 0;
-}
-
-static int answer_call(struct csd_call *call)
-{
-	DBusMessage *msg;
-
-	msg = dbus_message_new_method_call(CSD_CALL_BUS_NAME,
-						call->object_path,
-						CSD_CALL_INSTANCE,
-						"Answer");
-	if (!msg) {
-		error("Unable to allocate new D-Bus message");
-		return -ENOMEM;
-	}
-
-	g_dbus_send_message(btd_get_dbus_connection(), msg);
-
-	return 0;
-}
-
-static struct pending_req *find_request(const DBusPendingCall *call)
-{
-	GSList *l;
-
-	for (l = pending; l; l = l->next) {
-		struct pending_req *req = l->data;
-
-		if (req->call == call)
-			return req;
-	}
-
-	return NULL;
-}
-
-static void pending_req_finalize(void *data)
-{
-	struct pending_req *req = data;
-
-	if (!dbus_pending_call_get_completed(req->call))
-		dbus_pending_call_cancel(req->call);
-
-	dbus_pending_call_unref(req->call);
-	g_free(req);
-}
-
-static void remove_pending(DBusPendingCall *call)
-{
-	struct pending_req *req = find_request(call);
-
-	pending = g_slist_remove(pending, req);
-	pending_req_finalize(req);
-}
-
-static void stop_ringtone_reply(DBusPendingCall *call, void *user_data)
-{
-	struct csd_call *coming = user_data;
-
-	remove_pending(call);
-	answer_call(coming);
-}
-
-static int stop_ringtone_and_answer(struct csd_call *call)
-{
-	int ret;
-
-	ret = send_method_call(OHM_BUS_NAME, OHM_PATH,
-				OHM_INTERFACE, "StopRingtone",
-				stop_ringtone_reply, call,
-				DBUS_TYPE_INVALID);
-	if (ret < 0)
-		return answer_call(call);
-
-	return 0;
-}
-
-static int split_call(struct csd_call *call)
-{
-	DBusMessage *msg;
-
-	msg = dbus_message_new_method_call(CSD_CALL_BUS_NAME,
-						call->object_path,
-						CSD_CALL_INSTANCE,
-						"Split");
-	if (!msg) {
-		error("Unable to allocate new D-Bus message");
-		return -ENOMEM;
-	}
-
-	g_dbus_send_message(btd_get_dbus_connection(), msg);
-
-	return 0;
-}
-
-static int unhold_call(struct csd_call *call)
-{
-	DBusMessage *msg;
-
-	msg = dbus_message_new_method_call(CSD_CALL_BUS_NAME, CSD_CALL_PATH,
-						CSD_CALL_INTERFACE,
-						"Unhold");
-	if (!msg) {
-		error("Unable to allocate new D-Bus message");
-		return -ENOMEM;
-	}
-
-	g_dbus_send_message(btd_get_dbus_connection(), msg);
-
-	return 0;
-}
-
-static int hold_call(struct csd_call *call)
-{
-	DBusMessage *msg;
-
-	msg = dbus_message_new_method_call(CSD_CALL_BUS_NAME, CSD_CALL_PATH,
-						CSD_CALL_INTERFACE,
-						"Hold");
-	if (!msg) {
-		error("Unable to allocate new D-Bus message");
-		return -ENOMEM;
-	}
-
-	g_dbus_send_message(btd_get_dbus_connection(), msg);
-
-	return 0;
-}
-
-static int swap_calls(void)
-{
-	DBusMessage *msg;
-
-	msg = dbus_message_new_method_call(CSD_CALL_BUS_NAME, CSD_CALL_PATH,
-						CSD_CALL_INTERFACE,
-						"Swap");
-	if (!msg) {
-		error("Unable to allocate new D-Bus message");
-		return -ENOMEM;
-	}
-
-	g_dbus_send_message(btd_get_dbus_connection(), msg);
-
-	return 0;
-}
-
-static int create_conference(void)
-{
-	DBusMessage *msg;
-
-	msg = dbus_message_new_method_call(CSD_CALL_BUS_NAME, CSD_CALL_PATH,
-						CSD_CALL_INTERFACE,
-						"Conference");
-	if (!msg) {
-		error("Unable to allocate new D-Bus message");
-		return -ENOMEM;
-	}
-
-	g_dbus_send_message(btd_get_dbus_connection(), msg);
-
-	return 0;
-}
-
-static int call_transfer(void)
-{
-	DBusMessage *msg;
-
-	msg = dbus_message_new_method_call(CSD_CALL_BUS_NAME, CSD_CALL_PATH,
-						CSD_CALL_INTERFACE,
-						"Transfer");
-	if (!msg) {
-		error("Unable to allocate new D-Bus message");
-		return -ENOMEM;
-	}
-
-	g_dbus_send_message(btd_get_dbus_connection(), msg);
-
-	return 0;
-}
-
-static int number_type(const char *number)
-{
-	if (number == NULL)
-		return NUMBER_TYPE_TELEPHONY;
-
-	if (number[0] == '+' || strncmp(number, "00", 2) == 0)
-		return NUMBER_TYPE_INTERNATIONAL;
-
-	return NUMBER_TYPE_TELEPHONY;
-}
-
-void telephony_device_connected(void *telephony_device)
-{
-	struct csd_call *coming;
-
-	DBG("telephony-maemo6: device %p connected", telephony_device);
-
-	coming = find_call_with_status(CSD_CALL_STATUS_MT_ALERTING);
-	if (coming) {
-		if (find_call_with_status(CSD_CALL_STATUS_ACTIVE))
-			telephony_call_waiting_ind(coming->number,
-						number_type(coming->number));
-		else
-			telephony_incoming_call_ind(coming->number,
-						number_type(coming->number));
-	}
-}
-
-static void remove_pending_by_data(gpointer data, gpointer user_data)
-{
-	struct pending_req *req = data;
-
-	if (req->user_data == user_data) {
-		pending = g_slist_remove(pending, req);
-		pending_req_finalize(req);
-	}
-}
-
-void telephony_device_disconnected(void *telephony_device)
-{
-	DBG("telephony-maemo6: device %p disconnected", telephony_device);
-	events_enabled = FALSE;
-
-	g_slist_foreach(pending, remove_pending_by_data, telephony_device);
-}
-
-void telephony_event_reporting_req(void *telephony_device, int ind)
-{
-	events_enabled = ind == 1 ? TRUE : FALSE;
-
-	telephony_event_reporting_rsp(telephony_device, CME_ERROR_NONE);
-}
-
-void telephony_response_and_hold_req(void *telephony_device, int rh)
-{
-	telephony_response_and_hold_rsp(telephony_device,
-						CME_ERROR_NOT_SUPPORTED);
-}
-
-void telephony_terminate_call_req(void *telephony_device)
-{
-	struct csd_call *call;
-	struct csd_call *alerting;
-	int err;
-
-	call = find_call_with_status(CSD_CALL_STATUS_ACTIVE);
-	if (!call)
-		call = find_non_idle_call();
-
-	if (!call) {
-		error("No active call");
-		telephony_terminate_call_rsp(telephony_device,
-						CME_ERROR_NOT_ALLOWED);
-		return;
-	}
-
-	alerting = find_call_with_status(CSD_CALL_STATUS_MO_ALERTING);
-	if (call->on_hold && alerting)
-		err = release_call(alerting);
-	else if (call->conference)
-		err = release_conference();
-	else
-		err = release_call(call);
-
-	if (err < 0)
-		telephony_terminate_call_rsp(telephony_device,
-						CME_ERROR_AG_FAILURE);
-	else
-		telephony_terminate_call_rsp(telephony_device, CME_ERROR_NONE);
-}
-
-void telephony_answer_call_req(void *telephony_device)
-{
-	struct csd_call *call;
-
-	call = find_call_with_status(CSD_CALL_STATUS_COMING);
-	if (!call)
-		call = find_call_with_status(CSD_CALL_STATUS_MT_ALERTING);
-
-	if (!call)
-		call = find_call_with_status(CSD_CALL_STATUS_PROCEEDING);
-
-	if (!call)
-		call = find_call_with_status(CSD_CALL_STATUS_WAITING);
-
-	if (!call) {
-		telephony_answer_call_rsp(telephony_device,
-						CME_ERROR_NOT_ALLOWED);
-		return;
-	}
-
-	if (stop_ringtone_and_answer(call) < 0)
-		telephony_answer_call_rsp(telephony_device,
-						CME_ERROR_AG_FAILURE);
-	else
-		telephony_answer_call_rsp(telephony_device, CME_ERROR_NONE);
-}
-
-static void create_call_reply(DBusPendingCall *call, void *user_data)
-{
-	DBusError err;
-	DBusMessage *reply;
-	void *telephony_device = user_data;
-
-	reply = dbus_pending_call_steal_reply(call);
-
-	dbus_error_init(&err);
-	if (dbus_set_error_from_message(&err, reply)) {
-		error("csd replied with an error: %s, %s",
-				err.name, err.message);
-		if (g_strcmp0(err.name,
-				"com.nokia.csd.Call.Error.CSInactive") == 0)
-			telephony_dial_number_rsp(telephony_device,
-						CME_ERROR_NO_NETWORK_SERVICE);
-		else
-			telephony_dial_number_rsp(telephony_device,
-							CME_ERROR_AG_FAILURE);
-		dbus_error_free(&err);
-	} else
-		telephony_dial_number_rsp(telephony_device, CME_ERROR_NONE);
-
-	dbus_message_unref(reply);
-	remove_pending(call);
-}
-
-void telephony_last_dialed_number_req(void *telephony_device)
-{
-	int ret;
-
-	DBG("telephony-maemo6: last dialed number request");
-
-	ret = send_method_call(CSD_CALL_BUS_NAME, CSD_CALL_PATH,
-				CSD_CALL_INTERFACE, "CreateFromLast",
-				create_call_reply, telephony_device,
-				DBUS_TYPE_INVALID);
-	if (ret < 0)
-		telephony_dial_number_rsp(telephony_device,
-						CME_ERROR_AG_FAILURE);
-}
-
-static const char *memory_dial_lookup(int location)
-{
-	if (location == 1)
-		return vmbx;
-	else
-		return NULL;
-}
-
-void telephony_dial_number_req(void *telephony_device, const char *number)
-{
-	int ret;
-
-	DBG("telephony-maemo6: dial request to %s", number);
-
-	if (strncmp(number, "*31#", 4) == 0)
-		number += 4;
-	else if (strncmp(number, "#31#", 4) == 0)
-		number += 4;
-	else if (number[0] == '>') {
-		const char *location = &number[1];
-
-		number = memory_dial_lookup(strtol(&number[1], NULL, 0));
-		if (!number) {
-			error("No number at memory location %s", location);
-			telephony_dial_number_rsp(telephony_device,
-						CME_ERROR_INVALID_INDEX);
-			return;
-		}
-	}
-
-	ret = send_method_call(CSD_CALL_BUS_NAME, CSD_CALL_PATH,
-				CSD_CALL_INTERFACE, "Create",
-				create_call_reply, telephony_device,
-				DBUS_TYPE_STRING, &number,
-				DBUS_TYPE_INVALID);
-	if (ret < 0)
-		telephony_dial_number_rsp(telephony_device,
-						CME_ERROR_AG_FAILURE);
-}
-
-static void start_dtmf_reply(DBusPendingCall *call, void *user_data)
-{
-	DBusError err;
-	DBusMessage *reply;
-
-	reply = dbus_pending_call_steal_reply(call);
-
-	dbus_error_init(&err);
-	if (dbus_set_error_from_message(&err, reply)) {
-		error("csd replied with an error: %s, %s",
-				err.name, err.message);
-
-		dbus_error_free(&err);
-	} else
-		send_method_call(CSD_CALL_BUS_NAME, CSD_CALL_PATH,
-				CSD_CALL_INTERFACE, "StopDTMF",
-				NULL, NULL,
-				DBUS_TYPE_INVALID);
-
-	dbus_message_unref(reply);
-	remove_pending(call);
-}
-
-static void start_dtmf(void *telephony_device, char tone)
-{
-	int ret;
-
-	/*
-	 * Stop tone immediately, modem will place it in queue and play
-	 * required time.
-	 */
-	ret = send_method_call(CSD_CALL_BUS_NAME, CSD_CALL_PATH,
-				CSD_CALL_INTERFACE, "StartDTMF",
-				start_dtmf_reply, NULL,
-				DBUS_TYPE_BYTE, &tone,
-				DBUS_TYPE_INVALID);
-	if (ret < 0) {
-		telephony_transmit_dtmf_rsp(telephony_device,
-						CME_ERROR_AG_FAILURE);
-		return;
-	}
-
-	telephony_transmit_dtmf_rsp(telephony_device, CME_ERROR_NONE);
-}
-
-static int tonegen_startevent(char tone)
-{
-	int ret;
-	dbus_uint32_t event_tone;
-	dbus_int32_t dbm0 = -15;
-	dbus_uint32_t duration = 150;
-
-	switch (tone) {
-	case '*':
-		event_tone = DTMF_ASTERISK;
-		break;
-	case '#':
-		event_tone = DTMF_HASHMARK;
-		break;
-	case 'A':
-		event_tone = DTMF_A;
-		break;
-	case 'B':
-		event_tone = DTMF_B;
-		break;
-	case 'C':
-		event_tone = DTMF_C;
-		break;
-	case 'D':
-		event_tone = DTMF_D;
-		break;
-	default:
-		ret = g_ascii_digit_value(tone);
-		if (ret < 0)
-			return -EINVAL;
-		event_tone = ret;
-	}
-
-	ret = send_method_call(TONEGEN_BUS_NAME, TONEGEN_PATH,
-				TONEGEN_INTERFACE, "StartEventTone",
-				NULL, NULL,
-				DBUS_TYPE_UINT32, &event_tone,
-				DBUS_TYPE_INT32, &dbm0,
-				DBUS_TYPE_UINT32, &duration,
-				DBUS_TYPE_INVALID);
-	return ret;
-}
-
-static gboolean stop_feedback_tone(gpointer user_data)
-{
-	if (g_slist_length(tones) > 0) {
-		gpointer ptone;
-		int ret;
-
-		send_method_call(TONEGEN_BUS_NAME, TONEGEN_PATH,
-				TONEGEN_INTERFACE, "StopTone",
-				NULL, NULL,
-				DBUS_TYPE_INVALID);
-
-		ptone = g_slist_nth_data(tones, 0);
-		tones = g_slist_remove(tones, ptone);
-
-		ret = tonegen_startevent(GPOINTER_TO_UINT(ptone));
-		if (ret < 0)
-			goto done;
-
-		return TRUE;
-	}
-done:
-	return FALSE;
-}
-
-static void tones_timer_notify(gpointer data)
-{
-	send_method_call(TONEGEN_BUS_NAME, TONEGEN_PATH,
-				TONEGEN_INTERFACE, "StopTone",
-				NULL, NULL,
-				DBUS_TYPE_INVALID);
-	g_slist_free(tones);
-	tones = NULL;
-
-	create_tones_timer = 0;
-}
-
-static void start_feedback_tone(char tone)
-{
-	if (!create_tones_timer) {
-		int ret;
-
-		ret = tonegen_startevent(tone);
-		if (ret < 0)
-			return;
-
-		create_tones_timer = g_timeout_add_full(G_PRIORITY_DEFAULT,
-						FEEDBACK_TONE_DURATION,
-						stop_feedback_tone,
-						NULL,
-						tones_timer_notify);
-	} else {
-		glong dtmf_tone = tone;
-
-		DBG("add %c to queue", tone);
-		tones = g_slist_append(tones, GUINT_TO_POINTER(dtmf_tone));
-	}
-}
-
-void telephony_transmit_dtmf_req(void *telephony_device, char tone)
-{
-	DBG("telephony-maemo6: transmit dtmf: %c", tone);
-
-	start_dtmf(telephony_device, tone);
-
-	if (!find_call_with_status(CSD_CALL_STATUS_ACTIVE))
-		error("No active call");
-	else
-		start_feedback_tone(tone);
-}
-
-void telephony_subscriber_number_req(void *telephony_device)
-{
-	DBG("telephony-maemo6: subscriber number request");
-	if (msisdn)
-		telephony_subscriber_number_ind(msisdn,
-						number_type(msisdn),
-						SUBSCRIBER_SERVICE_VOICE);
-	telephony_subscriber_number_rsp(telephony_device, CME_ERROR_NONE);
-}
-
-static int csd_status_to_hfp(struct csd_call *call)
-{
-	switch (call->status) {
-	case CSD_CALL_STATUS_IDLE:
-	case CSD_CALL_STATUS_MO_RELEASE:
-	case CSD_CALL_STATUS_MT_RELEASE:
-	case CSD_CALL_STATUS_TERMINATED:
-		return -1;
-	case CSD_CALL_STATUS_CREATE:
-		return CALL_STATUS_DIALING;
-	case CSD_CALL_STATUS_WAITING:
-		return CALL_STATUS_WAITING;
-	case CSD_CALL_STATUS_PROCEEDING:
-		/* PROCEEDING can happen in outgoing/incoming */
-		if (call->originating)
-			return CALL_STATUS_DIALING;
-
-		/*
-		 * PROCEEDING is followed by WAITING CSD status, therefore
-		 * second incoming call status indication is set immediately
-		 * to waiting.
-		 */
-		if (g_slist_length(active_calls) > 0)
-			return CALL_STATUS_WAITING;
-
-		return CALL_STATUS_INCOMING;
-	case CSD_CALL_STATUS_COMING:
-		if (g_slist_length(active_calls) > 0)
-			return CALL_STATUS_WAITING;
-
-		return CALL_STATUS_INCOMING;
-	case CSD_CALL_STATUS_MO_ALERTING:
-		return CALL_STATUS_ALERTING;
-	case CSD_CALL_STATUS_MT_ALERTING:
-		return CALL_STATUS_INCOMING;
-	case CSD_CALL_STATUS_ANSWERED:
-	case CSD_CALL_STATUS_ACTIVE:
-	case CSD_CALL_STATUS_RECONNECT_PENDING:
-	case CSD_CALL_STATUS_SWAP_INITIATED:
-	case CSD_CALL_STATUS_HOLD_INITIATED:
-		return CALL_STATUS_ACTIVE;
-	case CSD_CALL_STATUS_RETRIEVE_INITIATED:
-	case CSD_CALL_STATUS_HOLD:
-		return CALL_STATUS_HELD;
-	default:
-		return -1;
-	}
-}
-
-void telephony_list_current_calls_req(void *telephony_device)
-{
-	GSList *l;
-	int i;
-
-	DBG("telephony-maemo6: list current calls request");
-
-	for (l = calls, i = 1; l != NULL; l = l->next, i++) {
-		struct csd_call *call = l->data;
-		int status, direction, multiparty;
-
-		status = csd_status_to_hfp(call);
-		if (status < 0)
-			continue;
-
-		direction = call->originating ?
-				CALL_DIR_OUTGOING : CALL_DIR_INCOMING;
-
-		multiparty = call->conference ?
-				CALL_MULTIPARTY_YES : CALL_MULTIPARTY_NO;
-
-		telephony_list_current_call_ind(i, direction, status,
-						CALL_MODE_VOICE, multiparty,
-						call->number,
-						number_type(call->number));
-	}
-
-	telephony_list_current_calls_rsp(telephony_device, CME_ERROR_NONE);
-}
-
-void telephony_operator_selection_req(void *telephony_device)
-{
-	telephony_operator_selection_ind(OPERATOR_MODE_AUTO,
-				net.operator_name ? net.operator_name : "");
-	telephony_operator_selection_rsp(telephony_device, CME_ERROR_NONE);
-}
-
-static void foreach_call_with_status(int status,
-					int (*func)(struct csd_call *call))
-{
-	GSList *l;
-
-	for (l = calls; l != NULL; l = l->next) {
-		struct csd_call *call = l->data;
-
-		if (call->status == status)
-			func(call);
-	}
-}
-
-void telephony_call_hold_req(void *telephony_device, const char *cmd)
-{
-	const char *idx;
-	struct csd_call *call;
-	int err = 0;
-
-	DBG("telephony-maemo6: got call hold request %s", cmd);
-
-	if (strlen(cmd) > 1)
-		idx = &cmd[1];
-	else
-		idx = NULL;
-
-	if (idx)
-		call = g_slist_nth_data(calls, strtol(idx, NULL, 0) - 1);
-	else
-		call = NULL;
-
-	switch (cmd[0]) {
-	case '0':
-		if (find_call_with_status(CSD_CALL_STATUS_WAITING))
-			foreach_call_with_status(CSD_CALL_STATUS_WAITING,
-								release_call);
-		else
-			foreach_call_with_status(CSD_CALL_STATUS_HOLD,
-								release_call);
-		break;
-	case '1':
-		if (idx) {
-			if (call)
-				err = release_call(call);
-			break;
-		}
-		foreach_call_with_status(CSD_CALL_STATUS_ACTIVE, release_call);
-		call = find_call_with_status(CSD_CALL_STATUS_WAITING);
-		if (call)
-			err = answer_call(call);
-		break;
-	case '2':
-		if (idx) {
-			if (call)
-				err = split_call(call);
-		} else {
-			struct csd_call *held, *wait;
-
-			call = find_call_with_status(CSD_CALL_STATUS_ACTIVE);
-			held = find_call_with_status(CSD_CALL_STATUS_HOLD);
-			wait = find_call_with_status(CSD_CALL_STATUS_WAITING);
-
-			if (wait)
-				err = answer_call(wait);
-			else if (call && held)
-				err = swap_calls();
-			else {
-				if (call)
-					err = hold_call(call);
-				if (held)
-					err = unhold_call(held);
-			}
-		}
-		break;
-	case '3':
-		if (find_call_with_status(CSD_CALL_STATUS_HOLD) ||
-				find_call_with_status(CSD_CALL_STATUS_WAITING))
-			err = create_conference();
-		break;
-	case '4':
-		err = call_transfer();
-		break;
-	default:
-		DBG("Unknown call hold request");
-		break;
-	}
-
-	if (err)
-		telephony_call_hold_rsp(telephony_device,
-					CME_ERROR_AG_FAILURE);
-	else
-		telephony_call_hold_rsp(telephony_device, CME_ERROR_NONE);
-}
-
-void telephony_nr_and_ec_req(void *telephony_device, gboolean enable)
-{
-	DBG("telephony-maemo6: got %s NR and EC request",
-			enable ? "enable" : "disable");
-	telephony_nr_and_ec_rsp(telephony_device, CME_ERROR_NONE);
-}
-
-void telephony_key_press_req(void *telephony_device, const char *keys)
-{
-	struct csd_call *active, *waiting;
-	int err;
-
-	DBG("telephony-maemo6: got key press request for %s", keys);
-
-	waiting = find_call_with_status(CSD_CALL_STATUS_COMING);
-	if (!waiting)
-		waiting = find_call_with_status(CSD_CALL_STATUS_MT_ALERTING);
-	if (!waiting)
-		waiting = find_call_with_status(CSD_CALL_STATUS_PROCEEDING);
-
-	active = find_call_with_status(CSD_CALL_STATUS_ACTIVE);
-
-	if (waiting)
-		err = answer_call(waiting);
-	else if (active)
-		err = release_call(active);
-	else
-		err = 0;
-
-	if (err < 0)
-		telephony_key_press_rsp(telephony_device,
-							CME_ERROR_AG_FAILURE);
-	else
-		telephony_key_press_rsp(telephony_device, CME_ERROR_NONE);
-}
-
-void telephony_voice_dial_req(void *telephony_device, gboolean enable)
-{
-	DBG("telephony-maemo6: got %s voice dial request",
-			enable ? "enable" : "disable");
-
-	telephony_voice_dial_rsp(telephony_device, CME_ERROR_NOT_SUPPORTED);
-}
-
-static void handle_incoming_call(DBusMessage *msg)
-{
-	const char *number, *call_path;
-	struct csd_call *call;
-
-	if (!dbus_message_get_args(msg, NULL,
-					DBUS_TYPE_OBJECT_PATH, &call_path,
-					DBUS_TYPE_STRING, &number,
-					DBUS_TYPE_INVALID)) {
-		error("Unexpected parameters in Call.Coming() signal");
-		return;
-	}
-
-	call = find_call(call_path);
-	if (!call) {
-		error("Didn't find any matching call object for %s",
-				call_path);
-		return;
-	}
-
-	DBG("Incoming call to %s from number %s", call_path, number);
-
-	g_free(call->number);
-	call->number = g_strdup(number);
-
-	if (find_call_with_status(CSD_CALL_STATUS_ACTIVE) ||
-			find_call_with_status(CSD_CALL_STATUS_HOLD))
-		telephony_call_waiting_ind(call->number,
-						number_type(call->number));
-	else
-		telephony_incoming_call_ind(call->number,
-						number_type(call->number));
-
-	telephony_update_indicator(maemo_indicators, "callsetup",
-					EV_CALLSETUP_INCOMING);
-}
-
-static void handle_outgoing_call(DBusMessage *msg)
-{
-	const char *number, *call_path;
-	struct csd_call *call;
-
-	if (!dbus_message_get_args(msg, NULL,
-					DBUS_TYPE_OBJECT_PATH, &call_path,
-					DBUS_TYPE_STRING, &number,
-					DBUS_TYPE_INVALID)) {
-		error("Unexpected parameters in Call.Created() signal");
-		return;
-	}
-
-	call = find_call(call_path);
-	if (!call) {
-		error("Didn't find any matching call object for %s",
-				call_path);
-		return;
-	}
-
-	DBG("Outgoing call from %s to number %s", call_path, number);
-
-	g_free(call->number);
-	call->number = g_strdup(number);
-
-	if (create_request_timer) {
-		g_source_remove(create_request_timer);
-		create_request_timer = 0;
-	}
-}
-
-static gboolean create_timeout(gpointer user_data)
-{
-	telephony_update_indicator(maemo_indicators, "callsetup",
-					EV_CALLSETUP_INACTIVE);
-	create_request_timer = 0;
-	return FALSE;
-}
-
-static void handle_create_requested(DBusMessage *msg)
-{
-	DBG("Call.CreateRequested()");
-
-	if (create_request_timer)
-		g_source_remove(create_request_timer);
-
-	create_request_timer = g_timeout_add_seconds(5, create_timeout, NULL);
-
-	telephony_update_indicator(maemo_indicators, "callsetup",
-					EV_CALLSETUP_OUTGOING);
-}
-
-static void call_set_status(struct csd_call *call, dbus_uint32_t status)
-{
-	dbus_uint32_t prev_status;
-	int callheld = telephony_get_indicator(maemo_indicators, "callheld");
-
-	prev_status = call->status;
-	DBG("Call %s changed from %s to %s", call->object_path,
-		call_status_str[prev_status], call_status_str[status]);
-
-	if (prev_status == status) {
-		DBG("Ignoring CSD Call state change to existing state");
-		return;
-	}
-
-	call->status = (int) status;
-
-	switch (status) {
-	case CSD_CALL_STATUS_IDLE:
-		if (call->setup) {
-			telephony_update_indicator(maemo_indicators,
-							"callsetup",
-							EV_CALLSETUP_INACTIVE);
-			if (!call->originating)
-				telephony_calling_stopped_ind();
-		}
-
-		g_free(call->number);
-		call->number = NULL;
-		call->originating = FALSE;
-		call->emergency = FALSE;
-		call->on_hold = FALSE;
-		call->conference = FALSE;
-		call->setup = FALSE;
-		break;
-	case CSD_CALL_STATUS_CREATE:
-		call->originating = TRUE;
-		call->setup = TRUE;
-		break;
-	case CSD_CALL_STATUS_COMING:
-		call->originating = FALSE;
-		call->setup = TRUE;
-		break;
-	case CSD_CALL_STATUS_PROCEEDING:
-		break;
-	case CSD_CALL_STATUS_MO_ALERTING:
-		telephony_update_indicator(maemo_indicators, "callsetup",
-						EV_CALLSETUP_ALERTING);
-		break;
-	case CSD_CALL_STATUS_MT_ALERTING:
-		/* Some headsets expect incoming call notification before they
-		 * can send ATA command. When call changed status from waiting
-		 * to alerting we need to send missing notification. Otherwise
-		 * headsets like Nokia BH-108 or BackBeat 903 are unable to
-		 * answer incoming call that was previously waiting. */
-		if (prev_status == CSD_CALL_STATUS_WAITING)
-			telephony_incoming_call_ind(call->number,
-						number_type(call->number));
-		break;
-	case CSD_CALL_STATUS_WAITING:
-		break;
-	case CSD_CALL_STATUS_ANSWERED:
-		break;
-	case CSD_CALL_STATUS_ACTIVE:
-		if (call->on_hold) {
-			call->on_hold = FALSE;
-			if (find_call_with_status(CSD_CALL_STATUS_HOLD))
-				telephony_update_indicator(maemo_indicators,
-							"callheld",
-							EV_CALLHELD_MULTIPLE);
-			else
-				telephony_update_indicator(maemo_indicators,
-							"callheld",
-							EV_CALLHELD_NONE);
-		} else {
-			if (!g_slist_find(active_calls, call))
-				active_calls = g_slist_prepend(active_calls, call);
-			if (g_slist_length(active_calls) == 1)
-				telephony_update_indicator(maemo_indicators,
-								"call",
-								EV_CALL_ACTIVE);
-			/* Upgrade callheld status if necessary */
-			if (callheld == EV_CALLHELD_ON_HOLD)
-				telephony_update_indicator(maemo_indicators,
-							"callheld",
-							EV_CALLHELD_MULTIPLE);
-			telephony_update_indicator(maemo_indicators,
-							"callsetup",
-							EV_CALLSETUP_INACTIVE);
-			if (!call->originating)
-				telephony_calling_stopped_ind();
-			call->setup = FALSE;
-		}
-		break;
-	case CSD_CALL_STATUS_MO_RELEASE:
-	case CSD_CALL_STATUS_MT_RELEASE:
-		active_calls = g_slist_remove(active_calls, call);
-		if (g_slist_length(active_calls) == 0)
-			telephony_update_indicator(maemo_indicators, "call",
-							EV_CALL_INACTIVE);
-
-		if (create_tones_timer)
-			g_source_remove(create_tones_timer);
-		break;
-	case CSD_CALL_STATUS_HOLD_INITIATED:
-		break;
-	case CSD_CALL_STATUS_HOLD:
-		call->on_hold = TRUE;
-		if (find_non_held_call())
-			telephony_update_indicator(maemo_indicators,
-							"callheld",
-							EV_CALLHELD_MULTIPLE);
-		else
-			telephony_update_indicator(maemo_indicators,
-							"callheld",
-							EV_CALLHELD_ON_HOLD);
-		break;
-	case CSD_CALL_STATUS_RETRIEVE_INITIATED:
-		break;
-	case CSD_CALL_STATUS_RECONNECT_PENDING:
-		break;
-	case CSD_CALL_STATUS_TERMINATED:
-		if (call->on_hold &&
-				!find_call_with_status(CSD_CALL_STATUS_HOLD)) {
-			telephony_update_indicator(maemo_indicators,
-							"callheld",
-							EV_CALLHELD_NONE);
-			return;
-		}
-
-		if (callheld == EV_CALLHELD_MULTIPLE &&
-				find_call_with_status(CSD_CALL_STATUS_HOLD) &&
-				!find_call_with_status(CSD_CALL_STATUS_ACTIVE))
-			telephony_update_indicator(maemo_indicators,
-							"callheld",
-							EV_CALLHELD_ON_HOLD);
-		break;
-	case CSD_CALL_STATUS_SWAP_INITIATED:
-		break;
-	default:
-		error("Unknown call status %u", status);
-		break;
-	}
-}
-
-static void handle_call_status(DBusMessage *msg, const char *call_path)
-{
-	struct csd_call *call;
-	dbus_uint32_t status, cause_type, cause;
-
-	if (!dbus_message_get_args(msg, NULL,
-					DBUS_TYPE_UINT32, &status,
-					DBUS_TYPE_UINT32, &cause_type,
-					DBUS_TYPE_UINT32, &cause,
-					DBUS_TYPE_INVALID)) {
-		error("Unexpected parameters in Instance.CallStatus() signal");
-		return;
-	}
-
-	call = find_call(call_path);
-	if (!call) {
-		error("Didn't find any matching call object for %s",
-				call_path);
-		return;
-	}
-
-	if (status > 16) {
-		error("Invalid call status %u", status);
-		return;
-	}
-
-	call_set_status(call, status);
-}
-
-static void handle_conference(DBusMessage *msg, gboolean joined)
-{
-	const char *path;
-	struct csd_call *call;
-
-	if (!dbus_message_get_args(msg, NULL,
-					DBUS_TYPE_OBJECT_PATH, &path,
-					DBUS_TYPE_INVALID)) {
-		error("Unexpected parameters in Conference.%s",
-					dbus_message_get_member(msg));
-		return;
-	}
-
-	call = find_call(path);
-	if (!call) {
-		error("Conference signal for unknown call %s", path);
-		return;
-	}
-
-	DBG("Call %s %s the conference", path, joined ? "joined" : "left");
-
-	call->conference = joined;
-}
-
-static uint8_t str2status(const char *state)
-{
-	if (g_strcmp0(state, "Home") == 0)
-		return NETWORK_REG_STATUS_HOME;
-	else if (g_strcmp0(state, "Roaming") == 0)
-		return NETWORK_REG_STATUS_ROAMING;
-	else if (g_strcmp0(state, "Offline") == 0)
-		return NETWORK_REG_STATUS_OFFLINE;
-	else if (g_strcmp0(state, "Searching") == 0)
-		return NETWORK_REG_STATUS_SEARCHING;
-	else if (g_strcmp0(state, "NoSim") == 0)
-		return NETWORK_REG_STATUS_NO_SIM;
-	else if (g_strcmp0(state, "Poweroff") == 0)
-		return NETWORK_REG_STATUS_POWEROFF;
-	else if (g_strcmp0(state, "Powersafe") == 0)
-		return NETWORK_REG_STATUS_POWERSAFE;
-	else if (g_strcmp0(state, "NoCoverage") == 0)
-		return NETWORK_REG_STATUS_NO_COVERAGE;
-	else if (g_strcmp0(state, "Reject") == 0)
-		return NETWORK_REG_STATUS_REJECTED;
-	else
-		return NETWORK_REG_STATUS_UNKOWN;
-}
-
-static void update_registration_status(const char *status)
-{
-	uint8_t new_status;
-
-	new_status = str2status(status);
-
-	if (net.status == new_status)
-		return;
-
-	switch (new_status) {
-	case NETWORK_REG_STATUS_HOME:
-		telephony_update_indicator(maemo_indicators, "roam",
-							EV_ROAM_INACTIVE);
-		if (net.status > NETWORK_REG_STATUS_ROAMING)
-			telephony_update_indicator(maemo_indicators,
-							"service",
-							EV_SERVICE_PRESENT);
-		break;
-	case NETWORK_REG_STATUS_ROAMING:
-		telephony_update_indicator(maemo_indicators, "roam",
-							EV_ROAM_ACTIVE);
-		if (net.status > NETWORK_REG_STATUS_ROAMING)
-			telephony_update_indicator(maemo_indicators,
-							"service",
-							EV_SERVICE_PRESENT);
-		break;
-	case NETWORK_REG_STATUS_OFFLINE:
-	case NETWORK_REG_STATUS_SEARCHING:
-	case NETWORK_REG_STATUS_NO_SIM:
-	case NETWORK_REG_STATUS_POWEROFF:
-	case NETWORK_REG_STATUS_POWERSAFE:
-	case NETWORK_REG_STATUS_NO_COVERAGE:
-	case NETWORK_REG_STATUS_REJECTED:
-	case NETWORK_REG_STATUS_UNKOWN:
-		if (net.status < NETWORK_REG_STATUS_OFFLINE)
-			telephony_update_indicator(maemo_indicators,
-							"service",
-							EV_SERVICE_NONE);
-		break;
-	}
-
-	net.status = new_status;
-
-	DBG("telephony-maemo6: registration status changed: %s", status);
-}
-
-static void handle_registration_changed(DBusMessage *msg)
-{
-	const char *status;
-
-	if (!dbus_message_get_args(msg, NULL,
-					DBUS_TYPE_STRING, &status,
-					DBUS_TYPE_INVALID)) {
-		error("Unexpected parameters in RegistrationChanged");
-		return;
-	}
-
-	update_registration_status(status);
-}
-
-static void update_signal_strength(int32_t signal_bars)
-{
-	if (signal_bars < 0) {
-		DBG("signal strength smaller than expected: %d < 0",
-								signal_bars);
-		signal_bars = 0;
-	} else if (signal_bars > 5) {
-		DBG("signal strength greater than expected: %d > 5",
-								signal_bars);
-		signal_bars = 5;
-	}
-
-	if (net.signal_bars == signal_bars)
-		return;
-
-	telephony_update_indicator(maemo_indicators, "signal", signal_bars);
-
-	net.signal_bars = signal_bars;
-	DBG("telephony-maemo6: signal strength updated: %d/5", signal_bars);
-}
-
-static void handle_signal_bars_changed(DBusMessage *msg)
-{
-	int32_t signal_bars;
-
-	if (!dbus_message_get_args(msg, NULL,
-					DBUS_TYPE_INT32, &signal_bars,
-					DBUS_TYPE_INVALID)) {
-		error("Unexpected parameters in SignalBarsChanged");
-		return;
-	}
-
-	update_signal_strength(signal_bars);
-}
-
-static gboolean iter_get_basic_args(DBusMessageIter *iter,
-					int first_arg_type, ...)
-{
-	int type;
-	va_list ap;
-
-	va_start(ap, first_arg_type);
-
-	for (type = first_arg_type; type != DBUS_TYPE_INVALID;
-			type = va_arg(ap, int)) {
-		void *value = va_arg(ap, void *);
-		int real_type = dbus_message_iter_get_arg_type(iter);
-
-		if (real_type != type) {
-			error("iter_get_basic_args: expected %c but got %c",
-					(char) type, (char) real_type);
-			break;
-		}
-
-		dbus_message_iter_get_basic(iter, value);
-		dbus_message_iter_next(iter);
-	}
-
-	va_end(ap);
-
-	return type == DBUS_TYPE_INVALID ? TRUE : FALSE;
-}
-
-static void hal_battery_level_reply(DBusPendingCall *call, void *user_data)
-{
-	DBusError err;
-	DBusMessage *reply;
-	dbus_int32_t level;
-	int *value = user_data;
-
-	reply = dbus_pending_call_steal_reply(call);
-
-	dbus_error_init(&err);
-	if (dbus_set_error_from_message(&err, reply)) {
-		error("hald replied with an error: %s, %s",
-				err.name, err.message);
-		dbus_error_free(&err);
-		goto done;
-	}
-
-	if (!dbus_message_get_args(reply, NULL,
-				DBUS_TYPE_INT32, &level,
-				DBUS_TYPE_INVALID)) {
-		error("Unexpected args in hald reply");
-		goto done;
-	}
-
-	*value = (int) level;
-
-	if (value == &battchg_last)
-		DBG("telephony-maemo6: battery.charge_level.last_full is %d",
-				*value);
-	else if (value == &battchg_design)
-		DBG("telephony-maemo6: battery.charge_level.design is %d",
-				*value);
-	else
-		DBG("telephony-maemo6: battery.charge_level.current is %d",
-				*value);
-
-	if ((battchg_design > 0 || battchg_last > 0) && battchg_cur >= 0) {
-		int new, max;
-
-		if (battchg_last > 0)
-			max = battchg_last;
-		else
-			max = battchg_design;
-
-		new = battchg_cur * 5 / max;
-
-		telephony_update_indicator(maemo_indicators, "battchg", new);
-	}
-
-done:
-	dbus_message_unref(reply);
-	remove_pending(call);
-}
-
-static void hal_get_integer(const char *path, const char *key, void *user_data)
-{
-	send_method_call("org.freedesktop.Hal", path,
-				"org.freedesktop.Hal.Device",
-				"GetPropertyInteger",
-				hal_battery_level_reply, user_data,
-				DBUS_TYPE_STRING, &key,
-				DBUS_TYPE_INVALID);
-}
-
-static void handle_hal_property_modified(DBusMessage *msg)
-{
-	DBusMessageIter iter, array;
-	dbus_int32_t num_changes;
-	const char *path;
-
-	path = dbus_message_get_path(msg);
-
-	dbus_message_iter_init(msg, &iter);
-
-	if (dbus_message_iter_get_arg_type(&iter) != DBUS_TYPE_INT32) {
-		error("Unexpected signature in hal PropertyModified signal");
-		return;
-	}
-
-	dbus_message_iter_get_basic(&iter, &num_changes);
-	dbus_message_iter_next(&iter);
-
-	if (dbus_message_iter_get_arg_type(&iter) != DBUS_TYPE_ARRAY) {
-		error("Unexpected signature in hal PropertyModified signal");
-		return;
-	}
-
-	dbus_message_iter_recurse(&iter, &array);
-
-	while (dbus_message_iter_get_arg_type(&array) != DBUS_TYPE_INVALID) {
-		DBusMessageIter prop;
-		const char *name;
-		dbus_bool_t added, removed;
-
-		dbus_message_iter_recurse(&array, &prop);
-
-		if (!iter_get_basic_args(&prop,
-					DBUS_TYPE_STRING, &name,
-					DBUS_TYPE_BOOLEAN, &added,
-					DBUS_TYPE_BOOLEAN, &removed,
-					DBUS_TYPE_INVALID)) {
-			error("Invalid hal PropertyModified parameters");
-			break;
-		}
-
-		if (g_str_equal(name, "battery.charge_level.last_full"))
-			hal_get_integer(path, name, &battchg_last);
-		else if (g_str_equal(name, "battery.charge_level.current"))
-			hal_get_integer(path, name, &battchg_cur);
-		else if (g_str_equal(name, "battery.charge_level.design"))
-			hal_get_integer(path, name, &battchg_design);
-
-		dbus_message_iter_next(&array);
-	}
-}
-
-static void csd_call_free(void *data)
-{
-	struct csd_call *call = data;
-
-	if (!call)
-		return;
-
-	g_free(call->object_path);
-	g_free(call->number);
-
-	g_slist_foreach(pending, remove_pending_by_data, call);
-
-	g_free(call);
-}
-
-static void parse_call_list(DBusMessageIter *iter)
-{
-	do {
-		DBusMessageIter call_iter;
-		struct csd_call *call;
-		const char *object_path, *number;
-		dbus_uint32_t status;
-		dbus_bool_t originating, terminating, emerg, on_hold, conf;
-
-		if (dbus_message_iter_get_arg_type(iter) != DBUS_TYPE_STRUCT) {
-			error("Unexpected signature in GetCallInfoAll reply");
-			break;
-		}
-
-		dbus_message_iter_recurse(iter, &call_iter);
-
-		if (!iter_get_basic_args(&call_iter,
-					DBUS_TYPE_OBJECT_PATH, &object_path,
-					DBUS_TYPE_UINT32, &status,
-					DBUS_TYPE_BOOLEAN, &originating,
-					DBUS_TYPE_BOOLEAN, &terminating,
-					DBUS_TYPE_BOOLEAN, &emerg,
-					DBUS_TYPE_BOOLEAN, &on_hold,
-					DBUS_TYPE_BOOLEAN, &conf,
-					DBUS_TYPE_STRING, &number,
-					DBUS_TYPE_INVALID)) {
-			error("Parsing call D-Bus parameters failed");
-			break;
-		}
-
-		call = find_call(object_path);
-		if (!call) {
-			call = g_new0(struct csd_call, 1);
-			call->object_path = g_strdup(object_path);
-			calls = g_slist_append(calls, call);
-			DBG("telephony-maemo6: new csd call instance at %s",
-								object_path);
-		}
-
-		if (status == CSD_CALL_STATUS_IDLE)
-			continue;
-
-		/* CSD gives incorrect call_hold property sometimes */
-		if ((call->status != CSD_CALL_STATUS_HOLD && on_hold) ||
-				(call->status == CSD_CALL_STATUS_HOLD &&
-								!on_hold)) {
-			error("Conflicting call status and on_hold property!");
-			on_hold = call->status == CSD_CALL_STATUS_HOLD;
-		}
-
-		call->originating = originating;
-		call->on_hold = on_hold;
-		call->conference = conf;
-		g_free(call->number);
-		call->number = g_strdup(number);
-
-		/* Update indicators */
-		call_set_status(call, status);
-
-	} while (dbus_message_iter_next(iter));
-}
-
-static void update_operator_name(const char *name)
-{
-	if (name == NULL)
-		return;
-
-	g_free(net.operator_name);
-	net.operator_name = g_strndup(name, 16);
-	DBG("telephony-maemo6: operator name updated: %s", name);
-}
-
-static void get_property_reply(DBusPendingCall *call, void *user_data)
-{
-	char *prop = user_data;
-	DBusError err;
-	DBusMessage *reply;
-	DBusMessageIter iter, sub;
-
-	reply = dbus_pending_call_steal_reply(call);
-
-	dbus_error_init(&err);
-	if (dbus_set_error_from_message(&err, reply)) {
-		error("csd replied with an error: %s, %s",
-				err.name, err.message);
-		dbus_error_free(&err);
-		goto done;
-	}
-
-	dbus_message_iter_init(reply, &iter);
-
-	if (dbus_message_iter_get_arg_type(&iter) != DBUS_TYPE_VARIANT) {
-		error("Unexpected signature in Get return");
-		goto done;
-	}
-
-	dbus_message_iter_recurse(&iter, &sub);
-
-	if (g_strcmp0(prop, "RegistrationStatus") == 0) {
-		const char *status;
-
-		dbus_message_iter_get_basic(&sub, &status);
-		update_registration_status(status);
-
-		get_property(CSD_CSNET_OPERATOR, "OperatorName");
-		get_property(CSD_CSNET_SIGNAL, "SignalBars");
-	} else if (g_strcmp0(prop, "OperatorName") == 0) {
-		const char *name;
-
-		dbus_message_iter_get_basic(&sub, &name);
-		update_operator_name(name);
-	} else if (g_strcmp0(prop, "SignalBars") == 0) {
-		int32_t signal_bars;
-
-		dbus_message_iter_get_basic(&sub, &signal_bars);
-		update_signal_strength(signal_bars);
-	}
-
-done:
-	g_free(prop);
-	dbus_message_unref(reply);
-	remove_pending(call);
-}
-
-static int get_property(const char *iface, const char *prop)
-{
-	return send_method_call(CSD_CSNET_BUS_NAME, CSD_CSNET_PATH,
-				DBUS_INTERFACE_PROPERTIES, "Get",
-				get_property_reply, g_strdup(prop),
-				DBUS_TYPE_STRING, &iface,
-				DBUS_TYPE_STRING, &prop,
-				DBUS_TYPE_INVALID);
-}
-
-static void handle_operator_name_changed(DBusMessage *msg)
-{
-	const char *name;
-
-	if (!dbus_message_get_args(msg, NULL,
-					DBUS_TYPE_STRING, &name,
-					DBUS_TYPE_INVALID)) {
-		error("Unexpected parameters in OperatorNameChanged");
-		return;
-	}
-
-	update_operator_name(name);
-}
-
-static void call_info_reply(DBusPendingCall *call, void *user_data)
-{
-	DBusError err;
-	DBusMessage *reply;
-	DBusMessageIter iter, sub;
-
-	get_calls_active = FALSE;
-
-	reply = dbus_pending_call_steal_reply(call);
-
-	dbus_error_init(&err);
-	if (dbus_set_error_from_message(&err, reply)) {
-		error("csd replied with an error: %s, %s",
-				err.name, err.message);
-		dbus_error_free(&err);
-		goto done;
-	}
-
-	dbus_message_iter_init(reply, &iter);
-
-	if (dbus_message_iter_get_arg_type(&iter) != DBUS_TYPE_ARRAY) {
-		error("Unexpected signature in GetCallInfoAll return");
-		goto done;
-	}
-
-	dbus_message_iter_recurse(&iter, &sub);
-
-	parse_call_list(&sub);
-
-	get_property(CSD_CSNET_REGISTRATION, "RegistrationStatus");
-
-done:
-	dbus_message_unref(reply);
-	remove_pending(call);
-}
-
-
-static void phonebook_read_reply(DBusPendingCall *call, void *user_data)
-{
-	DBusError derr;
-	DBusMessage *reply;
-	const char *name, *number, *secondname, *additionalnumber, *email;
-	int index;
-	char **number_type = user_data;
-
-	reply = dbus_pending_call_steal_reply(call);
-
-	dbus_error_init(&derr);
-	if (dbus_set_error_from_message(&derr, reply)) {
-		error("%s.ReadFirst replied with an error: %s, %s",
-				CSD_SIMPB_INTERFACE, derr.name, derr.message);
-		dbus_error_free(&derr);
-		if (number_type == &vmbx)
-			vmbx = g_strdup(getenv("VMBX_NUMBER"));
-		goto done;
-	}
-
-	dbus_error_init(&derr);
-	if (dbus_message_get_args(reply, NULL,
-				DBUS_TYPE_INT32, &index,
-				DBUS_TYPE_STRING, &name,
-				DBUS_TYPE_STRING, &number,
-				DBUS_TYPE_STRING, &secondname,
-				DBUS_TYPE_STRING, &additionalnumber,
-				DBUS_TYPE_STRING, &email,
-				DBUS_TYPE_INVALID) == FALSE) {
-		error("Unable to parse %s.ReadFirst arguments: %s, %s",
-				CSD_SIMPB_INTERFACE, derr.name, derr.message);
-		dbus_error_free(&derr);
-		goto done;
-	}
-
-	if (number_type == &msisdn) {
-		g_free(msisdn);
-		msisdn = g_strdup(number);
-		DBG("Got MSISDN %s (%s)", number, name);
-	} else {
-		g_free(vmbx);
-		vmbx = g_strdup(number);
-		DBG("Got voice mailbox number %s (%s)", number, name);
-	}
-
-done:
-	dbus_message_unref(reply);
-	remove_pending(call);
-}
-
-static void csd_init(void)
-{
-	const char *pb_type;
-	int ret;
-
-	ret = send_method_call(CSD_CALL_BUS_NAME, CSD_CALL_PATH,
-				CSD_CALL_INTERFACE, "GetCallInfoAll",
-				call_info_reply, NULL, DBUS_TYPE_INVALID);
-	if (ret < 0) {
-		error("Unable to sent GetCallInfoAll method call");
-		return;
-	}
-
-	get_calls_active = TRUE;
-
-	pb_type = CSD_SIMPB_TYPE_MSISDN;
-
-	ret = send_method_call(CSD_SIMPB_BUS_NAME, CSD_SIMPB_PATH,
-				CSD_SIMPB_INTERFACE, "ReadFirst",
-				phonebook_read_reply, &msisdn,
-				DBUS_TYPE_STRING, &pb_type,
-				DBUS_TYPE_INVALID);
-	if (ret < 0) {
-		error("Unable to send " CSD_SIMPB_INTERFACE ".read()");
-		return;
-	}
-
-	/* Voicemail should be in MBDN index 0 */
-	pb_type = CSD_SIMPB_TYPE_MBDN;
-
-	ret = send_method_call(CSD_SIMPB_BUS_NAME, CSD_SIMPB_PATH,
-				CSD_SIMPB_INTERFACE, "ReadFirst",
-				phonebook_read_reply, &vmbx,
-				DBUS_TYPE_STRING, &pb_type,
-				DBUS_TYPE_INVALID);
-	if (ret < 0) {
-		error("Unable to send " CSD_SIMPB_INTERFACE ".read()");
-		return;
-	}
-}
-
-static void handle_modem_state(DBusMessage *msg)
-{
-	const char *state;
-
-	if (!dbus_message_get_args(msg, NULL, DBUS_TYPE_STRING, &state,
-							DBUS_TYPE_INVALID)) {
-		error("Unexpected modem state parameters");
-		return;
-	}
-
-	DBG("SSC modem state: %s", state);
-
-	if (calls != NULL || get_calls_active)
-		return;
-
-	if (g_str_equal(state, "cmt_ready") || g_str_equal(state, "online"))
-		csd_init();
-}
-
-static void modem_state_reply(DBusPendingCall *call, void *user_data)
-{
-	DBusMessage *reply = dbus_pending_call_steal_reply(call);
-	DBusError err;
-
-	dbus_error_init(&err);
-	if (dbus_set_error_from_message(&err, reply)) {
-		error("get_modem_state: %s, %s", err.name, err.message);
-		dbus_error_free(&err);
-	} else
-		handle_modem_state(reply);
-
-	dbus_message_unref(reply);
-	remove_pending(call);
-}
-
-static gboolean signal_filter(DBusConnection *conn, DBusMessage *msg,
-								void *data)
-{
-	const char *path = dbus_message_get_path(msg);
-
-	if (dbus_message_is_signal(msg, CSD_CALL_INTERFACE, "Coming"))
-		handle_incoming_call(msg);
-	else if (dbus_message_is_signal(msg, CSD_CALL_INTERFACE, "Created"))
-		handle_outgoing_call(msg);
-	else if (dbus_message_is_signal(msg, CSD_CALL_INTERFACE,
-							"CreateRequested"))
-		handle_create_requested(msg);
-	else if (dbus_message_is_signal(msg, CSD_CALL_INSTANCE, "CallStatus"))
-		handle_call_status(msg, path);
-	else if (dbus_message_is_signal(msg, CSD_CALL_CONFERENCE, "Joined"))
-		handle_conference(msg, TRUE);
-	else if (dbus_message_is_signal(msg, CSD_CALL_CONFERENCE, "Left"))
-		handle_conference(msg, FALSE);
-	else if (dbus_message_is_signal(msg, CSD_CSNET_REGISTRATION,
-				"RegistrationChanged"))
-		handle_registration_changed(msg);
-	else if (dbus_message_is_signal(msg, CSD_CSNET_OPERATOR,
-				"OperatorNameChanged"))
-		handle_operator_name_changed(msg);
-	else if (dbus_message_is_signal(msg, CSD_CSNET_SIGNAL,
-				"SignalBarsChanged"))
-		handle_signal_bars_changed(msg);
-	else if (dbus_message_is_signal(msg, "org.freedesktop.Hal.Device",
-					"PropertyModified"))
-		handle_hal_property_modified(msg);
-	else if (dbus_message_is_signal(msg, SSC_DBUS_IFACE,
-						"modem_state_changed_ind"))
-		handle_modem_state(msg);
-
-	return TRUE;
-}
-
-static void add_watch(const char *sender, const char *path,
-				const char *interface, const char *member)
-{
-	guint watch;
-
-	watch = g_dbus_add_signal_watch(btd_get_dbus_connection(),
-					sender, path, interface,
-					member, signal_filter, NULL, NULL);
-
-	watches = g_slist_prepend(watches, GUINT_TO_POINTER(watch));
-}
-
-static void hal_find_device_reply(DBusPendingCall *call, void *user_data)
-{
-	DBusError err;
-	DBusMessage *reply;
-	DBusMessageIter iter, sub;
-	const char *path;
-	int type;
-
-	reply = dbus_pending_call_steal_reply(call);
-
-	dbus_error_init(&err);
-	if (dbus_set_error_from_message(&err, reply)) {
-		error("hald replied with an error: %s, %s",
-				err.name, err.message);
-		dbus_error_free(&err);
-		goto done;
-	}
-
-	dbus_message_iter_init(reply, &iter);
-
-	if (dbus_message_iter_get_arg_type(&iter) != DBUS_TYPE_ARRAY) {
-		error("Unexpected signature in FindDeviceByCapability return");
-		goto done;
-	}
-
-	dbus_message_iter_recurse(&iter, &sub);
-
-	type = dbus_message_iter_get_arg_type(&sub);
-
-	if (type != DBUS_TYPE_OBJECT_PATH && type != DBUS_TYPE_STRING) {
-		error("No hal device with battery capability found");
-		goto done;
-	}
-
-	dbus_message_iter_get_basic(&sub, &path);
-
-	DBG("telephony-maemo6: found battery device at %s", path);
-
-	add_watch(NULL, path, "org.freedesktop.Hal.Device",
-							"PropertyModified");
-
-	hal_get_integer(path, "battery.charge_level.last_full", &battchg_last);
-	hal_get_integer(path, "battery.charge_level.current", &battchg_cur);
-	hal_get_integer(path, "battery.charge_level.design", &battchg_design);
-
-done:
-	dbus_message_unref(reply);
-	remove_pending(call);
-}
-
-int telephony_init(void)
-{
-	const char *battery_cap = "battery";
-	uint32_t features = AG_FEATURE_EC_ANDOR_NR |
-				AG_FEATURE_INBAND_RINGTONE |
-				AG_FEATURE_REJECT_A_CALL |
-				AG_FEATURE_ENHANCED_CALL_STATUS |
-				AG_FEATURE_ENHANCED_CALL_CONTROL |
-				AG_FEATURE_EXTENDED_ERROR_RESULT_CODES |
-				AG_FEATURE_THREE_WAY_CALLING;
-	int i;
-
-	DBG("");
-
-	add_watch(NULL, NULL, CSD_CALL_INTERFACE, NULL);
-	add_watch(NULL, NULL, CSD_CALL_INSTANCE, NULL);
-	add_watch(NULL, NULL, CSD_CALL_CONFERENCE, NULL);
-	add_watch(NULL, NULL, CSD_CSNET_REGISTRATION, "RegistrationChanged");
-	add_watch(NULL, NULL, CSD_CSNET_OPERATOR, "OperatorNameChanged");
-	add_watch(NULL, NULL, CSD_CSNET_SIGNAL, "SignalBarsChanged");
-	add_watch(NULL, NULL, SSC_DBUS_IFACE, "modem_state_changed_ind");
-
-	if (send_method_call(SSC_DBUS_NAME, SSC_DBUS_PATH, SSC_DBUS_IFACE,
-					"get_modem_state", modem_state_reply,
-					NULL, DBUS_TYPE_INVALID) < 0)
-		error("Unable to send " SSC_DBUS_IFACE ".get_modem_state()");
-
-	/* Reset indicators */
-	for (i = 0; maemo_indicators[i].desc != NULL; i++) {
-		if (g_str_equal(maemo_indicators[i].desc, "battchg"))
-			maemo_indicators[i].val = 5;
-		else
-			maemo_indicators[i].val = 0;
-	}
-
-	telephony_ready_ind(features, maemo_indicators, BTRH_NOT_SUPPORTED,
-								chld_str);
-	if (send_method_call("org.freedesktop.Hal",
-				"/org/freedesktop/Hal/Manager",
-				"org.freedesktop.Hal.Manager",
-				"FindDeviceByCapability",
-				hal_find_device_reply, NULL,
-				DBUS_TYPE_STRING, &battery_cap,
-				DBUS_TYPE_INVALID) < 0)
-		error("Unable to send HAL method call");
-
-	return 0;
-}
-
-static void remove_watch(gpointer data)
-{
-	g_dbus_remove_watch(GPOINTER_TO_UINT(data));
-}
-
-void telephony_exit(void)
-{
-	DBG("");
-
-	g_free(net.operator_name);
-	net.operator_name = NULL;
-
-	net.status = NETWORK_REG_STATUS_UNKOWN;
-	net.signal_bars = 0;
-
-	g_slist_free(active_calls);
-	active_calls = NULL;
-
-	g_slist_free_full(calls, csd_call_free);
-	calls = NULL;
-
-	g_slist_free_full(pending, pending_req_finalize);
-	pending = NULL;
-
-	g_slist_free_full(watches, remove_watch);
-	watches = NULL;
-
-	telephony_deinit();
-}
-- 
1.7.11.7


^ permalink raw reply related

* [PATCH BlueZ 06/13] build: Remove telephony-ofono.c
From: Luiz Augusto von Dentz @ 2012-11-13 13:21 UTC (permalink / raw)
  To: linux-bluetooth
In-Reply-To: <1352812880-7306-1-git-send-email-luiz.dentz@gmail.com>

From: Luiz Augusto von Dentz <luiz.von.dentz@intel.com>

---
 Makefile.am             |    4 +-
 audio/telephony-ofono.c | 1636 -----------------------------------------------
 2 files changed, 1 insertion(+), 1639 deletions(-)
 delete mode 100644 audio/telephony-ofono.c

diff --git a/Makefile.am b/Makefile.am
index b7e861b..84566c8 100644
--- a/Makefile.am
+++ b/Makefile.am
@@ -125,8 +125,7 @@ builtin_nodist += audio/telephony.c
 
 noinst_LIBRARIES += audio/libtelephony.a
 
-audio_libtelephony_a_SOURCES = audio/telephony.h audio/telephony-dummy.c \
-				audio/telephony-ofono.c
+audio_libtelephony_a_SOURCES = audio/telephony.h audio/telephony-dummy.c
 endif
 
 if SAPPLUGIN
@@ -314,7 +313,6 @@ EXTRA_DIST += src/genbuiltin src/bluetooth.conf src/org.bluez.service \
 			src/main.conf profiles/network/network.conf \
 			profiles/input/input.conf profiles/proximity/proximity.conf \
 			audio/audio.conf audio/telephony-dummy.c \
-			audio/telephony-ofono.c \
 			profiles/sap/sap-dummy.c profiles/sap/sap-u8500.c
 
 include Makefile.tools
diff --git a/audio/telephony-ofono.c b/audio/telephony-ofono.c
deleted file mode 100644
index f87b652..0000000
--- a/audio/telephony-ofono.c
+++ /dev/null
@@ -1,1636 +0,0 @@
-/*
- *
- *  BlueZ - Bluetooth protocol stack for Linux
- *
- *  Copyright (C) 2009-2010  Intel Corporation
- *  Copyright (C) 2006-2009  Nokia Corporation
- *  Copyright (C) 2004-2010  Marcel Holtmann <marcel@holtmann.org>
- *
- *
- *  This program is free software; you can redistribute it and/or modify
- *  it under the terms of the GNU General Public License as published by
- *  the Free Software Foundation; either version 2 of the License, or
- *  (at your option) any later version.
- *
- *  This program is distributed in the hope that it will be useful,
- *  but WITHOUT ANY WARRANTY; without even the implied warranty of
- *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
- *  GNU General Public License for more details.
- *
- *  You should have received a copy of the GNU General Public License
- *  along with this program; if not, write to the Free Software
- *  Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
- *
- */
-
-#ifdef HAVE_CONFIG_H
-#include <config.h>
-#endif
-
-#include <stdlib.h>
-#include <stdio.h>
-#include <string.h>
-#include <stdint.h>
-#include <glib.h>
-#include <dbus/dbus.h>
-#include <gdbus.h>
-
-#include <bluetooth/sdp.h>
-
-#include "dbus-common.h"
-#include "log.h"
-#include "telephony.h"
-
-enum net_registration_status {
-	NETWORK_REG_STATUS_HOME = 0x00,
-	NETWORK_REG_STATUS_ROAM,
-	NETWORK_REG_STATUS_NOSERV
-};
-
-struct voice_call {
-	char *obj_path;
-	int status;
-	gboolean originating;
-	gboolean conference;
-	char *number;
-	guint watch;
-};
-
-static char *modem_obj_path = NULL;
-static char *last_dialed_number = NULL;
-static GSList *calls = NULL;
-static GSList *watches = NULL;
-static GSList *pending = NULL;
-
-#define OFONO_BUS_NAME "org.ofono"
-#define OFONO_PATH "/"
-#define OFONO_MODEM_INTERFACE "org.ofono.Modem"
-#define OFONO_MANAGER_INTERFACE "org.ofono.Manager"
-#define OFONO_NETWORKREG_INTERFACE "org.ofono.NetworkRegistration"
-#define OFONO_VCMANAGER_INTERFACE "org.ofono.VoiceCallManager"
-#define OFONO_VC_INTERFACE "org.ofono.VoiceCall"
-
-/* HAL battery namespace key values */
-static int battchg_cur = -1;    /* "battery.charge_level.current" */
-static int battchg_last = -1;   /* "battery.charge_level.last_full" */
-static int battchg_design = -1; /* "battery.charge_level.design" */
-
-static struct {
-	uint8_t status;
-	uint32_t signals_bar;
-	char *operator_name;
-} net = {
-	.status = NETWORK_REG_STATUS_NOSERV,
-	.signals_bar = 0,
-	.operator_name = NULL,
-};
-
-static const char *chld_str = "0,1,1x,2,2x,3,4";
-static char *subscriber_number = NULL;
-
-static gboolean events_enabled = FALSE;
-
-static struct indicator ofono_indicators[] =
-{
-	{ "battchg",	"0-5",	5,	TRUE },
-	{ "signal",	"0-5",	5,	TRUE },
-	{ "service",	"0,1",	1,	TRUE },
-	{ "call",	"0,1",	0,	TRUE },
-	{ "callsetup",	"0-3",	0,	TRUE },
-	{ "callheld",	"0-2",	0,	FALSE },
-	{ "roam",	"0,1",	0,	TRUE },
-	{ NULL }
-};
-
-static struct voice_call *find_vc(const char *path)
-{
-	GSList *l;
-
-	for (l = calls; l != NULL; l = l->next) {
-		struct voice_call *vc = l->data;
-
-		if (g_str_equal(vc->obj_path, path))
-			return vc;
-	}
-
-	return NULL;
-}
-
-static struct voice_call *find_vc_with_status(int status)
-{
-	GSList *l;
-
-	for (l = calls; l != NULL; l = l->next) {
-		struct voice_call *vc = l->data;
-
-		if (vc->status == status)
-			return vc;
-	}
-
-	return NULL;
-}
-
-static struct voice_call *find_vc_without_status(int status)
-{
-	GSList *l;
-
-	for (l = calls; l != NULL; l = l->next) {
-		struct voice_call *call = l->data;
-
-		if (call->status != status)
-			return call;
-	}
-
-	return NULL;
-}
-
-static int number_type(const char *number)
-{
-	if (number == NULL)
-		return NUMBER_TYPE_TELEPHONY;
-
-	if (number[0] == '+' || strncmp(number, "00", 2) == 0)
-		return NUMBER_TYPE_INTERNATIONAL;
-
-	return NUMBER_TYPE_TELEPHONY;
-}
-
-void telephony_device_connected(void *telephony_device)
-{
-	struct voice_call *coming;
-
-	DBG("telephony-ofono: device %p connected", telephony_device);
-
-	coming = find_vc_with_status(CALL_STATUS_ALERTING);
-	if (coming) {
-		if (find_vc_with_status(CALL_STATUS_ACTIVE))
-			telephony_call_waiting_ind(coming->number,
-						number_type(coming->number));
-		else
-			telephony_incoming_call_ind(coming->number,
-						number_type(coming->number));
-	}
-}
-
-void telephony_device_disconnected(void *telephony_device)
-{
-	DBG("telephony-ofono: device %p disconnected", telephony_device);
-	events_enabled = FALSE;
-}
-
-void telephony_event_reporting_req(void *telephony_device, int ind)
-{
-	events_enabled = ind == 1 ? TRUE : FALSE;
-
-	telephony_event_reporting_rsp(telephony_device, CME_ERROR_NONE);
-}
-
-void telephony_response_and_hold_req(void *telephony_device, int rh)
-{
-	telephony_response_and_hold_rsp(telephony_device,
-						CME_ERROR_NOT_SUPPORTED);
-}
-
-void telephony_last_dialed_number_req(void *telephony_device)
-{
-	DBG("telephony-ofono: last dialed number request");
-
-	if (last_dialed_number)
-		telephony_dial_number_req(telephony_device, last_dialed_number);
-	else
-		telephony_last_dialed_number_rsp(telephony_device,
-				CME_ERROR_NOT_ALLOWED);
-}
-
-static int send_method_call(const char *dest, const char *path,
-                                const char *interface, const char *method,
-                                DBusPendingCallNotifyFunction cb,
-                                void *user_data, int type, ...)
-{
-	DBusConnection *conn = btd_get_dbus_connection();
-	DBusMessage *msg;
-	DBusPendingCall *call;
-	va_list args;
-
-	msg = dbus_message_new_method_call(dest, path, interface, method);
-	if (!msg) {
-		error("Unable to allocate new D-Bus %s message", method);
-		return -ENOMEM;
-	}
-
-	va_start(args, type);
-
-	if (!dbus_message_append_args_valist(msg, type, args)) {
-		dbus_message_unref(msg);
-		va_end(args);
-		return -EIO;
-	}
-
-	va_end(args);
-
-	if (!cb) {
-		g_dbus_send_message(conn, msg);
-		return 0;
-	}
-
-	if (!dbus_connection_send_with_reply(conn, msg, &call, -1)) {
-		error("Sending %s failed", method);
-		dbus_message_unref(msg);
-		return -EIO;
-	}
-
-	dbus_pending_call_set_notify(call, cb, user_data, NULL);
-	pending = g_slist_prepend(pending, call);
-	dbus_message_unref(msg);
-
-	return 0;
-}
-
-static int answer_call(struct voice_call *vc)
-{
-	DBG("%s", vc->number);
-	return send_method_call(OFONO_BUS_NAME, vc->obj_path,
-						OFONO_VC_INTERFACE, "Answer",
-						NULL, NULL, DBUS_TYPE_INVALID);
-}
-
-static int release_call(struct voice_call *vc)
-{
-	DBG("%s", vc->number);
-	return send_method_call(OFONO_BUS_NAME, vc->obj_path,
-						OFONO_VC_INTERFACE, "Hangup",
-						NULL, NULL, DBUS_TYPE_INVALID);
-}
-
-static int release_answer_calls(void)
-{
-	DBG("");
-	return send_method_call(OFONO_BUS_NAME, modem_obj_path,
-						OFONO_VCMANAGER_INTERFACE,
-						"ReleaseAndAnswer",
-						NULL, NULL, DBUS_TYPE_INVALID);
-}
-
-static int split_call(struct voice_call *call)
-{
-	DBG("%s", call->number);
-	return send_method_call(OFONO_BUS_NAME, modem_obj_path,
-						OFONO_VCMANAGER_INTERFACE,
-						"PrivateChat",
-						NULL, NULL,
-						DBUS_TYPE_OBJECT_PATH,
-						call->obj_path,
-						DBUS_TYPE_INVALID);
-	return -1;
-}
-
-static int swap_calls(void)
-{
-	DBG("");
-	return send_method_call(OFONO_BUS_NAME, modem_obj_path,
-						OFONO_VCMANAGER_INTERFACE,
-						"SwapCalls",
-						NULL, NULL, DBUS_TYPE_INVALID);
-}
-
-static int create_conference(void)
-{
-	DBG("");
-	return send_method_call(OFONO_BUS_NAME, modem_obj_path,
-						OFONO_VCMANAGER_INTERFACE,
-						"CreateMultiparty",
-						NULL, NULL, DBUS_TYPE_INVALID);
-}
-
-static int release_conference(void)
-{
-	DBG("");
-	return send_method_call(OFONO_BUS_NAME, modem_obj_path,
-						OFONO_VCMANAGER_INTERFACE,
-						"HangupMultiparty",
-						NULL, NULL, DBUS_TYPE_INVALID);
-}
-
-static int call_transfer(void)
-{
-	DBG("");
-	return send_method_call(OFONO_BUS_NAME, modem_obj_path,
-						OFONO_VCMANAGER_INTERFACE,
-						"Transfer",
-						NULL, NULL, DBUS_TYPE_INVALID);
-}
-
-void telephony_terminate_call_req(void *telephony_device)
-{
-	struct voice_call *call;
-	struct voice_call *alerting;
-	int err;
-
-	call = find_vc_with_status(CALL_STATUS_ACTIVE);
-	if (!call)
-		call = calls->data;
-
-	if (!call) {
-		error("No active call");
-		telephony_terminate_call_rsp(telephony_device,
-						CME_ERROR_NOT_ALLOWED);
-		return;
-	}
-
-	alerting = find_vc_with_status(CALL_STATUS_ALERTING);
-	if (call->status == CALL_STATUS_HELD && alerting)
-		err = release_call(alerting);
-	else if (call->conference)
-		err = release_conference();
-	else
-		err = release_call(call);
-
-	if (err < 0)
-		telephony_terminate_call_rsp(telephony_device,
-						CME_ERROR_AG_FAILURE);
-	else
-		telephony_terminate_call_rsp(telephony_device, CME_ERROR_NONE);
-}
-
-void telephony_answer_call_req(void *telephony_device)
-{
-	struct voice_call *vc;
-	int ret;
-
-	vc = find_vc_with_status(CALL_STATUS_INCOMING);
-	if (!vc)
-		vc = find_vc_with_status(CALL_STATUS_ALERTING);
-
-	if (!vc)
-		vc = find_vc_with_status(CALL_STATUS_WAITING);
-
-	if (!vc) {
-		telephony_answer_call_rsp(telephony_device,
-					CME_ERROR_NOT_ALLOWED);
-		return;
-	}
-
-	ret = answer_call(vc);
-	if (ret < 0) {
-		telephony_answer_call_rsp(telephony_device,
-					CME_ERROR_AG_FAILURE);
-		return;
-	}
-
-	telephony_answer_call_rsp(telephony_device, CME_ERROR_NONE);
-}
-
-void telephony_dial_number_req(void *telephony_device, const char *number)
-{
-	const char *clir;
-	int ret;
-
-	DBG("telephony-ofono: dial request to %s", number);
-
-	if (!modem_obj_path) {
-		telephony_dial_number_rsp(telephony_device,
-					CME_ERROR_AG_FAILURE);
-		return;
-	}
-
-	if (!strncmp(number, "*31#", 4)) {
-		number += 4;
-		clir = "enabled";
-	} else if (!strncmp(number, "#31#", 4)) {
-		number += 4;
-		clir =  "disabled";
-	} else
-		clir = "default";
-
-	ret = send_method_call(OFONO_BUS_NAME, modem_obj_path,
-			OFONO_VCMANAGER_INTERFACE,
-                        "Dial", NULL, NULL,
-			DBUS_TYPE_STRING, &number,
-			DBUS_TYPE_STRING, &clir,
-			DBUS_TYPE_INVALID);
-
-	if (ret < 0)
-		telephony_dial_number_rsp(telephony_device,
-			CME_ERROR_AG_FAILURE);
-	else
-		telephony_dial_number_rsp(telephony_device, CME_ERROR_NONE);
-}
-
-void telephony_transmit_dtmf_req(void *telephony_device, char tone)
-{
-	char *tone_string;
-	int ret;
-
-	DBG("telephony-ofono: transmit dtmf: %c", tone);
-
-	if (!modem_obj_path) {
-		telephony_transmit_dtmf_rsp(telephony_device,
-					CME_ERROR_AG_FAILURE);
-		return;
-	}
-
-	tone_string = g_strdup_printf("%c", tone);
-	ret = send_method_call(OFONO_BUS_NAME, modem_obj_path,
-			OFONO_VCMANAGER_INTERFACE,
-			"SendTones", NULL, NULL,
-			DBUS_TYPE_STRING, &tone_string,
-			DBUS_TYPE_INVALID);
-	g_free(tone_string);
-
-	if (ret < 0)
-		telephony_transmit_dtmf_rsp(telephony_device,
-			CME_ERROR_AG_FAILURE);
-	else
-		telephony_transmit_dtmf_rsp(telephony_device, CME_ERROR_NONE);
-}
-
-void telephony_subscriber_number_req(void *telephony_device)
-{
-	DBG("telephony-ofono: subscriber number request");
-
-	if (subscriber_number)
-		telephony_subscriber_number_ind(subscriber_number,
-						NUMBER_TYPE_TELEPHONY,
-						SUBSCRIBER_SERVICE_VOICE);
-	telephony_subscriber_number_rsp(telephony_device, CME_ERROR_NONE);
-}
-
-void telephony_list_current_calls_req(void *telephony_device)
-{
-	GSList *l;
-	int i;
-
-	DBG("telephony-ofono: list current calls request");
-
-	for (l = calls, i = 1; l != NULL; l = l->next, i++) {
-		struct voice_call *vc = l->data;
-		int direction, multiparty;
-
-		direction = vc->originating ?
-				CALL_DIR_OUTGOING : CALL_DIR_INCOMING;
-
-		multiparty = vc->conference ?
-				CALL_MULTIPARTY_YES : CALL_MULTIPARTY_NO;
-
-		DBG("call %s direction %d multiparty %d", vc->number,
-							direction, multiparty);
-
-		telephony_list_current_call_ind(i, direction, vc->status,
-					CALL_MODE_VOICE, multiparty,
-					vc->number, number_type(vc->number));
-	}
-
-	telephony_list_current_calls_rsp(telephony_device, CME_ERROR_NONE);
-}
-
-void telephony_operator_selection_req(void *telephony_device)
-{
-	DBG("telephony-ofono: operator selection request");
-
-	telephony_operator_selection_ind(OPERATOR_MODE_AUTO,
-				net.operator_name ? net.operator_name : "");
-	telephony_operator_selection_rsp(telephony_device, CME_ERROR_NONE);
-}
-
-static void foreach_vc_with_status(int status,
-					int (*func)(struct voice_call *vc))
-{
-	GSList *l;
-
-	for (l = calls; l != NULL; l = l->next) {
-		struct voice_call *call = l->data;
-
-		if (call->status == status)
-			func(call);
-	}
-}
-
-void telephony_call_hold_req(void *telephony_device, const char *cmd)
-{
-	const char *idx;
-	struct voice_call *call;
-	int err = 0;
-
-	DBG("telephony-ofono: got call hold request %s", cmd);
-
-	if (strlen(cmd) > 1)
-		idx = &cmd[1];
-	else
-		idx = NULL;
-
-	if (idx)
-		call = g_slist_nth_data(calls, strtol(idx, NULL, 0) - 1);
-	else
-		call = NULL;
-
-	switch (cmd[0]) {
-	case '0':
-		if (find_vc_with_status(CALL_STATUS_WAITING))
-			foreach_vc_with_status(CALL_STATUS_WAITING,
-								release_call);
-		else
-			foreach_vc_with_status(CALL_STATUS_HELD, release_call);
-		break;
-	case '1':
-		if (idx) {
-			if (call)
-				err = release_call(call);
-			break;
-		}
-		err = release_answer_calls();
-		break;
-	case '2':
-		if (idx) {
-			if (call)
-				err = split_call(call);
-		} else {
-			call = find_vc_with_status(CALL_STATUS_WAITING);
-
-			if (call)
-				err = answer_call(call);
-			else
-				err = swap_calls();
-		}
-		break;
-	case '3':
-		if (find_vc_with_status(CALL_STATUS_HELD) ||
-				find_vc_with_status(CALL_STATUS_WAITING))
-			err = create_conference();
-		break;
-	case '4':
-		err = call_transfer();
-		break;
-	default:
-		DBG("Unknown call hold request");
-		break;
-	}
-
-	if (err)
-		telephony_call_hold_rsp(telephony_device,
-					CME_ERROR_AG_FAILURE);
-	else
-		telephony_call_hold_rsp(telephony_device, CME_ERROR_NONE);
-}
-
-void telephony_nr_and_ec_req(void *telephony_device, gboolean enable)
-{
-	DBG("telephony-ofono: got %s NR and EC request",
-			enable ? "enable" : "disable");
-
-	telephony_nr_and_ec_rsp(telephony_device, CME_ERROR_NONE);
-}
-
-void telephony_key_press_req(void *telephony_device, const char *keys)
-{
-	struct voice_call *active, *incoming;
-	int err;
-
-	DBG("telephony-ofono: got key press request for %s", keys);
-
-	incoming = find_vc_with_status(CALL_STATUS_INCOMING);
-
-	active = find_vc_with_status(CALL_STATUS_ACTIVE);
-
-	if (incoming)
-		err = answer_call(incoming);
-	else if (active)
-		err = release_call(active);
-	else
-		err = 0;
-
-	if (err < 0)
-		telephony_key_press_rsp(telephony_device,
-							CME_ERROR_AG_FAILURE);
-	else
-		telephony_key_press_rsp(telephony_device, CME_ERROR_NONE);
-}
-
-void telephony_voice_dial_req(void *telephony_device, gboolean enable)
-{
-	DBG("telephony-ofono: got %s voice dial request",
-			enable ? "enable" : "disable");
-
-	telephony_voice_dial_rsp(telephony_device, CME_ERROR_NOT_SUPPORTED);
-}
-
-static gboolean iter_get_basic_args(DBusMessageIter *iter,
-					int first_arg_type, ...)
-{
-	int type;
-	va_list ap;
-
-	va_start(ap, first_arg_type);
-
-	for (type = first_arg_type; type != DBUS_TYPE_INVALID;
-		type = va_arg(ap, int)) {
-		void *value = va_arg(ap, void *);
-		int real_type = dbus_message_iter_get_arg_type(iter);
-
-		if (real_type != type) {
-			error("iter_get_basic_args: expected %c but got %c",
-				(char) type, (char) real_type);
-			break;
-		}
-
-		dbus_message_iter_get_basic(iter, value);
-		dbus_message_iter_next(iter);
-	}
-
-	va_end(ap);
-
-	return type == DBUS_TYPE_INVALID ? TRUE : FALSE;
-}
-
-static void call_free(void *data)
-{
-	struct voice_call *vc = data;
-
-	DBG("%s", vc->obj_path);
-
-	if (vc->status == CALL_STATUS_ACTIVE)
-		telephony_update_indicator(ofono_indicators, "call",
-							EV_CALL_INACTIVE);
-	else
-		telephony_update_indicator(ofono_indicators, "callsetup",
-							EV_CALLSETUP_INACTIVE);
-
-	if (vc->status == CALL_STATUS_INCOMING)
-		telephony_calling_stopped_ind();
-
-	g_dbus_remove_watch(vc->watch);
-	g_free(vc->obj_path);
-	g_free(vc->number);
-	g_free(vc);
-}
-
-static gboolean handle_vc_property_changed(DBusConnection *conn,
-					DBusMessage *msg, void *data)
-{
-	struct voice_call *vc = data;
-	const char *obj_path = dbus_message_get_path(msg);
-	DBusMessageIter iter, sub;
-	const char *property, *state;
-
-	DBG("path %s", obj_path);
-
-	dbus_message_iter_init(msg, &iter);
-
-	if (dbus_message_iter_get_arg_type(&iter) != DBUS_TYPE_STRING) {
-		error("Unexpected signature in vc PropertyChanged signal");
-		return TRUE;
-	}
-
-	dbus_message_iter_get_basic(&iter, &property);
-	DBG("property %s", property);
-
-	dbus_message_iter_next(&iter);
-	dbus_message_iter_recurse(&iter, &sub);
-	if (g_str_equal(property, "State")) {
-		dbus_message_iter_get_basic(&sub, &state);
-		DBG("State %s", state);
-		if (g_str_equal(state, "disconnected")) {
-			calls = g_slist_remove(calls, vc);
-			call_free(vc);
-		} else if (g_str_equal(state, "active")) {
-			telephony_update_indicator(ofono_indicators,
-							"call", EV_CALL_ACTIVE);
-			telephony_update_indicator(ofono_indicators,
-							"callsetup",
-							EV_CALLSETUP_INACTIVE);
-			if (vc->status == CALL_STATUS_INCOMING)
-				telephony_calling_stopped_ind();
-			vc->status = CALL_STATUS_ACTIVE;
-		} else if (g_str_equal(state, "alerting")) {
-			telephony_update_indicator(ofono_indicators,
-					"callsetup", EV_CALLSETUP_ALERTING);
-			vc->status = CALL_STATUS_ALERTING;
-			vc->originating = TRUE;
-		} else if (g_str_equal(state, "incoming")) {
-			/* state change from waiting to incoming */
-			telephony_update_indicator(ofono_indicators,
-					"callsetup", EV_CALLSETUP_INCOMING);
-			telephony_incoming_call_ind(vc->number,
-						NUMBER_TYPE_TELEPHONY);
-			vc->status = CALL_STATUS_INCOMING;
-			vc->originating = FALSE;
-		} else if (g_str_equal(state, "held")) {
-			vc->status = CALL_STATUS_HELD;
-			if (find_vc_without_status(CALL_STATUS_HELD))
-				telephony_update_indicator(ofono_indicators,
-							"callheld",
-							EV_CALLHELD_MULTIPLE);
-			else
-				telephony_update_indicator(ofono_indicators,
-							"callheld",
-							EV_CALLHELD_ON_HOLD);
-		}
-	} else if (g_str_equal(property, "Multiparty")) {
-		dbus_bool_t multiparty;
-
-		dbus_message_iter_get_basic(&sub, &multiparty);
-		DBG("Multiparty %s", multiparty ? "True" : "False");
-		vc->conference = multiparty;
-	}
-
-	return TRUE;
-}
-
-static struct voice_call *call_new(const char *path, DBusMessageIter *properties)
-{
-	struct voice_call *vc;
-
-	DBG("%s", path);
-
-	vc = g_new0(struct voice_call, 1);
-	vc->obj_path = g_strdup(path);
-	vc->watch = g_dbus_add_signal_watch(btd_get_dbus_connection(),
-					NULL, path,
-					OFONO_VC_INTERFACE, "PropertyChanged",
-					handle_vc_property_changed, vc, NULL);
-
-	while (dbus_message_iter_get_arg_type(properties)
-						== DBUS_TYPE_DICT_ENTRY) {
-		DBusMessageIter entry, value;
-		const char *property, *cli, *state;
-		dbus_bool_t multiparty;
-
-		dbus_message_iter_recurse(properties, &entry);
-		dbus_message_iter_get_basic(&entry, &property);
-
-		dbus_message_iter_next(&entry);
-		dbus_message_iter_recurse(&entry, &value);
-
-		if (g_str_equal(property, "LineIdentification")) {
-			dbus_message_iter_get_basic(&value, &cli);
-			DBG("cli %s", cli);
-			vc->number = g_strdup(cli);
-		} else if (g_str_equal(property, "State")) {
-			dbus_message_iter_get_basic(&value, &state);
-			DBG("state %s", state);
-			if (g_str_equal(state, "incoming"))
-				vc->status = CALL_STATUS_INCOMING;
-			else if (g_str_equal(state, "dialing"))
-				vc->status = CALL_STATUS_DIALING;
-			else if (g_str_equal(state, "alerting"))
-				vc->status = CALL_STATUS_ALERTING;
-			else if (g_str_equal(state, "waiting"))
-				vc->status = CALL_STATUS_WAITING;
-			else if (g_str_equal(state, "held"))
-				vc->status = CALL_STATUS_HELD;
-		} else if (g_str_equal(property, "Multiparty")) {
-			dbus_message_iter_get_basic(&value, &multiparty);
-			DBG("Multipary %s", multiparty ? "True" : "False");
-			vc->conference = multiparty;
-		}
-
-		dbus_message_iter_next(properties);
-	}
-
-	switch (vc->status) {
-	case CALL_STATUS_INCOMING:
-		DBG("CALL_STATUS_INCOMING");
-		vc->originating = FALSE;
-		telephony_update_indicator(ofono_indicators, "callsetup",
-					EV_CALLSETUP_INCOMING);
-		telephony_incoming_call_ind(vc->number, NUMBER_TYPE_TELEPHONY);
-		break;
-	case CALL_STATUS_DIALING:
-		DBG("CALL_STATUS_DIALING");
-		vc->originating = TRUE;
-		g_free(last_dialed_number);
-		last_dialed_number = g_strdup(vc->number);
-		telephony_update_indicator(ofono_indicators, "callsetup",
-					EV_CALLSETUP_OUTGOING);
-		break;
-	case CALL_STATUS_ALERTING:
-		DBG("CALL_STATUS_ALERTING");
-		vc->originating = TRUE;
-		g_free(last_dialed_number);
-		last_dialed_number = g_strdup(vc->number);
-		telephony_update_indicator(ofono_indicators, "callsetup",
-					EV_CALLSETUP_ALERTING);
-		break;
-	case CALL_STATUS_WAITING:
-		DBG("CALL_STATUS_WAITING");
-		vc->originating = FALSE;
-		telephony_update_indicator(ofono_indicators, "callsetup",
-					EV_CALLSETUP_INCOMING);
-		telephony_call_waiting_ind(vc->number, NUMBER_TYPE_TELEPHONY);
-		break;
-	}
-
-	return vc;
-}
-
-static void remove_pending(DBusPendingCall *call)
-{
-	pending = g_slist_remove(pending, call);
-	dbus_pending_call_unref(call);
-}
-
-static void call_added(const char *path, DBusMessageIter *properties)
-{
-	struct voice_call *vc;
-
-	DBG("%s", path);
-
-	vc = find_vc(path);
-	if (vc)
-		return;
-
-	vc = call_new(path, properties);
-	calls = g_slist_prepend(calls, vc);
-}
-
-static void get_calls_reply(DBusPendingCall *call, void *user_data)
-{
-	DBusError err;
-	DBusMessage *reply;
-	DBusMessageIter iter, entry;
-
-	DBG("");
-	reply = dbus_pending_call_steal_reply(call);
-
-	dbus_error_init(&err);
-	if (dbus_set_error_from_message(&err, reply)) {
-		error("ofono replied with an error: %s, %s",
-				err.name, err.message);
-		dbus_error_free(&err);
-		goto done;
-	}
-
-	dbus_message_iter_init(reply, &iter);
-
-	if (dbus_message_iter_get_arg_type(&iter) != DBUS_TYPE_ARRAY) {
-		error("Unexpected signature");
-		goto done;
-	}
-
-	dbus_message_iter_recurse(&iter, &entry);
-
-	while (dbus_message_iter_get_arg_type(&entry)
-						== DBUS_TYPE_STRUCT) {
-		const char *path;
-		DBusMessageIter value, properties;
-
-		dbus_message_iter_recurse(&entry, &value);
-		dbus_message_iter_get_basic(&value, &path);
-
-		dbus_message_iter_next(&value);
-		dbus_message_iter_recurse(&value, &properties);
-
-		call_added(path, &properties);
-
-		dbus_message_iter_next(&entry);
-	}
-
-done:
-	dbus_message_unref(reply);
-	remove_pending(call);
-}
-
-static void handle_network_property(const char *property, DBusMessageIter *variant)
-{
-	const char *status, *operator;
-	unsigned int signals_bar;
-
-	if (g_str_equal(property, "Status")) {
-		dbus_message_iter_get_basic(variant, &status);
-		DBG("Status is %s", status);
-		if (g_str_equal(status, "registered")) {
-			net.status = NETWORK_REG_STATUS_HOME;
-			telephony_update_indicator(ofono_indicators,
-						"roam", EV_ROAM_INACTIVE);
-			telephony_update_indicator(ofono_indicators,
-						"service", EV_SERVICE_PRESENT);
-		} else if (g_str_equal(status, "roaming")) {
-			net.status = NETWORK_REG_STATUS_ROAM;
-			telephony_update_indicator(ofono_indicators,
-						"roam", EV_ROAM_ACTIVE);
-			telephony_update_indicator(ofono_indicators,
-						"service", EV_SERVICE_PRESENT);
-		} else {
-			net.status = NETWORK_REG_STATUS_NOSERV;
-			telephony_update_indicator(ofono_indicators,
-						"roam", EV_ROAM_INACTIVE);
-			telephony_update_indicator(ofono_indicators,
-						"service", EV_SERVICE_NONE);
-		}
-	} else if (g_str_equal(property, "Name")) {
-		dbus_message_iter_get_basic(variant, &operator);
-		DBG("Operator is %s", operator);
-		g_free(net.operator_name);
-		net.operator_name = g_strdup(operator);
-	} else if (g_str_equal(property, "SignalStrength")) {
-		dbus_message_iter_get_basic(variant, &signals_bar);
-		DBG("SignalStrength is %d", signals_bar);
-		net.signals_bar = signals_bar;
-		telephony_update_indicator(ofono_indicators, "signal",
-						(signals_bar + 20) / 21);
-	}
-}
-
-static int parse_network_properties(DBusMessageIter *properties)
-{
-	int i;
-
-	/* Reset indicators */
-	for (i = 0; ofono_indicators[i].desc != NULL; i++) {
-		if (g_str_equal(ofono_indicators[i].desc, "battchg"))
-			ofono_indicators[i].val = 5;
-		else
-			ofono_indicators[i].val = 0;
-	}
-
-	while (dbus_message_iter_get_arg_type(properties)
-						== DBUS_TYPE_DICT_ENTRY) {
-		const char *key;
-		DBusMessageIter value, entry;
-
-		dbus_message_iter_recurse(properties, &entry);
-		dbus_message_iter_get_basic(&entry, &key);
-
-		dbus_message_iter_next(&entry);
-		dbus_message_iter_recurse(&entry, &value);
-
-		handle_network_property(key, &value);
-
-		dbus_message_iter_next(properties);
-	}
-
-	return 0;
-}
-
-static void get_properties_reply(DBusPendingCall *call, void *user_data)
-{
-	DBusError err;
-	DBusMessage *reply;
-	DBusMessageIter iter, properties;
-	int ret = 0;
-
-	DBG("");
-	reply = dbus_pending_call_steal_reply(call);
-
-	dbus_error_init(&err);
-	if (dbus_set_error_from_message(&err, reply)) {
-		error("ofono replied with an error: %s, %s",
-				err.name, err.message);
-		dbus_error_free(&err);
-		goto done;
-	}
-
-	dbus_message_iter_init(reply, &iter);
-
-	if (dbus_message_iter_get_arg_type(&iter) != DBUS_TYPE_ARRAY) {
-		error("Unexpected signature");
-		goto done;
-	}
-
-	dbus_message_iter_recurse(&iter, &properties);
-
-	ret = parse_network_properties(&properties);
-	if (ret < 0) {
-		error("Unable to parse %s.GetProperty reply",
-						OFONO_NETWORKREG_INTERFACE);
-		goto done;
-	}
-
-	ret = send_method_call(OFONO_BUS_NAME, modem_obj_path,
-				OFONO_VCMANAGER_INTERFACE, "GetCalls",
-				get_calls_reply, NULL, DBUS_TYPE_INVALID);
-	if (ret < 0)
-		error("Unable to send %s.GetCalls",
-						OFONO_VCMANAGER_INTERFACE);
-
-done:
-	dbus_message_unref(reply);
-	remove_pending(call);
-}
-
-static void network_found(const char *path)
-{
-	int ret;
-
-	DBG("%s", path);
-
-	modem_obj_path = g_strdup(path);
-
-	ret = send_method_call(OFONO_BUS_NAME, path,
-				OFONO_NETWORKREG_INTERFACE, "GetProperties",
-				get_properties_reply, NULL, DBUS_TYPE_INVALID);
-	if (ret < 0)
-		error("Unable to send %s.GetProperties",
-						OFONO_NETWORKREG_INTERFACE);
-}
-
-static void modem_removed(const char *path)
-{
-	if (g_strcmp0(modem_obj_path, path) != 0)
-		return;
-
-	DBG("%s", path);
-
-	g_slist_free_full(calls, call_free);
-	calls = NULL;
-
-	g_free(net.operator_name);
-	net.operator_name = NULL;
-	net.status = NETWORK_REG_STATUS_NOSERV;
-	net.signals_bar = 0;
-
-	g_free(modem_obj_path);
-	modem_obj_path = NULL;
-}
-
-static void parse_modem_interfaces(const char *path, DBusMessageIter *ifaces)
-{
-	DBG("%s", path);
-
-	while (dbus_message_iter_get_arg_type(ifaces) == DBUS_TYPE_STRING) {
-		const char *iface;
-
-		dbus_message_iter_get_basic(ifaces, &iface);
-
-		if (g_str_equal(iface, OFONO_NETWORKREG_INTERFACE)) {
-			network_found(path);
-			return;
-		}
-
-		dbus_message_iter_next(ifaces);
-	}
-
-	modem_removed(path);
-}
-
-static void modem_added(const char *path, DBusMessageIter *properties)
-{
-	if (modem_obj_path != NULL) {
-		DBG("Ignoring, modem already exist");
-		return;
-	}
-
-	DBG("%s", path);
-
-	while (dbus_message_iter_get_arg_type(properties)
-						== DBUS_TYPE_DICT_ENTRY) {
-		const char *key;
-		DBusMessageIter interfaces, value, entry;
-
-		dbus_message_iter_recurse(properties, &entry);
-		dbus_message_iter_get_basic(&entry, &key);
-
-		dbus_message_iter_next(&entry);
-		dbus_message_iter_recurse(&entry, &value);
-
-		if (strcasecmp(key, "Interfaces") != 0)
-			goto next;
-
-		if (dbus_message_iter_get_arg_type(&value)
-							!= DBUS_TYPE_ARRAY) {
-			error("Invalid Signature");
-			return;
-		}
-
-		dbus_message_iter_recurse(&value, &interfaces);
-
-		parse_modem_interfaces(path, &interfaces);
-
-		if (modem_obj_path != NULL)
-			return;
-
-	next:
-		dbus_message_iter_next(properties);
-	}
-}
-
-static void get_modems_reply(DBusPendingCall *call, void *user_data)
-{
-	DBusError err;
-	DBusMessage *reply;
-	DBusMessageIter iter, entry;
-
-	DBG("");
-	reply = dbus_pending_call_steal_reply(call);
-
-	dbus_error_init(&err);
-	if (dbus_set_error_from_message(&err, reply)) {
-		error("ofono replied with an error: %s, %s",
-				err.name, err.message);
-		dbus_error_free(&err);
-		goto done;
-	}
-
-	/* Skip modem selection if a modem already exist */
-	if (modem_obj_path != NULL)
-		goto done;
-
-	dbus_message_iter_init(reply, &iter);
-
-	if (dbus_message_iter_get_arg_type(&iter) != DBUS_TYPE_ARRAY) {
-		error("Unexpected signature");
-		goto done;
-	}
-
-	dbus_message_iter_recurse(&iter, &entry);
-
-	while (dbus_message_iter_get_arg_type(&entry)
-						== DBUS_TYPE_STRUCT) {
-		const char *path;
-		DBusMessageIter item, properties;
-
-		dbus_message_iter_recurse(&entry, &item);
-		dbus_message_iter_get_basic(&item, &path);
-
-		dbus_message_iter_next(&item);
-		dbus_message_iter_recurse(&item, &properties);
-
-		modem_added(path, &properties);
-		if (modem_obj_path != NULL)
-			break;
-
-		dbus_message_iter_next(&entry);
-	}
-
-done:
-	dbus_message_unref(reply);
-	remove_pending(call);
-}
-
-static gboolean handle_network_property_changed(DBusConnection *conn,
-						DBusMessage *msg, void *data)
-{
-	DBusMessageIter iter, variant;
-	const char *property;
-
-	dbus_message_iter_init(msg, &iter);
-
-	if (dbus_message_iter_get_arg_type(&iter) != DBUS_TYPE_STRING) {
-		error("Unexpected signature in networkregistration"
-					" PropertyChanged signal");
-		return TRUE;
-	}
-	dbus_message_iter_get_basic(&iter, &property);
-	DBG("in handle_registration_property_changed(),"
-					" the property is %s", property);
-
-	dbus_message_iter_next(&iter);
-	dbus_message_iter_recurse(&iter, &variant);
-
-	handle_network_property(property, &variant);
-
-	return TRUE;
-}
-
-static void handle_modem_property(const char *path, const char *property,
-						DBusMessageIter *variant)
-{
-	DBG("%s", property);
-
-	if (g_str_equal(property, "Interfaces")) {
-		DBusMessageIter interfaces;
-
-		if (dbus_message_iter_get_arg_type(variant)
-							!= DBUS_TYPE_ARRAY) {
-			error("Invalid signature");
-			return;
-		}
-
-		dbus_message_iter_recurse(variant, &interfaces);
-		parse_modem_interfaces(path, &interfaces);
-	}
-}
-
-static gboolean handle_modem_property_changed(DBusConnection *conn,
-						DBusMessage *msg, void *data)
-{
-	DBusMessageIter iter, variant;
-	const char *property, *path;
-
-	path = dbus_message_get_path(msg);
-
-	/* Ignore if modem already exist and paths doesn't match */
-	if (modem_obj_path != NULL &&
-				g_str_equal(path, modem_obj_path) == FALSE)
-		return TRUE;
-
-	dbus_message_iter_init(msg, &iter);
-
-	if (dbus_message_iter_get_arg_type(&iter) != DBUS_TYPE_STRING) {
-		error("Unexpected signature in %s.%s PropertyChanged signal",
-					dbus_message_get_interface(msg),
-					dbus_message_get_member(msg));
-		return TRUE;
-	}
-
-	dbus_message_iter_get_basic(&iter, &property);
-
-	dbus_message_iter_next(&iter);
-	dbus_message_iter_recurse(&iter, &variant);
-
-	handle_modem_property(path, property, &variant);
-
-	return TRUE;
-}
-
-static gboolean handle_vcmanager_call_added(DBusConnection *conn,
-						DBusMessage *msg, void *data)
-{
-	DBusMessageIter iter, properties;
-	const char *path = dbus_message_get_path(msg);
-
-	/* Ignore call if modem path doesn't math */
-	if (g_strcmp0(modem_obj_path, path) != 0)
-		return TRUE;
-
-	dbus_message_iter_init(msg, &iter);
-
-	if (dbus_message_iter_get_arg_type(&iter)
-						!= DBUS_TYPE_OBJECT_PATH) {
-		error("Unexpected signature in %s.%s signal",
-					dbus_message_get_interface(msg),
-					dbus_message_get_member(msg));
-		return TRUE;
-	}
-
-	dbus_message_iter_get_basic(&iter, &path);
-	dbus_message_iter_next(&iter);
-	dbus_message_iter_recurse(&iter, &properties);
-
-	call_added(path, &properties);
-
-	return TRUE;
-}
-
-static void call_removed(const char *path)
-{
-	struct voice_call *vc;
-
-	DBG("%s", path);
-
-	vc = find_vc(path);
-	if (vc == NULL)
-		return;
-
-	calls = g_slist_remove(calls, vc);
-	call_free(vc);
-}
-
-static gboolean handle_vcmanager_call_removed(DBusConnection *conn,
-						DBusMessage *msg, void *data)
-{
-	const char *path = dbus_message_get_path(msg);
-
-	/* Ignore call if modem path doesn't math */
-	if (g_strcmp0(modem_obj_path, path) != 0)
-		return TRUE;
-
-	if (!dbus_message_get_args(msg, NULL,
-				DBUS_TYPE_OBJECT_PATH, &path,
-				DBUS_TYPE_INVALID)) {
-		error("Unexpected signature in %s.%s signal",
-					dbus_message_get_interface(msg),
-					dbus_message_get_member(msg));
-		return TRUE;
-	}
-
-	call_removed(path);
-
-	return TRUE;
-}
-
-static gboolean handle_manager_modem_added(DBusConnection *conn,
-						DBusMessage *msg, void *data)
-{
-	DBusMessageIter iter, properties;
-	const char *path;
-
-	if (modem_obj_path != NULL)
-		return TRUE;
-
-	dbus_message_iter_init(msg, &iter);
-
-	if (dbus_message_iter_get_arg_type(&iter)
-						!= DBUS_TYPE_OBJECT_PATH) {
-		error("Unexpected signature in %s.%s signal",
-					dbus_message_get_interface(msg),
-					dbus_message_get_member(msg));
-		return TRUE;
-	}
-
-	dbus_message_iter_get_basic(&iter, &path);
-	dbus_message_iter_next(&iter);
-	dbus_message_iter_recurse(&iter, &properties);
-
-	modem_added(path, &properties);
-
-	return TRUE;
-}
-
-static gboolean handle_manager_modem_removed(DBusConnection *conn,
-						DBusMessage *msg, void *data)
-{
-	const char *path;
-
-	if (!dbus_message_get_args(msg, NULL,
-				DBUS_TYPE_OBJECT_PATH, &path,
-				DBUS_TYPE_INVALID)) {
-		error("Unexpected signature in %s.%s signal",
-					dbus_message_get_interface(msg),
-					dbus_message_get_member(msg));
-		return TRUE;
-	}
-
-	modem_removed(path);
-
-	return TRUE;
-}
-
-static void hal_battery_level_reply(DBusPendingCall *call, void *user_data)
-{
-	DBusMessage *reply;
-	DBusError err;
-	dbus_int32_t level;
-	int *value = user_data;
-
-	reply = dbus_pending_call_steal_reply(call);
-
-	dbus_error_init(&err);
-	if (dbus_set_error_from_message(&err, reply)) {
-		error("hald replied with an error: %s, %s",
-				err.name, err.message);
-		dbus_error_free(&err);
-		goto done;
-	}
-
-	dbus_error_init(&err);
-	if (dbus_message_get_args(reply, &err,
-				DBUS_TYPE_INT32, &level,
-				DBUS_TYPE_INVALID) == FALSE) {
-		error("Unable to parse GetPropertyInteger reply: %s, %s",
-							err.name, err.message);
-		dbus_error_free(&err);
-		goto done;
-	}
-
-	*value = (int) level;
-
-	if (value == &battchg_last)
-		DBG("telephony-ofono: battery.charge_level.last_full"
-					" is %d", *value);
-	else if (value == &battchg_design)
-		DBG("telephony-ofono: battery.charge_level.design"
-					" is %d", *value);
-	else
-		DBG("telephony-ofono: battery.charge_level.current"
-					" is %d", *value);
-
-	if ((battchg_design > 0 || battchg_last > 0) && battchg_cur >= 0) {
-		int new, max;
-
-		if (battchg_last > 0)
-			max = battchg_last;
-		else
-			max = battchg_design;
-
-		new = battchg_cur * 5 / max;
-
-		telephony_update_indicator(ofono_indicators, "battchg", new);
-	}
-done:
-	dbus_message_unref(reply);
-	remove_pending(call);
-}
-
-static void hal_get_integer(const char *path, const char *key, void *user_data)
-{
-	send_method_call("org.freedesktop.Hal", path,
-			"org.freedesktop.Hal.Device",
-			"GetPropertyInteger",
-			hal_battery_level_reply, user_data,
-			DBUS_TYPE_STRING, &key,
-			DBUS_TYPE_INVALID);
-}
-
-static gboolean handle_hal_property_modified(DBusConnection *conn,
-						DBusMessage *msg, void *data)
-{
-	const char *path;
-	DBusMessageIter iter, array;
-	dbus_int32_t num_changes;
-
-	path = dbus_message_get_path(msg);
-
-	dbus_message_iter_init(msg, &iter);
-
-	if (dbus_message_iter_get_arg_type(&iter) != DBUS_TYPE_INT32) {
-		error("Unexpected signature in hal PropertyModified signal");
-		return TRUE;
-	}
-
-	dbus_message_iter_get_basic(&iter, &num_changes);
-	dbus_message_iter_next(&iter);
-
-	if (dbus_message_iter_get_arg_type(&iter) != DBUS_TYPE_ARRAY) {
-		error("Unexpected signature in hal PropertyModified signal");
-		return TRUE;
-	}
-
-	dbus_message_iter_recurse(&iter, &array);
-
-	while (dbus_message_iter_get_arg_type(&array) != DBUS_TYPE_INVALID) {
-		DBusMessageIter prop;
-		const char *name;
-		dbus_bool_t added, removed;
-
-		dbus_message_iter_recurse(&array, &prop);
-
-		if (!iter_get_basic_args(&prop,
-					DBUS_TYPE_STRING, &name,
-					DBUS_TYPE_BOOLEAN, &added,
-					DBUS_TYPE_BOOLEAN, &removed,
-					DBUS_TYPE_INVALID)) {
-			error("Invalid hal PropertyModified parameters");
-			break;
-		}
-
-		if (g_str_equal(name, "battery.charge_level.last_full"))
-			hal_get_integer(path, name, &battchg_last);
-		else if (g_str_equal(name, "battery.charge_level.current"))
-			hal_get_integer(path, name, &battchg_cur);
-		else if (g_str_equal(name, "battery.charge_level.design"))
-			hal_get_integer(path, name, &battchg_design);
-
-		dbus_message_iter_next(&array);
-	}
-
-	return TRUE;
-}
-
-static void add_watch(const char *sender, const char *path,
-				const char *interface, const char *member,
-				GDBusSignalFunction function)
-{
-	guint watch;
-
-	watch = g_dbus_add_signal_watch(btd_get_dbus_connection(),
-					sender, path, interface,
-					member, function, NULL, NULL);
-
-	watches = g_slist_prepend(watches, GUINT_TO_POINTER(watch));
-}
-
-static void hal_find_device_reply(DBusPendingCall *call, void *user_data)
-{
-	DBusMessage *reply;
-	DBusError err;
-	DBusMessageIter iter, sub;
-	int type;
-	const char *path;
-
-	DBG("begin of hal_find_device_reply()");
-	reply = dbus_pending_call_steal_reply(call);
-
-	dbus_error_init(&err);
-
-	if (dbus_set_error_from_message(&err, reply)) {
-		error("hald replied with an error: %s, %s",
-				err.name, err.message);
-		dbus_error_free(&err);
-		goto done;
-	}
-
-	dbus_message_iter_init(reply, &iter);
-
-	if (dbus_message_iter_get_arg_type(&iter) != DBUS_TYPE_ARRAY) {
-		error("Unexpected signature in hal_find_device_reply()");
-		goto done;
-	}
-
-	dbus_message_iter_recurse(&iter, &sub);
-
-	type = dbus_message_iter_get_arg_type(&sub);
-
-	if (type != DBUS_TYPE_OBJECT_PATH && type != DBUS_TYPE_STRING) {
-		error("No hal device with battery capability found");
-		goto done;
-	}
-
-	dbus_message_iter_get_basic(&sub, &path);
-
-	DBG("telephony-ofono: found battery device at %s", path);
-
-	add_watch(NULL, path, "org.freedesktop.Hal.Device",
-			"PropertyModified", handle_hal_property_modified);
-
-	hal_get_integer(path, "battery.charge_level.last_full", &battchg_last);
-	hal_get_integer(path, "battery.charge_level.current", &battchg_cur);
-	hal_get_integer(path, "battery.charge_level.design", &battchg_design);
-done:
-	dbus_message_unref(reply);
-	remove_pending(call);
-}
-
-static void handle_service_connect(DBusConnection *conn, void *user_data)
-{
-	DBG("telephony-ofono: %s found", OFONO_BUS_NAME);
-
-	send_method_call(OFONO_BUS_NAME, OFONO_PATH,
-				OFONO_MANAGER_INTERFACE, "GetModems",
-				get_modems_reply, NULL, DBUS_TYPE_INVALID);
-}
-
-static void handle_service_disconnect(DBusConnection *conn, void *user_data)
-{
-	DBG("telephony-ofono: %s exitted", OFONO_BUS_NAME);
-
-	if (modem_obj_path)
-		modem_removed(modem_obj_path);
-}
-
-int telephony_init(void)
-{
-	uint32_t features = AG_FEATURE_EC_ANDOR_NR |
-				AG_FEATURE_INBAND_RINGTONE |
-				AG_FEATURE_REJECT_A_CALL |
-				AG_FEATURE_ENHANCED_CALL_STATUS |
-				AG_FEATURE_ENHANCED_CALL_CONTROL |
-				AG_FEATURE_EXTENDED_ERROR_RESULT_CODES |
-				AG_FEATURE_THREE_WAY_CALLING;
-	const char *battery_cap = "battery";
-	int ret;
-	guint watch;
-
-	add_watch(OFONO_BUS_NAME, NULL, OFONO_MODEM_INTERFACE,
-			"PropertyChanged", handle_modem_property_changed);
-	add_watch(OFONO_BUS_NAME, NULL, OFONO_NETWORKREG_INTERFACE,
-			"PropertyChanged", handle_network_property_changed);
-	add_watch(OFONO_BUS_NAME, NULL, OFONO_MANAGER_INTERFACE,
-			"ModemAdded", handle_manager_modem_added);
-	add_watch(OFONO_BUS_NAME, NULL, OFONO_MANAGER_INTERFACE,
-			"ModemRemoved", handle_manager_modem_removed);
-	add_watch(OFONO_BUS_NAME, NULL, OFONO_VCMANAGER_INTERFACE,
-			"CallAdded", handle_vcmanager_call_added);
-	add_watch(OFONO_BUS_NAME, NULL, OFONO_VCMANAGER_INTERFACE,
-			"CallRemoved", handle_vcmanager_call_removed);
-
-	watch = g_dbus_add_service_watch(btd_get_dbus_connection(),
-						OFONO_BUS_NAME,
-						handle_service_connect,
-						handle_service_disconnect,
-						NULL, NULL);
-	if (watch == 0)
-		return -ENOMEM;
-
-	watches = g_slist_prepend(watches, GUINT_TO_POINTER(watch));
-
-	ret = send_method_call("org.freedesktop.Hal",
-				"/org/freedesktop/Hal/Manager",
-				"org.freedesktop.Hal.Manager",
-				"FindDeviceByCapability",
-				hal_find_device_reply, NULL,
-				DBUS_TYPE_STRING, &battery_cap,
-				DBUS_TYPE_INVALID);
-	if (ret < 0)
-		return ret;
-
-	DBG("telephony_init() successfully");
-
-	telephony_ready_ind(features, ofono_indicators, BTRH_NOT_SUPPORTED,
-								chld_str);
-
-	return ret;
-}
-
-static void remove_watch(gpointer data)
-{
-	g_dbus_remove_watch(GPOINTER_TO_UINT(data));
-}
-
-static void pending_free(void *data)
-{
-	DBusPendingCall *call = data;
-
-	if (!dbus_pending_call_get_completed(call))
-		dbus_pending_call_cancel(call);
-
-	dbus_pending_call_unref(call);
-}
-
-void telephony_exit(void)
-{
-	DBG("");
-
-	g_free(last_dialed_number);
-	last_dialed_number = NULL;
-
-	if (modem_obj_path)
-		modem_removed(modem_obj_path);
-
-	g_slist_free_full(watches, remove_watch);
-	watches = NULL;
-
-	g_slist_free_full(pending, pending_free);
-	pending = NULL;
-
-	telephony_deinit();
-}
-- 
1.7.11.7


^ permalink raw reply related

* [PATCH BlueZ 07/13] build: Remove telephony-dummy.c
From: Luiz Augusto von Dentz @ 2012-11-13 13:21 UTC (permalink / raw)
  To: linux-bluetooth
In-Reply-To: <1352812880-7306-1-git-send-email-luiz.dentz@gmail.com>

From: Luiz Augusto von Dentz <luiz.von.dentz@intel.com>

---
 Makefile.am             |  10 +-
 audio/telephony-dummy.c | 444 ------------------------------------------------
 2 files changed, 1 insertion(+), 453 deletions(-)
 delete mode 100644 audio/telephony-dummy.c

diff --git a/Makefile.am b/Makefile.am
index 84566c8..ad2e27a 100644
--- a/Makefile.am
+++ b/Makefile.am
@@ -121,11 +121,6 @@ builtin_sources += audio/main.c \
 			audio/transport.h audio/transport.c \
 			audio/player.h audio/player.c \
 			audio/telephony.h audio/a2dp-codecs.h
-builtin_nodist += audio/telephony.c
-
-noinst_LIBRARIES += audio/libtelephony.a
-
-audio_libtelephony_a_SOURCES = audio/telephony.h audio/telephony-dummy.c
 endif
 
 if SAPPLUGIN
@@ -312,7 +307,7 @@ endif
 EXTRA_DIST += src/genbuiltin src/bluetooth.conf src/org.bluez.service \
 			src/main.conf profiles/network/network.conf \
 			profiles/input/input.conf profiles/proximity/proximity.conf \
-			audio/audio.conf audio/telephony-dummy.c \
+			audio/audio.conf \
 			profiles/sap/sap-dummy.c profiles/sap/sap-u8500.c
 
 include Makefile.tools
@@ -398,9 +393,6 @@ MAINTAINERCLEANFILES = Makefile.in \
 src/builtin.h: src/genbuiltin $(builtin_sources)
 	$(AM_V_GEN)$(srcdir)/src/genbuiltin $(builtin_modules) > $@
 
-audio/telephony.c: audio/@TELEPHONY_DRIVER@
-	$(AM_V_GEN)$(LN_S) $(abs_top_builddir)/$< $@
-
 profiles/sap/sap.c: profiles/sap/@SAP_DRIVER@
 	$(AM_V_GEN)$(LN_S) $(abs_top_srcdir)/$< $@
 
diff --git a/audio/telephony-dummy.c b/audio/telephony-dummy.c
deleted file mode 100644
index d1bbfd5..0000000
--- a/audio/telephony-dummy.c
+++ /dev/null
@@ -1,444 +0,0 @@
-/*
- *
- *  BlueZ - Bluetooth protocol stack for Linux
- *
- *  Copyright (C) 2006-2010  Nokia Corporation
- *  Copyright (C) 2004-2010  Marcel Holtmann <marcel@holtmann.org>
- *
- *
- *  This program is free software; you can redistribute it and/or modify
- *  it under the terms of the GNU General Public License as published by
- *  the Free Software Foundation; either version 2 of the License, or
- *  (at your option) any later version.
- *
- *  This program is distributed in the hope that it will be useful,
- *  but WITHOUT ANY WARRANTY; without even the implied warranty of
- *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
- *  GNU General Public License for more details.
- *
- *  You should have received a copy of the GNU General Public License
- *  along with this program; if not, write to the Free Software
- *  Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
- *
- */
-
-#ifdef HAVE_CONFIG_H
-#include <config.h>
-#endif
-
-#include <stdlib.h>
-#include <stdio.h>
-#include <stdint.h>
-#include <glib.h>
-#include <dbus/dbus.h>
-#include <gdbus.h>
-
-#include "dbus-common.h"
-#include "log.h"
-#include "telephony.h"
-#include "error.h"
-
-#define TELEPHONY_DUMMY_IFACE "org.bluez.TelephonyTest"
-#define TELEPHONY_DUMMY_PATH "/org/bluez/test"
-
-static const char *chld_str = "0,1,1x,2,2x,3,4";
-static char *subscriber_number = NULL;
-static char *active_call_number = NULL;
-static int active_call_status = 0;
-static int active_call_dir = 0;
-
-static gboolean events_enabled = FALSE;
-
-static struct indicator dummy_indicators[] =
-{
-	{ "battchg",	"0-5",	5,	TRUE },
-	{ "signal",	"0-5",	5,	TRUE },
-	{ "service",	"0,1",	1,	TRUE },
-	{ "call",	"0,1",	0,	TRUE },
-	{ "callsetup",	"0-3",	0,	TRUE },
-	{ "callheld",	"0-2",	0,	FALSE },
-	{ "roam",	"0,1",	0,	TRUE },
-	{ NULL }
-};
-
-void telephony_device_connected(void *telephony_device)
-{
-	DBG("telephony-dummy: device %p connected", telephony_device);
-}
-
-void telephony_device_disconnected(void *telephony_device)
-{
-	DBG("telephony-dummy: device %p disconnected", telephony_device);
-	events_enabled = FALSE;
-}
-
-void telephony_event_reporting_req(void *telephony_device, int ind)
-{
-	events_enabled = ind == 1 ? TRUE : FALSE;
-
-	telephony_event_reporting_rsp(telephony_device, CME_ERROR_NONE);
-}
-
-void telephony_response_and_hold_req(void *telephony_device, int rh)
-{
-	telephony_response_and_hold_rsp(telephony_device,
-						CME_ERROR_NOT_SUPPORTED);
-}
-
-void telephony_last_dialed_number_req(void *telephony_device)
-{
-	telephony_last_dialed_number_rsp(telephony_device, CME_ERROR_NONE);
-
-	/* Notify outgoing call set-up successfully initiated */
-	telephony_update_indicator(dummy_indicators, "callsetup",
-					EV_CALLSETUP_OUTGOING);
-	telephony_update_indicator(dummy_indicators, "callsetup",
-					EV_CALLSETUP_ALERTING);
-
-	active_call_status = CALL_STATUS_ALERTING;
-	active_call_dir = CALL_DIR_OUTGOING;
-}
-
-void telephony_terminate_call_req(void *telephony_device)
-{
-	g_free(active_call_number);
-	active_call_number = NULL;
-
-	telephony_terminate_call_rsp(telephony_device, CME_ERROR_NONE);
-
-	if (telephony_get_indicator(dummy_indicators, "callsetup") > 0)
-		telephony_update_indicator(dummy_indicators, "callsetup",
-						EV_CALLSETUP_INACTIVE);
-	else
-		telephony_update_indicator(dummy_indicators, "call",
-						EV_CALL_INACTIVE);
-}
-
-void telephony_answer_call_req(void *telephony_device)
-{
-	telephony_answer_call_rsp(telephony_device, CME_ERROR_NONE);
-
-	telephony_update_indicator(dummy_indicators, "call", EV_CALL_ACTIVE);
-	telephony_update_indicator(dummy_indicators, "callsetup",
-					EV_CALLSETUP_INACTIVE);
-
-	active_call_status = CALL_STATUS_ACTIVE;
-}
-
-void telephony_dial_number_req(void *telephony_device, const char *number)
-{
-	g_free(active_call_number);
-	active_call_number = g_strdup(number);
-
-	DBG("telephony-dummy: dial request to %s", active_call_number);
-
-	telephony_dial_number_rsp(telephony_device, CME_ERROR_NONE);
-
-	/* Notify outgoing call set-up successfully initiated */
-	telephony_update_indicator(dummy_indicators, "callsetup",
-					EV_CALLSETUP_OUTGOING);
-	telephony_update_indicator(dummy_indicators, "callsetup",
-					EV_CALLSETUP_ALERTING);
-
-	active_call_status = CALL_STATUS_ALERTING;
-	active_call_dir = CALL_DIR_OUTGOING;
-}
-
-void telephony_transmit_dtmf_req(void *telephony_device, char tone)
-{
-	DBG("telephony-dummy: transmit dtmf: %c", tone);
-	telephony_transmit_dtmf_rsp(telephony_device, CME_ERROR_NONE);
-}
-
-void telephony_subscriber_number_req(void *telephony_device)
-{
-	DBG("telephony-dummy: subscriber number request");
-	if (subscriber_number)
-		telephony_subscriber_number_ind(subscriber_number,
-						NUMBER_TYPE_TELEPHONY,
-						SUBSCRIBER_SERVICE_VOICE);
-	telephony_subscriber_number_rsp(telephony_device, CME_ERROR_NONE);
-}
-
-void telephony_list_current_calls_req(void *telephony_device)
-{
-	DBG("telephony-dummy: list current calls request");
-	if (active_call_number)
-		telephony_list_current_call_ind(1, active_call_dir,
-						active_call_status,
-						CALL_MODE_VOICE,
-						CALL_MULTIPARTY_NO,
-						active_call_number,
-						NUMBER_TYPE_TELEPHONY);
-	telephony_list_current_calls_rsp(telephony_device, CME_ERROR_NONE);
-}
-
-void telephony_operator_selection_req(void *telephony_device)
-{
-	telephony_operator_selection_ind(OPERATOR_MODE_AUTO, "DummyOperator");
-	telephony_operator_selection_rsp(telephony_device, CME_ERROR_NONE);
-}
-
-void telephony_call_hold_req(void *telephony_device, const char *cmd)
-{
-	DBG("telephony-dymmy: got call hold request %s", cmd);
-	telephony_call_hold_rsp(telephony_device, CME_ERROR_NONE);
-}
-
-void telephony_nr_and_ec_req(void *telephony_device, gboolean enable)
-{
-	DBG("telephony-dummy: got %s NR and EC request",
-			enable ? "enable" : "disable");
-
-	telephony_nr_and_ec_rsp(telephony_device, CME_ERROR_NONE);
-}
-
-void telephony_voice_dial_req(void *telephony_device, gboolean enable)
-{
-	DBG("telephony-dummy: got %s voice dial request",
-			enable ? "enable" : "disable");
-
-	g_dbus_emit_signal(btd_get_dbus_connection(), TELEPHONY_DUMMY_PATH,
-			TELEPHONY_DUMMY_IFACE, "VoiceDial",
-			DBUS_TYPE_INVALID);
-
-	telephony_voice_dial_rsp(telephony_device, CME_ERROR_NONE);
-}
-
-void telephony_key_press_req(void *telephony_device, const char *keys)
-{
-	DBG("telephony-dummy: got key press request for %s", keys);
-	telephony_key_press_rsp(telephony_device, CME_ERROR_NONE);
-}
-
-/* D-Bus method handlers */
-static DBusMessage *outgoing_call(DBusConnection *conn, DBusMessage *msg,
-					void *data)
-{
-	const char *number;
-
-	if (!dbus_message_get_args(msg, NULL, DBUS_TYPE_STRING, &number,
-						DBUS_TYPE_INVALID))
-		return btd_error_invalid_args(msg);
-
-	DBG("telephony-dummy: outgoing call to %s", number);
-
-	g_free(active_call_number);
-	active_call_number = g_strdup(number);
-
-	telephony_update_indicator(dummy_indicators, "callsetup",
-					EV_CALLSETUP_OUTGOING);
-	telephony_update_indicator(dummy_indicators, "callsetup",
-					EV_CALLSETUP_ALERTING);
-
-	active_call_status = CALL_STATUS_ALERTING;
-	active_call_dir = CALL_DIR_OUTGOING;
-
-	return dbus_message_new_method_return(msg);
-}
-
-static DBusMessage *incoming_call(DBusConnection *conn, DBusMessage *msg,
-					void *data)
-{
-	const char *number;
-
-	if (!dbus_message_get_args(msg, NULL, DBUS_TYPE_STRING, &number,
-						DBUS_TYPE_INVALID))
-		return btd_error_invalid_args(msg);
-
-	DBG("telephony-dummy: incoming call to %s", number);
-
-	g_free(active_call_number);
-	active_call_number = g_strdup(number);
-
-	telephony_update_indicator(dummy_indicators, "callsetup",
-					EV_CALLSETUP_INCOMING);
-
-	active_call_status = CALL_STATUS_INCOMING;
-	active_call_dir = CALL_DIR_INCOMING;
-
-	telephony_incoming_call_ind(number, NUMBER_TYPE_TELEPHONY);
-
-	return dbus_message_new_method_return(msg);
-}
-
-static DBusMessage *cancel_call(DBusConnection *conn, DBusMessage *msg,
-					void *data)
-{
-	DBG("telephony-dummy: cancel call");
-
-	g_free(active_call_number);
-	active_call_number = NULL;
-
-	if (telephony_get_indicator(dummy_indicators, "callsetup") > 0) {
-		telephony_update_indicator(dummy_indicators, "callsetup",
-						EV_CALLSETUP_INACTIVE);
-		telephony_calling_stopped_ind();
-	}
-
-	if (telephony_get_indicator(dummy_indicators, "call") > 0)
-		telephony_update_indicator(dummy_indicators, "call",
-						EV_CALL_INACTIVE);
-
-	return dbus_message_new_method_return(msg);
-}
-
-static DBusMessage *signal_strength(DBusConnection *conn, DBusMessage *msg,
-					void *data)
-{
-	dbus_uint32_t strength;
-
-	if (!dbus_message_get_args(msg, NULL, DBUS_TYPE_UINT32, &strength,
-						DBUS_TYPE_INVALID))
-		return btd_error_invalid_args(msg);
-
-	if (strength > 5)
-		return btd_error_invalid_args(msg);
-
-	telephony_update_indicator(dummy_indicators, "signal", strength);
-
-	DBG("telephony-dummy: signal strength set to %u", strength);
-
-	return dbus_message_new_method_return(msg);
-}
-
-static DBusMessage *battery_level(DBusConnection *conn, DBusMessage *msg,
-					void *data)
-{
-	dbus_uint32_t level;
-
-	if (!dbus_message_get_args(msg, NULL, DBUS_TYPE_UINT32, &level,
-						DBUS_TYPE_INVALID))
-		return btd_error_invalid_args(msg);
-
-	if (level > 5)
-		return btd_error_invalid_args(msg);
-
-	telephony_update_indicator(dummy_indicators, "battchg", level);
-
-	DBG("telephony-dummy: battery level set to %u", level);
-
-	return dbus_message_new_method_return(msg);
-}
-
-static DBusMessage *roaming_status(DBusConnection *conn, DBusMessage *msg,
-					void *data)
-{
-	dbus_bool_t roaming;
-	int val;
-
-	if (!dbus_message_get_args(msg, NULL, DBUS_TYPE_BOOLEAN, &roaming,
-						DBUS_TYPE_INVALID))
-		return btd_error_invalid_args(msg);
-
-	val = roaming ? EV_ROAM_ACTIVE : EV_ROAM_INACTIVE;
-
-	telephony_update_indicator(dummy_indicators, "roam", val);
-
-	DBG("telephony-dummy: roaming status set to %d", val);
-
-	return dbus_message_new_method_return(msg);
-}
-
-static DBusMessage *registration_status(DBusConnection *conn, DBusMessage *msg,
-					void *data)
-{
-	dbus_bool_t registration;
-	int val;
-
-	if (!dbus_message_get_args(msg, NULL, DBUS_TYPE_BOOLEAN, &registration,
-						DBUS_TYPE_INVALID))
-		return btd_error_invalid_args(msg);
-
-	val = registration ? EV_SERVICE_PRESENT : EV_SERVICE_NONE;
-
-	telephony_update_indicator(dummy_indicators, "service", val);
-
-	DBG("telephony-dummy: registration status set to %d", val);
-
-	return dbus_message_new_method_return(msg);
-}
-
-static DBusMessage *set_subscriber_number(DBusConnection *conn,
-						DBusMessage *msg,
-						void *data)
-{
-	const char *number;
-
-	if (!dbus_message_get_args(msg, NULL, DBUS_TYPE_STRING, &number,
-						DBUS_TYPE_INVALID))
-		return btd_error_invalid_args(msg);
-
-	g_free(subscriber_number);
-	subscriber_number = g_strdup(number);
-
-	DBG("telephony-dummy: subscriber number set to %s", number);
-
-	return dbus_message_new_method_return(msg);
-}
-
-static const GDBusMethodTable dummy_methods[] = {
-	{ GDBUS_METHOD("OutgoingCall",
-			GDBUS_ARGS({ "number", "s" }), NULL,
-			outgoing_call) },
-	{ GDBUS_METHOD("IncomingCall",
-			GDBUS_ARGS({ "number", "s" }), NULL,
-			incoming_call) },
-	{ GDBUS_METHOD("CancelCall", NULL, NULL, cancel_call) },
-	{ GDBUS_METHOD("SignalStrength",
-			GDBUS_ARGS({ "strength", "u" }), NULL,
-			signal_strength) },
-	{ GDBUS_METHOD("BatteryLevel",
-			GDBUS_ARGS({ "level", "u" }), NULL,
-			battery_level) },
-	{ GDBUS_METHOD("RoamingStatus",
-			GDBUS_ARGS({ "roaming", "b" }), NULL,
-			roaming_status) },
-	{ GDBUS_METHOD("RegistrationStatus",
-			GDBUS_ARGS({ "registration", "b" }), NULL,
-			registration_status) },
-	{ GDBUS_METHOD("SetSubscriberNumber",
-			GDBUS_ARGS({ "number", "s" }), NULL,
-			set_subscriber_number) },
-	{ }
-};
-
-static const GDBusSignalTable dummy_signals[] = {
-	{ GDBUS_SIGNAL("VoiceDial", NULL) },
-	{ }
-};
-
-int telephony_init(void)
-{
-	uint32_t features = AG_FEATURE_REJECT_A_CALL |
-				AG_FEATURE_ENHANCED_CALL_STATUS |
-				AG_FEATURE_EXTENDED_ERROR_RESULT_CODES;
-
-	DBG("");
-
-	if (g_dbus_register_interface(btd_get_dbus_connection(),
-					TELEPHONY_DUMMY_PATH,
-					TELEPHONY_DUMMY_IFACE,
-					dummy_methods, dummy_signals,
-					NULL, NULL, NULL) == FALSE) {
-		error("telephony-dummy interface %s init failed on path %s",
-			TELEPHONY_DUMMY_IFACE, TELEPHONY_DUMMY_PATH);
-		return -1;
-	}
-
-	telephony_ready_ind(features, dummy_indicators, BTRH_NOT_SUPPORTED,
-								chld_str);
-
-	return 0;
-}
-
-void telephony_exit(void)
-{
-	DBG("");
-
-	g_dbus_unregister_interface(btd_get_dbus_connection(),
-					TELEPHONY_DUMMY_PATH,
-					TELEPHONY_DUMMY_IFACE);
-
-	telephony_deinit();
-}
-- 
1.7.11.7


^ permalink raw reply related

* [PATCH BlueZ 08/13] build: Remove telephony.h
From: Luiz Augusto von Dentz @ 2012-11-13 13:21 UTC (permalink / raw)
  To: linux-bluetooth
In-Reply-To: <1352812880-7306-1-git-send-email-luiz.dentz@gmail.com>

From: Luiz Augusto von Dentz <luiz.von.dentz@intel.com>

---
 Makefile.am       |   2 +-
 audio/manager.c   |   1 -
 audio/telephony.h | 244 ------------------------------------------------------
 3 files changed, 1 insertion(+), 246 deletions(-)
 delete mode 100644 audio/telephony.h

diff --git a/Makefile.am b/Makefile.am
index ad2e27a..a8660af 100644
--- a/Makefile.am
+++ b/Makefile.am
@@ -120,7 +120,7 @@ builtin_sources += audio/main.c \
 			audio/media.h audio/media.c \
 			audio/transport.h audio/transport.c \
 			audio/player.h audio/player.c \
-			audio/telephony.h audio/a2dp-codecs.h
+			audio/a2dp-codecs.h
 endif
 
 if SAPPLUGIN
diff --git a/audio/manager.c b/audio/manager.c
index d151f16..0960d28 100644
--- a/audio/manager.c
+++ b/audio/manager.c
@@ -68,7 +68,6 @@
 #include "control.h"
 #include "manager.h"
 #include "sdpd.h"
-#include "telephony.h"
 
 struct audio_adapter {
 	struct btd_adapter *btd_adapter;
diff --git a/audio/telephony.h b/audio/telephony.h
deleted file mode 100644
index 73b390c..0000000
--- a/audio/telephony.h
+++ /dev/null
@@ -1,244 +0,0 @@
-/*
- *
- *  BlueZ - Bluetooth protocol stack for Linux
- *
- *  Copyright (C) 2006-2010  Nokia Corporation
- *  Copyright (C) 2004-2010  Marcel Holtmann <marcel@holtmann.org>
- *
- *
- *  This program is free software; you can redistribute it and/or modify
- *  it under the terms of the GNU General Public License as published by
- *  the Free Software Foundation; either version 2 of the License, or
- *  (at your option) any later version.
- *
- *  This program is distributed in the hope that it will be useful,
- *  but WITHOUT ANY WARRANTY; without even the implied warranty of
- *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
- *  GNU General Public License for more details.
- *
- *  You should have received a copy of the GNU General Public License
- *  along with this program; if not, write to the Free Software
- *  Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
- *
- */
-
-#include <stdint.h>
-#include <errno.h>
-#include <glib.h>
-
-/* Response and hold values */
-#define BTRH_NOT_SUPPORTED	-2
-#define BTRH_NONE		-1
-#define BTRH_HOLD		0
-#define BTRH_ACCEPT		1
-#define BTRH_REJECT		2
-
-/* HFP feature bits */
-#define AG_FEATURE_THREE_WAY_CALLING		0x0001
-#define AG_FEATURE_EC_ANDOR_NR			0x0002
-#define AG_FEATURE_VOICE_RECOGNITION		0x0004
-#define AG_FEATURE_INBAND_RINGTONE		0x0008
-#define AG_FEATURE_ATTACH_NUMBER_TO_VOICETAG	0x0010
-#define AG_FEATURE_REJECT_A_CALL		0x0020
-#define AG_FEATURE_ENHANCED_CALL_STATUS		0x0040
-#define AG_FEATURE_ENHANCED_CALL_CONTROL	0x0080
-#define AG_FEATURE_EXTENDED_ERROR_RESULT_CODES	0x0100
-
-#define HF_FEATURE_EC_ANDOR_NR			0x0001
-#define HF_FEATURE_CALL_WAITING_AND_3WAY	0x0002
-#define HF_FEATURE_CLI_PRESENTATION		0x0004
-#define HF_FEATURE_VOICE_RECOGNITION		0x0008
-#define HF_FEATURE_REMOTE_VOLUME_CONTROL	0x0010
-#define HF_FEATURE_ENHANCED_CALL_STATUS		0x0020
-#define HF_FEATURE_ENHANCED_CALL_CONTROL	0x0040
-
-/* Indicator event values */
-#define EV_SERVICE_NONE			0
-#define EV_SERVICE_PRESENT		1
-
-#define EV_CALL_INACTIVE		0
-#define EV_CALL_ACTIVE			1
-
-#define EV_CALLSETUP_INACTIVE		0
-#define EV_CALLSETUP_INCOMING		1
-#define EV_CALLSETUP_OUTGOING		2
-#define EV_CALLSETUP_ALERTING		3
-
-#define EV_CALLHELD_NONE		0
-#define EV_CALLHELD_MULTIPLE		1
-#define EV_CALLHELD_ON_HOLD		2
-
-#define EV_ROAM_INACTIVE		0
-#define EV_ROAM_ACTIVE			1
-
-/* Call parameters */
-#define CALL_DIR_OUTGOING		0
-#define CALL_DIR_INCOMING		1
-
-#define CALL_STATUS_ACTIVE		0
-#define CALL_STATUS_HELD		1
-#define CALL_STATUS_DIALING		2
-#define CALL_STATUS_ALERTING		3
-#define CALL_STATUS_INCOMING		4
-#define CALL_STATUS_WAITING		5
-
-#define CALL_MODE_VOICE			0
-#define CALL_MODE_DATA			1
-#define CALL_MODE_FAX			2
-
-#define CALL_MULTIPARTY_NO		0
-#define CALL_MULTIPARTY_YES		1
-
-/* Subscriber number parameters */
-#define SUBSCRIBER_SERVICE_VOICE	4
-#define SUBSCRIBER_SERVICE_FAX		5
-
-/* Operator selection mode values */
-#define OPERATOR_MODE_AUTO		0
-#define OPERATOR_MODE_MANUAL		1
-#define OPERATOR_MODE_DEREGISTER	2
-#define OPERATOR_MODE_MANUAL_AUTO	4
-
-/* Some common number types */
-#define NUMBER_TYPE_UNKNOWN		128
-#define NUMBER_TYPE_TELEPHONY		129
-#define NUMBER_TYPE_INTERNATIONAL	145
-#define NUMBER_TYPE_NATIONAL		161
-#define NUMBER_TYPE_VOIP		255
-
-/* Extended Audio Gateway Error Result Codes */
-typedef enum {
-	CME_ERROR_NONE			= -1,
-	CME_ERROR_AG_FAILURE		= 0,
-	CME_ERROR_NO_PHONE_CONNECTION	= 1,
-	CME_ERROR_NOT_ALLOWED		= 3,
-	CME_ERROR_NOT_SUPPORTED		= 4,
-	CME_ERROR_PH_SIM_PIN_REQUIRED	= 5,
-	CME_ERROR_SIM_NOT_INSERTED	= 10,
-	CME_ERROR_SIM_PIN_REQUIRED	= 11,
-	CME_ERROR_SIM_PUK_REQUIRED	= 12,
-	CME_ERROR_SIM_FAILURE		= 13,
-	CME_ERROR_SIM_BUSY		= 14,
-	CME_ERROR_INCORRECT_PASSWORD	= 16,
-	CME_ERROR_SIM_PIN2_REQUIRED	= 17,
-	CME_ERROR_SIM_PUK2_REQUIRED	= 18,
-	CME_ERROR_MEMORY_FULL		= 20,
-	CME_ERROR_INVALID_INDEX		= 21,
-	CME_ERROR_MEMORY_FAILURE	= 23,
-	CME_ERROR_TEXT_STRING_TOO_LONG	= 24,
-	CME_ERROR_INVALID_TEXT_STRING	= 25,
-	CME_ERROR_DIAL_STRING_TOO_LONG	= 26,
-	CME_ERROR_INVALID_DIAL_STRING	= 27,
-	CME_ERROR_NO_NETWORK_SERVICE	= 30,
-	CME_ERROR_NETWORK_TIMEOUT	= 31,
-	CME_ERROR_NETWORK_NOT_ALLOWED	= 32,
-} cme_error_t;
-
-struct indicator {
-	const char *desc;
-	const char *range;
-	int val;
-	gboolean ignore_redundant;
-};
-
-/* Notify telephony-*.c of connected/disconnected devices. Implemented by
- * telephony-*.c
- */
-void telephony_device_connected(void *telephony_device);
-void telephony_device_disconnected(void *telephony_device);
-
-/* HF requests (sent by the handsfree device). These are implemented by
- * telephony-*.c
- */
-void telephony_event_reporting_req(void *telephony_device, int ind);
-void telephony_response_and_hold_req(void *telephony_device, int rh);
-void telephony_last_dialed_number_req(void *telephony_device);
-void telephony_terminate_call_req(void *telephony_device);
-void telephony_answer_call_req(void *telephony_device);
-void telephony_dial_number_req(void *telephony_device, const char *number);
-void telephony_transmit_dtmf_req(void *telephony_device, char tone);
-void telephony_subscriber_number_req(void *telephony_device);
-void telephony_list_current_calls_req(void *telephony_device);
-void telephony_operator_selection_req(void *telephony_device);
-void telephony_call_hold_req(void *telephony_device, const char *cmd);
-void telephony_nr_and_ec_req(void *telephony_device, gboolean enable);
-void telephony_voice_dial_req(void *telephony_device, gboolean enable);
-void telephony_key_press_req(void *telephony_device, const char *keys);
-
-/* AG responses to HF requests. These are implemented by headset.c */
-int telephony_event_reporting_rsp(void *telephony_device, cme_error_t err);
-int telephony_response_and_hold_rsp(void *telephony_device, cme_error_t err);
-int telephony_last_dialed_number_rsp(void *telephony_device, cme_error_t err);
-int telephony_terminate_call_rsp(void *telephony_device, cme_error_t err);
-int telephony_answer_call_rsp(void *telephony_device, cme_error_t err);
-int telephony_dial_number_rsp(void *telephony_device, cme_error_t err);
-int telephony_transmit_dtmf_rsp(void *telephony_device, cme_error_t err);
-int telephony_subscriber_number_rsp(void *telephony_device, cme_error_t err);
-int telephony_list_current_calls_rsp(void *telephony_device, cme_error_t err);
-int telephony_operator_selection_rsp(void *telephony_device, cme_error_t err);
-int telephony_call_hold_rsp(void *telephony_device, cme_error_t err);
-int telephony_nr_and_ec_rsp(void *telephony_device, cme_error_t err);
-int telephony_voice_dial_rsp(void *telephony_device, cme_error_t err);
-int telephony_key_press_rsp(void *telephony_device, cme_error_t err);
-
-/* Event indications by AG. These are implemented by headset.c */
-int telephony_event_ind(int index);
-int telephony_response_and_hold_ind(int rh);
-int telephony_incoming_call_ind(const char *number, int type);
-int telephony_calling_stopped_ind(void);
-int telephony_ready_ind(uint32_t features, const struct indicator *indicators,
-			int rh, const char *chld);
-int telephony_deinit(void);
-int telephony_list_current_call_ind(int idx, int dir, int status, int mode,
-					int mprty, const char *number,
-					int type);
-int telephony_subscriber_number_ind(const char *number, int type,
-					int service);
-int telephony_call_waiting_ind(const char *number, int type);
-int telephony_operator_selection_ind(int mode, const char *oper);
-
-/* Helper function for quick indicator updates */
-static inline int telephony_update_indicator(struct indicator *indicators,
-						const char *desc,
-						int new_val)
-{
-	int i;
-	struct indicator *ind = NULL;
-
-	for (i = 0; indicators[i].desc != NULL; i++) {
-		if (g_str_equal(indicators[i].desc, desc)) {
-			ind = &indicators[i];
-			break;
-		}
-	}
-
-	if (!ind)
-		return -ENOENT;
-
-	DBG("Telephony indicator \"%s\" %d->%d", desc, ind->val, new_val);
-
-	if (ind->ignore_redundant && ind->val == new_val) {
-		DBG("Ignoring no-change indication");
-		return 0;
-	}
-
-	ind->val = new_val;
-
-	return telephony_event_ind(i);
-}
-
-static inline int telephony_get_indicator(const struct indicator *indicators,
-						const char *desc)
-{
-	int i;
-
-	for (i = 0; indicators[i].desc != NULL; i++) {
-		if (g_str_equal(indicators[i].desc, desc))
-			return indicators[i].val;
-	}
-
-	return -ENOENT;
-}
-
-int telephony_init(void);
-void telephony_exit(void);
-- 
1.7.11.7


^ permalink raw reply related

* [PATCH BlueZ 09/13] build: Remove headset.c and headset.h
From: Luiz Augusto von Dentz @ 2012-11-13 13:21 UTC (permalink / raw)
  To: linux-bluetooth
In-Reply-To: <1352812880-7306-1-git-send-email-luiz.dentz@gmail.com>

From: Luiz Augusto von Dentz <luiz.von.dentz@intel.com>

---
 Makefile.am     |    1 -
 audio/device.h  |    1 -
 audio/headset.c | 2822 -------------------------------------------------------
 audio/headset.h |  112 ---
 4 files changed, 2936 deletions(-)
 delete mode 100644 audio/headset.c
 delete mode 100644 audio/headset.h

diff --git a/Makefile.am b/Makefile.am
index a8660af..7f8ff26 100644
--- a/Makefile.am
+++ b/Makefile.am
@@ -108,7 +108,6 @@ builtin_modules += audio
 builtin_sources += audio/main.c \
 			audio/manager.h audio/manager.c \
 			audio/gateway.h audio/gateway.c \
-			audio/headset.h audio/headset.c \
 			audio/control.h audio/control.c \
 			audio/avctp.h audio/avctp.c \
 			audio/avrcp.h audio/avrcp.c \
diff --git a/audio/device.h b/audio/device.h
index 1e2cac1..89916be 100644
--- a/audio/device.h
+++ b/audio/device.h
@@ -38,7 +38,6 @@ struct audio_device {
 
 	gboolean auto_connect;
 
-	struct headset *headset;
 	struct gateway *gateway;
 	struct sink *sink;
 	struct source *source;
diff --git a/audio/headset.c b/audio/headset.c
deleted file mode 100644
index fb660f5..0000000
--- a/audio/headset.c
+++ /dev/null
@@ -1,2822 +0,0 @@
-/*
- *
- *  BlueZ - Bluetooth protocol stack for Linux
- *
- *  Copyright (C) 2006-2010  Nokia Corporation
- *  Copyright (C) 2004-2010  Marcel Holtmann <marcel@holtmann.org>
- *
- *
- *  This program is free software; you can redistribute it and/or modify
- *  it under the terms of the GNU General Public License as published by
- *  the Free Software Foundation; either version 2 of the License, or
- *  (at your option) any later version.
- *
- *  This program is distributed in the hope that it will be useful,
- *  but WITHOUT ANY WARRANTY; without even the implied warranty of
- *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
- *  GNU General Public License for more details.
- *
- *  You should have received a copy of the GNU General Public License
- *  along with this program; if not, write to the Free Software
- *  Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
- *
- */
-
-#ifdef HAVE_CONFIG_H
-#include <config.h>
-#endif
-
-#include <stdio.h>
-#include <errno.h>
-#include <fcntl.h>
-#include <unistd.h>
-#include <stdlib.h>
-#include <stdarg.h>
-#include <stdbool.h>
-#include <signal.h>
-#include <string.h>
-#include <getopt.h>
-#include <sys/ioctl.h>
-#include <sys/socket.h>
-#include <assert.h>
-
-#include <bluetooth/bluetooth.h>
-#include <bluetooth/sdp.h>
-#include <bluetooth/sdp_lib.h>
-#include <bluetooth/uuid.h>
-
-#include <glib.h>
-#include <dbus/dbus.h>
-#include <gdbus.h>
-
-#include "log.h"
-#include "device.h"
-#include "manager.h"
-#include "error.h"
-#include "telephony.h"
-#include "headset.h"
-#include "sdp-client.h"
-#include "btio.h"
-#include "dbus-common.h"
-#include "../src/adapter.h"
-#include "../src/device.h"
-
-#define DC_TIMEOUT 3
-
-#define RING_INTERVAL 3
-
-#define BUF_SIZE 1024
-
-#define HEADSET_GAIN_SPEAKER 'S'
-#define HEADSET_GAIN_MICROPHONE 'M'
-
-static struct {
-	gboolean telephony_ready;	/* Telephony plugin initialized */
-	uint32_t features;		/* HFP AG features */
-	const struct indicator *indicators;	/* Available HFP indicators */
-	int er_mode;			/* Event reporting mode */
-	int er_ind;			/* Event reporting for indicators */
-	int rh;				/* Response and Hold state */
-	char *number;			/* Incoming phone number */
-	int number_type;		/* Incoming number type */
-	guint ring_timer;		/* For incoming call indication */
-	const char *chld;		/* Response to AT+CHLD=? */
-} ag = {
-	.telephony_ready = FALSE,
-	.features = 0,
-	.er_mode = 3,
-	.er_ind = 0,
-	.rh = BTRH_NOT_SUPPORTED,
-	.number = NULL,
-	.number_type = 0,
-	.ring_timer = 0,
-};
-
-static gboolean sco_hci = TRUE;
-static gboolean fast_connectable = FALSE;
-
-static GSList *active_devices = NULL;
-
-static char *str_state[] = {
-	"HEADSET_STATE_DISCONNECTED",
-	"HEADSET_STATE_CONNECTING",
-	"HEADSET_STATE_CONNECTED",
-	"HEADSET_STATE_PLAY_IN_PROGRESS",
-	"HEADSET_STATE_PLAYING",
-};
-
-struct headset_state_callback {
-	headset_state_cb cb;
-	void *user_data;
-	unsigned int id;
-};
-
-struct headset_nrec_callback {
-	unsigned int id;
-	headset_nrec_cb cb;
-	void *user_data;
-};
-
-struct connect_cb {
-	unsigned int id;
-	headset_stream_cb_t cb;
-	void *cb_data;
-};
-
-struct pending_connect {
-	DBusMessage *msg;
-	DBusPendingCall *call;
-	GIOChannel *io;
-	int err;
-	headset_state_t target_state;
-	GSList *callbacks;
-	uint16_t svclass;
-};
-
-struct headset_slc {
-	char buf[BUF_SIZE];
-	int data_start;
-	int data_length;
-
-	gboolean cli_active;
-	gboolean cme_enabled;
-	gboolean cwa_enabled;
-	gboolean pending_ring;
-	gboolean inband_ring;
-	gboolean nrec;
-	gboolean nrec_req;
-
-	int sp_gain;
-	int mic_gain;
-
-	unsigned int hf_features;
-};
-
-struct headset {
-	uint32_t hsp_handle;
-	uint32_t hfp_handle;
-
-	int rfcomm_ch;
-
-	GIOChannel *rfcomm;
-	GIOChannel *tmp_rfcomm;
-	GIOChannel *sco;
-	guint sco_id;
-
-	gboolean auto_dc;
-
-	guint dc_timer;
-
-	gboolean hfp_active;
-	gboolean search_hfp;
-	gboolean rfcomm_initiator;
-
-	headset_state_t state;
-	struct pending_connect *pending;
-
-	headset_lock_t lock;
-	struct headset_slc *slc;
-	GSList *nrec_cbs;
-};
-
-struct event {
-	const char *cmd;
-	int (*callback) (struct audio_device *device, const char *buf);
-};
-
-static GSList *headset_callbacks = NULL;
-
-static void error_connect_failed(DBusMessage *msg, int err)
-{
-	DBusMessage *reply = btd_error_failed(msg,
-			err < 0 ? strerror(-err) : "Connect failed");
-	g_dbus_send_message(btd_get_dbus_connection(), reply);
-}
-
-static int rfcomm_connect(struct audio_device *device, headset_stream_cb_t cb,
-				void *user_data, unsigned int *cb_id);
-static int get_records(struct audio_device *device, headset_stream_cb_t cb,
-			void *user_data, unsigned int *cb_id);
-
-static void print_ag_features(uint32_t features)
-{
-	GString *gstr;
-	char *str;
-
-	if (features == 0) {
-		DBG("HFP AG features: (none)");
-		return;
-	}
-
-	gstr = g_string_new("HFP AG features: ");
-
-	if (features & AG_FEATURE_THREE_WAY_CALLING)
-		g_string_append(gstr, "\"Three-way calling\" ");
-	if (features & AG_FEATURE_EC_ANDOR_NR)
-		g_string_append(gstr, "\"EC and/or NR function\" ");
-	if (features & AG_FEATURE_VOICE_RECOGNITION)
-		g_string_append(gstr, "\"Voice recognition function\" ");
-	if (features & AG_FEATURE_INBAND_RINGTONE)
-		g_string_append(gstr, "\"In-band ring tone capability\" ");
-	if (features & AG_FEATURE_ATTACH_NUMBER_TO_VOICETAG)
-		g_string_append(gstr, "\"Attach a number to a voice tag\" ");
-	if (features & AG_FEATURE_REJECT_A_CALL)
-		g_string_append(gstr, "\"Ability to reject a call\" ");
-	if (features & AG_FEATURE_ENHANCED_CALL_STATUS)
-		g_string_append(gstr, "\"Enhanced call status\" ");
-	if (features & AG_FEATURE_ENHANCED_CALL_CONTROL)
-		g_string_append(gstr, "\"Enhanced call control\" ");
-	if (features & AG_FEATURE_EXTENDED_ERROR_RESULT_CODES)
-		g_string_append(gstr, "\"Extended Error Result Codes\" ");
-
-	str = g_string_free(gstr, FALSE);
-
-	DBG("%s", str);
-
-	g_free(str);
-}
-
-static void print_hf_features(uint32_t features)
-{
-	GString *gstr;
-	char *str;
-
-	if (features == 0) {
-		DBG("HFP HF features: (none)");
-		return;
-	}
-
-	gstr = g_string_new("HFP HF features: ");
-
-	if (features & HF_FEATURE_EC_ANDOR_NR)
-		g_string_append(gstr, "\"EC and/or NR function\" ");
-	if (features & HF_FEATURE_CALL_WAITING_AND_3WAY)
-		g_string_append(gstr, "\"Call waiting and 3-way calling\" ");
-	if (features & HF_FEATURE_CLI_PRESENTATION)
-		g_string_append(gstr, "\"CLI presentation capability\" ");
-	if (features & HF_FEATURE_VOICE_RECOGNITION)
-		g_string_append(gstr, "\"Voice recognition activation\" ");
-	if (features & HF_FEATURE_REMOTE_VOLUME_CONTROL)
-		g_string_append(gstr, "\"Remote volume control\" ");
-	if (features & HF_FEATURE_ENHANCED_CALL_STATUS)
-		g_string_append(gstr, "\"Enhanced call status\" ");
-	if (features & HF_FEATURE_ENHANCED_CALL_CONTROL)
-		g_string_append(gstr, "\"Enhanced call control\" ");
-
-	str = g_string_free(gstr, FALSE);
-
-	DBG("%s", str);
-
-	g_free(str);
-}
-
-static const char *state2str(headset_state_t state)
-{
-	switch (state) {
-	case HEADSET_STATE_DISCONNECTED:
-		return "disconnected";
-	case HEADSET_STATE_CONNECTING:
-		return "connecting";
-	case HEADSET_STATE_CONNECTED:
-	case HEADSET_STATE_PLAY_IN_PROGRESS:
-		return "connected";
-	case HEADSET_STATE_PLAYING:
-		return "playing";
-	}
-
-	return NULL;
-}
-
-static int headset_send_valist(struct headset *hs, char *format, va_list ap)
-{
-	char rsp[BUF_SIZE];
-	ssize_t total_written, count;
-	int fd;
-
-	count = vsnprintf(rsp, sizeof(rsp), format, ap);
-
-	if (count < 0)
-		return -EINVAL;
-
-	if (!hs->rfcomm) {
-		error("headset_send: the headset is not connected");
-		return -EIO;
-	}
-
-	total_written = 0;
-	fd = g_io_channel_unix_get_fd(hs->rfcomm);
-
-	while (total_written < count) {
-		ssize_t written;
-
-		written = write(fd, rsp + total_written,
-				count - total_written);
-		if (written < 0)
-			return -errno;
-
-		total_written += written;
-	}
-
-	return 0;
-}
-
-static int __attribute__((format(printf, 2, 3)))
-			headset_send(struct headset *hs, char *format, ...)
-{
-	va_list ap;
-	int ret;
-
-	va_start(ap, format);
-	ret = headset_send_valist(hs, format, ap);
-	va_end(ap);
-
-	return ret;
-}
-
-static int supported_features(struct audio_device *device, const char *buf)
-{
-	struct headset *hs = device->headset;
-	struct headset_slc *slc = hs->slc;
-	int err;
-
-	if (strlen(buf) < 9)
-		return -EINVAL;
-
-	slc->hf_features = strtoul(&buf[8], NULL, 10);
-
-	print_hf_features(slc->hf_features);
-
-	err = headset_send(hs, "\r\n+BRSF: %u\r\n", ag.features);
-	if (err < 0)
-		return err;
-
-	return headset_send(hs, "\r\nOK\r\n");
-}
-
-static char *indicator_ranges(const struct indicator *indicators)
-{
-	int i;
-	GString *gstr;
-
-	gstr = g_string_new("\r\n+CIND: ");
-
-	for (i = 0; indicators[i].desc != NULL; i++) {
-		if (i == 0)
-			g_string_append_printf(gstr, "(\"%s\",(%s))",
-						indicators[i].desc,
-						indicators[i].range);
-		else
-			g_string_append_printf(gstr, ",(\"%s\",(%s))",
-						indicators[i].desc,
-						indicators[i].range);
-	}
-
-	g_string_append(gstr, "\r\n");
-
-	return g_string_free(gstr, FALSE);
-}
-
-static char *indicator_values(const struct indicator *indicators)
-{
-	int i;
-	GString *gstr;
-
-	gstr = g_string_new("\r\n+CIND: ");
-
-	for (i = 0; indicators[i].desc != NULL; i++) {
-		if (i == 0)
-			g_string_append_printf(gstr, "%d", indicators[i].val);
-		else
-			g_string_append_printf(gstr, ",%d", indicators[i].val);
-	}
-
-	g_string_append(gstr, "\r\n");
-
-	return g_string_free(gstr, FALSE);
-}
-
-static int report_indicators(struct audio_device *device, const char *buf)
-{
-	struct headset *hs = device->headset;
-	int err;
-	char *str;
-
-	if (strlen(buf) < 8)
-		return -EINVAL;
-
-	if (ag.indicators == NULL) {
-		error("HFP AG indicators not initialized");
-		return headset_send(hs, "\r\nERROR\r\n");
-	}
-
-	if (buf[7] == '=')
-		str = indicator_ranges(ag.indicators);
-	else
-		str = indicator_values(ag.indicators);
-
-	err = headset_send(hs, "%s", str);
-
-	g_free(str);
-
-	if (err < 0)
-		return err;
-
-	return headset_send(hs, "\r\nOK\r\n");
-}
-
-static void pending_connect_complete(struct connect_cb *cb, struct audio_device *dev)
-{
-	struct headset *hs = dev->headset;
-
-	if (hs->pending->err < 0)
-		cb->cb(NULL, cb->cb_data);
-	else
-		cb->cb(dev, cb->cb_data);
-}
-
-static void pending_connect_finalize(struct audio_device *dev)
-{
-	struct headset *hs = dev->headset;
-	struct pending_connect *p = hs->pending;
-
-	if (p == NULL)
-		return;
-
-	if (p->svclass)
-		bt_cancel_discovery(&dev->src, &dev->dst);
-
-	g_slist_foreach(p->callbacks, (GFunc) pending_connect_complete, dev);
-
-	g_slist_free_full(p->callbacks, g_free);
-
-	if (p->io) {
-		g_io_channel_shutdown(p->io, TRUE, NULL);
-		g_io_channel_unref(p->io);
-	}
-
-	if (p->msg)
-		dbus_message_unref(p->msg);
-
-	if (p->call) {
-		dbus_pending_call_cancel(p->call);
-		dbus_pending_call_unref(p->call);
-	}
-
-	g_free(p);
-
-	hs->pending = NULL;
-}
-
-static void pending_connect_init(struct headset *hs, headset_state_t target_state)
-{
-	if (hs->pending) {
-		if (hs->pending->target_state < target_state)
-			hs->pending->target_state = target_state;
-		return;
-	}
-
-	hs->pending = g_new0(struct pending_connect, 1);
-	hs->pending->target_state = target_state;
-}
-
-static unsigned int connect_cb_new(struct headset *hs,
-					headset_state_t target_state,
-					headset_stream_cb_t func,
-					void *user_data)
-{
-	struct connect_cb *cb;
-	static unsigned int free_cb_id = 1;
-
-	pending_connect_init(hs, target_state);
-
-	if (!func)
-		return 0;
-
-	cb = g_new(struct connect_cb, 1);
-
-	cb->cb = func;
-	cb->cb_data = user_data;
-	cb->id = free_cb_id++;
-
-	hs->pending->callbacks = g_slist_append(hs->pending->callbacks,
-						cb);
-
-	return cb->id;
-}
-
-static void __attribute__((format(printf, 3, 4)))
-		send_foreach_headset(GSList *devices,
-					int (*cmp) (struct headset *hs),
-					char *format, ...)
-{
-	GSList *l;
-	va_list ap;
-
-	for (l = devices; l != NULL; l = l->next) {
-		struct audio_device *device = l->data;
-		struct headset *hs = device->headset;
-		int ret;
-
-		assert(hs != NULL);
-
-		if (cmp && cmp(hs) != 0)
-			continue;
-
-		va_start(ap, format);
-		ret = headset_send_valist(hs, format, ap);
-		if (ret < 0)
-			error("Failed to send to headset: %s (%d)",
-					strerror(-ret), -ret);
-		va_end(ap);
-	}
-}
-
-static int cli_cmp(struct headset *hs)
-{
-	struct headset_slc *slc = hs->slc;
-
-	if (!hs->hfp_active)
-		return -1;
-
-	if (slc->cli_active)
-		return 0;
-	else
-		return -1;
-}
-
-static gboolean ring_timer_cb(gpointer data)
-{
-	send_foreach_headset(active_devices, NULL, "\r\nRING\r\n");
-
-	if (ag.number)
-		send_foreach_headset(active_devices, cli_cmp,
-					"\r\n+CLIP: \"%s\",%d\r\n",
-					ag.number, ag.number_type);
-
-	return TRUE;
-}
-
-static void sco_connect_cb(GIOChannel *chan, GError *err, gpointer user_data)
-{
-	int sk;
-	struct audio_device *dev = user_data;
-	struct headset *hs = dev->headset;
-	struct headset_slc *slc = hs->slc;
-	struct pending_connect *p = hs->pending;
-
-	if (err) {
-		error("%s", err->message);
-
-		if (p != NULL) {
-			p->err = -errno;
-			if (p->msg)
-				error_connect_failed(p->msg, p->err);
-			pending_connect_finalize(dev);
-		}
-
-		if (hs->rfcomm)
-			headset_set_state(dev, HEADSET_STATE_CONNECTED);
-		else
-			headset_set_state(dev, HEADSET_STATE_DISCONNECTED);
-
-		return;
-	}
-
-	DBG("SCO socket opened for headset %s", device_get_path(dev->btd_dev));
-
-	sk = g_io_channel_unix_get_fd(chan);
-
-	DBG("SCO fd=%d", sk);
-
-	if (p) {
-		p->io = NULL;
-		if (p->msg) {
-			DBusMessage *reply;
-			reply = dbus_message_new_method_return(p->msg);
-			g_dbus_send_message(btd_get_dbus_connection(), reply);
-		}
-
-		pending_connect_finalize(dev);
-	}
-
-	fcntl(sk, F_SETFL, 0);
-
-	headset_set_state(dev, HEADSET_STATE_PLAYING);
-
-	if (slc->pending_ring) {
-		ring_timer_cb(NULL);
-		ag.ring_timer = g_timeout_add_seconds(RING_INTERVAL,
-						ring_timer_cb,
-						NULL);
-		slc->pending_ring = FALSE;
-	}
-}
-
-static int sco_connect(struct audio_device *dev, headset_stream_cb_t cb,
-			void *user_data, unsigned int *cb_id)
-{
-	struct headset *hs = dev->headset;
-	GError *err = NULL;
-	GIOChannel *io;
-
-	if (hs->state != HEADSET_STATE_CONNECTED)
-		return -EINVAL;
-
-	io = bt_io_connect(sco_connect_cb, dev, NULL, &err,
-				BT_IO_OPT_SOURCE_BDADDR, &dev->src,
-				BT_IO_OPT_DEST_BDADDR, &dev->dst,
-				BT_IO_OPT_INVALID);
-	if (!io) {
-		error("%s", err->message);
-		g_error_free(err);
-		return -EIO;
-	}
-
-	hs->sco = io;
-
-	headset_set_state(dev, HEADSET_STATE_PLAY_IN_PROGRESS);
-
-	pending_connect_init(hs, HEADSET_STATE_PLAYING);
-
-	if (cb) {
-		unsigned int id = connect_cb_new(hs, HEADSET_STATE_PLAYING,
-							cb, user_data);
-		if (cb_id)
-			*cb_id = id;
-	}
-
-	return 0;
-}
-
-static int hfp_cmp(struct headset *hs)
-{
-	if (hs->hfp_active)
-		return 0;
-	else
-		return -1;
-}
-
-static void hfp_slc_complete(struct audio_device *dev)
-{
-	struct headset *hs = dev->headset;
-	struct pending_connect *p = hs->pending;
-
-	DBG("HFP Service Level Connection established");
-
-	headset_set_state(dev, HEADSET_STATE_CONNECTED);
-
-	if (p == NULL)
-		return;
-
-	if (p->target_state == HEADSET_STATE_CONNECTED) {
-		if (p->msg) {
-			DBusMessage *reply = dbus_message_new_method_return(p->msg);
-			g_dbus_send_message(btd_get_dbus_connection(), reply);
-		}
-		pending_connect_finalize(dev);
-		return;
-	}
-
-	p->err = sco_connect(dev, NULL, NULL, NULL);
-	if (p->err < 0) {
-		if (p->msg)
-			error_connect_failed(p->msg, p->err);
-		pending_connect_finalize(dev);
-	}
-}
-
-static int telephony_generic_rsp(struct audio_device *device, cme_error_t err)
-{
-	struct headset *hs = device->headset;
-	struct headset_slc *slc = hs->slc;
-
-	if ((err != CME_ERROR_NONE) && slc->cme_enabled)
-		return headset_send(hs, "\r\n+CME ERROR: %d\r\n", err);
-
-	switch (err) {
-	case CME_ERROR_NONE:
-		return headset_send(hs, "\r\nOK\r\n");
-	case CME_ERROR_NO_NETWORK_SERVICE:
-		return headset_send(hs, "\r\nNO CARRIER\r\n");
-	default:
-		return headset_send(hs, "\r\nERROR\r\n");
-	}
-}
-
-int telephony_event_reporting_rsp(void *telephony_device, cme_error_t err)
-{
-	struct audio_device *device = telephony_device;
-	struct headset *hs = device->headset;
-	struct headset_slc *slc = hs->slc;
-	int ret;
-
-	if (err != CME_ERROR_NONE)
-		return telephony_generic_rsp(telephony_device, err);
-
-	ret = headset_send(hs, "\r\nOK\r\n");
-	if (ret < 0)
-		return ret;
-
-	if (hs->state != HEADSET_STATE_CONNECTING)
-		return 0;
-
-	if (slc->hf_features & HF_FEATURE_CALL_WAITING_AND_3WAY &&
-			ag.features & AG_FEATURE_THREE_WAY_CALLING)
-		return 0;
-
-	hfp_slc_complete(device);
-
-	return 0;
-}
-
-static int event_reporting(struct audio_device *dev, const char *buf)
-{
-	char **tokens; /* <mode>, <keyp>, <disp>, <ind>, <bfr> */
-
-	if (strlen(buf) < 13)
-		return -EINVAL;
-
-	tokens = g_strsplit(&buf[8], ",", 5);
-	if (g_strv_length(tokens) < 4) {
-		g_strfreev(tokens);
-		return -EINVAL;
-	}
-
-	ag.er_mode = atoi(tokens[0]);
-	ag.er_ind = atoi(tokens[3]);
-
-	g_strfreev(tokens);
-	tokens = NULL;
-
-	DBG("Event reporting (CMER): mode=%d, ind=%d",
-			ag.er_mode, ag.er_ind);
-
-	switch (ag.er_ind) {
-	case 0:
-	case 1:
-		telephony_event_reporting_req(dev, ag.er_ind);
-		break;
-	default:
-		return -EINVAL;
-	}
-
-	return 0;
-}
-
-static int call_hold(struct audio_device *dev, const char *buf)
-{
-	struct headset *hs = dev->headset;
-	int err;
-
-	if (strlen(buf) < 9)
-		return -EINVAL;
-
-	if (buf[8] != '?') {
-		telephony_call_hold_req(dev, &buf[8]);
-		return 0;
-	}
-
-	err = headset_send(hs, "\r\n+CHLD: (%s)\r\n", ag.chld);
-	if (err < 0)
-		return err;
-
-	err = headset_send(hs, "\r\nOK\r\n");
-	if (err < 0)
-		return err;
-
-	if (hs->state != HEADSET_STATE_CONNECTING)
-		return 0;
-
-	hfp_slc_complete(dev);
-
-	return 0;
-}
-
-int telephony_key_press_rsp(void *telephony_device, cme_error_t err)
-{
-	return telephony_generic_rsp(telephony_device, err);
-}
-
-static int key_press(struct audio_device *device, const char *buf)
-{
-	if (strlen(buf) < 9)
-		return -EINVAL;
-
-	g_dbus_emit_signal(btd_get_dbus_connection(),
-			device_get_path(device->btd_dev),
-			AUDIO_HEADSET_INTERFACE, "AnswerRequested",
-			DBUS_TYPE_INVALID);
-
-	if (ag.ring_timer) {
-		g_source_remove(ag.ring_timer);
-		ag.ring_timer = 0;
-	}
-
-	telephony_key_press_req(device, &buf[8]);
-
-	return 0;
-}
-
-int telephony_answer_call_rsp(void *telephony_device, cme_error_t err)
-{
-	return telephony_generic_rsp(telephony_device, err);
-}
-
-static int answer_call(struct audio_device *device, const char *buf)
-{
-	if (ag.ring_timer) {
-		g_source_remove(ag.ring_timer);
-		ag.ring_timer = 0;
-	}
-
-	if (ag.number) {
-		g_free(ag.number);
-		ag.number = NULL;
-	}
-
-	telephony_answer_call_req(device);
-
-	return 0;
-}
-
-int telephony_terminate_call_rsp(void *telephony_device,
-					cme_error_t err)
-{
-	struct audio_device *device = telephony_device;
-	struct headset *hs = device->headset;
-
-	if (err != CME_ERROR_NONE)
-		return telephony_generic_rsp(telephony_device, err);
-
-	g_dbus_emit_signal(btd_get_dbus_connection(),
-			device_get_path(device->btd_dev),
-			AUDIO_HEADSET_INTERFACE, "CallTerminated",
-			DBUS_TYPE_INVALID);
-
-	return headset_send(hs, "\r\nOK\r\n");
-}
-
-static int terminate_call(struct audio_device *device, const char *buf)
-{
-	if (ag.number) {
-		g_free(ag.number);
-		ag.number = NULL;
-	}
-
-	if (ag.ring_timer) {
-		g_source_remove(ag.ring_timer);
-		ag.ring_timer = 0;
-	}
-
-	telephony_terminate_call_req(device);
-
-	return 0;
-}
-
-static int cli_notification(struct audio_device *device, const char *buf)
-{
-	struct headset *hs = device->headset;
-	struct headset_slc *slc = hs->slc;
-
-	if (strlen(buf) < 9)
-		return -EINVAL;
-
-	slc->cli_active = buf[8] == '1' ? TRUE : FALSE;
-
-	return headset_send(hs, "\r\nOK\r\n");
-}
-
-int telephony_response_and_hold_rsp(void *telephony_device, cme_error_t err)
-{
-	return telephony_generic_rsp(telephony_device, err);
-}
-
-static int response_and_hold(struct audio_device *device, const char *buf)
-{
-	struct headset *hs = device->headset;
-
-	if (strlen(buf) < 8)
-		return -EINVAL;
-
-	if (ag.rh == BTRH_NOT_SUPPORTED)
-		return telephony_generic_rsp(device, CME_ERROR_NOT_SUPPORTED);
-
-	if (buf[7] == '=') {
-		telephony_response_and_hold_req(device, atoi(&buf[8]) < 0);
-		return 0;
-	}
-
-	if (ag.rh >= 0)
-		headset_send(hs, "\r\n+BTRH: %d\r\n", ag.rh);
-
-	return headset_send(hs, "\r\nOK\r\n");
-}
-
-int telephony_last_dialed_number_rsp(void *telephony_device, cme_error_t err)
-{
-	return telephony_generic_rsp(telephony_device, err);
-}
-
-static int last_dialed_number(struct audio_device *device, const char *buf)
-{
-	telephony_last_dialed_number_req(device);
-
-	return 0;
-}
-
-int telephony_dial_number_rsp(void *telephony_device, cme_error_t err)
-{
-	return telephony_generic_rsp(telephony_device, err);
-}
-
-static int dial_number(struct audio_device *device, const char *buf)
-{
-	char number[BUF_SIZE];
-	size_t buf_len;
-
-	buf_len = strlen(buf);
-
-	if (buf[buf_len - 1] != ';') {
-		DBG("Rejecting non-voice call dial request");
-		return -EINVAL;
-	}
-
-	memset(number, 0, sizeof(number));
-	strncpy(number, &buf[3], buf_len - 4);
-
-	telephony_dial_number_req(device, number);
-
-	return 0;
-}
-
-static int headset_set_gain(struct audio_device *device, uint16_t gain, char type)
-{
-	struct headset *hs = device->headset;
-	struct headset_slc *slc = hs->slc;
-	const char *name, *property;
-
-	if (gain > 15) {
-		error("Invalid gain value: %u", gain);
-		return -EINVAL;
-	}
-
-	switch (type) {
-	case HEADSET_GAIN_SPEAKER:
-		if (slc->sp_gain == gain) {
-			DBG("Ignoring no-change in speaker gain");
-			return -EALREADY;
-		}
-		name = "SpeakerGainChanged";
-		property = "SpeakerGain";
-		slc->sp_gain = gain;
-		break;
-	case HEADSET_GAIN_MICROPHONE:
-		if (slc->mic_gain == gain) {
-			DBG("Ignoring no-change in microphone gain");
-			return -EALREADY;
-		}
-		name = "MicrophoneGainChanged";
-		property = "MicrophoneGain";
-		slc->mic_gain = gain;
-		break;
-	default:
-		error("Unknown gain setting");
-		return -EINVAL;
-	}
-
-	g_dbus_emit_signal(btd_get_dbus_connection(),
-				device_get_path(device->btd_dev),
-				AUDIO_HEADSET_INTERFACE, name,
-				DBUS_TYPE_UINT16, &gain,
-				DBUS_TYPE_INVALID);
-
-	emit_property_changed(device_get_path(device->btd_dev),
-				AUDIO_HEADSET_INTERFACE, property,
-				DBUS_TYPE_UINT16, &gain);
-
-	return 0;
-}
-
-static int signal_gain_setting(struct audio_device *device, const char *buf)
-{
-	struct headset *hs = device->headset;
-	dbus_uint16_t gain;
-	int err;
-
-	if (strlen(buf) < 8) {
-		error("Too short string for Gain setting");
-		return -EINVAL;
-	}
-
-	gain = (dbus_uint16_t) strtol(&buf[7], NULL, 10);
-
-	err = headset_set_gain(device, gain, buf[5]);
-	if (err < 0 && err != -EALREADY)
-		return err;
-
-	return headset_send(hs, "\r\nOK\r\n");
-}
-
-int telephony_transmit_dtmf_rsp(void *telephony_device, cme_error_t err)
-{
-	return telephony_generic_rsp(telephony_device, err);
-}
-
-static int dtmf_tone(struct audio_device *device, const char *buf)
-{
-	char tone;
-
-	if (strlen(buf) < 8) {
-		error("Too short string for DTMF tone");
-		return -EINVAL;
-	}
-
-	tone = buf[7];
-	if (tone >= '#' && tone <= 'D')
-		telephony_transmit_dtmf_req(device, tone);
-	else
-		return -EINVAL;
-
-	return 0;
-}
-
-int telephony_subscriber_number_rsp(void *telephony_device, cme_error_t err)
-{
-	return telephony_generic_rsp(telephony_device, err);
-}
-
-static int subscriber_number(struct audio_device *device, const char *buf)
-{
-	telephony_subscriber_number_req(device);
-
-	return 0;
-}
-
-int telephony_list_current_calls_rsp(void *telephony_device, cme_error_t err)
-{
-	return telephony_generic_rsp(telephony_device, err);
-}
-
-static int list_current_calls(struct audio_device *device, const char *buf)
-{
-	telephony_list_current_calls_req(device);
-
-	return 0;
-}
-
-static int extended_errors(struct audio_device *device, const char *buf)
-{
-	struct headset *hs = device->headset;
-	struct headset_slc *slc = hs->slc;
-
-	if (strlen(buf) < 9)
-		return -EINVAL;
-
-	if (buf[8] == '1') {
-		slc->cme_enabled = TRUE;
-		DBG("CME errors enabled for headset %p", hs);
-	} else {
-		slc->cme_enabled = FALSE;
-		DBG("CME errors disabled for headset %p", hs);
-	}
-
-	return headset_send(hs, "\r\nOK\r\n");
-}
-
-static int call_waiting_notify(struct audio_device *device, const char *buf)
-{
-	struct headset *hs = device->headset;
-	struct headset_slc *slc = hs->slc;
-
-	if (strlen(buf) < 9)
-		return -EINVAL;
-
-	if (buf[8] == '1') {
-		slc->cwa_enabled = TRUE;
-		DBG("Call waiting notification enabled for headset %p", hs);
-	} else {
-		slc->cwa_enabled = FALSE;
-		DBG("Call waiting notification disabled for headset %p", hs);
-	}
-
-	return headset_send(hs, "\r\nOK\r\n");
-}
-
-int telephony_operator_selection_rsp(void *telephony_device, cme_error_t err)
-{
-	return telephony_generic_rsp(telephony_device, err);
-}
-
-int telephony_call_hold_rsp(void *telephony_device, cme_error_t err)
-{
-	return telephony_generic_rsp(telephony_device, err);
-}
-
-int telephony_nr_and_ec_rsp(void *telephony_device, cme_error_t err)
-{
-	struct audio_device *device = telephony_device;
-	struct headset *hs = device->headset;
-	struct headset_slc *slc = hs->slc;
-
-	if (err == CME_ERROR_NONE) {
-		GSList *l;
-
-		for (l = hs->nrec_cbs; l; l = l->next) {
-			struct headset_nrec_callback *nrec_cb = l->data;
-
-			nrec_cb->cb(device, slc->nrec_req, nrec_cb->user_data);
-		}
-
-		slc->nrec = hs->slc->nrec_req;
-	}
-
-	return telephony_generic_rsp(telephony_device, err);
-}
-
-int telephony_voice_dial_rsp(void *telephony_device, cme_error_t err)
-{
-	return telephony_generic_rsp(telephony_device, err);
-}
-
-int telephony_operator_selection_ind(int mode, const char *oper)
-{
-	if (!active_devices)
-		return -ENODEV;
-
-	send_foreach_headset(active_devices, hfp_cmp,
-				"\r\n+COPS: %d,0,\"%s\"\r\n",
-				mode, oper);
-	return 0;
-}
-
-static int operator_selection(struct audio_device *device, const char *buf)
-{
-	struct headset *hs = device->headset;
-
-	if (strlen(buf) < 8)
-		return -EINVAL;
-
-	switch (buf[7]) {
-	case '?':
-		telephony_operator_selection_req(device);
-		break;
-	case '=':
-		return headset_send(hs, "\r\nOK\r\n");
-	default:
-		return -EINVAL;
-	}
-
-	return 0;
-}
-
-static int nr_and_ec(struct audio_device *device, const char *buf)
-{
-	struct headset *hs = device->headset;
-	struct headset_slc *slc = hs->slc;
-
-	if (strlen(buf) < 9)
-		return -EINVAL;
-
-	if (buf[8] == '0')
-		slc->nrec_req = FALSE;
-	else
-		slc->nrec_req = TRUE;
-
-	telephony_nr_and_ec_req(device, slc->nrec_req);
-
-	return 0;
-}
-
-static int voice_dial(struct audio_device *device, const char *buf)
-{
-	gboolean enable;
-
-	if (strlen(buf) < 9)
-		return -EINVAL;
-
-	if (buf[8] == '0')
-		enable = FALSE;
-	else
-		enable = TRUE;
-
-	telephony_voice_dial_req(device, enable);
-
-	return 0;
-}
-
-static int apple_command(struct audio_device *device, const char *buf)
-{
-	DBG("Got Apple command: %s", buf);
-
-	return telephony_generic_rsp(device, CME_ERROR_NONE);
-}
-
-static struct event event_callbacks[] = {
-	{ "ATA", answer_call },
-	{ "ATD", dial_number },
-	{ "AT+VG", signal_gain_setting },
-	{ "AT+BRSF", supported_features },
-	{ "AT+CIND", report_indicators },
-	{ "AT+CMER", event_reporting },
-	{ "AT+CHLD", call_hold },
-	{ "AT+CHUP", terminate_call },
-	{ "AT+CKPD", key_press },
-	{ "AT+CLIP", cli_notification },
-	{ "AT+BTRH", response_and_hold },
-	{ "AT+BLDN", last_dialed_number },
-	{ "AT+VTS", dtmf_tone },
-	{ "AT+CNUM", subscriber_number },
-	{ "AT+CLCC", list_current_calls },
-	{ "AT+CMEE", extended_errors },
-	{ "AT+CCWA", call_waiting_notify },
-	{ "AT+COPS", operator_selection },
-	{ "AT+NREC", nr_and_ec },
-	{ "AT+BVRA", voice_dial },
-	{ "AT+XAPL", apple_command },
-	{ "AT+IPHONEACCEV", apple_command },
-	{ 0 }
-};
-
-static int handle_event(struct audio_device *device, const char *buf)
-{
-	struct event *ev;
-
-	DBG("Received %s", buf);
-
-	for (ev = event_callbacks; ev->cmd; ev++) {
-		if (!strncmp(buf, ev->cmd, strlen(ev->cmd)))
-			return ev->callback(device, buf);
-	}
-
-	return -EINVAL;
-}
-
-static void close_sco(struct audio_device *device)
-{
-	struct headset *hs = device->headset;
-
-	if (hs->sco) {
-		int sock = g_io_channel_unix_get_fd(hs->sco);
-		shutdown(sock, SHUT_RDWR);
-		g_io_channel_shutdown(hs->sco, TRUE, NULL);
-		g_io_channel_unref(hs->sco);
-		hs->sco = NULL;
-	}
-
-	if (hs->sco_id) {
-		g_source_remove(hs->sco_id);
-		hs->sco_id = 0;
-	}
-}
-
-static gboolean rfcomm_io_cb(GIOChannel *chan, GIOCondition cond,
-				struct audio_device *device)
-{
-	struct headset *hs;
-	struct headset_slc *slc;
-	unsigned char buf[BUF_SIZE];
-	ssize_t bytes_read;
-	size_t free_space;
-	int fd;
-
-	if (cond & G_IO_NVAL)
-		return FALSE;
-
-	hs = device->headset;
-	slc = hs->slc;
-
-	if (cond & (G_IO_ERR | G_IO_HUP)) {
-		DBG("ERR or HUP on RFCOMM socket");
-		goto failed;
-	}
-
-	fd = g_io_channel_unix_get_fd(chan);
-
-	bytes_read = read(fd, buf, sizeof(buf) - 1);
-	if (bytes_read < 0)
-		return TRUE;
-
-	free_space = sizeof(slc->buf) - slc->data_start -
-			slc->data_length - 1;
-
-	if (free_space < (size_t) bytes_read) {
-		/* Very likely that the HS is sending us garbage so
-		 * just ignore the data and disconnect */
-		error("Too much data to fit incoming buffer");
-		goto failed;
-	}
-
-	memcpy(&slc->buf[slc->data_start], buf, bytes_read);
-	slc->data_length += bytes_read;
-
-	/* Make sure the data is null terminated so we can use string
-	 * functions */
-	slc->buf[slc->data_start + slc->data_length] = '\0';
-
-	while (slc->data_length > 0) {
-		char *cr;
-		int err;
-		off_t cmd_len;
-
-		cr = strchr(&slc->buf[slc->data_start], '\r');
-		if (!cr)
-			break;
-
-		cmd_len = 1 + (off_t) cr - (off_t) &slc->buf[slc->data_start];
-		*cr = '\0';
-
-		if (cmd_len > 1)
-			err = handle_event(device, &slc->buf[slc->data_start]);
-		else
-			/* Silently skip empty commands */
-			err = 0;
-
-		if (err == -EINVAL) {
-			error("Badly formated or unrecognized command: %s",
-					&slc->buf[slc->data_start]);
-			err = telephony_generic_rsp(device,
-						CME_ERROR_NOT_SUPPORTED);
-			if (err < 0)
-				goto failed;
-		} else if (err < 0)
-			error("Error handling command %s: %s (%d)",
-						&slc->buf[slc->data_start],
-						strerror(-err), -err);
-
-		slc->data_start += cmd_len;
-		slc->data_length -= cmd_len;
-
-		if (!slc->data_length)
-			slc->data_start = 0;
-	}
-
-	return TRUE;
-
-failed:
-	headset_set_state(device, HEADSET_STATE_DISCONNECTED);
-
-	return FALSE;
-}
-
-static gboolean sco_cb(GIOChannel *chan, GIOCondition cond,
-			struct audio_device *device)
-{
-	if (cond & G_IO_NVAL)
-		return FALSE;
-
-	error("Audio connection got disconnected");
-
-	pending_connect_finalize(device);
-	headset_set_state(device, HEADSET_STATE_CONNECTED);
-
-	return FALSE;
-}
-
-void headset_connect_cb(GIOChannel *chan, GError *err, gpointer user_data)
-{
-	struct audio_device *dev = user_data;
-	struct headset *hs = dev->headset;
-	struct pending_connect *p = hs->pending;
-	char hs_address[18];
-
-	if (err) {
-		error("%s", err->message);
-		goto failed;
-	}
-
-	/* For HFP telephony isn't ready just disconnect */
-	if (hs->hfp_active && !ag.telephony_ready) {
-		error("Unable to accept HFP connection since the telephony "
-				"subsystem isn't initialized");
-		goto failed;
-	}
-
-	hs->rfcomm = hs->tmp_rfcomm;
-	hs->tmp_rfcomm = NULL;
-
-	ba2str(&dev->dst, hs_address);
-
-	if (p)
-		p->io = NULL;
-	else
-		hs->auto_dc = FALSE;
-
-	g_io_add_watch(chan, G_IO_IN | G_IO_ERR | G_IO_HUP| G_IO_NVAL,
-			(GIOFunc) rfcomm_io_cb, dev);
-
-	DBG("%s: Connected to %s", device_get_path(dev->btd_dev), hs_address);
-
-	hs->slc = g_new0(struct headset_slc, 1);
-	hs->slc->sp_gain = 15;
-	hs->slc->mic_gain = 15;
-	hs->slc->nrec = TRUE;
-
-	/* In HFP mode wait for Service Level Connection */
-	if (hs->hfp_active)
-		return;
-
-	headset_set_state(dev, HEADSET_STATE_CONNECTED);
-
-	if (p && p->target_state == HEADSET_STATE_PLAYING) {
-		p->err = sco_connect(dev, NULL, NULL, NULL);
-		if (p->err < 0)
-			goto failed;
-		return;
-	}
-
-	if (p && p->msg) {
-		DBusMessage *reply = dbus_message_new_method_return(p->msg);
-		g_dbus_send_message(btd_get_dbus_connection(), reply);
-	}
-
-	pending_connect_finalize(dev);
-
-	return;
-
-failed:
-	if (p && p->msg)
-		error_connect_failed(p->msg, p->err);
-	pending_connect_finalize(dev);
-	if (hs->rfcomm)
-		headset_set_state(dev, HEADSET_STATE_CONNECTED);
-	else
-		headset_set_state(dev, HEADSET_STATE_DISCONNECTED);
-}
-
-static int headset_set_channel(struct headset *headset,
-				const sdp_record_t *record, uint16_t svc)
-{
-	int ch;
-	sdp_list_t *protos;
-
-	if (sdp_get_access_protos(record, &protos) < 0) {
-		error("Unable to get access protos from headset record");
-		return -1;
-	}
-
-	ch = sdp_get_proto_port(protos, RFCOMM_UUID);
-
-	sdp_list_foreach(protos, (sdp_list_func_t) sdp_list_free, NULL);
-	sdp_list_free(protos, NULL);
-
-	if (ch <= 0) {
-		error("Unable to get RFCOMM channel from Headset record");
-		return -1;
-	}
-
-	headset->rfcomm_ch = ch;
-
-	if (svc == HANDSFREE_SVCLASS_ID) {
-		headset->hfp_handle = record->handle;
-		headset->hsp_handle = 0;
-		DBG("Discovered Handsfree service on channel %d", ch);
-	} else {
-		headset->hsp_handle = record->handle;
-		headset->hfp_handle = 0;
-		DBG("Discovered Headset service on channel %d", ch);
-	}
-
-	return 0;
-}
-
-static void get_record_cb(sdp_list_t *recs, int err, gpointer user_data)
-{
-	struct audio_device *dev = user_data;
-	struct headset *hs = dev->headset;
-	struct pending_connect *p = hs->pending;
-	sdp_record_t *record = NULL;
-	sdp_list_t *r;
-	uuid_t uuid;
-
-	assert(hs->pending != NULL);
-
-	if (err < 0) {
-		error("Unable to get service record: %s (%d)",
-							strerror(-err), -err);
-		p->err = -err;
-		if (p->msg)
-			error_connect_failed(p->msg, p->err);
-		goto failed;
-	}
-
-	if (!recs || !recs->data) {
-		error("No records found");
-		goto failed_not_supported;
-	}
-
-	sdp_uuid16_create(&uuid, p->svclass);
-
-	for (r = recs; r != NULL; r = r->next) {
-		sdp_list_t *classes;
-		uuid_t class;
-
-		record = r->data;
-
-		if (sdp_get_service_classes(record, &classes) < 0) {
-			error("Unable to get service classes from record");
-			continue;
-		}
-
-		memcpy(&class, classes->data, sizeof(uuid));
-
-		sdp_list_free(classes, free);
-
-		if (sdp_uuid_cmp(&class, &uuid) == 0)
-			break;
-	}
-
-	if (r == NULL) {
-		error("No record found with UUID 0x%04x", p->svclass);
-		goto failed_not_supported;
-	}
-
-	if (headset_set_channel(hs, record, p->svclass) < 0) {
-		error("Unable to extract RFCOMM channel from service record");
-		goto failed_not_supported;
-	}
-
-	/* Set svclass to 0 so we can easily check that SDP is no-longer
-	 * going on (to know if bt_cancel_discovery needs to be called) */
-	p->svclass = 0;
-
-	err = rfcomm_connect(dev, NULL, NULL, NULL);
-	if (err < 0) {
-		error("Unable to connect: %s (%d)", strerror(-err), -err);
-		p->err = -err;
-		if (p->msg != NULL)
-			error_connect_failed(p->msg, p->err);
-		goto failed;
-	}
-
-	return;
-
-failed_not_supported:
-	if (p->svclass == HANDSFREE_SVCLASS_ID &&
-			get_records(dev, NULL, NULL, NULL) == 0)
-		return;
-	if (p->msg) {
-		DBusMessage *reply = btd_error_not_supported(p->msg);
-		g_dbus_send_message(btd_get_dbus_connection(), reply);
-	}
-failed:
-	p->svclass = 0;
-	pending_connect_finalize(dev);
-	headset_set_state(dev, HEADSET_STATE_DISCONNECTED);
-}
-
-static int get_records(struct audio_device *device, headset_stream_cb_t cb,
-			void *user_data, unsigned int *cb_id)
-{
-	struct headset *hs = device->headset;
-	uint16_t svclass;
-	uuid_t uuid;
-	int err;
-
-	if (hs->pending && hs->pending->svclass == HANDSFREE_SVCLASS_ID)
-		svclass = HEADSET_SVCLASS_ID;
-	else
-		svclass = hs->search_hfp ? HANDSFREE_SVCLASS_ID :
-							HEADSET_SVCLASS_ID;
-
-	sdp_uuid16_create(&uuid, svclass);
-
-	err = bt_search_service(&device->src, &device->dst, &uuid,
-						get_record_cb, device, NULL);
-	if (err < 0)
-		return err;
-
-	if (hs->pending) {
-		hs->pending->svclass = svclass;
-		return 0;
-	}
-
-	headset_set_state(device, HEADSET_STATE_CONNECTING);
-
-	pending_connect_init(hs, HEADSET_STATE_CONNECTED);
-
-	hs->pending->svclass = svclass;
-
-	if (cb) {
-		unsigned int id;
-		id = connect_cb_new(hs, HEADSET_STATE_CONNECTED,
-					cb, user_data);
-		if (cb_id)
-			*cb_id = id;
-	}
-
-	return 0;
-}
-
-static int rfcomm_connect(struct audio_device *dev, headset_stream_cb_t cb,
-				void *user_data, unsigned int *cb_id)
-{
-	struct headset *hs = dev->headset;
-	char address[18];
-	GError *err = NULL;
-
-	if (hs->rfcomm_ch < 0)
-		return get_records(dev, cb, user_data, cb_id);
-
-	ba2str(&dev->dst, address);
-
-	DBG("%s: Connecting to %s channel %d", device_get_path(dev->btd_dev),
-						address, hs->rfcomm_ch);
-
-	hs->tmp_rfcomm = bt_io_connect(headset_connect_cb, dev,
-					NULL, &err,
-					BT_IO_OPT_SOURCE_BDADDR, &dev->src,
-					BT_IO_OPT_DEST_BDADDR, &dev->dst,
-					BT_IO_OPT_CHANNEL, hs->rfcomm_ch,
-					BT_IO_OPT_SEC_LEVEL, BT_IO_SEC_MEDIUM,
-					BT_IO_OPT_INVALID);
-
-	hs->rfcomm_ch = -1;
-
-	if (!hs->tmp_rfcomm) {
-		error("%s", err->message);
-		g_error_free(err);
-		return -EIO;
-	}
-
-	hs->hfp_active = hs->hfp_handle != 0 ? TRUE : FALSE;
-	hs->rfcomm_initiator = FALSE;
-
-	headset_set_state(dev, HEADSET_STATE_CONNECTING);
-
-	pending_connect_init(hs, HEADSET_STATE_CONNECTED);
-
-	if (cb) {
-		unsigned int id = connect_cb_new(hs, HEADSET_STATE_CONNECTED,
-							cb, user_data);
-		if (cb_id)
-			*cb_id = id;
-	}
-
-	return 0;
-}
-
-static DBusMessage *hs_stop(DBusConnection *conn, DBusMessage *msg,
-					void *data)
-{
-	struct audio_device *device = data;
-	struct headset *hs = device->headset;
-	DBusMessage *reply = NULL;
-
-	if (hs->state < HEADSET_STATE_PLAY_IN_PROGRESS)
-		return btd_error_not_connected(msg);
-
-	reply = dbus_message_new_method_return(msg);
-	if (!reply)
-		return NULL;
-
-	headset_set_state(device, HEADSET_STATE_CONNECTED);
-
-	return reply;
-}
-
-static DBusMessage *hs_disconnect(DBusConnection *conn, DBusMessage *msg,
-					void *data)
-{
-	struct audio_device *device = data;
-	struct headset *hs = device->headset;
-	char hs_address[18];
-
-	if (hs->state == HEADSET_STATE_DISCONNECTED)
-		return btd_error_not_connected(msg);
-
-	headset_shutdown(device);
-	ba2str(&device->dst, hs_address);
-	info("Disconnected from %s, %s", hs_address,
-					device_get_path(device->btd_dev));
-
-	return dbus_message_new_method_return(msg);
-
-}
-
-static DBusMessage *hs_is_connected(DBusConnection *conn,
-						DBusMessage *msg,
-						void *data)
-{
-	struct audio_device *device = data;
-	DBusMessage *reply;
-	dbus_bool_t connected;
-
-	reply = dbus_message_new_method_return(msg);
-	if (!reply)
-		return NULL;
-
-	connected = (device->headset->state >= HEADSET_STATE_CONNECTED);
-
-	dbus_message_append_args(reply, DBUS_TYPE_BOOLEAN, &connected,
-					DBUS_TYPE_INVALID);
-
-	return reply;
-}
-
-static DBusMessage *hs_connect(DBusConnection *conn, DBusMessage *msg,
-					void *data)
-{
-	struct audio_device *device = data;
-	struct headset *hs = device->headset;
-	int err;
-
-	if (hs->state == HEADSET_STATE_CONNECTING)
-		return btd_error_in_progress(msg);
-	else if (hs->state > HEADSET_STATE_CONNECTING)
-		return btd_error_already_connected(msg);
-
-	if (hs->hfp_handle && !ag.telephony_ready)
-		return btd_error_not_ready(msg);
-
-	device->auto_connect = FALSE;
-
-	err = rfcomm_connect(device, NULL, NULL, NULL);
-	if (err < 0)
-		return btd_error_failed(msg, strerror(-err));
-
-	hs->auto_dc = FALSE;
-
-	hs->pending->msg = dbus_message_ref(msg);
-
-	return NULL;
-}
-
-static DBusMessage *hs_ring(DBusConnection *conn, DBusMessage *msg,
-					void *data)
-{
-	struct audio_device *device = data;
-	struct headset *hs = device->headset;
-	DBusMessage *reply = NULL;
-	int err;
-
-	if (hs->state < HEADSET_STATE_CONNECTED)
-		return btd_error_not_connected(msg);
-
-	reply = dbus_message_new_method_return(msg);
-	if (!reply)
-		return NULL;
-
-	if (ag.ring_timer) {
-		DBG("IndicateCall received when already indicating");
-		return reply;
-	}
-
-	err = headset_send(hs, "\r\nRING\r\n");
-	if (err < 0) {
-		dbus_message_unref(reply);
-		return btd_error_failed(msg, strerror(-err));
-	}
-
-	ring_timer_cb(NULL);
-	ag.ring_timer = g_timeout_add_seconds(RING_INTERVAL, ring_timer_cb,
-						NULL);
-
-	return reply;
-}
-
-static DBusMessage *hs_cancel_call(DBusConnection *conn,
-					DBusMessage *msg,
-					void *data)
-{
-	struct audio_device *device = data;
-	struct headset *hs = device->headset;
-	DBusMessage *reply = NULL;
-
-	if (hs->state < HEADSET_STATE_CONNECTED)
-		return btd_error_not_connected(msg);
-
-	reply = dbus_message_new_method_return(msg);
-	if (!reply)
-		return NULL;
-
-	if (ag.ring_timer) {
-		g_source_remove(ag.ring_timer);
-		ag.ring_timer = 0;
-	} else
-		DBG("Got CancelCall method call but no call is active");
-
-	return reply;
-}
-
-static DBusMessage *hs_set_gain(DBusMessage *msg,
-				void *data, uint16_t gain,
-				char type)
-{
-	struct audio_device *device = data;
-	struct headset *hs = device->headset;
-	DBusMessage *reply;
-	int err;
-
-	if (hs->state < HEADSET_STATE_CONNECTED)
-		return btd_error_not_connected(msg);
-
-	err = headset_set_gain(device, gain, type);
-	if (err < 0)
-		return btd_error_invalid_args(msg);
-
-	reply = dbus_message_new_method_return(msg);
-	if (!reply)
-		return NULL;
-
-	if (hs->state == HEADSET_STATE_PLAYING) {
-		err = headset_send(hs, "\r\n+VG%c=%u\r\n", type, gain);
-		if (err < 0) {
-			dbus_message_unref(reply);
-			return btd_error_failed(msg, strerror(-err));
-		}
-	}
-
-	return reply;
-}
-
-static DBusMessage *hs_get_properties(DBusConnection *conn,
-					DBusMessage *msg, void *data)
-{
-	struct audio_device *device = data;
-	DBusMessage *reply;
-	DBusMessageIter iter;
-	DBusMessageIter dict;
-	gboolean value;
-	const char *state;
-
-	reply = dbus_message_new_method_return(msg);
-	if (!reply)
-		return NULL;
-
-	dbus_message_iter_init_append(reply, &iter);
-
-	dbus_message_iter_open_container(&iter, DBUS_TYPE_ARRAY,
-			DBUS_DICT_ENTRY_BEGIN_CHAR_AS_STRING
-			DBUS_TYPE_STRING_AS_STRING DBUS_TYPE_VARIANT_AS_STRING
-			DBUS_DICT_ENTRY_END_CHAR_AS_STRING, &dict);
-
-
-	/* Playing */
-	value = (device->headset->state == HEADSET_STATE_PLAYING);
-	dict_append_entry(&dict, "Playing", DBUS_TYPE_BOOLEAN, &value);
-
-	/* State */
-	state = state2str(device->headset->state);
-	if (state)
-		dict_append_entry(&dict, "State", DBUS_TYPE_STRING, &state);
-
-	/* Connected */
-	value = (device->headset->state >= HEADSET_STATE_CONNECTED);
-	dict_append_entry(&dict, "Connected", DBUS_TYPE_BOOLEAN, &value);
-
-	if (!value)
-		goto done;
-
-	/* SpeakerGain */
-	dict_append_entry(&dict, "SpeakerGain",
-				DBUS_TYPE_UINT16,
-				&device->headset->slc->sp_gain);
-
-	/* MicrophoneGain */
-	dict_append_entry(&dict, "MicrophoneGain",
-				DBUS_TYPE_UINT16,
-				&device->headset->slc->mic_gain);
-
-done:
-	dbus_message_iter_close_container(&iter, &dict);
-
-	return reply;
-}
-
-static DBusMessage *hs_set_property(DBusConnection *conn,
-					DBusMessage *msg, void *data)
-{
-	const char *property;
-	DBusMessageIter iter;
-	DBusMessageIter sub;
-	uint16_t gain;
-
-	if (!dbus_message_iter_init(msg, &iter))
-		return btd_error_invalid_args(msg);
-
-	if (dbus_message_iter_get_arg_type(&iter) != DBUS_TYPE_STRING)
-		return btd_error_invalid_args(msg);
-
-	dbus_message_iter_get_basic(&iter, &property);
-	dbus_message_iter_next(&iter);
-
-	if (dbus_message_iter_get_arg_type(&iter) != DBUS_TYPE_VARIANT)
-		return btd_error_invalid_args(msg);
-	dbus_message_iter_recurse(&iter, &sub);
-
-	if (g_str_equal("SpeakerGain", property)) {
-		if (dbus_message_iter_get_arg_type(&sub) != DBUS_TYPE_UINT16)
-			return btd_error_invalid_args(msg);
-
-		dbus_message_iter_get_basic(&sub, &gain);
-		return hs_set_gain(msg, data, gain,
-					HEADSET_GAIN_SPEAKER);
-	} else if (g_str_equal("MicrophoneGain", property)) {
-		if (dbus_message_iter_get_arg_type(&sub) != DBUS_TYPE_UINT16)
-			return btd_error_invalid_args(msg);
-
-		dbus_message_iter_get_basic(&sub, &gain);
-		return hs_set_gain(msg, data, gain,
-					HEADSET_GAIN_MICROPHONE);
-	}
-
-	return btd_error_invalid_args(msg);
-}
-
-static const GDBusMethodTable headset_methods[] = {
-	{ GDBUS_ASYNC_METHOD("Connect", NULL, NULL, hs_connect) },
-	{ GDBUS_METHOD("Disconnect", NULL, NULL, hs_disconnect) },
-	{ GDBUS_METHOD("IsConnected",
-			NULL, GDBUS_ARGS({ "connected", "b" }),
-			hs_is_connected) },
-	{ GDBUS_METHOD("IndicateCall", NULL, NULL, hs_ring) },
-	{ GDBUS_METHOD("CancelCall", NULL, NULL, hs_cancel_call) },
-	{ GDBUS_METHOD("Stop", NULL, NULL, hs_stop) },
-	{ GDBUS_METHOD("GetProperties",
-			NULL, GDBUS_ARGS({ "properties", "a{sv}" }),
-			hs_get_properties) },
-	{ GDBUS_METHOD("SetProperty",
-			GDBUS_ARGS({ "name", "s" }, { "value", "v" }), NULL,
-			hs_set_property) },
-	{ }
-};
-
-static const GDBusSignalTable headset_signals[] = {
-	{ GDBUS_DEPRECATED_SIGNAL("Connected", NULL) },
-	{ GDBUS_DEPRECATED_SIGNAL("Disconnected", NULL) },
-	{ GDBUS_SIGNAL("AnswerRequested", NULL) },
-	{ GDBUS_DEPRECATED_SIGNAL("Stopped", NULL) },
-	{ GDBUS_DEPRECATED_SIGNAL("Playing", NULL) },
-	{ GDBUS_DEPRECATED_SIGNAL("SpeakerGainChanged",
-						GDBUS_ARGS({ "gain", "q" })) },
-	{ GDBUS_DEPRECATED_SIGNAL("MicrophoneGainChanged",
-						GDBUS_ARGS({ "gain", "q" })) },
-	{ GDBUS_SIGNAL("CallTerminated", NULL) },
-	{ GDBUS_SIGNAL("PropertyChanged",
-			GDBUS_ARGS({ "name", "s" }, { "value", "v" })) },
-	{ }
-};
-
-void headset_update(struct audio_device *dev, struct headset *headset,
-								GSList *uuids)
-{
-	const sdp_record_t *record;
-
-	if (g_slist_find_custom(uuids, HFP_HS_UUID, bt_uuid_strcmp) &&
-						headset->hfp_handle == 0) {
-		record = btd_device_get_record(dev->btd_dev, HFP_HS_UUID);
-		if (record)
-			headset->hfp_handle = record->handle;
-	}
-
-	if (g_slist_find_custom(uuids, HSP_HS_UUID, bt_uuid_strcmp) &&
-						headset->hsp_handle == 0) {
-		record = btd_device_get_record(dev->btd_dev, HSP_HS_UUID);
-		if (record)
-			headset->hsp_handle = record->handle;
-	}
-}
-
-static int headset_close_rfcomm(struct audio_device *dev)
-{
-	struct headset *hs = dev->headset;
-	GIOChannel *rfcomm = hs->tmp_rfcomm ? hs->tmp_rfcomm : hs->rfcomm;
-
-	if (rfcomm) {
-		g_io_channel_shutdown(rfcomm, TRUE, NULL);
-		g_io_channel_unref(rfcomm);
-		hs->tmp_rfcomm = NULL;
-		hs->rfcomm = NULL;
-	}
-
-	g_free(hs->slc);
-	hs->slc = NULL;
-
-	return 0;
-}
-
-static void headset_free(struct audio_device *dev)
-{
-	struct headset *hs = dev->headset;
-
-	if (hs->dc_timer) {
-		g_source_remove(hs->dc_timer);
-		hs->dc_timer = 0;
-	}
-
-	close_sco(dev);
-
-	headset_close_rfcomm(dev);
-
-	g_slist_free_full(hs->nrec_cbs, g_free);
-
-	g_free(hs);
-	dev->headset = NULL;
-}
-
-static void path_unregister(void *data)
-{
-	struct audio_device *dev = data;
-	struct headset *hs = dev->headset;
-
-	if (hs->state > HEADSET_STATE_DISCONNECTED) {
-		DBG("Headset unregistered while device was connected!");
-		headset_shutdown(dev);
-	}
-
-	DBG("Unregistered interface %s on path %s",
-		AUDIO_HEADSET_INTERFACE, device_get_path(dev->btd_dev));
-
-	headset_free(dev);
-}
-
-void headset_unregister(struct audio_device *dev)
-{
-	g_dbus_unregister_interface(btd_get_dbus_connection(),
-						device_get_path(dev->btd_dev),
-						AUDIO_HEADSET_INTERFACE);
-}
-
-struct headset *headset_init(struct audio_device *dev, GSList *uuids,
-							gboolean hfp_enabled)
-{
-	struct headset *hs;
-
-	hs = g_new0(struct headset, 1);
-	hs->rfcomm_ch = -1;
-	hs->search_hfp = hfp_enabled;
-
-	headset_update(dev, hs, uuids);
-
-	if (!g_dbus_register_interface(btd_get_dbus_connection(),
-					device_get_path(dev->btd_dev),
-					AUDIO_HEADSET_INTERFACE,
-					headset_methods, headset_signals, NULL,
-					dev, path_unregister)) {
-		g_free(hs);
-		return NULL;
-	}
-
-	DBG("Registered interface %s on path %s", AUDIO_HEADSET_INTERFACE,
-						device_get_path(dev->btd_dev));
-
-	return hs;
-}
-
-uint32_t headset_config_init(GKeyFile *config)
-{
-	GError *err = NULL;
-	char *str;
-
-	/* Use the default values if there is no config file */
-	if (config == NULL)
-		return ag.features;
-
-	str = g_key_file_get_string(config, "General", "SCORouting",
-					&err);
-	if (err) {
-		DBG("audio.conf: %s", err->message);
-		g_clear_error(&err);
-	} else {
-		if (strcmp(str, "PCM") == 0)
-			sco_hci = FALSE;
-		else if (strcmp(str, "HCI") == 0)
-			sco_hci = TRUE;
-		else
-			error("Invalid Headset Routing value: %s", str);
-		g_free(str);
-	}
-
-	/* Init fast connectable option */
-	str = g_key_file_get_string(config, "Headset", "FastConnectable",
-					&err);
-	if (err) {
-		DBG("audio.conf: %s", err->message);
-		g_clear_error(&err);
-	} else {
-		fast_connectable = strcmp(str, "true") == 0;
-		if (fast_connectable)
-			manager_set_fast_connectable(FALSE);
-		g_free(str);
-	}
-
-	return ag.features;
-}
-
-static gboolean hs_dc_timeout(struct audio_device *dev)
-{
-	headset_set_state(dev, HEADSET_STATE_DISCONNECTED);
-	return FALSE;
-}
-
-gboolean headset_cancel_stream(struct audio_device *dev, unsigned int id)
-{
-	struct headset *hs = dev->headset;
-	struct pending_connect *p = hs->pending;
-	GSList *l;
-	struct connect_cb *cb = NULL;
-
-	if (!p)
-		return FALSE;
-
-	for (l = p->callbacks; l != NULL; l = l->next) {
-		struct connect_cb *tmp = l->data;
-
-		if (tmp->id == id) {
-			cb = tmp;
-			break;
-		}
-	}
-
-	if (!cb)
-		return FALSE;
-
-	p->callbacks = g_slist_remove(p->callbacks, cb);
-	g_free(cb);
-
-	if (p->callbacks || p->msg)
-		return TRUE;
-
-	if (hs->auto_dc) {
-		if (hs->rfcomm)
-			hs->dc_timer = g_timeout_add_seconds(DC_TIMEOUT,
-						(GSourceFunc) hs_dc_timeout,
-						dev);
-		else
-			headset_set_state(dev, HEADSET_STATE_DISCONNECTED);
-	}
-
-	return TRUE;
-}
-
-static gboolean dummy_connect_complete(struct audio_device *dev)
-{
-	pending_connect_finalize(dev);
-	return FALSE;
-}
-
-unsigned int headset_request_stream(struct audio_device *dev,
-					headset_stream_cb_t cb,
-					void *user_data)
-{
-	struct headset *hs = dev->headset;
-	unsigned int id;
-
-	if (hs->state == HEADSET_STATE_PLAYING) {
-		id = connect_cb_new(hs, HEADSET_STATE_PLAYING, cb, user_data);
-		g_idle_add((GSourceFunc) dummy_connect_complete, dev);
-		return id;
-	}
-
-	if (hs->dc_timer) {
-		g_source_remove(hs->dc_timer);
-		hs->dc_timer = 0;
-	}
-
-	if (hs->state == HEADSET_STATE_CONNECTING ||
-			hs->state == HEADSET_STATE_PLAY_IN_PROGRESS)
-		return connect_cb_new(hs, HEADSET_STATE_PLAYING, cb, user_data);
-
-	if (hs->rfcomm == NULL) {
-		if (rfcomm_connect(dev, cb, user_data, &id) < 0)
-			return 0;
-		hs->auto_dc = TRUE;
-	} else if (sco_connect(dev, cb, user_data, &id) < 0)
-		return 0;
-
-	hs->pending->target_state = HEADSET_STATE_PLAYING;
-
-	return id;
-}
-
-unsigned int headset_config_stream(struct audio_device *dev,
-					gboolean auto_dc,
-					headset_stream_cb_t cb,
-					void *user_data)
-{
-	struct headset *hs = dev->headset;
-	unsigned int id = 0;
-
-	if (hs->dc_timer) {
-		g_source_remove(hs->dc_timer);
-		hs->dc_timer = 0;
-	}
-
-	if (hs->state == HEADSET_STATE_CONNECTING)
-		return connect_cb_new(hs, HEADSET_STATE_CONNECTED, cb,
-					user_data);
-
-	if (hs->rfcomm)
-		goto done;
-
-	if (rfcomm_connect(dev, cb, user_data, &id) < 0)
-		return 0;
-
-	hs->auto_dc = auto_dc;
-	hs->pending->target_state = HEADSET_STATE_CONNECTED;
-
-	return id;
-
-done:
-	id = connect_cb_new(hs, HEADSET_STATE_CONNECTED, cb, user_data);
-	g_idle_add((GSourceFunc) dummy_connect_complete, dev);
-	return id;
-}
-
-unsigned int headset_suspend_stream(struct audio_device *dev,
-					headset_stream_cb_t cb,
-					void *user_data)
-{
-	struct headset *hs = dev->headset;
-	unsigned int id;
-	int sock;
-
-	if (hs->state == HEADSET_STATE_DISCONNECTED ||
-				hs->state == HEADSET_STATE_CONNECTING)
-		return 0;
-
-	if (hs->dc_timer) {
-		g_source_remove(hs->dc_timer);
-		hs->dc_timer = 0;
-	}
-
-	if (hs->sco) {
-		sock = g_io_channel_unix_get_fd(hs->sco);
-
-		/* shutdown but leave the socket open and wait for hup */
-		shutdown(sock, SHUT_RDWR);
-	} else {
-		headset_set_state(dev, HEADSET_STATE_CONNECTED);
-
-		g_idle_add((GSourceFunc) dummy_connect_complete, dev);
-	}
-
-	id = connect_cb_new(hs, HEADSET_STATE_CONNECTED, cb, user_data);
-
-	return id;
-}
-
-gboolean headset_get_hfp_active(struct audio_device *dev)
-{
-	struct headset *hs = dev->headset;
-
-	return hs->hfp_active;
-}
-
-void headset_set_hfp_active(struct audio_device *dev, gboolean active)
-{
-	struct headset *hs = dev->headset;
-
-	hs->hfp_active = active;
-}
-
-gboolean headset_get_rfcomm_initiator(struct audio_device *dev)
-{
-	struct headset *hs = dev->headset;
-
-	return hs->rfcomm_initiator;
-}
-
-void headset_set_rfcomm_initiator(struct audio_device *dev,
-					gboolean initiator)
-{
-	struct headset *hs = dev->headset;
-
-	hs->rfcomm_initiator = initiator;
-}
-
-GIOChannel *headset_get_rfcomm(struct audio_device *dev)
-{
-	struct headset *hs = dev->headset;
-
-	return hs->tmp_rfcomm;
-}
-
-int headset_connect_rfcomm(struct audio_device *dev, GIOChannel *io)
-{
-	struct headset *hs = dev->headset;
-
-	if (hs->tmp_rfcomm)
-		return -EALREADY;
-
-	hs->tmp_rfcomm = g_io_channel_ref(io);
-
-	return 0;
-}
-
-int headset_connect_sco(struct audio_device *dev, GIOChannel *io)
-{
-	struct headset *hs = dev->headset;
-	struct headset_slc *slc = hs->slc;
-
-	if (hs->sco)
-		return -EISCONN;
-
-	hs->sco = g_io_channel_ref(io);
-
-	if (slc->pending_ring) {
-		ring_timer_cb(NULL);
-		ag.ring_timer = g_timeout_add_seconds(RING_INTERVAL,
-						ring_timer_cb,
-						NULL);
-		slc->pending_ring = FALSE;
-	}
-
-	return 0;
-}
-
-void headset_set_state(struct audio_device *dev, headset_state_t state)
-{
-	struct headset *hs = dev->headset;
-	struct headset_slc *slc = hs->slc;
-	gboolean value;
-	const char *state_str;
-	headset_state_t old_state = hs->state;
-	GSList *l;
-
-	if (old_state == state)
-		return;
-
-	state_str = state2str(state);
-
-	switch (state) {
-	case HEADSET_STATE_DISCONNECTED:
-		value = FALSE;
-		close_sco(dev);
-		headset_close_rfcomm(dev);
-		emit_property_changed(device_get_path(dev->btd_dev),
-					AUDIO_HEADSET_INTERFACE, "State",
-					DBUS_TYPE_STRING, &state_str);
-		g_dbus_emit_signal(btd_get_dbus_connection(),
-					device_get_path(dev->btd_dev),
-					AUDIO_HEADSET_INTERFACE,
-					"Disconnected",
-					DBUS_TYPE_INVALID);
-		if (hs->state > HEADSET_STATE_CONNECTING) {
-			emit_property_changed(device_get_path(dev->btd_dev),
-					AUDIO_HEADSET_INTERFACE, "Connected",
-					DBUS_TYPE_BOOLEAN, &value);
-			telephony_device_disconnected(dev);
-		}
-		active_devices = g_slist_remove(active_devices, dev);
-		break;
-	case HEADSET_STATE_CONNECTING:
-		emit_property_changed(device_get_path(dev->btd_dev),
-					AUDIO_HEADSET_INTERFACE, "State",
-					DBUS_TYPE_STRING, &state_str);
-		break;
-	case HEADSET_STATE_CONNECTED:
-		close_sco(dev);
-		if (hs->state != HEADSET_STATE_PLAY_IN_PROGRESS)
-			emit_property_changed(device_get_path(dev->btd_dev),
-					AUDIO_HEADSET_INTERFACE, "State",
-					DBUS_TYPE_STRING, &state_str);
-		if (hs->state < state) {
-			if (ag.features & AG_FEATURE_INBAND_RINGTONE)
-				slc->inband_ring = TRUE;
-			else
-				slc->inband_ring = FALSE;
-			g_dbus_emit_signal(btd_get_dbus_connection(),
-						device_get_path(dev->btd_dev),
-						AUDIO_HEADSET_INTERFACE,
-						"Connected",
-						DBUS_TYPE_INVALID);
-			value = TRUE;
-			emit_property_changed(device_get_path(dev->btd_dev),
-						AUDIO_HEADSET_INTERFACE,
-						"Connected",
-						DBUS_TYPE_BOOLEAN, &value);
-			active_devices = g_slist_append(active_devices, dev);
-			telephony_device_connected(dev);
-		} else if (hs->state == HEADSET_STATE_PLAYING) {
-			value = FALSE;
-			g_dbus_emit_signal(btd_get_dbus_connection(),
-						device_get_path(dev->btd_dev),
-						AUDIO_HEADSET_INTERFACE,
-						"Stopped",
-						DBUS_TYPE_INVALID);
-			emit_property_changed(device_get_path(dev->btd_dev),
-						AUDIO_HEADSET_INTERFACE,
-						"Playing",
-						DBUS_TYPE_BOOLEAN, &value);
-		}
-		break;
-	case HEADSET_STATE_PLAY_IN_PROGRESS:
-		break;
-	case HEADSET_STATE_PLAYING:
-		value = TRUE;
-		emit_property_changed(device_get_path(dev->btd_dev),
-					AUDIO_HEADSET_INTERFACE, "State",
-					DBUS_TYPE_STRING, &state_str);
-
-		/* Do not watch HUP since we need to know when the link is
-		   really disconnected */
-		hs->sco_id = g_io_add_watch(hs->sco,
-					G_IO_ERR | G_IO_NVAL,
-					(GIOFunc) sco_cb, dev);
-
-		g_dbus_emit_signal(btd_get_dbus_connection(),
-					device_get_path(dev->btd_dev),
-					AUDIO_HEADSET_INTERFACE, "Playing",
-					DBUS_TYPE_INVALID);
-		emit_property_changed(device_get_path(dev->btd_dev),
-					AUDIO_HEADSET_INTERFACE, "Playing",
-					DBUS_TYPE_BOOLEAN, &value);
-
-		if (slc->sp_gain >= 0)
-			headset_send(hs, "\r\n+VGS=%u\r\n", slc->sp_gain);
-		if (slc->mic_gain >= 0)
-			headset_send(hs, "\r\n+VGM=%u\r\n", slc->mic_gain);
-		break;
-	}
-
-	hs->state = state;
-
-	DBG("State changed %s: %s -> %s", device_get_path(dev->btd_dev),
-				str_state[old_state], str_state[state]);
-
-	for (l = headset_callbacks; l != NULL; l = l->next) {
-		struct headset_state_callback *cb = l->data;
-		cb->cb(dev, old_state, state, cb->user_data);
-	}
-}
-
-headset_state_t headset_get_state(struct audio_device *dev)
-{
-	struct headset *hs = dev->headset;
-
-	return hs->state;
-}
-
-int headset_get_channel(struct audio_device *dev)
-{
-	struct headset *hs = dev->headset;
-
-	return hs->rfcomm_ch;
-}
-
-gboolean headset_is_active(struct audio_device *dev)
-{
-	struct headset *hs = dev->headset;
-
-	if (hs->state != HEADSET_STATE_DISCONNECTED)
-		return TRUE;
-
-	return FALSE;
-}
-
-headset_lock_t headset_get_lock(struct audio_device *dev)
-{
-	struct headset *hs = dev->headset;
-
-	return hs->lock;
-}
-
-gboolean headset_lock(struct audio_device *dev, headset_lock_t lock)
-{
-	struct headset *hs = dev->headset;
-
-	if (hs->lock & lock)
-		return FALSE;
-
-	hs->lock |= lock;
-
-	return TRUE;
-}
-
-gboolean headset_unlock(struct audio_device *dev, headset_lock_t lock)
-{
-	struct headset *hs = dev->headset;
-
-	if (!(hs->lock & lock))
-		return FALSE;
-
-	hs->lock &= ~lock;
-
-	if (hs->lock)
-		return TRUE;
-
-	if (hs->state == HEADSET_STATE_PLAYING)
-		headset_set_state(dev, HEADSET_STATE_CONNECTED);
-
-	if (hs->auto_dc) {
-		if (hs->state == HEADSET_STATE_CONNECTED)
-			hs->dc_timer = g_timeout_add_seconds(DC_TIMEOUT,
-						(GSourceFunc) hs_dc_timeout,
-						dev);
-		else
-			headset_set_state(dev, HEADSET_STATE_DISCONNECTED);
-	}
-
-	return TRUE;
-}
-
-gboolean headset_suspend(struct audio_device *dev, void *data)
-{
-	return TRUE;
-}
-
-gboolean headset_play(struct audio_device *dev, void *data)
-{
-	return TRUE;
-}
-
-int headset_get_sco_fd(struct audio_device *dev)
-{
-	struct headset *hs = dev->headset;
-
-	if (!hs->sco)
-		return -1;
-
-	return g_io_channel_unix_get_fd(hs->sco);
-}
-
-gboolean headset_get_nrec(struct audio_device *dev)
-{
-	struct headset *hs = dev->headset;
-
-	if (!hs->slc)
-		return TRUE;
-
-	return hs->slc->nrec;
-}
-
-unsigned int headset_add_nrec_cb(struct audio_device *dev,
-					headset_nrec_cb cb, void *user_data)
-{
-	struct headset *hs = dev->headset;
-	struct headset_nrec_callback *nrec_cb;
-	static unsigned int id = 0;
-
-	nrec_cb = g_new(struct headset_nrec_callback, 1);
-	nrec_cb->cb = cb;
-	nrec_cb->user_data = user_data;
-	nrec_cb->id = ++id;
-
-	hs->nrec_cbs = g_slist_prepend(hs->nrec_cbs, nrec_cb);
-
-	return nrec_cb->id;
-}
-
-gboolean headset_remove_nrec_cb(struct audio_device *dev, unsigned int id)
-{
-	struct headset *hs = dev->headset;
-	GSList *l;
-
-	for (l = hs->nrec_cbs; l != NULL; l = l->next) {
-		struct headset_nrec_callback *cb = l->data;
-		if (cb && cb->id == id) {
-			hs->nrec_cbs = g_slist_remove(hs->nrec_cbs, cb);
-			g_free(cb);
-			return TRUE;
-		}
-	}
-
-	return FALSE;
-}
-
-gboolean headset_get_inband(struct audio_device *dev)
-{
-	struct headset *hs = dev->headset;
-
-	if (!hs->slc)
-		return TRUE;
-
-	return hs->slc->inband_ring;
-}
-
-gboolean headset_get_sco_hci(struct audio_device *dev)
-{
-	return sco_hci;
-}
-
-void headset_shutdown(struct audio_device *dev)
-{
-	struct pending_connect *p = dev->headset->pending;
-
-	if (p && p->msg)
-		error_connect_failed(p->msg, ECANCELED);
-
-	pending_connect_finalize(dev);
-	headset_set_state(dev, HEADSET_STATE_DISCONNECTED);
-}
-
-int telephony_event_ind(int index)
-{
-	if (!active_devices)
-		return -ENODEV;
-
-	if (!ag.er_ind) {
-		DBG("telephony_report_event called but events are disabled");
-		return -EINVAL;
-	}
-
-	send_foreach_headset(active_devices, hfp_cmp,
-				"\r\n+CIEV: %d,%d\r\n", index + 1,
-				ag.indicators[index].val);
-
-	return 0;
-}
-
-int telephony_response_and_hold_ind(int rh)
-{
-	if (!active_devices)
-		return -ENODEV;
-
-	ag.rh = rh;
-
-	/* If we aren't in any response and hold state don't send anything */
-	if (ag.rh < 0)
-		return 0;
-
-	send_foreach_headset(active_devices, hfp_cmp, "\r\n+BTRH: %d\r\n",
-				ag.rh);
-
-	return 0;
-}
-
-int telephony_incoming_call_ind(const char *number, int type)
-{
-	struct audio_device *dev;
-	struct headset *hs;
-	struct headset_slc *slc;
-
-	if (fast_connectable)
-		manager_set_fast_connectable(TRUE);
-
-	if (!active_devices)
-		return -ENODEV;
-
-	/* Get the latest connected device */
-	dev = active_devices->data;
-	hs = dev->headset;
-	slc = hs->slc;
-
-	if (ag.ring_timer) {
-		DBG("telephony_incoming_call_ind: already calling");
-		return -EBUSY;
-	}
-
-	/* With HSP 1.2 the RING messages should *not* be sent if inband
-	 * ringtone is being used */
-	if (!hs->hfp_active && slc->inband_ring)
-		return 0;
-
-	g_free(ag.number);
-	ag.number = g_strdup(number);
-	ag.number_type = type;
-
-	if (slc->inband_ring && hs->hfp_active &&
-					hs->state != HEADSET_STATE_PLAYING) {
-		slc->pending_ring = TRUE;
-		return 0;
-	}
-
-	ring_timer_cb(NULL);
-	ag.ring_timer = g_timeout_add_seconds(RING_INTERVAL, ring_timer_cb,
-						NULL);
-
-	return 0;
-}
-
-int telephony_calling_stopped_ind(void)
-{
-	struct audio_device *dev;
-
-	if (fast_connectable)
-		manager_set_fast_connectable(FALSE);
-
-	if (ag.ring_timer) {
-		g_source_remove(ag.ring_timer);
-		ag.ring_timer = 0;
-	}
-
-	if (!active_devices)
-		return 0;
-
-	/* In case SCO isn't fully up yet */
-	dev = active_devices->data;
-
-	if (!dev->headset->slc->pending_ring && !ag.ring_timer)
-		return -EINVAL;
-
-	dev->headset->slc->pending_ring = FALSE;
-
-	return 0;
-}
-
-int telephony_ready_ind(uint32_t features,
-			const struct indicator *indicators, int rh,
-			const char *chld)
-{
-	ag.telephony_ready = TRUE;
-	ag.features = features;
-	ag.indicators = indicators;
-	ag.rh = rh;
-	ag.chld = chld;
-
-	DBG("Telephony plugin initialized");
-
-	print_ag_features(ag.features);
-
-	return 0;
-}
-
-int telephony_deinit(void)
-{
-	g_free(ag.number);
-
-	memset(&ag, 0, sizeof(ag));
-
-	ag.er_mode = 3;
-	ag.rh = BTRH_NOT_SUPPORTED;
-
-	DBG("Telephony deinitialized");
-
-	return 0;
-}
-
-int telephony_list_current_call_ind(int idx, int dir, int status, int mode,
-					int mprty, const char *number,
-					int type)
-{
-	if (!active_devices)
-		return -ENODEV;
-
-	if (number && strlen(number) > 0)
-		send_foreach_headset(active_devices, hfp_cmp,
-				"\r\n+CLCC: %d,%d,%d,%d,%d,\"%s\",%d\r\n",
-				idx, dir, status, mode, mprty, number, type);
-	else
-		send_foreach_headset(active_devices, hfp_cmp,
-					"\r\n+CLCC: %d,%d,%d,%d,%d\r\n",
-					idx, dir, status, mode, mprty);
-
-	return 0;
-}
-
-int telephony_subscriber_number_ind(const char *number, int type, int service)
-{
-	if (!active_devices)
-		return -ENODEV;
-
-	send_foreach_headset(active_devices, hfp_cmp,
-				"\r\n+CNUM: ,%s,%d,,%d\r\n",
-				number, type, service);
-
-	return 0;
-}
-
-static int cwa_cmp(struct headset *hs)
-{
-	if (!hs->hfp_active)
-		return -1;
-
-	if (hs->slc->cwa_enabled)
-		return 0;
-	else
-		return -1;
-}
-
-int telephony_call_waiting_ind(const char *number, int type)
-{
-	if (!active_devices)
-		return -ENODEV;
-
-	send_foreach_headset(active_devices, cwa_cmp,
-				"\r\n+CCWA: \"%s\",%d\r\n",
-				number, type);
-
-	return 0;
-}
-
-unsigned int headset_add_state_cb(headset_state_cb cb, void *user_data)
-{
-	struct headset_state_callback *state_cb;
-	static unsigned int id = 0;
-
-	state_cb = g_new(struct headset_state_callback, 1);
-	state_cb->cb = cb;
-	state_cb->user_data = user_data;
-	state_cb->id = ++id;
-
-	headset_callbacks = g_slist_append(headset_callbacks, state_cb);
-
-	return state_cb->id;
-}
-
-gboolean headset_remove_state_cb(unsigned int id)
-{
-	GSList *l;
-
-	for (l = headset_callbacks; l != NULL; l = l->next) {
-		struct headset_state_callback *cb = l->data;
-		if (cb && cb->id == id) {
-			headset_callbacks = g_slist_remove(headset_callbacks, cb);
-			g_free(cb);
-			return TRUE;
-		}
-	}
-
-	return FALSE;
-}
diff --git a/audio/headset.h b/audio/headset.h
deleted file mode 100644
index 736e4fe..0000000
--- a/audio/headset.h
+++ /dev/null
@@ -1,112 +0,0 @@
-/*
- *
- *  BlueZ - Bluetooth protocol stack for Linux
- *
- *  Copyright (C) 2006-2010  Nokia Corporation
- *  Copyright (C) 2004-2010  Marcel Holtmann <marcel@holtmann.org>
- *
- *
- *  This program is free software; you can redistribute it and/or modify
- *  it under the terms of the GNU General Public License as published by
- *  the Free Software Foundation; either version 2 of the License, or
- *  (at your option) any later version.
- *
- *  This program is distributed in the hope that it will be useful,
- *  but WITHOUT ANY WARRANTY; without even the implied warranty of
- *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
- *  GNU General Public License for more details.
- *
- *  You should have received a copy of the GNU General Public License
- *  along with this program; if not, write to the Free Software
- *  Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
- *
- */
-
-#define AUDIO_HEADSET_INTERFACE "org.bluez.Headset"
-
-#define DEFAULT_HS_AG_CHANNEL 12
-#define DEFAULT_HF_AG_CHANNEL 13
-
-typedef enum {
-	HEADSET_STATE_DISCONNECTED,
-	HEADSET_STATE_CONNECTING,
-	HEADSET_STATE_CONNECTED,
-	HEADSET_STATE_PLAY_IN_PROGRESS,
-	HEADSET_STATE_PLAYING
-} headset_state_t;
-
-typedef enum {
-	HEADSET_LOCK_READ = 1,
-	HEADSET_LOCK_WRITE = 1 << 1,
-} headset_lock_t;
-
-typedef void (*headset_state_cb) (struct audio_device *dev,
-					headset_state_t old_state,
-					headset_state_t new_state,
-					void *user_data);
-typedef void (*headset_nrec_cb) (struct audio_device *dev,
-					gboolean nrec,
-					void *user_data);
-
-unsigned int headset_add_state_cb(headset_state_cb cb, void *user_data);
-gboolean headset_remove_state_cb(unsigned int id);
-
-typedef void (*headset_stream_cb_t) (struct audio_device *dev, void *user_data);
-
-void headset_connect_cb(GIOChannel *chan, GError *err, gpointer user_data);
-
-GIOChannel *headset_get_rfcomm(struct audio_device *dev);
-
-struct headset *headset_init(struct audio_device *dev, GSList *uuids,
-							gboolean hfp_enabled);
-
-void headset_unregister(struct audio_device *dev);
-
-uint32_t headset_config_init(GKeyFile *config);
-
-void headset_update(struct audio_device *dev, struct headset *headset,
-								GSList *uuids);
-
-unsigned int headset_config_stream(struct audio_device *dev,
-					gboolean auto_dc,
-					headset_stream_cb_t cb,
-					void *user_data);
-unsigned int headset_request_stream(struct audio_device *dev,
-					headset_stream_cb_t cb,
-					void *user_data);
-unsigned int headset_suspend_stream(struct audio_device *dev,
-					headset_stream_cb_t cb,
-					void *user_data);
-gboolean headset_cancel_stream(struct audio_device *dev, unsigned int id);
-
-gboolean headset_get_hfp_active(struct audio_device *dev);
-void headset_set_hfp_active(struct audio_device *dev, gboolean active);
-
-gboolean headset_get_rfcomm_initiator(struct audio_device *dev);
-void headset_set_rfcomm_initiator(struct audio_device *dev,
-							gboolean initiator);
-
-int headset_connect_rfcomm(struct audio_device *dev, GIOChannel *chan);
-int headset_connect_sco(struct audio_device *dev, GIOChannel *io);
-
-headset_state_t headset_get_state(struct audio_device *dev);
-void headset_set_state(struct audio_device *dev, headset_state_t state);
-
-int headset_get_channel(struct audio_device *dev);
-
-int headset_get_sco_fd(struct audio_device *dev);
-gboolean headset_get_nrec(struct audio_device *dev);
-unsigned int headset_add_nrec_cb(struct audio_device *dev,
-					headset_nrec_cb cb, void *user_data);
-gboolean headset_remove_nrec_cb(struct audio_device *dev, unsigned int id);
-gboolean headset_get_inband(struct audio_device *dev);
-gboolean headset_get_sco_hci(struct audio_device *dev);
-
-gboolean headset_is_active(struct audio_device *dev);
-
-headset_lock_t headset_get_lock(struct audio_device *dev);
-gboolean headset_lock(struct audio_device *dev, headset_lock_t lock);
-gboolean headset_unlock(struct audio_device *dev, headset_lock_t lock);
-gboolean headset_suspend(struct audio_device *dev, void *data);
-gboolean headset_play(struct audio_device *dev, void *data);
-void headset_shutdown(struct audio_device *dev);
-- 
1.7.11.7


^ permalink raw reply related

* [PATCH BlueZ 10/13] audio: Remove code HFP and HS gateway role
From: Luiz Augusto von Dentz @ 2012-11-13 13:21 UTC (permalink / raw)
  To: linux-bluetooth
In-Reply-To: <1352812880-7306-1-git-send-email-luiz.dentz@gmail.com>

From: Luiz Augusto von Dentz <luiz.von.dentz@intel.com>

This is to be replaced with external profile support.
---
 audio/device.c    |   7 --
 audio/main.c      |  72 +-------------
 audio/manager.c   | 288 +-----------------------------------------------------
 audio/manager.h   |   3 +-
 audio/media.c     |  71 +-------------
 audio/transport.c | 165 -------------------------------
 6 files changed, 8 insertions(+), 598 deletions(-)

diff --git a/audio/device.c b/audio/device.c
index aaa666d..df57d81 100644
--- a/audio/device.c
+++ b/audio/device.c
@@ -53,7 +53,6 @@
 #include "control.h"
 #include "avctp.h"
 #include "avrcp.h"
-#include "gateway.h"
 #include "sink.h"
 #include "source.h"
 
@@ -500,9 +499,6 @@ gboolean audio_device_is_active(struct audio_device *dev,
 	else if (!strcmp(interface, AUDIO_CONTROL_INTERFACE) && dev->control &&
 				control_is_active(dev))
 		return TRUE;
-	else if (!strcmp(interface, AUDIO_GATEWAY_INTERFACE) && dev->gateway &&
-				gateway_is_active(dev))
-		return TRUE;
 
 	return FALSE;
 }
@@ -514,9 +510,6 @@ void audio_device_unregister(struct audio_device *device)
 		device->hs_preauth_id = 0;
 	}
 
-	if (device->gateway)
-		gateway_unregister(device);
-
 	if (device->sink)
 		sink_unregister(device);
 
diff --git a/audio/main.c b/audio/main.c
index a423b79..ce060fc 100644
--- a/audio/main.c
+++ b/audio/main.c
@@ -43,7 +43,6 @@
 #include "log.h"
 #include "device.h"
 #include "manager.h"
-#include "gateway.h"
 
 static GIOChannel *sco_server = NULL;
 
@@ -66,83 +65,18 @@ static GKeyFile *load_config_file(const char *file)
 	return keyfile;
 }
 
-static void sco_server_cb(GIOChannel *chan, GError *err, gpointer data)
-{
-	int sk;
-	struct audio_device *device;
-	char addr[18];
-	bdaddr_t src, dst;
-
-	if (err) {
-		error("sco_server_cb: %s", err->message);
-		return;
-	}
-
-	bt_io_get(chan, &err,
-			BT_IO_OPT_SOURCE_BDADDR, &src,
-			BT_IO_OPT_DEST_BDADDR, &dst,
-			BT_IO_OPT_DEST, addr,
-			BT_IO_OPT_INVALID);
-	if (err) {
-		error("bt_io_get: %s", err->message);
-		goto drop;
-	}
-
-	device = manager_find_device(NULL, &src, &dst,
-						AUDIO_GATEWAY_INTERFACE,
-						FALSE);
-	if (!device)
-		goto drop;
-
-	if (device->gateway) {
-		if (!gateway_is_connected(device)) {
-			DBG("Refusing SCO from non-connected AG");
-			goto drop;
-		}
-
-		if (gateway_connect_sco(device, chan) < 0)
-			goto drop;
-	} else
-		goto drop;
-
-	sk = g_io_channel_unix_get_fd(chan);
-	fcntl(sk, F_SETFL, 0);
-
-	DBG("Accepted SCO connection from %s", addr);
-
-	return;
-
-drop:
-	g_io_channel_shutdown(chan, TRUE, NULL);
-}
-
 static int audio_init(void)
 {
 	GKeyFile *config;
-	gboolean enable_sco;
 
 	config = load_config_file(CONFIGDIR "/audio.conf");
 
-	if (audio_manager_init(config, &enable_sco) < 0)
-		goto failed;
-
-	if (!enable_sco)
-		return 0;
-
-	sco_server = bt_io_listen(sco_server_cb, NULL, NULL,
-					NULL, NULL,
-					BT_IO_OPT_INVALID);
-	if (!sco_server) {
-		error("Unable to start SCO server socket");
-		goto failed;
+	if (audio_manager_init(config) < 0) {
+		audio_manager_exit();
+		return -EIO;
 	}
 
 	return 0;
-
-failed:
-	audio_manager_exit();
-
-	return -EIO;
 }
 
 static void audio_exit(void)
diff --git a/audio/manager.c b/audio/manager.c
index 0960d28..f59a2f3 100644
--- a/audio/manager.c
+++ b/audio/manager.c
@@ -61,7 +61,6 @@
 #include "avdtp.h"
 #include "media.h"
 #include "a2dp.h"
-#include "gateway.h"
 #include "sink.h"
 #include "source.h"
 #include "avrcp.h"
@@ -88,7 +87,6 @@ static GSList *adapters = NULL;
 static GSList *devices = NULL;
 
 static struct enabled_interfaces enabled = {
-	.gateway	= FALSE,
 	.sink		= TRUE,
 	.source		= FALSE,
 	.control	= TRUE,
@@ -107,197 +105,6 @@ static struct audio_adapter *find_adapter(GSList *list,
 	return NULL;
 }
 
-static sdp_record_t *hfp_hs_record(uint8_t ch)
-{
-	sdp_list_t *svclass_id, *pfseq, *apseq, *root;
-	uuid_t root_uuid, svclass_uuid, ga_svclass_uuid;
-	uuid_t l2cap_uuid, rfcomm_uuid;
-	sdp_profile_desc_t profile;
-	sdp_record_t *record;
-	sdp_list_t *aproto, *proto[2];
-	sdp_data_t *channel;
-
-	record = sdp_record_alloc();
-	if (!record)
-		return NULL;
-
-	sdp_uuid16_create(&root_uuid, PUBLIC_BROWSE_GROUP);
-	root = sdp_list_append(0, &root_uuid);
-	sdp_set_browse_groups(record, root);
-
-	sdp_uuid16_create(&svclass_uuid, HANDSFREE_SVCLASS_ID);
-	svclass_id = sdp_list_append(0, &svclass_uuid);
-	sdp_uuid16_create(&ga_svclass_uuid, GENERIC_AUDIO_SVCLASS_ID);
-	svclass_id = sdp_list_append(svclass_id, &ga_svclass_uuid);
-	sdp_set_service_classes(record, svclass_id);
-
-	sdp_uuid16_create(&profile.uuid, HANDSFREE_PROFILE_ID);
-	profile.version = 0x0105;
-	pfseq = sdp_list_append(0, &profile);
-	sdp_set_profile_descs(record, pfseq);
-
-	sdp_uuid16_create(&l2cap_uuid, L2CAP_UUID);
-	proto[0] = sdp_list_append(0, &l2cap_uuid);
-	apseq = sdp_list_append(0, proto[0]);
-
-	sdp_uuid16_create(&rfcomm_uuid, RFCOMM_UUID);
-	proto[1] = sdp_list_append(0, &rfcomm_uuid);
-	channel = sdp_data_alloc(SDP_UINT8, &ch);
-	proto[1] = sdp_list_append(proto[1], channel);
-	apseq = sdp_list_append(apseq, proto[1]);
-
-	aproto = sdp_list_append(0, apseq);
-	sdp_set_access_protos(record, aproto);
-
-	sdp_set_info_attr(record, "Hands-Free", 0, 0);
-
-	sdp_data_free(channel);
-	sdp_list_free(proto[0], 0);
-	sdp_list_free(proto[1], 0);
-	sdp_list_free(apseq, 0);
-	sdp_list_free(pfseq, 0);
-	sdp_list_free(aproto, 0);
-	sdp_list_free(root, 0);
-	sdp_list_free(svclass_id, 0);
-
-	return record;
-}
-
-static void gateway_auth_cb(DBusError *derr, void *user_data)
-{
-	struct audio_device *device = user_data;
-
-	if (derr && dbus_error_is_set(derr)) {
-		error("Access denied: %s", derr->message);
-		gateway_set_state(device, GATEWAY_STATE_DISCONNECTED);
-	} else {
-		char ag_address[18];
-
-		ba2str(&device->dst, ag_address);
-		DBG("Accepted AG connection from %s for %s",
-			ag_address, device_get_path(device->btd_dev));
-
-		gateway_start_service(device);
-	}
-}
-
-static void hf_io_cb(GIOChannel *chan, gpointer data)
-{
-	bdaddr_t src, dst;
-	GError *err = NULL;
-	uint8_t ch;
-	const char *server_uuid, *remote_uuid;
-	struct audio_device *device;
-	guint auth_id;
-
-	bt_io_get(chan, &err,
-			BT_IO_OPT_SOURCE_BDADDR, &src,
-			BT_IO_OPT_DEST_BDADDR, &dst,
-			BT_IO_OPT_CHANNEL, &ch,
-			BT_IO_OPT_INVALID);
-
-	if (err) {
-		error("%s", err->message);
-		g_error_free(err);
-		return;
-	}
-
-	server_uuid = HFP_HS_UUID;
-	remote_uuid = HFP_AG_UUID;
-
-	device = manager_get_device(&src, &dst, TRUE);
-	if (!device)
-		goto drop;
-
-	if (!device->gateway) {
-		btd_device_add_uuid(device->btd_dev, remote_uuid);
-		if (!device->gateway)
-			goto drop;
-	}
-
-	if (gateway_is_active(device)) {
-		DBG("Refusing new connection since one already exists");
-		goto drop;
-	}
-
-	if (gateway_connect_rfcomm(device, chan) < 0) {
-		error("Allocating new GIOChannel failed!");
-		goto drop;
-	}
-
-	auth_id = btd_request_authorization(&device->src, &device->dst,
-						server_uuid, gateway_auth_cb,
-						device);
-	if (auth_id == 0) {
-		DBG("Authorization denied");
-		gateway_set_state(device, GATEWAY_STATE_DISCONNECTED);
-	}
-
-	return;
-
-drop:
-	g_io_channel_shutdown(chan, TRUE, NULL);
-}
-
-static int gateway_server_init(struct audio_adapter *adapter)
-{
-	uint8_t chan = DEFAULT_HFP_HS_CHANNEL;
-	sdp_record_t *record;
-	gboolean master = TRUE;
-	GError *err = NULL;
-	GIOChannel *io;
-	const bdaddr_t *src;
-
-	if (config) {
-		gboolean tmp;
-
-		tmp = g_key_file_get_boolean(config, "General", "Master",
-						&err);
-		if (err) {
-			DBG("audio.conf: %s", err->message);
-			g_clear_error(&err);
-		} else
-			master = tmp;
-	}
-
-	src = adapter_get_address(adapter->btd_adapter);
-
-	io = bt_io_listen(NULL, hf_io_cb, adapter, NULL, &err,
-				BT_IO_OPT_SOURCE_BDADDR, src,
-				BT_IO_OPT_CHANNEL, chan,
-				BT_IO_OPT_SEC_LEVEL, BT_IO_SEC_MEDIUM,
-				BT_IO_OPT_MASTER, master,
-				BT_IO_OPT_INVALID);
-	if (!io) {
-		error("%s", err->message);
-		g_error_free(err);
-		return -1;
-	}
-
-	adapter->hfp_hs_server = io;
-	record = hfp_hs_record(chan);
-	if (!record) {
-		error("Unable to allocate new service record");
-		goto failed;
-	}
-
-	if (add_record_to_server(src, record) < 0) {
-		error("Unable to register HFP HS service record");
-		sdp_record_free(record);
-		goto failed;
-	}
-
-	adapter->hfp_hs_record_id = record->handle;
-
-	return 0;
-
-failed:
-	g_io_channel_shutdown(adapter->hfp_hs_server, TRUE, NULL);
-	g_io_channel_unref(adapter->hfp_hs_server);
-	adapter->hfp_hs_server = NULL;
-	return -1;
-}
-
 static struct audio_device *get_audio_dev(struct btd_device *device)
 {
 	struct btd_adapter *adapter = device_get_adapter(device);
@@ -321,25 +128,6 @@ static void audio_remove(struct btd_profile *p, struct btd_device *device)
 	audio_device_unregister(dev);
 }
 
-static int ag_probe(struct btd_profile *p, struct btd_device *device,
-								GSList *uuids)
-{
-	struct audio_device *audio_dev;
-
-	audio_dev = get_audio_dev(device);
-	if (!audio_dev) {
-		DBG("unable to get a device object");
-		return -1;
-	}
-
-	if (audio_dev->gateway)
-		return -EALREADY;
-
-	audio_dev->gateway = gateway_init(audio_dev);
-
-	return 0;
-}
-
 static int a2dp_probe(struct btd_profile *p, struct btd_device *device,
 								GSList *uuids)
 {
@@ -431,49 +219,6 @@ static struct audio_adapter *audio_adapter_get(struct btd_adapter *adapter)
 	return adp;
 }
 
-static int gateway_server_probe(struct btd_profile *p,
-						struct btd_adapter *adapter)
-{
-	struct audio_adapter *adp;
-	int err;
-
-	adp = audio_adapter_get(adapter);
-	if (!adp)
-		return -EINVAL;
-
-	err = gateway_server_init(adp);
-	if (err < 0)
-		audio_adapter_unref(adp);
-
-	return err;
-}
-
-static void gateway_server_remove(struct btd_profile *p,
-						struct btd_adapter *adapter)
-{
-	struct audio_adapter *adp;
-	const gchar *path = adapter_get_path(adapter);
-
-	DBG("path %s", path);
-
-	adp = find_adapter(adapters, adapter);
-	if (!adp)
-		return;
-
-	if (adp->hfp_hs_record_id) {
-		remove_record_from_server(adp->hfp_hs_record_id);
-		adp->hfp_hs_record_id = 0;
-	}
-
-	if (adp->hfp_hs_server) {
-		g_io_channel_shutdown(adp->hfp_hs_server, TRUE, NULL);
-		g_io_channel_unref(adp->hfp_hs_server);
-		adp->hfp_hs_server = NULL;
-	}
-
-	audio_adapter_unref(adp);
-}
-
 static int a2dp_server_probe(struct btd_profile *p,
 						struct btd_adapter *adapter)
 {
@@ -580,17 +325,6 @@ static void media_server_remove(struct btd_adapter *adapter)
 	audio_adapter_unref(adp);
 }
 
-static struct btd_profile gateway_profile = {
-	.name		= "audio-gateway",
-
-	.remote_uuids	= BTD_UUIDS(HSP_AG_UUID, HFP_AG_UUID),
-	.device_probe	= ag_probe,
-	.device_remove	= audio_remove,
-
-	.adapter_probe	= gateway_server_probe,
-	.adapter_remove = gateway_server_remove,
-};
-
 static struct btd_profile a2dp_profile = {
 	.name		= "audio-a2dp",
 
@@ -620,7 +354,7 @@ static struct btd_adapter_driver media_driver = {
 	.remove	= media_server_remove,
 };
 
-int audio_manager_init(GKeyFile *conf, gboolean *enable_sco)
+int audio_manager_init(GKeyFile *conf)
 {
 	char **list;
 	int i;
@@ -635,9 +369,7 @@ int audio_manager_init(GKeyFile *conf, gboolean *enable_sco)
 	list = g_key_file_get_string_list(config, "General", "Enable",
 						NULL, NULL);
 	for (i = 0; list && list[i] != NULL; i++) {
-		if (g_str_equal(list[i], "Gateway"))
-			enabled.gateway = TRUE;
-		else if (g_str_equal(list[i], "Sink"))
+		if (g_str_equal(list[i], "Sink"))
 			enabled.sink = TRUE;
 		else if (g_str_equal(list[i], "Source"))
 			enabled.source = TRUE;
@@ -649,9 +381,7 @@ int audio_manager_init(GKeyFile *conf, gboolean *enable_sco)
 	list = g_key_file_get_string_list(config, "General", "Disable",
 						NULL, NULL);
 	for (i = 0; list && list[i] != NULL; i++) {
-		if (g_str_equal(list[i], "Gateway"))
-			enabled.gateway = FALSE;
-		else if (g_str_equal(list[i], "Sink"))
+		if (g_str_equal(list[i], "Sink"))
 			enabled.sink = FALSE;
 		else if (g_str_equal(list[i], "Source"))
 			enabled.source = FALSE;
@@ -677,9 +407,6 @@ int audio_manager_init(GKeyFile *conf, gboolean *enable_sco)
 		max_connected_headsets = i;
 
 proceed:
-	if (enabled.gateway)
-		btd_profile_register(&gateway_profile);
-
 	if (enabled.source || enabled.sink)
 		btd_profile_register(&a2dp_profile);
 
@@ -688,8 +415,6 @@ proceed:
 
 	btd_register_adapter_driver(&media_driver);
 
-	*enable_sco = enabled.gateway;
-
 	return 0;
 }
 
@@ -700,9 +425,6 @@ void audio_manager_exit(void)
 		config = NULL;
 	}
 
-	if (enabled.gateway)
-		btd_profile_unregister(&gateway_profile);
-
 	if (enabled.source || enabled.sink)
 		btd_profile_unregister(&a2dp_profile);
 
@@ -734,10 +456,6 @@ GSList *manager_find_devices(const char *path,
 		if ((dst && bacmp(dst, BDADDR_ANY)) && bacmp(&dev->dst, dst))
 			continue;
 
-		if (interface && !strcmp(AUDIO_GATEWAY_INTERFACE, interface)
-				&& !dev->gateway)
-			continue;
-
 		if (interface && !strcmp(AUDIO_SINK_INTERFACE, interface)
 				&& !dev->sink)
 			continue;
diff --git a/audio/manager.h b/audio/manager.h
index d3b5692..5691063 100644
--- a/audio/manager.h
+++ b/audio/manager.h
@@ -23,14 +23,13 @@
  */
 
 struct enabled_interfaces {
-	gboolean gateway;
 	gboolean sink;
 	gboolean source;
 	gboolean control;
 	gboolean media_player;
 };
 
-int audio_manager_init(GKeyFile *config, gboolean *enable_sco);
+int audio_manager_init(GKeyFile *config);
 void audio_manager_exit(void);
 
 struct audio_device *manager_find_device(const char *path,
diff --git a/audio/media.c b/audio/media.c
index ea0b44e..65037fe 100644
--- a/audio/media.c
+++ b/audio/media.c
@@ -46,7 +46,6 @@
 #include "transport.h"
 #include "a2dp.h"
 #include "avrcp.h"
-#include "gateway.h"
 #include "manager.h"
 
 #define MEDIA_INTERFACE "org.bluez.Media"
@@ -140,9 +139,6 @@ static void media_endpoint_destroy(struct media_endpoint *endpoint)
 {
 	DBG("sender=%s path=%s", endpoint->sender, endpoint->path);
 
-	if (endpoint->ag_watch)
-		gateway_remove_state_cb(endpoint->ag_watch);
-
 	media_endpoint_cancel_all(endpoint);
 
 	g_slist_free_full(endpoint->transports,
@@ -550,49 +546,6 @@ static void a2dp_destroy_endpoint(void *user_data)
 	release_endpoint(endpoint);
 }
 
-static void gateway_setconf_cb(struct media_endpoint *endpoint, void *ret,
-						int size, void *user_data)
-{
-	struct audio_device *dev = user_data;
-
-	if (ret != NULL)
-		return;
-
-	gateway_set_state(dev, GATEWAY_STATE_DISCONNECTED);
-}
-
-static void gateway_state_changed(struct audio_device *dev,
-					gateway_state_t old_state,
-					gateway_state_t new_state,
-					void *user_data)
-{
-	struct media_endpoint *endpoint = user_data;
-	struct media_transport *transport;
-
-	DBG("");
-
-	if (bacmp(&endpoint->adapter->src, &dev->src) != 0)
-		return;
-
-	switch (new_state) {
-	case GATEWAY_STATE_DISCONNECTED:
-		transport = find_device_transport(endpoint, dev);
-		if (transport != NULL) {
-			DBG("Clear endpoint %p", endpoint);
-			clear_configuration(endpoint, transport);
-		}
-		break;
-	case GATEWAY_STATE_CONNECTING:
-		set_configuration(endpoint, dev, NULL, 0,
-					gateway_setconf_cb, dev, NULL);
-		break;
-	case GATEWAY_STATE_CONNECTED:
-		break;
-	case GATEWAY_STATE_PLAYING:
-		break;
-	}
-}
-
 static gboolean endpoint_init_a2dp_source(struct media_endpoint *endpoint,
 						gboolean delay_reporting,
 						int *err)
@@ -621,28 +574,6 @@ static gboolean endpoint_init_a2dp_sink(struct media_endpoint *endpoint,
 	return TRUE;
 }
 
-static gboolean endpoint_init_hs(struct media_endpoint *endpoint, int *err)
-{
-	GSList *list;
-	GSList *l;
-
-	endpoint->ag_watch = gateway_add_state_cb(gateway_state_changed,
-								endpoint);
-	list = manager_find_devices(NULL, &endpoint->adapter->src, BDADDR_ANY,
-						AUDIO_GATEWAY_INTERFACE, TRUE);
-
-	for (l = list; l != NULL; l = l->next) {
-		struct audio_device *dev = l->data;
-
-		set_configuration(endpoint, dev, NULL, 0,
-						gateway_setconf_cb, dev, NULL);
-	}
-
-	g_slist_free(list);
-
-	return TRUE;
-}
-
 static struct media_endpoint *media_endpoint_create(struct media_adapter *adapter,
 						const char *sender,
 						const char *path,
@@ -681,7 +612,7 @@ static struct media_endpoint *media_endpoint_create(struct media_adapter *adapte
 		succeeded = TRUE;
 	else if (strcasecmp(uuid, HFP_HS_UUID) == 0 ||
 					strcasecmp(uuid, HSP_HS_UUID) == 0)
-		succeeded = endpoint_init_hs(endpoint, err);
+		succeeded = TRUE;
 	else {
 		succeeded = FALSE;
 
diff --git a/audio/transport.c b/audio/transport.c
index 74562ea..994c423 100644
--- a/audio/transport.c
+++ b/audio/transport.c
@@ -44,7 +44,6 @@
 #include "media.h"
 #include "transport.h"
 #include "a2dp.h"
-#include "gateway.h"
 #include "sink.h"
 #include "source.h"
 #include "avrcp.h"
@@ -109,7 +108,6 @@ struct media_transport {
 	transport_lock_t	lock;
 	transport_state_t	state;
 	guint			hs_watch;
-	guint			ag_watch;
 	guint			source_watch;
 	guint			sink_watch;
 	guint			(*resume) (struct media_transport *transport,
@@ -211,9 +209,6 @@ void media_transport_destroy(struct media_transport *transport)
 {
 	char *path;
 
-	if (transport->ag_watch)
-		gateway_remove_state_cb(transport->ag_watch);
-
 	if (transport->sink_watch)
 		sink_remove_state_cb(transport->sink_watch);
 
@@ -461,127 +456,6 @@ static void cancel_a2dp(struct media_transport *transport, guint id)
 	a2dp_cancel(transport->device, id);
 }
 
-static void gateway_resume_complete(struct audio_device *dev, GError *err,
-							void *user_data)
-{
-	struct media_owner *owner = user_data;
-	struct media_request *req = owner->pending;
-	struct media_transport *transport = owner->transport;
-	int fd;
-	uint16_t imtu, omtu;
-	gboolean ret;
-
-	req->id = 0;
-
-	if (dev == NULL)
-		goto fail;
-
-	if (err) {
-		error("Failed to resume gateway: error %s", err->message);
-		goto fail;
-	}
-
-	fd = gateway_get_sco_fd(dev);
-	if (fd < 0)
-		goto fail;
-
-	imtu = 48;
-	omtu = 48;
-
-	media_transport_set_fd(transport, fd, imtu, omtu);
-
-	if ((owner->lock & TRANSPORT_LOCK_READ) == 0)
-		imtu = 0;
-
-	if ((owner->lock & TRANSPORT_LOCK_WRITE) == 0)
-		omtu = 0;
-
-	ret = g_dbus_send_reply(btd_get_dbus_connection(), req->msg,
-						DBUS_TYPE_UNIX_FD, &fd,
-						DBUS_TYPE_UINT16, &imtu,
-						DBUS_TYPE_UINT16, &omtu,
-						DBUS_TYPE_INVALID);
-	if (ret == FALSE)
-		goto fail;
-
-	media_owner_remove(owner);
-
-	transport_set_state(transport, TRANSPORT_STATE_ACTIVE);
-
-	return;
-
-fail:
-	media_transport_remove(transport, owner);
-}
-
-static guint resume_gateway(struct media_transport *transport,
-				struct media_owner *owner)
-{
-	struct audio_device *device = transport->device;
-
-	if (state_in_use(transport->state))
-		goto done;
-
-	if (gateway_lock(device, GATEWAY_LOCK_READ |
-						GATEWAY_LOCK_WRITE) == FALSE)
-		return 0;
-
-	if (transport->state == TRANSPORT_STATE_IDLE)
-		transport_set_state(transport, TRANSPORT_STATE_REQUESTING);
-
-done:
-	return gateway_request_stream(device, gateway_resume_complete,
-					owner);
-}
-
-static gboolean gateway_suspend_complete(gpointer user_data)
-{
-	struct media_owner *owner = user_data;
-	struct media_transport *transport = owner->transport;
-	struct audio_device *device = transport->device;
-
-	/* Release always succeeds */
-	if (owner->pending) {
-		owner->pending->id = 0;
-		media_request_reply(owner->pending, 0);
-		media_owner_remove(owner);
-	}
-
-	gateway_unlock(device, GATEWAY_LOCK_READ | GATEWAY_LOCK_WRITE);
-	transport_set_state(transport, TRANSPORT_STATE_IDLE);
-	media_transport_remove(transport, owner);
-	return FALSE;
-}
-
-static guint suspend_gateway(struct media_transport *transport,
-						struct media_owner *owner)
-{
-	struct audio_device *device = transport->device;
-	static int id = 1;
-
-	if (!owner) {
-		gateway_state_t state = gateway_get_state(device);
-
-		gateway_unlock(device, GATEWAY_LOCK_READ | GATEWAY_LOCK_WRITE);
-
-		if (state == GATEWAY_STATE_PLAYING)
-			transport_set_state(transport, TRANSPORT_STATE_PENDING);
-		else
-			transport_set_state(transport, TRANSPORT_STATE_IDLE);
-
-		return 0;
-	}
-
-	gateway_suspend_stream(device);
-	g_idle_add(gateway_suspend_complete, owner);
-	return id++;
-}
-
-static void cancel_gateway(struct media_transport *transport, guint id)
-{
-	gateway_cancel_stream(transport->device, id);
-}
-
 static void media_owner_exit(DBusConnection *connection, void *user_data)
 {
 	struct media_owner *owner = user_data;
@@ -806,13 +680,6 @@ static int set_property_a2dp(struct media_transport *transport,
 	return -EINVAL;
 }
 
-static int set_property_gateway(struct media_transport *transport,
-						const char *property,
-						DBusMessageIter *value)
-{
-	return -EINVAL;
-}
-
 static DBusMessage *set_property(DBusConnection *conn, DBusMessage *msg,
 								void *data)
 {
@@ -871,12 +738,6 @@ static void get_properties_a2dp(struct media_transport *transport,
 							&a2dp->volume);
 }
 
-static void get_properties_gateway(struct media_transport *transport,
-						DBusMessageIter *dict)
-{
-	/* None */
-}
-
 void transport_get_properties(struct media_transport *transport,
 							DBusMessageIter *iter)
 {
@@ -1009,22 +870,6 @@ static void transport_update_playing(struct media_transport *transport,
 		transport_set_state(transport, TRANSPORT_STATE_PENDING);
 }
 
-static void gateway_state_changed(struct audio_device *dev,
-						gateway_state_t old_state,
-						gateway_state_t new_state,
-						void *user_data)
-{
-	struct media_transport *transport = user_data;
-
-	if (dev != transport->device)
-		return;
-
-	if (new_state == GATEWAY_STATE_PLAYING)
-		transport_update_playing(transport, TRUE);
-	else
-		transport_update_playing(transport, FALSE);
-}
-
 static void sink_state_changed(struct audio_device *dev,
 						sink_state_t old_state,
 						sink_state_t new_state,
@@ -1100,16 +945,6 @@ struct media_transport *media_transport_create(struct media_endpoint *endpoint,
 			transport->source_watch = source_add_state_cb(
 							source_state_changed,
 							transport);
-	} else if (strcasecmp(uuid, HFP_HS_UUID) == 0 ||
-			strcasecmp(uuid, HSP_HS_UUID) == 0) {
-		transport->resume = resume_gateway;
-		transport->suspend = suspend_gateway;
-		transport->cancel = cancel_gateway;
-		transport->get_properties = get_properties_gateway;
-		transport->set_property = set_property_gateway;
-		transport->ag_watch = gateway_add_state_cb(
-							gateway_state_changed,
-							transport);
 	} else
 		goto fail;
 
-- 
1.7.11.7


^ permalink raw reply related

* [PATCH BlueZ 11/13] build: Remove gateway.c and gateway.h
From: Luiz Augusto von Dentz @ 2012-11-13 13:21 UTC (permalink / raw)
  To: linux-bluetooth
In-Reply-To: <1352812880-7306-1-git-send-email-luiz.dentz@gmail.com>

From: Luiz Augusto von Dentz <luiz.von.dentz@intel.com>

---
 Makefile.am     |    1 -
 audio/device.h  |    1 -
 audio/gateway.c | 1048 -------------------------------------------------------
 audio/gateway.h |   75 ----
 4 files changed, 1125 deletions(-)
 delete mode 100644 audio/gateway.c
 delete mode 100644 audio/gateway.h

diff --git a/Makefile.am b/Makefile.am
index 7f8ff26..84ae237 100644
--- a/Makefile.am
+++ b/Makefile.am
@@ -107,7 +107,6 @@ if AUDIOPLUGIN
 builtin_modules += audio
 builtin_sources += audio/main.c \
 			audio/manager.h audio/manager.c \
-			audio/gateway.h audio/gateway.c \
 			audio/control.h audio/control.c \
 			audio/avctp.h audio/avctp.c \
 			audio/avrcp.h audio/avrcp.c \
diff --git a/audio/device.h b/audio/device.h
index 89916be..f0d178d 100644
--- a/audio/device.h
+++ b/audio/device.h
@@ -38,7 +38,6 @@ struct audio_device {
 
 	gboolean auto_connect;
 
-	struct gateway *gateway;
 	struct sink *sink;
 	struct source *source;
 	struct control *control;
diff --git a/audio/gateway.c b/audio/gateway.c
deleted file mode 100644
index 1b1164c..0000000
--- a/audio/gateway.c
+++ /dev/null
@@ -1,1048 +0,0 @@
-/*
- *
- *  BlueZ - Bluetooth protocol stack for Linux
- *
- *  Copyright (C) 2006-2010  Nokia Corporation
- *  Copyright (C) 2004-2010  Marcel Holtmann <marcel@holtmann.org>
- *  Copyright (C) 2008-2009  Leonid Movshovich <event.riga@gmail.org>
- *  Copyright (C) 2010  ProFUSION embedded systems
- *
- *
- *  This program is free software; you can redistribute it and/or modify
- *  it under the terms of the GNU General Public License as published by
- *  the Free Software Foundation; either version 2 of the License, or
- *  (at your option) any later version.
- *
- *  This program is distributed in the hope that it will be useful,
- *  but WITHOUT ANY WARRANTY; without even the implied warranty of
- *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
- *  GNU General Public License for more details.
- *
- *  You should have received a copy of the GNU General Public License
- *  along with this program; if not, write to the Free Software
- *  Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
- *
- */
-
-#ifdef HAVE_CONFIG_H
-#include <config.h>
-#endif
-
-#include <stdint.h>
-#include <stdlib.h>
-#include <string.h>
-#include <fcntl.h>
-#include <errno.h>
-
-#include <glib.h>
-#include <dbus/dbus.h>
-#include <gdbus.h>
-
-#include <bluetooth/bluetooth.h>
-#include <bluetooth/sdp.h>
-#include <bluetooth/sdp_lib.h>
-
-#include "../src/adapter.h"
-#include "../src/device.h"
-
-#include "sdp-client.h"
-#include "device.h"
-#include "gateway.h"
-#include "log.h"
-#include "error.h"
-#include "btio.h"
-#include "dbus-common.h"
-
-struct hf_agent {
-	char *name;	/* Bus id */
-	char *path;	/* D-Bus path */
-	guint watch;	/* Disconnect watch */
-	DBusPendingCall *call;
-};
-
-struct connect_cb {
-	unsigned int id;
-	gateway_stream_cb_t cb;
-	void *cb_data;
-};
-
-struct gateway {
-	gateway_state_t state;
-	GIOChannel *rfcomm;
-	GIOChannel *sco;
-	GIOChannel *incoming;
-	guint rfcomm_id;
-	guint sco_id;
-	GSList *callbacks;
-	struct hf_agent *agent;
-	DBusMessage *msg;
-	int version;
-	gateway_lock_t lock;
-};
-
-struct gateway_state_callback {
-	gateway_state_cb cb;
-	void *user_data;
-	unsigned int id;
-};
-
-static GSList *gateway_callbacks = NULL;
-
-int gateway_close(struct audio_device *device);
-
-GQuark gateway_error_quark(void)
-{
-	return g_quark_from_static_string("gateway-error-quark");
-}
-
-static const char *state2str(gateway_state_t state)
-{
-	switch (state) {
-	case GATEWAY_STATE_DISCONNECTED:
-		return "disconnected";
-	case GATEWAY_STATE_CONNECTING:
-		return "connecting";
-	case GATEWAY_STATE_CONNECTED:
-		return "connected";
-	case GATEWAY_STATE_PLAYING:
-		return "playing";
-	default:
-		return "";
-	}
-}
-
-static void agent_free(struct hf_agent *agent)
-{
-	if (!agent)
-		return;
-
-	if (agent->call)
-		dbus_pending_call_unref(agent->call);
-
-	g_dbus_remove_watch(agent->watch);
-
-	g_free(agent->name);
-	g_free(agent->path);
-	g_free(agent);
-}
-
-static void change_state(struct audio_device *dev, gateway_state_t new_state)
-{
-	struct gateway *gw = dev->gateway;
-	const char *val;
-	GSList *l;
-	gateway_state_t old_state;
-
-	if (gw->state == new_state)
-		return;
-
-	val = state2str(new_state);
-	old_state = gw->state;
-	gw->state = new_state;
-
-	emit_property_changed(device_get_path(dev->btd_dev),
-				AUDIO_GATEWAY_INTERFACE, "State",
-				DBUS_TYPE_STRING, &val);
-
-	for (l = gateway_callbacks; l != NULL; l = l->next) {
-		struct gateway_state_callback *cb = l->data;
-		cb->cb(dev, old_state, new_state, cb->user_data);
-	}
-}
-
-void gateway_set_state(struct audio_device *dev, gateway_state_t new_state)
-{
-	switch (new_state) {
-	case GATEWAY_STATE_DISCONNECTED:
-		gateway_close(dev);
-		break;
-	case GATEWAY_STATE_CONNECTING:
-	case GATEWAY_STATE_CONNECTED:
-	case GATEWAY_STATE_PLAYING:
-		break;
-	}
-}
-
-static void agent_cancel(struct hf_agent *agent)
-{
-	if (!agent->call)
-		return;
-
-	dbus_pending_call_cancel(agent->call);
-	dbus_pending_call_unref(agent->call);
-	agent->call = NULL;
-}
-
-static void agent_disconnect(struct audio_device *dev, struct hf_agent *agent)
-{
-	DBusMessage *msg;
-
-	msg = dbus_message_new_method_call(agent->name, agent->path,
-			"org.bluez.HandsfreeAgent", "Release");
-
-	g_dbus_send_message(btd_get_dbus_connection(), msg);
-
-	agent_cancel(agent);
-}
-
-static gboolean agent_sendfd(struct hf_agent *agent, int fd,
-		DBusPendingCallNotifyFunction notify, void *data)
-{
-	struct audio_device *dev = data;
-	struct gateway *gw = dev->gateway;
-	DBusMessage *msg;
-
-	if (agent->call)
-		return FALSE;
-
-	msg = dbus_message_new_method_call(agent->name, agent->path,
-			"org.bluez.HandsfreeAgent", "NewConnection");
-
-	dbus_message_append_args(msg, DBUS_TYPE_UNIX_FD, &fd,
-					DBUS_TYPE_UINT16, &gw->version,
-					DBUS_TYPE_INVALID);
-
-	if (dbus_connection_send_with_reply(btd_get_dbus_connection(), msg,
-						&agent->call, -1) == FALSE) {
-		dbus_message_unref(msg);
-		return FALSE;
-	}
-
-	dbus_pending_call_set_notify(agent->call, notify, dev, NULL);
-	dbus_message_unref(msg);
-
-	return TRUE;
-}
-
-static unsigned int connect_cb_new(struct gateway *gw,
-					gateway_stream_cb_t func,
-					void *user_data)
-{
-	struct connect_cb *cb;
-	static unsigned int free_cb_id = 1;
-
-	if (!func)
-		return 0;
-
-	cb = g_new(struct connect_cb, 1);
-
-	cb->cb = func;
-	cb->cb_data = user_data;
-	cb->id = free_cb_id++;
-
-	gw->callbacks = g_slist_append(gw->callbacks, cb);
-
-	return cb->id;
-}
-
-static void run_connect_cb(struct audio_device *dev, GError *err)
-{
-	struct gateway *gw = dev->gateway;
-	GSList *l;
-
-	for (l = gw->callbacks; l != NULL; l = l->next) {
-		struct connect_cb *cb = l->data;
-		cb->cb(dev, err, cb->cb_data);
-	}
-
-	g_slist_free_full(gw->callbacks, g_free);
-	gw->callbacks = NULL;
-}
-
-static gboolean sco_io_cb(GIOChannel *chan, GIOCondition cond,
-			struct audio_device *dev)
-{
-	struct gateway *gw = dev->gateway;
-
-	if (cond & G_IO_NVAL)
-		return FALSE;
-
-	DBG("sco connection is released");
-
-	g_source_remove(gw->sco_id);
-	gw->sco_id = 0;
-
-	g_io_channel_shutdown(gw->sco, TRUE, NULL);
-	g_io_channel_unref(gw->sco);
-	gw->sco = NULL;
-	change_state(dev, GATEWAY_STATE_CONNECTED);
-
-	return FALSE;
-}
-
-static void sco_connect_cb(GIOChannel *chan, GError *err, gpointer user_data)
-{
-	struct audio_device *dev = (struct audio_device *) user_data;
-	struct gateway *gw = dev->gateway;
-
-	DBG("at the begin of sco_connect_cb() in gateway.c");
-
-	gw->sco = g_io_channel_ref(chan);
-
-	gw->sco_id = g_io_add_watch(gw->sco, G_IO_ERR | G_IO_HUP | G_IO_NVAL,
-						(GIOFunc) sco_io_cb, dev);
-
-	if (err) {
-		error("sco_connect_cb(): %s", err->message);
-		gateway_suspend_stream(dev);
-		return;
-	}
-
-	change_state(dev, GATEWAY_STATE_PLAYING);
-	run_connect_cb(dev, NULL);
-}
-
-static gboolean rfcomm_disconnect_cb(GIOChannel *chan, GIOCondition cond,
-			struct audio_device *dev)
-{
-	if (cond & G_IO_NVAL)
-		return FALSE;
-
-	gateway_close(dev);
-
-	return FALSE;
-}
-
-static void newconnection_reply(DBusPendingCall *call, void *data)
-{
-	struct audio_device *dev = data;
-	struct gateway *gw = dev->gateway;
-	struct hf_agent *agent = gw->agent;
-	DBusMessage *reply = dbus_pending_call_steal_reply(call);
-	DBusError derr;
-
-	dbus_pending_call_unref(agent->call);
-	agent->call = NULL;
-
-	dbus_error_init(&derr);
-	if (!dbus_set_error_from_message(&derr, reply)) {
-		DBG("Agent reply: file descriptor passed successfully");
-		gw->rfcomm_id = g_io_add_watch(gw->rfcomm,
-						G_IO_ERR | G_IO_HUP | G_IO_NVAL,
-						(GIOFunc) rfcomm_disconnect_cb,
-						dev);
-		change_state(dev, GATEWAY_STATE_CONNECTED);
-		goto done;
-	}
-
-	DBG("Agent reply: %s", derr.message);
-
-	dbus_error_free(&derr);
-	gateway_close(dev);
-
-done:
-	dbus_message_unref(reply);
-}
-
-static void rfcomm_connect_cb(GIOChannel *chan, GError *err,
-				gpointer user_data)
-{
-	DBusConnection *conn = btd_get_dbus_connection();
-	struct audio_device *dev = user_data;
-	struct gateway *gw = dev->gateway;
-	DBusMessage *reply;
-	int sk, ret;
-
-	if (err) {
-		error("connect(): %s", err->message);
-		goto fail;
-	}
-
-	if (!gw->agent) {
-		error("Handsfree Agent not registered");
-		goto fail;
-	}
-
-	sk = g_io_channel_unix_get_fd(chan);
-
-	if (gw->rfcomm == NULL)
-		gw->rfcomm = g_io_channel_ref(chan);
-
-	ret = agent_sendfd(gw->agent, sk, newconnection_reply, dev);
-
-	if (!gw->msg)
-		return;
-
-	if (ret)
-		reply = dbus_message_new_method_return(gw->msg);
-	else
-		reply = btd_error_failed(gw->msg, "Can't pass file descriptor");
-
-	g_dbus_send_message(conn, reply);
-
-	return;
-
-fail:
-	if (gw->msg) {
-		DBusMessage *reply;
-		reply = btd_error_failed(gw->msg, "Connect failed");
-		g_dbus_send_message(conn, reply);
-	}
-
-	gateway_close(dev);
-}
-
-static int get_remote_profile_version(sdp_record_t *rec)
-{
-	uuid_t uuid;
-	sdp_list_t *profiles;
-	sdp_profile_desc_t *desc;
-	int ver = 0;
-
-	sdp_uuid16_create(&uuid, HANDSFREE_PROFILE_ID);
-
-	sdp_get_profile_descs(rec, &profiles);
-	if (profiles == NULL)
-		goto done;
-
-	desc = profiles->data;
-
-	if (sdp_uuid16_cmp(&desc->uuid, &uuid) == 0)
-		ver = desc->version;
-
-	sdp_list_free(profiles, free);
-
-done:
-	return ver;
-}
-
-static void get_incoming_record_cb(sdp_list_t *recs, int err,
-					gpointer user_data)
-{
-	struct audio_device *dev = user_data;
-	struct gateway *gw = dev->gateway;
-	GError *gerr = NULL;
-
-	if (err < 0) {
-		error("Unable to get service record: %s (%d)", strerror(-err),
-					-err);
-		goto fail;
-	}
-
-	if (!recs || !recs->data) {
-		error("No records found");
-		goto fail;
-	}
-
-	gw->version = get_remote_profile_version(recs->data);
-	if (gw->version == 0)
-		goto fail;
-
-	rfcomm_connect_cb(gw->incoming, gerr, dev);
-	return;
-
-fail:
-	gateway_close(dev);
-}
-
-static void unregister_incoming(gpointer user_data)
-{
-	struct audio_device *dev = user_data;
-	struct gateway *gw = dev->gateway;
-
-	if (gw->incoming) {
-		g_io_channel_unref(gw->incoming);
-		gw->incoming = NULL;
-	}
-}
-
-static void rfcomm_incoming_cb(GIOChannel *chan, GError *err,
-				gpointer user_data)
-{
-	struct audio_device *dev = user_data;
-	struct gateway *gw = dev->gateway;
-	uuid_t uuid;
-
-	gw->incoming = g_io_channel_ref(chan);
-
-	sdp_uuid16_create(&uuid, HANDSFREE_AGW_SVCLASS_ID);
-	if (bt_search_service(&dev->src, &dev->dst, &uuid,
-						get_incoming_record_cb, dev,
-						unregister_incoming) == 0)
-		return;
-
-	unregister_incoming(dev);
-	gateway_close(dev);
-}
-
-static void get_record_cb(sdp_list_t *recs, int err, gpointer user_data)
-{
-	struct audio_device *dev = user_data;
-	struct gateway *gw = dev->gateway;
-	int ch;
-	sdp_list_t *protos, *classes;
-	uuid_t uuid;
-	GIOChannel *io;
-	GError *gerr = NULL;
-
-	if (err < 0) {
-		error("Unable to get service record: %s (%d)", strerror(-err),
-					-err);
-		goto fail;
-	}
-
-	if (!recs || !recs->data) {
-		error("No records found");
-		err = -EIO;
-		goto fail;
-	}
-
-	if (sdp_get_service_classes(recs->data, &classes) < 0) {
-		error("Unable to get service classes from record");
-		err = -EINVAL;
-		goto fail;
-	}
-
-	if (sdp_get_access_protos(recs->data, &protos) < 0) {
-		error("Unable to get access protocols from record");
-		err = -ENODATA;
-		goto fail;
-	}
-
-	gw->version = get_remote_profile_version(recs->data);
-	if (gw->version == 0) {
-		error("Unable to get profile version from record");
-		err = -EINVAL;
-		goto fail;
-	}
-
-	memcpy(&uuid, classes->data, sizeof(uuid));
-	sdp_list_free(classes, free);
-
-	if (!sdp_uuid128_to_uuid(&uuid) || uuid.type != SDP_UUID16 ||
-			uuid.value.uuid16 != HANDSFREE_AGW_SVCLASS_ID) {
-		sdp_list_free(protos, NULL);
-		error("Invalid service record or not HFP");
-		err = -EIO;
-		goto fail;
-	}
-
-	ch = sdp_get_proto_port(protos, RFCOMM_UUID);
-	sdp_list_foreach(protos, (sdp_list_func_t) sdp_list_free, NULL);
-	sdp_list_free(protos, NULL);
-	if (ch <= 0) {
-		error("Unable to extract RFCOMM channel from service record");
-		err = -EIO;
-		goto fail;
-	}
-
-	io = bt_io_connect(rfcomm_connect_cb, dev, NULL, &gerr,
-				BT_IO_OPT_SOURCE_BDADDR, &dev->src,
-				BT_IO_OPT_DEST_BDADDR, &dev->dst,
-				BT_IO_OPT_SEC_LEVEL, BT_IO_SEC_MEDIUM,
-				BT_IO_OPT_CHANNEL, ch,
-				BT_IO_OPT_INVALID);
-	if (!io) {
-		error("Unable to connect: %s", gerr->message);
-		goto fail;
-	}
-
-	g_io_channel_unref(io);
-	return;
-
-fail:
-	if (gw->msg) {
-		DBusMessage *reply = btd_error_failed(gw->msg,
-					gerr ? gerr->message : strerror(-err));
-		g_dbus_send_message(btd_get_dbus_connection(), reply);
-	}
-
-	gateway_close(dev);
-
-	if (gerr)
-		g_error_free(gerr);
-}
-
-static int get_records(struct audio_device *device)
-{
-	uuid_t uuid;
-	int err;
-
-	sdp_uuid16_create(&uuid, HANDSFREE_AGW_SVCLASS_ID);
-
-	err = bt_search_service(&device->src, &device->dst, &uuid,
-						get_record_cb, device, NULL);
-	if (err < 0)
-		return err;
-
-	change_state(device, GATEWAY_STATE_CONNECTING);
-
-	return 0;
-}
-
-static DBusMessage *ag_connect(DBusConnection *conn, DBusMessage *msg,
-				void *data)
-{
-	struct audio_device *au_dev = (struct audio_device *) data;
-	struct gateway *gw = au_dev->gateway;
-	int err;
-
-	if (gw->state == GATEWAY_STATE_CONNECTING)
-		return btd_error_in_progress(msg);
-	else if (gw->state > GATEWAY_STATE_CONNECTING)
-		return btd_error_already_connected(msg);
-
-	if (!gw->agent)
-		return btd_error_agent_not_available(msg);
-
-	err = get_records(au_dev);
-	if (err < 0)
-		return btd_error_failed(msg, strerror(-err));
-
-	gw->msg = dbus_message_ref(msg);
-
-	return NULL;
-}
-
-int gateway_close(struct audio_device *device)
-{
-	GError *gerr = NULL;
-	struct gateway *gw = device->gateway;
-	int sock;
-
-	if (gw->rfcomm_id != 0) {
-		g_source_remove(gw->rfcomm_id);
-		gw->rfcomm_id = 0;
-	}
-
-	if (gw->sco_id != 0) {
-		g_source_remove(gw->sco_id);
-		gw->sco_id = 0;
-	}
-
-	if (gw->rfcomm) {
-		sock = g_io_channel_unix_get_fd(gw->rfcomm);
-		shutdown(sock, SHUT_RDWR);
-
-		g_io_channel_shutdown(gw->rfcomm, TRUE, NULL);
-		g_io_channel_unref(gw->rfcomm);
-		gw->rfcomm = NULL;
-	}
-
-	if (gw->sco) {
-		g_io_channel_shutdown(gw->sco, TRUE, NULL);
-		g_io_channel_unref(gw->sco);
-		gw->sco = NULL;
-	}
-
-	if (gw->agent)
-		agent_cancel(gw->agent);
-
-	change_state(device, GATEWAY_STATE_DISCONNECTED);
-	g_set_error(&gerr, GATEWAY_ERROR,
-			GATEWAY_ERROR_DISCONNECTED, "Disconnected");
-	run_connect_cb(device, gerr);
-	g_error_free(gerr);
-
-	return 0;
-}
-
-static DBusMessage *ag_disconnect(DBusConnection *conn, DBusMessage *msg,
-					void *data)
-{
-	struct audio_device *device = data;
-	struct gateway *gw = device->gateway;
-	DBusMessage *reply = NULL;
-	char gw_addr[18];
-
-	if (!gw->rfcomm)
-		return btd_error_not_connected(msg);
-
-	reply = dbus_message_new_method_return(msg);
-	if (!reply)
-		return NULL;
-
-	gateway_close(device);
-	ba2str(&device->dst, gw_addr);
-	DBG("Disconnected from %s, %s", gw_addr,
-					device_get_path(device->btd_dev));
-
-	return reply;
-}
-
-static void agent_exited(DBusConnection *conn, void *data)
-{
-	struct gateway *gateway = data;
-	struct hf_agent *agent = gateway->agent;
-
-	DBG("Agent %s exited", agent->name);
-
-	agent_free(agent);
-	gateway->agent = NULL;
-}
-
-static DBusMessage *ag_get_properties(DBusConnection *conn, DBusMessage *msg,
-					void *data)
-{
-	struct audio_device *device = data;
-	struct gateway *gw = device->gateway;
-	DBusMessage *reply;
-	DBusMessageIter iter;
-	DBusMessageIter dict;
-	const char *value;
-
-
-	reply = dbus_message_new_method_return(msg);
-	if (!reply)
-		return NULL;
-
-	dbus_message_iter_init_append(reply, &iter);
-
-	dbus_message_iter_open_container(&iter, DBUS_TYPE_ARRAY,
-			DBUS_DICT_ENTRY_BEGIN_CHAR_AS_STRING
-			DBUS_TYPE_STRING_AS_STRING DBUS_TYPE_VARIANT_AS_STRING
-			DBUS_DICT_ENTRY_END_CHAR_AS_STRING, &dict);
-
-	value = state2str(gw->state);
-	dict_append_entry(&dict, "State",
-			DBUS_TYPE_STRING, &value);
-
-	dbus_message_iter_close_container(&iter, &dict);
-
-	return reply;
-}
-
-static DBusMessage *register_agent(DBusConnection *conn,
-					DBusMessage *msg, void *data)
-{
-	struct audio_device *device = data;
-	struct gateway *gw = device->gateway;
-	struct hf_agent *agent;
-	const char *path, *name;
-
-	if (gw->agent)
-		return btd_error_already_exists(msg);
-
-	if (!dbus_message_get_args(msg, NULL, DBUS_TYPE_OBJECT_PATH, &path,
-						DBUS_TYPE_INVALID))
-		return btd_error_invalid_args(msg);
-
-	name = dbus_message_get_sender(msg);
-	agent = g_new0(struct hf_agent, 1);
-
-	agent->name = g_strdup(name);
-	agent->path = g_strdup(path);
-
-	agent->watch = g_dbus_add_disconnect_watch(conn, name,
-						agent_exited, gw, NULL);
-
-	gw->agent = agent;
-
-	return dbus_message_new_method_return(msg);
-}
-
-static DBusMessage *unregister_agent(DBusConnection *conn,
-				DBusMessage *msg, void *data)
-{
-	struct audio_device *device = data;
-	struct gateway *gw = device->gateway;
-	const char *path;
-
-	if (!gw->agent)
-		goto done;
-
-	if (strcmp(gw->agent->name, dbus_message_get_sender(msg)) != 0)
-		return btd_error_not_authorized(msg);
-
-	if (!dbus_message_get_args(msg, NULL,
-				DBUS_TYPE_OBJECT_PATH, &path,
-				DBUS_TYPE_INVALID))
-		return btd_error_invalid_args(msg);
-
-	if (strcmp(gw->agent->path, path) != 0)
-		return btd_error_does_not_exist(msg);
-
-	agent_free(gw->agent);
-	gw->agent = NULL;
-
-done:
-	return dbus_message_new_method_return(msg);
-}
-
-static const GDBusMethodTable gateway_methods[] = {
-	{ GDBUS_ASYNC_METHOD("Connect", NULL, NULL, ag_connect) },
-	{ GDBUS_ASYNC_METHOD("Disconnect", NULL, NULL, ag_disconnect) },
-	{ GDBUS_METHOD("GetProperties",
-			NULL, GDBUS_ARGS({ "properties", "a{sv}" }),
-			ag_get_properties) },
-	{ GDBUS_METHOD("RegisterAgent",
-			GDBUS_ARGS({ "agent", "o" }), NULL, register_agent) },
-	{ GDBUS_METHOD("UnregisterAgent",
-			GDBUS_ARGS({ "agent", "o" }), NULL, unregister_agent) },
-	{ }
-};
-
-static const GDBusSignalTable gateway_signals[] = {
-	{ GDBUS_SIGNAL("PropertyChanged",
-			GDBUS_ARGS({ "name", "s" }, { "value", "v" })) },
-	{ }
-};
-
-static void path_unregister(void *data)
-{
-	struct audio_device *dev = data;
-
-	DBG("Unregistered interface %s on path %s",
-		AUDIO_GATEWAY_INTERFACE, device_get_path(dev->btd_dev));
-
-	gateway_close(dev);
-
-	if (dev->gateway->agent)
-		agent_free(dev->gateway->agent);
-
-	g_free(dev->gateway);
-	dev->gateway = NULL;
-}
-
-void gateway_unregister(struct audio_device *dev)
-{
-	if (dev->gateway->agent)
-		agent_disconnect(dev, dev->gateway->agent);
-
-	g_dbus_unregister_interface(btd_get_dbus_connection(),
-						device_get_path(dev->btd_dev),
-						AUDIO_GATEWAY_INTERFACE);
-}
-
-struct gateway *gateway_init(struct audio_device *dev)
-{
-	if (!g_dbus_register_interface(btd_get_dbus_connection(),
-					device_get_path(dev->btd_dev),
-					AUDIO_GATEWAY_INTERFACE,
-					gateway_methods, gateway_signals,
-					NULL, dev, path_unregister))
-		return NULL;
-
-	return g_new0(struct gateway, 1);
-}
-
-gboolean gateway_is_connected(struct audio_device *dev)
-{
-	struct gateway *gw = dev->gateway;
-
-	if (gw->state == GATEWAY_STATE_CONNECTED)
-		return TRUE;
-
-	return FALSE;
-}
-
-gboolean gateway_is_active(struct audio_device *dev)
-{
-	struct gateway *gw = dev->gateway;
-
-	if (gw->state != GATEWAY_STATE_DISCONNECTED)
-		return TRUE;
-
-	return FALSE;
-}
-
-gateway_state_t gateway_get_state(struct audio_device *dev)
-{
-	struct gateway *gw = dev->gateway;
-
-	return gw->state;
-}
-
-int gateway_connect_rfcomm(struct audio_device *dev, GIOChannel *io)
-{
-	if (!io)
-		return -EINVAL;
-
-	dev->gateway->rfcomm = g_io_channel_ref(io);
-
-	change_state(dev, GATEWAY_STATE_CONNECTING);
-
-	return 0;
-}
-
-int gateway_connect_sco(struct audio_device *dev, GIOChannel *io)
-{
-	struct gateway *gw = dev->gateway;
-
-	if (gw->sco)
-		return -EISCONN;
-
-	gw->sco = g_io_channel_ref(io);
-
-	gw->sco_id = g_io_add_watch(gw->sco, G_IO_ERR | G_IO_HUP | G_IO_NVAL,
-						(GIOFunc) sco_io_cb, dev);
-
-	change_state(dev, GATEWAY_STATE_PLAYING);
-
-	return 0;
-}
-
-void gateway_start_service(struct audio_device *dev)
-{
-	struct gateway *gw = dev->gateway;
-	GError *err = NULL;
-
-	if (gw->rfcomm == NULL)
-		return;
-
-	if (!bt_io_accept(gw->rfcomm, rfcomm_incoming_cb, dev, NULL, &err)) {
-		error("bt_io_accept: %s", err->message);
-		g_error_free(err);
-		gateway_close(dev);
-	}
-}
-
-static gboolean request_stream_cb(gpointer data)
-{
-	run_connect_cb(data, NULL);
-	return FALSE;
-}
-
-/* These are functions to be called from unix.c for audio system
- * ifaces (alsa, gstreamer, etc.) */
-unsigned int gateway_request_stream(struct audio_device *dev,
-				gateway_stream_cb_t cb, void *user_data)
-{
-	struct gateway *gw = dev->gateway;
-	GError *err = NULL;
-	GIOChannel *io;
-
-	if (!gw->rfcomm) {
-		if (get_records(dev) < 0)
-			return 0;
-	} else if (!gw->sco) {
-		io = bt_io_connect(sco_connect_cb, dev, NULL, &err,
-				BT_IO_OPT_SOURCE_BDADDR, &dev->src,
-				BT_IO_OPT_DEST_BDADDR, &dev->dst,
-				BT_IO_OPT_SEC_LEVEL, BT_IO_SEC_MEDIUM,
-				BT_IO_OPT_INVALID);
-		if (!io) {
-			error("%s", err->message);
-			g_error_free(err);
-			return 0;
-		}
-	} else
-		g_idle_add(request_stream_cb, dev);
-
-	return connect_cb_new(gw, cb, user_data);
-}
-
-gboolean gateway_cancel_stream(struct audio_device *dev, unsigned int id)
-{
-	struct gateway *gw = dev->gateway;
-	GSList *l;
-	struct connect_cb *cb = NULL;
-
-	for (l = gw->callbacks; l != NULL; l = l->next) {
-		struct connect_cb *tmp = l->data;
-
-		if (tmp->id == id) {
-			cb = tmp;
-			break;
-		}
-	}
-
-	if (!cb)
-		return FALSE;
-
-	gw->callbacks = g_slist_remove(gw->callbacks, cb);
-	g_free(cb);
-
-	gateway_suspend_stream(dev);
-
-	return TRUE;
-}
-
-int gateway_get_sco_fd(struct audio_device *dev)
-{
-	struct gateway *gw = dev->gateway;
-
-	if (!gw || !gw->sco)
-		return -1;
-
-	return g_io_channel_unix_get_fd(gw->sco);
-}
-
-void gateway_suspend_stream(struct audio_device *dev)
-{
-	GError *gerr = NULL;
-	struct gateway *gw = dev->gateway;
-
-	if (!gw || !gw->sco)
-		return;
-
-	g_source_remove(gw->sco_id);
-	gw->sco_id = 0;
-
-	g_io_channel_shutdown(gw->sco, TRUE, NULL);
-	g_io_channel_unref(gw->sco);
-	gw->sco = NULL;
-	g_set_error(&gerr, GATEWAY_ERROR, GATEWAY_ERROR_SUSPENDED, "Suspended");
-	run_connect_cb(dev, gerr);
-	g_error_free(gerr);
-	change_state(dev, GATEWAY_STATE_CONNECTED);
-}
-
-unsigned int gateway_add_state_cb(gateway_state_cb cb, void *user_data)
-{
-	struct gateway_state_callback *state_cb;
-	static unsigned int id = 0;
-
-	state_cb = g_new(struct gateway_state_callback, 1);
-	state_cb->cb = cb;
-	state_cb->user_data = user_data;
-	state_cb->id = ++id;
-
-	gateway_callbacks = g_slist_append(gateway_callbacks, state_cb);
-
-	return state_cb->id;
-}
-
-gboolean gateway_remove_state_cb(unsigned int id)
-{
-	GSList *l;
-
-	for (l = gateway_callbacks; l != NULL; l = l->next) {
-		struct gateway_state_callback *cb = l->data;
-		if (cb && cb->id == id) {
-			gateway_callbacks = g_slist_remove(gateway_callbacks,
-									cb);
-			g_free(cb);
-			return TRUE;
-		}
-	}
-
-	return FALSE;
-}
-
-gateway_lock_t gateway_get_lock(struct audio_device *dev)
-{
-	struct gateway *gw = dev->gateway;
-
-	return gw->lock;
-}
-
-gboolean gateway_lock(struct audio_device *dev, gateway_lock_t lock)
-{
-	struct gateway *gw = dev->gateway;
-
-	if (gw->lock & lock)
-		return FALSE;
-
-	gw->lock |= lock;
-
-	return TRUE;
-}
-
-gboolean gateway_unlock(struct audio_device *dev, gateway_lock_t lock)
-{
-	struct gateway *gw = dev->gateway;
-
-	if (!(gw->lock & lock))
-		return FALSE;
-
-	gw->lock &= ~lock;
-
-	if (gw->lock)
-		return TRUE;
-
-	if (gw->state == GATEWAY_STATE_PLAYING)
-		gateway_suspend_stream(dev);
-
-	return TRUE;
-}
diff --git a/audio/gateway.h b/audio/gateway.h
deleted file mode 100644
index d87d76a..0000000
--- a/audio/gateway.h
+++ /dev/null
@@ -1,75 +0,0 @@
-/*
- *
- *  BlueZ - Bluetooth protocol stack for Linux
- *
- *  Copyright (C) 2006-2010  Nokia Corporation
- *  Copyright (C) 2004-2010  Marcel Holtmann <marcel@holtmann.org>
- *
- *
- *  This program is free software; you can redistribute it and/or modify
- *  it under the terms of the GNU General Public License as published by
- *  the Free Software Foundation; either version 2 of the License, or
- *  (at your option) any later version.
- *
- *  This program is distributed in the hope that it will be useful,
- *  but WITHOUT ANY WARRANTY; without even the implied warranty of
- *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
- *  GNU General Public License for more details.
- *
- *  You should have received a copy of the GNU General Public License
- *  along with this program; if not, write to the Free Software
- *  Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
- *
- */
-
-#define AUDIO_GATEWAY_INTERFACE "org.bluez.HandsfreeGateway"
-
-#define DEFAULT_HFP_HS_CHANNEL 7
-
-typedef enum {
-	GATEWAY_STATE_DISCONNECTED,
-	GATEWAY_STATE_CONNECTING,
-	GATEWAY_STATE_CONNECTED,
-	GATEWAY_STATE_PLAYING,
-} gateway_state_t;
-
-typedef enum {
-	GATEWAY_LOCK_READ = 1,
-	GATEWAY_LOCK_WRITE = 1 << 1,
-} gateway_lock_t;
-
-typedef enum {
-	GATEWAY_ERROR_DISCONNECTED,
-	GATEWAY_ERROR_SUSPENDED,
-} gateway_error_t;
-
-#define GATEWAY_ERROR gateway_error_quark()
-
-GQuark gateway_error_quark(void);
-
-typedef void (*gateway_state_cb) (struct audio_device *dev,
-					gateway_state_t old_state,
-					gateway_state_t new_state,
-					void *user_data);
-typedef void (*gateway_stream_cb_t) (struct audio_device *dev, GError *err,
-		void *user_data);
-
-void gateway_set_state(struct audio_device *dev, gateway_state_t new_state);
-void gateway_unregister(struct audio_device *dev);
-struct gateway *gateway_init(struct audio_device *dev);
-gboolean gateway_is_active(struct audio_device *dev);
-gboolean gateway_is_connected(struct audio_device *dev);
-gateway_state_t gateway_get_state(struct audio_device *dev);
-int gateway_connect_rfcomm(struct audio_device *dev, GIOChannel *io);
-int gateway_connect_sco(struct audio_device *dev, GIOChannel *chan);
-void gateway_start_service(struct audio_device *device);
-unsigned int gateway_request_stream(struct audio_device *dev,
-			gateway_stream_cb_t cb, void *user_data);
-gboolean gateway_cancel_stream(struct audio_device *dev, unsigned int id);
-int gateway_get_sco_fd(struct audio_device *dev);
-void gateway_suspend_stream(struct audio_device *dev);
-unsigned int gateway_add_state_cb(gateway_state_cb cb, void *user_data);
-gboolean gateway_remove_state_cb(unsigned int id);
-gateway_lock_t gateway_get_lock(struct audio_device *dev);
-gboolean gateway_lock(struct audio_device *dev, gateway_lock_t lock);
-gboolean gateway_unlock(struct audio_device *dev, gateway_lock_t lock);
-- 
1.7.11.7


^ permalink raw reply related

* [PATCH BlueZ 12/13] audio: Move to profiles directory
From: Luiz Augusto von Dentz @ 2012-11-13 13:21 UTC (permalink / raw)
  To: linux-bluetooth
In-Reply-To: <1352812880-7306-1-git-send-email-luiz.dentz@gmail.com>

From: Luiz Augusto von Dentz <luiz.von.dentz@intel.com>

---
 Makefile.am                             | 32 ++++++++++++++++----------------
 {audio => profiles/audio}/a2dp-codecs.h |  0
 {audio => profiles/audio}/a2dp.c        |  0
 {audio => profiles/audio}/a2dp.h        |  0
 {audio => profiles/audio}/audio.conf    |  0
 {audio => profiles/audio}/avctp.c       |  0
 {audio => profiles/audio}/avctp.h       |  0
 {audio => profiles/audio}/avdtp.c       |  0
 {audio => profiles/audio}/avdtp.h       |  0
 {audio => profiles/audio}/avrcp.c       |  0
 {audio => profiles/audio}/avrcp.h       |  0
 {audio => profiles/audio}/control.c     |  0
 {audio => profiles/audio}/control.h     |  0
 {audio => profiles/audio}/device.c      |  0
 {audio => profiles/audio}/device.h      |  0
 {audio => profiles/audio}/main.c        |  0
 {audio => profiles/audio}/manager.c     |  0
 {audio => profiles/audio}/manager.h     |  0
 {audio => profiles/audio}/media.c       |  0
 {audio => profiles/audio}/media.h       |  0
 {audio => profiles/audio}/player.c      |  0
 {audio => profiles/audio}/player.h      |  0
 {audio => profiles/audio}/rtp.h         |  0
 {audio => profiles/audio}/sink.c        |  0
 {audio => profiles/audio}/sink.h        |  0
 {audio => profiles/audio}/source.c      |  0
 {audio => profiles/audio}/source.h      |  0
 {audio => profiles/audio}/transport.c   |  0
 {audio => profiles/audio}/transport.h   |  0
 29 files changed, 16 insertions(+), 16 deletions(-)
 rename {audio => profiles/audio}/a2dp-codecs.h (100%)
 rename {audio => profiles/audio}/a2dp.c (100%)
 rename {audio => profiles/audio}/a2dp.h (100%)
 rename {audio => profiles/audio}/audio.conf (100%)
 rename {audio => profiles/audio}/avctp.c (100%)
 rename {audio => profiles/audio}/avctp.h (100%)
 rename {audio => profiles/audio}/avdtp.c (100%)
 rename {audio => profiles/audio}/avdtp.h (100%)
 rename {audio => profiles/audio}/avrcp.c (100%)
 rename {audio => profiles/audio}/avrcp.h (100%)
 rename {audio => profiles/audio}/control.c (100%)
 rename {audio => profiles/audio}/control.h (100%)
 rename {audio => profiles/audio}/device.c (100%)
 rename {audio => profiles/audio}/device.h (100%)
 rename {audio => profiles/audio}/main.c (100%)
 rename {audio => profiles/audio}/manager.c (100%)
 rename {audio => profiles/audio}/manager.h (100%)
 rename {audio => profiles/audio}/media.c (100%)
 rename {audio => profiles/audio}/media.h (100%)
 rename {audio => profiles/audio}/player.c (100%)
 rename {audio => profiles/audio}/player.h (100%)
 rename {audio => profiles/audio}/rtp.h (100%)
 rename {audio => profiles/audio}/sink.c (100%)
 rename {audio => profiles/audio}/sink.h (100%)
 rename {audio => profiles/audio}/source.c (100%)
 rename {audio => profiles/audio}/source.h (100%)
 rename {audio => profiles/audio}/transport.c (100%)
 rename {audio => profiles/audio}/transport.h (100%)

diff --git a/Makefile.am b/Makefile.am
index 84ae237..10c811a 100644
--- a/Makefile.am
+++ b/Makefile.am
@@ -105,20 +105,20 @@ endif
 
 if AUDIOPLUGIN
 builtin_modules += audio
-builtin_sources += audio/main.c \
-			audio/manager.h audio/manager.c \
-			audio/control.h audio/control.c \
-			audio/avctp.h audio/avctp.c \
-			audio/avrcp.h audio/avrcp.c \
-			audio/device.h audio/device.c \
-			audio/source.h audio/source.c \
-			audio/sink.h audio/sink.c \
-			audio/a2dp.h audio/a2dp.c \
-			audio/avdtp.h audio/avdtp.c \
-			audio/media.h audio/media.c \
-			audio/transport.h audio/transport.c \
-			audio/player.h audio/player.c \
-			audio/a2dp-codecs.h
+builtin_sources += profiles/audio/main.c \
+			profiles/audio/manager.h profiles/audio/manager.c \
+			profiles/audio/control.h profiles/audio/control.c \
+			profiles/audio/avctp.h profiles/audio/avctp.c \
+			profiles/audio/avrcp.h profiles/audio/avrcp.c \
+			profiles/audio/device.h profiles/audio/device.c \
+			profiles/audio/source.h profiles/audio/source.c \
+			profiles/audio/sink.h profiles/audio/sink.c \
+			profiles/audio/a2dp.h profiles/audio/a2dp.c \
+			profiles/audio/avdtp.h profiles/audio/avdtp.c \
+			profiles/audio/media.h profiles/audio/media.c \
+			profiles/audio/transport.h profiles/audio/transport.c \
+			profiles/audio/player.h profiles/audio/player.c \
+			profiles/audio/a2dp-codecs.h
 endif
 
 if SAPPLUGIN
@@ -305,7 +305,7 @@ endif
 EXTRA_DIST += src/genbuiltin src/bluetooth.conf src/org.bluez.service \
 			src/main.conf profiles/network/network.conf \
 			profiles/input/input.conf profiles/proximity/proximity.conf \
-			audio/audio.conf \
+			profiles/audio/audio.conf \
 			profiles/sap/sap-dummy.c profiles/sap/sap-u8500.c
 
 include Makefile.tools
@@ -347,7 +347,7 @@ EXTRA_DIST += doc/manager-api.txt \
 AM_CFLAGS += @DBUS_CFLAGS@ @GLIB_CFLAGS@
 
 AM_CPPFLAGS = -I$(builddir)/lib -I$(builddir)/src -I$(srcdir)/src \
-			-I$(srcdir)/audio -I$(srcdir)/gdbus \
+			-I$(srcdir)/profiles/audio -I$(srcdir)/gdbus \
 			-I$(srcdir)/attrib -I$(srcdir)/btio -I$(srcdir)/tools \
 			-I$(builddir)/tools -I$(srcdir)/monitor
 
diff --git a/audio/a2dp-codecs.h b/profiles/audio/a2dp-codecs.h
similarity index 100%
rename from audio/a2dp-codecs.h
rename to profiles/audio/a2dp-codecs.h
diff --git a/audio/a2dp.c b/profiles/audio/a2dp.c
similarity index 100%
rename from audio/a2dp.c
rename to profiles/audio/a2dp.c
diff --git a/audio/a2dp.h b/profiles/audio/a2dp.h
similarity index 100%
rename from audio/a2dp.h
rename to profiles/audio/a2dp.h
diff --git a/audio/audio.conf b/profiles/audio/audio.conf
similarity index 100%
rename from audio/audio.conf
rename to profiles/audio/audio.conf
diff --git a/audio/avctp.c b/profiles/audio/avctp.c
similarity index 100%
rename from audio/avctp.c
rename to profiles/audio/avctp.c
diff --git a/audio/avctp.h b/profiles/audio/avctp.h
similarity index 100%
rename from audio/avctp.h
rename to profiles/audio/avctp.h
diff --git a/audio/avdtp.c b/profiles/audio/avdtp.c
similarity index 100%
rename from audio/avdtp.c
rename to profiles/audio/avdtp.c
diff --git a/audio/avdtp.h b/profiles/audio/avdtp.h
similarity index 100%
rename from audio/avdtp.h
rename to profiles/audio/avdtp.h
diff --git a/audio/avrcp.c b/profiles/audio/avrcp.c
similarity index 100%
rename from audio/avrcp.c
rename to profiles/audio/avrcp.c
diff --git a/audio/avrcp.h b/profiles/audio/avrcp.h
similarity index 100%
rename from audio/avrcp.h
rename to profiles/audio/avrcp.h
diff --git a/audio/control.c b/profiles/audio/control.c
similarity index 100%
rename from audio/control.c
rename to profiles/audio/control.c
diff --git a/audio/control.h b/profiles/audio/control.h
similarity index 100%
rename from audio/control.h
rename to profiles/audio/control.h
diff --git a/audio/device.c b/profiles/audio/device.c
similarity index 100%
rename from audio/device.c
rename to profiles/audio/device.c
diff --git a/audio/device.h b/profiles/audio/device.h
similarity index 100%
rename from audio/device.h
rename to profiles/audio/device.h
diff --git a/audio/main.c b/profiles/audio/main.c
similarity index 100%
rename from audio/main.c
rename to profiles/audio/main.c
diff --git a/audio/manager.c b/profiles/audio/manager.c
similarity index 100%
rename from audio/manager.c
rename to profiles/audio/manager.c
diff --git a/audio/manager.h b/profiles/audio/manager.h
similarity index 100%
rename from audio/manager.h
rename to profiles/audio/manager.h
diff --git a/audio/media.c b/profiles/audio/media.c
similarity index 100%
rename from audio/media.c
rename to profiles/audio/media.c
diff --git a/audio/media.h b/profiles/audio/media.h
similarity index 100%
rename from audio/media.h
rename to profiles/audio/media.h
diff --git a/audio/player.c b/profiles/audio/player.c
similarity index 100%
rename from audio/player.c
rename to profiles/audio/player.c
diff --git a/audio/player.h b/profiles/audio/player.h
similarity index 100%
rename from audio/player.h
rename to profiles/audio/player.h
diff --git a/audio/rtp.h b/profiles/audio/rtp.h
similarity index 100%
rename from audio/rtp.h
rename to profiles/audio/rtp.h
diff --git a/audio/sink.c b/profiles/audio/sink.c
similarity index 100%
rename from audio/sink.c
rename to profiles/audio/sink.c
diff --git a/audio/sink.h b/profiles/audio/sink.h
similarity index 100%
rename from audio/sink.h
rename to profiles/audio/sink.h
diff --git a/audio/source.c b/profiles/audio/source.c
similarity index 100%
rename from audio/source.c
rename to profiles/audio/source.c
diff --git a/audio/source.h b/profiles/audio/source.h
similarity index 100%
rename from audio/source.h
rename to profiles/audio/source.h
diff --git a/audio/transport.c b/profiles/audio/transport.c
similarity index 100%
rename from audio/transport.c
rename to profiles/audio/transport.c
diff --git a/audio/transport.h b/profiles/audio/transport.h
similarity index 100%
rename from audio/transport.h
rename to profiles/audio/transport.h
-- 
1.7.11.7


^ permalink raw reply related

* [PATCH BlueZ 13/13] audio: Add support for passing endpoints as custom property
From: Luiz Augusto von Dentz @ 2012-11-13 13:21 UTC (permalink / raw)
  To: linux-bluetooth
In-Reply-To: <1352812880-7306-1-git-send-email-luiz.dentz@gmail.com>

From: Luiz Augusto von Dentz <luiz.von.dentz@intel.com>

This adds the possibility to pass the registered endpoints to external
components implementing the same profile.
---
 profiles/audio/media.c | 140 ++++++++++++++++++++++++++++++++++++++++---------
 1 file changed, 114 insertions(+), 26 deletions(-)

diff --git a/profiles/audio/media.c b/profiles/audio/media.c
index 65037fe..6d45373 100644
--- a/profiles/audio/media.c
+++ b/profiles/audio/media.c
@@ -35,7 +35,9 @@
 #include <gdbus.h>
 
 #include "../src/adapter.h"
+#include "../src/device.h"
 #include "../src/dbus-common.h"
+#include "../src/profile.h"
 
 #include "glib-helper.h"
 #include "log.h"
@@ -574,6 +576,111 @@ static gboolean endpoint_init_a2dp_sink(struct media_endpoint *endpoint,
 	return TRUE;
 }
 
+static struct media_endpoint *media_adapter_find_endpoint(
+						struct media_adapter *adapter,
+						const char *sender,
+						const char *path,
+						const char *uuid)
+{
+	GSList *l;
+
+	for (l = adapter->endpoints; l; l = l->next) {
+		struct media_endpoint *endpoint = l->data;
+
+		if (sender && g_strcmp0(endpoint->sender, sender) != 0)
+			continue;
+
+		if (path && g_strcmp0(endpoint->path, path) != 0)
+			continue;
+
+		if (uuid && g_strcmp0(endpoint->uuid, uuid) != 0)
+			continue;
+
+		return endpoint;
+	}
+
+	return NULL;
+}
+
+static bool endpoint_properties_exists(const char *uuid,
+						struct btd_device *dev,
+						void *user_data)
+{
+	struct media_adapter *adapter = user_data;
+	struct btd_adapter *btd_adapter = device_get_adapter(dev);
+	const bdaddr_t *src = adapter_get_address(btd_adapter);
+
+	if (bacmp(&adapter->src, src) != 0)
+		return false;
+
+	if (media_adapter_find_endpoint(adapter, NULL, NULL, uuid) == NULL)
+		return false;
+
+	return true;
+}
+
+static void append_endpoint(struct media_endpoint *endpoint,
+						DBusMessageIter *dict)
+{
+	DBusMessageIter entry, var, props;
+
+	dbus_message_iter_open_container(dict, DBUS_TYPE_DICT_ENTRY,
+							NULL, &entry);
+
+	dbus_message_iter_append_basic(&entry, DBUS_TYPE_STRING,
+						&endpoint->sender);
+
+	dbus_message_iter_open_container(&entry, DBUS_TYPE_VARIANT, "a{sv}",
+								&var);
+
+	dbus_message_iter_open_container(&var, DBUS_TYPE_ARRAY,
+					DBUS_DICT_ENTRY_BEGIN_CHAR_AS_STRING
+					DBUS_TYPE_STRING_AS_STRING
+					DBUS_TYPE_VARIANT_AS_STRING
+					DBUS_DICT_ENTRY_END_CHAR_AS_STRING,
+					&props);
+
+	dict_append_entry(&props, "Path", DBUS_TYPE_OBJECT_PATH,
+							&endpoint->path);
+	dict_append_entry(&props, "Codec", DBUS_TYPE_BYTE, &endpoint->codec);
+	dict_append_array(&props, "Capabilities", DBUS_TYPE_BYTE,
+				&endpoint->capabilities, endpoint->size);
+
+	dbus_message_iter_close_container(&var, &props);
+	dbus_message_iter_close_container(&entry, &var);
+	dbus_message_iter_close_container(dict, &entry);
+}
+
+static bool endpoint_properties_get(const char *uuid,
+						struct btd_device *dev,
+						DBusMessageIter *iter,
+						void *user_data)
+{
+	struct media_adapter *adapter = user_data;
+	DBusMessageIter dict;
+	GSList *l;
+
+	dbus_message_iter_open_container(iter, DBUS_TYPE_ARRAY,
+					DBUS_DICT_ENTRY_BEGIN_CHAR_AS_STRING
+					DBUS_TYPE_STRING_AS_STRING
+					DBUS_TYPE_VARIANT_AS_STRING
+					DBUS_DICT_ENTRY_END_CHAR_AS_STRING,
+					&dict);
+
+	for (l = adapter->endpoints; l; l = l->next) {
+		struct media_endpoint *endpoint = l->data;
+
+		if (g_strcmp0(endpoint->uuid, uuid) != 0)
+			continue;
+
+		append_endpoint(endpoint, &dict);
+	}
+
+	dbus_message_iter_close_container(iter, &dict);
+
+	return true;
+}
+
 static struct media_endpoint *media_endpoint_create(struct media_adapter *adapter,
 						const char *sender,
 						const char *path,
@@ -629,6 +736,13 @@ static struct media_endpoint *media_endpoint_create(struct media_adapter *adapte
 						sender, media_endpoint_exit,
 						endpoint, NULL);
 
+	if (media_adapter_find_endpoint(adapter, NULL, NULL, uuid) == NULL) {
+		btd_profile_add_custom_prop(uuid, "a{sv}", "Endpoints",
+						endpoint_properties_exists,
+						endpoint_properties_get,
+						adapter);
+	}
+
 	adapter->endpoints = g_slist_append(adapter->endpoints, endpoint);
 	info("Endpoint registered: sender=%s path=%s", sender, path);
 
@@ -637,32 +751,6 @@ static struct media_endpoint *media_endpoint_create(struct media_adapter *adapte
 	return endpoint;
 }
 
-static struct media_endpoint *media_adapter_find_endpoint(
-						struct media_adapter *adapter,
-						const char *sender,
-						const char *path,
-						const char *uuid)
-{
-	GSList *l;
-
-	for (l = adapter->endpoints; l; l = l->next) {
-		struct media_endpoint *endpoint = l->data;
-
-		if (sender && g_strcmp0(endpoint->sender, sender) != 0)
-			continue;
-
-		if (path && g_strcmp0(endpoint->path, path) != 0)
-			continue;
-
-		if (uuid && g_strcmp0(endpoint->uuid, uuid) != 0)
-			continue;
-
-		return endpoint;
-	}
-
-	return NULL;
-}
-
 static int parse_properties(DBusMessageIter *props, const char **uuid,
 				gboolean *delay_reporting, uint8_t *codec,
 				uint8_t **capabilities, int *size)
-- 
1.7.11.7


^ permalink raw reply related

* Re: [PATCH BlueZ 1/3] avctp: Fix dead assignment in control_response
From: Luiz Augusto von Dentz @ 2012-11-13 13:33 UTC (permalink / raw)
  To: linux-bluetooth
In-Reply-To: <1352812880-7306-3-git-send-email-luiz.dentz@gmail.com>

Hi,

On Tue, Nov 13, 2012 at 3:21 PM, Luiz Augusto von Dentz
<luiz.dentz@gmail.com> wrote:
> From: Szymon Janc <szymon.janc@tieto.com>
>
> Value stored to req is never read before writing it again.
> ---
>  audio/avctp.c | 2 +-
>  1 file changed, 1 insertion(+), 1 deletion(-)
>
> diff --git a/audio/avctp.c b/audio/avctp.c
> index 6ba25e4..29756f6 100644
> --- a/audio/avctp.c
> +++ b/audio/avctp.c
> @@ -577,7 +577,7 @@ static void control_response(struct avctp_channel *control,
>                                         size_t operand_count)
>  {
>         struct avctp_pending_req *p = control->p;
> -       struct avctp_control_req *req = p->data;
> +       struct avctp_control_req *req;
>         GSList *l;
>
>         if (p && p->transaction == avctp->transaction) {
> --
> 1.7.11.7

Please ignore this set, it was in my outgoing folder as I just applied
them but they are not part of HFP patchset.


-- 
Luiz Augusto von Dentz

^ permalink raw reply

* Re: [PATCH BlueZ 00/13] Remove HFP implementation
From: Johan Hedberg @ 2012-11-13 14:16 UTC (permalink / raw)
  To: Luiz Augusto von Dentz; +Cc: linux-bluetooth
In-Reply-To: <1352812880-7306-1-git-send-email-luiz.dentz@gmail.com>

Hi Luiz,

On Tue, Nov 13, 2012, Luiz Augusto von Dentz wrote:
> These changes remove HFP implemention from audio plugin and move audio
> under profiles directory.
> 
> HFP can be emulated by test-profile -u hfp, all the telephony backends
> are gone as well since this is now suppose to be a external profile
> probably done inside the telephony stack e.g. oFono in use in the
> platform.
> 
> Luiz Augusto von Dentz (13):
>   audio: Remove HFP and HSP headset role support
>   audio: Remove HFP option from audio.conf
>   audio: Remove code using headset
>   build: Remove telephony-maemo5.c
>   build: Remove telephony-maemo6.c
>   build: Remove telephony-ofono.c
>   build: Remove telephony-dummy.c
>   build: Remove telephony.h
>   build: Remove headset.c and headset.h
>   audio: Remove code HFP and HS gateway role
>   build: Remove gateway.c and gateway.h
>   audio: Move to profiles directory
>   audio: Add support for passing endpoints as custom property
> 
>  Makefile.am                             |   48 +-
>  audio/gateway.c                         | 1048 ------------
>  audio/gateway.h                         |   75 -
>  audio/headset.c                         | 2825 -------------------------------
>  audio/headset.h                         |  112 --
>  audio/manager.c                         | 1387 ---------------
>  audio/telephony-dummy.c                 |  444 -----
>  audio/telephony-maemo5.c                | 2102 -----------------------
>  audio/telephony-maemo6.c                | 2196 ------------------------
>  audio/telephony-ofono.c                 | 1636 ------------------
>  audio/telephony.h                       |  244 ---
>  {audio => profiles/audio}/a2dp-codecs.h |    0
>  {audio => profiles/audio}/a2dp.c        |    0
>  {audio => profiles/audio}/a2dp.h        |    0
>  {audio => profiles/audio}/audio.conf    |    4 -
>  {audio => profiles/audio}/avctp.c       |    0
>  {audio => profiles/audio}/avctp.h       |    0
>  {audio => profiles/audio}/avdtp.c       |    0
>  {audio => profiles/audio}/avdtp.h       |    0
>  {audio => profiles/audio}/avrcp.c       |    0
>  {audio => profiles/audio}/avrcp.h       |    0
>  {audio => profiles/audio}/control.c     |    0
>  {audio => profiles/audio}/control.h     |    0
>  {audio => profiles/audio}/device.c      |  198 +--
>  {audio => profiles/audio}/device.h      |    2 -
>  {audio => profiles/audio}/main.c        |   98 +-
>  profiles/audio/manager.c                |  552 ++++++
>  {audio => profiles/audio}/manager.h     |    7 +-
>  {audio => profiles/audio}/media.c       |  245 ++-
>  {audio => profiles/audio}/media.h       |    0
>  {audio => profiles/audio}/player.c      |    0
>  {audio => profiles/audio}/player.h      |    0
>  {audio => profiles/audio}/rtp.h         |    0
>  {audio => profiles/audio}/sink.c        |    0
>  {audio => profiles/audio}/sink.h        |    0
>  {audio => profiles/audio}/source.c      |    0
>  {audio => profiles/audio}/source.h      |    0
>  {audio => profiles/audio}/transport.c   |  380 -----
>  {audio => profiles/audio}/transport.h   |    0
>  39 files changed, 673 insertions(+), 12930 deletions(-)
>  delete mode 100644 audio/gateway.c
>  delete mode 100644 audio/gateway.h
>  delete mode 100644 audio/headset.c
>  delete mode 100644 audio/headset.h
>  delete mode 100644 audio/manager.c
>  delete mode 100644 audio/telephony-dummy.c
>  delete mode 100644 audio/telephony-maemo5.c
>  delete mode 100644 audio/telephony-maemo6.c
>  delete mode 100644 audio/telephony-ofono.c
>  delete mode 100644 audio/telephony.h
>  rename {audio => profiles/audio}/a2dp-codecs.h (100%)
>  rename {audio => profiles/audio}/a2dp.c (100%)
>  rename {audio => profiles/audio}/a2dp.h (100%)
>  rename {audio => profiles/audio}/audio.conf (93%)
>  rename {audio => profiles/audio}/avctp.c (100%)
>  rename {audio => profiles/audio}/avctp.h (100%)
>  rename {audio => profiles/audio}/avdtp.c (100%)
>  rename {audio => profiles/audio}/avdtp.h (100%)
>  rename {audio => profiles/audio}/avrcp.c (100%)
>  rename {audio => profiles/audio}/avrcp.h (100%)
>  rename {audio => profiles/audio}/control.c (100%)
>  rename {audio => profiles/audio}/control.h (100%)
>  rename {audio => profiles/audio}/device.c (69%)
>  rename {audio => profiles/audio}/device.h (96%)
>  rename {audio => profiles/audio}/main.c (53%)
>  create mode 100644 profiles/audio/manager.c
>  rename {audio => profiles/audio}/manager.h (89%)
>  rename {audio => profiles/audio}/media.c (91%)
>  rename {audio => profiles/audio}/media.h (100%)
>  rename {audio => profiles/audio}/player.c (100%)
>  rename {audio => profiles/audio}/player.h (100%)
>  rename {audio => profiles/audio}/rtp.h (100%)
>  rename {audio => profiles/audio}/sink.c (100%)
>  rename {audio => profiles/audio}/sink.h (100%)
>  rename {audio => profiles/audio}/source.c (100%)
>  rename {audio => profiles/audio}/source.h (100%)
>  rename {audio => profiles/audio}/transport.c (72%)
>  rename {audio => profiles/audio}/transport.h (100%)

Looks good to me. Feel free to apply.

Johan

^ permalink raw reply

* Re: [PATCH BlueZ 00/13] Remove HFP implementation
From: Luiz Augusto von Dentz @ 2012-11-13 15:39 UTC (permalink / raw)
  To: Luiz Augusto von Dentz, linux-bluetooth
In-Reply-To: <20121113141639.GA28578@x220>

Hi Johan,

On Tue, Nov 13, 2012 at 4:16 PM, Johan Hedberg <johan.hedberg@gmail.com> wrote:
> Hi Luiz,
>
> On Tue, Nov 13, 2012, Luiz Augusto von Dentz wrote:
>> These changes remove HFP implemention from audio plugin and move audio
>> under profiles directory.
>>
>> HFP can be emulated by test-profile -u hfp, all the telephony backends
>> are gone as well since this is now suppose to be a external profile
>> probably done inside the telephony stack e.g. oFono in use in the
>> platform.
>>
>> Luiz Augusto von Dentz (13):
>>   audio: Remove HFP and HSP headset role support
>>   audio: Remove HFP option from audio.conf
>>   audio: Remove code using headset
>>   build: Remove telephony-maemo5.c
>>   build: Remove telephony-maemo6.c
>>   build: Remove telephony-ofono.c
>>   build: Remove telephony-dummy.c
>>   build: Remove telephony.h
>>   build: Remove headset.c and headset.h
>>   audio: Remove code HFP and HS gateway role
>>   build: Remove gateway.c and gateway.h
>>   audio: Move to profiles directory
>>   audio: Add support for passing endpoints as custom property
>>
>>  Makefile.am                             |   48 +-
>>  audio/gateway.c                         | 1048 ------------
>>  audio/gateway.h                         |   75 -
>>  audio/headset.c                         | 2825 -------------------------------
>>  audio/headset.h                         |  112 --
>>  audio/manager.c                         | 1387 ---------------
>>  audio/telephony-dummy.c                 |  444 -----
>>  audio/telephony-maemo5.c                | 2102 -----------------------
>>  audio/telephony-maemo6.c                | 2196 ------------------------
>>  audio/telephony-ofono.c                 | 1636 ------------------
>>  audio/telephony.h                       |  244 ---
>>  {audio => profiles/audio}/a2dp-codecs.h |    0
>>  {audio => profiles/audio}/a2dp.c        |    0
>>  {audio => profiles/audio}/a2dp.h        |    0
>>  {audio => profiles/audio}/audio.conf    |    4 -
>>  {audio => profiles/audio}/avctp.c       |    0
>>  {audio => profiles/audio}/avctp.h       |    0
>>  {audio => profiles/audio}/avdtp.c       |    0
>>  {audio => profiles/audio}/avdtp.h       |    0
>>  {audio => profiles/audio}/avrcp.c       |    0
>>  {audio => profiles/audio}/avrcp.h       |    0
>>  {audio => profiles/audio}/control.c     |    0
>>  {audio => profiles/audio}/control.h     |    0
>>  {audio => profiles/audio}/device.c      |  198 +--
>>  {audio => profiles/audio}/device.h      |    2 -
>>  {audio => profiles/audio}/main.c        |   98 +-
>>  profiles/audio/manager.c                |  552 ++++++
>>  {audio => profiles/audio}/manager.h     |    7 +-
>>  {audio => profiles/audio}/media.c       |  245 ++-
>>  {audio => profiles/audio}/media.h       |    0
>>  {audio => profiles/audio}/player.c      |    0
>>  {audio => profiles/audio}/player.h      |    0
>>  {audio => profiles/audio}/rtp.h         |    0
>>  {audio => profiles/audio}/sink.c        |    0
>>  {audio => profiles/audio}/sink.h        |    0
>>  {audio => profiles/audio}/source.c      |    0
>>  {audio => profiles/audio}/source.h      |    0
>>  {audio => profiles/audio}/transport.c   |  380 -----
>>  {audio => profiles/audio}/transport.h   |    0
>>  39 files changed, 673 insertions(+), 12930 deletions(-)
>>  delete mode 100644 audio/gateway.c
>>  delete mode 100644 audio/gateway.h
>>  delete mode 100644 audio/headset.c
>>  delete mode 100644 audio/headset.h
>>  delete mode 100644 audio/manager.c
>>  delete mode 100644 audio/telephony-dummy.c
>>  delete mode 100644 audio/telephony-maemo5.c
>>  delete mode 100644 audio/telephony-maemo6.c
>>  delete mode 100644 audio/telephony-ofono.c
>>  delete mode 100644 audio/telephony.h
>>  rename {audio => profiles/audio}/a2dp-codecs.h (100%)
>>  rename {audio => profiles/audio}/a2dp.c (100%)
>>  rename {audio => profiles/audio}/a2dp.h (100%)
>>  rename {audio => profiles/audio}/audio.conf (93%)
>>  rename {audio => profiles/audio}/avctp.c (100%)
>>  rename {audio => profiles/audio}/avctp.h (100%)
>>  rename {audio => profiles/audio}/avdtp.c (100%)
>>  rename {audio => profiles/audio}/avdtp.h (100%)
>>  rename {audio => profiles/audio}/avrcp.c (100%)
>>  rename {audio => profiles/audio}/avrcp.h (100%)
>>  rename {audio => profiles/audio}/control.c (100%)
>>  rename {audio => profiles/audio}/control.h (100%)
>>  rename {audio => profiles/audio}/device.c (69%)
>>  rename {audio => profiles/audio}/device.h (96%)
>>  rename {audio => profiles/audio}/main.c (53%)
>>  create mode 100644 profiles/audio/manager.c
>>  rename {audio => profiles/audio}/manager.h (89%)
>>  rename {audio => profiles/audio}/media.c (91%)
>>  rename {audio => profiles/audio}/media.h (100%)
>>  rename {audio => profiles/audio}/player.c (100%)
>>  rename {audio => profiles/audio}/player.h (100%)
>>  rename {audio => profiles/audio}/rtp.h (100%)
>>  rename {audio => profiles/audio}/sink.c (100%)
>>  rename {audio => profiles/audio}/sink.h (100%)
>>  rename {audio => profiles/audio}/source.c (100%)
>>  rename {audio => profiles/audio}/source.h (100%)
>>  rename {audio => profiles/audio}/transport.c (72%)
>>  rename {audio => profiles/audio}/transport.h (100%)
>
> Looks good to me. Feel free to apply.

Pushed upstream.

-- 
Luiz Augusto von Dentz

^ permalink raw reply

* Re: [PATCH BlueZ 1/2] audio: Fix headset NULL pointer dereference during AT+BLDN response
From: Johan Hedberg @ 2012-11-13 15:40 UTC (permalink / raw)
  To: Syam Sidhardhan; +Cc: Syam Sidhardhan, linux-bluetooth
In-Reply-To: <CAFBvHifFX-8vcQciLktVhUgjN7Z-QaQmST2Jbi=gKtz96iHLvg@mail.gmail.com>

Hi Syam,

On Fri, Nov 09, 2012, Syam Sidhardhan wrote:
> On Tue, Oct 23, 2012 at 7:27 PM, Syam Sidhardhan <s.syam@samsung.com> wrote:
> > While waiting for the AT+BLDN asynchronous response, if RFCOMM got
> > disconnected, then respose will cause NULL pointer dereference.
> >
> > During headset disconnection, the headset state changes from
> > HEADSET_STATE_CONNECTED to HEADSET_STATE_DISCONNECTED along with
> > freeing the dev->headset. During the response, in telephony_generic_rsp
> > its dereferencing.
> >
> > Log:
> > bluetoothd[5573]: audio/headset.c:handle_event() Received AT+BLDN
> > bluetoothd[5573]: audio/telephony.c:telephony_last_dialed_number_req()
> >  telephony-tizen: last dialed number request
> > bluetoothd[5573]: audio/telephony.c:dbus_method_call_send() +
> > bluetoothd[5573]: audio/telephony.c:dbus_method_call_send() -
> > bluetoothd[5573]: Endpoint replied with an error: org.freedesktop.DBus\
> >  .Error.NoReply
> > bluetoothd[5573]: audio/telephony.c:telephony_device_disconnected()
> >  telephony-tizen: device 0x40439b60 disconnected
> > bluetoothd[5573]: audio/headset.c:headset_set_state() State changed
> >  /org/bluez/5573/hci0/dev_BC_47_60_F5_88_89:
> >  HEADSET_STATE_CONNECTED -> HEADSET_STATE_DISCONNECTED
> > bluetoothd[5573]: audio/media.c:headset_state_changed()
> > bluetoothd[5573]: audio/media.c:headset_state_changed() Clear endpoint
> >  0x40430620
> > bluetoothd[5573]: audio/telephony.c:telephony_dial_number_reply()
> >  redial_reply
> > bluetoothd[5573]: audio/telephony.c:telephony_dial_number_reply()
> >  dial_reply reply: No Call log
> > ---
> >  audio/headset.c |    3 +++
> >  1 files changed, 3 insertions(+), 0 deletions(-)
> >
> > diff --git a/audio/headset.c b/audio/headset.c
> > index bd83a65..30d24cf 100644
> > --- a/audio/headset.c
> > +++ b/audio/headset.c
> > @@ -689,6 +689,9 @@ static int telephony_generic_rsp(struct audio_device *device, cme_error_t err)
> >         struct headset *hs = device->headset;
> >         struct headset_slc *slc = hs->slc;
> >
> > +       if (!slc)
> > +               return -EIO;
> > +
> >         if ((err != CME_ERROR_NONE) && slc->cme_enabled)
> >                 return headset_send(hs, "\r\n+CME ERROR: %d\r\n", err);
> >
> 
> ping.

This file doesn't exist in bluez.git anymore.

Johan

^ permalink raw reply

* [PATCH BlueZ 1/2] TODO: Add entry for runtime selection of drivers
From: Anderson Lizardo @ 2012-11-13 15:49 UTC (permalink / raw)
  To: linux-bluetooth; +Cc: Anderson Lizardo

This will allow to drop usage of symlinks to C files, which require
messing with CPPFLAGS so headers can be found by the preprocessor.

It also allows for easier testing, because it is not necessary to
rebuild BlueZ to test different drivers.
---
 TODO |    9 +++++++++
 1 file changed, 9 insertions(+)

diff --git a/TODO b/TODO
index ca14955..4f58423 100644
--- a/TODO
+++ b/TODO
@@ -36,6 +36,15 @@ General
   Priority: Low
   Complexity: C1
 
+- Remove usage of symlinks for drivers, such as profiles/input/suspend.c and
+  profiles/sap/sap.c. Instead, select drivers at runtime by using config
+  options or probing for running D-Bus services (using e.g.
+  g_dbus_add_service_watch()). Idea first mentioned on
+  http://thread.gmane.org/gmane.linux.bluez.kernel/30175/focus=30190.
+
+  Priority: Low
+  Complexity: C2
+
 BlueZ 5
 =======
 
-- 
1.7.9.5


^ permalink raw reply related

* [PATCH BlueZ 2/2] TODO: Trivial typo fixes
From: Anderson Lizardo @ 2012-11-13 15:49 UTC (permalink / raw)
  To: linux-bluetooth; +Cc: Anderson Lizardo
In-Reply-To: <1352821786-20230-1-git-send-email-anderson.lizardo@openbossa.org>

---
 TODO |   10 +++++-----
 1 file changed, 5 insertions(+), 5 deletions(-)

diff --git a/TODO b/TODO
index 4f58423..ad3232b 100644
--- a/TODO
+++ b/TODO
@@ -24,7 +24,7 @@ General
   Priority: high
   Complexity: C4
 
-- Rename glib-helper file to a more convenient name. The ideia is try to keep
+- Rename glib-helper file to a more convenient name. The idea is try to keep
   only sdp helpers functions. bt_* prefix shall be also changed.
 
   Priority: Low
@@ -48,7 +48,7 @@ General
 BlueZ 5
 =======
 
-Priority/Complexity ommited as all items are required before 5.0 is
+Priority/Complexity omitted as all items are required before 5.0 is
 released.
 
 - Remove telephony driver framework and replace with a org.bluez.Profile
@@ -163,7 +163,7 @@ Low Energy
   Complexity: C1
 
 - Static random address setup and storage. Once this address is written
-  in the a given remote, the address can not be changed anymore.
+  in a given remote, the address can not be changed anymore.
 
   Priority: Low
   Complexity: C1
@@ -178,7 +178,7 @@ Low Energy
 
 - Device Name Characteristic is a GAP characteristic for Low Energy. This
   characteristic shall be integrated/used in the discovery procedure. The
-  ideia is to report the value of this characteristic using DeviceFound signals.
+  idea is to report the value of this characteristic using DeviceFound signals.
   Discussion with the community is needed before to start this task. Other GAP
   characteristics for LE needs to follow a similar approach. It is not clear
   if all GAP characteristics can be exposed using properties instead of a primary
@@ -268,7 +268,7 @@ ATT/GATT
   Priority: Low
   Complecity: C1
 
-- Add sdp discovery support to gattool with BR (--sdp, default is 0x1f)
+- Add sdp discovery support to gatttool with BR (--sdp, default is 0x1f)
 
   Priority: Low
   Complexity: C1
-- 
1.7.9.5


^ permalink raw reply related

* net, bluetooth: object debug warning in bt_host_release()
From: Sasha Levin @ 2012-11-13 16:18 UTC (permalink / raw)
  To: marcel, gustavo, Johan Hedberg, David S. Miller
  Cc: linux-bluetooth, netdev, linux-kernel@vger.kernel.org, Dave Jones

Hi all,

While fuzzing with trinity on a KVM tools (lkvm) guest running latest -next kernel I've
stumbled on the following:

[ 1434.201149] ------------[ cut here ]------------
[ 1434.204998] WARNING: at lib/debugobjects.c:261 debug_print_object+0x8e/0xb0()
[ 1434.208324] ODEBUG: free active (active state 0) object type: work_struct hint: hci_power_on+0x0/0x90
[ 1434.210386] Pid: 8564, comm: trinity-child25 Tainted: G        W    3.7.0-rc5-next-20121112-sasha-00018-g2f4ce0e #127
[ 1434.210760] Call Trace:
[ 1434.210760]  [<ffffffff819f3d6e>] ? debug_print_object+0x8e/0xb0
[ 1434.210760]  [<ffffffff8110b887>] warn_slowpath_common+0x87/0xb0
[ 1434.210760]  [<ffffffff8110b911>] warn_slowpath_fmt+0x41/0x50
[ 1434.210760]  [<ffffffff819f3d6e>] debug_print_object+0x8e/0xb0
[ 1434.210760]  [<ffffffff8376b750>] ? hci_dev_open+0x310/0x310
[ 1434.210760]  [<ffffffff83bf94e5>] ? _raw_spin_unlock_irqrestore+0x55/0xa0
[ 1434.210760]  [<ffffffff819f3ee5>] __debug_check_no_obj_freed+0xa5/0x230
[ 1434.210760]  [<ffffffff83785db0>] ? bt_host_release+0x10/0x20
[ 1434.210760]  [<ffffffff819f4d15>] debug_check_no_obj_freed+0x15/0x20
[ 1434.210760]  [<ffffffff8125eee7>] kfree+0x227/0x330
[ 1434.210760]  [<ffffffff83785db0>] bt_host_release+0x10/0x20
[ 1434.210760]  [<ffffffff81e539e5>] device_release+0x65/0xc0
[ 1434.210760]  [<ffffffff819d3975>] kobject_cleanup+0x145/0x190
[ 1434.210760]  [<ffffffff819d39cd>] kobject_release+0xd/0x10
[ 1434.210760]  [<ffffffff819d33cc>] kobject_put+0x4c/0x60
[ 1434.210760]  [<ffffffff81e548b2>] put_device+0x12/0x20
[ 1434.210760]  [<ffffffff8376a334>] hci_free_dev+0x24/0x30
[ 1434.210760]  [<ffffffff82fd8fe1>] vhci_release+0x31/0x60
[ 1434.210760]  [<ffffffff8127be12>] __fput+0x122/0x250
[ 1434.210760]  [<ffffffff811cab0d>] ? rcu_user_exit+0x9d/0xd0
[ 1434.210760]  [<ffffffff8127bf49>] ____fput+0x9/0x10
[ 1434.210760]  [<ffffffff81133402>] task_work_run+0xb2/0xf0
[ 1434.210760]  [<ffffffff8106cfa7>] do_notify_resume+0x77/0xa0
[ 1434.210760]  [<ffffffff83bfb0ea>] int_signal+0x12/0x17
[ 1434.210760] ---[ end trace a6d57fefbc8a8cc7 ]---

Not that the guest doesn't emulate anything that looks like a bluetooth device or
has bluetooth capabilities.


Thanks,
Sasha

^ permalink raw reply

* Re: [PATCH BlueZ 1/2] audio: Fix headset NULL pointer dereference during AT+BLDN response
From: Syam Sidhardhan @ 2012-11-13 16:27 UTC (permalink / raw)
  To: Syam Sidhardhan, Syam Sidhardhan, linux-bluetooth
In-Reply-To: <20121113154019.GA29811@x220>

Hi Johan,

On Tue, Nov 13, 2012 at 9:10 PM, Johan Hedberg <johan.hedberg@gmail.com> wrote:
> Hi Syam,
>
> On Fri, Nov 09, 2012, Syam Sidhardhan wrote:
>> On Tue, Oct 23, 2012 at 7:27 PM, Syam Sidhardhan <s.syam@samsung.com> wrote:
>> > While waiting for the AT+BLDN asynchronous response, if RFCOMM got
>> > disconnected, then respose will cause NULL pointer dereference.
>> >
>> > During headset disconnection, the headset state changes from
>> > HEADSET_STATE_CONNECTED to HEADSET_STATE_DISCONNECTED along with
>> > freeing the dev->headset. During the response, in telephony_generic_rsp
>> > its dereferencing.
>> >
>> > Log:
>> > bluetoothd[5573]: audio/headset.c:handle_event() Received AT+BLDN
>> > bluetoothd[5573]: audio/telephony.c:telephony_last_dialed_number_req()
>> >  telephony-tizen: last dialed number request
>> > bluetoothd[5573]: audio/telephony.c:dbus_method_call_send() +
>> > bluetoothd[5573]: audio/telephony.c:dbus_method_call_send() -
>> > bluetoothd[5573]: Endpoint replied with an error: org.freedesktop.DBus\
>> >  .Error.NoReply
>> > bluetoothd[5573]: audio/telephony.c:telephony_device_disconnected()
>> >  telephony-tizen: device 0x40439b60 disconnected
>> > bluetoothd[5573]: audio/headset.c:headset_set_state() State changed
>> >  /org/bluez/5573/hci0/dev_BC_47_60_F5_88_89:
>> >  HEADSET_STATE_CONNECTED -> HEADSET_STATE_DISCONNECTED
>> > bluetoothd[5573]: audio/media.c:headset_state_changed()
>> > bluetoothd[5573]: audio/media.c:headset_state_changed() Clear endpoint
>> >  0x40430620
>> > bluetoothd[5573]: audio/telephony.c:telephony_dial_number_reply()
>> >  redial_reply
>> > bluetoothd[5573]: audio/telephony.c:telephony_dial_number_reply()
>> >  dial_reply reply: No Call log
>> > ---
>> >  audio/headset.c |    3 +++
>> >  1 files changed, 3 insertions(+), 0 deletions(-)
>> >
>> > diff --git a/audio/headset.c b/audio/headset.c
>> > index bd83a65..30d24cf 100644
>> > --- a/audio/headset.c
>> > +++ b/audio/headset.c
>> > @@ -689,6 +689,9 @@ static int telephony_generic_rsp(struct audio_device *device, cme_error_t err)
>> >         struct headset *hs = device->headset;
>> >         struct headset_slc *slc = hs->slc;
>> >
>> > +       if (!slc)
>> > +               return -EIO;
>> > +
>> >         if ((err != CME_ERROR_NONE) && slc->cme_enabled)
>> >                 return headset_send(hs, "\r\n+CME ERROR: %d\r\n", err);
>> >
>>
>> ping.
>
> This file doesn't exist in bluez.git anymore.
>

 Yes,  I noticed Luiz patch which removes the headset.c and other
stuff. Thank you.

Regards,
Syam.

^ permalink raw reply

* Re: [PATCHv1 11/12] Bluetooth: AMP: Use l2cap_physical_cfm in phylink complete evt
From: Mat Martineau @ 2012-11-13 17:29 UTC (permalink / raw)
  To: Andrei Emeltchenko; +Cc: linux-bluetooth, marcel
In-Reply-To: <20121112092641.GA10008@aemeltch-MOBL1>


Hi Andrei -

On Mon, 12 Nov 2012, Andrei Emeltchenko wrote:

> Hi Mat,
>
> On Fri, Nov 02, 2012 at 08:39:09AM -0700, Mat Martineau wrote:
> ...
>>>>> +void amp_physical_cfm(struct hci_conn *bredr_hcon, struct hci_conn *hs_hcon)
>>>>> +{
>>>>> +	struct hci_dev *bredr_hdev = hci_dev_hold(bredr_hcon->hdev);
>>>>> +	struct amp_mgr *mgr = hs_hcon->amp_mgr;
>>>>> +	struct l2cap_chan *bredr_chan;
>>>>> +
>>>>> +	BT_DBG("bredr_hcon %p hs_hcon %p mgr %p", bredr_hcon, hs_hcon, mgr);
>>>>> +
>>>>> +	if (!bredr_hdev || !mgr || !mgr->bredr_chan)
>>>>> +		return;
>>>>> +
>>>>> +	bredr_chan = mgr->bredr_chan;
>>>>> +
>>>>> +	set_bit(FLAG_EFS_ENABLE, &bredr_chan->flags);
>>>>> +	bredr_chan->ctrl_id = hs_hcon->remote_id;
>>>>> +	bredr_chan->hs_hcon = hs_hcon;
>>>>> +	bredr_chan->conn->mtu = hs_hcon->hdev->block_mtu;
>>>>> +	bredr_chan->fcs = L2CAP_FCS_NONE;
>>
>> Changing FCS requires L2CAP reconfiguration for the channel, and
>> chan->fcs shouldn't be modified until reconfiguration happens.
>> While it doesn't make much sense to do so, the remote device may
>> want to keep FCS enabled.  The move may also fail and you don't want
>> to forget the original FCS setting in that case.
>
> So we agree that FCS shall not be used for High Speed channels. I was
> thinking more about the case where we start sending data right over HS
> channel. The configuration should be just started.

No matter what the BlueZ implementation prefers, it must be able to 
handle a remote device that requests FCS during L2CAP config.  If one 
side requests FCS, then it must be used.

Do we want BlueZ to always ignore the L2CAP FCS socket option on AMP 
controllers?  (Marcel?)  This checksum is always redundant with 802.11 
AMP controllers.

> What would be the better place to init FCS? l2cap_physical_cfm after
> checking channel moving status?

I think it should be as late as possible before L2CAP configuration 
begins in order to be sure the channel is really on AMP.  For the 
"create channel" case, set_default_fcs could see if an AMP link is 
being used and turn the FCS off.

>>>> Sorry I missed this earlier: bredr_chan needs to be locked before
>>>> changing it.  I suggest passing the information to
>>>> l2cap_physical_cfm and letting that function update the structure
>>>> members while it holds the lock.
>>>
>>> what about locking here and changing l2cap_physical_cfm to unlocked
>>> __l2cap_physical_cfm ?
>>
>> My preference is to not manipulate l2cap_chan too much outside of
>> l2cap_core, and to keep the channel move or channel create state
>> machines inside l2cap_core.  l2cap_physical_cfm checks the channel
>> state before modifying it.  The move or new connection may have been
>> canceled or be in the wrong state, in which case the structure
>> should not be modified even though the physical link was completed.
>
> so maybe we shall move some code to l2cap_physical_cfm ?

Yes, I think l2cap_physical_cfm is a better place for changes to 
l2cap_chan.


Regards,
--
Mat Martineau

Employee of Qualcomm Innovation Center, Inc.
Qualcomm Innovation Center, Inc. is a member of Code Aurora Forum, hosted by The Linux Foundation

^ permalink raw reply

* Fw: [Bug 50541] New: Kernel OOPS in hidp when resuming from suspend
From: Stephen Hemminger @ 2012-11-13 17:33 UTC (permalink / raw)
  To: Marcel Holtmann; +Cc: linux-bluetooth



Begin forwarded message:

Date: Tue, 13 Nov 2012 17:04:18 +0000 (UTC)
From: bugzilla-daemon@bugzilla.kernel.org
To: shemminger@linux-foundation.org
Subject: [Bug 50541] New: Kernel OOPS in hidp when resuming from suspend


https://bugzilla.kernel.org/show_bug.cgi?id=50541

           Summary: Kernel OOPS in hidp when resuming from suspend
           Product: Networking
           Version: 2.5
    Kernel Version: 3.5
          Platform: All
        OS/Version: Linux
              Tree: Mainline
            Status: NEW
          Severity: normal
          Priority: P1
         Component: Other
        AssignedTo: shemminger@linux-foundation.org
        ReportedBy: karllinuxtest.relton@ntlworld.com
        Regression: Yes


Somewhere between 3.2 and 3.5 an issue with bluetooth keyboards on resuming
from suspend crept in.

On a resume I now get the following:

Oct 23 15:42:34 laptop2 kernel: [10357.752131] BUG: unable to handle kernel
NULL pointer dereference at   (null)
Oct 23 15:42:34 laptop2 kernel: [10357.752273] IP: [<c1037a58>]
__ticket_spin_lock+0x8/0x30
Oct 23 15:42:34 laptop2 kernel: [10357.752379] *pdpt = 0000000000000000 *pde =
f000ec62f000ec62 
Oct 23 15:42:34 laptop2 kernel: [10357.752485] Oops: 0002 [#1] SMP 
Oct 23 15:42:34 laptop2 kernel: [10357.752551] Modules linked in: hid_generic
hid_apple hidp hid bnep rfcomm parport_pc ppdev autofs4 nfsd nfs binfmt_misc
lockd fscache auth_rpcgss nfs_acl sunrpc nls_iso8859_1 dm_crypt arc4
snd_hda_codec_idt snd_hda_intel snd_hda_codec joydev coretemp pcmcia iwlwifi
snd_hwdep snd_pcm yenta_socket snd_seq_midi btusb pcmcia_rsrc snd_rawmidi
pcmcia_core mac80211 kvm bluetooth snd_seq_midi_event snd_seq dell_laptop
dell_wmi cfg80211 snd_timer snd_seq_device microcode psmouse gpio_ich dcdbas
serio_raw sparse_keymap lpc_ich mac_hid snd soundcore snd_page_alloc
firewire_sbp2 lp parport firewire_ohci firewire_core crc_itu_t tg3 i915 wmi
drm_kms_helper drm i2c_algo_bit video
Oct 23 15:42:34 laptop2 kernel: [10357.753834] 
Oct 23 15:42:34 laptop2 kernel: [10357.753868] Pid: 10165, comm:
khidpd_05ac0256 Tainted: G        W    3.5.0-17-generic #28-Ubuntu Dell Inc.
Latitude D630                   /0KU184
Oct 23 15:42:34 laptop2 kernel: [10357.754104] EIP: 0060:[<c1037a58>] EFLAGS:
00010096 CPU: 1
Oct 23 15:42:34 laptop2 kernel: [10357.754205] EIP is at
__ticket_spin_lock+0x8/0x30
Oct 23 15:42:34 laptop2 kernel: [10357.754286] EAX: 00000000 EBX: 00000296 ECX:
00000000 EDX: 00000100
Oct 23 15:42:34 laptop2 kernel: [10357.754393] ESI: dfaedfa4 EDI: 00000000 EBP:
dfaedefc ESP: dfaedefc
Oct 23 15:42:34 laptop2 kernel: [10357.754501]  DS: 007b ES: 007b FS: 00d8 GS:
00e0 SS: 0068
Oct 23 15:42:34 laptop2 kernel: [10357.754594] CR0: 8005003b CR2: 00000000 CR3:
01974000 CR4: 000007f0
Oct 23 15:42:34 laptop2 kernel: [10357.754702] DR0: 00000000 DR1: 00000000 DR2:
00000000 DR3: 00000000
Oct 23 15:42:34 laptop2 kernel: [10357.754808] DR6: ffff0ff0 DR7: 00000400
Oct 23 15:42:34 laptop2 kernel: [10357.754875] Process khidpd_05ac0256 (pid:
10165, ti=dfaec000 task=df2b0cb0 task.ti=dfaec000)
Oct 23 15:42:34 laptop2 kernel: [10357.755021] Stack:
Oct 23 15:42:34 laptop2 kernel: [10357.755058]  dfaedf04 c1037af8 dfaedf18
c15c924d dfaedf98 dfaedfa4 00000000 dfaedf2c
Oct 23 15:42:34 laptop2 kernel: [10357.755221]  c10654b3 00000000 cfb0b800
e56d0c00 dfaedfb8 f902ea9b 00000000 00000001
Oct 23 15:42:34 laptop2 kernel: [10357.755383]  df2b0cb0 cfb0b8c0 e56d1a00
e56d0c00 cfb0b890 cfb0b880 df2b0cb0 e56d1a48
Oct 23 15:42:34 laptop2 kernel: [10357.755544] Call Trace:
Oct 23 15:42:34 laptop2 kernel: [10357.755595]  [<c1037af8>]
default_spin_lock_flags+0x8/0x10
Oct 23 15:42:34 laptop2 kernel: [10357.755698]  [<c15c924d>]
_raw_spin_lock_irqsave+0x2d/0x40
Oct 23 15:42:34 laptop2 kernel: [10357.755800]  [<c10654b3>]
finish_wait+0x33/0x70
Oct 23 15:42:34 laptop2 kernel: [10357.755885]  [<f902ea9b>]
hidp_session+0x48b/0x730 [hidp]
Oct 23 15:42:34 laptop2 kernel: [10357.755985]  [<c1075e90>] ?
try_to_wake_up+0x230/0x230
Oct 23 15:42:34 laptop2 kernel: [10357.756079]  [<c1075e90>] ?
try_to_wake_up+0x230/0x230
Oct 23 15:42:34 laptop2 kernel: [10357.756090]  [<c10654f0>] ?
finish_wait+0x70/0x70
Oct 23 15:42:34 laptop2 kernel: [10357.756090]  [<f902e610>] ?
hidp_input_report.isra.4+0x2a0/0x2a0 [hidp]
Oct 23 15:42:34 laptop2 kernel: [10357.756090]  [<c1064dd2>] kthread+0x72/0x80
Oct 23 15:42:34 laptop2 kernel: [10357.756090]  [<c1064d60>] ?
kthread_freezable_should_stop+0x60/0x60
Oct 23 15:42:34 laptop2 kernel: [10357.756090]  [<c15d04fe>]
kernel_thread_helper+0x6/0x10
Oct 23 15:42:34 laptop2 kernel: [10357.756090] Code: b9 fa 78 03 c1 e9 59 ff ff
ff 90 b8 03 79 03 c1 b9 00 79 03 c1 e9 49 ff ff ff 66 90 66 90 66 90 66 90 90
55 ba 00 01 00 00 89 e5 <f0> 66 0f c1 10 0f b6 ce 38 d1 74 0d 8d 74 26 00 f3 90
0f b6 10 
Oct 23 15:42:34 laptop2 kernel: [10357.756090] EIP: [<c1037a58>]
__ticket_spin_lock+0x8/0x30 SS:ESP 0068:dfaedefc
Oct 23 15:42:34 laptop2 kernel: [10357.756090] CR2: 0000000000000000
Oct 23 15:42:34 laptop2 kernel: [10357.756090] ---[ end trace 9a445e0f7d0acd41
]---

The issue seems to be in hidp, which makes sense.

Problem still exists in 3.7.

-- 
Configure bugmail: https://bugzilla.kernel.org/userprefs.cgi?tab=email
------- You are receiving this mail because: -------
You are the assignee for the bug.

^ permalink raw reply

* Re: [PATCH BlueZ 1/2] TODO: Add entry for runtime selection of drivers
From: Johan Hedberg @ 2012-11-13 17:42 UTC (permalink / raw)
  To: Anderson Lizardo; +Cc: linux-bluetooth
In-Reply-To: <1352821786-20230-1-git-send-email-anderson.lizardo@openbossa.org>

Hi Lizardo,

On Tue, Nov 13, 2012, Anderson Lizardo wrote:
> This will allow to drop usage of symlinks to C files, which require
> messing with CPPFLAGS so headers can be found by the preprocessor.
> 
> It also allows for easier testing, because it is not necessary to
> rebuild BlueZ to test different drivers.
> ---
>  TODO |    9 +++++++++
>  1 file changed, 9 insertions(+)

Both patches have been applied. Thanks.

Johan

^ permalink raw reply


This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox