Bluetooth: Fix mgmt_pin_code_reply command status opcode
[linux-2.6-block.git] / net / bluetooth / mgmt.c
CommitLineData
0381101f
JH
1/*
2 BlueZ - Bluetooth protocol stack for Linux
3 Copyright (C) 2010 Nokia Corporation
4
5 This program is free software; you can redistribute it and/or modify
6 it under the terms of the GNU General Public License version 2 as
7 published by the Free Software Foundation;
8
9 THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
10 OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
11 FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT OF THIRD PARTY RIGHTS.
12 IN NO EVENT SHALL THE COPYRIGHT HOLDER(S) AND AUTHOR(S) BE LIABLE FOR ANY
13 CLAIM, OR ANY SPECIAL INDIRECT OR CONSEQUENTIAL DAMAGES, OR ANY DAMAGES
14 WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
15 ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
16 OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
17
18 ALL LIABILITY, INCLUDING LIABILITY FOR INFRINGEMENT OF ANY PATENTS,
19 COPYRIGHTS, TRADEMARKS OR OTHER RIGHTS, RELATING TO USE OF THIS
20 SOFTWARE IS DISCLAIMED.
21*/
22
23/* Bluetooth HCI Management interface */
24
72359753 25#include <linux/uaccess.h>
0381101f
JH
26#include <asm/unaligned.h>
27
28#include <net/bluetooth/bluetooth.h>
29#include <net/bluetooth/hci_core.h>
30#include <net/bluetooth/mgmt.h>
31
02d98129
JH
32#define MGMT_VERSION 0
33#define MGMT_REVISION 1
34
eec8d2bc
JH
35struct pending_cmd {
36 struct list_head list;
37 __u16 opcode;
38 int index;
39 void *cmd;
40 struct sock *sk;
e9a416b5 41 void *user_data;
eec8d2bc
JH
42};
43
44LIST_HEAD(cmd_list);
45
f7b64e69
JH
46static int cmd_status(struct sock *sk, u16 cmd, u8 status)
47{
48 struct sk_buff *skb;
49 struct mgmt_hdr *hdr;
50 struct mgmt_ev_cmd_status *ev;
51
52 BT_DBG("sock %p", sk);
53
54 skb = alloc_skb(sizeof(*hdr) + sizeof(*ev), GFP_ATOMIC);
55 if (!skb)
56 return -ENOMEM;
57
58 hdr = (void *) skb_put(skb, sizeof(*hdr));
59
60 hdr->opcode = cpu_to_le16(MGMT_EV_CMD_STATUS);
61 hdr->len = cpu_to_le16(sizeof(*ev));
62
63 ev = (void *) skb_put(skb, sizeof(*ev));
64 ev->status = status;
65 put_unaligned_le16(cmd, &ev->opcode);
66
67 if (sock_queue_rcv_skb(sk, skb) < 0)
68 kfree_skb(skb);
69
70 return 0;
71}
72
a38528f1 73static int cmd_complete(struct sock *sk, u16 cmd, void *rp, size_t rp_len)
02d98129
JH
74{
75 struct sk_buff *skb;
76 struct mgmt_hdr *hdr;
77 struct mgmt_ev_cmd_complete *ev;
02d98129
JH
78
79 BT_DBG("sock %p", sk);
80
a38528f1 81 skb = alloc_skb(sizeof(*hdr) + sizeof(*ev) + rp_len, GFP_ATOMIC);
02d98129
JH
82 if (!skb)
83 return -ENOMEM;
84
85 hdr = (void *) skb_put(skb, sizeof(*hdr));
02d98129 86
a38528f1
JH
87 hdr->opcode = cpu_to_le16(MGMT_EV_CMD_COMPLETE);
88 hdr->len = cpu_to_le16(sizeof(*ev) + rp_len);
02d98129 89
a38528f1
JH
90 ev = (void *) skb_put(skb, sizeof(*ev) + rp_len);
91 put_unaligned_le16(cmd, &ev->opcode);
92 memcpy(ev->data, rp, rp_len);
02d98129
JH
93
94 if (sock_queue_rcv_skb(sk, skb) < 0)
95 kfree_skb(skb);
96
97 return 0;
98}
99
a38528f1
JH
100static int read_version(struct sock *sk)
101{
102 struct mgmt_rp_read_version rp;
103
104 BT_DBG("sock %p", sk);
105
106 rp.version = MGMT_VERSION;
107 put_unaligned_le16(MGMT_REVISION, &rp.revision);
108
109 return cmd_complete(sk, MGMT_OP_READ_VERSION, &rp, sizeof(rp));
110}
111
faba42eb
JH
112static int read_index_list(struct sock *sk)
113{
faba42eb
JH
114 struct mgmt_rp_read_index_list *rp;
115 struct list_head *p;
a38528f1 116 size_t rp_len;
faba42eb 117 u16 count;
a38528f1 118 int i, err;
faba42eb
JH
119
120 BT_DBG("sock %p", sk);
121
122 read_lock(&hci_dev_list_lock);
123
124 count = 0;
125 list_for_each(p, &hci_dev_list) {
126 count++;
127 }
128
a38528f1
JH
129 rp_len = sizeof(*rp) + (2 * count);
130 rp = kmalloc(rp_len, GFP_ATOMIC);
131 if (!rp) {
b2c60d42 132 read_unlock(&hci_dev_list_lock);
faba42eb 133 return -ENOMEM;
b2c60d42 134 }
faba42eb 135
faba42eb
JH
136 put_unaligned_le16(count, &rp->num_controllers);
137
138 i = 0;
139 list_for_each(p, &hci_dev_list) {
140 struct hci_dev *d = list_entry(p, struct hci_dev, list);
ab81cbf9
JH
141
142 hci_del_off_timer(d);
143
ebc99feb
JH
144 set_bit(HCI_MGMT, &d->flags);
145
ab81cbf9
JH
146 if (test_bit(HCI_SETUP, &d->flags))
147 continue;
148
faba42eb
JH
149 put_unaligned_le16(d->id, &rp->index[i++]);
150 BT_DBG("Added hci%u", d->id);
151 }
152
153 read_unlock(&hci_dev_list_lock);
154
a38528f1 155 err = cmd_complete(sk, MGMT_OP_READ_INDEX_LIST, rp, rp_len);
faba42eb 156
a38528f1
JH
157 kfree(rp);
158
159 return err;
faba42eb
JH
160}
161
f7b64e69 162static int read_controller_info(struct sock *sk, unsigned char *data, u16 len)
0381101f 163{
a38528f1
JH
164 struct mgmt_rp_read_info rp;
165 struct mgmt_cp_read_info *cp = (void *) data;
f7b64e69
JH
166 struct hci_dev *hdev;
167 u16 dev_id;
0381101f
JH
168
169 BT_DBG("sock %p", sk);
170
f7b64e69
JH
171 if (len != 2)
172 return cmd_status(sk, MGMT_OP_READ_INFO, EINVAL);
173
f7b64e69
JH
174 dev_id = get_unaligned_le16(&cp->index);
175
176 BT_DBG("request for hci%u", dev_id);
177
178 hdev = hci_dev_get(dev_id);
a38528f1 179 if (!hdev)
f7b64e69 180 return cmd_status(sk, MGMT_OP_READ_INFO, ENODEV);
f7b64e69 181
ab81cbf9
JH
182 hci_del_off_timer(hdev);
183
f7b64e69
JH
184 hci_dev_lock_bh(hdev);
185
ebc99feb
JH
186 set_bit(HCI_MGMT, &hdev->flags);
187
a38528f1
JH
188 put_unaligned_le16(hdev->id, &rp.index);
189 rp.type = hdev->dev_type;
f7b64e69 190
a38528f1
JH
191 rp.powered = test_bit(HCI_UP, &hdev->flags);
192 rp.connectable = test_bit(HCI_PSCAN, &hdev->flags);
193 rp.discoverable = test_bit(HCI_ISCAN, &hdev->flags);
194 rp.pairable = test_bit(HCI_PSCAN, &hdev->flags);
f7b64e69
JH
195
196 if (test_bit(HCI_AUTH, &hdev->flags))
a38528f1 197 rp.sec_mode = 3;
f7b64e69 198 else if (hdev->ssp_mode > 0)
a38528f1 199 rp.sec_mode = 4;
f7b64e69 200 else
a38528f1 201 rp.sec_mode = 2;
f7b64e69 202
a38528f1
JH
203 bacpy(&rp.bdaddr, &hdev->bdaddr);
204 memcpy(rp.features, hdev->features, 8);
205 memcpy(rp.dev_class, hdev->dev_class, 3);
206 put_unaligned_le16(hdev->manufacturer, &rp.manufacturer);
207 rp.hci_ver = hdev->hci_ver;
208 put_unaligned_le16(hdev->hci_rev, &rp.hci_rev);
f7b64e69
JH
209
210 hci_dev_unlock_bh(hdev);
211 hci_dev_put(hdev);
0381101f 212
a38528f1 213 return cmd_complete(sk, MGMT_OP_READ_INFO, &rp, sizeof(rp));
0381101f
JH
214}
215
eec8d2bc
JH
216static void mgmt_pending_free(struct pending_cmd *cmd)
217{
218 sock_put(cmd->sk);
219 kfree(cmd->cmd);
220 kfree(cmd);
221}
222
366a0336
JH
223static struct pending_cmd *mgmt_pending_add(struct sock *sk, u16 opcode,
224 u16 index, void *data, u16 len)
eec8d2bc
JH
225{
226 struct pending_cmd *cmd;
227
228 cmd = kmalloc(sizeof(*cmd), GFP_ATOMIC);
229 if (!cmd)
366a0336 230 return NULL;
eec8d2bc
JH
231
232 cmd->opcode = opcode;
233 cmd->index = index;
234
235 cmd->cmd = kmalloc(len, GFP_ATOMIC);
236 if (!cmd->cmd) {
237 kfree(cmd);
366a0336 238 return NULL;
eec8d2bc
JH
239 }
240
241 memcpy(cmd->cmd, data, len);
242
243 cmd->sk = sk;
244 sock_hold(sk);
245
246 list_add(&cmd->list, &cmd_list);
247
366a0336 248 return cmd;
eec8d2bc
JH
249}
250
251static void mgmt_pending_foreach(u16 opcode, int index,
252 void (*cb)(struct pending_cmd *cmd, void *data),
253 void *data)
254{
255 struct list_head *p, *n;
256
257 list_for_each_safe(p, n, &cmd_list) {
258 struct pending_cmd *cmd;
259
260 cmd = list_entry(p, struct pending_cmd, list);
261
262 if (cmd->opcode != opcode)
263 continue;
264
265 if (index >= 0 && cmd->index != index)
266 continue;
267
268 cb(cmd, data);
269 }
270}
271
272static struct pending_cmd *mgmt_pending_find(u16 opcode, int index)
273{
274 struct list_head *p;
275
276 list_for_each(p, &cmd_list) {
277 struct pending_cmd *cmd;
278
279 cmd = list_entry(p, struct pending_cmd, list);
280
281 if (cmd->opcode != opcode)
282 continue;
283
284 if (index >= 0 && cmd->index != index)
285 continue;
286
287 return cmd;
288 }
289
290 return NULL;
291}
292
73f22f62
JH
293static void mgmt_pending_remove(u16 opcode, int index)
294{
295 struct pending_cmd *cmd;
296
297 cmd = mgmt_pending_find(opcode, index);
298 if (cmd == NULL)
299 return;
300
301 list_del(&cmd->list);
302 mgmt_pending_free(cmd);
303}
304
eec8d2bc
JH
305static int set_powered(struct sock *sk, unsigned char *data, u16 len)
306{
72a734ec 307 struct mgmt_mode *cp;
eec8d2bc 308 struct hci_dev *hdev;
366a0336 309 struct pending_cmd *cmd;
eec8d2bc 310 u16 dev_id;
366a0336 311 int err, up;
eec8d2bc
JH
312
313 cp = (void *) data;
314 dev_id = get_unaligned_le16(&cp->index);
315
316 BT_DBG("request for hci%u", dev_id);
317
318 hdev = hci_dev_get(dev_id);
319 if (!hdev)
320 return cmd_status(sk, MGMT_OP_SET_POWERED, ENODEV);
321
322 hci_dev_lock_bh(hdev);
323
324 up = test_bit(HCI_UP, &hdev->flags);
72a734ec 325 if ((cp->val && up) || (!cp->val && !up)) {
366a0336 326 err = cmd_status(sk, MGMT_OP_SET_POWERED, EALREADY);
eec8d2bc
JH
327 goto failed;
328 }
329
330 if (mgmt_pending_find(MGMT_OP_SET_POWERED, dev_id)) {
366a0336 331 err = cmd_status(sk, MGMT_OP_SET_POWERED, EBUSY);
eec8d2bc
JH
332 goto failed;
333 }
334
366a0336
JH
335 cmd = mgmt_pending_add(sk, MGMT_OP_SET_POWERED, dev_id, data, len);
336 if (!cmd) {
337 err = -ENOMEM;
eec8d2bc 338 goto failed;
366a0336 339 }
eec8d2bc 340
72a734ec 341 if (cp->val)
eec8d2bc
JH
342 queue_work(hdev->workqueue, &hdev->power_on);
343 else
344 queue_work(hdev->workqueue, &hdev->power_off);
345
366a0336 346 err = 0;
eec8d2bc
JH
347
348failed:
349 hci_dev_unlock_bh(hdev);
350 hci_dev_put(hdev);
366a0336 351 return err;
eec8d2bc
JH
352}
353
73f22f62
JH
354static int set_discoverable(struct sock *sk, unsigned char *data, u16 len)
355{
72a734ec 356 struct mgmt_mode *cp;
73f22f62 357 struct hci_dev *hdev;
366a0336 358 struct pending_cmd *cmd;
73f22f62
JH
359 u16 dev_id;
360 u8 scan;
361 int err;
362
363 cp = (void *) data;
364 dev_id = get_unaligned_le16(&cp->index);
365
366 BT_DBG("request for hci%u", dev_id);
367
368 hdev = hci_dev_get(dev_id);
369 if (!hdev)
370 return cmd_status(sk, MGMT_OP_SET_DISCOVERABLE, ENODEV);
371
372 hci_dev_lock_bh(hdev);
373
374 if (!test_bit(HCI_UP, &hdev->flags)) {
375 err = cmd_status(sk, MGMT_OP_SET_DISCOVERABLE, ENETDOWN);
376 goto failed;
377 }
378
379 if (mgmt_pending_find(MGMT_OP_SET_DISCOVERABLE, dev_id) ||
9fbcbb45 380 mgmt_pending_find(MGMT_OP_SET_CONNECTABLE, dev_id)) {
73f22f62
JH
381 err = cmd_status(sk, MGMT_OP_SET_DISCOVERABLE, EBUSY);
382 goto failed;
383 }
384
72a734ec 385 if (cp->val == test_bit(HCI_ISCAN, &hdev->flags) &&
73f22f62
JH
386 test_bit(HCI_PSCAN, &hdev->flags)) {
387 err = cmd_status(sk, MGMT_OP_SET_DISCOVERABLE, EALREADY);
388 goto failed;
389 }
390
366a0336
JH
391 cmd = mgmt_pending_add(sk, MGMT_OP_SET_DISCOVERABLE, dev_id, data, len);
392 if (!cmd) {
393 err = -ENOMEM;
73f22f62 394 goto failed;
366a0336 395 }
73f22f62
JH
396
397 scan = SCAN_PAGE;
398
72a734ec 399 if (cp->val)
73f22f62
JH
400 scan |= SCAN_INQUIRY;
401
402 err = hci_send_cmd(hdev, HCI_OP_WRITE_SCAN_ENABLE, 1, &scan);
403 if (err < 0)
404 mgmt_pending_remove(MGMT_OP_SET_DISCOVERABLE, dev_id);
405
406failed:
407 hci_dev_unlock_bh(hdev);
408 hci_dev_put(hdev);
409
410 return err;
411}
412
9fbcbb45
JH
413static int set_connectable(struct sock *sk, unsigned char *data, u16 len)
414{
72a734ec 415 struct mgmt_mode *cp;
9fbcbb45 416 struct hci_dev *hdev;
366a0336 417 struct pending_cmd *cmd;
9fbcbb45
JH
418 u16 dev_id;
419 u8 scan;
420 int err;
421
422 cp = (void *) data;
423 dev_id = get_unaligned_le16(&cp->index);
424
425 BT_DBG("request for hci%u", dev_id);
426
427 hdev = hci_dev_get(dev_id);
428 if (!hdev)
429 return cmd_status(sk, MGMT_OP_SET_CONNECTABLE, ENODEV);
430
431 hci_dev_lock_bh(hdev);
432
433 if (!test_bit(HCI_UP, &hdev->flags)) {
434 err = cmd_status(sk, MGMT_OP_SET_CONNECTABLE, ENETDOWN);
435 goto failed;
436 }
437
438 if (mgmt_pending_find(MGMT_OP_SET_DISCOVERABLE, dev_id) ||
439 mgmt_pending_find(MGMT_OP_SET_CONNECTABLE, dev_id)) {
440 err = cmd_status(sk, MGMT_OP_SET_CONNECTABLE, EBUSY);
441 goto failed;
442 }
443
72a734ec 444 if (cp->val == test_bit(HCI_PSCAN, &hdev->flags)) {
9fbcbb45
JH
445 err = cmd_status(sk, MGMT_OP_SET_CONNECTABLE, EALREADY);
446 goto failed;
447 }
448
366a0336
JH
449 cmd = mgmt_pending_add(sk, MGMT_OP_SET_CONNECTABLE, dev_id, data, len);
450 if (!cmd) {
451 err = -ENOMEM;
9fbcbb45 452 goto failed;
366a0336 453 }
9fbcbb45 454
72a734ec 455 if (cp->val)
9fbcbb45
JH
456 scan = SCAN_PAGE;
457 else
458 scan = 0;
459
460 err = hci_send_cmd(hdev, HCI_OP_WRITE_SCAN_ENABLE, 1, &scan);
461 if (err < 0)
462 mgmt_pending_remove(MGMT_OP_SET_CONNECTABLE, dev_id);
463
464failed:
465 hci_dev_unlock_bh(hdev);
466 hci_dev_put(hdev);
467
468 return err;
469}
470
c542a06c
JH
471static int mgmt_event(u16 event, void *data, u16 data_len, struct sock *skip_sk)
472{
473 struct sk_buff *skb;
474 struct mgmt_hdr *hdr;
475
476 skb = alloc_skb(sizeof(*hdr) + data_len, GFP_ATOMIC);
477 if (!skb)
478 return -ENOMEM;
479
480 bt_cb(skb)->channel = HCI_CHANNEL_CONTROL;
481
482 hdr = (void *) skb_put(skb, sizeof(*hdr));
483 hdr->opcode = cpu_to_le16(event);
484 hdr->len = cpu_to_le16(data_len);
485
486 memcpy(skb_put(skb, data_len), data, data_len);
487
488 hci_send_to_sock(NULL, skb, skip_sk);
489 kfree_skb(skb);
490
491 return 0;
492}
493
053f0211
JH
494static int send_mode_rsp(struct sock *sk, u16 opcode, u16 index, u8 val)
495{
a38528f1 496 struct mgmt_mode rp;
053f0211 497
a38528f1
JH
498 put_unaligned_le16(index, &rp.index);
499 rp.val = val;
053f0211 500
a38528f1 501 return cmd_complete(sk, opcode, &rp, sizeof(rp));
053f0211
JH
502}
503
c542a06c
JH
504static int set_pairable(struct sock *sk, unsigned char *data, u16 len)
505{
506 struct mgmt_mode *cp, ev;
507 struct hci_dev *hdev;
508 u16 dev_id;
509 int err;
510
511 cp = (void *) data;
512 dev_id = get_unaligned_le16(&cp->index);
513
514 BT_DBG("request for hci%u", dev_id);
515
516 hdev = hci_dev_get(dev_id);
517 if (!hdev)
518 return cmd_status(sk, MGMT_OP_SET_PAIRABLE, ENODEV);
519
520 hci_dev_lock_bh(hdev);
521
522 if (cp->val)
523 set_bit(HCI_PAIRABLE, &hdev->flags);
524 else
525 clear_bit(HCI_PAIRABLE, &hdev->flags);
526
527 err = send_mode_rsp(sk, MGMT_OP_SET_PAIRABLE, dev_id, cp->val);
528 if (err < 0)
529 goto failed;
530
531 put_unaligned_le16(dev_id, &ev.index);
532 ev.val = cp->val;
533
534 err = mgmt_event(MGMT_EV_PAIRABLE, &ev, sizeof(ev), sk);
535
536failed:
537 hci_dev_unlock_bh(hdev);
538 hci_dev_put(hdev);
539
540 return err;
541}
542
1aff6f09
JH
543static u8 get_service_classes(struct hci_dev *hdev)
544{
545 struct list_head *p;
546 u8 val = 0;
547
548 list_for_each(p, &hdev->uuids) {
549 struct bt_uuid *uuid = list_entry(p, struct bt_uuid, list);
550
551 val |= uuid->svc_hint;
552 }
553
554 return val;
555}
556
557static int update_class(struct hci_dev *hdev)
558{
559 u8 cod[3];
560
561 BT_DBG("%s", hdev->name);
562
563 if (test_bit(HCI_SERVICE_CACHE, &hdev->flags))
564 return 0;
565
566 cod[0] = hdev->minor_class;
567 cod[1] = hdev->major_class;
568 cod[2] = get_service_classes(hdev);
569
570 if (memcmp(cod, hdev->dev_class, 3) == 0)
571 return 0;
572
573 return hci_send_cmd(hdev, HCI_OP_WRITE_CLASS_OF_DEV, sizeof(cod), cod);
574}
575
2aeb9a1a
JH
576static int add_uuid(struct sock *sk, unsigned char *data, u16 len)
577{
578 struct mgmt_cp_add_uuid *cp;
579 struct hci_dev *hdev;
580 struct bt_uuid *uuid;
581 u16 dev_id;
582 int err;
583
584 cp = (void *) data;
585 dev_id = get_unaligned_le16(&cp->index);
586
587 BT_DBG("request for hci%u", dev_id);
588
589 hdev = hci_dev_get(dev_id);
590 if (!hdev)
591 return cmd_status(sk, MGMT_OP_ADD_UUID, ENODEV);
592
593 hci_dev_lock_bh(hdev);
594
595 uuid = kmalloc(sizeof(*uuid), GFP_ATOMIC);
596 if (!uuid) {
597 err = -ENOMEM;
598 goto failed;
599 }
600
601 memcpy(uuid->uuid, cp->uuid, 16);
1aff6f09 602 uuid->svc_hint = cp->svc_hint;
2aeb9a1a
JH
603
604 list_add(&uuid->list, &hdev->uuids);
605
1aff6f09
JH
606 err = update_class(hdev);
607 if (err < 0)
608 goto failed;
609
a38528f1 610 err = cmd_complete(sk, MGMT_OP_ADD_UUID, &dev_id, sizeof(dev_id));
2aeb9a1a
JH
611
612failed:
613 hci_dev_unlock_bh(hdev);
614 hci_dev_put(hdev);
615
616 return err;
617}
618
619static int remove_uuid(struct sock *sk, unsigned char *data, u16 len)
620{
621 struct list_head *p, *n;
622 struct mgmt_cp_add_uuid *cp;
623 struct hci_dev *hdev;
624 u8 bt_uuid_any[] = { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 };
625 u16 dev_id;
626 int err, found;
627
628 cp = (void *) data;
629 dev_id = get_unaligned_le16(&cp->index);
630
631 BT_DBG("request for hci%u", dev_id);
632
633 hdev = hci_dev_get(dev_id);
634 if (!hdev)
635 return cmd_status(sk, MGMT_OP_REMOVE_UUID, ENODEV);
636
637 hci_dev_lock_bh(hdev);
638
639 if (memcmp(cp->uuid, bt_uuid_any, 16) == 0) {
640 err = hci_uuids_clear(hdev);
641 goto unlock;
642 }
643
644 found = 0;
645
646 list_for_each_safe(p, n, &hdev->uuids) {
647 struct bt_uuid *match = list_entry(p, struct bt_uuid, list);
648
649 if (memcmp(match->uuid, cp->uuid, 16) != 0)
650 continue;
651
652 list_del(&match->list);
653 found++;
654 }
655
656 if (found == 0) {
657 err = cmd_status(sk, MGMT_OP_REMOVE_UUID, ENOENT);
658 goto unlock;
659 }
660
1aff6f09
JH
661 err = update_class(hdev);
662 if (err < 0)
663 goto unlock;
664
a38528f1 665 err = cmd_complete(sk, MGMT_OP_REMOVE_UUID, &dev_id, sizeof(dev_id));
2aeb9a1a
JH
666
667unlock:
668 hci_dev_unlock_bh(hdev);
669 hci_dev_put(hdev);
670
671 return err;
672}
673
1aff6f09
JH
674static int set_dev_class(struct sock *sk, unsigned char *data, u16 len)
675{
676 struct hci_dev *hdev;
677 struct mgmt_cp_set_dev_class *cp;
678 u16 dev_id;
679 int err;
680
681 cp = (void *) data;
682 dev_id = get_unaligned_le16(&cp->index);
683
684 BT_DBG("request for hci%u", dev_id);
685
686 hdev = hci_dev_get(dev_id);
687 if (!hdev)
688 return cmd_status(sk, MGMT_OP_SET_DEV_CLASS, ENODEV);
689
690 hci_dev_lock_bh(hdev);
691
692 hdev->major_class = cp->major;
693 hdev->minor_class = cp->minor;
694
695 err = update_class(hdev);
696
697 if (err == 0)
a38528f1
JH
698 err = cmd_complete(sk, MGMT_OP_SET_DEV_CLASS, &dev_id,
699 sizeof(dev_id));
1aff6f09
JH
700
701 hci_dev_unlock_bh(hdev);
702 hci_dev_put(hdev);
703
704 return err;
705}
706
707static int set_service_cache(struct sock *sk, unsigned char *data, u16 len)
708{
709 struct hci_dev *hdev;
710 struct mgmt_cp_set_service_cache *cp;
711 u16 dev_id;
712 int err;
713
714 cp = (void *) data;
715 dev_id = get_unaligned_le16(&cp->index);
716
717 hdev = hci_dev_get(dev_id);
718 if (!hdev)
719 return cmd_status(sk, MGMT_OP_SET_SERVICE_CACHE, ENODEV);
720
721 hci_dev_lock_bh(hdev);
722
723 BT_DBG("hci%u enable %d", dev_id, cp->enable);
724
725 if (cp->enable) {
726 set_bit(HCI_SERVICE_CACHE, &hdev->flags);
727 err = 0;
728 } else {
729 clear_bit(HCI_SERVICE_CACHE, &hdev->flags);
730 err = update_class(hdev);
731 }
732
733 if (err == 0)
a38528f1
JH
734 err = cmd_complete(sk, MGMT_OP_SET_SERVICE_CACHE, &dev_id,
735 sizeof(dev_id));
1aff6f09
JH
736
737 hci_dev_unlock_bh(hdev);
738 hci_dev_put(hdev);
739
740 return err;
741}
742
55ed8ca1
JH
743static int load_keys(struct sock *sk, unsigned char *data, u16 len)
744{
745 struct hci_dev *hdev;
746 struct mgmt_cp_load_keys *cp;
747 u16 dev_id, key_count, expected_len;
748 int i;
749
750 cp = (void *) data;
751 dev_id = get_unaligned_le16(&cp->index);
752 key_count = get_unaligned_le16(&cp->key_count);
753
754 expected_len = sizeof(*cp) + key_count * sizeof(struct mgmt_key_info);
755 if (expected_len != len) {
756 BT_ERR("load_keys: expected %u bytes, got %u bytes",
757 len, expected_len);
758 return -EINVAL;
759 }
760
761 hdev = hci_dev_get(dev_id);
762 if (!hdev)
763 return cmd_status(sk, MGMT_OP_LOAD_KEYS, ENODEV);
764
765 BT_DBG("hci%u debug_keys %u key_count %u", dev_id, cp->debug_keys,
766 key_count);
767
768 hci_dev_lock_bh(hdev);
769
770 hci_link_keys_clear(hdev);
771
772 set_bit(HCI_LINK_KEYS, &hdev->flags);
773
774 if (cp->debug_keys)
775 set_bit(HCI_DEBUG_KEYS, &hdev->flags);
776 else
777 clear_bit(HCI_DEBUG_KEYS, &hdev->flags);
778
779 for (i = 0; i < key_count; i++) {
780 struct mgmt_key_info *key = &cp->keys[i];
781
782 hci_add_link_key(hdev, 0, &key->bdaddr, key->val, key->type,
783 key->pin_len);
784 }
785
786 hci_dev_unlock_bh(hdev);
787 hci_dev_put(hdev);
788
789 return 0;
790}
791
792static int remove_key(struct sock *sk, unsigned char *data, u16 len)
793{
794 struct hci_dev *hdev;
795 struct mgmt_cp_remove_key *cp;
796 struct hci_conn *conn;
797 u16 dev_id;
798 int err;
799
800 cp = (void *) data;
801 dev_id = get_unaligned_le16(&cp->index);
802
803 hdev = hci_dev_get(dev_id);
804 if (!hdev)
805 return cmd_status(sk, MGMT_OP_REMOVE_KEY, ENODEV);
806
807 hci_dev_lock_bh(hdev);
808
809 err = hci_remove_link_key(hdev, &cp->bdaddr);
810 if (err < 0) {
811 err = cmd_status(sk, MGMT_OP_REMOVE_KEY, -err);
812 goto unlock;
813 }
814
815 err = 0;
816
817 if (!test_bit(HCI_UP, &hdev->flags) || !cp->disconnect)
818 goto unlock;
819
820 conn = hci_conn_hash_lookup_ba(hdev, ACL_LINK, &cp->bdaddr);
821 if (conn) {
822 struct hci_cp_disconnect dc;
823
824 put_unaligned_le16(conn->handle, &dc.handle);
825 dc.reason = 0x13; /* Remote User Terminated Connection */
826 err = hci_send_cmd(hdev, HCI_OP_DISCONNECT, 0, NULL);
827 }
828
829unlock:
830 hci_dev_unlock_bh(hdev);
831 hci_dev_put(hdev);
832
833 return err;
834}
835
8962ee74
JH
836static int disconnect(struct sock *sk, unsigned char *data, u16 len)
837{
838 struct hci_dev *hdev;
839 struct mgmt_cp_disconnect *cp;
840 struct hci_cp_disconnect dc;
366a0336 841 struct pending_cmd *cmd;
8962ee74
JH
842 struct hci_conn *conn;
843 u16 dev_id;
844 int err;
845
846 BT_DBG("");
847
848 cp = (void *) data;
849 dev_id = get_unaligned_le16(&cp->index);
850
851 hdev = hci_dev_get(dev_id);
852 if (!hdev)
853 return cmd_status(sk, MGMT_OP_DISCONNECT, ENODEV);
854
855 hci_dev_lock_bh(hdev);
856
857 if (!test_bit(HCI_UP, &hdev->flags)) {
858 err = cmd_status(sk, MGMT_OP_DISCONNECT, ENETDOWN);
859 goto failed;
860 }
861
862 if (mgmt_pending_find(MGMT_OP_DISCONNECT, dev_id)) {
863 err = cmd_status(sk, MGMT_OP_DISCONNECT, EBUSY);
864 goto failed;
865 }
866
867 conn = hci_conn_hash_lookup_ba(hdev, ACL_LINK, &cp->bdaddr);
868 if (!conn) {
869 err = cmd_status(sk, MGMT_OP_DISCONNECT, ENOTCONN);
870 goto failed;
871 }
872
366a0336
JH
873 cmd = mgmt_pending_add(sk, MGMT_OP_DISCONNECT, dev_id, data, len);
874 if (!cmd) {
875 err = -ENOMEM;
8962ee74 876 goto failed;
366a0336 877 }
8962ee74
JH
878
879 put_unaligned_le16(conn->handle, &dc.handle);
880 dc.reason = 0x13; /* Remote User Terminated Connection */
881
882 err = hci_send_cmd(hdev, HCI_OP_DISCONNECT, sizeof(dc), &dc);
883 if (err < 0)
884 mgmt_pending_remove(MGMT_OP_DISCONNECT, dev_id);
885
886failed:
887 hci_dev_unlock_bh(hdev);
888 hci_dev_put(hdev);
889
890 return err;
891}
892
2784eb41
JH
893static int get_connections(struct sock *sk, unsigned char *data, u16 len)
894{
2784eb41 895 struct mgmt_cp_get_connections *cp;
2784eb41
JH
896 struct mgmt_rp_get_connections *rp;
897 struct hci_dev *hdev;
898 struct list_head *p;
a38528f1 899 size_t rp_len;
2784eb41
JH
900 u16 dev_id, count;
901 int i, err;
902
903 BT_DBG("");
904
905 cp = (void *) data;
906 dev_id = get_unaligned_le16(&cp->index);
907
908 hdev = hci_dev_get(dev_id);
909 if (!hdev)
910 return cmd_status(sk, MGMT_OP_GET_CONNECTIONS, ENODEV);
911
912 hci_dev_lock_bh(hdev);
913
914 count = 0;
915 list_for_each(p, &hdev->conn_hash.list) {
916 count++;
917 }
918
a38528f1
JH
919 rp_len = sizeof(*rp) + (count * sizeof(bdaddr_t));
920 rp = kmalloc(rp_len, GFP_ATOMIC);
921 if (!rp) {
2784eb41
JH
922 err = -ENOMEM;
923 goto unlock;
924 }
925
2784eb41
JH
926 put_unaligned_le16(dev_id, &rp->index);
927 put_unaligned_le16(count, &rp->conn_count);
928
929 read_lock(&hci_dev_list_lock);
930
931 i = 0;
932 list_for_each(p, &hdev->conn_hash.list) {
933 struct hci_conn *c = list_entry(p, struct hci_conn, list);
934
935 bacpy(&rp->conn[i++], &c->dst);
936 }
937
938 read_unlock(&hci_dev_list_lock);
939
a38528f1 940 err = cmd_complete(sk, MGMT_OP_GET_CONNECTIONS, rp, rp_len);
2784eb41
JH
941
942unlock:
a38528f1 943 kfree(rp);
2784eb41
JH
944 hci_dev_unlock_bh(hdev);
945 hci_dev_put(hdev);
946 return err;
947}
948
980e1a53
JH
949static int pin_code_reply(struct sock *sk, unsigned char *data, u16 len)
950{
951 struct hci_dev *hdev;
952 struct mgmt_cp_pin_code_reply *cp;
953 struct hci_cp_pin_code_reply reply;
366a0336 954 struct pending_cmd *cmd;
980e1a53
JH
955 u16 dev_id;
956 int err;
957
958 BT_DBG("");
959
960 cp = (void *) data;
961 dev_id = get_unaligned_le16(&cp->index);
962
963 hdev = hci_dev_get(dev_id);
964 if (!hdev)
59a24b5d 965 return cmd_status(sk, MGMT_OP_PIN_CODE_REPLY, ENODEV);
980e1a53
JH
966
967 hci_dev_lock_bh(hdev);
968
969 if (!test_bit(HCI_UP, &hdev->flags)) {
970 err = cmd_status(sk, MGMT_OP_PIN_CODE_REPLY, ENETDOWN);
971 goto failed;
972 }
973
366a0336
JH
974 cmd = mgmt_pending_add(sk, MGMT_OP_PIN_CODE_REPLY, dev_id, data, len);
975 if (!cmd) {
976 err = -ENOMEM;
980e1a53 977 goto failed;
366a0336 978 }
980e1a53
JH
979
980 bacpy(&reply.bdaddr, &cp->bdaddr);
981 reply.pin_len = cp->pin_len;
982 memcpy(reply.pin_code, cp->pin_code, 16);
983
984 err = hci_send_cmd(hdev, HCI_OP_PIN_CODE_REPLY, sizeof(reply), &reply);
985 if (err < 0)
986 mgmt_pending_remove(MGMT_OP_PIN_CODE_REPLY, dev_id);
987
988failed:
989 hci_dev_unlock_bh(hdev);
990 hci_dev_put(hdev);
991
992 return err;
993}
994
995static int pin_code_neg_reply(struct sock *sk, unsigned char *data, u16 len)
996{
997 struct hci_dev *hdev;
998 struct mgmt_cp_pin_code_neg_reply *cp;
366a0336 999 struct pending_cmd *cmd;
980e1a53
JH
1000 u16 dev_id;
1001 int err;
1002
1003 BT_DBG("");
1004
1005 cp = (void *) data;
1006 dev_id = get_unaligned_le16(&cp->index);
1007
1008 hdev = hci_dev_get(dev_id);
1009 if (!hdev)
1010 return cmd_status(sk, MGMT_OP_PIN_CODE_NEG_REPLY, ENODEV);
1011
1012 hci_dev_lock_bh(hdev);
1013
1014 if (!test_bit(HCI_UP, &hdev->flags)) {
1015 err = cmd_status(sk, MGMT_OP_PIN_CODE_NEG_REPLY, ENETDOWN);
1016 goto failed;
1017 }
1018
366a0336 1019 cmd = mgmt_pending_add(sk, MGMT_OP_PIN_CODE_NEG_REPLY, dev_id,
980e1a53 1020 data, len);
366a0336
JH
1021 if (!cmd) {
1022 err = -ENOMEM;
980e1a53 1023 goto failed;
366a0336 1024 }
980e1a53
JH
1025
1026 err = hci_send_cmd(hdev, HCI_OP_PIN_CODE_NEG_REPLY, sizeof(bdaddr_t),
1027 &cp->bdaddr);
1028 if (err < 0)
1029 mgmt_pending_remove(MGMT_OP_PIN_CODE_NEG_REPLY, dev_id);
1030
1031failed:
1032 hci_dev_unlock_bh(hdev);
1033 hci_dev_put(hdev);
1034
1035 return err;
1036}
1037
17fa4b9d
JH
1038static int set_io_capability(struct sock *sk, unsigned char *data, u16 len)
1039{
1040 struct hci_dev *hdev;
1041 struct mgmt_cp_set_io_capability *cp;
1042 u16 dev_id;
1043
1044 BT_DBG("");
1045
1046 cp = (void *) data;
1047 dev_id = get_unaligned_le16(&cp->index);
1048
1049 hdev = hci_dev_get(dev_id);
1050 if (!hdev)
1051 return cmd_status(sk, MGMT_OP_SET_IO_CAPABILITY, ENODEV);
1052
1053 hci_dev_lock_bh(hdev);
1054
1055 hdev->io_capability = cp->io_capability;
1056
1057 BT_DBG("%s IO capability set to 0x%02x", hdev->name,
1058 hdev->io_capability);
1059
1060 hci_dev_unlock_bh(hdev);
1061 hci_dev_put(hdev);
1062
1063 return cmd_complete(sk, MGMT_OP_SET_IO_CAPABILITY,
1064 &dev_id, sizeof(dev_id));
1065}
1066
e9a416b5
JH
1067static inline struct pending_cmd *find_pairing(struct hci_conn *conn)
1068{
1069 struct hci_dev *hdev = conn->hdev;
1070 struct list_head *p;
1071
1072 list_for_each(p, &cmd_list) {
1073 struct pending_cmd *cmd;
1074
1075 cmd = list_entry(p, struct pending_cmd, list);
1076
1077 if (cmd->opcode != MGMT_OP_PAIR_DEVICE)
1078 continue;
1079
1080 if (cmd->index != hdev->id)
1081 continue;
1082
1083 if (cmd->user_data != conn)
1084 continue;
1085
1086 return cmd;
1087 }
1088
1089 return NULL;
1090}
1091
1092static void pairing_complete(struct pending_cmd *cmd, u8 status)
1093{
1094 struct mgmt_rp_pair_device rp;
1095 struct hci_conn *conn = cmd->user_data;
1096
1097 rp.index = cmd->index;
1098 bacpy(&rp.bdaddr, &conn->dst);
1099 rp.status = status;
1100
1101 cmd_complete(cmd->sk, MGMT_OP_PAIR_DEVICE, &rp, sizeof(rp));
1102
1103 /* So we don't get further callbacks for this connection */
1104 conn->connect_cfm_cb = NULL;
1105 conn->security_cfm_cb = NULL;
1106 conn->disconn_cfm_cb = NULL;
1107
1108 hci_conn_put(conn);
1109
1110 list_del(&cmd->list);
1111 mgmt_pending_free(cmd);
1112}
1113
1114static void pairing_complete_cb(struct hci_conn *conn, u8 status)
1115{
1116 struct pending_cmd *cmd;
1117
1118 BT_DBG("status %u", status);
1119
1120 cmd = find_pairing(conn);
1121 if (!cmd) {
1122 BT_DBG("Unable to find a pending command");
1123 return;
1124 }
1125
1126 pairing_complete(cmd, status);
1127}
1128
1129static int pair_device(struct sock *sk, unsigned char *data, u16 len)
1130{
1131 struct hci_dev *hdev;
1132 struct mgmt_cp_pair_device *cp;
1133 struct pending_cmd *cmd;
1134 u8 sec_level, auth_type;
1135 struct hci_conn *conn;
1136 u16 dev_id;
1137 int err;
1138
1139 BT_DBG("");
1140
1141 cp = (void *) data;
1142 dev_id = get_unaligned_le16(&cp->index);
1143
1144 hdev = hci_dev_get(dev_id);
1145 if (!hdev)
1146 return cmd_status(sk, MGMT_OP_PAIR_DEVICE, ENODEV);
1147
1148 hci_dev_lock_bh(hdev);
1149
1150 if (cp->io_cap == 0x03) {
1151 sec_level = BT_SECURITY_MEDIUM;
1152 auth_type = HCI_AT_DEDICATED_BONDING;
1153 } else {
1154 sec_level = BT_SECURITY_HIGH;
1155 auth_type = HCI_AT_DEDICATED_BONDING_MITM;
1156 }
1157
1158 conn = hci_connect(hdev, ACL_LINK, &cp->bdaddr, sec_level, auth_type);
1159 if (!conn) {
1160 err = -ENOMEM;
1161 goto unlock;
1162 }
1163
1164 if (conn->connect_cfm_cb) {
1165 hci_conn_put(conn);
1166 err = cmd_status(sk, MGMT_OP_PAIR_DEVICE, EBUSY);
1167 goto unlock;
1168 }
1169
1170 cmd = mgmt_pending_add(sk, MGMT_OP_PAIR_DEVICE, dev_id, data, len);
1171 if (!cmd) {
1172 err = -ENOMEM;
1173 hci_conn_put(conn);
1174 goto unlock;
1175 }
1176
1177 conn->connect_cfm_cb = pairing_complete_cb;
1178 conn->security_cfm_cb = pairing_complete_cb;
1179 conn->disconn_cfm_cb = pairing_complete_cb;
1180 conn->io_capability = cp->io_cap;
1181 cmd->user_data = conn;
1182
1183 if (conn->state == BT_CONNECTED &&
1184 hci_conn_security(conn, sec_level, auth_type))
1185 pairing_complete(cmd, 0);
1186
1187 err = 0;
1188
1189unlock:
1190 hci_dev_unlock_bh(hdev);
1191 hci_dev_put(hdev);
1192
1193 return err;
1194}
1195
a5c29683
JH
1196static int user_confirm_reply(struct sock *sk, unsigned char *data, u16 len,
1197 int success)
1198{
1199 struct mgmt_cp_user_confirm_reply *cp = (void *) data;
1200 u16 dev_id, mgmt_op, hci_op;
1201 struct pending_cmd *cmd;
1202 struct hci_dev *hdev;
1203 int err;
1204
1205 BT_DBG("");
1206
1207 dev_id = get_unaligned_le16(&cp->index);
1208
1209 if (success) {
1210 mgmt_op = MGMT_OP_USER_CONFIRM_REPLY;
1211 hci_op = HCI_OP_USER_CONFIRM_REPLY;
1212 } else {
1213 mgmt_op = MGMT_OP_USER_CONFIRM_NEG_REPLY;
1214 hci_op = HCI_OP_USER_CONFIRM_NEG_REPLY;
1215 }
1216
1217 hdev = hci_dev_get(dev_id);
1218 if (!hdev)
1219 return cmd_status(sk, mgmt_op, ENODEV);
1220
1221 if (!test_bit(HCI_UP, &hdev->flags)) {
1222 err = cmd_status(sk, mgmt_op, ENETDOWN);
1223 goto failed;
1224 }
1225
1226 cmd = mgmt_pending_add(sk, mgmt_op, dev_id, data, len);
1227 if (!cmd) {
1228 err = -ENOMEM;
1229 goto failed;
1230 }
1231
1232 err = hci_send_cmd(hdev, hci_op, sizeof(cp->bdaddr), &cp->bdaddr);
1233 if (err < 0) {
1234 list_del(&cmd->list);
1235 mgmt_pending_free(cmd);
1236 }
1237
1238failed:
1239 hci_dev_unlock_bh(hdev);
1240 hci_dev_put(hdev);
1241
1242 return err;
1243}
1244
0381101f
JH
1245int mgmt_control(struct sock *sk, struct msghdr *msg, size_t msglen)
1246{
1247 unsigned char *buf;
1248 struct mgmt_hdr *hdr;
1249 u16 opcode, len;
1250 int err;
1251
1252 BT_DBG("got %zu bytes", msglen);
1253
1254 if (msglen < sizeof(*hdr))
1255 return -EINVAL;
1256
1257 buf = kmalloc(msglen, GFP_ATOMIC);
1258 if (!buf)
1259 return -ENOMEM;
1260
1261 if (memcpy_fromiovec(buf, msg->msg_iov, msglen)) {
1262 err = -EFAULT;
1263 goto done;
1264 }
1265
1266 hdr = (struct mgmt_hdr *) buf;
1267 opcode = get_unaligned_le16(&hdr->opcode);
1268 len = get_unaligned_le16(&hdr->len);
1269
1270 if (len != msglen - sizeof(*hdr)) {
1271 err = -EINVAL;
1272 goto done;
1273 }
1274
1275 switch (opcode) {
02d98129
JH
1276 case MGMT_OP_READ_VERSION:
1277 err = read_version(sk);
1278 break;
faba42eb
JH
1279 case MGMT_OP_READ_INDEX_LIST:
1280 err = read_index_list(sk);
1281 break;
f7b64e69
JH
1282 case MGMT_OP_READ_INFO:
1283 err = read_controller_info(sk, buf + sizeof(*hdr), len);
1284 break;
eec8d2bc
JH
1285 case MGMT_OP_SET_POWERED:
1286 err = set_powered(sk, buf + sizeof(*hdr), len);
1287 break;
73f22f62
JH
1288 case MGMT_OP_SET_DISCOVERABLE:
1289 err = set_discoverable(sk, buf + sizeof(*hdr), len);
1290 break;
9fbcbb45
JH
1291 case MGMT_OP_SET_CONNECTABLE:
1292 err = set_connectable(sk, buf + sizeof(*hdr), len);
1293 break;
c542a06c
JH
1294 case MGMT_OP_SET_PAIRABLE:
1295 err = set_pairable(sk, buf + sizeof(*hdr), len);
1296 break;
2aeb9a1a
JH
1297 case MGMT_OP_ADD_UUID:
1298 err = add_uuid(sk, buf + sizeof(*hdr), len);
1299 break;
1300 case MGMT_OP_REMOVE_UUID:
1301 err = remove_uuid(sk, buf + sizeof(*hdr), len);
1302 break;
1aff6f09
JH
1303 case MGMT_OP_SET_DEV_CLASS:
1304 err = set_dev_class(sk, buf + sizeof(*hdr), len);
1305 break;
1306 case MGMT_OP_SET_SERVICE_CACHE:
1307 err = set_service_cache(sk, buf + sizeof(*hdr), len);
1308 break;
55ed8ca1
JH
1309 case MGMT_OP_LOAD_KEYS:
1310 err = load_keys(sk, buf + sizeof(*hdr), len);
1311 break;
1312 case MGMT_OP_REMOVE_KEY:
1313 err = remove_key(sk, buf + sizeof(*hdr), len);
1314 break;
8962ee74
JH
1315 case MGMT_OP_DISCONNECT:
1316 err = disconnect(sk, buf + sizeof(*hdr), len);
1317 break;
2784eb41
JH
1318 case MGMT_OP_GET_CONNECTIONS:
1319 err = get_connections(sk, buf + sizeof(*hdr), len);
1320 break;
980e1a53
JH
1321 case MGMT_OP_PIN_CODE_REPLY:
1322 err = pin_code_reply(sk, buf + sizeof(*hdr), len);
1323 break;
1324 case MGMT_OP_PIN_CODE_NEG_REPLY:
1325 err = pin_code_neg_reply(sk, buf + sizeof(*hdr), len);
1326 break;
17fa4b9d
JH
1327 case MGMT_OP_SET_IO_CAPABILITY:
1328 err = set_io_capability(sk, buf + sizeof(*hdr), len);
1329 break;
e9a416b5
JH
1330 case MGMT_OP_PAIR_DEVICE:
1331 err = pair_device(sk, buf + sizeof(*hdr), len);
1332 break;
a5c29683
JH
1333 case MGMT_OP_USER_CONFIRM_REPLY:
1334 err = user_confirm_reply(sk, buf + sizeof(*hdr), len, 1);
1335 break;
1336 case MGMT_OP_USER_CONFIRM_NEG_REPLY:
1337 err = user_confirm_reply(sk, buf + sizeof(*hdr), len, 0);
1338 break;
0381101f
JH
1339 default:
1340 BT_DBG("Unknown op %u", opcode);
e41d8b4e 1341 err = cmd_status(sk, opcode, 0x01);
0381101f
JH
1342 break;
1343 }
1344
e41d8b4e
JH
1345 if (err < 0)
1346 goto done;
1347
0381101f
JH
1348 err = msglen;
1349
1350done:
1351 kfree(buf);
1352 return err;
1353}
c71e97bf 1354
c71e97bf
JH
1355int mgmt_index_added(u16 index)
1356{
1357 struct mgmt_ev_index_added ev;
1358
1359 put_unaligned_le16(index, &ev.index);
1360
eec8d2bc 1361 return mgmt_event(MGMT_EV_INDEX_ADDED, &ev, sizeof(ev), NULL);
c71e97bf
JH
1362}
1363
1364int mgmt_index_removed(u16 index)
1365{
1366 struct mgmt_ev_index_added ev;
1367
1368 put_unaligned_le16(index, &ev.index);
1369
eec8d2bc
JH
1370 return mgmt_event(MGMT_EV_INDEX_REMOVED, &ev, sizeof(ev), NULL);
1371}
1372
73f22f62 1373struct cmd_lookup {
72a734ec 1374 u8 val;
eec8d2bc
JH
1375 struct sock *sk;
1376};
1377
72a734ec 1378static void mode_rsp(struct pending_cmd *cmd, void *data)
eec8d2bc 1379{
72a734ec 1380 struct mgmt_mode *cp = cmd->cmd;
73f22f62 1381 struct cmd_lookup *match = data;
eec8d2bc 1382
72a734ec 1383 if (cp->val != match->val)
eec8d2bc
JH
1384 return;
1385
053f0211 1386 send_mode_rsp(cmd->sk, cmd->opcode, cmd->index, cp->val);
eec8d2bc
JH
1387
1388 list_del(&cmd->list);
1389
1390 if (match->sk == NULL) {
1391 match->sk = cmd->sk;
1392 sock_hold(match->sk);
1393 }
1394
1395 mgmt_pending_free(cmd);
c71e97bf 1396}
5add6af8
JH
1397
1398int mgmt_powered(u16 index, u8 powered)
1399{
72a734ec 1400 struct mgmt_mode ev;
73f22f62 1401 struct cmd_lookup match = { powered, NULL };
eec8d2bc 1402 int ret;
5add6af8 1403
72a734ec 1404 mgmt_pending_foreach(MGMT_OP_SET_POWERED, index, mode_rsp, &match);
5add6af8 1405
72a734ec
JH
1406 put_unaligned_le16(index, &ev.index);
1407 ev.val = powered;
eec8d2bc
JH
1408
1409 ret = mgmt_event(MGMT_EV_POWERED, &ev, sizeof(ev), match.sk);
1410
1411 if (match.sk)
1412 sock_put(match.sk);
1413
1414 return ret;
5add6af8 1415}
73f22f62 1416
73f22f62
JH
1417int mgmt_discoverable(u16 index, u8 discoverable)
1418{
72a734ec 1419 struct mgmt_mode ev;
73f22f62
JH
1420 struct cmd_lookup match = { discoverable, NULL };
1421 int ret;
1422
73f22f62 1423 mgmt_pending_foreach(MGMT_OP_SET_DISCOVERABLE, index,
72a734ec
JH
1424 mode_rsp, &match);
1425
1426 put_unaligned_le16(index, &ev.index);
1427 ev.val = discoverable;
73f22f62
JH
1428
1429 ret = mgmt_event(MGMT_EV_DISCOVERABLE, &ev, sizeof(ev), match.sk);
1430
1431 if (match.sk)
1432 sock_put(match.sk);
1433
1434 return ret;
1435}
9fbcbb45 1436
9fbcbb45
JH
1437int mgmt_connectable(u16 index, u8 connectable)
1438{
72a734ec 1439 struct mgmt_mode ev;
9fbcbb45
JH
1440 struct cmd_lookup match = { connectable, NULL };
1441 int ret;
1442
72a734ec 1443 mgmt_pending_foreach(MGMT_OP_SET_CONNECTABLE, index, mode_rsp, &match);
9fbcbb45 1444
72a734ec
JH
1445 put_unaligned_le16(index, &ev.index);
1446 ev.val = connectable;
9fbcbb45
JH
1447
1448 ret = mgmt_event(MGMT_EV_CONNECTABLE, &ev, sizeof(ev), match.sk);
1449
1450 if (match.sk)
1451 sock_put(match.sk);
1452
1453 return ret;
1454}
55ed8ca1
JH
1455
1456int mgmt_new_key(u16 index, struct link_key *key, u8 old_key_type)
1457{
1458 struct mgmt_ev_new_key ev;
1459
1460 memset(&ev, 0, sizeof(ev));
1461
1462 put_unaligned_le16(index, &ev.index);
1463
1464 bacpy(&ev.key.bdaddr, &key->bdaddr);
1465 ev.key.type = key->type;
1466 memcpy(ev.key.val, key->val, 16);
1467 ev.key.pin_len = key->pin_len;
1468 ev.old_key_type = old_key_type;
1469
1470 return mgmt_event(MGMT_EV_NEW_KEY, &ev, sizeof(ev), NULL);
1471}
f7520543
JH
1472
1473int mgmt_connected(u16 index, bdaddr_t *bdaddr)
1474{
1475 struct mgmt_ev_connected ev;
1476
1477 put_unaligned_le16(index, &ev.index);
1478 bacpy(&ev.bdaddr, bdaddr);
1479
1480 return mgmt_event(MGMT_EV_CONNECTED, &ev, sizeof(ev), NULL);
1481}
1482
8962ee74
JH
1483static void disconnect_rsp(struct pending_cmd *cmd, void *data)
1484{
1485 struct mgmt_cp_disconnect *cp = cmd->cmd;
1486 struct sock **sk = data;
a38528f1 1487 struct mgmt_rp_disconnect rp;
8962ee74 1488
a38528f1
JH
1489 put_unaligned_le16(cmd->index, &rp.index);
1490 bacpy(&rp.bdaddr, &cp->bdaddr);
8962ee74 1491
a38528f1 1492 cmd_complete(cmd->sk, MGMT_OP_DISCONNECT, &rp, sizeof(rp));
8962ee74
JH
1493
1494 *sk = cmd->sk;
1495 sock_hold(*sk);
1496
1497 list_del(&cmd->list);
1498 mgmt_pending_free(cmd);
1499}
1500
f7520543
JH
1501int mgmt_disconnected(u16 index, bdaddr_t *bdaddr)
1502{
1503 struct mgmt_ev_disconnected ev;
8962ee74
JH
1504 struct sock *sk = NULL;
1505 int err;
1506
1507 mgmt_pending_foreach(MGMT_OP_DISCONNECT, index, disconnect_rsp, &sk);
f7520543
JH
1508
1509 put_unaligned_le16(index, &ev.index);
1510 bacpy(&ev.bdaddr, bdaddr);
1511
8962ee74
JH
1512 err = mgmt_event(MGMT_EV_DISCONNECTED, &ev, sizeof(ev), sk);
1513
1514 if (sk)
1515 sock_put(sk);
1516
1517 return err;
1518}
1519
1520int mgmt_disconnect_failed(u16 index)
1521{
1522 struct pending_cmd *cmd;
1523 int err;
1524
1525 cmd = mgmt_pending_find(MGMT_OP_DISCONNECT, index);
1526 if (!cmd)
1527 return -ENOENT;
1528
1529 err = cmd_status(cmd->sk, MGMT_OP_DISCONNECT, EIO);
1530
1531 list_del(&cmd->list);
1532 mgmt_pending_free(cmd);
1533
1534 return err;
f7520543 1535}
17d5c04c
JH
1536
1537int mgmt_connect_failed(u16 index, bdaddr_t *bdaddr, u8 status)
1538{
1539 struct mgmt_ev_connect_failed ev;
1540
1541 put_unaligned_le16(index, &ev.index);
1542 bacpy(&ev.bdaddr, bdaddr);
1543 ev.status = status;
1544
1545 return mgmt_event(MGMT_EV_CONNECT_FAILED, &ev, sizeof(ev), NULL);
1546}
980e1a53
JH
1547
1548int mgmt_pin_code_request(u16 index, bdaddr_t *bdaddr)
1549{
1550 struct mgmt_ev_pin_code_request ev;
1551
1552 put_unaligned_le16(index, &ev.index);
1553 bacpy(&ev.bdaddr, bdaddr);
1554
1555 return mgmt_event(MGMT_EV_PIN_CODE_REQUEST, &ev, sizeof(ev), NULL);
1556}
1557
1558int mgmt_pin_code_reply_complete(u16 index, bdaddr_t *bdaddr, u8 status)
1559{
1560 struct pending_cmd *cmd;
1561 int err;
1562
1563 cmd = mgmt_pending_find(MGMT_OP_PIN_CODE_REPLY, index);
1564 if (!cmd)
1565 return -ENOENT;
1566
1567 if (status != 0)
1568 err = cmd_status(cmd->sk, MGMT_OP_PIN_CODE_REPLY, status);
1569 else
1570 err = cmd_complete(cmd->sk, MGMT_OP_PIN_CODE_REPLY,
1571 bdaddr, sizeof(*bdaddr));
1572
1573 list_del(&cmd->list);
1574 mgmt_pending_free(cmd);
1575
1576 return err;
1577}
1578
1579int mgmt_pin_code_neg_reply_complete(u16 index, bdaddr_t *bdaddr, u8 status)
1580{
1581 struct pending_cmd *cmd;
1582 int err;
1583
1584 cmd = mgmt_pending_find(MGMT_OP_PIN_CODE_NEG_REPLY, index);
1585 if (!cmd)
1586 return -ENOENT;
1587
1588 if (status != 0)
1589 err = cmd_status(cmd->sk, MGMT_OP_PIN_CODE_NEG_REPLY, status);
1590 else
1591 err = cmd_complete(cmd->sk, MGMT_OP_PIN_CODE_NEG_REPLY,
1592 bdaddr, sizeof(*bdaddr));
1593
1594 list_del(&cmd->list);
1595 mgmt_pending_free(cmd);
1596
1597 return err;
1598}
a5c29683
JH
1599
1600int mgmt_user_confirm_request(u16 index, bdaddr_t *bdaddr, __le32 value)
1601{
1602 struct mgmt_ev_user_confirm_request ev;
1603
1604 BT_DBG("hci%u", index);
1605
1606 put_unaligned_le16(index, &ev.index);
1607 bacpy(&ev.bdaddr, bdaddr);
1608 put_unaligned_le32(value, &ev.value);
1609
1610 return mgmt_event(MGMT_EV_USER_CONFIRM_REQUEST, &ev, sizeof(ev), NULL);
1611}
1612
1613static int confirm_reply_complete(u16 index, bdaddr_t *bdaddr, u8 status,
1614 u8 opcode)
1615{
1616 struct pending_cmd *cmd;
1617 struct mgmt_rp_user_confirm_reply rp;
1618 int err;
1619
1620 cmd = mgmt_pending_find(opcode, index);
1621 if (!cmd)
1622 return -ENOENT;
1623
1624 put_unaligned_le16(index, &rp.index);
1625 bacpy(&rp.bdaddr, bdaddr);
1626 rp.status = status;
1627 err = cmd_complete(cmd->sk, opcode, &rp, sizeof(rp));
1628
1629 list_del(&cmd->list);
1630 mgmt_pending_free(cmd);
1631
1632 return err;
1633}
1634
1635int mgmt_user_confirm_reply_complete(u16 index, bdaddr_t *bdaddr, u8 status)
1636{
1637 return confirm_reply_complete(index, bdaddr, status,
1638 MGMT_OP_USER_CONFIRM_REPLY);
1639}
1640
1641int mgmt_user_confirm_neg_reply_complete(u16 index, bdaddr_t *bdaddr,
1642 u8 status)
1643{
1644 return confirm_reply_complete(index, bdaddr, status,
1645 MGMT_OP_USER_CONFIRM_NEG_REPLY);
1646}