diff options
author | Kausik Sinnaswamy <kausik@broadcom.com> | 2012-03-06 17:08:42 -0800 |
---|---|---|
committer | Matthew Xie <mattx@google.com> | 2012-07-14 11:19:11 -0700 |
commit | b23905722d8a1c714d66aaee2da5712694596426 (patch) | |
tree | bb7ff539fa94fa219d87415253f56c147dac7876 /btif/src | |
parent | 3d576de19430085695937c04dffb2f0c8daf38e5 (diff) | |
download | external_bluetooth_bluedroid-b23905722d8a1c714d66aaee2da5712694596426.zip external_bluetooth_bluedroid-b23905722d8a1c714d66aaee2da5712694596426.tar.gz external_bluetooth_bluedroid-b23905722d8a1c714d66aaee2da5712694596426.tar.bz2 |
Dynamic enable/disable profiles using the profile's init/cleanup APIs
Change-Id: I40ed55ada7aad0cc0e017cae16049472ef318542
Diffstat (limited to 'btif/src')
-rw-r--r-- | btif/src/btif_core.c | 65 | ||||
-rw-r--r-- | btif/src/btif_dm.c | 67 | ||||
-rw-r--r-- | btif/src/btif_hf.c | 42 | ||||
-rw-r--r-- | btif/src/btif_storage.c | 31 |
4 files changed, 187 insertions, 18 deletions
diff --git a/btif/src/btif_core.c b/btif/src/btif_core.c index 570a7c5..022e1f4 100644 --- a/btif/src/btif_core.c +++ b/btif/src/btif_core.c @@ -83,7 +83,7 @@ static UINT32 btif_task_stack[(BTIF_TASK_STACK_SIZE + 3) / 4]; /* checks whether any HAL operation other than enable is permitted */ static int btif_enabled = 0; static int btif_shutdown_pending = 0; - +static tBTA_SERVICE_MASK btif_enabled_services = 0; /************************************************************************************ ** Local type definitions ************************************************************************************/ @@ -129,6 +129,7 @@ void bte_main_shutdown(void); void bte_main_enable_lpm(BOOLEAN enable); #endif void bte_main_postload_cfg(void); +void btif_dm_execute_service_request(UINT16 event, char *p_param); /************************************************************************************ ** Functions @@ -1036,3 +1037,65 @@ bt_status_t btif_get_remote_service_record(bt_bdaddr_t *remote_addr, return btif_dm_get_remote_service_record(remote_addr, uuid); } +tBTA_SERVICE_MASK btif_get_enabled_services_mask(void) +{ + return btif_enabled_services; +} + +/******************************************************************************* +** +** Function btif_enable_service +** +** Description Enables the service 'service_ID' to the service_mask. +** Upon BT enable, BTIF core shall invoke the BTA APIs to +** enable the profiles +** +** Returns bt_status_t +** +*******************************************************************************/ +bt_status_t btif_enable_service(tBTA_SERVICE_ID service_id) +{ + tBTA_SERVICE_ID *p_id = &service_id; + /* If BT is enabled, we need to switch to BTIF context and trigger the + * enable for that profile + * + * Otherwise, we just set the flag. On BT_Enable, the DM will trigger + * enable for the profiles that have been enabled */ + btif_enabled_services |= (1 << service_id); + BTIF_TRACE_ERROR2("%s: Current Services:0x%x", __FUNCTION__, btif_enabled_services); + if (btif_enabled == TRUE) + { + btif_transfer_context(btif_dm_execute_service_request, + BTIF_DM_ENABLE_SERVICE, + (char*)p_id, sizeof(tBTA_SERVICE_ID), NULL); + } + return BT_STATUS_SUCCESS; +} +/******************************************************************************* +** +** Function btif_disable_service +** +** Description Disables the service 'service_ID' to the service_mask. +** Upon BT disable, BTIF core shall invoke the BTA APIs to +** disable the profiles +** +** Returns bt_status_t +** +*******************************************************************************/ +bt_status_t btif_disable_service(tBTA_SERVICE_ID service_id) +{ + tBTA_SERVICE_ID *p_id = &service_id; + /* If BT is enabled, we need to switch to BTIF context and trigger the + * disable for that profile so that the appropriate uuid_property_changed will + * be triggerred. Otherwise, we just need to clear the service_id in the mask + */ + btif_enabled_services &= (tBTA_SERVICE_MASK)(~(1<<service_id)); + BTIF_TRACE_ERROR2("%s: Current Services:0x%x", __FUNCTION__, btif_enabled_services); + if (btif_enabled == TRUE) + { + btif_transfer_context(btif_dm_execute_service_request, + BTIF_DM_DISABLE_SERVICE, + (char*)p_id, sizeof(tBTA_SERVICE_ID), NULL); + } + return BT_STATUS_SUCCESS; +} diff --git a/btif/src/btif_dm.c b/btif/src/btif_dm.c index 750bb76..8fbc31d 100644 --- a/btif/src/btif_dm.c +++ b/btif/src/btif_dm.c @@ -96,11 +96,29 @@ static bt_status_t btif_dm_get_remote_services(bt_bdaddr_t *remote_addr); ** Externs ******************************************************************************/ extern UINT16 bta_service_id_to_uuid_lkup_tbl [BTA_MAX_SERVICE_ID]; +extern bt_status_t btif_hf_execute_service(BOOLEAN b_enable); /****************************************************************************** ** Functions ******************************************************************************/ +bt_status_t btif_in_execute_service_request(tBTA_SERVICE_ID service_id, + BOOLEAN b_enable) +{ + /* Check the service_ID and invoke the profile's BT state changed API */ + switch (service_id) + { + case BTA_HFP_SERVICE_ID: + { + btif_hf_execute_service(b_enable); + }break; + default: + BTIF_TRACE_ERROR1("%s: Unknown service being enabled", __FUNCTION__); + return BT_STATUS_FAIL; + } + return BT_STATUS_SUCCESS; +} + /******************************************************************************* ** ** Function check_eir_remote_name @@ -659,6 +677,8 @@ static void btif_dm_upstreams_evt(UINT16 event, char* p_param) { tBTA_DM_SEC_EVT dm_event = (tBTA_DM_SEC_EVT)event; tBTA_DM_SEC *p_data = (tBTA_DM_SEC*)p_param; + tBTA_SERVICE_MASK service_mask; + uint32_t i; BTIF_TRACE_EVENT1("btif_dm_upstreams_cback ev: %d", event); @@ -688,15 +708,39 @@ static void btif_dm_upstreams_evt(UINT16 event, char* p_param) /* A name exists in the storage. Make this the device name */ BTA_DmSetDeviceName((char*)prop.val); } + + /* for each of the enabled services in the mask, trigger the profile + * enable */ + service_mask = btif_get_enabled_services_mask(); + for (i=0; i <= BTA_MAX_SERVICE_ID; i++) + { + if (service_mask & + (tBTA_SERVICE_MASK)(BTA_SERVICE_ID_TO_SERVICE_MASK(i))) + { + btif_in_execute_service_request(i, TRUE); + } + } /* This function will also trigger the adapter_properties_cb ** and bonded_devices_info_cb */ btif_storage_load_bonded_devices(); + btif_enable_bluetooth_evt(p_data->enable.status, p_data->enable.bd_addr); } break; case BTA_DM_DISABLE_EVT: + /* for each of the enabled services in the mask, trigger the profile + * disable */ + service_mask = btif_get_enabled_services_mask(); + for (i=0; i <= BTA_MAX_SERVICE_ID; i++) + { + if (service_mask & + (tBTA_SERVICE_MASK)(BTA_SERVICE_ID_TO_SERVICE_MASK(i))) + { + btif_in_execute_service_request(i, FALSE); + } + } btif_disable_bluetooth_evt(); break; @@ -1168,3 +1212,26 @@ bt_status_t btif_dm_get_remote_service_record(bt_bdaddr_t *remote_addr, return BT_STATUS_SUCCESS; } + +void btif_dm_execute_service_request(UINT16 event, char *p_param) +{ + BOOLEAN b_enable = FALSE; + bt_status_t status; + if (event == BTIF_DM_ENABLE_SERVICE) + { + b_enable = TRUE; + } + status = btif_in_execute_service_request(*((tBTA_SERVICE_ID*)p_param), b_enable); + if (status == BT_STATUS_SUCCESS) + { + bt_property_t property; + bt_uuid_t local_uuids[BT_MAX_NUM_UUIDS]; + /* Now send the UUID_PROPERTY_CHANGED event to the upper layer */ + BTIF_STORAGE_FILL_PROPERTY(&property, BT_PROPERTY_UUIDS, + sizeof(local_uuids), local_uuids); + btif_storage_get_adapter_property(&property); + CHECK_CALL_CBACK(bt_hal_cbacks, adapter_properties_cb, + BT_STATUS_SUCCESS, 1, &property); + } + return; +} diff --git a/btif/src/btif_hf.c b/btif/src/btif_hf.c index 7f0e6bc..06e7fe3 100644 --- a/btif/src/btif_hf.c +++ b/btif/src/btif_hf.c @@ -422,16 +422,13 @@ static void bte_hf_evt(tBTA_AG_EVT event, tBTA_AG *p_data) *******************************************************************************/ static bt_status_t init( bthf_callbacks_t* callbacks ) { - char * p_service_names[] = {BTIF_HSAG_SERVICE_NAME, BTIF_HFAG_SERVICE_NAME}; - BTIF_TRACE_EVENT1("%s", __FUNCTION__); bt_hf_callbacks = callbacks; - /* Enable and register with BTA-AG */ - BTA_AgEnable (BTA_AG_PARSE, bte_hf_evt); - BTA_AgRegister(BTIF_HF_SERVICES, BTIF_HF_SECURITY, BTIF_HF_FEATURES, - p_service_names, BTIF_HF_ID_1); + /* Invoke the enable service API to the core to set the appropriate service_id + * Internally, the HSP_SERVICE_ID shall also be enabled */ + btif_enable_service(BTA_HFP_SERVICE_ID); return BT_STATUS_SUCCESS; } @@ -966,10 +963,7 @@ static void cleanup( void ) if (bt_hf_callbacks) { - /* De-register AG */ - BTA_AgDeregister(btif_hf_cb.handle); - /* Disable AG */ - BTA_AgDisable(); + btif_disable_service(BTA_HFP_SERVICE_ID); bt_hf_callbacks = NULL; } } @@ -996,6 +990,34 @@ static const bthf_interface_t bthfInterface = { /******************************************************************************* ** +** Function btif_hf_execute_service +** +** Description Initializes/Shuts down the service +** +** Returns BT_STATUS_SUCCESS on success, BT_STATUS_FAIL otherwise +** +*******************************************************************************/ +bt_status_t btif_hf_execute_service(BOOLEAN b_enable) +{ + char * p_service_names[] = {BTIF_HSAG_SERVICE_NAME, BTIF_HFAG_SERVICE_NAME}; + if (b_enable) + { + /* Enable and register with BTA-AG */ + BTA_AgEnable (BTA_AG_PARSE, bte_hf_evt); + BTA_AgRegister(BTIF_HF_SERVICES, BTIF_HF_SECURITY, BTIF_HF_FEATURES, + p_service_names, BTIF_HF_ID_1); + } + else { + /* De-register AG */ + BTA_AgDeregister(btif_hf_cb.handle); + /* Disable AG */ + BTA_AgDisable(); + } + return BT_STATUS_SUCCESS; +} + +/******************************************************************************* +** ** Function btif_hf_get_interface ** ** Description Get the hf callback interface diff --git a/btif/src/btif_storage.c b/btif/src/btif_storage.c index a55821d..6c0c337 100644 --- a/btif/src/btif_storage.c +++ b/btif/src/btif_storage.c @@ -170,6 +170,11 @@ typedef struct { } btif_bonded_devices_t; /************************************************************************************ +** Extern variables +************************************************************************************/ +extern UINT16 bta_service_id_to_uuid_lkup_tbl [BTA_MAX_SERVICE_ID]; + +/************************************************************************************ ** Static variables ************************************************************************************/ @@ -589,14 +594,26 @@ bt_status_t btif_storage_get_adapter_property(bt_property_t *property) /* publish list of local supported services */ bt_uuid_t *p_uuid = (bt_uuid_t*)property->val; uint32_t num_uuids = 0; + uint32_t i; -#if BTA_AG_INCLUDED == TRUE - uuid16_to_uuid128(UUID_SERVCLASS_AG_HANDSFREE, p_uuid + num_uuids); - num_uuids++; - uuid16_to_uuid128(UUID_SERVCLASS_HEADSET_AUDIO_GATEWAY, p_uuid + num_uuids); - num_uuids++; -#endif - + tBTA_SERVICE_MASK service_mask = btif_get_enabled_services_mask(); + BTIF_TRACE_ERROR2("%s service_mask:0x%x", __FUNCTION__, service_mask); + for (i=0; i < BTA_MAX_SERVICE_ID; i++) + { + if(service_mask + &(tBTA_SERVICE_MASK)(1 << i)) + { + uuid16_to_uuid128(bta_service_id_to_uuid_lkup_tbl[i], p_uuid+num_uuids); + num_uuids++; + /* BTA_HSP_SERVICE_ID is a special case and gets enabled automatically + * when BTA_HFP_SERVICE_ID is enabled */ + if (i == BTA_HFP_SERVICE_ID) { + uuid16_to_uuid128(bta_service_id_to_uuid_lkup_tbl[BTA_HSP_SERVICE_ID], + p_uuid+num_uuids); + num_uuids++; + } + } + } property->len = (num_uuids)*sizeof(bt_uuid_t); return BT_STATUS_SUCCESS; } |