1 /* $NetBSD: bluetooth.c$ */
6 * Copyright (c) 2001-2003 Maksim Yevmenkin <m_evmenkin@yahoo.com>
9 * Redistribution and use in source and binary forms, with or without
10 * modification, are permitted provided that the following conditions
12 * 1. Redistributions of source code must retain the above copyright
13 * notice, this list of conditions and the following disclaimer.
14 * 2. Redistributions in binary form must reproduce the above copyright
15 * notice, this list of conditions and the following disclaimer in the
16 * documentation and/or other materials provided with the distribution.
18 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
19 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
20 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
21 * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
22 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
23 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
24 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
25 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
26 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
27 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
30 * $Id: bluetooth.c,v 1.1 2006/06/19 15:44:36 gdamore Exp $
31 * $FreeBSD: src/lib/libbluetooth/bluetooth.c,v 1.2 2004/03/05 08:10:17 markm Exp $
34 #include <sys/cdefs.h>
35 __RCSID("$NetBSD: bluetooth.c$");
37 #include <bluetooth.h>
42 #define _PATH_BT_HOSTS "/etc/bluetooth/hosts"
43 #define _PATH_BT_PROTOCOLS "/etc/bluetooth/protocols"
46 static FILE *hostf
= NULL
;
47 static int host_stayopen
= 0;
48 static struct hostent host
;
49 static bdaddr_t host_addr
;
50 static char *host_addr_ptrs
[2];
51 static char *host_aliases
[MAXALIASES
];
53 static FILE *protof
= NULL
;
54 static int proto_stayopen
= 0;
55 static struct protoent proto
;
56 static char *proto_aliases
[MAXALIASES
];
58 static char buf
[BUFSIZ
+ 1];
60 static int bt_hex_byte (char const *str
);
61 static int bt_hex_nibble (char nibble
);
64 bt_gethostbyname(char const *name
)
69 bt_sethostent(host_stayopen
);
70 while ((p
= bt_gethostent()) != NULL
) {
71 if (strcasecmp(p
->h_name
, name
) == 0)
73 for (cp
= p
->h_aliases
; *cp
!= 0; cp
++)
74 if (strcasecmp(*cp
, name
) == 0)
84 bt_gethostbyaddr(char const *addr
, socklen_t len
, int type
)
88 if (type
!= AF_BLUETOOTH
|| len
!= sizeof(bdaddr_t
)) {
89 h_errno
= NO_RECOVERY
;
93 bt_sethostent(host_stayopen
);
94 while ((p
= bt_gethostent()) != NULL
)
95 if (p
->h_addrtype
== type
&& memcmp(p
->h_addr
, addr
, len
) == 0)
108 hostf
= fopen(_PATH_BT_HOSTS
, "r");
111 h_errno
= NETDB_INTERNAL
;
115 if ((p
= fgets(buf
, sizeof(buf
), hostf
)) == NULL
) {
116 h_errno
= HOST_NOT_FOUND
;
121 if ((cp
= strpbrk(p
, "#\n")) == NULL
)
124 if ((cp
= strpbrk(p
, " \t")) == NULL
)
127 if (bt_aton(p
, &host_addr
) == 0)
129 host_addr_ptrs
[0] = (char *) &host_addr
;
130 host_addr_ptrs
[1] = NULL
;
131 host
.h_addr_list
= host_addr_ptrs
;
132 host
.h_length
= sizeof(host_addr
);
133 host
.h_addrtype
= AF_BLUETOOTH
;
134 while (*cp
== ' ' || *cp
== '\t')
137 q
= host
.h_aliases
= host_aliases
;
138 if ((cp
= strpbrk(cp
, " \t")) != NULL
)
140 while (cp
!= NULL
&& *cp
!= 0) {
141 if (*cp
== ' ' || *cp
== '\t') {
145 if (q
< &host_aliases
[MAXALIASES
- 1])
147 if ((cp
= strpbrk(cp
, " \t")) != NULL
)
151 h_errno
= NETDB_SUCCESS
;
157 bt_sethostent(int stayopen
)
160 hostf
= fopen(_PATH_BT_HOSTS
, "r");
164 host_stayopen
= stayopen
;
170 if (hostf
!= NULL
&& host_stayopen
== 0) {
171 (void) fclose(hostf
);
177 bt_getprotobyname(char const *name
)
182 bt_setprotoent(proto_stayopen
);
183 while ((p
= bt_getprotoent()) != NULL
) {
184 if (strcmp(p
->p_name
, name
) == 0)
186 for (cp
= p
->p_aliases
; *cp
!= 0; cp
++)
187 if (strcmp(*cp
, name
) == 0)
197 bt_getprotobynumber(int num
)
201 bt_setprotoent(proto_stayopen
);
202 while ((p
= bt_getprotoent()) != NULL
)
203 if (p
->p_proto
== num
)
216 protof
= fopen(_PATH_BT_PROTOCOLS
, "r");
221 if ((p
= fgets(buf
, sizeof(buf
), protof
)) == NULL
)
225 if ((cp
= strpbrk(p
, "#\n")) == NULL
)
229 if ((cp
= strpbrk(p
, " \t")) == NULL
)
232 while (*cp
== ' ' || *cp
== '\t')
234 if ((p
= strpbrk(cp
, " \t")) != NULL
)
236 proto
.p_proto
= (int)strtol(cp
, NULL
, 0);
237 q
= proto
.p_aliases
= proto_aliases
;
240 while (cp
!= NULL
&& *cp
!= 0) {
241 if (*cp
== ' ' || *cp
== '\t') {
245 if (q
< &proto_aliases
[MAXALIASES
- 1])
247 if ((cp
= strpbrk(cp
, " \t")) != NULL
)
257 bt_setprotoent(int stayopen
)
260 protof
= fopen(_PATH_BT_PROTOCOLS
, "r");
264 proto_stayopen
= stayopen
;
270 if (protof
!= NULL
) {
271 (void) fclose(protof
);
277 bt_ntoa(bdaddr_t
const *ba
, char *str
)
279 static char buffer
[24];
284 sprintf(str
, "%2.2x:%2.2x:%2.2x:%2.2x:%2.2x:%2.2x",
285 ba
->b
[5], ba
->b
[4], ba
->b
[3], ba
->b
[2], ba
->b
[1], ba
->b
[0]);
291 bt_aton(char const *str
, bdaddr_t
*ba
)
296 memset(ba
, 0, sizeof(*ba
));
298 for (i
= 5, end
= strchr(str
, ':');
299 i
> 0 && *str
!= '\0' && end
!= NULL
;
300 i
--, str
= end
+ 1, end
= strchr(str
, ':')) {
303 b
= bt_hex_nibble(str
[0]);
307 b
= bt_hex_byte(str
);
321 if (i
!= 0 || end
!= NULL
|| *str
== 0)
324 switch (strlen(str
)) {
326 b
= bt_hex_nibble(str
[0]);
330 b
= bt_hex_byte(str
);
347 bt_hex_byte(char const *str
)
351 if ((n1
= bt_hex_nibble(str
[0])) < 0)
354 if ((n2
= bt_hex_nibble(str
[1])) < 0)
357 return ((((n1
& 0x0f) << 4) | (n2
& 0x0f)) & 0xff);
361 bt_hex_nibble(char nibble
)
363 if ('0' <= nibble
&& nibble
<= '9')
364 return (nibble
- '0');
366 if ('a' <= nibble
&& nibble
<= 'f')
367 return (nibble
- 'a' + 0xa);
369 if ('A' <= nibble
&& nibble
<= 'F')
370 return (nibble
- 'A' + 0xa);