Diff between 1c990f90e7b80def0f132f99b74f3ffadaae60fe and 66420a5391ec41dc5ce7e4ce789ec4b7e5827af4

Changed Files

File Additions Deletions Status
lib/mgmt.h +5 -0 modified
mgmt/main.c +35 -8 modified
plugins/hciops.c +2 -2 modified
plugins/mgmtops.c +17 -3 modified
src/event.c +5 -1 modified
src/event.h +2 -1 modified

Full Patch

diff --git a/lib/mgmt.h b/lib/mgmt.h
index f121b12..83f9f77 100644
--- a/lib/mgmt.h
+++ b/lib/mgmt.h
@@ -316,6 +316,11 @@ struct mgmt_ev_new_link_key {
 } __packed;
 
 #define MGMT_EV_DEVICE_CONNECTED	0x000A
+struct mgmt_ev_device_connected {
+	struct mgmt_addr_info addr;
+	uint16_t eir_len;
+	uint8_t eir[0];
+} __packed;
 
 #define MGMT_EV_DEVICE_DISCONNECTED	0x000B
 
diff --git a/mgmt/main.c b/mgmt/main.c
index 20d7bf8..69ec248 100644
--- a/mgmt/main.c
+++ b/mgmt/main.c
@@ -411,22 +411,49 @@ static const char *typestr(uint8_t type)
 	return "(unknown)";
 }
 
-static int mgmt_connected(int mgmt_sk, uint16_t index, bool connected,
-				struct mgmt_addr_info *ev, uint16_t len)
+static int mgmt_connected(int mgmt_sk, uint16_t index,
+					struct mgmt_ev_device_connected *ev,
+					uint16_t len)
 {
-	const char *ev_name = connected ? "connected" : "disconnected";
+	uint16_t eir_len;
+
+	if (len != sizeof(*ev)) {
+		fprintf(stderr,
+			"Invalid connected event length (%u bytes)\n", len);
+		return -EINVAL;
+	}
+
+	eir_len = bt_get_le16(&ev->eir_len);
+	if (len != sizeof(*ev) + eir_len) {
+		fprintf(stderr, "Invalid connected event length "
+			"(%u bytes, eir_len %u bytes)\n", len, eir_len);
+		return -EINVAL;
+	}
 
+	if (monitor) {
+		char addr[18];
+		ba2str(&ev->addr.bdaddr, addr);
+		printf("hci%u %s type %s connected eir_len %u\n", index, addr,
+					typestr(ev->addr.type), eir_len);
+	}
+
+	return 0;
+}
+
+static int mgmt_disconnected(int mgmt_sk, uint16_t index,
+				struct mgmt_addr_info *ev, uint16_t len)
+{
 	if (len != sizeof(*ev)) {
 		fprintf(stderr,
-			"Invalid %s event length (%u bytes)\n", ev_name, len);
+			"Invalid disconnected event length (%u bytes)\n", len);
 		return -EINVAL;
 	}
 
 	if (monitor) {
 		char addr[18];
 		ba2str(&ev->bdaddr, addr);
-		printf("hci%u %s type %s %s\n", index, addr,
-						typestr(ev->type), ev_name);
+		printf("hci%u %s type %s disconnected\n", index, addr,
+							typestr(ev->type));
 	}
 
 	return 0;
@@ -784,9 +811,9 @@ static int mgmt_handle_event(int mgmt_sk, uint16_t ev, uint16_t index,
 	case MGMT_EV_NEW_LINK_KEY:
 		return mgmt_new_link_key(mgmt_sk, index, data, len);
 	case MGMT_EV_DEVICE_CONNECTED:
-		return mgmt_connected(mgmt_sk, index, true, data, len);
+		return mgmt_connected(mgmt_sk, index, data, len);
 	case MGMT_EV_DEVICE_DISCONNECTED:
-		return mgmt_connected(mgmt_sk, index, false, data, len);
+		return mgmt_disconnected(mgmt_sk, index, data, len);
 	case MGMT_EV_CONNECT_FAILED:
 		return mgmt_conn_failed(mgmt_sk, index, data, len);
 	case MGMT_EV_AUTH_FAILED:
diff --git a/plugins/hciops.c b/plugins/hciops.c
index 77d2421..0ebf533 100644
--- a/plugins/hciops.c
+++ b/plugins/hciops.c
@@ -2153,7 +2153,7 @@ static inline void conn_complete(int index, void *ptr)
 	conn = get_connection(dev, &evt->bdaddr);
 	conn->handle = btohs(evt->handle);
 
-	btd_event_conn_complete(&dev->bdaddr, &evt->bdaddr);
+	btd_event_conn_complete(&dev->bdaddr, &evt->bdaddr, NULL, NULL);
 
 	if (conn->secmode3)
 		bonding_complete(dev, conn, 0);
@@ -2189,7 +2189,7 @@ static inline void le_conn_complete(int index, void *ptr)
 	conn = get_connection(dev, &evt->peer_bdaddr);
 	conn->handle = btohs(evt->handle);
 
-	btd_event_conn_complete(&dev->bdaddr, &evt->peer_bdaddr);
+	btd_event_conn_complete(&dev->bdaddr, &evt->peer_bdaddr, NULL, NULL);
 
 	/* check if the remote version needs be requested */
 	ba2str(&dev->bdaddr, local_addr);
diff --git a/plugins/mgmtops.c b/plugins/mgmtops.c
index 23dc552..470266b 100644
--- a/plugins/mgmtops.c
+++ b/plugins/mgmtops.c
@@ -48,6 +48,7 @@
 #include "device.h"
 #include "event.h"
 #include "oob.h"
+#include "eir.h"
 
 #define MGMT_BUF_SIZE 1024
 
@@ -397,8 +398,10 @@ static void mgmt_new_link_key(int sk, uint16_t index, void *buf, size_t len)
 
 static void mgmt_device_connected(int sk, uint16_t index, void *buf, size_t len)
 {
-	struct mgmt_addr_info *ev = buf;
+	struct mgmt_ev_device_connected *ev = buf;
+	struct eir_data eir_data;
 	struct controller_info *info;
+	uint16_t eir_len;
 	char addr[18];
 
 	if (len < sizeof(*ev)) {
@@ -406,7 +409,13 @@ static void mgmt_device_connected(int sk, uint16_t index, void *buf, size_t len)
 		return;
 	}
 
-	ba2str(&ev->bdaddr, addr);
+	eir_len = bt_get_le16(&ev->eir_len);
+	if (len < sizeof(*ev) + eir_len) {
+		error("Too small device_connected event");
+		return;
+	}
+
+	ba2str(&ev->addr.bdaddr, addr);
 
 	DBG("hci%u device %s connected", index, addr);
 
@@ -417,7 +426,12 @@ static void mgmt_device_connected(int sk, uint16_t index, void *buf, size_t len)
 
 	info = &controllers[index];
 
-	btd_event_conn_complete(&info->bdaddr, &ev->bdaddr);
+	memset(&eir_data, 0, sizeof(eir_data));
+	if (eir_len > 0)
+		eir_parse(&eir_data, ev->eir, eir_len);
+
+	btd_event_conn_complete(&info->bdaddr, &ev->addr.bdaddr,
+					eir_data.name, eir_data.dev_class);
 }
 
 static void mgmt_device_disconnected(int sk, uint16_t index, void *buf,
diff --git a/src/event.c b/src/event.c
index 6854990..d0e192b 100644
--- a/src/event.c
+++ b/src/event.c
@@ -370,7 +370,8 @@ int btd_event_link_key_notify(bdaddr_t *local, bdaddr_t *peer,
 	return ret;
 }
 
-void btd_event_conn_complete(bdaddr_t *local, bdaddr_t *peer)
+void btd_event_conn_complete(bdaddr_t *local, bdaddr_t *peer,
+						char *name, uint8_t *dev_class)
 {
 	struct btd_adapter *adapter;
 	struct btd_device *device;
@@ -381,6 +382,9 @@ void btd_event_conn_complete(bdaddr_t *local, bdaddr_t *peer)
 	update_lastused(local, peer);
 
 	adapter_add_connection(adapter, device);
+
+	if (name != NULL)
+		btd_event_remote_name(local, peer, name);
 }
 
 void btd_event_conn_failed(bdaddr_t *local, bdaddr_t *peer, uint8_t status)
diff --git a/src/event.h b/src/event.h
index 708eeb9..57b7fd9 100644
--- a/src/event.h
+++ b/src/event.h
@@ -29,7 +29,8 @@ void btd_event_device_found(bdaddr_t *local, bdaddr_t *peer, addr_type_t type,
 void btd_event_set_legacy_pairing(bdaddr_t *local, bdaddr_t *peer, gboolean legacy);
 void btd_event_remote_class(bdaddr_t *local, bdaddr_t *peer, uint32_t class);
 void btd_event_remote_name(bdaddr_t *local, bdaddr_t *peer, char *name);
-void btd_event_conn_complete(bdaddr_t *local, bdaddr_t *peer);
+void btd_event_conn_complete(bdaddr_t *local, bdaddr_t *peer,
+					char *name, uint8_t *dev_class);
 void btd_event_conn_failed(bdaddr_t *local, bdaddr_t *peer, uint8_t status);
 void btd_event_disconn_complete(bdaddr_t *local, bdaddr_t *peer);
 void btd_event_simple_pairing_complete(bdaddr_t *local, bdaddr_t *peer, uint8_t status);