Home | History | Annotate | Download | only in audio
      1 /*
      2  *
      3  *  BlueZ - Bluetooth protocol stack for Linux
      4  *
      5  *  Copyright (C) 2006-2007  Nokia Corporation
      6  *  Copyright (C) 2004-2009  Marcel Holtmann <marcel (at) holtmann.org>
      7  *
      8  *
      9  *  This program is free software; you can redistribute it and/or modify
     10  *  it under the terms of the GNU General Public License as published by
     11  *  the Free Software Foundation; either version 2 of the License, or
     12  *  (at your option) any later version.
     13  *
     14  *  This program is distributed in the hope that it will be useful,
     15  *  but WITHOUT ANY WARRANTY; without even the implied warranty of
     16  *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
     17  *  GNU General Public License for more details.
     18  *
     19  *  You should have received a copy of the GNU General Public License
     20  *  along with this program; if not, write to the Free Software
     21  *  Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
     22  *
     23  */
     24 
     25 #ifdef HAVE_CONFIG_H
     26 #include <config.h>
     27 #endif
     28 
     29 #include <stdlib.h>
     30 #include <errno.h>
     31 
     32 #include <dbus/dbus.h>
     33 #include <glib.h>
     34 
     35 #include <bluetooth/bluetooth.h>
     36 #include <bluetooth/sdp.h>
     37 #include <bluetooth/sdp_lib.h>
     38 
     39 #include "logging.h"
     40 #include "device.h"
     41 #include "manager.h"
     42 #include "avdtp.h"
     43 #include "sink.h"
     44 #include "source.h"
     45 #include "a2dp.h"
     46 #include "sdpd.h"
     47 
     48 /* The duration that streams without users are allowed to stay in
     49  * STREAMING state. */
     50 #define SUSPEND_TIMEOUT 5
     51 #define RECONFIGURE_TIMEOUT 500
     52 
     53 #ifndef MIN
     54 # define MIN(x, y) ((x) < (y) ? (x) : (y))
     55 #endif
     56 
     57 #ifndef MAX
     58 # define MAX(x, y) ((x) > (y) ? (x) : (y))
     59 #endif
     60 
     61 struct a2dp_sep {
     62 	uint8_t type;
     63 	uint8_t codec;
     64 	struct avdtp_local_sep *sep;
     65 	struct avdtp *session;
     66 	struct avdtp_stream *stream;
     67 	guint suspend_timer;
     68 	gboolean locked;
     69 	gboolean suspending;
     70 	gboolean starting;
     71 };
     72 
     73 struct a2dp_setup_cb {
     74 	a2dp_config_cb_t config_cb;
     75 	a2dp_stream_cb_t resume_cb;
     76 	a2dp_stream_cb_t suspend_cb;
     77 	void *user_data;
     78 	unsigned int id;
     79 };
     80 
     81 struct a2dp_setup {
     82 	struct audio_device *dev;
     83 	struct avdtp *session;
     84 	struct a2dp_sep *sep;
     85 	struct avdtp_stream *stream;
     86 	struct avdtp_error *err;
     87 	GSList *client_caps;
     88 	gboolean reconfigure;
     89 	gboolean canceled;
     90 	gboolean start;
     91 	GSList *cb;
     92 	int ref;
     93 };
     94 
     95 static DBusConnection *connection = NULL;
     96 
     97 struct a2dp_server {
     98 	bdaddr_t src;
     99 	GSList *sinks;
    100 	GSList *sources;
    101 	uint32_t source_record_id;
    102 	uint32_t sink_record_id;
    103 };
    104 
    105 static GSList *servers = NULL;
    106 static GSList *setups = NULL;
    107 static unsigned int cb_id = 0;
    108 
    109 static struct a2dp_setup *setup_ref(struct a2dp_setup *setup)
    110 {
    111 	setup->ref++;
    112 
    113 	debug("setup_ref(%p): ref=%d", setup, setup->ref);
    114 
    115 	return setup;
    116 }
    117 
    118 static void setup_free(struct a2dp_setup *s)
    119 {
    120 	debug("setup_free(%p)", s);
    121 	setups = g_slist_remove(setups, s);
    122 	if (s->session)
    123 		avdtp_unref(s->session);
    124 	g_slist_foreach(s->cb, (GFunc) g_free, NULL);
    125 	g_slist_free(s->cb);
    126 	g_free(s);
    127 }
    128 
    129 static void setup_unref(struct a2dp_setup *setup)
    130 {
    131 	setup->ref--;
    132 
    133 	debug("setup_unref(%p): ref=%d", setup, setup->ref);
    134 
    135 	if (setup->ref <= 0)
    136 		setup_free(setup);
    137 }
    138 
    139 static struct audio_device *a2dp_get_dev(struct avdtp *session)
    140 {
    141 	bdaddr_t src, dst;
    142 
    143 	avdtp_get_peers(session, &src, &dst);
    144 
    145 	return manager_find_device(NULL, &src, &dst, NULL, FALSE);
    146 }
    147 
    148 static gboolean finalize_config(struct a2dp_setup *s)
    149 {
    150 	GSList *l;
    151 
    152 	setup_ref(s);
    153 	for (l = s->cb; l != NULL; l = l->next) {
    154 		struct a2dp_setup_cb *cb = l->data;
    155 		struct avdtp_stream *stream = s->err ? NULL : s->stream;
    156 
    157 		if (!cb->config_cb)
    158 			continue;
    159 
    160 		cb->config_cb(s->session, s->sep, stream, s->err,
    161 							cb->user_data);
    162 		cb->config_cb = NULL;
    163 		setup_unref(s);
    164 	}
    165 
    166 	setup_unref(s);
    167 	return FALSE;
    168 }
    169 
    170 static gboolean finalize_config_errno(struct a2dp_setup *s, int err)
    171 {
    172 	struct avdtp_error avdtp_err;
    173 
    174 	avdtp_error_init(&avdtp_err, AVDTP_ERROR_ERRNO, -err);
    175 	s->err = err ? &avdtp_err : NULL;
    176 
    177 	return finalize_config(s);
    178 }
    179 
    180 static gboolean finalize_resume(struct a2dp_setup *s)
    181 {
    182 	GSList *l;
    183 
    184 	setup_ref(s);
    185 	for (l = s->cb; l != NULL; l = l->next) {
    186 		struct a2dp_setup_cb *cb = l->data;
    187 
    188 		if (cb && cb->resume_cb) {
    189 			cb->resume_cb(s->session, s->err, cb->user_data);
    190 			cb->resume_cb = NULL;
    191 			setup_unref(s);
    192 		}
    193 	}
    194 
    195 	setup_unref(s);
    196 	return FALSE;
    197 }
    198 
    199 static gboolean finalize_suspend(struct a2dp_setup *s)
    200 {
    201 	GSList *l;
    202 
    203 	setup_ref(s);
    204 	for (l = s->cb; l != NULL; l = l->next) {
    205 		struct a2dp_setup_cb *cb = l->data;
    206 
    207 		if (cb->suspend_cb) {
    208 			cb->suspend_cb(s->session, s->err, cb->user_data);
    209 			cb->suspend_cb = NULL;
    210 			setup_unref(s);
    211 		}
    212 	}
    213 
    214 	setup_unref(s);
    215 	return FALSE;
    216 }
    217 
    218 static gboolean finalize_suspend_errno(struct a2dp_setup *s, int err)
    219 {
    220 	struct avdtp_error avdtp_err;
    221 
    222 	avdtp_error_init(&avdtp_err, AVDTP_ERROR_ERRNO, -err);
    223 	s->err = err ? &avdtp_err : NULL;
    224 
    225 	return finalize_suspend(s);
    226 }
    227 
    228 static struct a2dp_setup *find_setup_by_session(struct avdtp *session)
    229 {
    230 	GSList *l;
    231 
    232 	for (l = setups; l != NULL; l = l->next) {
    233 		struct a2dp_setup *setup = l->data;
    234 
    235 		if (setup->session == session)
    236 			return setup;
    237 	}
    238 
    239 	return NULL;
    240 }
    241 
    242 static struct a2dp_setup *find_setup_by_dev(struct audio_device *dev)
    243 {
    244 	GSList *l;
    245 
    246 	for (l = setups; l != NULL; l = l->next) {
    247 		struct a2dp_setup *setup = l->data;
    248 
    249 		if (setup->dev == dev)
    250 			return setup;
    251 	}
    252 
    253 	return NULL;
    254 }
    255 
    256 static void stream_state_changed(struct avdtp_stream *stream,
    257 					avdtp_state_t old_state,
    258 					avdtp_state_t new_state,
    259 					struct avdtp_error *err,
    260 					void *user_data)
    261 {
    262 	struct a2dp_sep *sep = user_data;
    263 
    264 	if (new_state != AVDTP_STATE_IDLE)
    265 		return;
    266 
    267 	if (sep->suspend_timer) {
    268 		g_source_remove(sep->suspend_timer);
    269 		sep->suspend_timer = 0;
    270 	}
    271 
    272 	if (sep->session) {
    273 		avdtp_unref(sep->session);
    274 		sep->session = NULL;
    275 	}
    276 
    277 	sep->stream = NULL;
    278 
    279 }
    280 
    281 static gboolean sbc_setconf_ind(struct avdtp *session,
    282 				struct avdtp_local_sep *sep,
    283 				struct avdtp_stream *stream,
    284 				GSList *caps, uint8_t *err,
    285 				uint8_t *category, void *user_data)
    286 {
    287 	struct a2dp_sep *a2dp_sep = user_data;
    288 	struct audio_device *dev;
    289 	struct avdtp_service_capability *cap;
    290 	struct avdtp_media_codec_capability *codec_cap;
    291 	struct sbc_codec_cap *sbc_cap;
    292 
    293 	if (a2dp_sep->type == AVDTP_SEP_TYPE_SINK)
    294 		debug("Sink %p: Set_Configuration_Ind", sep);
    295 	else
    296 		debug("Source %p: Set_Configuration_Ind", sep);
    297 
    298 	dev = a2dp_get_dev(session);
    299 	if (!dev) {
    300 		*err = AVDTP_UNSUPPORTED_CONFIGURATION;
    301 		*category = 0x00;
    302 		return FALSE;
    303 	}
    304 
    305 	/* Check bipool range */
    306 	for (codec_cap = NULL; caps; caps = g_slist_next(caps)) {
    307 		cap = caps->data;
    308 		if (cap->category != AVDTP_MEDIA_CODEC)
    309 			continue;
    310 
    311 		if (cap->length < sizeof(struct sbc_codec_cap))
    312 			continue;
    313 
    314 		codec_cap = (void *) cap->data;
    315 
    316 		if (codec_cap->media_codec_type != A2DP_CODEC_SBC)
    317 			continue;
    318 
    319 		sbc_cap = (void *) codec_cap;
    320 
    321 		if (sbc_cap->min_bitpool < MIN_BITPOOL ||
    322 					sbc_cap->max_bitpool > MAX_BITPOOL) {
    323 			*err = AVDTP_UNSUPPORTED_CONFIGURATION;
    324 			*category = AVDTP_MEDIA_CODEC;
    325 			return FALSE;
    326 		}
    327 
    328 		break;
    329 	}
    330 
    331 	avdtp_stream_add_cb(session, stream, stream_state_changed, a2dp_sep);
    332 	a2dp_sep->stream = stream;
    333 
    334 	if (a2dp_sep->type == AVDTP_SEP_TYPE_SOURCE)
    335 		sink_new_stream(dev, session, stream);
    336 
    337 	return TRUE;
    338 }
    339 
    340 static gboolean sbc_getcap_ind(struct avdtp *session, struct avdtp_local_sep *sep,
    341 				GSList **caps, uint8_t *err, void *user_data)
    342 {
    343 	struct a2dp_sep *a2dp_sep = user_data;
    344 	struct avdtp_service_capability *media_transport, *media_codec;
    345 	struct sbc_codec_cap sbc_cap;
    346 
    347 	if (a2dp_sep->type == AVDTP_SEP_TYPE_SINK)
    348 		debug("Sink %p: Get_Capability_Ind", sep);
    349 	else
    350 		debug("Source %p: Get_Capability_Ind", sep);
    351 
    352 	*caps = NULL;
    353 
    354 	media_transport = avdtp_service_cap_new(AVDTP_MEDIA_TRANSPORT,
    355 						NULL, 0);
    356 
    357 	*caps = g_slist_append(*caps, media_transport);
    358 
    359 	memset(&sbc_cap, 0, sizeof(struct sbc_codec_cap));
    360 
    361 	sbc_cap.cap.media_type = AVDTP_MEDIA_TYPE_AUDIO;
    362 	sbc_cap.cap.media_codec_type = A2DP_CODEC_SBC;
    363 
    364 #ifdef ANDROID
    365 	sbc_cap.frequency = SBC_SAMPLING_FREQ_44100;
    366 #else
    367 	sbc_cap.frequency = ( SBC_SAMPLING_FREQ_48000 |
    368 				SBC_SAMPLING_FREQ_44100 |
    369 				SBC_SAMPLING_FREQ_32000 |
    370 				SBC_SAMPLING_FREQ_16000 );
    371 #endif
    372 
    373 	sbc_cap.channel_mode = ( SBC_CHANNEL_MODE_JOINT_STEREO |
    374 					SBC_CHANNEL_MODE_STEREO |
    375 					SBC_CHANNEL_MODE_DUAL_CHANNEL |
    376 					SBC_CHANNEL_MODE_MONO );
    377 
    378 	sbc_cap.block_length = ( SBC_BLOCK_LENGTH_16 |
    379 					SBC_BLOCK_LENGTH_12 |
    380 					SBC_BLOCK_LENGTH_8 |
    381 					SBC_BLOCK_LENGTH_4 );
    382 
    383 	sbc_cap.subbands = ( SBC_SUBBANDS_8 | SBC_SUBBANDS_4 );
    384 
    385 	sbc_cap.allocation_method = ( SBC_ALLOCATION_LOUDNESS |
    386 					SBC_ALLOCATION_SNR );
    387 
    388 	sbc_cap.min_bitpool = MIN_BITPOOL;
    389 	sbc_cap.max_bitpool = MAX_BITPOOL;
    390 
    391 	media_codec = avdtp_service_cap_new(AVDTP_MEDIA_CODEC, &sbc_cap,
    392 						sizeof(sbc_cap));
    393 
    394 	*caps = g_slist_append(*caps, media_codec);
    395 
    396 	return TRUE;
    397 }
    398 
    399 static gboolean mpeg_setconf_ind(struct avdtp *session,
    400 				struct avdtp_local_sep *sep,
    401 				struct avdtp_stream *stream,
    402 				GSList *caps, uint8_t *err,
    403 				uint8_t *category, void *user_data)
    404 {
    405 	struct a2dp_sep *a2dp_sep = user_data;
    406 	struct audio_device *dev;
    407 
    408 	if (a2dp_sep->type == AVDTP_SEP_TYPE_SINK)
    409 		debug("Sink %p: Set_Configuration_Ind", sep);
    410 	else
    411 		debug("Source %p: Set_Configuration_Ind", sep);
    412 
    413 	dev = a2dp_get_dev(session);
    414 	if (!dev) {
    415 		*err = AVDTP_UNSUPPORTED_CONFIGURATION;
    416 		*category = 0x00;
    417 		return FALSE;
    418 	}
    419 
    420 	avdtp_stream_add_cb(session, stream, stream_state_changed, a2dp_sep);
    421 	a2dp_sep->stream = stream;
    422 
    423 	if (a2dp_sep->type == AVDTP_SEP_TYPE_SOURCE)
    424 		sink_new_stream(dev, session, stream);
    425 
    426 	return TRUE;
    427 }
    428 
    429 static gboolean mpeg_getcap_ind(struct avdtp *session,
    430 				struct avdtp_local_sep *sep,
    431 				GSList **caps, uint8_t *err, void *user_data)
    432 {
    433 	struct a2dp_sep *a2dp_sep = user_data;
    434 	struct avdtp_service_capability *media_transport, *media_codec;
    435 	struct mpeg_codec_cap mpeg_cap;
    436 
    437 	if (a2dp_sep->type == AVDTP_SEP_TYPE_SINK)
    438 		debug("Sink %p: Get_Capability_Ind", sep);
    439 	else
    440 		debug("Source %p: Get_Capability_Ind", sep);
    441 
    442 	*caps = NULL;
    443 
    444 	media_transport = avdtp_service_cap_new(AVDTP_MEDIA_TRANSPORT,
    445 						NULL, 0);
    446 
    447 	*caps = g_slist_append(*caps, media_transport);
    448 
    449 	memset(&mpeg_cap, 0, sizeof(struct mpeg_codec_cap));
    450 
    451 	mpeg_cap.cap.media_type = AVDTP_MEDIA_TYPE_AUDIO;
    452 	mpeg_cap.cap.media_codec_type = A2DP_CODEC_MPEG12;
    453 
    454 	mpeg_cap.frequency = ( MPEG_SAMPLING_FREQ_48000 |
    455 				MPEG_SAMPLING_FREQ_44100 |
    456 				MPEG_SAMPLING_FREQ_32000 |
    457 				MPEG_SAMPLING_FREQ_24000 |
    458 				MPEG_SAMPLING_FREQ_22050 |
    459 				MPEG_SAMPLING_FREQ_16000 );
    460 
    461 	mpeg_cap.channel_mode = ( MPEG_CHANNEL_MODE_JOINT_STEREO |
    462 					MPEG_CHANNEL_MODE_STEREO |
    463 					MPEG_CHANNEL_MODE_DUAL_CHANNEL |
    464 					MPEG_CHANNEL_MODE_MONO );
    465 
    466 	mpeg_cap.layer = ( MPEG_LAYER_MP3 | MPEG_LAYER_MP2 | MPEG_LAYER_MP1 );
    467 
    468 	mpeg_cap.bitrate = 0xFFFF;
    469 
    470 	media_codec = avdtp_service_cap_new(AVDTP_MEDIA_CODEC, &mpeg_cap,
    471 						sizeof(mpeg_cap));
    472 
    473 	*caps = g_slist_append(*caps, media_codec);
    474 
    475 	return TRUE;
    476 }
    477 
    478 static void setconf_cfm(struct avdtp *session, struct avdtp_local_sep *sep,
    479 				struct avdtp_stream *stream,
    480 				struct avdtp_error *err, void *user_data)
    481 {
    482 	struct a2dp_sep *a2dp_sep = user_data;
    483 	struct a2dp_setup *setup;
    484 	struct audio_device *dev;
    485 	int ret;
    486 
    487 	if (a2dp_sep->type == AVDTP_SEP_TYPE_SINK)
    488 		debug("Sink %p: Set_Configuration_Cfm", sep);
    489 	else
    490 		debug("Source %p: Set_Configuration_Cfm", sep);
    491 
    492 	setup = find_setup_by_session(session);
    493 
    494 	if (err) {
    495 		if (setup) {
    496 			setup->err = err;
    497 			finalize_config(setup);
    498 		}
    499 		return;
    500 	}
    501 
    502 	avdtp_stream_add_cb(session, stream, stream_state_changed, a2dp_sep);
    503 	a2dp_sep->stream = stream;
    504 
    505 	if (!setup)
    506 		return;
    507 
    508 	dev = a2dp_get_dev(session);
    509 
    510 	/* Notify D-Bus interface of the new stream */
    511 	if (a2dp_sep->type == AVDTP_SEP_TYPE_SOURCE)
    512 		sink_new_stream(dev, session, setup->stream);
    513 	else
    514 		source_new_stream(dev, session, setup->stream);
    515 
    516 	ret = avdtp_open(session, stream);
    517 	if (ret < 0) {
    518 		error("Error on avdtp_open %s (%d)", strerror(-ret), -ret);
    519 		setup->stream = NULL;
    520 		finalize_config_errno(setup, ret);
    521 	}
    522 }
    523 
    524 static gboolean getconf_ind(struct avdtp *session, struct avdtp_local_sep *sep,
    525 				uint8_t *err, void *user_data)
    526 {
    527 	struct a2dp_sep *a2dp_sep = user_data;
    528 
    529 	if (a2dp_sep->type == AVDTP_SEP_TYPE_SINK)
    530 		debug("Sink %p: Get_Configuration_Ind", sep);
    531 	else
    532 		debug("Source %p: Get_Configuration_Ind", sep);
    533 	return TRUE;
    534 }
    535 
    536 static void getconf_cfm(struct avdtp *session, struct avdtp_local_sep *sep,
    537 			struct avdtp_stream *stream, struct avdtp_error *err,
    538 			void *user_data)
    539 {
    540 	struct a2dp_sep *a2dp_sep = user_data;
    541 
    542 	if (a2dp_sep->type == AVDTP_SEP_TYPE_SINK)
    543 		debug("Sink %p: Set_Configuration_Cfm", sep);
    544 	else
    545 		debug("Source %p: Set_Configuration_Cfm", sep);
    546 }
    547 
    548 static gboolean open_ind(struct avdtp *session, struct avdtp_local_sep *sep,
    549 				struct avdtp_stream *stream, uint8_t *err,
    550 				void *user_data)
    551 {
    552 	struct a2dp_sep *a2dp_sep = user_data;
    553 
    554 	if (a2dp_sep->type == AVDTP_SEP_TYPE_SINK)
    555 		debug("Sink %p: Open_Ind", sep);
    556 	else
    557 		debug("Source %p: Open_Ind", sep);
    558 	return TRUE;
    559 }
    560 
    561 static void open_cfm(struct avdtp *session, struct avdtp_local_sep *sep,
    562 			struct avdtp_stream *stream, struct avdtp_error *err,
    563 			void *user_data)
    564 {
    565 	struct a2dp_sep *a2dp_sep = user_data;
    566 	struct a2dp_setup *setup;
    567 
    568 	if (a2dp_sep->type == AVDTP_SEP_TYPE_SINK)
    569 		debug("Sink %p: Open_Cfm", sep);
    570 	else
    571 		debug("Source %p: Open_Cfm", sep);
    572 
    573 	setup = find_setup_by_session(session);
    574 	if (!setup)
    575 		return;
    576 
    577 	if (setup->canceled) {
    578 		if (!err)
    579 			avdtp_close(session, stream);
    580 		setup_unref(setup);
    581 		return;
    582 	}
    583 
    584 	if (setup->reconfigure)
    585 		setup->reconfigure = FALSE;
    586 
    587 	if (err) {
    588 		setup->stream = NULL;
    589 		setup->err = err;
    590 	}
    591 
    592 	finalize_config(setup);
    593 }
    594 
    595 static gboolean suspend_timeout(struct a2dp_sep *sep)
    596 {
    597 	if (avdtp_suspend(sep->session, sep->stream) == 0)
    598 		sep->suspending = TRUE;
    599 
    600 	sep->suspend_timer = 0;
    601 
    602 	avdtp_unref(sep->session);
    603 	sep->session = NULL;
    604 
    605 	return FALSE;
    606 }
    607 
    608 static gboolean start_ind(struct avdtp *session, struct avdtp_local_sep *sep,
    609 				struct avdtp_stream *stream, uint8_t *err,
    610 				void *user_data)
    611 {
    612 	struct a2dp_sep *a2dp_sep = user_data;
    613 	struct a2dp_setup *setup;
    614 
    615 	if (a2dp_sep->type == AVDTP_SEP_TYPE_SINK)
    616 		debug("Sink %p: Start_Ind", sep);
    617 	else
    618 		debug("Source %p: Start_Ind", sep);
    619 
    620 	setup = find_setup_by_session(session);
    621 	if (setup) {
    622 		if (setup->canceled)
    623 			setup_unref(setup);
    624 		else
    625 			finalize_resume(setup);
    626 	}
    627 
    628 	if (!a2dp_sep->locked) {
    629 		a2dp_sep->session = avdtp_ref(session);
    630 		a2dp_sep->suspend_timer = g_timeout_add_seconds(SUSPEND_TIMEOUT,
    631 						(GSourceFunc) suspend_timeout,
    632 						a2dp_sep);
    633 	}
    634 
    635 	return TRUE;
    636 }
    637 
    638 static void start_cfm(struct avdtp *session, struct avdtp_local_sep *sep,
    639 			struct avdtp_stream *stream, struct avdtp_error *err,
    640 			void *user_data)
    641 {
    642 	struct a2dp_sep *a2dp_sep = user_data;
    643 	struct a2dp_setup *setup;
    644 
    645 	if (a2dp_sep->type == AVDTP_SEP_TYPE_SINK)
    646 		debug("Sink %p: Start_Cfm", sep);
    647 	else
    648 		debug("Source %p: Start_Cfm", sep);
    649 
    650 	setup = find_setup_by_session(session);
    651 	if (!setup)
    652 		return;
    653 
    654 	if (setup->canceled) {
    655 		if (!err)
    656 			avdtp_close(session, stream);
    657 		setup_unref(setup);
    658 		return;
    659 	}
    660 
    661 	if (err) {
    662 		setup->stream = NULL;
    663 		setup->err = err;
    664 	}
    665 
    666 	finalize_resume(setup);
    667 }
    668 
    669 static gboolean suspend_ind(struct avdtp *session, struct avdtp_local_sep *sep,
    670 				struct avdtp_stream *stream, uint8_t *err,
    671 				void *user_data)
    672 {
    673 	struct a2dp_sep *a2dp_sep = user_data;
    674 
    675 	if (a2dp_sep->type == AVDTP_SEP_TYPE_SINK)
    676 		debug("Sink %p: Suspend_Ind", sep);
    677 	else
    678 		debug("Source %p: Suspend_Ind", sep);
    679 
    680 	if (a2dp_sep->suspend_timer) {
    681 		g_source_remove(a2dp_sep->suspend_timer);
    682 		a2dp_sep->suspend_timer = 0;
    683 		avdtp_unref(a2dp_sep->session);
    684 		a2dp_sep->session = NULL;
    685 	}
    686 
    687 	return TRUE;
    688 }
    689 
    690 static void suspend_cfm(struct avdtp *session, struct avdtp_local_sep *sep,
    691 			struct avdtp_stream *stream, struct avdtp_error *err,
    692 			void *user_data)
    693 {
    694 	struct a2dp_sep *a2dp_sep = user_data;
    695 	struct a2dp_setup *setup;
    696 	gboolean start;
    697 
    698 	if (a2dp_sep->type == AVDTP_SEP_TYPE_SINK)
    699 		debug("Sink %p: Suspend_Cfm", sep);
    700 	else
    701 		debug("Source %p: Suspend_Cfm", sep);
    702 
    703 	a2dp_sep->suspending = FALSE;
    704 
    705 	setup = find_setup_by_session(session);
    706 	if (!setup)
    707 		return;
    708 
    709 	start = setup->start;
    710 	setup->start = FALSE;
    711 
    712 	if (err) {
    713 		setup->stream = NULL;
    714 		setup->err = err;
    715 		finalize_suspend(setup);
    716 	}
    717 	else
    718 		finalize_suspend_errno(setup, 0);
    719 
    720 	if (!start)
    721 		return;
    722 
    723 	if (err) {
    724 		setup->err = err;
    725 		finalize_suspend(setup);
    726 	} else if (avdtp_start(session, a2dp_sep->stream) < 0) {
    727 		struct avdtp_error start_err;
    728 		error("avdtp_start failed");
    729 		avdtp_error_init(&start_err, AVDTP_ERROR_ERRNO, EIO);
    730 		setup->err = err;
    731 		finalize_suspend(setup);
    732 	}
    733 }
    734 
    735 static gboolean close_ind(struct avdtp *session, struct avdtp_local_sep *sep,
    736 				struct avdtp_stream *stream, uint8_t *err,
    737 				void *user_data)
    738 {
    739 	struct a2dp_sep *a2dp_sep = user_data;
    740 
    741 	if (a2dp_sep->type == AVDTP_SEP_TYPE_SINK)
    742 		debug("Sink %p: Close_Ind", sep);
    743 	else
    744 		debug("Source %p: Close_Ind", sep);
    745 
    746 	return TRUE;
    747 }
    748 
    749 static gboolean a2dp_reconfigure(gpointer data)
    750 {
    751 	struct a2dp_setup *setup = data;
    752 	struct avdtp_local_sep *lsep;
    753 	struct avdtp_remote_sep *rsep;
    754 	struct avdtp_service_capability *cap;
    755 	struct avdtp_media_codec_capability *codec_cap = NULL;
    756 	GSList *l;
    757 	int posix_err;
    758 
    759 	for (l = setup->client_caps; l != NULL; l = l->next) {
    760 		cap = l->data;
    761 
    762 		if (cap->category != AVDTP_MEDIA_CODEC)
    763 			continue;
    764 
    765 		codec_cap = (void *) cap->data;
    766 		break;
    767 	}
    768 
    769 	if (!codec_cap) {
    770 		error("Cannot find capabilities to reconfigure");
    771 		posix_err = -EINVAL;
    772 		goto failed;
    773 	}
    774 
    775 	posix_err = avdtp_get_seps(setup->session, AVDTP_SEP_TYPE_SINK,
    776 					codec_cap->media_type,
    777 					codec_cap->media_codec_type,
    778 					&lsep, &rsep);
    779 	if (posix_err < 0) {
    780 		error("No matching ACP and INT SEPs found");
    781 		goto failed;
    782 	}
    783 
    784 	posix_err = avdtp_set_configuration(setup->session, rsep, lsep,
    785 						setup->client_caps,
    786 						&setup->stream);
    787 	if (posix_err < 0) {
    788 		error("avdtp_set_configuration: %s", strerror(-posix_err));
    789 		goto failed;
    790 	}
    791 
    792 	return FALSE;
    793 
    794 failed:
    795 	finalize_config_errno(setup, posix_err);
    796 	return FALSE;
    797 }
    798 
    799 static void close_cfm(struct avdtp *session, struct avdtp_local_sep *sep,
    800 			struct avdtp_stream *stream, struct avdtp_error *err,
    801 			void *user_data)
    802 {
    803 	struct a2dp_sep *a2dp_sep = user_data;
    804 	struct a2dp_setup *setup;
    805 
    806 	if (a2dp_sep->type == AVDTP_SEP_TYPE_SINK)
    807 		debug("Sink %p: Close_Cfm", sep);
    808 	else
    809 		debug("Source %p: Close_Cfm", sep);
    810 
    811 	setup = find_setup_by_session(session);
    812 	if (!setup)
    813 		return;
    814 
    815 	if (setup->canceled) {
    816 		setup_unref(setup);
    817 		return;
    818 	}
    819 
    820 	if (err) {
    821 		setup->stream = NULL;
    822 		setup->err = err;
    823 		finalize_config(setup);
    824 		return;
    825 	}
    826 
    827 	if (setup->reconfigure)
    828 		g_timeout_add(RECONFIGURE_TIMEOUT, a2dp_reconfigure, setup);
    829 }
    830 
    831 static gboolean abort_ind(struct avdtp *session, struct avdtp_local_sep *sep,
    832 				struct avdtp_stream *stream, uint8_t *err,
    833 				void *user_data)
    834 {
    835 	struct a2dp_sep *a2dp_sep = user_data;
    836 
    837 	if (a2dp_sep->type == AVDTP_SEP_TYPE_SINK)
    838 		debug("Sink %p: Abort_Ind", sep);
    839 	else
    840 		debug("Source %p: Abort_Ind", sep);
    841 
    842 	a2dp_sep->stream = NULL;
    843 
    844 	return TRUE;
    845 }
    846 
    847 static void abort_cfm(struct avdtp *session, struct avdtp_local_sep *sep,
    848 			struct avdtp_stream *stream, struct avdtp_error *err,
    849 			void *user_data)
    850 {
    851 	struct a2dp_sep *a2dp_sep = user_data;
    852 	struct a2dp_setup *setup;
    853 
    854 	if (a2dp_sep->type == AVDTP_SEP_TYPE_SINK)
    855 		debug("Sink %p: Abort_Cfm", sep);
    856 	else
    857 		debug("Source %p: Abort_Cfm", sep);
    858 
    859 	setup = find_setup_by_session(session);
    860 	if (!setup)
    861 		return;
    862 
    863 	setup_unref(setup);
    864 }
    865 
    866 static gboolean reconf_ind(struct avdtp *session, struct avdtp_local_sep *sep,
    867 				uint8_t *err, void *user_data)
    868 {
    869 	struct a2dp_sep *a2dp_sep = user_data;
    870 
    871 	if (a2dp_sep->type == AVDTP_SEP_TYPE_SINK)
    872 		debug("Sink %p: ReConfigure_Ind", sep);
    873 	else
    874 		debug("Source %p: ReConfigure_Ind", sep);
    875 	return TRUE;
    876 }
    877 
    878 static void reconf_cfm(struct avdtp *session, struct avdtp_local_sep *sep,
    879 			struct avdtp_stream *stream, struct avdtp_error *err,
    880 			void *user_data)
    881 {
    882 	struct a2dp_sep *a2dp_sep = user_data;
    883 	struct a2dp_setup *setup;
    884 
    885 	if (a2dp_sep->type == AVDTP_SEP_TYPE_SINK)
    886 		debug("Sink %p: ReConfigure_Cfm", sep);
    887 	else
    888 		debug("Source %p: ReConfigure_Cfm", sep);
    889 
    890 	setup = find_setup_by_session(session);
    891 	if (!setup)
    892 		return;
    893 
    894 	if (setup->canceled) {
    895 		if (!err)
    896 			avdtp_close(session, stream);
    897 		setup_unref(setup);
    898 		return;
    899 	}
    900 
    901 	if (err) {
    902 		setup->stream = NULL;
    903 		setup->err = err;
    904 	}
    905 
    906 	finalize_config(setup);
    907 }
    908 
    909 static struct avdtp_sep_cfm cfm = {
    910 	.set_configuration	= setconf_cfm,
    911 	.get_configuration	= getconf_cfm,
    912 	.open			= open_cfm,
    913 	.start			= start_cfm,
    914 	.suspend		= suspend_cfm,
    915 	.close			= close_cfm,
    916 	.abort			= abort_cfm,
    917 	.reconfigure		= reconf_cfm
    918 };
    919 
    920 static struct avdtp_sep_ind sbc_ind = {
    921 	.get_capability		= sbc_getcap_ind,
    922 	.set_configuration	= sbc_setconf_ind,
    923 	.get_configuration	= getconf_ind,
    924 	.open			= open_ind,
    925 	.start			= start_ind,
    926 	.suspend		= suspend_ind,
    927 	.close			= close_ind,
    928 	.abort			= abort_ind,
    929 	.reconfigure		= reconf_ind
    930 };
    931 
    932 static struct avdtp_sep_ind mpeg_ind = {
    933 	.get_capability		= mpeg_getcap_ind,
    934 	.set_configuration	= mpeg_setconf_ind,
    935 	.get_configuration	= getconf_ind,
    936 	.open			= open_ind,
    937 	.start			= start_ind,
    938 	.suspend		= suspend_ind,
    939 	.close			= close_ind,
    940 	.abort			= abort_ind,
    941 	.reconfigure		= reconf_ind
    942 };
    943 
    944 static sdp_record_t *a2dp_record(uint8_t type)
    945 {
    946 	sdp_list_t *svclass_id, *pfseq, *apseq, *root;
    947 	uuid_t root_uuid, l2cap_uuid, avdtp_uuid, a2dp_uuid;
    948 	sdp_profile_desc_t profile[1];
    949 	sdp_list_t *aproto, *proto[2];
    950 	sdp_record_t *record;
    951 	sdp_data_t *psm, *version, *features;
    952 	uint16_t lp = AVDTP_UUID, ver = 0x0100, feat = 0x000F;
    953 
    954 	record = sdp_record_alloc();
    955 	if (!record)
    956 		return NULL;
    957 
    958 	sdp_uuid16_create(&root_uuid, PUBLIC_BROWSE_GROUP);
    959 	root = sdp_list_append(0, &root_uuid);
    960 	sdp_set_browse_groups(record, root);
    961 
    962 	if (type == AVDTP_SEP_TYPE_SOURCE)
    963 		sdp_uuid16_create(&a2dp_uuid, AUDIO_SOURCE_SVCLASS_ID);
    964 	else
    965 		sdp_uuid16_create(&a2dp_uuid, AUDIO_SINK_SVCLASS_ID);
    966 	svclass_id = sdp_list_append(0, &a2dp_uuid);
    967 	sdp_set_service_classes(record, svclass_id);
    968 
    969 	sdp_uuid16_create(&profile[0].uuid, ADVANCED_AUDIO_PROFILE_ID);
    970 	profile[0].version = 0x0100;
    971 	pfseq = sdp_list_append(0, &profile[0]);
    972 	sdp_set_profile_descs(record, pfseq);
    973 
    974 	sdp_uuid16_create(&l2cap_uuid, L2CAP_UUID);
    975 	proto[0] = sdp_list_append(0, &l2cap_uuid);
    976 	psm = sdp_data_alloc(SDP_UINT16, &lp);
    977 	proto[0] = sdp_list_append(proto[0], psm);
    978 	apseq = sdp_list_append(0, proto[0]);
    979 
    980 	sdp_uuid16_create(&avdtp_uuid, AVDTP_UUID);
    981 	proto[1] = sdp_list_append(0, &avdtp_uuid);
    982 	version = sdp_data_alloc(SDP_UINT16, &ver);
    983 	proto[1] = sdp_list_append(proto[1], version);
    984 	apseq = sdp_list_append(apseq, proto[1]);
    985 
    986 	aproto = sdp_list_append(0, apseq);
    987 	sdp_set_access_protos(record, aproto);
    988 
    989 	features = sdp_data_alloc(SDP_UINT16, &feat);
    990 	sdp_attr_add(record, SDP_ATTR_SUPPORTED_FEATURES, features);
    991 
    992 	if (type == AVDTP_SEP_TYPE_SOURCE)
    993 		sdp_set_info_attr(record, "Audio Source", 0, 0);
    994 	else
    995 		sdp_set_info_attr(record, "Audio Sink", 0, 0);
    996 
    997 	free(psm);
    998 	free(version);
    999 	sdp_list_free(proto[0], 0);
   1000 	sdp_list_free(proto[1], 0);
   1001 	sdp_list_free(apseq, 0);
   1002 	sdp_list_free(pfseq, 0);
   1003 	sdp_list_free(aproto, 0);
   1004 	sdp_list_free(root, 0);
   1005 	sdp_list_free(svclass_id, 0);
   1006 
   1007 	return record;
   1008 }
   1009 
   1010 static struct a2dp_sep *a2dp_add_sep(struct a2dp_server *server, uint8_t type,
   1011 					uint8_t codec)
   1012 {
   1013 	struct a2dp_sep *sep;
   1014 	GSList **l;
   1015 	uint32_t *record_id;
   1016 	sdp_record_t *record;
   1017 	struct avdtp_sep_ind *ind;
   1018 
   1019 	sep = g_new0(struct a2dp_sep, 1);
   1020 
   1021 	ind = (codec == A2DP_CODEC_MPEG12) ? &mpeg_ind : &sbc_ind;
   1022 	sep->sep = avdtp_register_sep(&server->src, type,
   1023 					AVDTP_MEDIA_TYPE_AUDIO, codec, ind,
   1024 					&cfm, sep);
   1025 	if (sep->sep == NULL) {
   1026 		g_free(sep);
   1027 		return NULL;
   1028 	}
   1029 
   1030 	sep->codec = codec;
   1031 	sep->type = type;
   1032 
   1033 	if (type == AVDTP_SEP_TYPE_SOURCE) {
   1034 		l = &server->sources;
   1035 		record_id = &server->source_record_id;
   1036 	} else {
   1037 		l = &server->sinks;
   1038 		record_id = &server->sink_record_id;
   1039 	}
   1040 
   1041 	if (*record_id != 0)
   1042 		goto add;
   1043 
   1044 	record = a2dp_record(type);
   1045 	if (!record) {
   1046 		error("Unable to allocate new service record");
   1047 		avdtp_unregister_sep(sep->sep);
   1048 		g_free(sep);
   1049 		return NULL;
   1050 	}
   1051 
   1052 	if (add_record_to_server(&server->src, record) < 0) {
   1053 		error("Unable to register A2DP service record");\
   1054 		sdp_record_free(record);
   1055 		avdtp_unregister_sep(sep->sep);
   1056 		g_free(sep);
   1057 		return NULL;
   1058 	}
   1059 	*record_id = record->handle;
   1060 
   1061 add:
   1062 	*l = g_slist_append(*l, sep);
   1063 
   1064 	return sep;
   1065 }
   1066 
   1067 static struct a2dp_server *find_server(GSList *list, const bdaddr_t *src)
   1068 {
   1069 	GSList *l;
   1070 
   1071 	for (l = list; l; l = l->next) {
   1072 		struct a2dp_server *server = l->data;
   1073 
   1074 		if (bacmp(&server->src, src) == 0)
   1075 			return server;
   1076 	}
   1077 
   1078 	return NULL;
   1079 }
   1080 
   1081 int a2dp_register(DBusConnection *conn, const bdaddr_t *src, GKeyFile *config)
   1082 {
   1083 	int sbc_srcs = 1, sbc_sinks = 1;
   1084 	int mpeg12_srcs = 0, mpeg12_sinks = 0;
   1085 	gboolean source = TRUE, sink = FALSE;
   1086 	char *str;
   1087 	GError *err = NULL;
   1088 	int i;
   1089 	struct a2dp_server *server;
   1090 
   1091 	if (!config)
   1092 		goto proceed;
   1093 
   1094 	str = g_key_file_get_string(config, "General", "Enable", &err);
   1095 
   1096 	if (err) {
   1097 		debug("audio.conf: %s", err->message);
   1098 		g_clear_error(&err);
   1099 	} else {
   1100 		if (strstr(str, "Sink"))
   1101 			source = TRUE;
   1102 		if (strstr(str, "Source"))
   1103 			sink = TRUE;
   1104 		g_free(str);
   1105 	}
   1106 
   1107 	str = g_key_file_get_string(config, "General", "Disable", &err);
   1108 
   1109 	if (err) {
   1110 		debug("audio.conf: %s", err->message);
   1111 		g_clear_error(&err);
   1112 	} else {
   1113 		if (strstr(str, "Sink"))
   1114 			source = FALSE;
   1115 		if (strstr(str, "Source"))
   1116 			sink = FALSE;
   1117 		g_free(str);
   1118 	}
   1119 
   1120 	str = g_key_file_get_string(config, "A2DP", "SBCSources", &err);
   1121 	if (err) {
   1122 		debug("audio.conf: %s", err->message);
   1123 		g_clear_error(&err);
   1124 	} else {
   1125 		sbc_srcs = atoi(str);
   1126 		g_free(str);
   1127 	}
   1128 
   1129 	str = g_key_file_get_string(config, "A2DP", "MPEG12Sources", &err);
   1130 	if (err) {
   1131 		debug("audio.conf: %s", err->message);
   1132 		g_clear_error(&err);
   1133 	} else {
   1134 		mpeg12_srcs = atoi(str);
   1135 		g_free(str);
   1136 	}
   1137 
   1138 	str = g_key_file_get_string(config, "A2DP", "SBCSinks", &err);
   1139 	if (err) {
   1140 		debug("audio.conf: %s", err->message);
   1141 		g_clear_error(&err);
   1142 	} else {
   1143 		sbc_sinks = atoi(str);
   1144 		g_free(str);
   1145 	}
   1146 
   1147 	str = g_key_file_get_string(config, "A2DP", "MPEG12Sinks", &err);
   1148 	if (err) {
   1149 		debug("audio.conf: %s", err->message);
   1150 		g_clear_error(&err);
   1151 	} else {
   1152 		mpeg12_sinks = atoi(str);
   1153 		g_free(str);
   1154 	}
   1155 
   1156 proceed:
   1157 	if (!connection)
   1158 		connection = dbus_connection_ref(conn);
   1159 
   1160 	server = find_server(servers, src);
   1161 	if (!server) {
   1162 		int av_err;
   1163 
   1164 		server = g_new0(struct a2dp_server, 1);
   1165 		if (!server)
   1166 			return -ENOMEM;
   1167 
   1168 		av_err = avdtp_init(src, config);
   1169 		if (av_err < 0)
   1170 			return av_err;
   1171 
   1172 		bacpy(&server->src, src);
   1173 		servers = g_slist_append(servers, server);
   1174 	}
   1175 
   1176 	if (source) {
   1177 		for (i = 0; i < sbc_srcs; i++)
   1178 			a2dp_add_sep(server, AVDTP_SEP_TYPE_SOURCE,
   1179 					A2DP_CODEC_SBC);
   1180 
   1181 		for (i = 0; i < mpeg12_srcs; i++)
   1182 			a2dp_add_sep(server, AVDTP_SEP_TYPE_SOURCE,
   1183 					A2DP_CODEC_MPEG12);
   1184 	}
   1185 
   1186 	if (sink) {
   1187 		for (i = 0; i < sbc_sinks; i++)
   1188 			a2dp_add_sep(server, AVDTP_SEP_TYPE_SINK,
   1189 					A2DP_CODEC_SBC);
   1190 
   1191 		for (i = 0; i < mpeg12_sinks; i++)
   1192 			a2dp_add_sep(server, AVDTP_SEP_TYPE_SINK,
   1193 					A2DP_CODEC_MPEG12);
   1194 	}
   1195 
   1196 	return 0;
   1197 }
   1198 
   1199 static void a2dp_unregister_sep(struct a2dp_sep *sep)
   1200 {
   1201 	avdtp_unregister_sep(sep->sep);
   1202 	g_free(sep);
   1203 }
   1204 
   1205 void a2dp_unregister(const bdaddr_t *src)
   1206 {
   1207 	struct a2dp_server *server;
   1208 
   1209 	server = find_server(servers, src);
   1210 	if (!server)
   1211 		return;
   1212 
   1213 	g_slist_foreach(server->sinks, (GFunc) a2dp_unregister_sep, NULL);
   1214 	g_slist_free(server->sinks);
   1215 
   1216 	g_slist_foreach(server->sources, (GFunc) a2dp_unregister_sep, NULL);
   1217 	g_slist_free(server->sources);
   1218 
   1219 	avdtp_exit(src);
   1220 
   1221 	if (server->source_record_id)
   1222 		remove_record_from_server(server->source_record_id);
   1223 
   1224 	if (server->sink_record_id)
   1225 		remove_record_from_server(server->sink_record_id);
   1226 
   1227 	servers = g_slist_remove(servers, server);
   1228 	g_free(server);
   1229 
   1230 	if (servers)
   1231 		return;
   1232 
   1233 	dbus_connection_unref(connection);
   1234 	connection = NULL;
   1235 }
   1236 
   1237 struct a2dp_sep *a2dp_get(struct avdtp *session,
   1238 				struct avdtp_remote_sep *rsep)
   1239 {
   1240 	GSList *l;
   1241 	struct a2dp_server *server;
   1242 	struct avdtp_service_capability *cap;
   1243 	struct avdtp_media_codec_capability *codec_cap = NULL;
   1244 	bdaddr_t src;
   1245 
   1246 	avdtp_get_peers(session, &src, NULL);
   1247 	server = find_server(servers, &src);
   1248 	if (!server)
   1249 		return NULL;
   1250 
   1251 	cap = avdtp_get_codec(rsep);
   1252 	codec_cap = (void *) cap->data;
   1253 
   1254 	if (avdtp_get_type(rsep) == AVDTP_SEP_TYPE_SINK)
   1255 		l = server->sources;
   1256 	else
   1257 		l = server->sinks;
   1258 
   1259 	for (; l != NULL; l = l->next) {
   1260 		struct a2dp_sep *sep = l->data;
   1261 
   1262 		if (sep->locked)
   1263 			continue;
   1264 
   1265 		if (sep->codec != codec_cap->media_codec_type)
   1266 			continue;
   1267 
   1268 		if (!sep->stream || avdtp_has_stream(session, sep->stream))
   1269 			return sep;
   1270 	}
   1271 
   1272 	return NULL;
   1273 }
   1274 
   1275 unsigned int a2dp_config(struct avdtp *session, struct a2dp_sep *sep,
   1276 				a2dp_config_cb_t cb, GSList *caps,
   1277 				void *user_data)
   1278 {
   1279 	struct a2dp_setup_cb *cb_data;
   1280 	GSList *l;
   1281 	struct a2dp_server *server;
   1282 	struct a2dp_setup *setup;
   1283 	struct a2dp_sep *tmp;
   1284 	struct avdtp_local_sep *lsep;
   1285 	struct avdtp_remote_sep *rsep;
   1286 	struct avdtp_service_capability *cap;
   1287 	struct avdtp_media_codec_capability *codec_cap = NULL;
   1288 	int posix_err;
   1289 	bdaddr_t src;
   1290 	uint8_t remote_type;
   1291 
   1292 	avdtp_get_peers(session, &src, NULL);
   1293 	server = find_server(servers, &src);
   1294 	if (!server)
   1295 		return 0;
   1296 
   1297 	for (l = caps; l != NULL; l = l->next) {
   1298 		cap = l->data;
   1299 
   1300 		if (cap->category != AVDTP_MEDIA_CODEC)
   1301 			continue;
   1302 
   1303 		codec_cap = (void *) cap->data;
   1304 		break;
   1305 	}
   1306 
   1307 	if (!codec_cap)
   1308 		return 0;
   1309 
   1310 	if (sep->codec != codec_cap->media_codec_type)
   1311 		return 0;
   1312 
   1313 	debug("a2dp_config: selected SEP %p", sep->sep);
   1314 
   1315 	cb_data = g_new0(struct a2dp_setup_cb, 1);
   1316 	cb_data->config_cb = cb;
   1317 	cb_data->user_data = user_data;
   1318 	cb_data->id = ++cb_id;
   1319 
   1320 	setup = find_setup_by_session(session);
   1321 	if (!setup) {
   1322 		setup = g_new0(struct a2dp_setup, 1);
   1323 		setup->session = avdtp_ref(session);
   1324 		setup->dev = a2dp_get_dev(session);
   1325 		setups = g_slist_append(setups, setup);
   1326 	}
   1327 
   1328 	setup_ref(setup);
   1329 	setup->cb = g_slist_append(setup->cb, cb_data);
   1330 	setup->sep = sep;
   1331 	setup->stream = sep->stream;
   1332 	setup->client_caps = caps;
   1333 
   1334 	switch (avdtp_sep_get_state(sep->sep)) {
   1335 	case AVDTP_STATE_IDLE:
   1336 		if (sep->type == AVDTP_SEP_TYPE_SOURCE) {
   1337 			l = server->sources;
   1338 			remote_type = AVDTP_SEP_TYPE_SINK;
   1339 		} else {
   1340 			remote_type = AVDTP_SEP_TYPE_SOURCE;
   1341 			l = server->sinks;
   1342 		}
   1343 
   1344 		for (; l != NULL; l = l->next) {
   1345 			tmp = l->data;
   1346 			if (avdtp_has_stream(session, tmp->stream))
   1347 				break;
   1348 		}
   1349 
   1350 		if (l != NULL) {
   1351 			setup->reconfigure = TRUE;
   1352 			if (avdtp_close(session, tmp->stream) < 0) {
   1353 				error("avdtp_close failed");
   1354 				goto failed;
   1355 			}
   1356 			break;
   1357 		}
   1358 
   1359 		if (avdtp_get_seps(session, remote_type,
   1360 				codec_cap->media_type,
   1361 				codec_cap->media_codec_type,
   1362 				&lsep, &rsep) < 0) {
   1363 			error("No matching ACP and INT SEPs found");
   1364 			goto failed;
   1365 		}
   1366 
   1367 		posix_err = avdtp_set_configuration(session, rsep, lsep,
   1368 							caps, &setup->stream);
   1369 		if (posix_err < 0) {
   1370 			error("avdtp_set_configuration: %s",
   1371 				strerror(-posix_err));
   1372 			goto failed;
   1373 		}
   1374 		break;
   1375 	case AVDTP_STATE_OPEN:
   1376 	case AVDTP_STATE_STREAMING:
   1377 		if (avdtp_stream_has_capabilities(setup->stream, caps)) {
   1378 			debug("Configuration match: resuming");
   1379 			g_idle_add((GSourceFunc) finalize_config, setup);
   1380 		} else if (!setup->reconfigure) {
   1381 			setup->reconfigure = TRUE;
   1382 			if (avdtp_close(session, sep->stream) < 0) {
   1383 				error("avdtp_close failed");
   1384 				goto failed;
   1385 			}
   1386 		}
   1387 		break;
   1388 	default:
   1389 		error("SEP in bad state for requesting a new stream");
   1390 		goto failed;
   1391 	}
   1392 
   1393 	return cb_data->id;
   1394 
   1395 failed:
   1396 	setup_unref(setup);
   1397 	cb_id--;
   1398 	return 0;
   1399 }
   1400 
   1401 unsigned int a2dp_resume(struct avdtp *session, struct a2dp_sep *sep,
   1402 				a2dp_stream_cb_t cb, void *user_data)
   1403 {
   1404 	struct a2dp_setup_cb *cb_data;
   1405 	struct a2dp_setup *setup;
   1406 
   1407 	cb_data = g_new0(struct a2dp_setup_cb, 1);
   1408 	cb_data->resume_cb = cb;
   1409 	cb_data->user_data = user_data;
   1410 	cb_data->id = ++cb_id;
   1411 
   1412 	setup = find_setup_by_session(session);
   1413 	if (!setup) {
   1414 		setup = g_new0(struct a2dp_setup, 1);
   1415 		setup->session = avdtp_ref(session);
   1416 		setup->dev = a2dp_get_dev(session);
   1417 		setups = g_slist_append(setups, setup);
   1418 	}
   1419 
   1420 	setup_ref(setup);
   1421 	setup->cb = g_slist_append(setup->cb, cb_data);
   1422 	setup->sep = sep;
   1423 	setup->stream = sep->stream;
   1424 
   1425 	switch (avdtp_sep_get_state(sep->sep)) {
   1426 	case AVDTP_STATE_IDLE:
   1427 		goto failed;
   1428 		break;
   1429 	case AVDTP_STATE_OPEN:
   1430 		if (avdtp_start(session, sep->stream) < 0) {
   1431 			error("avdtp_start failed");
   1432 			goto failed;
   1433 		}
   1434 		break;
   1435 	case AVDTP_STATE_STREAMING:
   1436 		if (!sep->suspending && sep->suspend_timer) {
   1437 			g_source_remove(sep->suspend_timer);
   1438 			sep->suspend_timer = 0;
   1439 			avdtp_unref(sep->session);
   1440 			sep->session = NULL;
   1441 		}
   1442 		if (sep->suspending)
   1443 			setup->start = TRUE;
   1444 		else
   1445 			g_idle_add((GSourceFunc) finalize_resume, setup);
   1446 		break;
   1447 	default:
   1448 		error("SEP in bad state for resume");
   1449 		goto failed;
   1450 	}
   1451 
   1452 	return cb_data->id;
   1453 
   1454 failed:
   1455 	setup_unref(setup);
   1456 	cb_id--;
   1457 	return 0;
   1458 }
   1459 
   1460 unsigned int a2dp_suspend(struct avdtp *session, struct a2dp_sep *sep,
   1461 				a2dp_stream_cb_t cb, void *user_data)
   1462 {
   1463 	struct a2dp_setup_cb *cb_data;
   1464 	struct a2dp_setup *setup;
   1465 
   1466 	cb_data = g_new0(struct a2dp_setup_cb, 1);
   1467 	cb_data->suspend_cb = cb;
   1468 	cb_data->user_data = user_data;
   1469 	cb_data->id = ++cb_id;
   1470 
   1471 	setup = find_setup_by_session(session);
   1472 	if (!setup) {
   1473 		setup = g_new0(struct a2dp_setup, 1);
   1474 		setup->session = avdtp_ref(session);
   1475 		setup->dev = a2dp_get_dev(session);
   1476 		setups = g_slist_append(setups, setup);
   1477 	}
   1478 
   1479 	setup_ref(setup);
   1480 	setup->cb = g_slist_append(setup->cb, cb_data);
   1481 	setup->sep = sep;
   1482 	setup->stream = sep->stream;
   1483 
   1484 	switch (avdtp_sep_get_state(sep->sep)) {
   1485 	case AVDTP_STATE_IDLE:
   1486 		error("a2dp_suspend: no stream to suspend");
   1487 		goto failed;
   1488 		break;
   1489 	case AVDTP_STATE_OPEN:
   1490 		g_idle_add((GSourceFunc) finalize_suspend, setup);
   1491 		break;
   1492 	case AVDTP_STATE_STREAMING:
   1493 		if (avdtp_suspend(session, sep->stream) < 0) {
   1494 			error("avdtp_suspend failed");
   1495 			goto failed;
   1496 		}
   1497 		break;
   1498 	default:
   1499 		error("SEP in bad state for suspend");
   1500 		goto failed;
   1501 	}
   1502 
   1503 	return cb_data->id;
   1504 
   1505 failed:
   1506 	setup_unref(setup);
   1507 	cb_id--;
   1508 	return 0;
   1509 }
   1510 
   1511 gboolean a2dp_cancel(struct audio_device *dev, unsigned int id)
   1512 {
   1513 	struct a2dp_setup_cb *cb_data;
   1514 	struct a2dp_setup *setup;
   1515 	GSList *l;
   1516 
   1517 	debug("a2dp_cancel()");
   1518 
   1519 	setup = find_setup_by_dev(dev);
   1520 	if (!setup)
   1521 		return FALSE;
   1522 
   1523 	for (cb_data = NULL, l = setup->cb; l != NULL; l = g_slist_next(l)) {
   1524 		struct a2dp_setup_cb *cb = l->data;
   1525 
   1526 		if (cb->id == id) {
   1527 			cb_data = cb;
   1528 			break;
   1529 		}
   1530 	}
   1531 
   1532 	if (!cb_data)
   1533 		error("a2dp_cancel: no matching callback with id %u", id);
   1534 
   1535 	setup->cb = g_slist_remove(setup->cb, cb_data);
   1536 	g_free(cb_data);
   1537 
   1538 	if (!setup->cb) {
   1539 		setup->canceled = TRUE;
   1540 		setup->sep = NULL;
   1541 	}
   1542 
   1543 	return TRUE;
   1544 }
   1545 
   1546 gboolean a2dp_sep_lock(struct a2dp_sep *sep, struct avdtp *session)
   1547 {
   1548 	if (sep->locked)
   1549 		return FALSE;
   1550 
   1551 	debug("SEP %p locked", sep->sep);
   1552 	sep->locked = TRUE;
   1553 
   1554 	return TRUE;
   1555 }
   1556 
   1557 gboolean a2dp_sep_unlock(struct a2dp_sep *sep, struct avdtp *session)
   1558 {
   1559 	avdtp_state_t state;
   1560 
   1561 	state = avdtp_sep_get_state(sep->sep);
   1562 
   1563 	sep->locked = FALSE;
   1564 
   1565 	debug("SEP %p unlocked", sep->sep);
   1566 
   1567 	if (!sep->stream || state == AVDTP_STATE_IDLE)
   1568 		return TRUE;
   1569 
   1570 	switch (state) {
   1571 	case AVDTP_STATE_OPEN:
   1572 		/* Set timer here */
   1573 		break;
   1574 	case AVDTP_STATE_STREAMING:
   1575 		if (avdtp_suspend(session, sep->stream) == 0)
   1576 			sep->suspending = TRUE;
   1577 		break;
   1578 	default:
   1579 		break;
   1580 	}
   1581 
   1582 	return TRUE;
   1583 }
   1584 
   1585 gboolean a2dp_sep_get_lock(struct a2dp_sep *sep)
   1586 {
   1587 	return sep->locked;
   1588 }
   1589 
   1590 static int stream_cmp(gconstpointer data, gconstpointer user_data)
   1591 {
   1592 	const struct a2dp_sep *sep = data;
   1593 	const struct avdtp_stream *stream = user_data;
   1594 
   1595 	return (sep->stream != stream);
   1596 }
   1597 
   1598 struct a2dp_sep *a2dp_get_sep(struct avdtp *session,
   1599 				struct avdtp_stream *stream)
   1600 {
   1601 	struct a2dp_server *server;
   1602 	bdaddr_t src, dst;
   1603 	GSList *l;
   1604 
   1605 	avdtp_get_peers(session, &src, &dst);
   1606 
   1607 	for (l = servers; l; l = l->next) {
   1608 		server = l->data;
   1609 
   1610 		if (bacmp(&src, &server->src) == 0)
   1611 			break;
   1612 	}
   1613 
   1614 	if (!l)
   1615 		return NULL;
   1616 
   1617 	l = g_slist_find_custom(server->sources, stream, stream_cmp);
   1618 	if (l)
   1619 		return l->data;
   1620 
   1621 	l = g_slist_find_custom(server->sinks, stream, stream_cmp);
   1622 	if (l)
   1623 		return l->data;
   1624 
   1625 	return NULL;
   1626 }
   1627