1 /** @file
2  *  @brief Bluetooth device address definitions and utilities.
3  */
4 
5 /*
6  * Copyright (c) 2019 Nordic Semiconductor ASA
7  *
8  * SPDX-License-Identifier: Apache-2.0
9  */
10 #ifndef ZEPHYR_INCLUDE_BLUETOOTH_ADDR_H_
11 #define ZEPHYR_INCLUDE_BLUETOOTH_ADDR_H_
12 
13 #include <string.h>
14 #include <sys/printk.h>
15 #include <zephyr/types.h>
16 
17 #ifdef __cplusplus
18 extern "C" {
19 #endif
20 
21 /**
22  * @brief Bluetooth device address definitions and utilities.
23  * @defgroup bt_addr Device Address
24  * @ingroup bluetooth
25  * @{
26  */
27 
28 #define BT_ADDR_LE_PUBLIC       0x00
29 #define BT_ADDR_LE_RANDOM       0x01
30 #define BT_ADDR_LE_PUBLIC_ID    0x02
31 #define BT_ADDR_LE_RANDOM_ID    0x03
32 
33 /** Bluetooth Device Address */
34 typedef struct {
35 	uint8_t  val[6];
36 } bt_addr_t;
37 
38 /** Bluetooth LE Device Address */
39 typedef struct {
40 	uint8_t      type;
41 	bt_addr_t a;
42 } bt_addr_le_t;
43 
44 /** Bluetooth device "any" address, not a valid address */
45 #define BT_ADDR_ANY     ((bt_addr_t[]) { { { 0, 0, 0, 0, 0, 0 } } })
46 /** Bluetooth device "none" address, not a valid address */
47 #define BT_ADDR_NONE    ((bt_addr_t[]) { { \
48 			 { 0xff, 0xff, 0xff, 0xff, 0xff, 0xff } } })
49 /** Bluetooth LE device "any" address, not a valid address */
50 #define BT_ADDR_LE_ANY  ((bt_addr_le_t[]) { { 0, { { 0, 0, 0, 0, 0, 0 } } } })
51 /** Bluetooth LE device "none" address, not a valid address */
52 #define BT_ADDR_LE_NONE ((bt_addr_le_t[]) { { 0, \
53 			 { { 0xff, 0xff, 0xff, 0xff, 0xff, 0xff } } } })
54 
55 /** @brief Compare Bluetooth device addresses.
56  *
57  *  @param a First Bluetooth device address to compare
58  *  @param b Second Bluetooth device address to compare
59  *
60  *  @return negative value if @a a < @a b, 0 if @a a == @a b, else positive
61  */
bt_addr_cmp(const bt_addr_t * a,const bt_addr_t * b)62 static inline int bt_addr_cmp(const bt_addr_t *a, const bt_addr_t *b)
63 {
64 	return memcmp(a, b, sizeof(*a));
65 }
66 
67 /** @brief Compare Bluetooth LE device addresses.
68  *
69  *  @param a First Bluetooth LE device address to compare
70  *  @param b Second Bluetooth LE device address to compare
71  *
72  *  @return negative value if @a a < @a b, 0 if @a a == @a b, else positive
73  */
bt_addr_le_cmp(const bt_addr_le_t * a,const bt_addr_le_t * b)74 static inline int bt_addr_le_cmp(const bt_addr_le_t *a, const bt_addr_le_t *b)
75 {
76 	return memcmp(a, b, sizeof(*a));
77 }
78 
79 /** @brief Copy Bluetooth device address.
80  *
81  *  @param dst Bluetooth device address destination buffer.
82  *  @param src Bluetooth device address source buffer.
83  */
bt_addr_copy(bt_addr_t * dst,const bt_addr_t * src)84 static inline void bt_addr_copy(bt_addr_t *dst, const bt_addr_t *src)
85 {
86 	memcpy(dst, src, sizeof(*dst));
87 }
88 
89 /** @brief Copy Bluetooth LE device address.
90  *
91  *  @param dst Bluetooth LE device address destination buffer.
92  *  @param src Bluetooth LE device address source buffer.
93  */
bt_addr_le_copy(bt_addr_le_t * dst,const bt_addr_le_t * src)94 static inline void bt_addr_le_copy(bt_addr_le_t *dst, const bt_addr_le_t *src)
95 {
96 	memcpy(dst, src, sizeof(*dst));
97 }
98 
99 /** Check if a Bluetooth LE random address is resolvable private address. */
100 #define BT_ADDR_IS_RPA(a)     (((a)->val[5] & 0xc0) == 0x40)
101 /** Check if a Bluetooth LE random address is a non-resolvable private address.
102  */
103 #define BT_ADDR_IS_NRPA(a)    (((a)->val[5] & 0xc0) == 0x00)
104 /** Check if a Bluetooth LE random address is a static address. */
105 #define BT_ADDR_IS_STATIC(a)  (((a)->val[5] & 0xc0) == 0xc0)
106 
107 /** Set a Bluetooth LE random address as a resolvable private address. */
108 #define BT_ADDR_SET_RPA(a)    ((a)->val[5] = (((a)->val[5] & 0x3f) | 0x40))
109 /** Set a Bluetooth LE random address as a non-resolvable private address. */
110 #define BT_ADDR_SET_NRPA(a)   ((a)->val[5] &= 0x3f)
111 /** Set a Bluetooth LE random address as a static address. */
112 #define BT_ADDR_SET_STATIC(a) ((a)->val[5] |= 0xc0)
113 
114 /** @brief Create a Bluetooth LE random non-resolvable private address. */
115 int bt_addr_le_create_nrpa(bt_addr_le_t *addr);
116 
117 /** @brief Create a Bluetooth LE random static address. */
118 int bt_addr_le_create_static(bt_addr_le_t *addr);
119 
120 /** @brief Check if a Bluetooth LE address is a random private resolvable
121  *         address.
122  *
123  *  @param addr Bluetooth LE device address.
124  *
125  *  @return true if address is a random private resolvable address.
126  */
bt_addr_le_is_rpa(const bt_addr_le_t * addr)127 static inline bool bt_addr_le_is_rpa(const bt_addr_le_t *addr)
128 {
129 	if (addr->type != BT_ADDR_LE_RANDOM) {
130 		return false;
131 	}
132 
133 	return BT_ADDR_IS_RPA(&addr->a);
134 }
135 
136 /** @brief Check if a Bluetooth LE address is valid identity address.
137  *
138  *  Valid Bluetooth LE identity addresses are either public address or
139  *  random static address.
140  *
141  *  @param addr Bluetooth LE device address.
142  *
143  *  @return true if address is a valid identity address.
144  */
bt_addr_le_is_identity(const bt_addr_le_t * addr)145 static inline bool bt_addr_le_is_identity(const bt_addr_le_t *addr)
146 {
147 	if (addr->type == BT_ADDR_LE_PUBLIC) {
148 		return true;
149 	}
150 
151 	return BT_ADDR_IS_STATIC(&addr->a);
152 }
153 
154 /** @def BT_ADDR_STR_LEN
155  *
156  *  @brief Recommended length of user string buffer for Bluetooth address
157  *
158  *  @details The recommended length guarantee the output of address
159  *  conversion will not lose valuable information about address being
160  *  processed.
161  */
162 #define BT_ADDR_STR_LEN 18
163 
164 /** @def BT_ADDR_LE_STR_LEN
165  *
166  *  @brief Recommended length of user string buffer for Bluetooth LE address
167  *
168  *  @details The recommended length guarantee the output of address
169  *  conversion will not lose valuable information about address being
170  *  processed.
171  */
172 #define BT_ADDR_LE_STR_LEN 30
173 
174 /** @brief Converts binary Bluetooth address to string.
175  *
176  *  @param addr Address of buffer containing binary Bluetooth address.
177  *  @param str Address of user buffer with enough room to store formatted
178  *  string containing binary address.
179  *  @param len Length of data to be copied to user string buffer. Refer to
180  *  BT_ADDR_STR_LEN about recommended value.
181  *
182  *  @return Number of successfully formatted bytes from binary address.
183  */
bt_addr_to_str(const bt_addr_t * addr,char * str,size_t len)184 static inline int bt_addr_to_str(const bt_addr_t *addr, char *str, size_t len)
185 {
186 	return snprintk(str, len, "%02X:%02X:%02X:%02X:%02X:%02X",
187 			addr->val[5], addr->val[4], addr->val[3],
188 			addr->val[2], addr->val[1], addr->val[0]);
189 }
190 
191 /** @brief Converts binary LE Bluetooth address to string.
192  *
193  *  @param addr Address of buffer containing binary LE Bluetooth address.
194  *  @param str Address of user buffer with enough room to store
195  *  formatted string containing binary LE address.
196  *  @param len Length of data to be copied to user string buffer. Refer to
197  *  BT_ADDR_LE_STR_LEN about recommended value.
198  *
199  *  @return Number of successfully formatted bytes from binary address.
200  */
bt_addr_le_to_str(const bt_addr_le_t * addr,char * str,size_t len)201 static inline int bt_addr_le_to_str(const bt_addr_le_t *addr, char *str,
202 				    size_t len)
203 {
204 	char type[10];
205 
206 	switch (addr->type) {
207 	case BT_ADDR_LE_PUBLIC:
208 		strcpy(type, "public");
209 		break;
210 	case BT_ADDR_LE_RANDOM:
211 		strcpy(type, "random");
212 		break;
213 	case BT_ADDR_LE_PUBLIC_ID:
214 		strcpy(type, "public-id");
215 		break;
216 	case BT_ADDR_LE_RANDOM_ID:
217 		strcpy(type, "random-id");
218 		break;
219 	default:
220 		snprintk(type, sizeof(type), "0x%02x", addr->type);
221 		break;
222 	}
223 
224 	return snprintk(str, len, "%02X:%02X:%02X:%02X:%02X:%02X (%s)",
225 			addr->a.val[5], addr->a.val[4], addr->a.val[3],
226 			addr->a.val[2], addr->a.val[1], addr->a.val[0], type);
227 }
228 
229 /** @brief Convert Bluetooth address from string to binary.
230  *
231  *  @param[in]  str   The string representation of a Bluetooth address.
232  *  @param[out] addr  Address of buffer to store the Bluetooth address
233  *
234  *  @return Zero on success or (negative) error code otherwise.
235  */
236 int bt_addr_from_str(const char *str, bt_addr_t *addr);
237 
238 /** @brief Convert LE Bluetooth address from string to binary.
239  *
240  *  @param[in]  str   The string representation of an LE Bluetooth address.
241  *  @param[in]  type  The string representation of the LE Bluetooth address
242  *                   type.
243  *  @param[out] addr  Address of buffer to store the LE Bluetooth address
244  *
245  *  @return Zero on success or (negative) error code otherwise.
246  */
247 int bt_addr_le_from_str(const char *str, const char *type, bt_addr_le_t *addr);
248 
249 /**
250  * @}
251  */
252 
253 #ifdef __cplusplus
254 }
255 #endif
256 
257 #endif /* ZEPHYR_INCLUDE_BLUETOOTH_ADDR_H_ */
258