xref: /freebsd/usr.sbin/bluetooth/hccontrol/host_controller_baseband.c (revision 63d1fd5970ec814904aa0f4580b10a0d302d08b2)
1 /*
2  * host_controller_baseband.c
3  *
4  * Copyright (c) 2001-2002 Maksim Yevmenkin <m_evmenkin@yahoo.com>
5  * All rights reserved.
6  *
7  * Redistribution and use in source and binary forms, with or without
8  * modification, are permitted provided that the following conditions
9  * are met:
10  * 1. Redistributions of source code must retain the above copyright
11  *    notice, this list of conditions and the following disclaimer.
12  * 2. Redistributions in binary form must reproduce the above copyright
13  *    notice, this list of conditions and the following disclaimer in the
14  *    documentation and/or other materials provided with the distribution.
15  *
16  * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
17  * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
18  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
19  * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
20  * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
21  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
22  * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
23  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
24  * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
25  * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
26  * SUCH DAMAGE.
27  *
28  * $Id: host_controller_baseband.c,v 1.4 2003/08/18 19:19:53 max Exp $
29  * $FreeBSD$
30  */
31 
32 #define L2CAP_SOCKET_CHECKED
33 #include <bluetooth.h>
34 #include <errno.h>
35 #include <stdio.h>
36 #include <string.h>
37 #include "hccontrol.h"
38 
39 /* Convert hex ASCII to int4 */
40 static int
41 hci_hexa2int4(const char *a)
42 {
43 	if ('0' <= *a && *a <= '9')
44 		return (*a - '0');
45 
46 	if ('A' <= *a && *a <= 'F')
47 		return (*a - 'A' + 0xa);
48 
49 	if ('a' <= *a && *a <= 'f')
50 		return (*a - 'a' + 0xa);
51 
52 	return (-1);
53 }
54 
55 /* Convert hex ASCII to int8 */
56 static int
57 hci_hexa2int8(const char *a)
58 {
59 	int	hi = hci_hexa2int4(a);
60 	int	lo = hci_hexa2int4(a + 1);
61 
62 	if (hi < 0 || lo < 0)
63 		return (-1);
64 
65 	return ((hi << 4) | lo);
66 }
67 
68 /* Convert ascii hex string to the uint8_t[] */
69 static int
70 hci_hexstring2array(char const *s, uint8_t *a, int asize)
71 {
72 	int	i, l, b;
73 
74 	l = strlen(s) / 2;
75 	if (l > asize)
76 		l = asize;
77 
78 	for (i = 0; i < l; i++) {
79 		b = hci_hexa2int8(s + i * 2);
80 		if (b < 0)
81 			return (-1);
82 
83 		a[i] = (b & 0xff);
84 	}
85 
86 	return (0);
87 }
88 
89 /* Send RESET to the unit */
90 static int
91 hci_reset(int s, int argc, char **argv)
92 {
93 	ng_hci_status_rp	rp;
94 	int			n;
95 
96 	n = sizeof(rp);
97 	if (hci_simple_request(s, NG_HCI_OPCODE(NG_HCI_OGF_HC_BASEBAND,
98 			NG_HCI_OCF_RESET), (char *) &rp, &n) == ERROR)
99 		return (ERROR);
100 
101 	if (rp.status != 0x00) {
102 		fprintf(stdout, "Status: %s [%#02x]\n",
103 			hci_status2str(rp.status), rp.status);
104 		return (FAILED);
105 	}
106 
107 	return (OK);
108 } /* hci_reset */
109 
110 /* Send Read_PIN_Type command to the unit */
111 static int
112 hci_read_pin_type(int s, int argc, char **argv)
113 {
114 	ng_hci_read_pin_type_rp	rp;
115 	int			n;
116 
117 	n = sizeof(rp);
118 	if (hci_simple_request(s, NG_HCI_OPCODE(NG_HCI_OGF_HC_BASEBAND,
119 			NG_HCI_OCF_READ_PIN_TYPE),
120 			(char *) &rp, &n) == ERROR)
121 		return (ERROR);
122 
123 	if (rp.status != 0x00) {
124 		fprintf(stdout, "Status: %s [%#02x]\n",
125 			hci_status2str(rp.status), rp.status);
126 		return (FAILED);
127 	}
128 
129 	fprintf(stdout, "PIN type: %s [%#02x]\n",
130 			hci_pin2str(rp.pin_type), rp.pin_type);
131 
132 	return (OK);
133 } /* hci_read_pin_type */
134 
135 /* Send Write_PIN_Type command to the unit */
136 static int
137 hci_write_pin_type(int s, int argc, char **argv)
138 {
139 	ng_hci_write_pin_type_cp	cp;
140 	ng_hci_write_pin_type_rp	rp;
141 	int				n;
142 
143 	/* parse command parameters */
144 	switch (argc) {
145 	case 1:
146 		if (sscanf(argv[0], "%d", &n) != 1 || n < 0 || n > 1)
147 			return (USAGE);
148 
149 		cp.pin_type = (uint8_t) n;
150 		break;
151 
152 	default:
153 		return (USAGE);
154 	}
155 
156 	/* send command */
157 	n = sizeof(rp);
158 	if (hci_request(s, NG_HCI_OPCODE(NG_HCI_OGF_HC_BASEBAND,
159 			NG_HCI_OCF_WRITE_PIN_TYPE),
160 			(char const *) &cp, sizeof(cp),
161 			(char *) &rp , &n) ==  ERROR)
162 		return (ERROR);
163 
164 	if (rp.status != 0x00) {
165 		fprintf(stdout, "Status: %s [%#02x]\n",
166 			hci_status2str(rp.status), rp.status);
167 		return (FAILED);
168 	}
169 
170 	return (OK);
171 } /* hci_write_pin_type */
172 
173 /* Send Read_Stored_Link_Key command to the unit */
174 static int
175 hci_read_stored_link_key(int s, int argc, char **argv)
176 {
177 	struct {
178 		ng_hci_cmd_pkt_t			hdr;
179 		ng_hci_read_stored_link_key_cp		cp;
180 	} __attribute__ ((packed))			cmd;
181 
182 	struct {
183 		ng_hci_event_pkt_t			hdr;
184 		union {
185 			ng_hci_command_compl_ep		cc;
186 			ng_hci_return_link_keys_ep	key;
187 			uint8_t				b[NG_HCI_EVENT_PKT_SIZE];
188 		}					ep;
189 	} __attribute__ ((packed))			event;
190 
191 	int						n, n1;
192 
193 	/* Send command */
194 	memset(&cmd, 0, sizeof(cmd));
195 	cmd.hdr.type = NG_HCI_CMD_PKT;
196 	cmd.hdr.opcode = htole16(NG_HCI_OPCODE(NG_HCI_OGF_HC_BASEBAND,
197 				NG_HCI_OCF_READ_STORED_LINK_KEY));
198 	cmd.hdr.length = sizeof(cmd.cp);
199 
200 	switch (argc) {
201 	case 1:
202 		/* parse BD_ADDR */
203 		if (!bt_aton(argv[0], &cmd.cp.bdaddr)) {
204 			struct hostent	*he = NULL;
205 
206 			if ((he = bt_gethostbyname(argv[0])) == NULL)
207 				return (USAGE);
208 
209 			memcpy(&cmd.cp.bdaddr, he->h_addr, sizeof(cmd.cp.bdaddr));
210 		}
211 		break;
212 
213 	default:
214 		cmd.cp.read_all = 1;
215 		break;
216 	}
217 
218 	if (hci_send(s, (char const *) &cmd, sizeof(cmd)) != OK)
219 		return (ERROR);
220 
221 	/* Receive events */
222 again:
223 	memset(&event, 0, sizeof(event));
224 	n = sizeof(event);
225 	if (hci_recv(s, (char *) &event, &n) != OK)
226 		return (ERROR);
227 
228 	if (n <= sizeof(event.hdr)) {
229 		errno = EMSGSIZE;
230 		return (ERROR);
231 	}
232 
233 	if (event.hdr.type != NG_HCI_EVENT_PKT) {
234 		errno = EIO;
235 		return (ERROR);
236 	}
237 
238 	/* Parse event */
239 	switch (event.hdr.event) {
240 	case NG_HCI_EVENT_COMMAND_COMPL: {
241 		ng_hci_read_stored_link_key_rp	*rp = NULL;
242 
243 		if (event.ep.cc.opcode == 0x0000 ||
244 		    event.ep.cc.opcode != cmd.hdr.opcode)
245 			goto again;
246 
247 		rp = (ng_hci_read_stored_link_key_rp *)(event.ep.b +
248 				sizeof(event.ep.cc));
249 
250 		fprintf(stdout, "Complete: Status: %s [%#x]\n",
251 				hci_status2str(rp->status), rp->status);
252 		fprintf(stdout, "Maximum Number of keys: %d\n",
253 				le16toh(rp->max_num_keys));
254 		fprintf(stdout, "Number of keys read: %d\n",
255 				le16toh(rp->num_keys_read));
256 		} break;
257 
258 	case NG_HCI_EVENT_RETURN_LINK_KEYS: {
259 		struct _key {
260 			bdaddr_t	bdaddr;
261 			uint8_t		key[NG_HCI_KEY_SIZE];
262 		} __attribute__ ((packed))	*k = NULL;
263 
264 		fprintf(stdout, "Event: Number of keys: %d\n",
265 			event.ep.key.num_keys);
266 
267 		k = (struct _key *)(event.ep.b + sizeof(event.ep.key));
268 		for (n = 0; n < event.ep.key.num_keys; n++) {
269 			fprintf(stdout, "\t%d: %s ",
270 				n + 1, hci_bdaddr2str(&k->bdaddr));
271 
272 			for (n1 = 0; n1 < sizeof(k->key); n1++)
273 				fprintf(stdout, "%02x", k->key[n1]);
274 			fprintf(stdout, "\n");
275 
276 			k ++;
277 		}
278 
279 		goto again;
280 
281 		} break;
282 
283 	default:
284 		goto again;
285 	}
286 
287 	return (OK);
288 } /* hci_read_store_link_key */
289 
290 /* Send Write_Stored_Link_Key command to the unit */
291 static int
292 hci_write_stored_link_key(int s, int argc, char **argv)
293 {
294 	struct {
295 		ng_hci_write_stored_link_key_cp	p;
296 		bdaddr_t			bdaddr;
297 		uint8_t				key[NG_HCI_KEY_SIZE];
298 	}					cp;
299 	ng_hci_write_stored_link_key_rp		rp;
300 	int32_t					n;
301 
302 	memset(&cp, 0, sizeof(cp));
303 
304 	switch (argc) {
305 	case 2:
306 		cp.p.num_keys_write = 1;
307 
308 		/* parse BD_ADDR */
309 		if (!bt_aton(argv[0], &cp.bdaddr)) {
310 			struct hostent	*he = NULL;
311 
312 			if ((he = bt_gethostbyname(argv[0])) == NULL)
313 				return (USAGE);
314 
315 			memcpy(&cp.bdaddr, he->h_addr, sizeof(cp.bdaddr));
316 		}
317 
318 		/* parse key */
319 		if (hci_hexstring2array(argv[1], cp.key, sizeof(cp.key)) < 0)
320 			return (USAGE);
321 		break;
322 
323 	default:
324 		return (USAGE);
325 	}
326 
327 	/* send command */
328 	n = sizeof(rp);
329 	if (hci_request(s, NG_HCI_OPCODE(NG_HCI_OGF_HC_BASEBAND,
330 			NG_HCI_OCF_WRITE_STORED_LINK_KEY),
331 			(char const *) &cp, sizeof(cp),
332 			(char *) &rp, &n) == ERROR)
333 		return (ERROR);
334 
335 	if (rp.status != 0x00) {
336 		fprintf(stdout, "Status: %s [%#02x]\n",
337 			hci_status2str(rp.status), rp.status);
338 		return (FAILED);
339 	}
340 
341 	fprintf(stdout, "Number of keys written: %d\n", rp.num_keys_written);
342 
343 	return (OK);
344 } /* hci_write_stored_link_key */
345 
346 
347 /* Send Delete_Stored_Link_Key command to the unit */
348 static int
349 hci_delete_stored_link_key(int s, int argc, char **argv)
350 {
351 	ng_hci_delete_stored_link_key_cp	cp;
352 	ng_hci_delete_stored_link_key_rp	rp;
353 	int32_t					n;
354 
355 	memset(&cp, 0, sizeof(cp));
356 
357 	switch (argc) {
358 	case 1:
359 		/* parse BD_ADDR */
360 		if (!bt_aton(argv[0], &cp.bdaddr)) {
361 			struct hostent	*he = NULL;
362 
363 			if ((he = bt_gethostbyname(argv[0])) == NULL)
364 				return (USAGE);
365 
366 			memcpy(&cp.bdaddr, he->h_addr, sizeof(cp.bdaddr));
367 		}
368 		break;
369 
370 	default:
371 		cp.delete_all = 1;
372 		break;
373 	}
374 
375 	/* send command */
376 	n = sizeof(cp);
377 	if (hci_request(s, NG_HCI_OPCODE(NG_HCI_OGF_HC_BASEBAND,
378 			NG_HCI_OCF_DELETE_STORED_LINK_KEY),
379 			(char const *) &cp, sizeof(cp),
380 			(char *) &rp, &n) == ERROR)
381 		return (ERROR);
382 
383 	if (rp.status != 0x00) {
384 		fprintf(stdout, "Status: %s [%#02x]\n",
385 			hci_status2str(rp.status), rp.status);
386 		return (FAILED);
387 	}
388 
389 	fprintf(stdout, "Number of keys deleted: %d\n", rp.num_keys_deleted);
390 
391 	return (OK);
392 } /* hci_delete_stored_link_key */
393 
394 /* Send Change_Local_Name command to the unit */
395 static int
396 hci_change_local_name(int s, int argc, char **argv)
397 {
398 	ng_hci_change_local_name_cp	cp;
399 	ng_hci_change_local_name_rp	rp;
400 	int				n;
401 
402 	/* parse command parameters */
403 	switch (argc) {
404 	case 1:
405 		snprintf(cp.name, sizeof(cp.name), "%s", argv[0]);
406 		break;
407 
408 	default:
409 		return (USAGE);
410 	}
411 
412 	/* send command */
413 	n = sizeof(rp);
414 	if (hci_request(s, NG_HCI_OPCODE(NG_HCI_OGF_HC_BASEBAND,
415 			NG_HCI_OCF_CHANGE_LOCAL_NAME),
416 			(char const *) &cp, sizeof(cp),
417 			(char *) &rp, &n) == ERROR)
418 		return (ERROR);
419 
420 	if (rp.status != 0x00) {
421 		fprintf(stdout, "Status: %s [%#02x]\n",
422 			hci_status2str(rp.status), rp.status);
423 		return (FAILED);
424 	}
425 
426 	return (OK);
427 } /* hci_change_local_name */
428 
429 /* Send Read_Local_Name command to the unit */
430 static int
431 hci_read_local_name(int s, int argc, char **argv)
432 {
433 	ng_hci_read_local_name_rp	rp;
434 	int				n;
435 
436 	n = sizeof(rp);
437 	if (hci_simple_request(s, NG_HCI_OPCODE(NG_HCI_OGF_HC_BASEBAND,
438 			NG_HCI_OCF_READ_LOCAL_NAME),
439 			(char *) &rp, &n) == ERROR)
440 		return (ERROR);
441 
442 	if (rp.status != 0x00) {
443 		fprintf(stdout, "Status: %s [%#02x]\n",
444 			hci_status2str(rp.status), rp.status);
445 		return (FAILED);
446 	}
447 
448 	fprintf(stdout, "Local name: %s\n", rp.name);
449 
450 	return (OK);
451 } /* hci_read_local_name */
452 
453 /* Send Read_Connection_Accept_Timeout to the unit */
454 static int
455 hci_read_connection_accept_timeout(int s, int argc, char **argv)
456 {
457 	ng_hci_read_con_accept_timo_rp	rp;
458 	int				n;
459 
460 	n = sizeof(rp);
461 	if (hci_simple_request(s, NG_HCI_OPCODE(NG_HCI_OGF_HC_BASEBAND,
462 			NG_HCI_OCF_READ_CON_ACCEPT_TIMO),
463 			(char *) &rp, &n) == ERROR)
464 		return (ERROR);
465 
466 	if (rp.status != 0x00) {
467 		fprintf(stdout, "Status: %s [%#02x]\n",
468 			hci_status2str(rp.status), rp.status);
469 		return (FAILED);
470 	}
471 
472 	rp.timeout = le16toh(rp.timeout);
473 	fprintf(stdout, "Connection accept timeout: %.2f msec [%d slots]\n",
474 			rp.timeout * 0.625, rp.timeout);
475 
476 	return (OK);
477 } /* hci_read_connection_accept_timeout */
478 
479 /* Send Write_Connection_Accept_Timeout to the unit */
480 static int
481 hci_write_connection_accept_timeout(int s, int argc, char **argv)
482 {
483 	ng_hci_write_con_accept_timo_cp	cp;
484 	ng_hci_write_con_accept_timo_rp	rp;
485 	int				n;
486 
487 	/* parse command parameters */
488 	switch (argc) {
489 	case 1:
490 		if (sscanf(argv[0], "%d", &n) != 1 || n < 1 || n > 0xb540)
491 			return (USAGE);
492 
493 		cp.timeout = (uint16_t) n;
494 		cp.timeout = htole16(cp.timeout);
495 		break;
496 
497 	default:
498 		return (USAGE);
499 	}
500 
501 	/* send command */
502 	n = sizeof(rp);
503 	if (hci_request(s, NG_HCI_OPCODE(NG_HCI_OGF_HC_BASEBAND,
504 			NG_HCI_OCF_WRITE_CON_ACCEPT_TIMO),
505 			(char const *) &cp, sizeof(cp),
506 			(char *) &rp, &n) == ERROR)
507 		return (ERROR);
508 
509 	if (rp.status != 0x00) {
510 		fprintf(stdout, "Status: %s [%#02x]\n",
511 			hci_status2str(rp.status), rp.status);
512 		return (FAILED);
513 	}
514 
515 	return (OK);
516 } /* hci_write_connection_accept_timeout */
517 
518 /* Send Read_Page_Timeout command to the unit */
519 static int
520 hci_read_page_timeout(int s, int argc, char **argv)
521 {
522 	ng_hci_read_page_timo_rp	rp;
523 	int				n;
524 
525 	n = sizeof(rp);
526 	if (hci_simple_request(s, NG_HCI_OPCODE(NG_HCI_OGF_HC_BASEBAND,
527 			NG_HCI_OCF_READ_PAGE_TIMO),
528 			(char *) &rp, &n) == ERROR)
529 		return (ERROR);
530 
531 	if (rp.status != 0x00) {
532 		fprintf(stdout, "Status: %s [%#02x]\n",
533 			hci_status2str(rp.status), rp.status);
534 		return (FAILED);
535 	}
536 
537 	rp.timeout = le16toh(rp.timeout);
538 	fprintf(stdout, "Page timeout: %.2f msec [%d slots]\n",
539 		rp.timeout * 0.625, rp.timeout);
540 
541 	return (OK);
542 } /* hci_read_page_timeoout */
543 
544 /* Send Write_Page_Timeout command to the unit */
545 static int
546 hci_write_page_timeout(int s, int argc, char **argv)
547 {
548 	ng_hci_write_page_timo_cp	cp;
549 	ng_hci_write_page_timo_rp	rp;
550 	int				n;
551 
552 	/* parse command parameters */
553 	switch (argc) {
554 	case 1:
555 		if (sscanf(argv[0], "%d", &n) != 1 || n < 1 || n > 0xffff)
556 			return (USAGE);
557 
558 		cp.timeout = (uint16_t) n;
559 		cp.timeout = htole16(cp.timeout);
560 		break;
561 
562 	default:
563 		return (USAGE);
564 	}
565 
566 	/* send command */
567 	n = sizeof(rp);
568 	if (hci_request(s, NG_HCI_OPCODE(NG_HCI_OGF_HC_BASEBAND,
569 			NG_HCI_OCF_WRITE_PAGE_TIMO),
570 			(char const *) &cp, sizeof(cp),
571 			(char *) &rp, &n) == ERROR)
572 		return (ERROR);
573 
574 	if (rp.status != 0x00) {
575 		fprintf(stdout, "Status: %s [%#02x]\n",
576 			hci_status2str(rp.status), rp.status);
577 		return (FAILED);
578 	}
579 
580 	return (OK);
581 } /* hci_write_page_timeout */
582 
583 /* Send Read_Scan_Enable command to the unit */
584 static int
585 hci_read_scan_enable(int s, int argc, char **argv)
586 {
587 	ng_hci_read_scan_enable_rp	rp;
588 	int				n;
589 
590 	n = sizeof(rp);
591 	if (hci_simple_request(s, NG_HCI_OPCODE(NG_HCI_OGF_HC_BASEBAND,
592 			NG_HCI_OCF_READ_SCAN_ENABLE),
593 			(char *) &rp, &n) == ERROR)
594 		return (ERROR);
595 
596 	if (rp.status != 0x00) {
597 		fprintf(stdout, "Status: %s [%#02x]\n",
598 			hci_status2str(rp.status), rp.status);
599 		return (FAILED);
600 	}
601 
602 	fprintf(stdout, "Scan enable: %s [%#02x]\n",
603 		hci_scan2str(rp.scan_enable), rp.scan_enable);
604 
605 	return (OK);
606 } /* hci_read_scan_enable */
607 
608 /* Send Write_Scan_Enable command to the unit */
609 static int
610 hci_write_scan_enable(int s, int argc, char **argv)
611 {
612 	ng_hci_write_scan_enable_cp	cp;
613 	ng_hci_write_scan_enable_rp	rp;
614 	int				n;
615 
616 	/* parse command parameters */
617 	switch (argc) {
618 	case 1:
619 		if (sscanf(argv[0], "%d", &n) != 1 || n < 0 || n > 3)
620 			return (USAGE);
621 
622 		cp.scan_enable = (uint8_t) n;
623 		break;
624 
625 	default:
626 		return (USAGE);
627 	}
628 
629 	n = sizeof(rp);
630 	if (hci_request(s, NG_HCI_OPCODE(NG_HCI_OGF_HC_BASEBAND,
631 			NG_HCI_OCF_WRITE_SCAN_ENABLE),
632 			(char const *) &cp, sizeof(cp),
633 			(char *) &rp, &n) == ERROR)
634 		return (ERROR);
635 
636 	if (rp.status != 0x00) {
637 		fprintf(stdout, "Status: %s [%#02x]\n",
638 			hci_status2str(rp.status), rp.status);
639 		return (FAILED);
640 	}
641 
642 	return (OK);
643 } /* hci_write_scan_enable */
644 
645 /* Send Read_Page_Scan_Activity command to the unit */
646 static int
647 hci_read_page_scan_activity(int s, int argc, char **argv)
648 {
649 	ng_hci_read_page_scan_activity_rp	rp;
650 	int					n;
651 
652 	n = sizeof(rp);
653 	if (hci_simple_request(s, NG_HCI_OPCODE(NG_HCI_OGF_HC_BASEBAND,
654 			NG_HCI_OCF_READ_PAGE_SCAN_ACTIVITY),
655 			(char *) &rp, &n) == ERROR)
656 		return (ERROR);
657 
658 	if (rp.status != 0x00) {
659 		fprintf(stdout, "Status: %s [%#02x]\n",
660 			hci_status2str(rp.status), rp.status);
661 		return (FAILED);
662 	}
663 
664 	rp.page_scan_interval = le16toh(rp.page_scan_interval);
665 	rp.page_scan_window = le16toh(rp.page_scan_window);
666 
667 	fprintf(stdout, "Page Scan Interval: %.2f msec [%d slots]\n",
668 		rp.page_scan_interval * 0.625, rp.page_scan_interval);
669 	fprintf(stdout, "Page Scan Window: %.2f msec [%d slots]\n",
670 		rp.page_scan_window * 0.625, rp.page_scan_window);
671 
672 	return (OK);
673 } /* hci_read_page_scan_activity */
674 
675 /* Send Write_Page_Scan_Activity command to the unit */
676 static int
677 hci_write_page_scan_activity(int s, int argc, char **argv)
678 {
679 	ng_hci_write_page_scan_activity_cp	cp;
680 	ng_hci_write_page_scan_activity_rp	rp;
681 	int					n;
682 
683 	/* parse command parameters */
684 	switch (argc) {
685 	case 2:
686 		/* page scan interval */
687 		if (sscanf(argv[0], "%d", &n) != 1 || n < 0x12 || n > 0x1000)
688 			return (USAGE);
689 
690 		cp.page_scan_interval = (uint16_t) n;
691 
692 		/* page scan window */
693 		if (sscanf(argv[1], "%d", &n) != 1 || n < 0x12 || n > 0x1000)
694 			return (USAGE);
695 
696 		cp.page_scan_window = (uint16_t) n;
697 
698 		if (cp.page_scan_window > cp.page_scan_interval)
699 			return (USAGE);
700 
701 		cp.page_scan_interval = htole16(cp.page_scan_interval);
702 		cp.page_scan_window = htole16(cp.page_scan_window);
703 		break;
704 
705 	default:
706 		return (USAGE);
707 	}
708 
709 	/* send command */
710 	n = sizeof(rp);
711 	if (hci_request(s, NG_HCI_OPCODE(NG_HCI_OGF_HC_BASEBAND,
712 			NG_HCI_OCF_WRITE_PAGE_SCAN_ACTIVITY),
713 			(char const *) &cp, sizeof(cp),
714 			(char *) &rp, &n) == ERROR)
715 		return (ERROR);
716 
717 	if (rp.status != 0x00) {
718 		fprintf(stdout, "Status: %s [%#02x]\n",
719 			hci_status2str(rp.status), rp.status);
720 		return (FAILED);
721 	}
722 
723 	return (OK);
724 } /* hci_write_page_scan_activity */
725 
726 /* Send Read_Inquiry_Scan_Activity command to the unit */
727 static int
728 hci_read_inquiry_scan_activity(int s, int argc, char **argv)
729 {
730 	ng_hci_read_inquiry_scan_activity_rp	rp;
731 	int					n;
732 
733 	n = sizeof(rp);
734 	if (hci_simple_request(s, NG_HCI_OPCODE(NG_HCI_OGF_HC_BASEBAND,
735 			NG_HCI_OCF_READ_INQUIRY_SCAN_ACTIVITY),
736 			(char *) &rp, &n) == ERROR)
737 		return (ERROR);
738 
739 	if (rp.status != 0x00) {
740 		fprintf(stdout, "Status: %s [%#02x]\n",
741 			hci_status2str(rp.status), rp.status);
742 		return (FAILED);
743 	}
744 
745 	rp.inquiry_scan_interval = le16toh(rp.inquiry_scan_interval);
746 	rp.inquiry_scan_window = le16toh(rp.inquiry_scan_window);
747 
748 	fprintf(stdout, "Inquiry Scan Interval: %.2f msec [%d slots]\n",
749 		rp.inquiry_scan_interval * 0.625, rp.inquiry_scan_interval);
750 	fprintf(stdout, "Inquiry Scan Window: %.2f msec [%d slots]\n",
751 		rp.inquiry_scan_window * 0.625, rp.inquiry_scan_interval);
752 
753 	return (OK);
754 } /* hci_read_inquiry_scan_activity */
755 
756 /* Send Write_Inquiry_Scan_Activity command to the unit */
757 static int
758 hci_write_inquiry_scan_activity(int s, int argc, char **argv)
759 {
760 	ng_hci_write_inquiry_scan_activity_cp	cp;
761 	ng_hci_write_inquiry_scan_activity_rp	rp;
762 	int					n;
763 
764 	/* parse command parameters */
765 	switch (argc) {
766 	case 2:
767 		/* inquiry scan interval */
768 		if (sscanf(argv[0], "%d", &n) != 1 || n < 0x12 || n > 0x1000)
769 			return (USAGE);
770 
771 		cp.inquiry_scan_interval = (uint16_t) n;
772 
773 		/* inquiry scan window */
774 		if (sscanf(argv[1], "%d", &n) != 1 || n < 0x12 || n > 0x1000)
775 			return (USAGE);
776 
777 		cp.inquiry_scan_window = (uint16_t) n;
778 
779 		if (cp.inquiry_scan_window > cp.inquiry_scan_interval)
780 			return (USAGE);
781 
782 		cp.inquiry_scan_interval =
783 			htole16(cp.inquiry_scan_interval);
784 		cp.inquiry_scan_window = htole16(cp.inquiry_scan_window);
785 		break;
786 
787 	default:
788 		return (USAGE);
789 	}
790 
791 	/* send command */
792 	n = sizeof(rp);
793 	if (hci_request(s, NG_HCI_OPCODE(NG_HCI_OGF_HC_BASEBAND,
794 			NG_HCI_OCF_WRITE_INQUIRY_SCAN_ACTIVITY),
795 			(char const *) &cp, sizeof(cp),
796 			(char *) &rp, &n) == ERROR)
797 		return (ERROR);
798 
799 	if (rp.status != 0x00) {
800 		fprintf(stdout, "Status: %s [%#02x]\n",
801 			hci_status2str(rp.status), rp.status);
802 		return (FAILED);
803 	}
804 
805 	return (OK);
806 } /* hci_write_inquiry_scan_activity */
807 
808 /* Send Read_Authentication_Enable command to the unit */
809 static int
810 hci_read_authentication_enable(int s, int argc, char **argv)
811 {
812 	ng_hci_read_auth_enable_rp	rp;
813 	int				n;
814 
815 	n = sizeof(rp);
816 	if (hci_simple_request(s, NG_HCI_OPCODE(NG_HCI_OGF_HC_BASEBAND,
817 			NG_HCI_OCF_READ_AUTH_ENABLE),
818 			(char *) &rp, &n) == ERROR)
819 		return (ERROR);
820 
821 	if (rp.status != 0x00) {
822 		fprintf(stdout, "Status: %s [%#02x]\n",
823 			hci_status2str(rp.status), rp.status);
824 		return (FAILED);
825 	}
826 
827 	fprintf(stdout, "Authentication Enable: %s [%d]\n",
828 		rp.auth_enable? "Enabled" : "Disabled", rp.auth_enable);
829 
830 	return (OK);
831 } /* hci_read_authentication_enable */
832 
833 /* Send Write_Authentication_Enable command to the unit */
834 static int
835 hci_write_authentication_enable(int s, int argc, char **argv)
836 {
837 	ng_hci_write_auth_enable_cp	cp;
838 	ng_hci_write_auth_enable_rp	rp;
839 	int				n;
840 
841 	/* parse command parameters */
842 	switch (argc) {
843 	case 1:
844 		if (sscanf(argv[0], "%d", &n) != 1 || n < 0 || n > 1)
845 			return (USAGE);
846 
847 		cp.auth_enable = (uint8_t) n;
848 		break;
849 
850 	default:
851 		return (USAGE);
852 	}
853 
854 	/* send command */
855 	n = sizeof(rp);
856 	if (hci_request(s, NG_HCI_OPCODE(NG_HCI_OGF_HC_BASEBAND,
857 			NG_HCI_OCF_WRITE_AUTH_ENABLE),
858 			(char const *) &cp, sizeof(cp),
859 			(char *) &rp, &n) == ERROR)
860 		return (ERROR);
861 
862 	if (rp.status != 0x00) {
863 		fprintf(stdout, "Status: %s [%#02x]\n",
864 			hci_status2str(rp.status), rp.status);
865 		return (FAILED);
866 	}
867 
868 	return (OK);
869 } /* hci_write_authentication_enable */
870 
871 /* Send Read_Encryption_Mode command to the unit */
872 static int
873 hci_read_encryption_mode(int s, int argc, char **argv)
874 {
875 	ng_hci_read_encryption_mode_rp	rp;
876 	int				n;
877 
878 	n = sizeof(rp);
879 	if (hci_simple_request(s, NG_HCI_OPCODE(NG_HCI_OGF_HC_BASEBAND,
880 			NG_HCI_OCF_READ_ENCRYPTION_MODE),
881 			(char *) &rp, &n) == ERROR)
882 		return (ERROR);
883 
884 	if (rp.status != 0x00) {
885 		fprintf(stdout, "Status: %s [%#02x]\n",
886 			hci_status2str(rp.status), rp.status);
887 		return (FAILED);
888 	}
889 
890 	fprintf(stdout, "Encryption mode: %s [%#02x]\n",
891 		hci_encrypt2str(rp.encryption_mode, 0), rp.encryption_mode);
892 
893 	return (OK);
894 } /* hci_read_encryption_mode */
895 
896 /* Send Write_Encryption_Mode command to the unit */
897 static int
898 hci_write_encryption_mode(int s, int argc, char **argv)
899 {
900 	ng_hci_write_encryption_mode_cp	cp;
901 	ng_hci_write_encryption_mode_rp	rp;
902 	int				n;
903 
904 	/* parse command parameters */
905 	switch (argc) {
906 	case 1:
907 		if (sscanf(argv[0], "%d", &n) != 1 || n < 0 || n > 2)
908 			return (USAGE);
909 
910 		cp.encryption_mode = (uint8_t) n;
911 		break;
912 
913 	default:
914 		return (USAGE);
915 	}
916 
917 	/* send command */
918 	n = sizeof(rp);
919 	if (hci_request(s, NG_HCI_OPCODE(NG_HCI_OGF_HC_BASEBAND,
920 			NG_HCI_OCF_WRITE_ENCRYPTION_MODE),
921 			(char const *) &cp, sizeof(cp),
922 			(char *) &rp, &n) == ERROR)
923 		return (ERROR);
924 
925 	if (rp.status != 0x00) {
926 		fprintf(stdout, "Status: %s [%#02x]\n",
927 			hci_status2str(rp.status), rp.status);
928 		return (FAILED);
929 	}
930 
931 	return (OK);
932 } /* hci_write_encryption_mode */
933 
934 /* Send Read_Class_Of_Device command to the unit */
935 static int
936 hci_read_class_of_device(int s, int argc, char **argv)
937 {
938 	ng_hci_read_unit_class_rp	rp;
939 	int				n;
940 
941 	n = sizeof(rp);
942 	if (hci_simple_request(s, NG_HCI_OPCODE(NG_HCI_OGF_HC_BASEBAND,
943 			NG_HCI_OCF_READ_UNIT_CLASS),
944 			(char *) &rp, &n) == ERROR)
945 		return (ERROR);
946 
947 	if (rp.status != 0x00) {
948 		fprintf(stdout, "Status: %s [%#02x]\n",
949 			hci_status2str(rp.status), rp.status);
950 		return (FAILED);
951 	}
952 
953 	fprintf(stdout, "Class: %02x:%02x:%02x\n",
954 		rp.uclass[2], rp.uclass[1], rp.uclass[0]);
955 
956 	return (0);
957 } /* hci_read_class_of_device */
958 
959 /* Send Write_Class_Of_Device command to the unit */
960 static int
961 hci_write_class_of_device(int s, int argc, char **argv)
962 {
963 	ng_hci_write_unit_class_cp	cp;
964 	ng_hci_write_unit_class_rp	rp;
965 	int				n0, n1, n2;
966 
967 	/* parse command parameters */
968 	switch (argc) {
969 	case 1:
970 		if (sscanf(argv[0], "%x:%x:%x", &n2, &n1, &n0) != 3)
971 			return (USAGE);
972 
973 		cp.uclass[0] = (n0 & 0xff);
974 		cp.uclass[1] = (n1 & 0xff);
975 		cp.uclass[2] = (n2 & 0xff);
976 		break;
977 
978 	default:
979 		return (USAGE);
980 	}
981 
982 	/* send command */
983 	n0 = sizeof(rp);
984 	if (hci_request(s, NG_HCI_OPCODE(NG_HCI_OGF_HC_BASEBAND,
985 			NG_HCI_OCF_WRITE_UNIT_CLASS),
986 			(char const *) &cp, sizeof(cp),
987 			(char *) &rp, &n0) == ERROR)
988 		return (ERROR);
989 
990 	if (rp.status != 0x00) {
991 		fprintf(stdout, "Status: %s [%#02x]\n",
992 			hci_status2str(rp.status), rp.status);
993 		return (FAILED);
994 	}
995 
996 	return (OK);
997 } /* hci_write_class_of_device */
998 
999 /* Send Read_Voice_Settings command to the unit */
1000 static int
1001 hci_read_voice_settings(int s, int argc, char **argv)
1002 {
1003 	ng_hci_read_voice_settings_rp	rp;
1004 	int				n,
1005 					input_coding,
1006 					input_data_format,
1007 					input_sample_size;
1008 
1009 	n = sizeof(rp);
1010 	if (hci_simple_request(s, NG_HCI_OPCODE(NG_HCI_OGF_HC_BASEBAND,
1011 			NG_HCI_OCF_READ_VOICE_SETTINGS),
1012 			(char *) &rp, &n) == ERROR)
1013 		return (ERROR);
1014 
1015 	if (rp.status != 0x00) {
1016 		fprintf(stdout, "Status: %s [%#02x]\n",
1017 			hci_status2str(rp.status), rp.status);
1018 		return (FAILED);
1019 	}
1020 
1021 	rp.settings = le16toh(rp.settings);
1022 
1023 	input_coding      = (rp.settings & 0x0300) >> 8;
1024 	input_data_format = (rp.settings & 0x00c0) >> 6;
1025 	input_sample_size = (rp.settings & 0x0020) >> 5;
1026 
1027 	fprintf(stdout, "Voice settings: %#04x\n", rp.settings);
1028 	fprintf(stdout, "Input coding: %s [%d]\n",
1029 		hci_coding2str(input_coding), input_coding);
1030 	fprintf(stdout, "Input data format: %s [%d]\n",
1031 		hci_vdata2str(input_data_format), input_data_format);
1032 
1033 	if (input_coding == 0x00) /* Only for Linear PCM */
1034 		fprintf(stdout, "Input sample size: %d bit [%d]\n",
1035 			input_sample_size? 16 : 8, input_sample_size);
1036 
1037 	return (OK);
1038 } /* hci_read_voice_settings */
1039 
1040 /* Send Write_Voice_Settings command to the unit */
1041 static int
1042 hci_write_voice_settings(int s, int argc, char **argv)
1043 {
1044 	ng_hci_write_voice_settings_cp	cp;
1045 	ng_hci_write_voice_settings_rp	rp;
1046 	int				n;
1047 
1048 	/* parse command parameters */
1049 	switch (argc) {
1050 	case 1:
1051 		if (sscanf(argv[0], "%x", &n) != 1)
1052 			return (USAGE);
1053 
1054 		cp.settings = (uint16_t) n;
1055 		cp.settings = htole16(cp.settings);
1056 		break;
1057 
1058 	default:
1059 		return (USAGE);
1060 	}
1061 
1062 	/* send command */
1063 	n = sizeof(rp);
1064 	if (hci_request(s, NG_HCI_OPCODE(NG_HCI_OGF_HC_BASEBAND,
1065 			NG_HCI_OCF_WRITE_VOICE_SETTINGS),
1066 			(char const *) &cp, sizeof(cp),
1067 			(char *) &rp, &n) == ERROR)
1068 		return (ERROR);
1069 
1070 	if (rp.status != 0x00) {
1071 		fprintf(stdout, "Status: %s [%#02x]\n",
1072 			hci_status2str(rp.status), rp.status);
1073 		return (FAILED);
1074 	}
1075 
1076 	return (OK);
1077 } /* hci_write_voice_settings */
1078 
1079 /* Send Read_Number_Broadcast_Restransmissions */
1080 static int
1081 hci_read_number_broadcast_retransmissions(int s, int argc, char **argv)
1082 {
1083 	ng_hci_read_num_broadcast_retrans_rp	rp;
1084 	int					n;
1085 
1086 	n = sizeof(rp);
1087 	if (hci_simple_request(s, NG_HCI_OPCODE(NG_HCI_OGF_HC_BASEBAND,
1088 			NG_HCI_OCF_READ_NUM_BROADCAST_RETRANS),
1089 			(char *) &rp, &n) == ERROR)
1090 		return (ERROR);
1091 
1092 	if (rp.status != 0x00) {
1093 		fprintf(stdout, "Status: %s [%#02x]\n",
1094 			hci_status2str(rp.status), rp.status);
1095 		return (FAILED);
1096 	}
1097 
1098 	fprintf(stdout, "Number of broadcast retransmissions: %d\n",
1099 		rp.counter);
1100 
1101 	return (OK);
1102 } /* hci_read_number_broadcast_retransmissions */
1103 
1104 /* Send Write_Number_Broadcast_Restransmissions */
1105 static int
1106 hci_write_number_broadcast_retransmissions(int s, int argc, char **argv)
1107 {
1108 	ng_hci_write_num_broadcast_retrans_cp	cp;
1109 	ng_hci_write_num_broadcast_retrans_rp	rp;
1110 	int					n;
1111 
1112 	/* parse command parameters */
1113 	switch (argc) {
1114 	case 1:
1115 		if (sscanf(argv[0], "%d", &n) != 1 || n < 0 || n > 0xff)
1116 			return (USAGE);
1117 
1118 		cp.counter = (uint8_t) n;
1119 		break;
1120 
1121 	default:
1122 		return (USAGE);
1123 	}
1124 
1125 	/* send command */
1126 	n = sizeof(rp);
1127 	if (hci_request(s, NG_HCI_OPCODE(NG_HCI_OGF_HC_BASEBAND,
1128 			NG_HCI_OCF_WRITE_NUM_BROADCAST_RETRANS),
1129 			(char const *) &cp, sizeof(cp),
1130 			(char *) &rp, &n) == ERROR)
1131 		return (ERROR);
1132 
1133 	if (rp.status != 0x00) {
1134 		fprintf(stdout, "Status: %s [%#02x]\n",
1135 			hci_status2str(rp.status), rp.status);
1136 		return (FAILED);
1137 	}
1138 
1139 	return (OK);
1140 } /* hci_write_number_broadcast_retransmissions */
1141 
1142 /* Send Read_Hold_Mode_Activity command to the unit */
1143 static int
1144 hci_read_hold_mode_activity(int s, int argc, char **argv)
1145 {
1146 	ng_hci_read_hold_mode_activity_rp	rp;
1147 	int					n;
1148 	char					buffer[1024];
1149 
1150 	n = sizeof(rp);
1151 	if (hci_simple_request(s, NG_HCI_OPCODE(NG_HCI_OGF_HC_BASEBAND,
1152 			NG_HCI_OCF_READ_HOLD_MODE_ACTIVITY),
1153 			(char *) &rp, &n) == ERROR)
1154 		return (ERROR);
1155 
1156 	if (rp.status != 0x00) {
1157 		fprintf(stdout, "Status: %s [%#02x]\n",
1158 			hci_status2str(rp.status), rp.status);
1159 		return (FAILED);
1160 	}
1161 
1162 	fprintf(stdout, "Hold Mode Activities: %#02x\n", rp.hold_mode_activity);
1163 	if (rp.hold_mode_activity == 0)
1164 		fprintf(stdout, "Maintain current Power State");
1165 	else
1166 		fprintf(stdout, "%s", hci_hmode2str(rp.hold_mode_activity,
1167 				buffer, sizeof(buffer)));
1168 
1169 	fprintf(stdout, "\n");
1170 
1171 	return (OK);
1172 } /* hci_read_hold_mode_activity */
1173 
1174 /* Send Write_Hold_Mode_Activity command to the unit */
1175 static int
1176 hci_write_hold_mode_activity(int s, int argc, char **argv)
1177 {
1178 	ng_hci_write_hold_mode_activity_cp	cp;
1179 	ng_hci_write_hold_mode_activity_rp	rp;
1180 	int					n;
1181 
1182 	/* parse command parameters */
1183 	switch (argc) {
1184 	case 1:
1185 		if (sscanf(argv[0], "%d", &n) != 1 || n < 0 || n > 4)
1186 			return (USAGE);
1187 
1188 		cp.hold_mode_activity = (uint8_t) n;
1189 		break;
1190 
1191 	default:
1192 		return (USAGE);
1193 	}
1194 
1195 	/* send command */
1196 	n = sizeof(rp);
1197 	if (hci_request(s, NG_HCI_OPCODE(NG_HCI_OGF_HC_BASEBAND,
1198 			NG_HCI_OCF_WRITE_HOLD_MODE_ACTIVITY),
1199 			(char const *) &cp, sizeof(cp),
1200 			(char *) &rp, &n) == ERROR)
1201 		return (ERROR);
1202 
1203 	if (rp.status != 0x00) {
1204 		fprintf(stdout, "Status: %s [%#02x]\n",
1205 			hci_status2str(rp.status), rp.status);
1206 		return (FAILED);
1207 	}
1208 
1209 	return (OK);
1210 } /* hci_write_hold_mode_activity */
1211 
1212 /* Send Read_SCO_Flow_Control_Enable command to the unit */
1213 static int
1214 hci_read_sco_flow_control_enable(int s, int argc, char **argv)
1215 {
1216 	ng_hci_read_sco_flow_control_rp	rp;
1217 	int				n;
1218 
1219 	n = sizeof(rp);
1220 	if (hci_simple_request(s, NG_HCI_OPCODE(NG_HCI_OGF_HC_BASEBAND,
1221 			NG_HCI_OCF_READ_SCO_FLOW_CONTROL),
1222 			(char *) &rp, &n) == ERROR)
1223 		return (ERROR);
1224 
1225 	if (rp.status != 0x00) {
1226 		fprintf(stdout, "Status: %s [%#02x]\n",
1227 			hci_status2str(rp.status), rp.status);
1228 		return (FAILED);
1229 	}
1230 
1231 	fprintf(stdout, "SCO flow control %s [%d]\n",
1232 		rp.flow_control? "enabled" : "disabled", rp.flow_control);
1233 
1234 	return (OK);
1235 } /* hci_read_sco_flow_control_enable */
1236 
1237 /* Send Write_SCO_Flow_Control_Enable command to the unit */
1238 static int
1239 hci_write_sco_flow_control_enable(int s, int argc, char **argv)
1240 {
1241 	ng_hci_write_sco_flow_control_cp	cp;
1242 	ng_hci_write_sco_flow_control_rp	rp;
1243 	int					n;
1244 
1245 	/* parse command parameters */
1246 	switch (argc) {
1247 	case 1:
1248 		if (sscanf(argv[0], "%d", &n) != 1 || n < 0 || n > 1)
1249 			return (USAGE);
1250 
1251 		cp.flow_control = (uint8_t) n;
1252 		break;
1253 
1254 	default:
1255 		return (USAGE);
1256 	}
1257 
1258 	/* send command */
1259 	n = sizeof(rp);
1260 	if (hci_request(s, NG_HCI_OPCODE(NG_HCI_OGF_HC_BASEBAND,
1261 			NG_HCI_OCF_WRITE_SCO_FLOW_CONTROL),
1262 			(char const *) &cp, sizeof(cp),
1263 			(char *) &rp, &n) == ERROR)
1264 		return (ERROR);
1265 
1266 	if (rp.status != 0x00) {
1267 		fprintf(stdout, "Status: %s [%#02x]\n",
1268 			hci_status2str(rp.status), rp.status);
1269 		return (FAILED);
1270 	}
1271 
1272 	return (OK);
1273 } /* hci_write_sco_flow_control_enable */
1274 
1275 /* Send Read_Link_Supervision_Timeout command to the unit */
1276 static int
1277 hci_read_link_supervision_timeout(int s, int argc, char **argv)
1278 {
1279 	ng_hci_read_link_supervision_timo_cp	cp;
1280 	ng_hci_read_link_supervision_timo_rp	rp;
1281 	int					n;
1282 
1283 	switch (argc) {
1284 	case 1:
1285 		/* connection handle */
1286 		if (sscanf(argv[0], "%d", &n) != 1 || n <= 0 || n > 0x0eff)
1287 			return (USAGE);
1288 
1289 		cp.con_handle = (uint16_t) (n & 0x0fff);
1290 		cp.con_handle = htole16(cp.con_handle);
1291 		break;
1292 
1293 	default:
1294 		return (USAGE);
1295 	}
1296 
1297 	/* send command */
1298 	n = sizeof(rp);
1299 	if (hci_request(s, NG_HCI_OPCODE(NG_HCI_OGF_HC_BASEBAND,
1300 			NG_HCI_OCF_READ_LINK_SUPERVISION_TIMO),
1301 			(char const *) &cp, sizeof(cp),
1302 			(char *) &rp, &n) == ERROR)
1303 		return (ERROR);
1304 
1305 	if (rp.status != 0x00) {
1306 		fprintf(stdout, "Status: %s [%#02x]\n",
1307 			hci_status2str(rp.status), rp.status);
1308 		return (FAILED);
1309 	}
1310 
1311 	rp.timeout = le16toh(rp.timeout);
1312 
1313 	fprintf(stdout, "Connection handle: %d\n", le16toh(rp.con_handle));
1314 	fprintf(stdout, "Link supervision timeout: %.2f msec [%d slots]\n",
1315 		rp.timeout * 0.625, rp.timeout);
1316 
1317 	return (OK);
1318 } /* hci_read_link_supervision_timeout */
1319 
1320 /* Send Write_Link_Supervision_Timeout command to the unit */
1321 static int
1322 hci_write_link_supervision_timeout(int s, int argc, char **argv)
1323 {
1324 	ng_hci_write_link_supervision_timo_cp	cp;
1325 	ng_hci_write_link_supervision_timo_rp	rp;
1326 	int					n;
1327 
1328 	switch (argc) {
1329 	case 2:
1330 		/* connection handle */
1331 		if (sscanf(argv[0], "%d", &n) != 1 || n <= 0 || n > 0x0eff)
1332 			return (USAGE);
1333 
1334 		cp.con_handle = (uint16_t) (n & 0x0fff);
1335 		cp.con_handle = htole16(cp.con_handle);
1336 
1337 		/* link supervision timeout */
1338 		if (sscanf(argv[1], "%d", &n) != 1 || n < 0 || n > 0xffff)
1339 			return (USAGE);
1340 
1341 		cp.timeout = (uint16_t) (n & 0x0fff);
1342 		cp.timeout = htole16(cp.timeout);
1343 		break;
1344 
1345 	default:
1346 		return (USAGE);
1347 	}
1348 
1349 	/* send command */
1350 	n = sizeof(rp);
1351 	if (hci_request(s, NG_HCI_OPCODE(NG_HCI_OGF_HC_BASEBAND,
1352 			NG_HCI_OCF_WRITE_LINK_SUPERVISION_TIMO),
1353 			(char const *) &cp, sizeof(cp),
1354 			(char *) &rp, &n) == ERROR)
1355 		return (ERROR);
1356 
1357 	if (rp.status != 0x00) {
1358 		fprintf(stdout, "Status: %s [%#02x]\n",
1359 			hci_status2str(rp.status), rp.status);
1360 		return (FAILED);
1361 	}
1362 
1363 	return (OK);
1364 } /* hci_write_link_supervision_timeout */
1365 
1366 /* Send Read_Page_Scan_Period_Mode command to the unit */
1367 static int
1368 hci_read_page_scan_period_mode(int s, int argc, char **argv)
1369 {
1370 	ng_hci_read_page_scan_period_rp	rp;
1371 	int				n;
1372 
1373 	n = sizeof(rp);
1374 	if (hci_simple_request(s, NG_HCI_OPCODE(NG_HCI_OGF_HC_BASEBAND,
1375 			NG_HCI_OCF_READ_PAGE_SCAN_PERIOD),
1376 			(char *) &rp, &n) == ERROR)
1377 		return (ERROR);
1378 
1379 	if (rp.status != 0x00) {
1380 		fprintf(stdout, "Status: %s [%#02x]\n",
1381 			hci_status2str(rp.status), rp.status);
1382 		return (FAILED);
1383 	}
1384 
1385 	fprintf(stdout, "Page scan period mode: %#02x\n",
1386 		rp.page_scan_period_mode);
1387 
1388 	return (OK);
1389 } /* hci_read_page_scan_period_mode */
1390 
1391 /* Send Write_Page_Scan_Period_Mode command to the unit */
1392 static int
1393 hci_write_page_scan_period_mode(int s, int argc, char **argv)
1394 {
1395 	ng_hci_write_page_scan_period_cp	cp;
1396 	ng_hci_write_page_scan_period_rp	rp;
1397 	int					n;
1398 
1399 	/* parse command arguments */
1400 	switch (argc) {
1401 	case 1:
1402 		if (sscanf(argv[0], "%d", &n) != 1 || n < 0 || n > 2)
1403 			return (USAGE);
1404 
1405 		cp.page_scan_period_mode = (n & 0xff);
1406 		break;
1407 
1408 	default:
1409 		return (USAGE);
1410 	}
1411 
1412 	/* send command */
1413 	n = sizeof(rp);
1414 	if (hci_request(s, NG_HCI_OPCODE(NG_HCI_OGF_HC_BASEBAND,
1415 			NG_HCI_OCF_WRITE_PAGE_SCAN_PERIOD),
1416 			(char const *) &cp, sizeof(cp),
1417 			(char *) &rp, &n) == ERROR)
1418 		return (ERROR);
1419 
1420 	if (rp.status != 0x00) {
1421 		fprintf(stdout, "Status: %s [%#02x]\n",
1422 			hci_status2str(rp.status), rp.status);
1423 		return (FAILED);
1424 	}
1425 
1426 	return (OK);
1427 } /* hci_write_page_scan_period_mode */
1428 
1429 /* Send Read_Page_Scan_Mode command to the unit */
1430 static int
1431 hci_read_page_scan_mode(int s, int argc, char **argv)
1432 {
1433 	ng_hci_read_page_scan_rp	rp;
1434 	int				n;
1435 
1436 	n = sizeof(rp);
1437 	if (hci_simple_request(s, NG_HCI_OPCODE(NG_HCI_OGF_HC_BASEBAND,
1438 			NG_HCI_OCF_READ_PAGE_SCAN),
1439 			(char *) &rp, &n) == ERROR)
1440 		return (ERROR);
1441 
1442 	if (rp.status != 0x00) {
1443 		fprintf(stdout, "Status: %s [%#02x]\n",
1444 			hci_status2str(rp.status), rp.status);
1445 		return (FAILED);
1446 	}
1447 
1448 	fprintf(stdout, "Page scan mode: %#02x\n", rp.page_scan_mode);
1449 
1450 	return (OK);
1451 } /* hci_read_page_scan_mode */
1452 
1453 /* Send Write_Page_Scan_Mode command to the unit */
1454 static int
1455 hci_write_page_scan_mode(int s, int argc, char **argv)
1456 {
1457 	ng_hci_write_page_scan_cp	cp;
1458 	ng_hci_write_page_scan_rp	rp;
1459 	int				n;
1460 
1461 	/* parse command arguments */
1462 	switch (argc) {
1463 	case 1:
1464 		if (sscanf(argv[0], "%d", &n) != 1 || n < 0 || n > 3)
1465 			return (USAGE);
1466 
1467 		cp.page_scan_mode = (n & 0xff);
1468 		break;
1469 
1470 	default:
1471 		return (USAGE);
1472 	}
1473 
1474 	/* send command */
1475 	n = sizeof(rp);
1476 	if (hci_request(s, NG_HCI_OPCODE(NG_HCI_OGF_HC_BASEBAND,
1477 			NG_HCI_OCF_WRITE_PAGE_SCAN),
1478 			(char const *) &cp, sizeof(cp),
1479 			(char *) &rp, &n) == ERROR)
1480 		return (ERROR);
1481 
1482 	if (rp.status != 0x00) {
1483 		fprintf(stdout, "Status: %s [%#02x]\n",
1484 			hci_status2str(rp.status), rp.status);
1485 		return (FAILED);
1486 	}
1487 
1488 	return (OK);
1489 } /* hci_write_page_scan_mode */
1490 
1491 static int
1492 hci_read_le_host_supported_command(int s, int argc, char **argv)
1493 {
1494 	ng_hci_read_le_host_supported_rp rp;
1495 	int n;
1496 	n = sizeof(rp);
1497 	if (hci_simple_request(s, NG_HCI_OPCODE(NG_HCI_OGF_HC_BASEBAND,
1498 			NG_HCI_OCF_READ_LE_HOST_SUPPORTED),
1499 			(char *) &rp, &n) == ERROR)
1500 		return (ERROR);
1501 
1502 	if (rp.status != 0x00) {
1503 		fprintf(stdout, "Status: %s [%#02x]\n",
1504 			hci_status2str(rp.status), rp.status);
1505 		return (FAILED);
1506 	}
1507 
1508 	fprintf(stdout, "LE Host support: %#02x\n", rp.le_supported_host);
1509 	fprintf(stdout, "Simulateneouse LE Host : %#02x\n", rp.simultaneous_le_host);
1510 
1511 	return (OK);
1512 
1513 }
1514 static int
1515 hci_write_le_host_supported_command(int s, int argc, char **argv)
1516 {
1517 	ng_hci_write_le_host_supported_cp cp;
1518 	ng_hci_write_le_host_supported_rp rp;
1519 
1520 	int n;
1521 
1522 	cp.le_supported_host = 0;
1523 	cp.simultaneous_le_host = 0;
1524 	switch (argc) {
1525 	case 2:
1526 		if (sscanf(argv[1], "%d", &n) != 1 || (n != 0 && n != 1)){
1527 			printf("ARGC2: %d\n", n);
1528 			return (USAGE);
1529 		}
1530 		cp.simultaneous_le_host = (n &1);
1531 
1532 	case 1:
1533 		if (sscanf(argv[0], "%d", &n) != 1 || (n != 0 && n != 1)){
1534 			printf("ARGC1: %d\n", n);
1535 			return (USAGE);
1536 		}
1537 
1538 		cp.le_supported_host = (n &1);
1539 		break;
1540 
1541 	default:
1542 		return (USAGE);
1543 	}
1544 
1545 
1546 	/* send command */
1547 	n = sizeof(rp);
1548 	if (hci_request(s, NG_HCI_OPCODE(NG_HCI_OGF_HC_BASEBAND,
1549 			NG_HCI_OCF_WRITE_LE_HOST_SUPPORTED),
1550 			(char const *) &cp, sizeof(cp),
1551 			(char *) &rp, &n) == ERROR)
1552 		return (ERROR);
1553 
1554 	if (rp.status != 0x00) {
1555 		fprintf(stdout, "Status: %s [%#02x]\n",
1556 			hci_status2str(rp.status), rp.status);
1557 		return (FAILED);
1558 	}
1559 
1560 	return (OK);
1561 }
1562 
1563 struct hci_command	host_controller_baseband_commands[] = {
1564 {
1565 "reset",
1566 "\nThe Reset command will reset the Host Controller and the Link Manager.\n" \
1567 "After the reset is completed, the current operational state will be lost,\n" \
1568 "the Bluetooth unit will enter standby mode and the Host Controller will\n" \
1569 "automatically revert to the default values for the parameters for which\n" \
1570 "default values are defined in the specification.",
1571 &hci_reset
1572 },
1573 {
1574 "read_pin_type",
1575 "\nThe Read_PIN_Type command is used for the Host to read whether the Link\n" \
1576 "Manager assumes that the Host supports variable PIN codes only a fixed PIN\n" \
1577 "code.",
1578 &hci_read_pin_type
1579 },
1580 {
1581 "write_pin_type <pin_type>",
1582 "\nThe Write_PIN_Type command is used for the Host to write to the Host\n" \
1583 "Controller whether the Host supports variable PIN codes or only a fixed PIN\n"\
1584 "code.\n\n" \
1585 "\t<pin_type> - dd; 0 - Variable; 1 - Fixed",
1586 &hci_write_pin_type
1587 },
1588 {
1589 "read_stored_link_key [<BD_ADDR>]",
1590 "\nThe Read_Stored_Link_Key command provides the ability to read one or\n" \
1591 "more link keys stored in the Bluetooth Host Controller. The Bluetooth Host\n" \
1592 "Controller can store a limited number of link keys for other Bluetooth\n" \
1593 "devices.\n\n" \
1594 "\t<BD_ADDR> - xx:xx:xx:xx:xx:xx BD_ADDR or name",
1595 &hci_read_stored_link_key
1596 },
1597 {
1598 "write_stored_link_key <BD_ADDR> <key>",
1599 "\nThe Write_Stored_Link_Key command provides the ability to write one\n" \
1600 "or more link keys to be stored in the Bluetooth Host Controller. The\n" \
1601 "Bluetooth Host Controller can store a limited number of link keys for other\n"\
1602 "Bluetooth devices. If no additional space is available in the Bluetooth\n"\
1603 "Host Controller then no additional link keys will be stored.\n\n" \
1604 "\t<BD_ADDR> - xx:xx:xx:xx:xx:xx BD_ADDR or name\n" \
1605 "\t<key>     - xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx up to 16 bytes link key",
1606 &hci_write_stored_link_key
1607 },
1608 {
1609 "delete_stored_link_key [<BD_ADDR>]",
1610 "\nThe Delete_Stored_Link_Key command provides the ability to remove one\n" \
1611 "or more of the link keys stored in the Bluetooth Host Controller. The\n" \
1612 "Bluetooth Host Controller can store a limited number of link keys for other\n"\
1613 "Bluetooth devices.\n\n" \
1614 "\t<BD_ADDR> - xx:xx:xx:xx:xx:xx BD_ADDR or name",
1615 &hci_delete_stored_link_key
1616 },
1617 {
1618 "change_local_name <name>",
1619 "\nThe Change_Local_Name command provides the ability to modify the user\n" \
1620 "friendly name for the Bluetooth unit.\n\n" \
1621 "\t<name> - string",
1622 &hci_change_local_name
1623 },
1624 {
1625 "read_local_name",
1626 "\nThe Read_Local_Name command provides the ability to read the\n" \
1627 "stored user-friendly name for the Bluetooth unit.",
1628 &hci_read_local_name
1629 },
1630 {
1631 "read_connection_accept_timeout",
1632 "\nThis command will read the value for the Connection_Accept_Timeout\n" \
1633 "configuration parameter. The Connection_Accept_Timeout configuration\n" \
1634 "parameter allows the Bluetooth hardware to automatically deny a\n" \
1635 "connection request after a specified time period has occurred and\n" \
1636 "the new connection is not accepted. Connection Accept Timeout\n" \
1637 "measured in Number of Baseband slots.",
1638 &hci_read_connection_accept_timeout
1639 },
1640 {
1641 "write_connection_accept_timeout <timeout>",
1642 "\nThis command will write the value for the Connection_Accept_Timeout\n" \
1643 "configuration parameter.\n\n" \
1644 "\t<timeout> - dddd; measured in number of baseband slots.",
1645 &hci_write_connection_accept_timeout
1646 },
1647 {
1648 "read_page_timeout",
1649 "\nThis command will read the value for the Page_Timeout configuration\n" \
1650 "parameter. The Page_Timeout configuration parameter defines the\n" \
1651 "maximum time the local Link Manager will wait for a baseband page\n" \
1652 "response from the remote unit at a locally initiated connection\n" \
1653 "attempt. Page Timeout measured in Number of Baseband slots.",
1654 &hci_read_page_timeout
1655 },
1656 {
1657 "write_page_timeout <timeout>",
1658 "\nThis command will write the value for the Page_Timeout configuration\n" \
1659 "parameter.\n\n" \
1660 "\t<timeout> - dddd; measured in number of baseband slots.",
1661 &hci_write_page_timeout
1662 },
1663 {
1664 "read_scan_enable",
1665 "\nThis command will read the value for the Scan_Enable parameter. The\n" \
1666 "Scan_Enable parameter controls whether or not the Bluetooth uint\n" \
1667 "will periodically scan for page attempts and/or inquiry requests\n" \
1668 "from other Bluetooth unit.\n\n" \
1669 "\t0x00 - No Scans enabled.\n" \
1670 "\t0x01 - Inquiry Scan enabled. Page Scan disabled.\n" \
1671 "\t0x02 - Inquiry Scan disabled. Page Scan enabled.\n" \
1672 "\t0x03 - Inquiry Scan enabled. Page Scan enabled.",
1673 &hci_read_scan_enable
1674 },
1675 {
1676 "write_scan_enable <scan_enable>",
1677 "\nThis command will write the value for the Scan_Enable parameter.\n" \
1678 "The Scan_Enable parameter controls whether or not the Bluetooth\n" \
1679 "unit will periodically scan for page attempts and/or inquiry\n" \
1680 "requests from other Bluetooth unit.\n\n" \
1681 "\t<scan_enable> - dd;\n" \
1682 "\t0 - No Scans enabled.\n" \
1683 "\t1 - Inquiry Scan enabled. Page Scan disabled.\n" \
1684 "\t2 - Inquiry Scan disabled. Page Scan enabled.\n" \
1685 "\t3 - Inquiry Scan enabled. Page Scan enabled.",
1686 &hci_write_scan_enable
1687 },
1688 {
1689 "read_page_scan_activity",
1690 "\nThis command will read the value for Page_Scan_Activity configuration\n" \
1691 "parameters. The Page_Scan_Interval configuration parameter defines the\n" \
1692 "amount of time between consecutive page scans. This time interval is \n" \
1693 "defined from when the Host Controller started its last page scan until\n" \
1694 "it begins the next page scan. The Page_Scan_Window configuration parameter\n" \
1695 "defines the amount of time for the duration of the page scan. The\n" \
1696 "Page_Scan_Window can only be less than or equal to the Page_Scan_Interval.",
1697 &hci_read_page_scan_activity
1698 },
1699 {
1700 "write_page_scan_activity interval(dddd) window(dddd)",
1701 "\nThis command will write the value for Page_Scan_Activity configuration\n" \
1702 "parameter. The Page_Scan_Interval configuration parameter defines the\n" \
1703 "amount of time between consecutive page scans. This is defined as the time\n" \
1704 "interval from when the Host Controller started its last page scan until it\n" \
1705 "begins the next page scan. The Page_Scan_Window configuration parameter\n" \
1706 "defines the amount of time for the duration of the page scan. \n" \
1707 "The Page_Scan_Window can only be less than or equal to the Page_Scan_Interval.\n\n" \
1708 "\t<interval> - Range: 0x0012 -- 0x100, Time = N * 0.625 msec\n" \
1709 "\t<window>   - Range: 0x0012 -- 0x100, Time = N * 0.625 msec",
1710 &hci_write_page_scan_activity
1711 },
1712 {
1713 "read_inquiry_scan_activity",
1714 "\nThis command will read the value for Inquiry_Scan_Activity configuration\n" \
1715 "parameter. The Inquiry_Scan_Interval configuration parameter defines the\n" \
1716 "amount of time between consecutive inquiry scans. This is defined as the\n" \
1717 "time interval from when the Host Controller started its last inquiry scan\n" \
1718 "until it begins the next inquiry scan.",
1719 &hci_read_inquiry_scan_activity
1720 },
1721 {
1722 "write_inquiry_scan_activity interval(dddd) window(dddd)",
1723 "\nThis command will write the value for Inquiry_Scan_Activity configuration\n"\
1724 "parameter. The Inquiry_Scan_Interval configuration parameter defines the\n" \
1725 "amount of time between consecutive inquiry scans. This is defined as the\n" \
1726 "time interval from when the Host Controller started its last inquiry scan\n" \
1727 "until it begins the next inquiry scan. The Inquiry_Scan_Window configuration\n" \
1728 "parameter defines the amount of time for the duration of the inquiry scan.\n" \
1729 "The Inquiry_Scan_Window can only be less than or equal to the Inquiry_Scan_Interval.\n\n" \
1730 "\t<interval> - Range: 0x0012 -- 0x100, Time = N * 0.625 msec\n" \
1731 "\t<window>   - Range: 0x0012 -- 0x100, Time = N * 0.625 msec",
1732 &hci_write_inquiry_scan_activity
1733 },
1734 {
1735 "read_authentication_enable",
1736 "\nThis command will read the value for the Authentication_Enable parameter.\n"\
1737 "The Authentication_Enable parameter controls if the local unit requires\n"\
1738 "to authenticate the remote unit at connection setup (between the\n" \
1739 "Create_Connection command or acceptance of an incoming ACL connection\n"\
1740 "and the corresponding Connection Complete event). At connection setup, only\n"\
1741 "the unit(s) with the Authentication_Enable parameter enabled will try to\n"\
1742 "authenticate the other unit.",
1743 &hci_read_authentication_enable
1744 },
1745 {
1746 "write_authentication_enable enable(0|1)",
1747 "\nThis command will write the value for the Authentication_Enable parameter.\n"\
1748 "The Authentication_Enable parameter controls if the local unit requires to\n"\
1749 "authenticate the remote unit at connection setup (between the\n" \
1750 "Create_Connection command or acceptance of an incoming ACL connection\n" \
1751 "and the corresponding Connection Complete event). At connection setup, only\n"\
1752 "the unit(s) with the Authentication_Enable parameter enabled will try to\n"\
1753 "authenticate the other unit.",
1754 &hci_write_authentication_enable
1755 },
1756 {
1757 "read_encryption_mode",
1758 "\nThis command will read the value for the Encryption_Mode parameter. The\n" \
1759 "Encryption_Mode parameter controls if the local unit requires encryption\n" \
1760 "to the remote unit at connection setup (between the Create_Connection\n" \
1761 "command or acceptance of an incoming ACL connection and the corresponding\n" \
1762 "Connection Complete event). At connection setup, only the unit(s) with\n" \
1763 "the Authentication_Enable parameter enabled and Encryption_Mode parameter\n" \
1764 "enabled will try to encrypt the connection to the other unit.\n\n" \
1765 "\t<encryption_mode>:\n" \
1766 "\t0x00 - Encryption disabled.\n" \
1767 "\t0x01 - Encryption only for point-to-point packets.\n" \
1768 "\t0x02 - Encryption for both point-to-point and broadcast packets.",
1769 &hci_read_encryption_mode
1770 },
1771 {
1772 "write_encryption_mode mode(0|1|2)",
1773 "\tThis command will write the value for the Encryption_Mode parameter.\n" \
1774 "The Encryption_Mode parameter controls if the local unit requires\n" \
1775 "encryption to the remote unit at connection setup (between the\n" \
1776 "Create_Connection command or acceptance of an incoming ACL connection\n" \
1777 "and the corresponding Connection Complete event). At connection setup,\n" \
1778 "only the unit(s) with the Authentication_Enable parameter enabled and\n" \
1779 "Encryption_Mode parameter enabled will try to encrypt the connection to\n" \
1780 "the other unit.\n\n" \
1781 "\t<encryption_mode> (dd)\n" \
1782 "\t0 - Encryption disabled.\n" \
1783 "\t1 - Encryption only for point-to-point packets.\n" \
1784 "\t2 - Encryption for both point-to-point and broadcast packets.",
1785 &hci_write_encryption_mode
1786 },
1787 {
1788 "read_class_of_device",
1789 "\nThis command will read the value for the Class_of_Device parameter.\n" \
1790 "The Class_of_Device parameter is used to indicate the capabilities of\n" \
1791 "the local unit to other units.",
1792 &hci_read_class_of_device
1793 },
1794 {
1795 "write_class_of_device class(xx:xx:xx)",
1796 "\nThis command will write the value for the Class_of_Device parameter.\n" \
1797 "The Class_of_Device parameter is used to indicate the capabilities of \n" \
1798 "the local unit to other units.\n\n" \
1799 "\t<class> (xx:xx:xx) - class of device",
1800 &hci_write_class_of_device
1801 },
1802 {
1803 "read_voice_settings",
1804 "\nThis command will read the values for the Voice_Setting parameter.\n" \
1805 "The Voice_Setting parameter controls all the various settings for voice\n" \
1806 "connections. These settings apply to all voice connections, and cannot be\n" \
1807 "set for individual voice connections. The Voice_Setting parameter controls\n" \
1808 "the configuration for voice connections: Input Coding, Air coding format,\n" \
1809 "input data format, Input sample size, and linear PCM parameter.",
1810 &hci_read_voice_settings
1811 },
1812 {
1813 "write_voice_settings settings(xxxx)",
1814 "\nThis command will write the values for the Voice_Setting parameter.\n" \
1815 "The Voice_Setting parameter controls all the various settings for voice\n" \
1816 "connections. These settings apply to all voice connections, and cannot be\n" \
1817 "set for individual voice connections. The Voice_Setting parameter controls\n" \
1818 "the configuration for voice connections: Input Coding, Air coding format,\n" \
1819 "input data format, Input sample size, and linear PCM parameter.\n\n" \
1820 "\t<voice_settings> (xxxx) - voice settings",
1821 &hci_write_voice_settings
1822 },
1823 {
1824 "read_number_broadcast_retransmissions",
1825 "\nThis command will read the unit's parameter value for the Number of\n" \
1826 "Broadcast Retransmissions. Broadcast packets are not acknowledged and are\n" \
1827 "unreliable.",
1828 &hci_read_number_broadcast_retransmissions
1829 },
1830 {
1831 "write_number_broadcast_retransmissions count(dd)",
1832 "\nThis command will write the unit's parameter value for the Number of\n" \
1833 "Broadcast Retransmissions. Broadcast packets are not acknowledged and are\n" \
1834 "unreliable.\n\n" \
1835 "\t<count> (dd) - number of broadcast retransimissions",
1836 &hci_write_number_broadcast_retransmissions
1837 },
1838 {
1839 "read_hold_mode_activity",
1840 "\nThis command will read the value for the Hold_Mode_Activity parameter.\n" \
1841 "The Hold_Mode_Activity value is used to determine what activities should\n" \
1842 "be suspended when the unit is in hold mode.",
1843 &hci_read_hold_mode_activity
1844 },
1845 {
1846 "write_hold_mode_activity settings(0|1|2|4)",
1847 "\nThis command will write the value for the Hold_Mode_Activity parameter.\n" \
1848 "The Hold_Mode_Activity value is used to determine what activities should\n" \
1849 "be suspended when the unit is in hold mode.\n\n" \
1850 "\t<settings> (dd) - bit mask:\n" \
1851 "\t0 - Maintain current Power State. Default\n" \
1852 "\t1 - Suspend Page Scan.\n" \
1853 "\t2 - Suspend Inquiry Scan.\n" \
1854 "\t4 - Suspend Periodic Inquiries.",
1855 &hci_write_hold_mode_activity
1856 },
1857 {
1858 "read_sco_flow_control_enable",
1859 "\nThe Read_SCO_Flow_Control_Enable command provides the ability to read\n" \
1860 "the SCO_Flow_Control_Enable setting. By using this setting, the Host can\n" \
1861 "decide if the Host Controller will send Number Of Completed Packets events\n" \
1862 "for SCO Connection Handles. This setting allows the Host to enable and\n" \
1863 "disable SCO flow control.",
1864 &hci_read_sco_flow_control_enable
1865 },
1866 {
1867 "write_sco_flow_control_enable enable(0|1)",
1868 "\nThe Write_SCO_Flow_Control_Enable command provides the ability to write\n" \
1869 "the SCO_Flow_Control_Enable setting. By using this setting, the Host can\n" \
1870 "decide if the Host Controller will send Number Of Completed Packets events\n" \
1871 "for SCO Connection Handles. This setting allows the Host to enable and\n" \
1872 "disable SCO flow control. The SCO_Flow_Control_Enable setting can only be\n" \
1873 "changed if no connections exist.",
1874 &hci_write_sco_flow_control_enable
1875 },
1876 {
1877 "read_link_supervision_timeout <connection_handle>",
1878 "\nThis command will read the value for the Link_Supervision_Timeout\n" \
1879 "parameter for the device. The Link_Supervision_Timeout parameter is used\n" \
1880 "by the master or slave Bluetooth device to monitor link loss. If, for any\n" \
1881 "reason, no Baseband packets are received from that Connection Handle for a\n" \
1882 "duration longer than the Link_Supervision_Timeout, the connection is\n"
1883 "disconnected.\n\n" \
1884 "\t<connection_handle> - dddd; connection handle\n",
1885 &hci_read_link_supervision_timeout
1886 },
1887 {
1888 "write_link_supervision_timeout <connection_handle> <timeout>",
1889 "\nThis command will write the value for the Link_Supervision_Timeout\n" \
1890 "parameter for the device. The Link_Supervision_Timeout parameter is used\n" \
1891 "by the master or slave Bluetooth device to monitor link loss. If, for any\n" \
1892 "reason, no Baseband packets are received from that connection handle for a\n" \
1893 "duration longer than the Link_Supervision_Timeout, the connection is\n" \
1894 "disconnected.\n\n" \
1895 "\t<connection_handle> - dddd; connection handle\n" \
1896 "\t<timeout>           - dddd; timeout measured in number of baseband slots\n",
1897 &hci_write_link_supervision_timeout
1898 },
1899 {
1900 "read_page_scan_period_mode",
1901 "\nThis command is used to read the mandatory Page_Scan_Period_Mode of the\n" \
1902 "local Bluetooth device. Every time an inquiry response message is sent, the\n"\
1903 "Bluetooth device will start a timer (T_mandatory_pscan), the value of which\n"\
1904 "is dependent on the Page_Scan_Period_Mode. As long as this timer has not\n" \
1905 "expired, the Bluetooth device will use the Page_Scan_Period_Mode for all\n" \
1906 "following page scans.",
1907 &hci_read_page_scan_period_mode
1908 },
1909 {
1910 "write_page_scan_period_mode <page_scan_period_mode>",
1911 "\nThis command is used to write the mandatory Page_Scan_Period_Mode of the\n" \
1912 "local Bluetooth device. Every time an inquiry response message is sent, the\n"\
1913 "Bluetooth device will start a timer (T_mandatory_pscan), the value of which\n"\
1914 "is dependent on the Page_Scan_Period_Mode. As long as this timer has not\n" \
1915 "expired, the Bluetooth device will use the Page_Scan_Period_Mode for all\n" \
1916 "following page scans.\n\n" \
1917 "\t<page_scan_period_mode> - dd; page scan period mode:\n" \
1918 "\t0x00 - P0 (Default)\n" \
1919 "\t0x01 - P1\n" \
1920 "\t0x02 - P2",
1921 &hci_write_page_scan_period_mode
1922 },
1923 {
1924 "read_page_scan_mode",
1925 "\nThis command is used to read the default page scan mode of the local\n" \
1926 "Bluetooth device. The Page_Scan_Mode parameter indicates the page scan mode\n"\
1927 "that is used for the default page scan. Currently one mandatory page scan\n"\
1928 "mode and three optional page scan modes are defined. Following an inquiry\n" \
1929 "response, if the Baseband timer T_mandatory_pscan has not expired, the\n" \
1930 "mandatory page scan mode must be applied.",
1931 &hci_read_page_scan_mode
1932 },
1933 {
1934 "write_page_scan_mode <page_scan_mode>",
1935 "\nThis command is used to write the default page scan mode of the local\n" \
1936 "Bluetooth device. The Page_Scan_Mode parameter indicates the page scan mode\n"\
1937 "that is used for the default page scan. Currently, one mandatory page scan\n"\
1938 "mode and three optional page scan modes are defined. Following an inquiry\n"\
1939 "response, if the Baseband timer T_mandatory_pscan has not expired, the\n" \
1940 "mandatory page scan mode must be applied.\n\n" \
1941 "\t<page_scan_mode> - dd; page scan mode:\n" \
1942 "\t0x00 - Mandatory Page Scan Mode (Default)\n" \
1943 "\t0x01 - Optional Page Scan Mode I\n" \
1944 "\t0x02 - Optional Page Scan Mode II\n" \
1945 "\t0x03 - Optional Page Scan Mode III",
1946 &hci_write_page_scan_mode
1947 },
1948 {
1949 "read_le_host_supported_command",	\
1950 "Read if this host is in le supported mode and stimulatenouse le supported mode",
1951 &hci_read_le_host_supported_command,
1952 },
1953 {
1954 "write_le_host_supported_command",	\
1955 "write_le_host_supported_command le_host[0|1] stimultajeous_le[0|1]",
1956 &hci_write_le_host_supported_command,
1957 },
1958 
1959 { NULL, }
1960 };
1961 
1962