diff --git a/profiles/audio/avrcp.c b/profiles/audio/avrcp.c
index 1622734..bf49cfe 100644
--- a/profiles/audio/avrcp.c
+++ b/profiles/audio/avrcp.c
#include "src/dbus-common.h"
#include "src/shared/timeout.h"
#include "src/shared/util.h"
+#include "src/btd.h"
#include "avctp.h"
#include "avrcp.h"
&volume);
}
- if (!session->controller && !avrcp_event_registered(session,
- AVRCP_EVENT_VOLUME_CHANGED))
+ if (btd_opts.avrcp.volume_without_target) {
+ /* If there is no target profile (we didn't create a controller
+ * for it), allow the call to pass through if the remote
+ * controller registered for a volume changed event.
+ */
+ if (!session->controller && !avrcp_event_registered(session,
+ AVRCP_EVENT_VOLUME_CHANGED))
+ return -ENOTSUP;
+ } else if (!session->controller ||
+ session->controller->version < 0x0104) {
return -ENOTSUP;
+ }
memset(buf, 0, sizeof(buf));
diff --git a/src/btd.h b/src/btd.h
index 383bd7c..147b61f 100644
--- a/src/btd.h
+++ b/src/btd.h
uint8_t stream_mode;
};
+struct btd_avrcp_opts {
+ bool volume_without_target;
+};
+
struct btd_advmon_opts {
uint8_t rssi_sampling_period;
};
enum mps_mode_t mps;
struct btd_avdtp_opts avdtp;
+ struct btd_avrcp_opts avrcp;
uint8_t key_size;
diff --git a/src/main.c b/src/main.c
index 69ae1b1..5bd3a03 100644
--- a/src/main.c
+++ b/src/main.c
NULL
};
+static const char *avrcp_options[] = {
+ "VolumeWithoutTarget",
+ NULL
+};
+
static const char *advmon_options[] = {
"RSSISamplingPeriod",
NULL
{ "GATT", gatt_options },
{ "CSIS", csip_options },
{ "AVDTP", avdtp_options },
+ { "AVRCP", avrcp_options },
{ "AdvMon", advmon_options },
{ }
};
parse_avdtp_stream_mode(config);
}
+static void parse_avrcp(GKeyFile *config)
+{
+ parse_config_bool(config, "AVRCP",
+ "VolumeWithoutTarget",
+ &btd_opts.avrcp.volume_without_target);
+}
+
static void parse_advmon(GKeyFile *config)
{
parse_config_u8(config, "AdvMon", "RSSISamplingPeriod",
parse_gatt(config);
parse_csis(config);
parse_avdtp(config);
+ parse_avrcp(config);
parse_advmon(config);
}
btd_opts.avdtp.session_mode = BT_IO_MODE_BASIC;
btd_opts.avdtp.stream_mode = BT_IO_MODE_BASIC;
+ btd_opts.avrcp.volume_without_target = false;
+
btd_opts.advmon.rssi_sampling_period = 0xFF;
btd_opts.csis.encrypt = true;
}
diff --git a/src/main.conf b/src/main.conf
index 82040b3..5d206b9 100644
--- a/src/main.conf
+++ b/src/main.conf
# streaming: Use L2CAP Streaming Mode
#StreamMode = basic
+[AVRCP]
+# Allow SetAbsoluteVolume calls to a peer device that does not advertise the
+# AVRCP remote control target profile. If it does advertise this profile, the
+# version is ignored.
+#VolumeWithoutTarget = false
+
[Policy]
#
# The ReconnectUUIDs defines the set of remote services that should try