Home | History | Annotate | Download | only in hh
      1 /******************************************************************************
      2  *
      3  *  Copyright (C) 2005-2012 Broadcom Corporation
      4  *
      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:
      8  *
      9  *  http://www.apache.org/licenses/LICENSE-2.0
     10  *
     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.
     16  *
     17  ******************************************************************************/
     18 
     19 /******************************************************************************
     20  *
     21  *  This file contains the HID host action functions.
     22  *
     23  ******************************************************************************/
     24 
     25 #include "bt_target.h"
     26 
     27 #if defined(BTA_HH_INCLUDED) && (BTA_HH_INCLUDED == TRUE)
     28 
     29 #include <string.h>
     30 
     31 #include "bta_sys.h"
     32 #include "btm_api.h"
     33 #include "l2c_api.h"
     34 #include "bta_hh_int.h"
     35 #include "bta_hh_co.h"
     36 
     37 /*****************************************************************************
     38 **  Constants
     39 *****************************************************************************/
     40 
     41 
     42 /*****************************************************************************
     43 **  Local Function prototypes
     44 *****************************************************************************/
     45 static void bta_hh_cback (UINT8 dev_handle, BD_ADDR addr, UINT8 event,
     46                             UINT32 data, BT_HDR *pdata);
     47 static tBTA_HH_STATUS bta_hh_get_trans_status(UINT32 result);
     48 
     49 #if BTA_HH_DEBUG
     50 static char* bta_hh_get_w4_event(UINT16 event);
     51 static char * bta_hh_hid_event_name(UINT16 event);
     52 #endif
     53 
     54 /*****************************************************************************
     55 **  Action Functions
     56 *****************************************************************************/
     57 /*******************************************************************************
     58 **
     59 ** Function         bta_hh_api_enable
     60 **
     61 ** Description      Perform necessary operations to enable HID host.
     62 **
     63 **
     64 ** Returns          void
     65 **
     66 *******************************************************************************/
     67 void bta_hh_api_enable(tBTA_HH_DATA *p_data)
     68 {
     69     tBTA_HH_STATUS      status = BTA_HH_ERR;
     70     UINT8               xx;
     71 
     72     /* initialize BTE HID */
     73     HID_HostInit();
     74 
     75     memset(&bta_hh_cb, 0, sizeof(tBTA_HH_CB));
     76 
     77     HID_HostSetSecurityLevel("", p_data->api_enable.sec_mask);
     78 
     79     /* Register with L2CAP */
     80     if ( HID_HostRegister (bta_hh_cback) == HID_SUCCESS)
     81     {
     82         /* store parameters */
     83         bta_hh_cb.p_cback = p_data->api_enable.p_cback;
     84 
     85         status = BTA_HH_OK;
     86         /* initialize device CB */
     87         for (xx = 0; xx < BTA_HH_MAX_DEVICE; xx ++)
     88         {
     89             bta_hh_cb.kdev[xx].state        = BTA_HH_IDLE_ST;
     90             bta_hh_cb.kdev[xx].hid_handle   = BTA_HH_INVALID_HANDLE;
     91             bta_hh_cb.kdev[xx].index        = xx;
     92         }
     93 
     94         /* initialize control block map */
     95         for (xx = 0; xx < BTA_HH_MAX_KNOWN; xx ++)
     96             bta_hh_cb.cb_index[xx]          = BTA_HH_IDX_INVALID;
     97     }
     98 
     99 #if (BTA_HH_LE_INCLUDED == TRUE)
    100     if (status == BTA_HH_OK)
    101     {
    102         bta_hh_le_enable();
    103     }
    104     else
    105 #endif
    106         /* signal BTA call back event */
    107         (* bta_hh_cb.p_cback)(BTA_HH_ENABLE_EVT, (tBTA_HH *)&status);
    108 }
    109 /*******************************************************************************
    110 **
    111 ** Function         bta_hh_api_disable
    112 **
    113 ** Description      Perform necessary operations to disable HID host.
    114 **
    115 **
    116 ** Returns          void
    117 **
    118 *******************************************************************************/
    119 void bta_hh_api_disable(void)
    120 {
    121     UINT8 xx;
    122 
    123     /* service is not enabled */
    124     if (bta_hh_cb.p_cback == NULL)
    125         return;
    126 
    127     /* no live connection, signal DISC_CMPL_EVT directly */
    128     if (!bta_hh_cb.cnt_num)
    129     {
    130         bta_hh_disc_cmpl();
    131     }
    132     else /* otherwise, disconnect all live connections */
    133     {
    134         bta_hh_cb.w4_disable = TRUE;
    135 
    136         for(xx = 0; xx < BTA_HH_MAX_DEVICE; xx ++)
    137         {
    138             /* send API_CLOSE event to every connected device */
    139             if ( bta_hh_cb.kdev[xx].state == BTA_HH_CONN_ST )
    140             {
    141                 /* disconnect all connected devices */
    142                 bta_hh_sm_execute(&bta_hh_cb.kdev[xx],
    143                                 BTA_HH_API_CLOSE_EVT,
    144                                 NULL);
    145             }
    146         }
    147     }
    148 
    149     return;
    150 }
    151 
    152 /*******************************************************************************
    153 **
    154 ** Function         bta_hh_disc_cmpl
    155 **
    156 ** Description      All connections have been closed, disable service.
    157 **
    158 **
    159 ** Returns          void
    160 **
    161 *******************************************************************************/
    162 void bta_hh_disc_cmpl(void)
    163 {
    164     tBTA_HH_STATUS  status = BTA_HH_OK;
    165 
    166     /* Deregister with lower layer */
    167     if (HID_HostDeregister()!= HID_SUCCESS)
    168         status = BTA_HH_ERR;
    169 
    170 #if (BTA_HH_LE_INCLUDED == TRUE)
    171     bta_hh_le_deregister();
    172     return;
    173 #endif
    174 
    175     bta_hh_cleanup_disable(status);
    176 }
    177 
    178 /*******************************************************************************
    179 **
    180 ** Function         bta_hh_sdp_cback
    181 **
    182 ** Description      SDP callback function.
    183 **
    184 ** Returns          void
    185 **
    186 *******************************************************************************/
    187 static void bta_hh_sdp_cback(UINT16 result, UINT16 attr_mask,
    188                                   tHID_DEV_SDP_INFO *sdp_rec )
    189 {
    190     tBTA_HH_DEV_CB     *p_cb = bta_hh_cb.p_cur;
    191     UINT8              hdl;
    192     tBTA_HH_STATUS    status = BTA_HH_ERR_SDP;
    193 
    194     /* make sure sdp succeeded and hh has not been disabled */
    195     if ((result == SDP_SUCCESS) && (p_cb != NULL))
    196     {
    197         /* security is required for the connection, add attr_mask bit*/
    198         if (p_cb->sec_mask)
    199             attr_mask |= HID_SEC_REQUIRED;
    200 
    201 #if BTA_HH_DEBUG
    202         APPL_TRACE_EVENT4("bta_hh_sdp_cback: p_cb: %d result 0x%02x, \
    203                             attr_mask 0x%02x, handle %x", \
    204                             p_cb, result, attr_mask,p_cb->hid_handle);
    205 #endif
    206 
    207         /* check to see type of device is supported , and should not been added before */
    208         if (bta_hh_tod_spt(p_cb, sdp_rec->sub_class))
    209         {
    210             /* if not added before */
    211             if (p_cb->hid_handle == BTA_HH_INVALID_HANDLE)
    212             {
    213                 /*  add device/update attr_mask information */
    214                 if(HID_HostAddDev (p_cb->addr, attr_mask, &hdl) == HID_SUCCESS)
    215                 {
    216                     status = BTA_HH_OK;
    217                     /* update cb_index[] map */
    218                     bta_hh_cb.cb_index[hdl] = p_cb->index;
    219                 }
    220                 else
    221                 {
    222                     p_cb->app_id = 0;
    223                 }
    224             }
    225             /* else : incoming connection after SDP should update the SDP information as well */
    226 
    227             if (p_cb->app_id != 0)
    228             {
    229                 /* update cb information with attr_mask, dscp_info etc. */
    230                 bta_hh_add_device_to_list(p_cb,  hdl, attr_mask,
    231                                             &sdp_rec->dscp_info,
    232                                             sdp_rec->sub_class,
    233                                             sdp_rec->ssr_max_latency,
    234                                             sdp_rec->ssr_min_tout,
    235                                             p_cb->app_id);
    236 
    237                 p_cb->dscp_info.ctry_code = sdp_rec->ctry_code;
    238 
    239                 status = BTA_HH_OK;
    240             }
    241 
    242         }
    243         else /* type of device is not supported */
    244             status = BTA_HH_ERR_TOD_UNSPT;
    245     }
    246 
    247     /* free disc_db when SDP is completed */
    248     utl_freebuf((void **)&bta_hh_cb.p_disc_db);
    249 
    250     /* send SDP_CMPL_EVT into state machine */
    251     bta_hh_sm_execute(p_cb, BTA_HH_SDP_CMPL_EVT, (tBTA_HH_DATA *)&status);
    252 
    253     return;
    254 }
    255 /*******************************************************************************
    256 **
    257 ** Function         bta_hh_di_sdp_cback
    258 **
    259 ** Description      SDP DI callback function.
    260 **
    261 ** Returns          void
    262 **
    263 *******************************************************************************/
    264 static void bta_hh_di_sdp_cback(UINT16 result)
    265 {
    266     tBTA_HH_DEV_CB     *p_cb = bta_hh_cb.p_cur;
    267     tBTA_HH_STATUS         status = BTA_HH_ERR_SDP;
    268     tSDP_DI_GET_RECORD  di_rec;
    269     tHID_STATUS ret;
    270 #if BTA_HH_DEBUG
    271     APPL_TRACE_EVENT2("bta_hh_di_sdp_cback: p_cb: %d result 0x%02x", p_cb, result);
    272 #endif
    273 
    274     /* if DI record does not exist on remote device, vendor_id in tBTA_HH_DEV_DSCP_INFO will be
    275          * set to 0xffff and we will allow the connection to go through. Spec mandates that DI
    276          * record be set, but many HID devices do not set this. So for IOP purposes, we allow the
    277          * connection to go through and update the DI record to invalid DI entry.*/
    278     if (((result == SDP_SUCCESS) || (result == SDP_NO_RECS_MATCH)) && (p_cb != NULL))
    279     {
    280         if(result == SDP_SUCCESS && SDP_GetNumDiRecords(bta_hh_cb.p_disc_db) != 0)
    281         {
    282             /* always update information with primary DI record */
    283             if (SDP_GetDiRecord(1, &di_rec, bta_hh_cb.p_disc_db) == SDP_SUCCESS)
    284             {
    285                 bta_hh_update_di_info(p_cb, di_rec.rec.vendor, di_rec.rec.product, di_rec.rec.version, 0);
    286             }
    287 
    288         }
    289         else /* no DI recrod available */
    290         {
    291             bta_hh_update_di_info(p_cb, BTA_HH_VENDOR_ID_INVALID, 0, 0, 0);
    292         }
    293 
    294         if ((ret = HID_HostGetSDPRecord(p_cb->addr,
    295                                  bta_hh_cb.p_disc_db,
    296                                  p_bta_hh_cfg->sdp_db_size,
    297                                  bta_hh_sdp_cback)) == HID_SUCCESS)
    298         {
    299             status = BTA_HH_OK;
    300         }
    301         else
    302         {
    303 #if BTA_HH_DEBUG
    304             APPL_TRACE_DEBUG1 ("bta_hh_di_sdp_cback:  HID_HostGetSDPRecord failed: Status 0x%2x",
    305                                ret);
    306 #endif
    307         }
    308     }
    309 
    310 
    311     if (status != BTA_HH_OK)
    312     {
    313         utl_freebuf((void **)&bta_hh_cb.p_disc_db);
    314         /* send SDP_CMPL_EVT into state machine */
    315         bta_hh_sm_execute(p_cb, BTA_HH_SDP_CMPL_EVT, (tBTA_HH_DATA *)&status);
    316     }
    317     return;
    318 
    319 }
    320 
    321 
    322 /*******************************************************************************
    323 **
    324 ** Function         bta_hh_start_sdp
    325 **
    326 ** Description      Start SDP service search, and obtain necessary SDP records.
    327 **                  Only one SDP service search request is allowed at the same
    328 **                  time. For every BTA_HhOpen API call, do SDP first unless SDP
    329 **                  has been done previously.
    330 **
    331 ** Returns          void
    332 **
    333 *******************************************************************************/
    334 void bta_hh_start_sdp(tBTA_HH_DEV_CB *p_cb, tBTA_HH_DATA *p_data)
    335 {
    336     tBTA_HH_STATUS          status = BTA_HH_ERR_SDP;
    337     UINT8                   hdl;
    338 
    339     p_cb->sec_mask  = p_data->api_conn.sec_mask;
    340     p_cb->mode      = p_data->api_conn.mode;
    341     bta_hh_cb.p_cur = p_cb;
    342 
    343 #if (BTA_HH_LE_INCLUDED == TRUE)
    344     if (bta_hh_is_le_device(p_cb, p_data->api_conn.bd_addr))
    345     {
    346         bta_hh_le_open_conn(p_cb, p_data->api_conn.bd_addr);
    347         return;
    348     }
    349 #endif
    350 
    351     /* if previously virtually cabled device, skip SDP */
    352     if (p_cb->app_id)
    353     {
    354         status = BTA_HH_OK;
    355 #if BTA_HH_DEBUG
    356         APPL_TRACE_DEBUG0("bta_hh_start_sdp:: skip SDP for known devices");
    357 #endif
    358         if (p_cb->hid_handle == BTA_HH_INVALID_HANDLE)
    359         {
    360             if (HID_HostAddDev (p_cb->addr, p_cb->attr_mask, &hdl) \
    361                 == HID_SUCCESS)
    362             {
    363                 /* update device CB with newly register device handle */
    364                 bta_hh_add_device_to_list(p_cb,  hdl, p_cb->attr_mask, NULL,
    365                                           p_cb->sub_class,
    366                                           p_cb->dscp_info.ssr_max_latency,
    367                                           p_cb->dscp_info.ssr_min_tout,
    368                                           p_cb->app_id);
    369                 /* update cb_index[] map */
    370                 bta_hh_cb.cb_index[hdl] = p_cb->index;
    371             }
    372             else
    373                 status = BTA_HH_ERR_NO_RES;
    374         }
    375         bta_hh_sm_execute(p_cb, BTA_HH_SDP_CMPL_EVT, (tBTA_HH_DATA *)&status);
    376 
    377         return;
    378     }
    379     /* GetSDPRecord. at one time only one SDP precedure can be active */
    380     else if (!bta_hh_cb.p_disc_db)
    381     {
    382         bta_hh_cb.p_disc_db = (tSDP_DISCOVERY_DB *) GKI_getbuf(p_bta_hh_cfg->sdp_db_size);
    383 
    384         if (bta_hh_cb.p_disc_db == NULL)
    385         {
    386             status = BTA_HH_ERR_NO_RES;
    387         }
    388         else
    389         {
    390             bta_hh_cb.p_cur = p_cb;
    391             /* do DI discovery first */
    392             if (SDP_DiDiscover(p_data->api_conn.bd_addr,
    393                                          bta_hh_cb.p_disc_db,
    394                                          p_bta_hh_cfg->sdp_db_size,
    395                                          bta_hh_di_sdp_cback) != SDP_SUCCESS)
    396             {
    397 #if BTA_HH_DEBUG
    398                 APPL_TRACE_DEBUG1 ("bta_hh_start_sdp:  SDP_DiDiscover failed: \
    399                     Status 0x%2X",status);
    400 #endif
    401                 status = BTA_HH_ERR_SDP;
    402                 utl_freebuf((void **)&bta_hh_cb.p_disc_db);
    403             }
    404             else
    405                 status = BTA_HH_OK;
    406         }
    407     }
    408 
    409     if (status != BTA_HH_OK)
    410         bta_hh_sm_execute(p_cb, BTA_HH_SDP_CMPL_EVT, (tBTA_HH_DATA *)&status);
    411 
    412     return;
    413 
    414 }
    415 /*******************************************************************************
    416 **
    417 ** Function         bta_hh_sdp_cmpl
    418 **
    419 ** Description      When SDP completed, initiate a connection or report error depend
    420 **                  on SDP result.
    421 **
    422 **
    423 ** Returns          void
    424 **
    425 *******************************************************************************/
    426 void bta_hh_sdp_cmpl(tBTA_HH_DEV_CB *p_cb, tBTA_HH_DATA *p_data)
    427 {
    428     tBTA_HH_CONN            conn_dat;
    429     tBTA_HH_STATUS          status = p_data->status;
    430 
    431 #if BTA_HH_DEBUG
    432     APPL_TRACE_DEBUG1 ("bta_hh_sdp_cmpl:  status 0x%2X",p_data->status);
    433 #endif
    434 
    435     /* initialize call back data */
    436     memset((void *)&conn_dat, 0, sizeof(tBTA_HH_CONN));
    437     conn_dat.handle = p_cb->hid_handle;
    438     bdcpy(conn_dat.bda, p_cb->addr);
    439 
    440     /* if SDP compl success */
    441     if ( status == BTA_HH_OK)
    442     {
    443         /* not incoming connection doing SDP, initiate a HID connection */
    444         if (!p_cb->incoming_conn)
    445         {
    446             tHID_STATUS ret;
    447             /* set security level */
    448             HID_HostSetSecurityLevel("", p_cb->sec_mask);
    449 
    450             /* open HID connection */
    451             if ((ret = HID_HostOpenDev (p_cb->hid_handle)) != HID_SUCCESS)
    452             {
    453 #if BTA_HH_DEBUG
    454                 APPL_TRACE_DEBUG1 ("bta_hh_sdp_cmpl:  HID_HostOpenDev failed: \
    455                     Status 0x%2X",ret);
    456 #endif
    457                 /* open fail, remove device from management device list */
    458                 HID_HostRemoveDev( p_cb->hid_handle);
    459                 status = BTA_HH_ERR;
    460             }
    461             else
    462             {
    463                 status = BTA_HH_OK;
    464             }
    465         }
    466         else /* incoming connection SDP finish */
    467         {
    468             bta_hh_sm_execute(p_cb, BTA_HH_OPEN_CMPL_EVT, NULL);
    469         }
    470     }
    471 
    472     if (status != BTA_HH_OK)
    473     {
    474         /* Check if this was incoming connection request  from an unknown device
    475            **and connection failed due to missing HID Device SDP UUID
    476            **In above condition, disconnect the link as well as remove the
    477            **device from list of HID devices*/
    478         if ((status == BTA_HH_ERR_SDP) &&
    479            (p_cb->incoming_conn) &&(p_cb->app_id == 0))
    480         {
    481             APPL_TRACE_DEBUG1 ("bta_hh_sdp_cmpl:SDP failed for  incoming conn :hndl %d",
    482                                 p_cb->incoming_hid_handle);
    483             HID_HostRemoveDev( p_cb->incoming_hid_handle);
    484         }
    485         conn_dat.status = status;
    486         (* bta_hh_cb.p_cback)(BTA_HH_OPEN_EVT, (tBTA_HH *)&conn_dat);
    487 
    488         /* move state machine W4_CONN ->IDLE */
    489         bta_hh_sm_execute(p_cb, BTA_HH_API_CLOSE_EVT, NULL);
    490 
    491         /* if this is an outgoing connection to an unknown device, clean up cb */
    492         if (p_cb->app_id == 0 && !p_cb->incoming_conn)
    493         {
    494             /* clean up device control block */
    495             bta_hh_clean_up_kdev(p_cb);
    496         }
    497 #if BTA_HH_DEBUG
    498         bta_hh_trace_dev_db();
    499 #endif
    500     }
    501     return;
    502 }
    503 
    504 /*******************************************************************************
    505 **
    506 ** Function         bta_hh_api_disc_act
    507 **
    508 ** Description      HID Host initiate a disconnection.
    509 **
    510 **
    511 ** Returns          void
    512 **
    513 *******************************************************************************/
    514 void bta_hh_api_disc_act(tBTA_HH_DEV_CB *p_cb, tBTA_HH_DATA *p_data)
    515 {
    516     tBTA_HH_CBDATA    disc_dat;
    517     tHID_STATUS     status;
    518 
    519 #if BTA_HH_LE_INCLUDED == TRUE
    520     if (p_cb->is_le_device)
    521         bta_hh_le_api_disc_act(p_cb);
    522     else
    523 #endif
    524     {
    525         /* found an active connection */
    526         disc_dat.handle = p_data ?(UINT8)p_data->hdr.layer_specific :p_cb->hid_handle;
    527         disc_dat.status = BTA_HH_ERR;
    528 
    529         status = HID_HostCloseDev(disc_dat.handle);
    530 
    531         if (status)
    532             (* bta_hh_cb.p_cback)(BTA_HH_CLOSE_EVT, (tBTA_HH *)&disc_dat);
    533     }
    534 
    535     return;
    536 
    537 }
    538 /*******************************************************************************
    539 **
    540 ** Function         bta_hh_open_cmpl_act
    541 **
    542 ** Description      HID host connection completed
    543 **
    544 **
    545 ** Returns          void
    546 **
    547 *******************************************************************************/
    548 void bta_hh_open_cmpl_act(tBTA_HH_DEV_CB *p_cb, tBTA_HH_DATA *p_data)
    549 {
    550     tBTA_HH_CONN        conn ;
    551     UINT8   dev_handle = p_data ? (UINT8)p_data->hid_cback.hdr.layer_specific : \
    552                         p_cb->hid_handle;
    553 
    554     memset((void *)&conn, 0, sizeof (tBTA_HH_CONN));
    555     conn.handle = dev_handle;
    556     bdcpy(conn.bda, p_cb->addr);
    557 
    558     /* increase connection number */
    559     bta_hh_cb.cnt_num ++;
    560 
    561     /* initialize device driver */
    562     bta_hh_co_open(p_cb->hid_handle, p_cb->sub_class,
    563                        p_cb->attr_mask,  p_cb->app_id);
    564 
    565 #if (BTA_HH_LE_INCLUDED == TRUE)
    566     conn.status = p_cb->status;
    567     conn.le_hid = p_cb->is_le_device;
    568     conn.scps_supported = p_cb->scps_supported;
    569 
    570     if (!p_cb->is_le_device)
    571 #endif
    572     {
    573         /* inform role manager */
    574         bta_sys_conn_open( BTA_ID_HH ,p_cb->app_id, p_cb->addr);
    575     }
    576     /* set protocol mode when not default report mode */
    577     if ( p_cb->mode != BTA_HH_PROTO_RPT_MODE
    578 #if (BTA_HH_LE_INCLUDED == TRUE)
    579          && !p_cb->is_le_device
    580 #endif
    581         )
    582     {
    583         if ((HID_HostWriteDev(dev_handle,
    584                               HID_TRANS_SET_PROTOCOL, HID_PAR_PROTOCOL_BOOT_MODE,
    585                               0,
    586                               0, NULL)) != HID_SUCCESS)
    587         {
    588             /* HID connection is up, while SET_PROTO fail */
    589             conn.status = BTA_HH_ERR_PROTO;
    590             (* bta_hh_cb.p_cback)(BTA_HH_OPEN_EVT, (tBTA_HH *)&conn);
    591         }
    592         else
    593         {
    594             conn.status = BTA_HH_OK;
    595             p_cb->w4_evt = BTA_HH_OPEN_EVT;
    596         }
    597     }
    598     else
    599         (* bta_hh_cb.p_cback)(BTA_HH_OPEN_EVT, (tBTA_HH *)&conn);
    600 
    601     p_cb->incoming_conn = FALSE;
    602     p_cb->incoming_hid_handle = BTA_HH_INVALID_HANDLE;
    603 
    604 }
    605 /*******************************************************************************
    606 **
    607 ** Function         bta_hh_open_act
    608 **
    609 ** Description      HID host receive HID_OPEN_EVT .
    610 **
    611 **
    612 ** Returns          void
    613 **
    614 *******************************************************************************/
    615 void bta_hh_open_act(tBTA_HH_DEV_CB *p_cb, tBTA_HH_DATA *p_data)
    616 {
    617     tBTA_HH_API_CONN    conn_data;
    618 
    619     UINT8   dev_handle = p_data ? (UINT8)p_data->hid_cback.hdr.layer_specific : \
    620                         p_cb->hid_handle;
    621 
    622 #if BTA_HH_DEBUG
    623     APPL_TRACE_EVENT1 ("bta_hh_open_act:  Device[%d] connected", dev_handle);
    624 #endif
    625 
    626     /* SDP has been done */
    627     if (p_cb->app_id != 0)
    628     {
    629         bta_hh_sm_execute(p_cb, BTA_HH_OPEN_CMPL_EVT, p_data);
    630     }
    631     else
    632     /*  app_id == 0 indicates an incoming conenction request arrives without SDP
    633         performed, do it first */
    634     {
    635         p_cb->incoming_conn = TRUE;
    636         /* store the handle here in case sdp fails - need to disconnect */
    637         p_cb->incoming_hid_handle = dev_handle;
    638 
    639         memset(&conn_data, 0, sizeof(tBTA_HH_API_CONN));
    640         bdcpy(conn_data.bd_addr, p_cb->addr);
    641         bta_hh_start_sdp(p_cb, (tBTA_HH_DATA *)&conn_data);
    642     }
    643 
    644     return;
    645 }
    646 
    647 
    648 /*******************************************************************************
    649 **
    650 ** Function         bta_hh_data_act
    651 **
    652 ** Description      HID Host process a data report
    653 **
    654 **
    655 ** Returns          void
    656 **
    657 *******************************************************************************/
    658 void bta_hh_data_act(tBTA_HH_DEV_CB *p_cb, tBTA_HH_DATA * p_data)
    659 {
    660     BT_HDR  *pdata = p_data->hid_cback.p_data;
    661     UINT8   *p_rpt = (UINT8 *)(pdata + 1) + pdata->offset;
    662 
    663     bta_hh_co_data((UINT8)p_data->hid_cback.hdr.layer_specific, p_rpt, pdata->len,
    664                     p_cb->mode, p_cb->sub_class, p_cb->dscp_info.ctry_code, p_cb->addr, p_cb->app_id);
    665 
    666     utl_freebuf((void **)&pdata);
    667 }
    668 
    669 
    670 /*******************************************************************************
    671 **
    672 ** Function         bta_hh_handsk_act
    673 **
    674 ** Description      HID Host process a handshake acknoledgement.
    675 **
    676 **
    677 ** Returns          void
    678 **
    679 *******************************************************************************/
    680 void bta_hh_handsk_act(tBTA_HH_DEV_CB *p_cb, tBTA_HH_DATA * p_data)
    681 {
    682     tBTA_HH_CBDATA  cback_data ;
    683     tBTA_HH_HSDATA  hs_data;
    684     tBTA_HH_CONN    conn ;
    685 
    686 #if BTA_HH_DEBUG
    687     APPL_TRACE_DEBUG2("HANDSHAKE received for: event = %s data= %d",
    688         bta_hh_get_w4_event(p_cb->w4_evt), p_data->hid_cback.data);
    689 #endif
    690 
    691     memset(&hs_data, 0, sizeof(tBTA_HH_HSDATA));
    692     memset(&cback_data, 0, sizeof(tBTA_HH_CBDATA));
    693 
    694     switch (p_cb->w4_evt)
    695     {
    696         /* GET_ transsaction, handshake indicate unsupported request */
    697         case BTA_HH_GET_PROTO_EVT:
    698             hs_data.rsp_data.proto_mode = BTA_HH_PROTO_UNKNOWN;
    699             /* fall through */
    700         case BTA_HH_GET_RPT_EVT:
    701         case BTA_HH_GET_IDLE_EVT :
    702             hs_data.handle = p_cb->hid_handle;
    703             /* if handshake gives an OK code for these transaction, fill in UNSUPT */
    704             if ((hs_data.status = bta_hh_get_trans_status(p_data->hid_cback.data)) == BTA_HH_OK)
    705                  hs_data.status = BTA_HH_HS_TRANS_NOT_SPT;
    706 
    707             (* bta_hh_cb.p_cback)(p_cb->w4_evt, (tBTA_HH *)&hs_data);
    708             p_cb->w4_evt = 0;
    709             break;
    710 
    711         /* acknoledgement from HID device for SET_ transaction */
    712         case BTA_HH_SET_RPT_EVT:
    713         case BTA_HH_SET_PROTO_EVT:
    714         case BTA_HH_SET_IDLE_EVT :
    715             cback_data.handle  = p_cb->hid_handle;
    716             cback_data.status = bta_hh_get_trans_status(p_data->hid_cback.data);
    717             (* bta_hh_cb.p_cback)(p_cb->w4_evt, (tBTA_HH *)&cback_data);
    718             p_cb->w4_evt = 0;
    719             break;
    720 
    721         /* SET_PROTOCOL when open connection */
    722         case BTA_HH_OPEN_EVT:
    723             conn.status =p_data->hid_cback.data ? BTA_HH_ERR_PROTO: BTA_HH_OK;
    724             conn.handle = p_cb->hid_handle;
    725             bdcpy(conn.bda, p_cb->addr);
    726             (* bta_hh_cb.p_cback)(p_cb->w4_evt, (tBTA_HH *)&conn);
    727 #if BTA_HH_DEBUG
    728             bta_hh_trace_dev_db();
    729 #endif
    730             p_cb->w4_evt = 0;
    731             break;
    732 
    733         default:
    734             /* unknow transaction handshake response */
    735             APPL_TRACE_DEBUG0("unknown transaction type");
    736             break;
    737     }
    738 
    739     /* transaction achknoledgement received, inform PM for mode change */
    740     bta_sys_idle(BTA_ID_HH, p_cb->app_id, p_cb->addr);
    741     return;
    742 }
    743 /*******************************************************************************
    744 **
    745 ** Function         bta_hh_ctrl_dat_act
    746 **
    747 ** Description      HID Host process a data report from control channel.
    748 **
    749 **
    750 ** Returns          void
    751 **
    752 *******************************************************************************/
    753 void bta_hh_ctrl_dat_act(tBTA_HH_DEV_CB *p_cb, tBTA_HH_DATA * p_data)
    754 {
    755     BT_HDR          *pdata = p_data->hid_cback.p_data;
    756     UINT8           *data = (UINT8 *)(pdata + 1) + pdata->offset;
    757     tBTA_HH_HSDATA    hs_data;
    758 
    759 #if BTA_HH_DEBUG
    760     APPL_TRACE_DEBUG1("Ctrl DATA received w4: event[%s]",
    761                         bta_hh_get_w4_event(p_cb->w4_evt));
    762 #endif
    763     hs_data.status  = BTA_HH_OK;
    764     hs_data.handle  = p_cb->hid_handle;
    765 
    766     switch (p_cb->w4_evt)
    767     {
    768     case BTA_HH_GET_IDLE_EVT:
    769         hs_data.rsp_data.idle_rate = *data;
    770         break;
    771     case BTA_HH_GET_RPT_EVT:
    772         hs_data.rsp_data.p_rpt_data = pdata;
    773         break;
    774     case BTA_HH_GET_PROTO_EVT:
    775         /* match up BTE/BTA report/boot mode def*/
    776         hs_data.rsp_data.proto_mode = ((*data) == HID_PAR_PROTOCOL_REPORT)? \
    777                     BTA_HH_PROTO_RPT_MODE : BTA_HH_PROTO_BOOT_MODE;
    778 #if BTA_HH_DEBUG
    779         APPL_TRACE_DEBUG1("GET_PROTOCOL Mode = [%s]",
    780             (hs_data.rsp_data.proto_mode == BTA_HH_PROTO_RPT_MODE)? "Report" : "Boot");
    781 #endif
    782         break;
    783     /* should not expect control DATA for SET_ transaction */
    784     case BTA_HH_SET_PROTO_EVT:
    785         /* fall through */
    786     case BTA_HH_SET_RPT_EVT:
    787         /* fall through */
    788     case BTA_HH_SET_IDLE_EVT :
    789         /* fall through */
    790     default:
    791 #if BTA_HH_DEBUG
    792         APPL_TRACE_DEBUG1("invalid  transaction type for DATA payload: 4_evt[%s]",
    793                         bta_hh_get_w4_event(p_cb->w4_evt));
    794 #endif
    795         break;
    796     }
    797 
    798     /* inform PM for mode change */
    799     bta_sys_busy(BTA_ID_HH, p_cb->app_id, p_cb->addr);
    800     bta_sys_idle(BTA_ID_HH, p_cb->app_id, p_cb->addr);
    801 
    802     (* bta_hh_cb.p_cback)(p_cb->w4_evt, (tBTA_HH *)&hs_data);
    803 
    804     p_cb->w4_evt = 0;
    805     utl_freebuf((void **)&pdata);
    806 
    807 }
    808 
    809 /*******************************************************************************
    810 **
    811 ** Function         bta_hh_open_failure
    812 **
    813 ** Description      report HID open failure when at wait for connection state and receive
    814 **                  device close event.
    815 **
    816 **
    817 ** Returns          void
    818 **
    819 *******************************************************************************/
    820 void bta_hh_open_failure(tBTA_HH_DEV_CB *p_cb, tBTA_HH_DATA *p_data)
    821 {
    822     tBTA_HH_CONN            conn_dat ;
    823     UINT32                  reason = p_data->hid_cback.data;    /* Reason for closing (32-bit) */
    824 
    825     memset(&conn_dat, 0, sizeof(tBTA_HH_CONN));
    826      conn_dat.handle = p_cb->hid_handle;
    827      conn_dat.status = (reason == HID_ERR_AUTH_FAILED) ?
    828                                     BTA_HH_ERR_AUTH_FAILED : BTA_HH_ERR;
    829      bdcpy(conn_dat.bda, p_cb->addr);
    830      HID_HostCloseDev(p_cb->hid_handle);
    831 
    832      /* Report OPEN fail event */
    833      (*bta_hh_cb.p_cback)(BTA_HH_OPEN_EVT, (tBTA_HH *)&conn_dat);
    834 
    835 #if BTA_HH_DEBUG
    836     bta_hh_trace_dev_db();
    837 #endif
    838     /* clean up control block, but retain SDP info and device handle */
    839     p_cb->vp            = FALSE;
    840     p_cb->w4_evt        = 0;
    841 
    842     /* if no connection is active and HH disable is signaled, disable service */
    843     if (bta_hh_cb.cnt_num == 0 && bta_hh_cb.w4_disable)
    844     {
    845         bta_hh_disc_cmpl();
    846     }
    847 
    848 }
    849 
    850 /*******************************************************************************
    851 **
    852 ** Function         bta_hh_close_act
    853 **
    854 ** Description      HID Host process a close event
    855 **
    856 **
    857 ** Returns          void
    858 **
    859 *******************************************************************************/
    860 void bta_hh_close_act (tBTA_HH_DEV_CB *p_cb, tBTA_HH_DATA *p_data)
    861 {
    862     tBTA_HH_CONN            conn_dat ;
    863     tBTA_HH_CBDATA          disc_dat = {BTA_HH_OK, 0};
    864     UINT32                  reason = p_data->hid_cback.data;    /* Reason for closing (32-bit) */
    865 
    866     /* if HID_HDEV_EVT_VC_UNPLUG was received, report BTA_HH_VC_UNPLUG_EVT */
    867     UINT16     event = p_cb->vp ? BTA_HH_VC_UNPLUG_EVT : BTA_HH_CLOSE_EVT;
    868 
    869     disc_dat.handle = p_cb->hid_handle;
    870     disc_dat.status = p_data->hid_cback.data;
    871 
    872     /* Check reason for closing */
    873     if ((reason & (HID_L2CAP_CONN_FAIL|HID_L2CAP_REQ_FAIL)) ||  /* Failure to initialize connection (page timeout or l2cap error) */
    874         (reason == HID_ERR_AUTH_FAILED) ||                      /* Authenication error (while initiating) */
    875         (reason == HID_ERR_L2CAP_FAILED))                       /* Failure creating l2cap connection */
    876     {
    877         /* Failure in opening connection */
    878         conn_dat.handle = p_cb->hid_handle;
    879         conn_dat.status = (reason == HID_ERR_AUTH_FAILED) ? BTA_HH_ERR_AUTH_FAILED : BTA_HH_ERR;
    880         bdcpy(conn_dat.bda, p_cb->addr);
    881         HID_HostCloseDev(p_cb->hid_handle);
    882 
    883         /* Report OPEN fail event */
    884         (*bta_hh_cb.p_cback)(BTA_HH_OPEN_EVT, (tBTA_HH *)&conn_dat);
    885 
    886 #if BTA_HH_DEBUG
    887         bta_hh_trace_dev_db();
    888 #endif
    889         return;
    890     }
    891     /* otherwise report CLOSE/VC_UNPLUG event */
    892     else
    893     {
    894         /* finaliza device driver */
    895         bta_hh_co_close(p_cb->hid_handle, p_cb->app_id);
    896         /* inform role manager */
    897         bta_sys_conn_close( BTA_ID_HH ,p_cb->app_id, p_cb->addr);
    898         /* update total conn number */
    899         bta_hh_cb.cnt_num --;
    900 
    901         if (disc_dat.status)
    902             disc_dat.status = BTA_HH_ERR;
    903 
    904         (*bta_hh_cb.p_cback)(event, (tBTA_HH *)&disc_dat);
    905 
    906         /* if virtually unplug, remove device */
    907         if (p_cb->vp )
    908         {
    909             HID_HostRemoveDev( p_cb->hid_handle);
    910             bta_hh_clean_up_kdev(p_cb);
    911         }
    912 
    913 #if BTA_HH_DEBUG
    914         bta_hh_trace_dev_db();
    915 #endif
    916     }
    917 
    918     /* clean up control block, but retain SDP info and device handle */
    919     p_cb->vp            = FALSE;
    920     p_cb->w4_evt        = 0;
    921 
    922     /* if no connection is active and HH disable is signaled, disable service */
    923     if (bta_hh_cb.cnt_num == 0 && bta_hh_cb.w4_disable)
    924     {
    925         bta_hh_disc_cmpl();
    926     }
    927 
    928     return;
    929 }
    930 
    931 /*******************************************************************************
    932 **
    933 ** Function         bta_hh_get_dscp_act
    934 **
    935 ** Description      Get device report descriptor
    936 **
    937 **
    938 ** Returns          void
    939 **
    940 *******************************************************************************/
    941 void bta_hh_get_dscp_act(tBTA_HH_DEV_CB *p_cb, tBTA_HH_DATA *p_data)
    942 {
    943 #if (BTA_HH_LE_INCLUDED == TRUE)
    944     if (p_cb->is_le_device)
    945     {
    946         bta_hh_le_get_dscp_act(p_cb);
    947     }
    948     else
    949 #endif
    950     (*bta_hh_cb.p_cback)(BTA_HH_GET_DSCP_EVT, (tBTA_HH *)&p_cb->dscp_info);
    951 }
    952 
    953 /*******************************************************************************
    954 **
    955 ** Function         bta_hh_maint_dev_act
    956 **
    957 ** Description      HID Host maintain device list.
    958 **
    959 **
    960 ** Returns          void
    961 **
    962 *******************************************************************************/
    963 void bta_hh_maint_dev_act(tBTA_HH_DEV_CB *p_cb, tBTA_HH_DATA *p_data)
    964 {
    965     tBTA_HH_MAINT_DEV       *p_dev_info = &p_data->api_maintdev;
    966     tBTA_HH_DEV_INFO        dev_info ;
    967     UINT8                   dev_handle;
    968 
    969     dev_info.status = BTA_HH_ERR;
    970     dev_info.handle = BTA_HH_INVALID_HANDLE;
    971 
    972     switch (p_dev_info->sub_event)
    973     {
    974     case BTA_HH_ADD_DEV_EVT:    /* add a device */
    975         bdcpy(dev_info.bda, p_dev_info->bda);
    976         /* initialize callback data */
    977         if (p_cb->hid_handle == BTA_HH_INVALID_HANDLE)
    978         {
    979 #if (BTA_HH_LE_INCLUDED == TRUE)
    980             if (bta_hh_is_le_device(p_cb, p_data->api_conn.bd_addr))
    981             {
    982                 dev_info.handle   = bta_hh_le_add_device(p_cb, p_dev_info);
    983                 dev_info.status   = BTA_HH_OK;
    984             }
    985             else
    986 #endif
    987 
    988             if (HID_HostAddDev(p_dev_info->bda, p_dev_info->attr_mask, &dev_handle)\
    989                             == HID_SUCCESS)
    990             {
    991                 dev_info.handle   = dev_handle;
    992                 dev_info.status   = BTA_HH_OK;
    993 
    994 #if (defined BTA_HH_LE_INCLUDED && BTA_HH_LE_INCLUDED == TRUE)
    995                 /* update DI information */
    996                 bta_hh_update_di_info(p_cb,
    997                                       p_dev_info->dscp_info.vendor_id,
    998                                       p_dev_info->dscp_info.product_id,
    999                                       p_dev_info->dscp_info.version,
   1000                                       p_dev_info->dscp_info.flag);
   1001 #else
   1002                 bta_hh_update_di_info(p_cb,
   1003                                       p_dev_info->dscp_info.vendor_id,
   1004                                       p_dev_info->dscp_info.product_id,
   1005                                       p_dev_info->dscp_info.version,
   1006                                       0);
   1007 
   1008 #endif
   1009                 /* add to BTA device list */
   1010                 bta_hh_add_device_to_list(p_cb, dev_handle,
   1011                                           p_dev_info->attr_mask,
   1012                                           &p_dev_info->dscp_info.descriptor,
   1013                                           p_dev_info->sub_class,
   1014                                           p_dev_info->dscp_info.ssr_max_latency,
   1015                                           p_dev_info->dscp_info.ssr_min_tout,
   1016                                           p_dev_info->app_id);
   1017                 /* update cb_index[] map */
   1018                 bta_hh_cb.cb_index[dev_handle] = p_cb->index;
   1019             }
   1020         }
   1021         else    /* device already been added */
   1022         {
   1023             dev_info.handle = p_cb->hid_handle;
   1024             dev_info.status = BTA_HH_OK;
   1025         }
   1026 #if BTA_HH_DEBUG
   1027         bta_hh_trace_dev_db();
   1028 #endif
   1029 
   1030         break;
   1031     case BTA_HH_RMV_DEV_EVT:    /* remove device */
   1032         dev_info.handle = (UINT8)p_dev_info->hdr.layer_specific;
   1033         bdcpy(dev_info.bda, p_cb->addr);
   1034 
   1035 #if BTA_HH_LE_INCLUDED == TRUE
   1036         if (p_cb->is_le_device)
   1037         {
   1038             bta_hh_le_remove_dev_bg_conn(p_cb);
   1039             bta_hh_sm_execute(p_cb, BTA_HH_API_CLOSE_EVT, NULL);
   1040             bta_hh_clean_up_kdev(p_cb);
   1041         }
   1042         else
   1043 #endif
   1044         {
   1045             if(HID_HostRemoveDev( dev_info.handle ) == HID_SUCCESS)
   1046             {
   1047                 dev_info.status  = BTA_HH_OK;
   1048 
   1049                 /* remove from known device list in BTA */
   1050                 bta_hh_clean_up_kdev(p_cb);
   1051             }
   1052         }
   1053         break;
   1054 
   1055     default:
   1056         APPL_TRACE_DEBUG0("invalid command");
   1057         break;
   1058     }
   1059 
   1060     (* bta_hh_cb.p_cback)(p_dev_info->sub_event, (tBTA_HH *)&dev_info);
   1061 }
   1062 /*******************************************************************************
   1063 **
   1064 ** Function         bta_hh_write_dev_act
   1065 **
   1066 ** Description      Write device action. can be SET/GET/DATA transaction.
   1067 **
   1068 ** Returns          void
   1069 **
   1070 *******************************************************************************/
   1071 void bta_hh_write_dev_act(tBTA_HH_DEV_CB *p_cb, tBTA_HH_DATA *p_data)
   1072 {
   1073     tBTA_HH_CBDATA     cbdata = {BTA_HH_OK, 0};
   1074     UINT16  event = (p_data->api_sndcmd.t_type - BTA_HH_FST_BTE_TRANS_EVT) +
   1075                         BTA_HH_FST_TRANS_CB_EVT;
   1076 
   1077 #if BTA_HH_LE_INCLUDED == TRUE
   1078     if (p_cb->is_le_device)
   1079         bta_hh_le_write_dev_act(p_cb, p_data);
   1080     else
   1081 #endif
   1082     {
   1083 
   1084     cbdata.handle = p_cb->hid_handle;
   1085 
   1086     /* match up BTE/BTA report/boot mode def */
   1087     if (p_data->api_sndcmd.t_type == HID_TRANS_SET_PROTOCOL)
   1088     {
   1089         p_data->api_sndcmd.param = ( p_data->api_sndcmd.param == BTA_HH_PROTO_RPT_MODE) ?\
   1090                         HID_PAR_PROTOCOL_REPORT :HID_PAR_PROTOCOL_BOOT_MODE;
   1091     }
   1092 
   1093     if (HID_HostWriteDev (p_cb->hid_handle,
   1094                        p_data->api_sndcmd.t_type,
   1095                        p_data->api_sndcmd.param,
   1096                        p_data->api_sndcmd.data,
   1097                        p_data->api_sndcmd.rpt_id,
   1098                        p_data->api_sndcmd.p_data) != HID_SUCCESS)
   1099     {
   1100         APPL_TRACE_ERROR0("HID_HostWriteDev Error ");
   1101         cbdata.status = BTA_HH_ERR;
   1102 
   1103         if (p_data->api_sndcmd.t_type != HID_TRANS_CONTROL &&
   1104             p_data->api_sndcmd.t_type != HID_TRANS_DATA)
   1105             (* bta_hh_cb.p_cback)(event, (tBTA_HH *)&cbdata);
   1106         else if (p_data->api_sndcmd.param == BTA_HH_CTRL_VIRTUAL_CABLE_UNPLUG)
   1107             (* bta_hh_cb.p_cback)(BTA_HH_VC_UNPLUG_EVT, (tBTA_HH *)&cbdata);
   1108     }
   1109     else
   1110     {
   1111 
   1112         switch(p_data->api_sndcmd.t_type)
   1113         {
   1114         case HID_TRANS_SET_PROTOCOL:
   1115             /* fall through */
   1116         case HID_TRANS_GET_REPORT:
   1117             /* fall through */
   1118         case HID_TRANS_SET_REPORT:
   1119             /* fall through */
   1120         case HID_TRANS_GET_PROTOCOL:
   1121             /* fall through */
   1122         case HID_TRANS_GET_IDLE:
   1123             /* fall through */
   1124         case HID_TRANS_SET_IDLE:/* set w4_handsk event name for callback function use */
   1125             p_cb->w4_evt = event;
   1126             break;
   1127         case HID_TRANS_DATA:  /* output report */
   1128             /* fall through */
   1129         case HID_TRANS_CONTROL:
   1130             /* no handshake event will be generated */
   1131             /* if VC_UNPLUG is issued, set flag */
   1132             if (p_data->api_sndcmd.param == BTA_HH_CTRL_VIRTUAL_CABLE_UNPLUG)
   1133                 p_cb->vp = TRUE;
   1134 
   1135             break;
   1136         /* currently not expected */
   1137         case HID_TRANS_DATAC:
   1138         default:
   1139             APPL_TRACE_DEBUG1("bta_hh_write_dev_act:: cmd type = %d",
   1140                             p_data->api_sndcmd.t_type);
   1141             break;
   1142         }
   1143 
   1144         /* if not control type transaction, notify PM for energy control */
   1145         if (p_data->api_sndcmd.t_type != HID_TRANS_CONTROL)
   1146         {
   1147             /* inform PM for mode change */
   1148             bta_sys_busy(BTA_ID_HH, p_cb->app_id, p_cb->addr);
   1149             bta_sys_idle(BTA_ID_HH, p_cb->app_id, p_cb->addr);
   1150         }
   1151         else if (p_data->api_sndcmd.param == BTA_HH_CTRL_SUSPEND)
   1152         {
   1153 			bta_sys_sco_close(BTA_ID_HH, p_cb->app_id, p_cb->addr);
   1154         }
   1155         else if (p_data->api_sndcmd.param == BTA_HH_CTRL_EXIT_SUSPEND)
   1156         {
   1157             bta_sys_busy(BTA_ID_HH, p_cb->app_id, p_cb->addr);
   1158         }
   1159     }
   1160 
   1161     }
   1162     return;
   1163 }
   1164 
   1165 /*****************************************************************************
   1166 **  Static Function
   1167 *****************************************************************************/
   1168 /*******************************************************************************
   1169 **
   1170 ** Function         bta_hh_cback
   1171 **
   1172 ** Description      BTA HH callback function.
   1173 **
   1174 **
   1175 ** Returns          void
   1176 **
   1177 *******************************************************************************/
   1178 static void bta_hh_cback (UINT8 dev_handle, BD_ADDR addr, UINT8 event,
   1179                         UINT32 data, BT_HDR *pdata)
   1180 {
   1181     tBTA_HH_CBACK_DATA    *p_buf = NULL;
   1182     UINT16  sm_event = BTA_HH_INVALID_EVT;
   1183     UINT8   xx = 0;
   1184 
   1185 #if BTA_HH_DEBUG
   1186     APPL_TRACE_DEBUG1("bta_hh_cback::HID_event [%s]", bta_hh_hid_event_name(event));
   1187 #endif
   1188 
   1189     switch (event)
   1190     {
   1191     case HID_HDEV_EVT_OPEN:
   1192         sm_event = BTA_HH_INT_OPEN_EVT;
   1193         break;
   1194     case HID_HDEV_EVT_CLOSE:
   1195         sm_event = BTA_HH_INT_CLOSE_EVT;
   1196         break;
   1197     case HID_HDEV_EVT_INTR_DATA:
   1198         sm_event = BTA_HH_INT_DATA_EVT;
   1199         break;
   1200     case HID_HDEV_EVT_HANDSHAKE:
   1201         sm_event = BTA_HH_INT_HANDSK_EVT;
   1202         break;
   1203     case HID_HDEV_EVT_CTRL_DATA:
   1204         sm_event = BTA_HH_INT_CTRL_DATA;
   1205         break;
   1206     case HID_HDEV_EVT_RETRYING:
   1207         break;
   1208     case HID_HDEV_EVT_INTR_DATC:
   1209     case HID_HDEV_EVT_CTRL_DATC:
   1210         /* Unhandled events: Free buffer for DATAC */
   1211         utl_freebuf((void **)&pdata);
   1212         break;
   1213     case HID_HDEV_EVT_VC_UNPLUG:
   1214         for (xx = 0; xx < BTA_HH_MAX_DEVICE; xx++)
   1215         {
   1216             if (bta_hh_cb.kdev[xx].hid_handle == dev_handle)
   1217             {
   1218                bta_hh_cb.kdev[xx].vp = TRUE;
   1219                break;
   1220             }
   1221         }
   1222         break;
   1223     }
   1224 
   1225     if (sm_event != BTA_HH_INVALID_EVT &&
   1226         (p_buf = (tBTA_HH_CBACK_DATA *)GKI_getbuf(sizeof(tBTA_HH_CBACK_DATA) +
   1227                     sizeof(BT_HDR))) != NULL)
   1228     {
   1229         p_buf->hdr.event  = sm_event;
   1230         p_buf->hdr.layer_specific = (UINT16)dev_handle;
   1231         p_buf->data       = data;
   1232         bdcpy(p_buf->addr, addr);
   1233         p_buf->p_data     = pdata;
   1234 
   1235         bta_sys_sendmsg(p_buf);
   1236     }
   1237 
   1238 }
   1239 /*******************************************************************************
   1240 **
   1241 ** Function         bta_hh_get_trans_status
   1242 **
   1243 ** Description      translate a handshake result code into BTA HH
   1244 **                  status code
   1245 **
   1246 *******************************************************************************/
   1247 static tBTA_HH_STATUS bta_hh_get_trans_status(UINT32 result)
   1248 {
   1249     switch(result)
   1250     {
   1251     case HID_PAR_HANDSHAKE_RSP_SUCCESS :                /*   (0) */
   1252         return BTA_HH_OK;
   1253     case HID_PAR_HANDSHAKE_RSP_NOT_READY :              /*   (1) */
   1254     case HID_PAR_HANDSHAKE_RSP_ERR_INVALID_REP_ID:      /*   (2) */
   1255     case HID_PAR_HANDSHAKE_RSP_ERR_UNSUPPORTED_REQ :    /*   (3) */
   1256     case HID_PAR_HANDSHAKE_RSP_ERR_INVALID_PARAM :      /*   (4) */
   1257         return (tBTA_HH_STATUS)result;
   1258     case HID_PAR_HANDSHAKE_RSP_ERR_UNKNOWN :            /*   (14) */
   1259     case HID_PAR_HANDSHAKE_RSP_ERR_FATAL  :             /*   (15) */
   1260     default:
   1261         return BTA_HH_HS_ERROR;
   1262         break;
   1263     }
   1264 }
   1265 /*****************************************************************************
   1266 **  Debug Functions
   1267 *****************************************************************************/
   1268 
   1269 #if (defined BTA_HH_DEBUG && BTA_HH_DEBUG == TRUE)
   1270 static char* bta_hh_get_w4_event(UINT16 event)
   1271 {
   1272     switch (event)
   1273     {
   1274     case BTA_HH_GET_RPT_EVT:
   1275         return "BTA_HH_GET_RPT_EVT";
   1276     case BTA_HH_SET_RPT_EVT:
   1277         return "BTA_HH_SET_RPT_EVT";
   1278     case BTA_HH_GET_PROTO_EVT:
   1279         return "BTA_HH_GET_PROTO_EVT";
   1280     case BTA_HH_SET_PROTO_EVT:
   1281         return "BTA_HH_SET_PROTO_EVT";
   1282     case BTA_HH_GET_IDLE_EVT:
   1283         return "BTA_HH_GET_IDLE_EVT";
   1284     case BTA_HH_SET_IDLE_EVT:
   1285         return "BTA_HH_SET_IDLE_EVT";
   1286     case BTA_HH_OPEN_EVT:
   1287         return "BTA_HH_OPEN_EVT";
   1288     default:
   1289         return "Unknown event";
   1290     }
   1291 
   1292 }
   1293 
   1294 static char * bta_hh_hid_event_name(UINT16 event)
   1295 {
   1296     switch (event)
   1297     {
   1298     case HID_HDEV_EVT_OPEN:
   1299         return "HID_HDEV_EVT_OPEN";
   1300     case HID_HDEV_EVT_CLOSE:
   1301         return "HID_HDEV_EVT_CLOSE";
   1302     case HID_HDEV_EVT_RETRYING:
   1303         return "HID_HDEV_EVT_RETRYING";
   1304     case HID_HDEV_EVT_INTR_DATA:
   1305         return "HID_HDEV_EVT_INTR_DATA";
   1306     case HID_HDEV_EVT_INTR_DATC:
   1307         return "HID_HDEV_EVT_INTR_DATC";
   1308     case HID_HDEV_EVT_CTRL_DATA:
   1309         return "HID_HDEV_EVT_CTRL_DATA";
   1310     case HID_HDEV_EVT_CTRL_DATC:
   1311         return "HID_HDEV_EVT_CTRL_DATC";
   1312     case HID_HDEV_EVT_HANDSHAKE:
   1313         return "HID_HDEV_EVT_HANDSHAKE";
   1314     case HID_HDEV_EVT_VC_UNPLUG:
   1315         return "HID_HDEV_EVT_VC_UNPLUG";
   1316     default:
   1317         return "Unknown HID event";
   1318     }
   1319 }
   1320 #endif
   1321 #endif /* BTA_HH_INCLUDED */
   1322 
   1323