1 /******************************************************************************
3 * Copyright (C) 2003-2012 Broadcom Corporation
5 * Licensed under the Apache License, Version 2.0 (the "License");
6 * you may not use this file except in compliance with the License.
7 * You may obtain a copy of the License at:
9 * http://www.apache.org/licenses/LICENSE-2.0
11 * Unless required by applicable law or agreed to in writing, software
12 * distributed under the License is distributed on an "AS IS" BASIS,
13 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14 * See the License for the specific language governing permissions and
15 * limitations under the License.
17 ******************************************************************************/
19 /******************************************************************************
21 * This is the main implementation file for the BTA system manager.
23 ******************************************************************************/
24 #define LOG_TAG "bt_bta_sys_main"
26 // #include <assert.h>
34 #include "bta_sys_int.h"
36 #include "fixed_queue.h"
40 #include "hash_functions.h"
41 // #include "osi/include/log.h"
42 // #include "osi/include/thread.h"
43 #if( defined BTA_AR_INCLUDED ) && (BTA_AR_INCLUDED == TRUE)
44 #include "bta_ar_api.h"
49 /* system manager control block definition */
50 #if BTA_DYNAMIC_MEMORY == FALSE
51 tBTA_SYS_CB bta_sys_cb;
54 fixed_queue_t *btu_bta_alarm_queue;
55 static hash_map_t *bta_alarm_hash_map;
56 static const size_t BTA_ALARM_HASH_MAP_SIZE = 17;
57 static pthread_mutex_t bta_alarm_lock;
58 // extern thread_t *bt_workqueue_thread;
61 /* TODO Bluedroid - Hard-coded trace levels - Needs to be configurable */
62 UINT8 appl_trace_level = APPL_INITIAL_TRACE_LEVEL;
63 UINT8 btif_trace_level = BT_TRACE_LEVEL_NONE;
65 // Communication queue between btu_task and bta.
66 extern fixed_queue_t *btu_bta_msg_queue;
67 void btu_bta_alarm_ready(fixed_queue_t *queue);
69 static const tBTA_SYS_REG bta_sys_hw_reg = {
75 /* type for action functions */
76 typedef void (*tBTA_SYS_ACTION)(tBTA_SYS_HW_MSG *p_data);
78 /* action function list */
79 const tBTA_SYS_ACTION bta_sys_action[] = {
80 /* device manager local device API events - cf bta_sys.h for events */
81 bta_sys_hw_api_enable, /* 0 BTA_SYS_HW_API_ENABLE_EVT */
82 bta_sys_hw_evt_enabled, /* 1 BTA_SYS_HW_EVT_ENABLED_EVT */
83 bta_sys_hw_evt_stack_enabled, /* 2 BTA_SYS_HW_EVT_STACK_ENABLED_EVT */
84 bta_sys_hw_api_disable, /* 3 BTA_SYS_HW_API_DISABLE_EVT */
85 bta_sys_hw_evt_disabled, /* 4 BTA_SYS_HW_EVT_DISABLED_EVT */
86 bta_sys_hw_error /* 5 BTA_SYS_HW_ERROR_EVT */
89 /* state machine action enumeration list */
91 /* device manager local device API events */
92 BTA_SYS_HW_API_ENABLE,
93 BTA_SYS_HW_EVT_ENABLED,
94 BTA_SYS_HW_EVT_STACK_ENABLED,
95 BTA_SYS_HW_API_DISABLE,
96 BTA_SYS_HW_EVT_DISABLED,
100 #define BTA_SYS_NUM_ACTIONS (BTA_SYS_MAX_EVT & 0x00ff)
101 #define BTA_SYS_IGNORE BTA_SYS_NUM_ACTIONS
103 /* state table information */
104 #define BTA_SYS_ACTIONS 2 /* number of actions */
105 #define BTA_SYS_NEXT_STATE 2 /* position of next state */
106 #define BTA_SYS_NUM_COLS 3 /* number of columns in state tables */
109 /* state table for OFF state */
110 const UINT8 bta_sys_hw_off[][BTA_SYS_NUM_COLS] = {
111 /* Event Action 1 Action 2 Next State */
112 /* API_ENABLE */ {BTA_SYS_HW_API_ENABLE, BTA_SYS_IGNORE, BTA_SYS_HW_STARTING},
113 /* EVT_ENABLED */ {BTA_SYS_IGNORE, BTA_SYS_IGNORE, BTA_SYS_HW_STARTING},
114 /* STACK_ENABLED */ {BTA_SYS_IGNORE, BTA_SYS_IGNORE, BTA_SYS_HW_ON},
115 /* API_DISABLE */ {BTA_SYS_HW_EVT_DISABLED, BTA_SYS_IGNORE, BTA_SYS_HW_OFF},
116 /* EVT_DISABLED */ {BTA_SYS_IGNORE, BTA_SYS_IGNORE, BTA_SYS_HW_OFF},
117 /* EVT_ERROR */ {BTA_SYS_IGNORE, BTA_SYS_IGNORE, BTA_SYS_HW_OFF}
120 const UINT8 bta_sys_hw_starting[][BTA_SYS_NUM_COLS] = {
121 /* Event Action 1 Action 2 Next State */
122 /* API_ENABLE */ {BTA_SYS_IGNORE, BTA_SYS_IGNORE, BTA_SYS_HW_STARTING}, /* wait for completion event */
123 /* EVT_ENABLED */ {BTA_SYS_HW_EVT_ENABLED, BTA_SYS_IGNORE, BTA_SYS_HW_STARTING},
124 /* STACK_ENABLED */ {BTA_SYS_HW_EVT_STACK_ENABLED, BTA_SYS_IGNORE, BTA_SYS_HW_ON},
125 /* API_DISABLE */ {BTA_SYS_IGNORE, BTA_SYS_IGNORE, BTA_SYS_HW_STOPPING}, /* successive disable/enable: change state wait for completion to disable */
126 /* EVT_DISABLED */ {BTA_SYS_HW_EVT_DISABLED, BTA_SYS_HW_API_ENABLE, BTA_SYS_HW_STARTING}, /* successive enable/disable: notify, then restart HW */
127 /* EVT_ERROR */ {BTA_SYS_HW_ERROR, BTA_SYS_IGNORE, BTA_SYS_HW_ON}
130 const UINT8 bta_sys_hw_on[][BTA_SYS_NUM_COLS] = {
131 /* Event Action 1 Action 2 Next State */
132 /* API_ENABLE */ {BTA_SYS_HW_API_ENABLE, BTA_SYS_IGNORE, BTA_SYS_HW_ON},
133 /* EVT_ENABLED */ {BTA_SYS_IGNORE, BTA_SYS_IGNORE, BTA_SYS_HW_ON},
134 /* STACK_ENABLED */ {BTA_SYS_IGNORE, BTA_SYS_IGNORE, BTA_SYS_HW_ON},
135 /* API_DISABLE */ {BTA_SYS_HW_API_DISABLE, BTA_SYS_IGNORE, BTA_SYS_HW_ON}, /* don't change the state here, as some other modules might be active */
136 /* EVT_DISABLED */ {BTA_SYS_HW_ERROR, BTA_SYS_IGNORE, BTA_SYS_HW_ON},
137 /* EVT_ERROR */ {BTA_SYS_HW_ERROR, BTA_SYS_IGNORE, BTA_SYS_HW_ON}
140 const UINT8 bta_sys_hw_stopping[][BTA_SYS_NUM_COLS] = {
141 /* Event Action 1 Action 2 Next State */
142 /* API_ENABLE */ {BTA_SYS_IGNORE, BTA_SYS_IGNORE, BTA_SYS_HW_STARTING}, /* change state, and wait for completion event to enable */
143 /* EVT_ENABLED */ {BTA_SYS_HW_EVT_ENABLED, BTA_SYS_IGNORE, BTA_SYS_HW_STOPPING}, /* successive enable/disable: finish the enable before disabling */
144 /* STACK_ENABLED */ {BTA_SYS_HW_EVT_STACK_ENABLED, BTA_SYS_HW_API_DISABLE, BTA_SYS_HW_STOPPING}, /* successive enable/disable: notify, then stop */
145 /* API_DISABLE */ {BTA_SYS_IGNORE, BTA_SYS_IGNORE, BTA_SYS_HW_STOPPING}, /* wait for completion event */
146 /* EVT_DISABLED */ {BTA_SYS_HW_EVT_DISABLED, BTA_SYS_IGNORE, BTA_SYS_HW_OFF},
147 /* EVT_ERROR */ {BTA_SYS_HW_API_DISABLE, BTA_SYS_IGNORE, BTA_SYS_HW_STOPPING}
150 typedef const UINT8 (*tBTA_SYS_ST_TBL)[BTA_SYS_NUM_COLS];
153 const tBTA_SYS_ST_TBL bta_sys_st_tbl[] = {
160 /*******************************************************************************
162 ** Function bta_sys_init
164 ** Description BTA initialization; called from task initialization.
169 *******************************************************************************/
170 void bta_sys_init(void)
172 memset(&bta_sys_cb, 0, sizeof(tBTA_SYS_CB));
174 pthread_mutex_init(&bta_alarm_lock, NULL);
176 bta_alarm_hash_map = hash_map_new(BTA_ALARM_HASH_MAP_SIZE,
177 hash_function_pointer, NULL, (data_free_fn)osi_alarm_free, NULL);
178 btu_bta_alarm_queue = fixed_queue_new(SIZE_MAX);
180 fixed_queue_register_dequeue(btu_bta_alarm_queue,
181 btu_bta_alarm_ready);
183 appl_trace_level = APPL_INITIAL_TRACE_LEVEL;
185 /* register BTA SYS message handler */
186 bta_sys_register( BTA_ID_SYS, &bta_sys_hw_reg);
188 /* register for BTM notifications */
189 BTM_RegisterForDeviceStatusNotif ((tBTM_DEV_STATUS_CB *)&bta_sys_hw_btm_cback );
191 #if( defined BTA_AR_INCLUDED ) && (BTA_AR_INCLUDED == TRUE)
197 void bta_sys_free(void)
199 fixed_queue_free(btu_bta_alarm_queue, NULL);
200 hash_map_free(bta_alarm_hash_map);
201 pthread_mutex_destroy(&bta_alarm_lock);
204 /*******************************************************************************
206 ** Function bta_dm_sm_execute
208 ** Description State machine event handling function for DM
213 *******************************************************************************/
214 BOOLEAN bta_sys_sm_execute(BT_HDR *p_msg)
216 BOOLEAN freebuf = TRUE;
217 tBTA_SYS_ST_TBL state_table;
221 APPL_TRACE_EVENT("bta_sys_sm_execute state:%d, event:0x%x\n", bta_sys_cb.state, p_msg->event);
223 /* look up the state table for the current state */
224 state_table = bta_sys_st_tbl[bta_sys_cb.state];
226 bta_sys_cb.state = state_table[p_msg->event & 0x00ff][BTA_SYS_NEXT_STATE];
228 /* execute action functions */
229 for (i = 0; i < BTA_SYS_ACTIONS; i++) {
230 if ((action = state_table[p_msg->event & 0x00ff][i]) != BTA_SYS_IGNORE) {
231 (*bta_sys_action[action])( (tBTA_SYS_HW_MSG *) p_msg);
241 void bta_sys_hw_register( tBTA_SYS_HW_MODULE module, tBTA_SYS_HW_CBACK *cback)
243 bta_sys_cb.sys_hw_cback[module] = cback;
247 void bta_sys_hw_unregister( tBTA_SYS_HW_MODULE module )
249 bta_sys_cb.sys_hw_cback[module] = NULL;
252 /*******************************************************************************
254 ** Function bta_sys_hw_btm_cback
256 ** Description This function is registered by BTA SYS to BTM in order to get status notifications
261 *******************************************************************************/
262 void bta_sys_hw_btm_cback( tBTM_DEV_STATUS status )
265 tBTA_SYS_HW_MSG *sys_event;
267 APPL_TRACE_DEBUG(" bta_sys_hw_btm_cback was called with parameter: %i" , status );
269 /* send a message to BTA SYS */
270 if ((sys_event = (tBTA_SYS_HW_MSG *) GKI_getbuf(sizeof(tBTA_SYS_HW_MSG))) != NULL) {
271 if (status == BTM_DEV_STATUS_UP) {
272 sys_event->hdr.event = BTA_SYS_EVT_STACK_ENABLED_EVT;
273 } else if (status == BTM_DEV_STATUS_DOWN) {
274 sys_event->hdr.event = BTA_SYS_ERROR_EVT;
276 /* BTM_DEV_STATUS_CMD_TOUT is ignored for now. */
277 GKI_freebuf (sys_event);
282 bta_sys_sendmsg(sys_event);
285 APPL_TRACE_DEBUG("ERROR bta_sys_hw_btm_cback couldn't send msg" );
291 /*******************************************************************************
293 ** Function bta_sys_hw_error
295 ** Description In case the HW device stops answering... Try to turn it off, then re-enable all
296 ** previously active SW modules.
298 ** Returns success or failure
300 *******************************************************************************/
301 void bta_sys_hw_error(tBTA_SYS_HW_MSG *p_sys_hw_msg)
304 UNUSED(p_sys_hw_msg);
306 APPL_TRACE_DEBUG("%s\n", __FUNCTION__);
308 for (module_index = 0; module_index < BTA_SYS_MAX_HW_MODULES; module_index++) {
309 if ( bta_sys_cb.sys_hw_module_active & ((UINT32)1 << module_index )) {
310 switch ( module_index) {
311 case BTA_SYS_HW_BLUETOOTH:
312 /* Send BTA_SYS_HW_ERROR_EVT to DM */
313 if (bta_sys_cb.sys_hw_cback[module_index] != NULL) {
314 bta_sys_cb.sys_hw_cback[module_index] (BTA_SYS_HW_ERROR_EVT);
318 /* not yet supported */
327 /*******************************************************************************
329 ** Function bta_sys_hw_enable
331 ** Description this function is called after API enable and HW has been turned on
334 ** Returns success or failure
336 *******************************************************************************/
338 void bta_sys_hw_api_enable( tBTA_SYS_HW_MSG *p_sys_hw_msg )
340 if ((!bta_sys_cb.sys_hw_module_active) && (bta_sys_cb.state != BTA_SYS_HW_ON)) {
341 /* register which HW module was turned on */
342 bta_sys_cb.sys_hw_module_active |= ((UINT32)1 << p_sys_hw_msg->hw_module );
344 tBTA_SYS_HW_MSG *p_msg;
345 if ((p_msg = (tBTA_SYS_HW_MSG *) GKI_getbuf(sizeof(tBTA_SYS_HW_MSG))) != NULL) {
346 p_msg->hdr.event = BTA_SYS_EVT_ENABLED_EVT;
347 p_msg->hw_module = p_sys_hw_msg->hw_module;
349 bta_sys_sendmsg(p_msg);
352 /* register which HW module was turned on */
353 bta_sys_cb.sys_hw_module_active |= ((UINT32)1 << p_sys_hw_msg->hw_module );
355 /* HW already in use, so directly notify the caller */
356 if (bta_sys_cb.sys_hw_cback[p_sys_hw_msg->hw_module ] != NULL ) {
357 bta_sys_cb.sys_hw_cback[p_sys_hw_msg->hw_module ]( BTA_SYS_HW_ON_EVT );
361 APPL_TRACE_EVENT ("bta_sys_hw_api_enable for %d, active modules 0x%04X\n",
362 p_sys_hw_msg->hw_module, bta_sys_cb.sys_hw_module_active);
366 /*******************************************************************************
368 ** Function bta_sys_hw_disable
370 ** Description if no other module is using the HW, this function will call ( if defined ) a user-macro to turn off the HW
373 ** Returns success or failure
375 *******************************************************************************/
376 void bta_sys_hw_api_disable(tBTA_SYS_HW_MSG *p_sys_hw_msg)
378 APPL_TRACE_DEBUG("bta_sys_hw_api_disable for %d, active modules: 0x%04X\n",
379 p_sys_hw_msg->hw_module, bta_sys_cb.sys_hw_module_active );
381 /* make sure the related SW blocks were stopped */
382 bta_sys_disable( p_sys_hw_msg->hw_module );
385 /* register which module we turn off */
386 bta_sys_cb.sys_hw_module_active &= ~((UINT32)1 << p_sys_hw_msg->hw_module );
389 /* if there are still some SW modules using the HW, just provide an answer to the calling */
390 if ( bta_sys_cb.sys_hw_module_active != 0 ) {
391 /* if there are still some SW modules using the HW, directly notify the caller */
392 if ( bta_sys_cb.sys_hw_cback[p_sys_hw_msg->hw_module ] != NULL ) {
393 bta_sys_cb.sys_hw_cback[p_sys_hw_msg->hw_module ]( BTA_SYS_HW_OFF_EVT );
396 /* manually update the state of our system */
397 bta_sys_cb.state = BTA_SYS_HW_STOPPING;
399 tBTA_SYS_HW_MSG *p_msg;
400 if ((p_msg = (tBTA_SYS_HW_MSG *) GKI_getbuf(sizeof(tBTA_SYS_HW_MSG))) != NULL) {
401 p_msg->hdr.event = BTA_SYS_EVT_DISABLED_EVT;
402 p_msg->hw_module = p_sys_hw_msg->hw_module;
404 bta_sys_sendmsg(p_msg);
411 /*******************************************************************************
413 ** Function bta_sys_hw_event_enabled
418 ** Returns success or failure
420 *******************************************************************************/
421 void bta_sys_hw_evt_enabled(tBTA_SYS_HW_MSG *p_sys_hw_msg)
423 APPL_TRACE_EVENT("bta_sys_hw_evt_enabled for %i\n", p_sys_hw_msg->hw_module);
424 BTM_DeviceReset( NULL );
428 /*******************************************************************************
430 ** Function bta_sys_hw_event_disabled
435 ** Returns success or failure
437 *******************************************************************************/
438 void bta_sys_hw_evt_disabled(tBTA_SYS_HW_MSG *p_sys_hw_msg)
440 UINT8 hw_module_index;
442 APPL_TRACE_DEBUG("bta_sys_hw_evt_disabled - module 0x%X\n", p_sys_hw_msg->hw_module);
444 for (hw_module_index = 0; hw_module_index < BTA_SYS_MAX_HW_MODULES; hw_module_index++) {
445 if (bta_sys_cb.sys_hw_cback[hw_module_index] != NULL) {
446 bta_sys_cb.sys_hw_cback[hw_module_index] (BTA_SYS_HW_OFF_EVT);
451 /*******************************************************************************
453 ** Function bta_sys_hw_event_stack_enabled
455 ** Description we receive this event once the SW side is ready ( stack, FW download,... ),
456 ** i.e. we can really start using the device. So notify the app.
458 ** Returns success or failure
460 *******************************************************************************/
461 void bta_sys_hw_evt_stack_enabled(tBTA_SYS_HW_MSG *p_sys_hw_msg)
463 UINT8 hw_module_index;
464 UNUSED(p_sys_hw_msg);
466 APPL_TRACE_DEBUG(" bta_sys_hw_evt_stack_enabled!notify the callers\n");
468 for (hw_module_index = 0; hw_module_index < BTA_SYS_MAX_HW_MODULES; hw_module_index++ ) {
469 if (bta_sys_cb.sys_hw_cback[hw_module_index] != NULL) {
470 bta_sys_cb.sys_hw_cback[hw_module_index] (BTA_SYS_HW_ON_EVT);
478 /*******************************************************************************
480 ** Function bta_sys_event
482 ** Description BTA event handler; called from task event handler.
487 *******************************************************************************/
488 void bta_sys_event(BT_HDR *p_msg)
491 BOOLEAN freebuf = TRUE;
493 APPL_TRACE_EVENT("BTA got event 0x%x\n", p_msg->event);
495 /* get subsystem id from event */
496 id = (UINT8) (p_msg->event >> 8);
498 /* verify id and call subsystem event handler */
499 if ((id < BTA_ID_MAX) && (bta_sys_cb.reg[id] != NULL)) {
500 freebuf = (*bta_sys_cb.reg[id]->evt_hdlr)(p_msg);
502 APPL_TRACE_WARNING("BTA got unregistered event id %d\n", id);
511 /*******************************************************************************
513 ** Function bta_sys_register
515 ** Description Called by other BTA subsystems to register their event
521 *******************************************************************************/
522 void bta_sys_register(UINT8 id, const tBTA_SYS_REG *p_reg)
524 bta_sys_cb.reg[id] = (tBTA_SYS_REG *) p_reg;
525 bta_sys_cb.is_reg[id] = TRUE;
528 /*******************************************************************************
530 ** Function bta_sys_deregister
532 ** Description Called by other BTA subsystems to de-register
538 *******************************************************************************/
539 void bta_sys_deregister(UINT8 id)
541 bta_sys_cb.is_reg[id] = FALSE;
544 /*******************************************************************************
546 ** Function bta_sys_is_register
548 ** Description Called by other BTA subsystems to get registeration
554 *******************************************************************************/
555 BOOLEAN bta_sys_is_register(UINT8 id)
557 return bta_sys_cb.is_reg[id];
560 /*******************************************************************************
562 ** Function bta_sys_sendmsg
564 ** Description Send a GKI message to BTA. This function is designed to
565 ** optimize sending of messages to BTA. It is called by BTA
566 ** API functions and call-in functions.
571 *******************************************************************************/
572 void bta_sys_sendmsg(void *p_msg)
574 // There is a race condition that occurs if the stack is shut down while
575 // there is a procedure in progress that can schedule a task via this
576 // message queue. This causes |btu_bta_msg_queue| to get cleaned up before
577 // it gets used here; hence we check for NULL before using it.
578 if (btu_bta_msg_queue) {
579 fixed_queue_enqueue(btu_bta_msg_queue, p_msg);
580 //ke_event_set(KE_EVENT_BTU_TASK_THREAD);
581 btu_task_post(SIG_BTU_WORK);
585 /*******************************************************************************
587 ** Function bta_sys_start_timer
589 ** Description Start a protocol timer for the specified amount
590 ** of time in milliseconds.
594 *******************************************************************************/
595 void bta_alarm_cb(void *data)
597 assert(data != NULL);
598 TIMER_LIST_ENT *p_tle = (TIMER_LIST_ENT *)data;
600 fixed_queue_enqueue(btu_bta_alarm_queue, p_tle);
602 btu_task_post(SIG_BTU_WORK);
605 void bta_sys_start_timer(TIMER_LIST_ENT *p_tle, UINT16 type, INT32 timeout_ms)
607 assert(p_tle != NULL);
609 // Get the alarm for this p_tle.
610 pthread_mutex_lock(&bta_alarm_lock);
611 if (!hash_map_has_key(bta_alarm_hash_map, p_tle)) {
612 hash_map_set(bta_alarm_hash_map, p_tle, osi_alarm_new("bta_sys", bta_alarm_cb, p_tle, 0, false));
614 pthread_mutex_unlock(&bta_alarm_lock);
616 osi_alarm_t *alarm = hash_map_get(bta_alarm_hash_map, p_tle);
618 LOG_ERROR("%s unable to create alarm.", __func__);
623 p_tle->ticks = timeout_ms;
624 //osi_alarm_set(alarm, (period_ms_t)timeout_ms, bta_alarm_cb, p_tle);
625 osi_alarm_set(alarm, (period_ms_t)timeout_ms);
628 bool hash_iter_ro_cb(hash_map_entry_t *hash_map_entry, void *context)
630 osi_alarm_t *alarm = (osi_alarm_t *)hash_map_entry->data;
631 period_ms_t *p_remaining_ms = (period_ms_t *)context;
632 *p_remaining_ms += osi_alarm_get_remaining_ms(alarm);
636 UINT32 bta_sys_get_remaining_ticks(TIMER_LIST_ENT *p_target_tle)
638 period_ms_t remaining_ms = 0;
639 pthread_mutex_lock(&bta_alarm_lock);
640 // Get the alarm for this p_tle
641 hash_map_foreach(bta_alarm_hash_map, hash_iter_ro_cb, &remaining_ms);
642 pthread_mutex_unlock(&bta_alarm_lock);
647 /*******************************************************************************
649 ** Function bta_sys_stop_timer
651 ** Description Stop a BTA timer.
655 *******************************************************************************/
656 void bta_sys_stop_timer(TIMER_LIST_ENT *p_tle)
658 assert(p_tle != NULL);
660 osi_alarm_t *alarm = hash_map_get(bta_alarm_hash_map, p_tle);
662 LOG_DEBUG("%s expected alarm was not in bta alarm hash map.", __func__);
665 osi_alarm_cancel(alarm);
668 /*******************************************************************************
670 ** Function bta_sys_disable
672 ** Description For each registered subsystem execute its disable function.
676 *******************************************************************************/
677 void bta_sys_disable(tBTA_SYS_HW_MODULE module)
682 APPL_TRACE_DEBUG("bta_sys_disable: module %i", module);
685 case BTA_SYS_HW_BLUETOOTH:
687 bta_id_max = BTA_ID_BLUETOOTH_MAX;
690 APPL_TRACE_WARNING("bta_sys_disable: unkown module");
694 for ( ; bta_id <= bta_id_max; bta_id++) {
695 if (bta_sys_cb.reg[bta_id] != NULL) {
696 if (bta_sys_cb.is_reg[bta_id] == TRUE && bta_sys_cb.reg[bta_id]->disable != NULL) {
697 (*bta_sys_cb.reg[bta_id]->disable)();
703 /*******************************************************************************
705 ** Function bta_sys_set_trace_level
707 ** Description Set trace level for BTA
711 *******************************************************************************/
712 void bta_sys_set_trace_level(UINT8 level)
714 appl_trace_level = level;
717 /*******************************************************************************
719 ** Function bta_sys_get_sys_features
721 ** Description Returns sys_features to other BTA modules.
723 ** Returns sys_features
725 *******************************************************************************/
726 UINT16 bta_sys_get_sys_features (void)
728 return bta_sys_cb.sys_features;