/*
 *
 *  BlueZ - Bluetooth protocol stack for Linux
 *
 *  Copyright (C) 2013-2014  Intel Corporation. All rights reserved.
 *
 *
 *  This library is free software; you can redistribute it and/or
 *  modify it under the terms of the GNU Lesser General Public
 *  License as published by the Free Software Foundation; either
 *  version 2.1 of the License, or (at your option) any later version.
 *
 *  This library 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
 *  Lesser General Public License for more details.
 *
 *  You should have received a copy of the GNU Lesser General Public
 *  License along with this library; 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 <stdbool.h>
#include <stdlib.h>
#include <errno.h>
#include <unistd.h>
#include <fcntl.h>
#include <glib.h>

#include "btio/btio.h"
#include "lib/bluetooth.h"
#include "lib/sdp.h"
#include "lib/sdp_lib.h"
#include "profiles/audio/a2dp-codecs.h"
#include "src/log.h"
#include "hal-msg.h"
#include "ipc-common.h"
#include "ipc.h"
#include "a2dp.h"
#include "utils.h"
#include "bluetooth.h"
#include "avdtp.h"
#include "avrcp.h"
#include "audio-msg.h"

#define SVC_HINT_CAPTURING 0x08
#define IDLE_TIMEOUT 1
#define AUDIO_RETRY_TIMEOUT 2

static GIOChannel *server = NULL;
static GSList *devices = NULL;
static GSList *endpoints = NULL;
static GSList *setups = NULL;
static bdaddr_t adapter_addr;
static uint32_t record_id = 0;
static guint audio_retry_id = 0;
static bool audio_retrying = false;

static struct ipc *hal_ipc = NULL;
static struct ipc *audio_ipc = NULL;

struct a2dp_preset {
	void *data;
	int8_t len;
};

struct a2dp_endpoint {
	uint8_t id;
	uint8_t codec;
	struct avdtp_local_sep *sep;
	struct a2dp_preset *caps;
	GSList *presets;
};

struct a2dp_device {
	bdaddr_t	dst;
	uint8_t		state;
	GIOChannel	*io;
	struct avdtp	*session;
	guint		idle_id;
};

struct a2dp_setup {
	struct a2dp_device *dev;
	struct a2dp_endpoint *endpoint;
	struct a2dp_preset *preset;
	struct avdtp_stream *stream;
	uint8_t state;
};

static int device_cmp(gconstpointer s, gconstpointer user_data)
{
	const struct a2dp_device *dev = s;
	const bdaddr_t *dst = user_data;

	return bacmp(&dev->dst, dst);
}

static void preset_free(void *data)
{
	struct a2dp_preset *preset = data;

	g_free(preset->data);
	g_free(preset);
}

static void unregister_endpoint(void *data)
{
	struct a2dp_endpoint *endpoint = data;

	if (endpoint->sep)
		avdtp_unregister_sep(endpoint->sep);

	if (endpoint->caps)
		preset_free(endpoint->caps);

	g_slist_free_full(endpoint->presets, preset_free);

	g_free(endpoint);
}

static void setup_free(void *data)
{
	struct a2dp_setup *setup = data;

	if (!g_slist_find(setup->endpoint->presets, setup->preset))
		preset_free(setup->preset);

	g_free(setup);
}

static void setup_remove(struct a2dp_setup *setup)
{
	setups = g_slist_remove(setups, setup);
	setup_free(setup);
}

static void setup_remove_all_by_dev(struct a2dp_device *dev)
{
	GSList *l = setups;

	while (l) {
		struct a2dp_setup *setup = l->data;
		GSList *next = g_slist_next(l);

		if (setup->dev == dev)
			setup_remove(setup);

		l = next;
	}
}

static void a2dp_device_free(void *data)
{
	struct a2dp_device *dev = data;

	if (dev->idle_id > 0)
		g_source_remove(dev->idle_id);

	if (dev->session)
		avdtp_unref(dev->session);

	if (dev->io) {
		g_io_channel_shutdown(dev->io, FALSE, NULL);
		g_io_channel_unref(dev->io);
	}

	setup_remove_all_by_dev(dev);

	g_free(dev);
}

static void a2dp_device_remove(struct a2dp_device *dev)
{
	devices = g_slist_remove(devices, dev);
	a2dp_device_free(dev);
}

static struct a2dp_device *a2dp_device_new(const bdaddr_t *dst)
{
	struct a2dp_device *dev;

	dev = g_new0(struct a2dp_device, 1);
	bacpy(&dev->dst, dst);
	devices = g_slist_prepend(devices, dev);

	return dev;
}

static bool a2dp_device_connect(struct a2dp_device *dev, BtIOConnect cb)
{
	GError *err = NULL;

	dev->io = bt_io_connect(cb, dev, NULL, &err,
					BT_IO_OPT_SOURCE_BDADDR, &adapter_addr,
					BT_IO_OPT_DEST_BDADDR, &dev->dst,
					BT_IO_OPT_PSM, AVDTP_PSM,
					BT_IO_OPT_SEC_LEVEL, BT_IO_SEC_MEDIUM,
					BT_IO_OPT_INVALID);
	if (err) {
		error("%s", err->message);
		g_error_free(err);
		return false;
	}

	return true;
}

static void bt_a2dp_notify_state(struct a2dp_device *dev, uint8_t state)
{
	struct hal_ev_a2dp_conn_state ev;
	char address[18];

	if (dev->state == state)
		return;

	dev->state = state;

	ba2str(&dev->dst, address);
	DBG("device %s state %u", address, state);

	bdaddr2android(&dev->dst, ev.bdaddr);
	ev.state = state;

	ipc_send_notif(hal_ipc, HAL_SERVICE_ID_A2DP, HAL_EV_A2DP_CONN_STATE,
							sizeof(ev), &ev);

	if (state != HAL_A2DP_STATE_DISCONNECTED)
		return;

	bt_avrcp_disconnect(&dev->dst);

	a2dp_device_remove(dev);
}

static void bt_audio_notify_state(struct a2dp_setup *setup, uint8_t state)
{
	struct hal_ev_a2dp_audio_state ev;
	char address[18];

	if (setup->state == state)
		return;

	setup->state = state;

	ba2str(&setup->dev->dst, address);
	DBG("device %s state %u", address, state);

	bdaddr2android(&setup->dev->dst, ev.bdaddr);
	ev.state = state;

	ipc_send_notif(hal_ipc, HAL_SERVICE_ID_A2DP, HAL_EV_A2DP_AUDIO_STATE,
							sizeof(ev), &ev);
}

static void disconnect_cb(void *user_data)
{
	struct a2dp_device *dev = user_data;

	bt_a2dp_notify_state(dev, HAL_A2DP_STATE_DISCONNECTED);
}

static int sbc_check_config(void *caps, uint8_t caps_len, void *conf,
							uint8_t conf_len)
{
	a2dp_sbc_t *cap, *config;

	if (conf_len != caps_len || conf_len != sizeof(a2dp_sbc_t)) {
		error("SBC: Invalid configuration size (%u)", conf_len);
		return -EINVAL;
	}

	cap = caps;
	config = conf;

	if (!(cap->frequency & config->frequency)) {
		error("SBC: Unsupported frequency (%u) by endpoint",
							config->frequency);
		return -EINVAL;
	}

	if (!(cap->channel_mode & config->channel_mode)) {
		error("SBC: Unsupported channel mode (%u) by endpoint",
							config->channel_mode);
		return -EINVAL;
	}

	if (!(cap->block_length & config->block_length)) {
		error("SBC: Unsupported block length (%u) by endpoint",
							config->block_length);
		return -EINVAL;
	}

	if (!(cap->allocation_method & config->allocation_method)) {
		error("SBC: Unsupported allocation method (%u) by endpoint",
							config->block_length);
		return -EINVAL;
	}

	if (config->max_bitpool < cap->min_bitpool) {
		error("SBC: Invalid maximun bitpool (%u < %u)",
					config->max_bitpool, cap->min_bitpool);
		return -EINVAL;
	}

	if (config->min_bitpool > cap->max_bitpool) {
		error("SBC: Invalid minimun bitpool (%u > %u)",
					config->min_bitpool, cap->min_bitpool);
		return -EINVAL;
	}

	if (config->max_bitpool > cap->max_bitpool)
		return -ERANGE;

	if (config->min_bitpool < cap->min_bitpool)
		return -ERANGE;

	return 0;
}

static int aac_check_config(void *caps, uint8_t caps_len, void *conf,
							uint8_t conf_len)
{
	a2dp_aac_t *cap, *config;

	if (conf_len != caps_len || conf_len != sizeof(a2dp_aac_t)) {
		error("AAC: Invalid configuration size (%u)", conf_len);
		return -EINVAL;
	}

	cap = caps;
	config = conf;

	if (!(cap->object_type & config->object_type)) {
		error("AAC: Unsupported object type (%u) by endpoint",
							config->object_type);
		return -EINVAL;
	}

	if (!(AAC_GET_FREQUENCY(*cap) & AAC_GET_FREQUENCY(*config))) {
		error("AAC: Unsupported frequency (%u) by endpoint",
						AAC_GET_FREQUENCY(*config));
		return -EINVAL;
	}

	if (!(cap->channels & config->channels)) {
		error("AAC: Unsupported channels (%u) by endpoint",
							config->channels);
		return -EINVAL;
	}

	/* VBR support in SNK is mandatory but let's make sure we don't try to
	 * have VBR on remote which for some reason does not support it
	 */
	if (!cap->vbr && config->vbr) {
		error("AAC: Unsupported VBR (%u) by endpoint",
							config->vbr);
		return -EINVAL;
	}

	if (AAC_GET_BITRATE(*cap) < AAC_GET_BITRATE(*config))
		return -ERANGE;

	return 0;
}

static int aptx_check_config(void *caps, uint8_t caps_len, void *conf,
							uint8_t conf_len)
{
	a2dp_aptx_t *cap, *config;

	if (conf_len != caps_len || conf_len != sizeof(a2dp_aptx_t)) {
		error("APTX: Invalid configuration size (%u)", conf_len);
		return -EINVAL;
	}

	cap = caps;
	config = conf;

	if (!(cap->frequency & config->frequency)) {
		error("APTX: Unsupported frequenct (%u) by endpoint",
							config->frequency);
		return -EINVAL;
	}

	if (!(cap->channel_mode & config->channel_mode)) {
		error("APTX: Unsupported channel mode (%u) by endpoint",
							config->channel_mode);
		return -EINVAL;
	}

	return 0;
}

static int check_capabilities(struct a2dp_preset *preset,
				struct avdtp_media_codec_capability *codec,
				uint8_t codec_len)
{
	a2dp_vendor_codec_t *vndcodec;

	/* Codec specific */
	switch (codec->media_codec_type) {
	case A2DP_CODEC_SBC:
		return sbc_check_config(codec->data, codec_len, preset->data,
								preset->len);
	case A2DP_CODEC_MPEG24:
		return aac_check_config(codec->data, codec_len, preset->data,
								preset->len);
	case A2DP_CODEC_VENDOR:
		vndcodec = (void *) codec->data;
		if (btohl(vndcodec->vendor_id) == APTX_VENDOR_ID &&
				btohs(vndcodec->codec_id) == APTX_CODEC_ID)
			return aptx_check_config(codec->data, codec_len,
						preset->data, preset->len);
		return -EINVAL;
	default:
		return -EINVAL;
	}
}

static struct a2dp_preset *sbc_select_range(void *caps, uint8_t caps_len,
						void *conf, uint8_t conf_len)
{
	struct a2dp_preset *p;
	a2dp_sbc_t *cap, *config;

	cap = caps;
	config = conf;

	config->min_bitpool = MAX(config->min_bitpool, cap->min_bitpool);
	config->max_bitpool = MIN(config->max_bitpool, cap->max_bitpool);

	p = g_new0(struct a2dp_preset, 1);
	p->len = conf_len;
	p->data = g_memdup(conf, p->len);

	return p;
}

static struct a2dp_preset *aac_select_range(void *caps, uint8_t caps_len,
						void *conf, uint8_t conf_len)
{
	struct a2dp_preset *p;
	a2dp_aac_t *cap, *config;
	uint32_t bitrate;

	cap = caps;
	config = conf;

	bitrate = MIN(AAC_GET_BITRATE(*cap), AAC_GET_BITRATE(*config));
	AAC_SET_BITRATE(*config, bitrate);

	p = g_new0(struct a2dp_preset, 1);
	p->len = conf_len;
	p->data = g_memdup(conf, p->len);

	return p;
}

static struct a2dp_preset *select_preset_range(struct a2dp_preset *preset,
				struct avdtp_media_codec_capability *codec,
				uint8_t codec_len)
{
	/* Codec specific */
	switch (codec->media_codec_type) {
	case A2DP_CODEC_SBC:
		return sbc_select_range(codec->data, codec_len, preset->data,
								preset->len);
	case A2DP_CODEC_MPEG24:
		return aac_select_range(codec->data, codec_len, preset->data,
								preset->len);
	default:
		return NULL;
	}
}

static struct a2dp_preset *select_preset(struct a2dp_endpoint *endpoint,
						struct avdtp_remote_sep *rsep)
{
	struct avdtp_service_capability *service;
	struct avdtp_media_codec_capability *codec;
	GSList *l;
	uint8_t codec_len;

	service = avdtp_get_codec(rsep);
	codec = (struct avdtp_media_codec_capability *) service->data;
	codec_len = service->length - sizeof(*codec);

	for (l = endpoint->presets; l; l = g_slist_next(l)) {
		struct a2dp_preset *preset = l->data;
		int err;

		err = check_capabilities(preset, codec, codec_len);
		if (err == 0)
			return preset;

		if (err == -ERANGE)
			return select_preset_range(preset, codec, codec_len);
	}

	return NULL;
}

static void setup_add(struct a2dp_device *dev, struct a2dp_endpoint *endpoint,
			struct a2dp_preset *preset, struct avdtp_stream *stream)
{
	struct a2dp_setup *setup;

	setup = g_new0(struct a2dp_setup, 1);
	setup->dev = dev;
	setup->endpoint = endpoint;
	setup->preset = preset;
	setup->stream = stream;
	setups = g_slist_append(setups, setup);

	if (dev->idle_id > 0) {
		g_source_remove(dev->idle_id);
		dev->idle_id = 0;
	}
}

static int select_configuration(struct a2dp_device *dev,
				struct a2dp_endpoint *endpoint,
				struct avdtp_remote_sep *rsep)
{
	struct a2dp_preset *preset;
	struct avdtp_stream *stream;
	struct avdtp_service_capability *service;
	struct avdtp_media_codec_capability *codec;
	GSList *caps;
	int err;

	preset = select_preset(endpoint, rsep);
	if (!preset) {
		error("Unable to select codec preset");
		return -EINVAL;
	}

	service = avdtp_service_cap_new(AVDTP_MEDIA_TRANSPORT, NULL, 0);
	caps = g_slist_append(NULL, service);

	codec = g_malloc0(sizeof(*codec) + preset->len);
	codec->media_type = AVDTP_MEDIA_TYPE_AUDIO;
	codec->media_codec_type = endpoint->codec;
	memcpy(codec->data, preset->data, preset->len);

	service = avdtp_service_cap_new(AVDTP_MEDIA_CODEC, codec,
						sizeof(*codec) + preset->len);
	caps = g_slist_append(caps, service);

	g_free(codec);

	err = avdtp_set_configuration(dev->session, rsep, endpoint->sep, caps,
								&stream);
	g_slist_free_full(caps, g_free);
	if (err < 0) {
		error("avdtp_set_configuration: %s", strerror(-err));
		return err;
	}

	setup_add(dev, endpoint, preset, stream);

	return 0;
}

static void discover_cb(struct avdtp *session, GSList *seps,
				struct avdtp_error *err, void *user_data)
{
	struct a2dp_device *dev = user_data;
	struct a2dp_endpoint *endpoint = NULL;
	struct avdtp_remote_sep *rsep = NULL;
	GSList *l;

	for (l = endpoints; l; l = g_slist_next(l)) {
		endpoint = l->data;

		rsep = avdtp_find_remote_sep(session, endpoint->sep);
		if (rsep)
			break;
	}

	if (!rsep) {
		error("Unable to find matching endpoint");
		goto failed;
	}

	if (select_configuration(dev, endpoint, rsep) < 0)
		goto failed;

	return;

failed:
	avdtp_shutdown(session);
}

static gboolean idle_timeout(gpointer user_data)
{
	struct a2dp_device *dev = user_data;
	int err;

	dev->idle_id = 0;

	err = avdtp_discover(dev->session, discover_cb, dev);
	if (err == 0)
		return FALSE;

	error("avdtp_discover: %s", strerror(-err));
	bt_a2dp_notify_state(dev, HAL_A2DP_STATE_DISCONNECTED);

	return FALSE;
}

static void signaling_connect_cb(GIOChannel *chan, GError *err,
							gpointer user_data)
{
	struct a2dp_device *dev = user_data;
	uint16_t imtu, omtu;
	GError *gerr = NULL;
	int fd;

	if (err) {
		bt_a2dp_notify_state(dev, HAL_A2DP_STATE_DISCONNECTED);
		error("%s", err->message);
		return;
	}

	bt_io_get(chan, &gerr,
			BT_IO_OPT_IMTU, &imtu,
			BT_IO_OPT_OMTU, &omtu,
			BT_IO_OPT_INVALID);
	if (gerr) {
		error("%s", gerr->message);
		g_error_free(gerr);
		goto failed;
	}

	fd = g_io_channel_unix_get_fd(chan);

	/* FIXME: Add proper version */
	dev->session = avdtp_new(fd, imtu, omtu, 0x0100);
	if (!dev->session)
		goto failed;

	avdtp_add_disconnect_cb(dev->session, disconnect_cb, dev);

	/* Proceed to stream setup if initiator */
	if (dev->io) {
		int perr;

		g_io_channel_unref(dev->io);
		dev->io = NULL;

		perr = avdtp_discover(dev->session, discover_cb, dev);
		if (perr < 0) {
			error("avdtp_discover: %s", strerror(-perr));
			goto failed;
		}
		bt_avrcp_connect(&dev->dst);
	} else /* Init idle timeout to discover */
		dev->idle_id = g_timeout_add_seconds(IDLE_TIMEOUT, idle_timeout,
									dev);

	return;

failed:
	bt_a2dp_notify_state(dev, HAL_A2DP_STATE_DISCONNECTED);
}

static void bt_a2dp_connect(const void *buf, uint16_t len)
{
	const struct hal_cmd_a2dp_connect *cmd = buf;
	struct a2dp_device *dev;
	uint8_t status;
	char addr[18];
	bdaddr_t dst;
	GSList *l;

	DBG("");

	android2bdaddr(&cmd->bdaddr, &dst);

	l = g_slist_find_custom(devices, &dst, device_cmp);
	if (l) {
		status = HAL_STATUS_FAILED;
		goto failed;
	}

	dev = a2dp_device_new(&dst);
	if (!a2dp_device_connect(dev, signaling_connect_cb)) {
		a2dp_device_remove(dev);
		status = HAL_STATUS_FAILED;
		goto failed;
	}

	ba2str(&dev->dst, addr);
	DBG("connecting to %s", addr);

	bt_a2dp_notify_state(dev, HAL_A2DP_STATE_CONNECTING);

	status = HAL_STATUS_SUCCESS;

failed:
	ipc_send_rsp(hal_ipc, HAL_SERVICE_ID_A2DP, HAL_OP_A2DP_CONNECT, status);
}

static void bt_a2dp_disconnect(const void *buf, uint16_t len)
{
	const struct hal_cmd_a2dp_connect *cmd = buf;
	uint8_t status;
	struct a2dp_device *dev;
	GSList *l;
	bdaddr_t dst;

	DBG("");

	android2bdaddr(&cmd->bdaddr, &dst);

	l = g_slist_find_custom(devices, &dst, device_cmp);
	if (!l) {
		status = HAL_STATUS_FAILED;
		goto failed;
	}

	dev = l->data;
	status = HAL_STATUS_SUCCESS;

	if (dev->io) {
		bt_a2dp_notify_state(dev, HAL_A2DP_STATE_DISCONNECTED);
		goto failed;
	}

	/* Wait AVDTP session to shutdown */
	avdtp_shutdown(dev->session);
	bt_a2dp_notify_state(dev, HAL_A2DP_STATE_DISCONNECTING);

failed:
	ipc_send_rsp(hal_ipc, HAL_SERVICE_ID_A2DP, HAL_OP_A2DP_DISCONNECT,
									status);
}

static const struct ipc_handler cmd_handlers[] = {
	/* HAL_OP_A2DP_CONNECT */
	{ bt_a2dp_connect, false, sizeof(struct hal_cmd_a2dp_connect) },
	/* HAL_OP_A2DP_DISCONNECT */
	{ bt_a2dp_disconnect, false, sizeof(struct hal_cmd_a2dp_disconnect) },
};

static struct a2dp_setup *find_setup_by_device(struct a2dp_device *dev)
{
	GSList *l;

	for (l = setups; l; l = g_slist_next(l)) {
		struct a2dp_setup *setup = l->data;

		if (setup->dev == dev)
			return setup;
	}

	return NULL;
}

static void transport_connect_cb(GIOChannel *chan, GError *err,
							gpointer user_data)
{
	struct a2dp_device *dev = user_data;
	struct a2dp_setup *setup;
	uint16_t imtu, omtu;
	GError *gerr = NULL;
	int fd;

	if (err) {
		error("%s", err->message);
		return;
	}

	setup = find_setup_by_device(dev);
	if (!setup) {
		error("Unable to find stream setup");
		return;
	}

	bt_io_get(chan, &gerr,
			BT_IO_OPT_IMTU, &imtu,
			BT_IO_OPT_OMTU, &omtu,
			BT_IO_OPT_INVALID);
	if (gerr) {
		error("%s", gerr->message);
		g_error_free(gerr);
		return;
	}

	fd = g_io_channel_unix_get_fd(chan);

	if (!avdtp_stream_set_transport(setup->stream, fd, imtu, omtu)) {
		error("avdtp_stream_set_transport: failed");
		return;
	}

	g_io_channel_set_close_on_unref(chan, FALSE);

	if (dev->io) {
		g_io_channel_unref(dev->io);
		dev->io = NULL;
	}

	bt_a2dp_notify_state(dev, HAL_A2DP_STATE_CONNECTED);
}

static void connect_cb(GIOChannel *chan, GError *err, gpointer user_data)
{
	struct a2dp_device *dev;
	bdaddr_t dst;
	char address[18];
	GError *gerr = NULL;
	GSList *l;

	if (err) {
		error("%s", err->message);
		return;
	}

	bt_io_get(chan, &gerr,
			BT_IO_OPT_DEST_BDADDR, &dst,
			BT_IO_OPT_INVALID);
	if (gerr) {
		error("%s", gerr->message);
		g_error_free(gerr);
		g_io_channel_shutdown(chan, TRUE, NULL);
		return;
	}

	ba2str(&dst, address);
	DBG("Incoming connection from %s", address);

	l = g_slist_find_custom(devices, &dst, device_cmp);
	if (l) {
		transport_connect_cb(chan, err, l->data);
		return;
	}

	dev = a2dp_device_new(&dst);
	bt_a2dp_notify_state(dev, HAL_A2DP_STATE_CONNECTING);
	signaling_connect_cb(chan, err, dev);
}

static sdp_record_t *a2dp_record(void)
{
	sdp_list_t *svclass_id, *pfseq, *apseq, *root;
	uuid_t root_uuid, l2cap_uuid, avdtp_uuid, a2dp_uuid;
	sdp_profile_desc_t profile[1];
	sdp_list_t *aproto, *proto[2];
	sdp_record_t *record;
	sdp_data_t *psm, *version, *features;
	uint16_t lp = AVDTP_UUID;
	uint16_t a2dp_ver = 0x0103, avdtp_ver = 0x0103, feat = 0x000f;

	record = sdp_record_alloc();
	if (!record)
		return NULL;

	sdp_uuid16_create(&root_uuid, PUBLIC_BROWSE_GROUP);
	root = sdp_list_append(NULL, &root_uuid);
	sdp_set_browse_groups(record, root);

	sdp_uuid16_create(&a2dp_uuid, AUDIO_SOURCE_SVCLASS_ID);
	svclass_id = sdp_list_append(NULL, &a2dp_uuid);
	sdp_set_service_classes(record, svclass_id);

	sdp_uuid16_create(&profile[0].uuid, ADVANCED_AUDIO_PROFILE_ID);
	profile[0].version = a2dp_ver;
	pfseq = sdp_list_append(NULL, &profile[0]);
	sdp_set_profile_descs(record, pfseq);

	sdp_uuid16_create(&l2cap_uuid, L2CAP_UUID);
	proto[0] = sdp_list_append(NULL, &l2cap_uuid);
	psm = sdp_data_alloc(SDP_UINT16, &lp);
	proto[0] = sdp_list_append(proto[0], psm);
	apseq = sdp_list_append(NULL, proto[0]);

	sdp_uuid16_create(&avdtp_uuid, AVDTP_UUID);
	proto[1] = sdp_list_append(NULL, &avdtp_uuid);
	version = sdp_data_alloc(SDP_UINT16, &avdtp_ver);
	proto[1] = sdp_list_append(proto[1], version);
	apseq = sdp_list_append(apseq, proto[1]);

	aproto = sdp_list_append(NULL, apseq);
	sdp_set_access_protos(record, aproto);

	features = sdp_data_alloc(SDP_UINT16, &feat);
	sdp_attr_add(record, SDP_ATTR_SUPPORTED_FEATURES, features);

	sdp_set_info_attr(record, "Audio Source", NULL, NULL);

	sdp_data_free(psm);
	sdp_data_free(version);
	sdp_list_free(proto[0], NULL);
	sdp_list_free(proto[1], NULL);
	sdp_list_free(apseq, NULL);
	sdp_list_free(pfseq, NULL);
	sdp_list_free(aproto, NULL);
	sdp_list_free(root, NULL);
	sdp_list_free(svclass_id, NULL);

	return record;
}

static gboolean sep_getcap_ind(struct avdtp *session,
					struct avdtp_local_sep *sep,
					GSList **caps, uint8_t *err,
					void *user_data)
{
	struct a2dp_endpoint *endpoint = user_data;
	struct a2dp_preset *cap = endpoint->caps;
	struct avdtp_service_capability *service;
	struct avdtp_media_codec_capability *codec;

	*caps = NULL;

	service = avdtp_service_cap_new(AVDTP_MEDIA_TRANSPORT, NULL, 0);
	*caps = g_slist_append(*caps, service);

	codec = g_malloc0(sizeof(*codec) + cap->len);
	codec->media_type = AVDTP_MEDIA_TYPE_AUDIO;
	codec->media_codec_type = endpoint->codec;
	memcpy(codec->data, cap->data, cap->len);

	service = avdtp_service_cap_new(AVDTP_MEDIA_CODEC, codec,
						sizeof(*codec) + cap->len);
	*caps = g_slist_append(*caps, service);
	g_free(codec);

	return TRUE;
}

static int check_config(struct a2dp_endpoint *endpoint,
						struct a2dp_preset *config)
{
	GSList *l;
	struct a2dp_preset *caps;

	for (l = endpoint->presets; l; l = g_slist_next(l)) {
		struct a2dp_preset *preset = l->data;

		if (preset->len != config->len)
			continue;

		if (memcmp(preset->data, config->data, preset->len) == 0)
			return 0;
	}

	caps = endpoint->caps;

	/* Codec specific */
	switch (endpoint->codec) {
	case A2DP_CODEC_SBC:
		return sbc_check_config(caps->data, caps->len, config->data,
								config->len);
	default:
		return -EINVAL;
	}
}

static struct a2dp_device *find_device_by_session(struct avdtp *session)
{
	GSList *l;

	for (l = devices; l; l = g_slist_next(l)) {
		struct a2dp_device *dev = l->data;

		if (dev->session == session)
			return dev;
	}

	return NULL;
}

static struct a2dp_setup *find_setup(uint8_t id)
{
	GSList *l;

	for (l = setups; l; l = g_slist_next(l)) {
		struct a2dp_setup *setup = l->data;

		if (setup->endpoint->id == id)
			return setup;
	}

	return NULL;
}

static void setup_remove_by_id(uint8_t id)
{
	struct a2dp_setup *setup;

	setup = find_setup(id);
	if (!setup) {
		error("Unable to find stream setup for endpoint %u", id);
		return;
	}

	setup_remove(setup);
}

static gboolean sep_setconf_ind(struct avdtp *session,
						struct avdtp_local_sep *sep,
						struct avdtp_stream *stream,
						GSList *caps,
						avdtp_set_configuration_cb cb,
						void *user_data)
{
	struct a2dp_endpoint *endpoint = user_data;
	struct a2dp_device *dev;
	struct a2dp_preset *preset = NULL;

	DBG("");

	dev = find_device_by_session(session);
	if (!dev) {
		error("Unable to find device for session %p", session);
		return FALSE;
	}

	for (; caps != NULL; caps = g_slist_next(caps)) {
		struct avdtp_service_capability *cap = caps->data;
		struct avdtp_media_codec_capability *codec;

		if (cap->category == AVDTP_DELAY_REPORTING)
			return FALSE;

		if (cap->category != AVDTP_MEDIA_CODEC)
			continue;

		codec = (struct avdtp_media_codec_capability *) cap->data;

		if (codec->media_codec_type != endpoint->codec)
			return FALSE;

		preset = g_new0(struct a2dp_preset, 1);
		preset->len = cap->length - sizeof(*codec);
		preset->data = g_memdup(codec->data, preset->len);

		if (check_config(endpoint, preset) < 0) {
			preset_free(preset);
			return FALSE;
		}
	}

	if (!preset)
		return FALSE;

	setup_add(dev, endpoint, preset, stream);

	cb(session, stream, NULL);

	return TRUE;
}

static gboolean sep_open_ind(struct avdtp *session, struct avdtp_local_sep *sep,
				struct avdtp_stream *stream, uint8_t *err,
				void *user_data)
{
	struct a2dp_endpoint *endpoint = user_data;
	struct a2dp_setup *setup;

	DBG("");

	setup = find_setup(endpoint->id);
	if (!setup) {
		error("Unable to find stream setup for endpoint %u",
								endpoint->id);
		*err = AVDTP_SEP_NOT_IN_USE;
		return FALSE;
	}

	return TRUE;
}

static gboolean sep_close_ind(struct avdtp *session,
						struct avdtp_local_sep *sep,
						struct avdtp_stream *stream,
						uint8_t *err,
						void *user_data)
{
	struct a2dp_endpoint *endpoint = user_data;
	struct a2dp_setup *setup;

	DBG("");

	setup = find_setup(endpoint->id);
	if (!setup) {
		error("Unable to find stream setup for endpoint %u",
								endpoint->id);
		*err = AVDTP_SEP_NOT_IN_USE;
		return FALSE;
	}

	bt_audio_notify_state(setup, HAL_AUDIO_STOPPED);

	setup_remove(setup);

	return TRUE;
}

static gboolean sep_start_ind(struct avdtp *session,
						struct avdtp_local_sep *sep,
						struct avdtp_stream *stream,
						uint8_t *err,
						void *user_data)
{
	struct a2dp_endpoint *endpoint = user_data;
	struct a2dp_setup *setup;

	DBG("");

	setup = find_setup(endpoint->id);
	if (!setup) {
		error("Unable to find stream setup for endpoint %u",
								endpoint->id);
		*err = AVDTP_SEP_NOT_IN_USE;
		return FALSE;
	}

	bt_audio_notify_state(setup, HAL_AUDIO_STARTED);

	return TRUE;
}

static gboolean sep_suspend_ind(struct avdtp *session,
						struct avdtp_local_sep *sep,
						struct avdtp_stream *stream,
						uint8_t *err,
						void *user_data)
{
	struct a2dp_endpoint *endpoint = user_data;
	struct a2dp_setup *setup;

	DBG("");

	setup = find_setup(endpoint->id);
	if (!setup) {
		error("Unable to find stream setup for endpoint %u",
								endpoint->id);
		*err = AVDTP_SEP_NOT_IN_USE;
		return FALSE;
	}

	bt_audio_notify_state(setup, HAL_AUDIO_SUSPEND);

	return TRUE;
}

static struct avdtp_sep_ind sep_ind = {
	.get_capability		= sep_getcap_ind,
	.set_configuration	= sep_setconf_ind,
	.open			= sep_open_ind,
	.close			= sep_close_ind,
	.start			= sep_start_ind,
	.suspend		= sep_suspend_ind,
};

static void sep_setconf_cfm(struct avdtp *session, struct avdtp_local_sep *sep,
				struct avdtp_stream *stream,
				struct avdtp_error *err, void *user_data)
{
	struct a2dp_endpoint *endpoint = user_data;
	struct a2dp_setup *setup;
	int ret;

	DBG("");

	setup = find_setup(endpoint->id);
	if (!setup) {
		error("Unable to find stream setup for endpoint %u",
								endpoint->id);
		return;
	}

	if (err)
		goto failed;

	ret = avdtp_open(session, stream);
	if (ret < 0) {
		error("avdtp_open: %s", strerror(-ret));
		goto failed;
	}

	return;

failed:
	setup_remove(setup);
}

static void sep_open_cfm(struct avdtp *session, struct avdtp_local_sep *sep,
			struct avdtp_stream *stream, struct avdtp_error *err,
			void *user_data)
{
	struct a2dp_endpoint *endpoint = user_data;
	struct a2dp_device *dev;

	DBG("");

	if (err)
		goto failed;

	dev = find_device_by_session(session);
	if (!dev) {
		error("Unable to find device for session");
		goto failed;
	}

	a2dp_device_connect(dev, transport_connect_cb);

	return;

failed:
	setup_remove_by_id(endpoint->id);
}

static void sep_start_cfm(struct avdtp *session, struct avdtp_local_sep *sep,
			struct avdtp_stream *stream, struct avdtp_error *err,
			void *user_data)
{
	struct a2dp_endpoint *endpoint = user_data;
	struct a2dp_setup *setup;

	DBG("");

	if (err) {
		setup_remove_by_id(endpoint->id);
		return;
	}

	setup = find_setup(endpoint->id);
	if (!setup) {
		error("Unable to find stream setup for %u endpoint",
								endpoint->id);
		return;
	}

	bt_audio_notify_state(setup, HAL_AUDIO_STARTED);
}

static void sep_suspend_cfm(struct avdtp *session, struct avdtp_local_sep *sep,
			struct avdtp_stream *stream, struct avdtp_error *err,
			void *user_data)
{
	struct a2dp_endpoint *endpoint = user_data;
	struct a2dp_setup *setup;

	DBG("");

	if (err) {
		setup_remove_by_id(endpoint->id);
		return;
	}

	setup = find_setup(endpoint->id);
	if (!setup) {
		error("Unable to find stream setup for %u endpoint",
								endpoint->id);
		return;
	}

	bt_audio_notify_state(setup, HAL_AUDIO_STOPPED);
}

static void sep_close_cfm(struct avdtp *session, struct avdtp_local_sep *sep,
			struct avdtp_stream *stream, struct avdtp_error *err,
			void *user_data)
{
	struct a2dp_endpoint *endpoint = user_data;
	struct a2dp_setup *setup;

	DBG("");

	if (err)
		return;

	setup = find_setup(endpoint->id);
	if (!setup) {
		error("Unable to find stream setup for %u endpoint",
								endpoint->id);
		return;
	}

	bt_audio_notify_state(setup, HAL_AUDIO_STOPPED);

	setup_remove(setup);
}

static void sep_abort_cfm(struct avdtp *session, struct avdtp_local_sep *sep,
			struct avdtp_stream *stream, struct avdtp_error *err,
			void *user_data)
{
	struct a2dp_endpoint *endpoint = user_data;

	DBG("");

	if (err)
		return;

	setup_remove_by_id(endpoint->id);
}

static struct avdtp_sep_cfm sep_cfm = {
	.set_configuration	= sep_setconf_cfm,
	.open			= sep_open_cfm,
	.start			= sep_start_cfm,
	.suspend		= sep_suspend_cfm,
	.close			= sep_close_cfm,
	.abort			= sep_abort_cfm,
};

static uint8_t register_endpoint(const uint8_t *uuid, uint8_t codec,
							GSList *presets)
{
	struct a2dp_endpoint *endpoint;

	/* FIXME: Add proper check for uuid */

	endpoint = g_new0(struct a2dp_endpoint, 1);
	endpoint->id = g_slist_length(endpoints) + 1;
	endpoint->codec = codec;
	endpoint->sep = avdtp_register_sep(AVDTP_SEP_TYPE_SOURCE,
						AVDTP_MEDIA_TYPE_AUDIO,
						codec, FALSE, &sep_ind,
						&sep_cfm, endpoint);
	endpoint->caps = presets->data;
	endpoint->presets = g_slist_copy(g_slist_nth(presets, 1));

	if (endpoint->codec == A2DP_CODEC_VENDOR) {
		a2dp_vendor_codec_t *vndcodec = (void *) endpoint->caps->data;

		avdtp_sep_set_vendor_codec(endpoint->sep,
						btohl(vndcodec->vendor_id),
						btohs(vndcodec->codec_id));
	}

	endpoints = g_slist_append(endpoints, endpoint);

	return endpoint->id;
}

static GSList *parse_presets(const struct audio_preset *p, uint8_t count,
								uint16_t len)
{
	GSList *l = NULL;
	uint8_t i;

	for (i = 0; count > i; i++) {
		const uint8_t *ptr = (const uint8_t *) p;
		struct a2dp_preset *preset;

		if (len < sizeof(struct audio_preset)) {
			DBG("Invalid preset index %u", i);
			g_slist_free_full(l, preset_free);
			return NULL;
		}

		len -= sizeof(struct audio_preset);
		if (len == 0 || len < p->len) {
			DBG("Invalid preset size of %u for index %u", len, i);
			g_slist_free_full(l, preset_free);
			return NULL;
		}

		preset = g_new0(struct a2dp_preset, 1);
		preset->len = p->len;
		preset->data = g_memdup(p->data, preset->len);
		l = g_slist_append(l, preset);

		len -= preset->len;
		ptr += sizeof(*p) + preset->len;
		p = (const struct audio_preset *) ptr;
	}

	return l;
}

static void bt_audio_open(const void *buf, uint16_t len)
{
	const struct audio_cmd_open *cmd = buf;
	struct audio_rsp_open rsp;
	GSList *presets;

	DBG("");

	audio_retrying = false;

	if (cmd->presets == 0) {
		error("No audio presets found");
		goto failed;
	}

	presets = parse_presets(cmd->preset, cmd->presets, len - sizeof(*cmd));
	if (!presets) {
		error("No audio presets found");
		goto failed;
	}

	rsp.id = register_endpoint(cmd->uuid, cmd->codec, presets);
	if (rsp.id == 0) {
		g_slist_free_full(presets, preset_free);
		error("Unable to register endpoint");
		goto failed;
	}

	g_slist_free(presets);

	ipc_send_rsp_full(audio_ipc, AUDIO_SERVICE_ID, AUDIO_OP_OPEN,
							sizeof(rsp), &rsp, -1);

	return;

failed:
	ipc_send_rsp(audio_ipc, AUDIO_SERVICE_ID, AUDIO_OP_OPEN,
							AUDIO_STATUS_FAILED);
}

static struct a2dp_endpoint *find_endpoint(uint8_t id)
{
	GSList *l;

	for (l = endpoints; l; l = g_slist_next(l)) {
		struct a2dp_endpoint *endpoint = l->data;

		if (endpoint->id == id)
			return endpoint;
	}

	return NULL;
}

static void bt_audio_close(const void *buf, uint16_t len)
{
	const struct audio_cmd_close *cmd = buf;
	struct a2dp_endpoint *endpoint;

	DBG("");

	endpoint = find_endpoint(cmd->id);
	if (!endpoint) {
		error("Unable to find endpoint %u", cmd->id);
		ipc_send_rsp(audio_ipc, AUDIO_SERVICE_ID, AUDIO_OP_CLOSE,
							AUDIO_STATUS_FAILED);
		return;
	}

	endpoints = g_slist_remove(endpoints, endpoint);
	unregister_endpoint(endpoint);

	ipc_send_rsp(audio_ipc, AUDIO_SERVICE_ID, AUDIO_OP_CLOSE,
							AUDIO_STATUS_SUCCESS);
}

static void bt_stream_open(const void *buf, uint16_t len)
{
	const struct audio_cmd_open_stream *cmd = buf;
	struct audio_rsp_open_stream *rsp;
	struct a2dp_setup *setup;
	int fd;
	uint16_t omtu;

	DBG("");

	if (cmd->id)
		setup = find_setup(cmd->id);
	else
		setup = setups ? setups->data : NULL;
	if (!setup) {
		error("Unable to find stream for endpoint %u", cmd->id);
		ipc_send_rsp(audio_ipc, AUDIO_SERVICE_ID, AUDIO_OP_OPEN_STREAM,
							AUDIO_STATUS_FAILED);
		return;
	}

	if (!avdtp_stream_get_transport(setup->stream, &fd, NULL, &omtu,
								NULL)) {
		error("avdtp_stream_get_transport: failed");
		ipc_send_rsp(audio_ipc, AUDIO_SERVICE_ID, AUDIO_OP_OPEN_STREAM,
							AUDIO_STATUS_FAILED);
		return;
	}

	len = sizeof(struct audio_rsp_open_stream) +
			sizeof(struct audio_preset) + setup->preset->len;
	rsp = g_malloc0(len);
	rsp->id = setup->endpoint->id;
	rsp->mtu = omtu;
	rsp->preset->len = setup->preset->len;
	memcpy(rsp->preset->data, setup->preset->data, setup->preset->len);

	ipc_send_rsp_full(audio_ipc, AUDIO_SERVICE_ID, AUDIO_OP_OPEN_STREAM,
								len, rsp, fd);

	g_free(rsp);
}

static void bt_stream_close(const void *buf, uint16_t len)
{
	const struct audio_cmd_close_stream *cmd = buf;
	struct a2dp_setup *setup;
	int err;

	DBG("");

	setup = find_setup(cmd->id);
	if (!setup) {
		error("Unable to find stream for endpoint %u", cmd->id);
		goto failed;
	}

	err = avdtp_close(setup->dev->session, setup->stream, FALSE);
	if (err < 0) {
		error("avdtp_close: %s", strerror(-err));
		goto failed;
	}

	ipc_send_rsp(audio_ipc, AUDIO_SERVICE_ID, AUDIO_OP_CLOSE_STREAM,
							AUDIO_STATUS_SUCCESS);

	return;

failed:
	ipc_send_rsp(audio_ipc, AUDIO_SERVICE_ID, AUDIO_OP_CLOSE_STREAM,
							AUDIO_STATUS_FAILED);
}

static void bt_stream_resume(const void *buf, uint16_t len)
{
	const struct audio_cmd_resume_stream *cmd = buf;
	struct a2dp_setup *setup;
	int err;

	DBG("");

	setup = find_setup(cmd->id);
	if (!setup) {
		error("Unable to find stream for endpoint %u", cmd->id);
		goto failed;
	}

	if (setup->state != HAL_AUDIO_STARTED) {
		err = avdtp_start(setup->dev->session, setup->stream);
		if (err < 0) {
			error("avdtp_start: %s", strerror(-err));
			goto failed;
		}
	}

	ipc_send_rsp(audio_ipc, AUDIO_SERVICE_ID, AUDIO_OP_RESUME_STREAM,
							AUDIO_STATUS_SUCCESS);

	return;

failed:
	ipc_send_rsp(audio_ipc, AUDIO_SERVICE_ID, AUDIO_OP_RESUME_STREAM,
							AUDIO_STATUS_FAILED);
}

static void bt_stream_suspend(const void *buf, uint16_t len)
{
	const struct audio_cmd_suspend_stream *cmd = buf;
	struct a2dp_setup *setup;
	int err;

	DBG("");

	setup = find_setup(cmd->id);
	if (!setup) {
		error("Unable to find stream for endpoint %u", cmd->id);
		goto failed;
	}

	err = avdtp_suspend(setup->dev->session, setup->stream);
	if (err < 0) {
		error("avdtp_suspend: %s", strerror(-err));
		goto failed;
	}

	ipc_send_rsp(audio_ipc, AUDIO_SERVICE_ID, AUDIO_OP_SUSPEND_STREAM,
							AUDIO_STATUS_SUCCESS);

	return;

failed:
	ipc_send_rsp(audio_ipc, AUDIO_SERVICE_ID, AUDIO_OP_SUSPEND_STREAM,
							AUDIO_STATUS_FAILED);
}

static const struct ipc_handler audio_handlers[] = {
	/* AUDIO_OP_OPEN */
	{ bt_audio_open, true, sizeof(struct audio_cmd_open) },
	/* AUDIO_OP_CLOSE */
	{ bt_audio_close, false, sizeof(struct audio_cmd_close) },
	/* AUDIO_OP_OPEN_STREAM */
	{ bt_stream_open, false, sizeof(struct audio_cmd_open_stream) },
	/* AUDIO_OP_CLOSE_STREAM */
	{ bt_stream_close, false, sizeof(struct audio_cmd_close_stream) },
	/* AUDIO_OP_RESUME_STREAM */
	{ bt_stream_resume, false, sizeof(struct audio_cmd_resume_stream) },
	/* AUDIO_OP_SUSPEND_STREAM */
	{ bt_stream_suspend, false, sizeof(struct audio_cmd_suspend_stream) },
};

static void bt_audio_unregister(void)
{
	DBG("");

	if (audio_retry_id > 0)
		g_source_remove(audio_retry_id);

	g_slist_free_full(endpoints, unregister_endpoint);
	endpoints = NULL;

	g_slist_free_full(setups, setup_free);
	setups = NULL;

	ipc_cleanup(audio_ipc);
	audio_ipc = NULL;
}

static bool bt_audio_register(ipc_disconnect_cb disconnect)
{
	DBG("");

	audio_ipc = ipc_init(BLUEZ_AUDIO_SK_PATH, sizeof(BLUEZ_AUDIO_SK_PATH),
				AUDIO_SERVICE_ID_MAX, false, disconnect, NULL);
	if (!audio_ipc)
		return false;

	ipc_register(audio_ipc, AUDIO_SERVICE_ID, audio_handlers,
						G_N_ELEMENTS(audio_handlers));

	return true;
}

static gboolean audio_retry_register(void *data)
{
	ipc_disconnect_cb cb = data;

	audio_retry_id = 0;
	audio_retrying = true;

	bt_audio_register(cb);

	return FALSE;
}

static void audio_disconnected(void *data)
{
	GSList *l;
	bool restart;

	DBG("");

	if (audio_retrying)
		goto retry;

	restart = endpoints != NULL ? true : false;

	bt_audio_unregister();

	for (l = devices; l; l = g_slist_next(l)) {
		struct a2dp_device *dev = l->data;

		avdtp_shutdown(dev->session);
	}

	if (!restart)
		return;

retry:
	audio_retry_id = g_timeout_add_seconds(AUDIO_RETRY_TIMEOUT,
						audio_retry_register,
						audio_disconnected);
}

bool bt_a2dp_register(struct ipc *ipc, const bdaddr_t *addr, uint8_t mode)
{
	GError *err = NULL;
	sdp_record_t *rec;

	DBG("");

	bacpy(&adapter_addr, addr);

	server = bt_io_listen(connect_cb, NULL, NULL, NULL, &err,
				BT_IO_OPT_SOURCE_BDADDR, &adapter_addr,
				BT_IO_OPT_PSM, AVDTP_PSM,
				BT_IO_OPT_SEC_LEVEL, BT_IO_SEC_MEDIUM,
				BT_IO_OPT_MASTER, true,
				BT_IO_OPT_INVALID);
	if (!server) {
		error("Failed to listen on AVDTP channel: %s", err->message);
		g_error_free(err);
		return false;
	}

	rec = a2dp_record();
	if (!rec) {
		error("Failed to allocate A2DP record");
		goto fail;
	}

	if (bt_adapter_add_record(rec, SVC_HINT_CAPTURING) < 0) {
		error("Failed to register A2DP record");
		sdp_record_free(rec);
		goto fail;
	}
	record_id = rec->handle;

	hal_ipc = ipc;

	ipc_register(hal_ipc, HAL_SERVICE_ID_A2DP, cmd_handlers,
						G_N_ELEMENTS(cmd_handlers));

	if (bt_audio_register(audio_disconnected))
		return true;

fail:
	g_io_channel_shutdown(server, TRUE, NULL);
	g_io_channel_unref(server);
	server = NULL;
	return false;
}

void bt_a2dp_unregister(void)
{
	DBG("");

	g_slist_free_full(setups, setup_free);
	setups = NULL;

	g_slist_free_full(endpoints, unregister_endpoint);
	endpoints = NULL;

	g_slist_free_full(devices, a2dp_device_free);
	devices = NULL;

	ipc_unregister(hal_ipc, HAL_SERVICE_ID_A2DP);
	hal_ipc = NULL;

	bt_adapter_remove_record(record_id);
	record_id = 0;

	if (server) {
		g_io_channel_shutdown(server, TRUE, NULL);
		g_io_channel_unref(server);
		server = NULL;
	}

	if (audio_ipc) {
		ipc_unregister(audio_ipc, AUDIO_SERVICE_ID);
		ipc_cleanup(audio_ipc);
		audio_ipc = NULL;
	}
}
