[1/2] bluez5: fix CVE-2018-10910

Message ID 20190325232108.10002-1-ross.burton@intel.com
State Accepted
Commit 7bdf9581e807b978b92f29e11ab2a9e69e08410f
Headers show
Series
  • [1/2] bluez5: fix CVE-2018-10910
Related show

Commit Message

Ross Burton March 25, 2019, 11:21 p.m.
Fix this CVE (Bluetooth discoverability may be enabled with no agents to handle
requests) by backporting a number of patches from upstream.

Signed-off-by: Ross Burton <ross.burton@intel.com>

---
 meta/recipes-connectivity/bluez5/bluez5.inc        |   1 +
 .../bluez5/bluez5/CVE-2018-10910.patch             | 705 +++++++++++++++++++++
 2 files changed, 706 insertions(+)
 create mode 100644 meta/recipes-connectivity/bluez5/bluez5/CVE-2018-10910.patch

-- 
2.11.0

-- 
_______________________________________________
Openembedded-core mailing list
Openembedded-core@lists.openembedded.org
http://lists.openembedded.org/mailman/listinfo/openembedded-core

Patch

diff --git a/meta/recipes-connectivity/bluez5/bluez5.inc b/meta/recipes-connectivity/bluez5/bluez5.inc
index 6d62f524591..aaf2af975d0 100644
--- a/meta/recipes-connectivity/bluez5/bluez5.inc
+++ b/meta/recipes-connectivity/bluez5/bluez5.inc
@@ -53,6 +53,7 @@  SRC_URI = "\
     file://0001-tests-add-a-target-for-building-tests-without-runnin.patch \
     file://0001-test-gatt-Fix-hung-issue.patch \
     file://0001-Makefile.am-Fix-a-race-issue-for-tools.patch \
+    file://CVE-2018-10910.patch \
 "
 S = "${WORKDIR}/bluez-${PV}"
 
diff --git a/meta/recipes-connectivity/bluez5/bluez5/CVE-2018-10910.patch b/meta/recipes-connectivity/bluez5/bluez5/CVE-2018-10910.patch
new file mode 100644
index 00000000000..b4b1846c45b
--- /dev/null
+++ b/meta/recipes-connectivity/bluez5/bluez5/CVE-2018-10910.patch
@@ -0,0 +1,705 @@ 
+A bug in Bluez may allow for the Bluetooth Discoverable state being set to on
+when no Bluetooth agent is registered with the system. This situation could
+lead to the unauthorized pairing of certain Bluetooth devices without any
+form of authentication.
+
+CVE: CVE-2018-10910
+Upstream-Status: Backport
+Signed-off-by: Ross Burton <ross.burton@intel.com>
+
+Subject:    [PATCH BlueZ 1/4] client: Add discoverable-timeout command
+From:       Luiz Augusto von Dentz <luiz.dentz () gmail ! com>
+Date:       2018-07-25 10:20:32
+Message-ID: 20180725102035.19439-1-luiz.dentz () gmail ! com
+[Download RAW message or body]
+
+From: Luiz Augusto von Dentz <luiz.von.dentz@intel.com>
+
+This adds discoverable-timeout command which can be used to get/set
+DiscoverableTimeout property:
+
+[bluetooth]# discoverable-timeout 180
+Changing discoverable-timeout 180 succeeded
+---
+ client/main.c | 43 +++++++++++++++++++++++++++++++++++++++++++
+ 1 file changed, 43 insertions(+)
+
+diff --git a/client/main.c b/client/main.c
+index 87323d8f7..59820c6d9 100644
+--- a/client/main.c
++++ b/client/main.c
+@@ -1061,6 +1061,47 @@ static void cmd_discoverable(int argc, char *argv[])
+ 	return bt_shell_noninteractive_quit(EXIT_FAILURE);
+ }
+ 
++static void cmd_discoverable_timeout(int argc, char *argv[])
++{
++	uint32_t value;
++	char *endptr = NULL;
++	char *str;
++
++	if (argc < 2) {
++		DBusMessageIter iter;
++
++		if (!g_dbus_proxy_get_property(default_ctrl->proxy,
++					"DiscoverableTimeout", &iter)) {
++			bt_shell_printf("Unable to get DiscoverableTimeout\n");
++			return bt_shell_noninteractive_quit(EXIT_FAILURE);
++		}
++
++		dbus_message_iter_get_basic(&iter, &value);
++
++		bt_shell_printf("DiscoverableTimeout: %d seconds\n", value);
++
++		return;
++	}
++
++	value = strtol(argv[1], &endptr, 0);
++	if (!endptr || *endptr != '\0' || value > UINT32_MAX) {
++		bt_shell_printf("Invalid argument\n");
++		return bt_shell_noninteractive_quit(EXIT_FAILURE);
++	}
++
++	str = g_strdup_printf("discoverable-timeout %d", value);
++
++	if (g_dbus_proxy_set_property_basic(default_ctrl->proxy,
++					"DiscoverableTimeout",
++					DBUS_TYPE_UINT32, &value,
++					generic_callback, str, g_free))
++		return;
++
++	g_free(str);
++
++	return bt_shell_noninteractive_quit(EXIT_FAILURE);
++}
++
+ static void cmd_agent(int argc, char *argv[])
+ {
+ 	dbus_bool_t enable;
+@@ -2549,6 +2590,8 @@ static const struct bt_shell_menu main_menu = {
+ 	{ "discoverable", "<on/off>", cmd_discoverable,
+ 					"Set controller discoverable mode",
+ 							NULL },
++	{ "discoverable-timeout", "[value]", cmd_discoverable_timeout,
++					"Set discoverable timeout", NULL },
+ 	{ "agent",        "<on/off/capability>", cmd_agent,
+ 				"Enable/disable agent with given capability",
+ 							capability_generator},
+-- 
+2.17.1
+
+Subject:    [PATCH BlueZ 2/4] client: Make show command print DiscoverableTimeout
+From:       Luiz Augusto von Dentz <luiz.dentz () gmail ! com>
+Date:       2018-07-25 10:20:33
+Message-ID: 20180725102035.19439-2-luiz.dentz () gmail ! com
+[Download RAW message or body]
+
+From: Luiz Augusto von Dentz <luiz.von.dentz@intel.com>
+
+Controller XX:XX:XX:XX:XX:XX (public)
+	Name: Vudentz's T460s
+	Alias: Intel-1
+	Class: 0x004c010c
+	Powered: yes
+	Discoverable: no
+	DiscoverableTimeout: 0x00000000
+	Pairable: yes
+	UUID: Headset AG                (00001112-0000-1000-8000-00805f9b34fb)
+	UUID: Generic Attribute Profile (00001801-0000-1000-8000-00805f9b34fb)
+	UUID: A/V Remote Control        (0000110e-0000-1000-8000-00805f9b34fb)
+	UUID: SIM Access                (0000112d-0000-1000-8000-00805f9b34fb)
+	UUID: Generic Access Profile    (00001800-0000-1000-8000-00805f9b34fb)
+	UUID: PnP Information           (00001200-0000-1000-8000-00805f9b34fb)
+	UUID: A/V Remote Control Target (0000110c-0000-1000-8000-00805f9b34fb)
+	UUID: Audio Source              (0000110a-0000-1000-8000-00805f9b34fb)
+	UUID: Audio Sink                (0000110b-0000-1000-8000-00805f9b34fb)
+	UUID: Headset                   (00001108-0000-1000-8000-00805f9b34fb)
+	Modalias: usb:v1D6Bp0246d0532
+	Discovering: no
+---
+ client/main.c | 1 +
+ 1 file changed, 1 insertion(+)
+
+diff --git a/client/main.c b/client/main.c
+index 59820c6d9..6f472d050 100644
+--- a/client/main.c
++++ b/client/main.c
+@@ -877,6 +877,7 @@ static void cmd_show(int argc, char *argv[])
+ 	print_property(proxy, "Class");
+ 	print_property(proxy, "Powered");
+ 	print_property(proxy, "Discoverable");
++	print_property(proxy, "DiscoverableTimeout");
+ 	print_property(proxy, "Pairable");
+ 	print_uuids(proxy);
+ 	print_property(proxy, "Modalias");
+-- 
+2.17.1
+Subject:    [PATCH BlueZ 3/4] adapter: Track pending settings
+From:       Luiz Augusto von Dentz <luiz.dentz () gmail ! com>
+Date:       2018-07-25 10:20:34
+Message-ID: 20180725102035.19439-3-luiz.dentz () gmail ! com
+[Download RAW message or body]
+
+From: Luiz Augusto von Dentz <luiz.von.dentz@intel.com>
+
+This tracks settings being changed and in case the settings is already
+pending considered it to be done.
+---
+ src/adapter.c | 30 ++++++++++++++++++++++++++++--
+ 1 file changed, 28 insertions(+), 2 deletions(-)
+
+diff --git a/src/adapter.c b/src/adapter.c
+index af340fd6e..20c20f9e9 100644
+--- a/src/adapter.c
++++ b/src/adapter.c
+@@ -196,6 +196,7 @@ struct btd_adapter {
+ 	char *name;			/* controller device name */
+ 	char *short_name;		/* controller short name */
+ 	uint32_t supported_settings;	/* controller supported settings */
++	uint32_t pending_settings;	/* pending controller settings */
+ 	uint32_t current_settings;	/* current controller settings */
+ 
+ 	char *path;			/* adapter object path */
+@@ -509,8 +510,10 @@ static void settings_changed(struct btd_adapter *adapter, uint32_t settings)
+ 	changed_mask = adapter->current_settings ^ settings;
+ 
+ 	adapter->current_settings = settings;
++	adapter->pending_settings &= ~changed_mask;
+ 
+ 	DBG("Changed settings: 0x%08x", changed_mask);
++	DBG("Pending settings: 0x%08x", adapter->pending_settings);
+ 
+ 	if (changed_mask & MGMT_SETTING_POWERED) {
+ 	        g_dbus_emit_property_changed(dbus_conn, adapter->path,
+@@ -596,10 +599,31 @@ static bool set_mode(struct btd_adapter *adapter, uint16_t opcode,
+ 							uint8_t mode)
+ {
+ 	struct mgmt_mode cp;
++	uint32_t setting = 0;
+ 
+ 	memset(&cp, 0, sizeof(cp));
+ 	cp.val = mode;
+ 
++	switch (mode) {
++	case MGMT_OP_SET_POWERED:
++		setting = MGMT_SETTING_POWERED;
++		break;
++	case MGMT_OP_SET_CONNECTABLE:
++		setting = MGMT_SETTING_CONNECTABLE;
++		break;
++	case MGMT_OP_SET_FAST_CONNECTABLE:
++		setting = MGMT_SETTING_FAST_CONNECTABLE;
++		break;
++	case MGMT_OP_SET_DISCOVERABLE:
++		setting = MGMT_SETTING_DISCOVERABLE;
++		break;
++	case MGMT_OP_SET_BONDABLE:
++		setting = MGMT_SETTING_DISCOVERABLE;
++		break;
++	}
++
++	adapter->pending_settings |= setting;
++
+ 	DBG("sending set mode command for index %u", adapter->dev_id);
+ 
+ 	if (mgmt_send(adapter->mgmt, opcode,
+@@ -2739,13 +2763,15 @@ static void property_set_mode(struct btd_adapter *adapter, uint32_t setting,
+ 	else
+ 		current_enable = FALSE;
+ 
+-	if (enable == current_enable) {
++	if (enable == current_enable || adapter->pending_settings & setting) {
+ 		g_dbus_pending_property_success(id);
+ 		return;
+ 	}
+ 
+ 	mode = (enable == TRUE) ? 0x01 : 0x00;
+ 
++	adapter->pending_settings |= setting;
++
+ 	switch (setting) {
+ 	case MGMT_SETTING_POWERED:
+ 		opcode = MGMT_OP_SET_POWERED;
+@@ -2798,7 +2824,7 @@ static void property_set_mode(struct btd_adapter *adapter, uint32_t setting,
+ 	data->id = id;
+ 
+ 	if (mgmt_send(adapter->mgmt, opcode, adapter->dev_id, len, param,
+-				property_set_mode_complete, data, g_free) > 0)
++			property_set_mode_complete, data, g_free) > 0)
+ 		return;
+ 
+ 	g_free(data);
+-- 
+2.17.1
+Subject:    [PATCH BlueZ 4/4] adapter: Check pending when setting DiscoverableTimeout
+From:       Luiz Augusto von Dentz <luiz.dentz () gmail ! com>
+Date:       2018-07-25 10:20:35
+Message-ID: 20180725102035.19439-4-luiz.dentz () gmail ! com
+[Download RAW message or body]
+
+From: Luiz Augusto von Dentz <luiz.von.dentz@intel.com>
+
+This makes DiscoverableTimeout check if discoverable is already pending
+and don't attempt to set it once again which may cause discoverable to
+be re-enabled when in fact the application just want to set the timeout
+alone.
+---
+ src/adapter.c | 14 +++++++++++++-
+ 1 file changed, 13 insertions(+), 1 deletion(-)
+
+diff --git a/src/adapter.c b/src/adapter.c
+index 20c20f9e9..f92c897c7 100644
+--- a/src/adapter.c
++++ b/src/adapter.c
+@@ -2901,6 +2901,7 @@ static void property_set_discoverable_timeout(
+ 				GDBusPendingPropertySet id, void *user_data)
+ {
+ 	struct btd_adapter *adapter = user_data;
++	bool enabled;
+ 	dbus_uint32_t value;
+ 
+ 	dbus_message_iter_get_basic(iter, &value);
+@@ -2914,8 +2915,19 @@ static void property_set_discoverable_timeout(
+ 	g_dbus_emit_property_changed(dbus_conn, adapter->path,
+ 				ADAPTER_INTERFACE, "DiscoverableTimeout");
+ 
++	if (adapter->pending_settings & MGMT_SETTING_DISCOVERABLE) {
++		if (adapter->current_settings & MGMT_SETTING_DISCOVERABLE)
++			enabled = false;
++		else
++			enabled = true;
++	} else {
++		if (adapter->current_settings & MGMT_SETTING_DISCOVERABLE)
++			enabled = true;
++		else
++			enabled = false;
++	}
+ 
+-	if (adapter->current_settings & MGMT_SETTING_DISCOVERABLE)
++	if (enabled)
+ 		set_discoverable(adapter, 0x01, adapter->discoverable_timeout);
+ }
+ 
+-- 
+2.17.1
+Subject:    [PATCH BlueZ 1/5] doc/adapter-api: Add Discoverable option to SetDiscoveryFilter
+From:       Luiz Augusto von Dentz <luiz.dentz () gmail ! com>
+Date:       2018-07-26 14:17:19
+Message-ID: 20180726141723.20199-1-luiz.dentz () gmail ! com
+[Download RAW message or body]
+
+From: Luiz Augusto von Dentz <luiz.von.dentz@intel.com>
+
+This enables the client to set its discoverable setting while
+discovering which is very typical situation as usually the setings
+application would allow incoming pairing request while scanning, so
+this would reduce the number of calls setting Discoverable and
+DiscoverableTimeout and restoring after done with discovery.
+---
+ doc/adapter-api.txt | 6 ++++++
+ 1 file changed, 6 insertions(+)
+
+diff --git a/doc/adapter-api.txt b/doc/adapter-api.txt
+index d14d0ca50..4791af2c7 100644
+--- a/doc/adapter-api.txt
++++ b/doc/adapter-api.txt
+@@ -113,6 +113,12 @@ Methods		void StartDiscovery()
+ 				generated for either ManufacturerData and
+ 				ServiceData everytime they are discovered.
+ 
++			bool Discoverable (Default: false)
++
++				Make adapter discoverable while discovering,
++				if the adapter is already discoverable this
++				setting this filter won't do anything.
++
+ 			When discovery filter is set, Device objects will be
+ 			created as new devices with matching criteria are
+ 			discovered regardless of they are connectable or
+-- 
+2.17.1
+Subject:    [PATCH BlueZ 2/5] adapter: Discovery filter discoverable
+From:       Luiz Augusto von Dentz <luiz.dentz () gmail ! com>
+Date:       2018-07-26 14:17:20
+Message-ID: 20180726141723.20199-2-luiz.dentz () gmail ! com
+[Download RAW message or body]
+
+From: Luiz Augusto von Dentz <luiz.von.dentz@intel.com>
+
+This implements the discovery filter discoverable and tracks which
+clients had enabled it and restores the settings when the last client
+enabling it exits.
+---
+ src/adapter.c | 56 +++++++++++++++++++++++++++++++++++++++++++++++++--
+ 1 file changed, 54 insertions(+), 2 deletions(-)
+
+diff --git a/src/adapter.c b/src/adapter.c
+index f92c897c7..bd9edddc6 100644
+--- a/src/adapter.c
++++ b/src/adapter.c
+@@ -157,6 +157,7 @@ struct discovery_filter {
+ 	int16_t rssi;
+ 	GSList *uuids;
+ 	bool duplicate;
++	bool discoverable;
+ };
+ 
+ struct watch_client {
+@@ -214,6 +215,7 @@ struct btd_adapter {
+ 
+ 	bool discovering;		/* discovering property state */
+ 	bool filtered_discovery;	/* we are doing filtered discovery */
++	bool filtered_discoverable;	/* we are doing filtered discovery */
+ 	bool no_scan_restart_delay;	/* when this flag is set, restart scan
+ 					 * without delay */
+ 	uint8_t discovery_type;		/* current active discovery type */
+@@ -1842,6 +1844,16 @@ static void discovery_free(void *user_data)
+ 	g_free(client);
+ }
+ 
++static bool set_filtered_discoverable(struct btd_adapter *adapter, bool enable)
++{
++	if (adapter->filtered_discoverable == enable)
++		return true;
++
++	adapter->filtered_discoverable = enable;
++
++	return set_discoverable(adapter, enable, 0);
++}
++
+ static void discovery_remove(struct watch_client *client)
+ {
+ 	struct btd_adapter *adapter = client->adapter;
+@@ -1854,6 +1866,22 @@ static void discovery_remove(struct watch_client *client)
+ 	adapter->discovery_list = g_slist_remove(adapter->discovery_list,
+ 								client);
+ 
++	if (adapter->filtered_discoverable &&
++			client->discovery_filter->discoverable) {
++		GSList *l;
++
++		for (l = adapter->discovery_list; l; l = g_slist_next(l)) {
++			struct watch_client *client = l->data;
++
++			if (client->discovery_filter->discoverable)
++				break;
++		}
++
++		/* Disable filtered discoverable if there are no clients */
++		if (!l)
++			set_filtered_discoverable(adapter, false);
++	}
++
+ 	discovery_free(client);
+ 
+ 	/*
+@@ -2224,6 +2252,15 @@ static DBusMessage *start_discovery(DBusConnection *conn,
+ 					     adapter->set_filter_list, client);
+ 		adapter->discovery_list = g_slist_prepend(
+ 					      adapter->discovery_list, client);
++
++		/* Reset discoverable filter if already set */
++		if (adapter->current_settings & MGMT_OP_SET_DISCOVERABLE)
++			goto done;
++
++		/* Set discoverable if filter requires and it*/
++		if (client->discovery_filter->discoverable)
++			set_filtered_discoverable(adapter, true);
++
+ 		goto done;
+ 	}
+ 
+@@ -2348,6 +2385,17 @@ static bool parse_duplicate_data(DBusMessageIter *value,
+ 	return true;
+ }
+ 
++static bool parse_discoverable(DBusMessageIter *value,
++					struct discovery_filter *filter)
++{
++	if (dbus_message_iter_get_arg_type(value) != DBUS_TYPE_BOOLEAN)
++		return false;
++
++	dbus_message_iter_get_basic(value, &filter->discoverable);
++
++	return true;
++}
++
+ struct filter_parser {
+ 	const char *name;
+ 	bool (*func)(DBusMessageIter *iter, struct discovery_filter *filter);
+@@ -2357,6 +2405,7 @@ struct filter_parser {
+ 	{ "Pathloss", parse_pathloss },
+ 	{ "Transport", parse_transport },
+ 	{ "DuplicateData", parse_duplicate_data },
++	{ "Discoverable", parse_discoverable },
+ 	{ }
+ };
+ 
+@@ -2396,6 +2445,7 @@ static bool parse_discovery_filter_dict(struct btd_adapter *adapter,
+ 	(*filter)->rssi = DISTANCE_VAL_INVALID;
+ 	(*filter)->type = get_scan_type(adapter);
+ 	(*filter)->duplicate = false;
++	(*filter)->discoverable = false;
+ 
+ 	dbus_message_iter_init(msg, &iter);
+ 	if (dbus_message_iter_get_arg_type(&iter) != DBUS_TYPE_ARRAY ||
+@@ -2441,8 +2491,10 @@ static bool parse_discovery_filter_dict(struct btd_adapter *adapter,
+ 		goto invalid_args;
+ 
+ 	DBG("filtered discovery params: transport: %d rssi: %d pathloss: %d "
+-		" duplicate data: %s ", (*filter)->type, (*filter)->rssi,
+-		(*filter)->pathloss, (*filter)->duplicate ? "true" : "false");
++		" duplicate data: %s discoverable %s", (*filter)->type,
++		(*filter)->rssi, (*filter)->pathloss,
++		(*filter)->duplicate ? "true" : "false",
++		(*filter)->discoverable ? "true" : "false");
+ 
+ 	return true;
+ 
+-- 
+2.17.1
+Subject:    [PATCH BlueZ 3/5] client: Add scan.discoverable command
+From:       Luiz Augusto von Dentz <luiz.dentz () gmail ! com>
+Date:       2018-07-26 14:17:21
+Message-ID: 20180726141723.20199-3-luiz.dentz () gmail ! com
+[Download RAW message or body]
+
+From: Luiz Augusto von Dentz <luiz.von.dentz@intel.com>
+
+This adds discoverable command to scan menu which can be used to set
+if adapter should become discoverable while scanning:
+
+[bluetooth]# scan.discoverable on
+[bluetooth]# scan on
+SetDiscoveryFilter success
+[CHG] Controller XX:XX:XX:XX:XX:XX Discoverable: yes
+Discovery started
+[CHG] Controller XX:XX:XX:XX:XX:XX Discovering: yes
+[bluetooth]# scan off
+Discovery stopped
+[CHG] Controller XX:XX:XX:XX:XX:XX Discoverable: no
+---
+ client/main.c | 29 +++++++++++++++++++++++++++++
+ 1 file changed, 29 insertions(+)
+
+diff --git a/client/main.c b/client/main.c
+index 6f472d050..6e6f6d2fb 100644
+--- a/client/main.c
++++ b/client/main.c
+@@ -1166,6 +1166,7 @@ static struct set_discovery_filter_args {
+ 	char **uuids;
+ 	size_t uuids_len;
+ 	dbus_bool_t duplicate;
++	dbus_bool_t discoverable;
+ 	bool set;
+ } filter = {
+ 	.rssi = DISTANCE_VAL_INVALID,
+@@ -1205,6 +1206,11 @@ static void set_discovery_filter_setup(DBusMessageIter *iter, void *user_data)
+ 						DBUS_TYPE_BOOLEAN,
+ 						&args->duplicate);
+ 
++	if (args->discoverable)
++		g_dbus_dict_append_entry(&dict, "Discoverable",
++						DBUS_TYPE_BOOLEAN,
++						&args->discoverable);
++
+ 	dbus_message_iter_close_container(iter, &dict);
+ }
+ 
+@@ -1362,6 +1368,26 @@ static void cmd_scan_filter_duplicate_data(int argc, char *argv[])
+ 	filter.set = false;
+ }
+ 
++static void cmd_scan_filter_discoverable(int argc, char *argv[])
++{
++	if (argc < 2 || !strlen(argv[1])) {
++		bt_shell_printf("Discoverable: %s\n",
++				filter.discoverable ? "on" : "off");
++		return bt_shell_noninteractive_quit(EXIT_SUCCESS);
++	}
++
++	if (!strcmp(argv[1], "on"))
++		filter.discoverable = true;
++	else if (!strcmp(argv[1], "off"))
++		filter.discoverable = false;
++	else {
++		bt_shell_printf("Invalid option: %s\n", argv[1]);
++		return bt_shell_noninteractive_quit(EXIT_FAILURE);
++	}
++
++	filter.set = false;
++}
++
+ static void filter_clear_uuids(void)
+ {
+ 	g_strfreev(filter.uuids);
+@@ -2510,6 +2536,9 @@ static const struct bt_shell_menu scan_menu = {
+ 	{ "duplicate-data", "[on/off]", cmd_scan_filter_duplicate_data,
+ 				"Set/Get duplicate data filter",
+ 				NULL },
++	{ "discoverable", "[on/off]", cmd_scan_filter_discoverable,
++				"Set/Get discoverable filter",
++				NULL },
+ 	{ "clear", "[uuids/rssi/pathloss/transport/duplicate-data]",
+ 				cmd_scan_filter_clear,
+ 				"Clears discovery filter.",
+-- 
+2.17.1
+Subject:    [PATCH BlueZ 4/5] client: Add scan.clear discoverable
+From:       Luiz Augusto von Dentz <luiz.dentz () gmail ! com>
+Date:       2018-07-26 14:17:22
+Message-ID: 20180726141723.20199-4-luiz.dentz () gmail ! com
+[Download RAW message or body]
+
+From: Luiz Augusto von Dentz <luiz.von.dentz@intel.com>
+
+This implements scan.clear for discoverable filter.
+---
+ client/main.c | 9 ++++++++-
+ 1 file changed, 8 insertions(+), 1 deletion(-)
+
+diff --git a/client/main.c b/client/main.c
+index 6e6f6d2fb..1a66a3ab4 100644
+--- a/client/main.c
++++ b/client/main.c
+@@ -1416,6 +1416,11 @@ static void filter_clear_duplicate(void)
+ 	filter.duplicate = false;
+ }
+ 
++static void filter_clear_discoverable(void)
++{
++	filter.discoverable = false;
++}
++
+ struct clear_entry {
+ 	const char *name;
+ 	void (*clear) (void);
+@@ -1427,6 +1432,7 @@ static const struct clear_entry filter_clear[] = {
+ 	{ "pathloss", filter_clear_pathloss },
+ 	{ "transport", filter_clear_transport },
+ 	{ "duplicate-data", filter_clear_duplicate },
++	{ "discoverable", filter_clear_discoverable },
+ 	{}
+ };
+ 
+@@ -2539,7 +2545,8 @@ static const struct bt_shell_menu scan_menu = {
+ 	{ "discoverable", "[on/off]", cmd_scan_filter_discoverable,
+ 				"Set/Get discoverable filter",
+ 				NULL },
+-	{ "clear", "[uuids/rssi/pathloss/transport/duplicate-data]",
++	{ "clear",
++		"[uuids/rssi/pathloss/transport/duplicate-data/discoverable]",
+ 				cmd_scan_filter_clear,
+ 				"Clears discovery filter.",
+ 				filter_clear_generator },
+-- 
+2.17.1
+Subject:    [PATCH BlueZ 5/5] adapter: Fix not keeping discovery filters
+From:       Luiz Augusto von Dentz <luiz.dentz () gmail ! com>
+Date:       2018-07-26 14:17:23
+Message-ID: 20180726141723.20199-5-luiz.dentz () gmail ! com
+[Download RAW message or body]
+
+From: Luiz Augusto von Dentz <luiz.von.dentz@intel.com>
+
+If the discovery has been stopped and the client has set filters those
+should be put back into filter list since the client may still be
+interested in using them the next time it start a scanning.
+---
+ src/adapter.c | 25 ++++++++++++++++---------
+ 1 file changed, 16 insertions(+), 9 deletions(-)
+
+diff --git a/src/adapter.c b/src/adapter.c
+index bd9edddc6..822bd3472 100644
+--- a/src/adapter.c
++++ b/src/adapter.c
+@@ -1854,7 +1854,7 @@ static bool set_filtered_discoverable(struct btd_adapter *adapter, bool enable)
+ 	return set_discoverable(adapter, enable, 0);
+ }
+ 
+-static void discovery_remove(struct watch_client *client)
++static void discovery_remove(struct watch_client *client, bool exit)
+ {
+ 	struct btd_adapter *adapter = client->adapter;
+ 
+@@ -1882,7 +1882,11 @@ static void discovery_remove(struct watch_client *client)
+ 			set_filtered_discoverable(adapter, false);
+ 	}
+ 
+-	discovery_free(client);
++	if (!exit && client->discovery_filter)
++		adapter->set_filter_list = g_slist_prepend(
++					adapter->set_filter_list, client);
++	else
++		discovery_free(client);
+ 
+ 	/*
+ 	 * If there are other client discoveries in progress, then leave
+@@ -1911,8 +1915,11 @@ static void stop_discovery_complete(uint8_t status, uint16_t length,
+ 		goto done;
+ 	}
+ 
+-	if (client->msg)
++	if (client->msg) {
+ 		g_dbus_send_reply(dbus_conn, client->msg, DBUS_TYPE_INVALID);
++		dbus_message_unref(client->msg);
++		client->msg = NULL;
++	}
+ 
+ 	adapter->discovery_type = 0x00;
+ 	adapter->discovery_enable = 0x00;
+@@ -1925,7 +1932,7 @@ static void stop_discovery_complete(uint8_t status, uint16_t length,
+ 	trigger_passive_scanning(adapter);
+ 
+ done:
+-	discovery_remove(client);
++	discovery_remove(client, false);
+ }
+ 
+ static int compare_sender(gconstpointer a, gconstpointer b)
+@@ -2146,14 +2153,14 @@ static int update_discovery_filter(struct btd_adapter *adapter)
+ 	return -EINPROGRESS;
+ }
+ 
+-static int discovery_stop(struct watch_client *client)
++static int discovery_stop(struct watch_client *client, bool exit)
+ {
+ 	struct btd_adapter *adapter = client->adapter;
+ 	struct mgmt_cp_stop_discovery cp;
+ 
+ 	/* Check if there are more client discovering */
+ 	if (g_slist_next(adapter->discovery_list)) {
+-		discovery_remove(client);
++		discovery_remove(client, exit);
+ 		update_discovery_filter(adapter);
+ 		return 0;
+ 	}
+@@ -2163,7 +2170,7 @@ static int discovery_stop(struct watch_client *client)
+ 	 * and so it is enough to send out the signal and just return.
+ 	 */
+ 	if (adapter->discovery_enable == 0x00) {
+-		discovery_remove(client);
++		discovery_remove(client, exit);
+ 		adapter->discovering = false;
+ 		g_dbus_emit_property_changed(dbus_conn, adapter->path,
+ 					ADAPTER_INTERFACE, "Discovering");
+@@ -2188,7 +2195,7 @@ static void discovery_disconnect(DBusConnection *conn, void *user_data)
+ 
+ 	DBG("owner %s", client->owner);
+ 
+-	discovery_stop(client);
++	discovery_stop(client, true);
+ }
+ 
+ /*
+@@ -2586,7 +2593,7 @@ static DBusMessage *stop_discovery(DBusConnection *conn,
+ 	if (client->msg)
+ 		return btd_error_busy(msg);
+ 
+-	err = discovery_stop(client);
++	err = discovery_stop(client, false);
+ 	switch (err) {
+ 	case 0:
+ 		return dbus_message_new_method_return(msg);
+-- 
+2.17.1