diff options
-rw-r--r-- | include/net/bluetooth/hci_core.h | 3 | ||||
-rw-r--r-- | net/bluetooth/hci_core.c | 3 | ||||
-rw-r--r-- | net/bluetooth/hci_event.c | 21 | ||||
-rw-r--r-- | net/bluetooth/hci_sysfs.c | 24 |
4 files changed, 50 insertions, 1 deletions
diff --git a/include/net/bluetooth/hci_core.h b/include/net/bluetooth/hci_core.h index 263e42b68e8d..7451a9c92d9d 100644 --- a/include/net/bluetooth/hci_core.h +++ b/include/net/bluetooth/hci_core.h | |||
@@ -72,6 +72,9 @@ struct hci_dev { | |||
72 | __u8 type; | 72 | __u8 type; |
73 | bdaddr_t bdaddr; | 73 | bdaddr_t bdaddr; |
74 | __u8 features[8]; | 74 | __u8 features[8]; |
75 | __u8 hci_ver; | ||
76 | __u16 hci_rev; | ||
77 | __u16 manufacturer; | ||
75 | __u16 voice_setting; | 78 | __u16 voice_setting; |
76 | 79 | ||
77 | __u16 pkt_type; | 80 | __u16 pkt_type; |
diff --git a/net/bluetooth/hci_core.c b/net/bluetooth/hci_core.c index 5ed474277903..338ae977a31b 100644 --- a/net/bluetooth/hci_core.c +++ b/net/bluetooth/hci_core.c | |||
@@ -206,6 +206,9 @@ static void hci_init_req(struct hci_dev *hdev, unsigned long opt) | |||
206 | /* Read Local Supported Features */ | 206 | /* Read Local Supported Features */ |
207 | hci_send_cmd(hdev, OGF_INFO_PARAM, OCF_READ_LOCAL_FEATURES, 0, NULL); | 207 | hci_send_cmd(hdev, OGF_INFO_PARAM, OCF_READ_LOCAL_FEATURES, 0, NULL); |
208 | 208 | ||
209 | /* Read Local Version */ | ||
210 | hci_send_cmd(hdev, OGF_INFO_PARAM, OCF_READ_LOCAL_VERSION, 0, NULL); | ||
211 | |||
209 | /* Read Buffer Size (ACL mtu, max pkt, etc.) */ | 212 | /* Read Buffer Size (ACL mtu, max pkt, etc.) */ |
210 | hci_send_cmd(hdev, OGF_INFO_PARAM, OCF_READ_BUFFER_SIZE, 0, NULL); | 213 | hci_send_cmd(hdev, OGF_INFO_PARAM, OCF_READ_BUFFER_SIZE, 0, NULL); |
211 | 214 | ||
diff --git a/net/bluetooth/hci_event.c b/net/bluetooth/hci_event.c index c6cd243939e6..7518bdbf34cd 100644 --- a/net/bluetooth/hci_event.c +++ b/net/bluetooth/hci_event.c | |||
@@ -298,6 +298,7 @@ static void hci_cc_host_ctl(struct hci_dev *hdev, __u16 ocf, struct sk_buff *skb | |||
298 | /* Command Complete OGF INFO_PARAM */ | 298 | /* Command Complete OGF INFO_PARAM */ |
299 | static void hci_cc_info_param(struct hci_dev *hdev, __u16 ocf, struct sk_buff *skb) | 299 | static void hci_cc_info_param(struct hci_dev *hdev, __u16 ocf, struct sk_buff *skb) |
300 | { | 300 | { |
301 | struct hci_rp_read_loc_version *lv; | ||
301 | struct hci_rp_read_local_features *lf; | 302 | struct hci_rp_read_local_features *lf; |
302 | struct hci_rp_read_buffer_size *bs; | 303 | struct hci_rp_read_buffer_size *bs; |
303 | struct hci_rp_read_bd_addr *ba; | 304 | struct hci_rp_read_bd_addr *ba; |
@@ -305,6 +306,23 @@ static void hci_cc_info_param(struct hci_dev *hdev, __u16 ocf, struct sk_buff *s | |||
305 | BT_DBG("%s ocf 0x%x", hdev->name, ocf); | 306 | BT_DBG("%s ocf 0x%x", hdev->name, ocf); |
306 | 307 | ||
307 | switch (ocf) { | 308 | switch (ocf) { |
309 | case OCF_READ_LOCAL_VERSION: | ||
310 | lv = (struct hci_rp_read_loc_version *) skb->data; | ||
311 | |||
312 | if (lv->status) { | ||
313 | BT_DBG("%s READ_LOCAL_VERSION failed %d", hdev->name, lf->status); | ||
314 | break; | ||
315 | } | ||
316 | |||
317 | hdev->hci_ver = lv->hci_ver; | ||
318 | hdev->hci_rev = btohs(lv->hci_rev); | ||
319 | hdev->manufacturer = btohs(lv->manufacturer); | ||
320 | |||
321 | BT_DBG("%s: manufacturer %d hci_ver %d hci_rev %d", hdev->name, | ||
322 | hdev->manufacturer, hdev->hci_ver, hdev->hci_rev); | ||
323 | |||
324 | break; | ||
325 | |||
308 | case OCF_READ_LOCAL_FEATURES: | 326 | case OCF_READ_LOCAL_FEATURES: |
309 | lf = (struct hci_rp_read_local_features *) skb->data; | 327 | lf = (struct hci_rp_read_local_features *) skb->data; |
310 | 328 | ||
@@ -329,7 +347,8 @@ static void hci_cc_info_param(struct hci_dev *hdev, __u16 ocf, struct sk_buff *s | |||
329 | if (hdev->features[1] & LMP_HV3) | 347 | if (hdev->features[1] & LMP_HV3) |
330 | hdev->pkt_type |= (HCI_HV3); | 348 | hdev->pkt_type |= (HCI_HV3); |
331 | 349 | ||
332 | BT_DBG("%s: features 0x%x 0x%x 0x%x", hdev->name, lf->features[0], lf->features[1], lf->features[2]); | 350 | BT_DBG("%s: features 0x%x 0x%x 0x%x", hdev->name, |
351 | lf->features[0], lf->features[1], lf->features[2]); | ||
333 | 352 | ||
334 | break; | 353 | break; |
335 | 354 | ||
diff --git a/net/bluetooth/hci_sysfs.c b/net/bluetooth/hci_sysfs.c index 09c61615e961..a5c4804b77f4 100644 --- a/net/bluetooth/hci_sysfs.c +++ b/net/bluetooth/hci_sysfs.c | |||
@@ -49,6 +49,24 @@ static ssize_t show_address(struct device *dev, struct device_attribute *attr, c | |||
49 | return sprintf(buf, "%s\n", batostr(&bdaddr)); | 49 | return sprintf(buf, "%s\n", batostr(&bdaddr)); |
50 | } | 50 | } |
51 | 51 | ||
52 | static ssize_t show_manufacturer(struct device *dev, struct device_attribute *attr, char *buf) | ||
53 | { | ||
54 | struct hci_dev *hdev = dev_get_drvdata(dev); | ||
55 | return sprintf(buf, "%d\n", hdev->manufacturer); | ||
56 | } | ||
57 | |||
58 | static ssize_t show_hci_version(struct device *dev, struct device_attribute *attr, char *buf) | ||
59 | { | ||
60 | struct hci_dev *hdev = dev_get_drvdata(dev); | ||
61 | return sprintf(buf, "%d\n", hdev->hci_ver); | ||
62 | } | ||
63 | |||
64 | static ssize_t show_hci_revision(struct device *dev, struct device_attribute *attr, char *buf) | ||
65 | { | ||
66 | struct hci_dev *hdev = dev_get_drvdata(dev); | ||
67 | return sprintf(buf, "%d\n", hdev->hci_rev); | ||
68 | } | ||
69 | |||
52 | static ssize_t show_inquiry_cache(struct device *dev, struct device_attribute *attr, char *buf) | 70 | static ssize_t show_inquiry_cache(struct device *dev, struct device_attribute *attr, char *buf) |
53 | { | 71 | { |
54 | struct hci_dev *hdev = dev_get_drvdata(dev); | 72 | struct hci_dev *hdev = dev_get_drvdata(dev); |
@@ -153,6 +171,9 @@ static ssize_t store_sniff_min_interval(struct device *dev, struct device_attrib | |||
153 | 171 | ||
154 | static DEVICE_ATTR(type, S_IRUGO, show_type, NULL); | 172 | static DEVICE_ATTR(type, S_IRUGO, show_type, NULL); |
155 | static DEVICE_ATTR(address, S_IRUGO, show_address, NULL); | 173 | static DEVICE_ATTR(address, S_IRUGO, show_address, NULL); |
174 | static DEVICE_ATTR(manufacturer, S_IRUGO, show_manufacturer, NULL); | ||
175 | static DEVICE_ATTR(hci_version, S_IRUGO, show_hci_version, NULL); | ||
176 | static DEVICE_ATTR(hci_revision, S_IRUGO, show_hci_revision, NULL); | ||
156 | static DEVICE_ATTR(inquiry_cache, S_IRUGO, show_inquiry_cache, NULL); | 177 | static DEVICE_ATTR(inquiry_cache, S_IRUGO, show_inquiry_cache, NULL); |
157 | 178 | ||
158 | static DEVICE_ATTR(idle_timeout, S_IRUGO | S_IWUSR, | 179 | static DEVICE_ATTR(idle_timeout, S_IRUGO | S_IWUSR, |
@@ -165,6 +186,9 @@ static DEVICE_ATTR(sniff_min_interval, S_IRUGO | S_IWUSR, | |||
165 | static struct device_attribute *bt_attrs[] = { | 186 | static struct device_attribute *bt_attrs[] = { |
166 | &dev_attr_type, | 187 | &dev_attr_type, |
167 | &dev_attr_address, | 188 | &dev_attr_address, |
189 | &dev_attr_manufacturer, | ||
190 | &dev_attr_hci_version, | ||
191 | &dev_attr_hci_revision, | ||
168 | &dev_attr_inquiry_cache, | 192 | &dev_attr_inquiry_cache, |
169 | &dev_attr_idle_timeout, | 193 | &dev_attr_idle_timeout, |
170 | &dev_attr_sniff_max_interval, | 194 | &dev_attr_sniff_max_interval, |