diff --git a/system/bta/dm/bta_dm_act.cc b/system/bta/dm/bta_dm_act.cc index 180e1b3aed855512f677d446ebd6e4d5b154b0e1..367e23ab9f8c0e6d9cc5e0955379e063ac38c721 100644 --- a/system/bta/dm/bta_dm_act.cc +++ b/system/bta/dm/bta_dm_act.cc @@ -2150,6 +2150,7 @@ static void bta_dm_inq_results_cb(tBTM_INQ_RESULTS* p_inq, const uint8_t* p_eir, result.inq_res.device_type = p_inq->device_type; result.inq_res.flag = p_inq->flag; result.inq_res.include_rsi = p_inq->include_rsi; + result.inq_res.clock_offset = p_inq->clock_offset; /* application will parse EIR to find out remote device name */ result.inq_res.p_eir = const_cast<uint8_t*>(p_eir); diff --git a/system/bta/include/bta_api.h b/system/bta/include/bta_api.h index e183897da40547ae33843ee76ea0ac39219efb01..bb5c21c364559668b7ae53e118c3d049a1f85c26 100644 --- a/system/bta/include/bta_api.h +++ b/system/bta/include/bta_api.h @@ -512,6 +512,7 @@ typedef struct { bool include_rsi; /* true, if ADV contains RSI data */ RawAddress original_bda; /* original address to pass up to GattService#onScanResult */ + uint16_t clock_offset; } tBTA_DM_INQ_RES; /* Structure associated with BTA_DM_INQ_CMPL_EVT */ diff --git a/system/btif/include/btif_config.h b/system/btif/include/btif_config.h index 185eae7d69c5fd8108c37b6f0d43fb55e81d5e54..b73db8debd6c50414c562cae8d35382e1cd939d1 100644 --- a/system/btif/include/btif_config.h +++ b/system/btif/include/btif_config.h @@ -71,3 +71,5 @@ std::vector<RawAddress> btif_config_get_paired_devices(); bool btif_config_clear(void); void btif_debug_config_dump(int fd); +bool btif_get_device_clockoffset(const RawAddress& bda, int* p_clock_offset); +bool btif_set_device_clockoffset(const RawAddress& bda, int clock_offset); diff --git a/system/btif/src/btif_config.cc b/system/btif/src/btif_config.cc index 3e6e4e37407260e11bceaca1a32f534c47eced69..21cf699107978f79266f72f28d7fe44d422f7b07 100644 --- a/system/btif/src/btif_config.cc +++ b/system/btif/src/btif_config.cc @@ -209,6 +209,31 @@ EXPORT_SYMBOL module_t btif_config_module = {.name = BTIF_CONFIG_MODULE, .shut_down = shut_down, .clean_up = clean_up}; +bool btif_get_device_clockoffset(const RawAddress& bda, int* p_clock_offset) { + if (p_clock_offset == NULL) return false; + + std::string addrstr = bda.ToString(); + const char* bd_addr_str = addrstr.c_str(); + + if (!btif_config_get_int(bd_addr_str, "ClockOffset", p_clock_offset)) return false; + + LOG_DEBUG("%s: Device [%s] clock_offset %d", __func__, bd_addr_str, + *p_clock_offset); + return true; +} + +bool btif_set_device_clockoffset(const RawAddress& bda, int clock_offset) { + + std::string addrstr = bda.ToString(); + const char* bd_addr_str = addrstr.c_str(); + + if (!btif_config_set_int(bd_addr_str, "ClockOffset", clock_offset)) return false; + + LOG_DEBUG("%s: Device [%s] clock_offset %d", __func__, bd_addr_str, + clock_offset); + return true; +} + bool btif_config_exist(const std::string& section, const std::string& key) { CHECK(bluetooth::shim::is_gd_stack_started_up()); return bluetooth::shim::BtifConfigInterface::HasProperty(section, key); diff --git a/system/btif/src/btif_dm.cc b/system/btif/src/btif_dm.cc index 50357e04b7bdfcce4f3805eed5066fd19a74d593..7f5904b493a356ce94013e8dda0826a7c4b277fe 100644 --- a/system/btif/src/btif_dm.cc +++ b/system/btif/src/btif_dm.cc @@ -1468,6 +1468,12 @@ static void btif_dm_search_devices_evt(tBTA_DM_SEARCH_EVT event, num_properties++; } + BTIF_TRACE_DEBUG("%s clock_offset is 0x%x", __func__, + p_search_data->inq_res.clock_offset); + if (p_search_data->inq_res.clock_offset & BTM_CLOCK_OFFSET_VALID) { + btif_set_device_clockoffset(bdaddr, (int)p_search_data->inq_res.clock_offset); + } + /* DEV_TYPE */ /* FixMe: Assumption is that bluetooth.h and BTE enums match */ diff --git a/system/stack/btm/btm_inq.cc b/system/stack/btm/btm_inq.cc index e992c149a9e85d32c6682e62f4bbc14f5f5750f0..60b8dcb8d470dbde63b059d38b40f099f6a063b6 100644 --- a/system/stack/btm/btm_inq.cc +++ b/system/stack/btm/btm_inq.cc @@ -54,6 +54,7 @@ #include "stack/include/inq_hci_link_interface.h" #include "types/bluetooth/uuid.h" #include "types/raw_address.h" +#include "btif/include/btif_config.h" namespace { constexpr char kBtmLogTag[] = "SCAN"; @@ -1579,14 +1580,26 @@ tBTM_STATUS btm_initiate_rem_name(const RawAddress& remote_bda, uint8_t origin, tINQ_DB_ENT* p_i = btm_inq_db_find(remote_bda); if (p_i && (p_i->inq_info.results.inq_result_type & BTM_INQ_RESULT_BR)) { tBTM_INQ_INFO* p_cur = &p_i->inq_info; + uint16_t clock_offset = p_cur->results.clock_offset | BTM_CLOCK_OFFSET_VALID; + int clock_offset_in_cfg = 0; + if (0 == (p_cur->results.clock_offset & BTM_CLOCK_OFFSET_VALID)) { + if (btif_get_device_clockoffset(remote_bda, &clock_offset_in_cfg)) { + clock_offset = clock_offset_in_cfg; + } + } + btsnd_hcic_rmt_name_req( remote_bda, p_cur->results.page_scan_rep_mode, - p_cur->results.page_scan_mode, - (uint16_t)(p_cur->results.clock_offset | BTM_CLOCK_OFFSET_VALID)); + p_cur->results.page_scan_mode, clock_offset); } else { + uint16_t clock_offset = 0; + int clock_offset_in_cfg = 0; + if (btif_get_device_clockoffset(remote_bda, &clock_offset_in_cfg)) { + clock_offset = clock_offset_in_cfg; + } /* Otherwise use defaults and mark the clock offset as invalid */ btsnd_hcic_rmt_name_req(remote_bda, HCI_PAGE_SCAN_REP_MODE_R1, - HCI_MANDATARY_PAGE_SCAN_MODE, 0); + HCI_MANDATARY_PAGE_SCAN_MODE, clock_offset); } p_inq->remname_active = true; diff --git a/system/test/mock/mock_btif_config.cc b/system/test/mock/mock_btif_config.cc index 3761b56124a36e113bbe2f413584e517d5314f3b..8696938d02824fa892220872327b34bd13d18faf 100644 --- a/system/test/mock/mock_btif_config.cc +++ b/system/test/mock/mock_btif_config.cc @@ -49,6 +49,8 @@ namespace mock { namespace btif_config { // Function state capture and return values, if needed +struct btif_get_device_clockoffset btif_get_device_clockoffset; +struct btif_set_device_clockoffset btif_set_device_clockoffset; struct btif_config_exist btif_config_exist; struct btif_config_get_int btif_config_get_int; struct btif_config_set_int btif_config_set_int; @@ -69,6 +71,14 @@ struct btif_debug_config_dump btif_debug_config_dump; } // namespace test // Mocked functions, if any +bool btif_get_device_clockoffset(const RawAddress& bda, int* p_clock_offset) { + inc_func_call_count(__func__); + return test::mock::btif_config::btif_get_device_clockoffset(bda, p_clock_offset); +} +bool btif_set_device_clockoffset(const RawAddress& bda, int clock_offset) { + inc_func_call_count(__func__); + return test::mock::btif_config::btif_set_device_clockoffset(bda, clock_offset); +} bool btif_config_exist(const std::string& section, const std::string& key) { inc_func_call_count(__func__); return test::mock::btif_config::btif_config_exist(section, key); diff --git a/system/test/mock/mock_btif_config.h b/system/test/mock/mock_btif_config.h index f2f07f535abdcc3cecf94f3cd8315097fdaf30b4..34928c9e8c45e9a40cae9ba3cc1f6e6f631fa6d3 100644 --- a/system/test/mock/mock_btif_config.h +++ b/system/test/mock/mock_btif_config.h @@ -43,6 +43,26 @@ namespace mock { namespace btif_config { // Shared state between mocked functions and tests +// Name: btif_get_device_clockoffset +// Params: const RawAddress& bda, int* p_clock_offset +// Returns: bool +struct btif_get_device_clockoffset { + std::function<bool(const RawAddress& bda, int* p_clock_offset)> body{ + [](const RawAddress& bda, int* p_clock_offset) { return false; }}; + bool operator()(const RawAddress& bda, int* p_clock_offset) { + return body(bda, p_clock_offset); + }; +}; +// Name: btif_set_device_clockoffset +// Params: const RawAddress& bda, int* p_clock_offset +// Returns: bool +struct btif_set_device_clockoffset { + std::function<bool(const RawAddress& bda, int clock_offset)> body{ + [](const RawAddress& bda, int clock_offset) { return false; }}; + bool operator()(const RawAddress& bda, int clock_offset) { + return body(bda, clock_offset); + }; +}; // Name: btif_config_exist // Params: const std::string& section, const std::string& key // Returns: bool