linux-bluetooth.vger.kernel.org archive mirror
 help / color / mirror / Atom feed
From: Pauli Virtanen <pav@iki.fi>
To: linux-bluetooth@vger.kernel.org
Cc: Pauli Virtanen <pav@iki.fi>
Subject: [PATCH BlueZ v3] media: clear the right transport when clearing BAP endpoint
Date: Sun, 12 Feb 2023 14:00:43 +0000	[thread overview]
Message-ID: <e15e60d7941eba174cf306b45c80bc53435554b0.1676210275.git.pav@iki.fi> (raw)
In-Reply-To: <f93d483b5deb1628ba822ab752767b17e946d9c8.1676145318.git.pav@iki.fi>

Each configured BAP stream is associated with a transport, and only that
transport should be cleared when the stream's configuration is cleared.

This is required for multiple BAP clients to use the same Media1
endpoint, which is what we should aim for to follow the spirit in which
the endpoints work in ASCS.  Sound servers generally can handle this,
since the *Configuration calls provide the transport paths, and for
different clients they are associated with different devices.
---

Notes:
    v3:
    * Match transports based on stream, not path.
    
      The path in bt_bap_stream user data is set to endpoint path on
      config, and may be freed too early, if endpoint is freed before
      clearing the PAC, as happens in bap.c:bap_disconnect
    
    In principle multiple clients should work, but I don't have equipment
    right now to test streaming for more than one client.

 profiles/audio/media.c     | 20 +++++++++++++-------
 profiles/audio/transport.c | 13 +++++++++++++
 profiles/audio/transport.h |  1 +
 3 files changed, 27 insertions(+), 7 deletions(-)

diff --git a/profiles/audio/media.c b/profiles/audio/media.c
index 505c4b3a6..8728b69e0 100644
--- a/profiles/audio/media.c
+++ b/profiles/audio/media.c
@@ -86,7 +86,6 @@ struct endpoint_request {
 struct media_endpoint {
 	struct a2dp_sep		*sep;
 	struct bt_bap_pac	*pac;
-	void			*stream;
 	char			*sender;	/* Endpoint DBus bus id */
 	char			*path;		/* Endpoint object path */
 	char			*uuid;		/* Endpoint property UUID */
@@ -1007,9 +1006,6 @@ static void pac_config_cb(struct media_endpoint *endpoint, void *ret, int size,
 	struct pac_config_data *data = user_data;
 	gboolean *ret_value = ret;
 
-	if (ret_value)
-		endpoint->stream = data->stream;
-
 	data->cb(data->stream, ret_value ? 0 : -EINVAL);
 }
 
@@ -1089,11 +1085,21 @@ static int pac_config(struct bt_bap_stream *stream, struct iovec *cfg,
 static void pac_clear(struct bt_bap_stream *stream, void *user_data)
 {
 	struct media_endpoint *endpoint = user_data;
+	GSList *item;
 
-	endpoint->stream = NULL;
+	DBG("endpoint %p stream %p", endpoint, stream);
 
-	while (endpoint->transports != NULL)
-		clear_configuration(endpoint, endpoint->transports->data);
+	item = endpoint->transports;
+	while (item) {
+		struct media_transport *transport = item->data;
+
+		if (media_transport_get_stream(transport) == stream) {
+			clear_configuration(endpoint, transport);
+			item = endpoint->transports;
+		} else {
+			item = item->next;
+		}
+	}
 }
 
 static struct bt_bap_pac_ops pac_ops = {
diff --git a/profiles/audio/transport.c b/profiles/audio/transport.c
index 5e057e2a5..b7aa5107b 100644
--- a/profiles/audio/transport.c
+++ b/profiles/audio/transport.c
@@ -1483,6 +1483,19 @@ const char *media_transport_get_path(struct media_transport *transport)
 	return transport->path;
 }
 
+void *media_transport_get_stream(struct media_transport *transport)
+{
+	struct bap_transport *bap;
+	const char *uuid;
+
+	uuid = media_endpoint_get_uuid(transport->endpoint);
+	if (strcasecmp(uuid, PAC_SINK_UUID) && strcasecmp(uuid, PAC_SOURCE_UUID))
+		return NULL;
+
+	bap = transport->data;
+	return bap->stream;
+}
+
 void media_transport_update_delay(struct media_transport *transport,
 							uint16_t delay)
 {
diff --git a/profiles/audio/transport.h b/profiles/audio/transport.h
index 102fc3cf1..5ca9b8f9e 100644
--- a/profiles/audio/transport.h
+++ b/profiles/audio/transport.h
@@ -19,6 +19,7 @@ struct media_transport *media_transport_create(struct btd_device *device,
 
 void media_transport_destroy(struct media_transport *transport);
 const char *media_transport_get_path(struct media_transport *transport);
+void *media_transport_get_stream(struct media_transport *transport);
 struct btd_device *media_transport_get_dev(struct media_transport *transport);
 int8_t media_transport_get_volume(struct media_transport *transport);
 void media_transport_update_delay(struct media_transport *transport,
-- 
2.39.1


  reply	other threads:[~2023-02-12 14:00 UTC|newest]

Thread overview: 6+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2023-02-11 19:55 [PATCH BlueZ v2 1/2] shared/bap: fix local endpoint state to be per-client Pauli Virtanen
2023-02-11 19:55 ` [PATCH BlueZ v2 2/2] media: clear the right transport when clearing BAP endpoint Pauli Virtanen
2023-02-12 14:00   ` Pauli Virtanen [this message]
2023-02-12 15:21     ` [BlueZ,v3] " bluez.test.bot
2023-02-11 21:38 ` [BlueZ,v2,1/2] shared/bap: fix local endpoint state to be per-client bluez.test.bot
2023-02-13 20:30 ` [PATCH BlueZ v2 1/2] " patchwork-bot+bluetooth

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=e15e60d7941eba174cf306b45c80bc53435554b0.1676210275.git.pav@iki.fi \
    --to=pav@iki.fi \
    --cc=linux-bluetooth@vger.kernel.org \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).