1*4d7e907cSAndroid Build Coastguard Worker //
2*4d7e907cSAndroid Build Coastguard Worker // Copyright 2016 The Android Open Source Project
3*4d7e907cSAndroid Build Coastguard Worker //
4*4d7e907cSAndroid Build Coastguard Worker // Licensed under the Apache License, Version 2.0 (the "License");
5*4d7e907cSAndroid Build Coastguard Worker // you may not use this file except in compliance with the License.
6*4d7e907cSAndroid Build Coastguard Worker // You may obtain a copy of the License at
7*4d7e907cSAndroid Build Coastguard Worker //
8*4d7e907cSAndroid Build Coastguard Worker // http://www.apache.org/licenses/LICENSE-2.0
9*4d7e907cSAndroid Build Coastguard Worker //
10*4d7e907cSAndroid Build Coastguard Worker // Unless required by applicable law or agreed to in writing, software
11*4d7e907cSAndroid Build Coastguard Worker // distributed under the License is distributed on an "AS IS" BASIS,
12*4d7e907cSAndroid Build Coastguard Worker // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13*4d7e907cSAndroid Build Coastguard Worker // See the License for the specific language governing permissions and
14*4d7e907cSAndroid Build Coastguard Worker // limitations under the License.
15*4d7e907cSAndroid Build Coastguard Worker //
16*4d7e907cSAndroid Build Coastguard Worker
17*4d7e907cSAndroid Build Coastguard Worker #include "bluetooth_address.h"
18*4d7e907cSAndroid Build Coastguard Worker
19*4d7e907cSAndroid Build Coastguard Worker #include <cutils/properties.h>
20*4d7e907cSAndroid Build Coastguard Worker #include <errno.h>
21*4d7e907cSAndroid Build Coastguard Worker #include <fcntl.h>
22*4d7e907cSAndroid Build Coastguard Worker #include <unistd.h>
23*4d7e907cSAndroid Build Coastguard Worker #include <utils/Log.h>
24*4d7e907cSAndroid Build Coastguard Worker
25*4d7e907cSAndroid Build Coastguard Worker namespace android {
26*4d7e907cSAndroid Build Coastguard Worker namespace hardware {
27*4d7e907cSAndroid Build Coastguard Worker namespace bluetooth {
28*4d7e907cSAndroid Build Coastguard Worker namespace V1_0 {
29*4d7e907cSAndroid Build Coastguard Worker namespace implementation {
30*4d7e907cSAndroid Build Coastguard Worker
bytes_to_string(const uint8_t * addr,char * addr_str)31*4d7e907cSAndroid Build Coastguard Worker void BluetoothAddress::bytes_to_string(const uint8_t* addr, char* addr_str) {
32*4d7e907cSAndroid Build Coastguard Worker sprintf(addr_str, "%02x:%02x:%02x:%02x:%02x:%02x", addr[0], addr[1], addr[2],
33*4d7e907cSAndroid Build Coastguard Worker addr[3], addr[4], addr[5]);
34*4d7e907cSAndroid Build Coastguard Worker }
35*4d7e907cSAndroid Build Coastguard Worker
string_to_bytes(const char * addr_str,uint8_t * addr)36*4d7e907cSAndroid Build Coastguard Worker bool BluetoothAddress::string_to_bytes(const char* addr_str, uint8_t* addr) {
37*4d7e907cSAndroid Build Coastguard Worker if (addr_str == NULL) return false;
38*4d7e907cSAndroid Build Coastguard Worker if (strnlen(addr_str, kStringLength) != kStringLength) return false;
39*4d7e907cSAndroid Build Coastguard Worker unsigned char trailing_char = '\0';
40*4d7e907cSAndroid Build Coastguard Worker
41*4d7e907cSAndroid Build Coastguard Worker return (sscanf(addr_str, "%02hhx:%02hhx:%02hhx:%02hhx:%02hhx:%02hhx%1c",
42*4d7e907cSAndroid Build Coastguard Worker &addr[0], &addr[1], &addr[2], &addr[3], &addr[4], &addr[5],
43*4d7e907cSAndroid Build Coastguard Worker &trailing_char) == kBytes);
44*4d7e907cSAndroid Build Coastguard Worker }
45*4d7e907cSAndroid Build Coastguard Worker
get_local_address(uint8_t * local_addr)46*4d7e907cSAndroid Build Coastguard Worker bool BluetoothAddress::get_local_address(uint8_t* local_addr) {
47*4d7e907cSAndroid Build Coastguard Worker char property[PROPERTY_VALUE_MAX] = {0};
48*4d7e907cSAndroid Build Coastguard Worker
49*4d7e907cSAndroid Build Coastguard Worker // Get local bdaddr storage path from a system property.
50*4d7e907cSAndroid Build Coastguard Worker if (property_get(PROPERTY_BT_BDADDR_PATH, property, NULL)) {
51*4d7e907cSAndroid Build Coastguard Worker ALOGD("%s: Trying %s", __func__, property);
52*4d7e907cSAndroid Build Coastguard Worker
53*4d7e907cSAndroid Build Coastguard Worker int addr_fd = open(property, O_RDONLY);
54*4d7e907cSAndroid Build Coastguard Worker if (addr_fd != -1) {
55*4d7e907cSAndroid Build Coastguard Worker char address[kStringLength + 1] = {0};
56*4d7e907cSAndroid Build Coastguard Worker int bytes_read = read(addr_fd, address, kStringLength);
57*4d7e907cSAndroid Build Coastguard Worker if (bytes_read == -1) {
58*4d7e907cSAndroid Build Coastguard Worker ALOGE("%s: Error reading address from %s: %s", __func__, property,
59*4d7e907cSAndroid Build Coastguard Worker strerror(errno));
60*4d7e907cSAndroid Build Coastguard Worker }
61*4d7e907cSAndroid Build Coastguard Worker close(addr_fd);
62*4d7e907cSAndroid Build Coastguard Worker
63*4d7e907cSAndroid Build Coastguard Worker // Null terminate the string.
64*4d7e907cSAndroid Build Coastguard Worker address[kStringLength] = '\0';
65*4d7e907cSAndroid Build Coastguard Worker
66*4d7e907cSAndroid Build Coastguard Worker // If the address is not all zeros, then use it.
67*4d7e907cSAndroid Build Coastguard Worker const uint8_t zero_bdaddr[kBytes] = {0, 0, 0, 0, 0, 0};
68*4d7e907cSAndroid Build Coastguard Worker if ((string_to_bytes(address, local_addr)) &&
69*4d7e907cSAndroid Build Coastguard Worker (memcmp(local_addr, zero_bdaddr, kBytes) != 0)) {
70*4d7e907cSAndroid Build Coastguard Worker ALOGD("%s: Got Factory BDA", __func__);
71*4d7e907cSAndroid Build Coastguard Worker return true;
72*4d7e907cSAndroid Build Coastguard Worker } else {
73*4d7e907cSAndroid Build Coastguard Worker ALOGE("%s: Got Invalid BDA '%s' from %s", __func__, address, property);
74*4d7e907cSAndroid Build Coastguard Worker }
75*4d7e907cSAndroid Build Coastguard Worker }
76*4d7e907cSAndroid Build Coastguard Worker }
77*4d7e907cSAndroid Build Coastguard Worker
78*4d7e907cSAndroid Build Coastguard Worker // No BDADDR found in the file. Look for BDA in a factory property.
79*4d7e907cSAndroid Build Coastguard Worker if (property_get(FACTORY_BDADDR_PROPERTY, property, NULL) &&
80*4d7e907cSAndroid Build Coastguard Worker string_to_bytes(property, local_addr)) {
81*4d7e907cSAndroid Build Coastguard Worker ALOGD("%s: Using FACTORY_BDADDR_PROPERTY", __func__);
82*4d7e907cSAndroid Build Coastguard Worker return true;
83*4d7e907cSAndroid Build Coastguard Worker }
84*4d7e907cSAndroid Build Coastguard Worker
85*4d7e907cSAndroid Build Coastguard Worker // No factory BDADDR found. Look for a previously stored BDA.
86*4d7e907cSAndroid Build Coastguard Worker if (property_get(PERSIST_BDADDR_PROPERTY, property, NULL) &&
87*4d7e907cSAndroid Build Coastguard Worker string_to_bytes(property, local_addr)) {
88*4d7e907cSAndroid Build Coastguard Worker ALOGD("%s: Using PERSIST_BDADDR_PROPERTY", __func__);
89*4d7e907cSAndroid Build Coastguard Worker return true;
90*4d7e907cSAndroid Build Coastguard Worker }
91*4d7e907cSAndroid Build Coastguard Worker
92*4d7e907cSAndroid Build Coastguard Worker return false;
93*4d7e907cSAndroid Build Coastguard Worker }
94*4d7e907cSAndroid Build Coastguard Worker
95*4d7e907cSAndroid Build Coastguard Worker } // namespace implementation
96*4d7e907cSAndroid Build Coastguard Worker } // namespace V1_0
97*4d7e907cSAndroid Build Coastguard Worker } // namespace bluetooth
98*4d7e907cSAndroid Build Coastguard Worker } // namespace hardware
99*4d7e907cSAndroid Build Coastguard Worker } // namespace android
100