/******************************************************************************
 *
 *  Copyright (C) 2009-2013 Broadcom Corporation
 *
 *  Licensed under the Apache License, Version 2.0 (the "License");
 *  you may not use this file except in compliance with the License.
 *  You may obtain a copy of the License at:
 *
 *  http://www.apache.org/licenses/LICENSE-2.0
 *
 *  Unless required by applicable law or agreed to in writing, software
 *  distributed under the License is distributed on an "AS IS" BASIS,
 *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 *  See the License for the specific language governing permissions and
 *  limitations under the License.
 *
 ******************************************************************************/

#include "bta_api.h"
#include "bta_hh_int.h"

#if (defined BTA_HH_LE_INCLUDED && BTA_HH_LE_INCLUDED == TRUE)

#include "bta_api.h"
#include <string.h>
#include "btm_api.h"
#include "btm_ble_api.h"
#include "bta_hh_co.h"
#include "bta_gatt_api.h"
#include "srvc_api.h"
#include "btm_int.h"
#include "utl.h"

#ifndef BTA_HH_LE_RECONN
#define BTA_HH_LE_RECONN    TRUE
#endif

#define BTA_HH_APP_ID_LE            0xff

#define BTA_HH_LE_RPT_TYPE_VALID(x)     ((x) <= BTA_LE_HID_RPT_FEATURE && (x)>=BTA_LE_HID_RPT_INPUT)

#define BTA_HH_LE_RPT_INST_ID_MAP(s,c)  (UINT8)(((s)<<4)|(c))
#define BTA_HH_LE_RPT_GET_SRVC_INST_ID(x)  (UINT8)(x  >> 4)
#define BTA_HH_LE_RPT_GET_RPT_INST_ID(x)  (UINT8)(x & 0x0f)


#define BTA_HH_LE_PROTO_BOOT_MODE      0x00
#define BTA_HH_LE_PROTO_REPORT_MODE      0x01

#define BTA_HH_SCPP_INST_DEF            0

#define BTA_HH_LE_DISC_CHAR_NUM     8
static const UINT16 bta_hh_le_disc_char_uuid[BTA_HH_LE_DISC_CHAR_NUM] =
{
    GATT_UUID_HID_INFORMATION,
    GATT_UUID_HID_REPORT_MAP,
    GATT_UUID_HID_CONTROL_POINT,
    GATT_UUID_HID_REPORT,
    GATT_UUID_HID_BT_KB_INPUT,
    GATT_UUID_HID_BT_KB_OUTPUT,
    GATT_UUID_HID_BT_MOUSE_INPUT,
    GATT_UUID_HID_PROTO_MODE        /* always make sure this is the last attribute to discover */
};

#define BTA_LE_HID_RTP_UUID_MAX     5
static const UINT16 bta_hh_uuid_to_rtp_type[BTA_LE_HID_RTP_UUID_MAX][2] =
{
    {GATT_UUID_HID_REPORT,       BTA_HH_RPTT_INPUT},
    {GATT_UUID_HID_BT_KB_INPUT,  BTA_HH_RPTT_INPUT},
    {GATT_UUID_HID_BT_KB_OUTPUT, BTA_HH_RPTT_OUTPUT},
    {GATT_UUID_HID_BT_MOUSE_INPUT, BTA_HH_RPTT_INPUT},
    {GATT_UUID_BATTERY_LEVEL,      BTA_HH_RPTT_INPUT}
};


static void bta_hh_gattc_callback(tBTA_GATTC_EVT event, tBTA_GATTC *p_data);
static void bta_hh_le_search_hid_chars(tBTA_HH_DEV_CB *p_dev_cb);
static void bta_hh_le_search_hid_included(tBTA_HH_DEV_CB *p_dev_cb);
static void bta_hh_le_search_scps(tBTA_HH_DEV_CB *p_cb);
static void bta_hh_le_search_scps_chars(tBTA_HH_DEV_CB *p_cb);
static void bta_hh_le_register_scpp_notif(tBTA_HH_DEV_CB *p_dev_cb, tBTA_GATT_STATUS status);
static void bta_hh_le_register_scpp_notif_cmpl(tBTA_HH_DEV_CB *p_dev_cb, tBTA_GATT_STATUS status);
static void bta_hh_le_add_dev_bg_conn(tBTA_HH_DEV_CB *p_cb, BOOLEAN check_bond);

#define BTA_HH_LE_SRVC_DEF      0

#if BTA_HH_DEBUG == TRUE
static const char *bta_hh_le_rpt_name[4] =
{
    "UNKNOWN",
    "INPUT",
    "OUTPUT",
    "FEATURE"
};

/*******************************************************************************
**
** Function         bta_hh_le_hid_report_dbg
**
** Description      debug function to print out all HID report available on remote
**                  device.
**
** Returns          void
**
*******************************************************************************/
static void bta_hh_le_hid_report_dbg(tBTA_HH_DEV_CB *p_cb)
{
    UINT8 i , j;
    tBTA_HH_LE_RPT  *p_rpt;
    char *  rpt_name;

    APPL_TRACE_DEBUG("HID Report DB");
    for (i = 0; i < BTA_HH_LE_HID_SRVC_MAX; i ++)
    {
        if (p_cb->hid_srvc[i].in_use)
        {
            p_rpt = &p_cb->hid_srvc[i].report[0];

            APPL_TRACE_DEBUG("\t HID serivce inst: %d", i);

            for (j = 0; j < BTA_HH_LE_RPT_MAX; j ++, p_rpt++)
            {
                rpt_name = "Unknown";
                if (p_rpt->in_use)
                {
                    if (p_rpt->uuid == GATT_UUID_HID_REPORT)
                        rpt_name = "Report";
                    if (p_rpt->uuid == GATT_UUID_HID_BT_KB_INPUT)
                        rpt_name = "Boot KB Input";
                    if (p_rpt->uuid == GATT_UUID_HID_BT_KB_OUTPUT)
                        rpt_name = "Boot KB Output";
                    if (p_rpt->uuid == GATT_UUID_HID_BT_MOUSE_INPUT)
                        rpt_name = "Boot MI Input";


                    APPL_TRACE_DEBUG("\t\t [%s- 0x%04x] [Type: %s], [ReportID: %d] [inst_id: %d]  [Clt_cfg: %d]",
                        rpt_name,
                        p_rpt->uuid ,
                        ((p_rpt->rpt_type < 4) ? bta_hh_le_rpt_name[p_rpt->rpt_type] : "UNKNOWN"),
                        p_rpt->rpt_id,
                        p_rpt->inst_id,
                        p_rpt->client_cfg_value);
                }
                else
                    break;
            }
        }
        else
            break;
    }
}
/*******************************************************************************
**
** Function         bta_hh_uuid_to_str
**
** Description
**
** Returns          void
**
*******************************************************************************/
static char *bta_hh_uuid_to_str(UINT16 uuid)
{
    switch(uuid)
    {
        case GATT_UUID_HID_INFORMATION:
            return "GATT_UUID_HID_INFORMATION";
        case GATT_UUID_HID_REPORT_MAP:
            return "GATT_UUID_HID_REPORT_MAP";
        case GATT_UUID_HID_CONTROL_POINT:
            return "GATT_UUID_HID_CONTROL_POINT";
        case GATT_UUID_HID_REPORT:
            return "GATT_UUID_HID_REPORT";
        case GATT_UUID_HID_PROTO_MODE:
            return "GATT_UUID_HID_PROTO_MODE";
        case GATT_UUID_HID_BT_KB_INPUT:
            return "GATT_UUID_HID_BT_KB_INPUT";
        case GATT_UUID_HID_BT_KB_OUTPUT:
            return "GATT_UUID_HID_BT_KB_OUTPUT";
        case GATT_UUID_HID_BT_MOUSE_INPUT:
            return "GATT_UUID_HID_BT_MOUSE_INPUT";
        case GATT_UUID_CHAR_CLIENT_CONFIG:
            return "GATT_UUID_CHAR_CLIENT_CONFIG";
        case GATT_UUID_EXT_RPT_REF_DESCR:
            return "GATT_UUID_EXT_RPT_REF_DESCR";
        case GATT_UUID_RPT_REF_DESCR:
            return "GATT_UUID_RPT_REF_DESCR";
        default:
            return "Unknown UUID";
    }
}
#endif
/*******************************************************************************
**
** Function         bta_hh_le_enable
**
** Description      initialize LE HID related functionality
**
**
** Returns          void
**
*******************************************************************************/
void bta_hh_le_enable(void)
{
    char       app_name[LEN_UUID_128 + 1];
    tBT_UUID    app_uuid = {LEN_UUID_128,{0}};
    UINT8       xx;

    bta_hh_cb.gatt_if = BTA_GATTS_INVALID_IF;

    for (xx = 0; xx < BTA_HH_MAX_DEVICE; xx ++)
        bta_hh_cb.le_cb_index[xx]       = BTA_HH_IDX_INVALID;

    memset (app_name, 0, LEN_UUID_128 + 1);
    strncpy(app_name, "BTA HH OVER LE", LEN_UUID_128);

    memcpy((void *)app_uuid.uu.uuid128, (void *)app_name, LEN_UUID_128);

    BTA_GATTC_AppRegister(&app_uuid, bta_hh_gattc_callback);

    return;
}
/*******************************************************************************
**
** Function         bta_hh_le_register_cmpl
**
** Description      BTA HH register with BTA GATTC completed
**
** Parameters:
**
*******************************************************************************/
void bta_hh_le_register_cmpl(tBTA_GATTC_REG *p_reg)
{
    tBTA_HH_STATUS      status = BTA_HH_ERR;

    if (p_reg->status == BTA_GATT_OK)
    {
        bta_hh_cb.gatt_if = p_reg->client_if;
        status = BTA_HH_OK;
    }
    else
        bta_hh_cb.gatt_if = BTA_GATTS_INVALID_IF;

    /* signal BTA call back event */
    (* bta_hh_cb.p_cback)(BTA_HH_ENABLE_EVT, (tBTA_HH *)&status);
}

/*******************************************************************************
**
** Function         bta_hh_le_is_hh_gatt_if
**
** Description      Check to see if client_if is BTA HH LE GATT interface
**
**
** Returns          whether it is HH GATT IF
**
*******************************************************************************/
BOOLEAN bta_hh_le_is_hh_gatt_if(tBTA_GATTC_IF client_if)
{
    return (bta_hh_cb.gatt_if == client_if);
}

/*******************************************************************************
**
** Function         bta_hh_le_deregister
**
** Description      De-register BTA HH from BTA GATTC
**
**
** Returns          void
**
*******************************************************************************/
void bta_hh_le_deregister(void)
{
    BTA_GATTC_AppDeregister(bta_hh_cb.gatt_if);
}

/*******************************************************************************
**
** Function         bta_hh_is_le_device
**
** Description      Check to see if the remote device is a LE only device
**
** Parameters:
**
*******************************************************************************/
BOOLEAN bta_hh_is_le_device(tBTA_HH_DEV_CB *p_cb, BD_ADDR remote_bda)
{
    p_cb->is_le_device = BTM_UseLeLink (remote_bda);

    return p_cb->is_le_device;
}
/*******************************************************************************
**
** Function         bta_hh_le_add_hid_srvc_entry
**
** Description      Add a HID service entry in the HID device control block
**
** Parameters:
**
*******************************************************************************/
BOOLEAN bta_hh_le_add_hid_srvc_entry(tBTA_HH_DEV_CB *p_dev_cb, UINT8 idx)
{
    BOOLEAN added = FALSE;

    if (idx < BTA_HH_LE_HID_SRVC_MAX)
    {
        p_dev_cb->hid_srvc[idx].in_use = TRUE;
        added = TRUE;
    }
    else
    {
        APPL_TRACE_ERROR("DB full,max HID service entry!");
    }
    return added;

}
/*******************************************************************************
**
** Function         bta_hh_le_open_conn
**
** Description      open a GATT connection first.
**
** Parameters:
**
*******************************************************************************/
void bta_hh_le_open_conn(tBTA_HH_DEV_CB *p_cb, BD_ADDR remote_bda)
{
    /* update cb_index[] map */
    p_cb->hid_handle = BTA_HH_GET_LE_DEV_HDL(p_cb->index);
    memcpy(p_cb->addr, remote_bda, BD_ADDR_LEN);
    bta_hh_cb.le_cb_index[BTA_HH_GET_LE_CB_IDX(p_cb->hid_handle)] = p_cb->index;
    p_cb->in_use = TRUE;

    BTA_GATTC_Open(bta_hh_cb.gatt_if, remote_bda, TRUE, BTA_GATT_TRANSPORT_LE);
}
/*******************************************************************************
**
** Function         bta_hh_le_fill_16bits_gatt_id
**
** Description      Utility function to fill a GATT ID strucure
**
*******************************************************************************/
void bta_hh_le_fill_16bits_gatt_id(UINT8 inst_id, UINT16 uuid,  tBTA_GATT_ID *p_output)
{
    p_output->inst_id        = inst_id;
    p_output->uuid.len       = LEN_UUID_16;
    p_output->uuid.uu.uuid16 = uuid;
}
/*******************************************************************************
**
** Function         bta_hh_le_fill_16bits_srvc_id
**
** Description      Utility function to fill a service ID strucure with a 16 bits
**                  service UUID.
**
*******************************************************************************/
void bta_hh_le_fill_16bits_srvc_id(BOOLEAN is_pri, UINT8 inst_id, UINT16 srvc_uuid,
                                   tBTA_GATT_SRVC_ID *p_output)
{
    memset((void *)p_output, 0, sizeof(tBTA_GATT_SRVC_ID));
    p_output->is_primary        = is_pri;
    bta_hh_le_fill_16bits_gatt_id(inst_id, srvc_uuid, &p_output->id);

}
/*******************************************************************************
**
** Function         bta_hh_le_fill_16bits_char_id
**
** Description      Utility function to fill a char ID strucure with a 16 bits
**                  char UUID.
**
*******************************************************************************/
void bta_hh_le_fill_16bits_char_id(UINT8 inst_id, UINT16 char_uuid,
                                   tBTA_GATT_ID *p_output)
{
    memset((void *)p_output, 0, sizeof(tBTA_GATT_ID));
    bta_hh_le_fill_16bits_gatt_id(inst_id, char_uuid, p_output);
}
/*******************************************************************************
**
** Function         bta_hh_le_find_dev_cb_by_conn_id
**
** Description      Utility function find a device control block by connection ID.
**
*******************************************************************************/
tBTA_HH_DEV_CB * bta_hh_le_find_dev_cb_by_conn_id(UINT16 conn_id)
{
    UINT8   i;
    tBTA_HH_DEV_CB *p_dev_cb = &bta_hh_cb.kdev[0];

    for (i = 0; i < BTA_HH_MAX_DEVICE; i ++, p_dev_cb ++)
    {
        if (p_dev_cb->in_use  && p_dev_cb->conn_id == conn_id)
            return p_dev_cb;
    }
    return NULL;
}
/*******************************************************************************
**
** Function         bta_hh_le_find_dev_cb_by_bda
**
** Description      Utility function find a device control block by BD address.
**
*******************************************************************************/
tBTA_HH_DEV_CB * bta_hh_le_find_dev_cb_by_bda(BD_ADDR bda)
{
    UINT8   i;
    tBTA_HH_DEV_CB *p_dev_cb = &bta_hh_cb.kdev[0];

    for (i = 0; i < BTA_HH_MAX_DEVICE; i ++, p_dev_cb ++)
    {
        if (p_dev_cb->in_use  &&
            memcmp(p_dev_cb->addr, bda, BD_ADDR_LEN) == 0)
            return p_dev_cb;
    }
    return NULL;
}

/*******************************************************************************
**
** Function         bta_hh_le_find_service_inst_by_battery_inst_id
**
** Description      find HID service instance ID by battery service instance ID
**
*******************************************************************************/
UINT8 bta_hh_le_find_service_inst_by_battery_inst_id(tBTA_HH_DEV_CB *p_cb, UINT8 ba_inst_id)
{
    UINT8   i;

    for (i = 0; i < BTA_HH_LE_HID_SRVC_MAX; i ++)
    {
        if (p_cb->hid_srvc[i].in_use &&
            p_cb->hid_srvc[i].incl_srvc_inst == ba_inst_id)
        {
            return i;
        }
    }
    return BTA_HH_IDX_INVALID;
}
/*******************************************************************************
**
** Function         bta_hh_le_find_report_entry
**
** Description      find the report entry by service instance and report UUID and
**                  instance ID
**
*******************************************************************************/
tBTA_HH_LE_RPT * bta_hh_le_find_report_entry(tBTA_HH_DEV_CB *p_cb,
                                             UINT8  srvc_inst_id,  /* service instance ID */
                                             UINT16 rpt_uuid,
                                             UINT8  char_inst_id)
{
    UINT8   i;
    UINT8   hid_inst_id = srvc_inst_id;
    tBTA_HH_LE_RPT *p_rpt;

    if (rpt_uuid == GATT_UUID_BATTERY_LEVEL)
    {
        hid_inst_id = bta_hh_le_find_service_inst_by_battery_inst_id(p_cb, srvc_inst_id);

        if (hid_inst_id == BTA_HH_IDX_INVALID)
            return NULL;
    }

    p_rpt = &p_cb->hid_srvc[hid_inst_id].report[0];

    for (i = 0; i < BTA_HH_LE_RPT_MAX; i ++, p_rpt ++)
    {
        if (p_rpt->uuid == rpt_uuid &&
            p_rpt->inst_id == BTA_HH_LE_RPT_INST_ID_MAP(srvc_inst_id, char_inst_id))
        {

            return p_rpt;
        }
    }
    return NULL;

}
/*******************************************************************************
**
** Function         bta_hh_le_find_rpt_by_idtype
**
** Description      find a report entry by report ID and protocol mode
**
** Returns          void
**
*******************************************************************************/
tBTA_HH_LE_RPT * bta_hh_le_find_rpt_by_idtype(tBTA_HH_LE_RPT*p_head, UINT8 mode,
                                              tBTA_HH_RPT_TYPE r_type, UINT8 rpt_id)
{
    tBTA_HH_LE_RPT *p_rpt = p_head;
    UINT8   i;

#if BTA_HH_DEBUG == TRUE
    APPL_TRACE_DEBUG("bta_hh_le_find_rpt_by_idtype: r_type: %d rpt_id: %d", r_type, rpt_id);
#endif

    for (i = 0 ; i < BTA_HH_LE_RPT_MAX; i ++, p_rpt++)
    {
        if (p_rpt->in_use && p_rpt->rpt_id == rpt_id && r_type == p_rpt->rpt_type)
        {
            /* return battery report w/o condition */
            if (p_rpt->uuid == GATT_UUID_BATTERY_LEVEL)
                return p_rpt;

            if (mode == BTA_HH_PROTO_RPT_MODE && p_rpt->uuid == GATT_UUID_HID_REPORT)
                return p_rpt;

            if ( mode ==BTA_HH_PROTO_BOOT_MODE &&
                (p_rpt->uuid >= GATT_UUID_HID_BT_KB_INPUT && p_rpt->uuid <= GATT_UUID_HID_BT_MOUSE_INPUT))
                return p_rpt;
        }
    }
    return NULL;
}
/*******************************************************************************
**
** Function         bta_hh_le_find_alloc_report_entry
**
** Description      find or allocate a report entry in the HID service report list.
**
*******************************************************************************/
tBTA_HH_LE_RPT * bta_hh_le_find_alloc_report_entry(tBTA_HH_DEV_CB *p_cb,
                                                   UINT8 srvc_inst_id,
                                                   UINT16 rpt_uuid,
                                                   UINT8  inst_id,
                                                   UINT8  prop)
{
    UINT8   i, hid_inst_id = srvc_inst_id;
    tBTA_HH_LE_RPT *p_rpt;

    if (rpt_uuid == GATT_UUID_BATTERY_LEVEL)
    {
        hid_inst_id = bta_hh_le_find_service_inst_by_battery_inst_id(p_cb, srvc_inst_id);

        if (hid_inst_id == BTA_HH_IDX_INVALID)
            return NULL;
    }
    p_rpt = &p_cb->hid_srvc[hid_inst_id].report[0];

    for (i = 0; i < BTA_HH_LE_RPT_MAX; i ++, p_rpt ++)
    {
        if (!p_rpt->in_use ||
            (p_rpt->uuid == rpt_uuid &&
             p_rpt->inst_id == BTA_HH_LE_RPT_INST_ID_MAP(srvc_inst_id, inst_id)))
        {
            if (!p_rpt->in_use)
            {
                p_rpt->in_use   = TRUE;
                p_rpt->index    = i;
                p_rpt->inst_id  = BTA_HH_LE_RPT_INST_ID_MAP(srvc_inst_id, inst_id);
                p_rpt->prop     = prop;
                p_rpt->uuid     = rpt_uuid;

                /* assign report type */
                for (i = 0; i < BTA_LE_HID_RTP_UUID_MAX; i ++)
                {
                    if (bta_hh_uuid_to_rtp_type[i][0] == rpt_uuid)
                    {
                        p_rpt->rpt_type = (tBTA_HH_RPT_TYPE)bta_hh_uuid_to_rtp_type[i][1];

                        if (rpt_uuid == GATT_UUID_HID_BT_KB_INPUT || rpt_uuid == GATT_UUID_HID_BT_KB_OUTPUT)
                            p_rpt->rpt_id = BTA_HH_KEYBD_RPT_ID;

                        if (rpt_uuid == GATT_UUID_HID_BT_MOUSE_INPUT)
                            p_rpt->rpt_id = BTA_HH_MOUSE_RPT_ID;

                        break;
                    }
                }
            }

            return p_rpt;
        }
    }
    return NULL;
}

/*******************************************************************************
**
** Function         bta_hh_le_read_char_dscrpt
**
** Description      read cahracteristic descriptor
**
*******************************************************************************/
tBTA_HH_STATUS bta_hh_le_read_char_dscrpt(tBTA_HH_DEV_CB *p_cb, UINT16 srvc_uuid, UINT8 srvc_inst_id,
                                UINT16 char_uuid, UINT8 char_inst_id, UINT16 char_descp_uuid)
{
    tBTA_GATTC_CHAR_ID  char_id;
    tBT_UUID        descr_uuid;
    tBTA_GATTC_CHAR_DESCR_ID    descr_id;
    tBTA_HH_STATUS  status = BTA_HH_ERR;

    bta_hh_le_fill_16bits_srvc_id(TRUE, srvc_inst_id, srvc_uuid, &char_id.srvc_id);
    bta_hh_le_fill_16bits_char_id(char_inst_id, char_uuid, &char_id.char_id);

    descr_uuid.len       = LEN_UUID_16;
    descr_uuid.uu.uuid16 = char_descp_uuid;

    /* find the report reference descriptor */
    if (BTA_GATTC_GetFirstCharDescr(p_cb->conn_id,
                                &char_id,
                                &descr_uuid,
                                &descr_id) == BTA_GATT_OK)
    {
        BTA_GATTC_ReadCharDescr(p_cb->conn_id,
                                &descr_id,
                                BTA_GATT_AUTH_REQ_NONE);

        status = BTA_HH_OK;
    }
    else
    {
#if BTA_HH_DEBUG == TRUE
        APPL_TRACE_ERROR("bta_hh_le_read_char_dscrpt: No such descrpt exists: %s(0x%04x)",
            bta_hh_uuid_to_str(char_descp_uuid), char_descp_uuid);
#endif
    }
    return status;
}
/*******************************************************************************
**
** Function         bta_hh_le_read_rpt_ref_descr
**
** Description      read report refernece descriptors in service discovery process
**
*******************************************************************************/
void bta_hh_le_read_rpt_ref_descr(tBTA_HH_DEV_CB *p_dev_cb, tBTA_HH_LE_RPT *p_rpt)
{
    BOOLEAN started = FALSE;
    UINT16  srvc_uuid, char_uuid;

    while (p_rpt != NULL)
    {
        if(!p_rpt->in_use)
            break;

        if (p_rpt->rpt_type == BTA_HH_RPTT_INPUT)
        {
            /* is battery report */
            if (p_rpt->uuid == GATT_UUID_BATTERY_LEVEL)
            {
#if BTA_HH_DEBUG == TRUE
                APPL_TRACE_DEBUG("read battery level report reference descriptor");
#endif
                srvc_uuid = UUID_SERVCLASS_BATTERY;
                char_uuid = GATT_UUID_BATTERY_LEVEL;
            }
            else
            {
#if BTA_HH_DEBUG == TRUE
                APPL_TRACE_DEBUG("read HID report reference descriptor");
#endif
                srvc_uuid = UUID_SERVCLASS_LE_HID;
                char_uuid = GATT_UUID_HID_REPORT;
            }

            if (bta_hh_le_read_char_dscrpt(p_dev_cb,
                                            srvc_uuid,
                                            BTA_HH_LE_RPT_GET_SRVC_INST_ID(p_rpt->inst_id),
                                            char_uuid,
                                            BTA_HH_LE_RPT_GET_RPT_INST_ID(p_rpt->inst_id),
                                            GATT_UUID_RPT_REF_DESCR)
                == BTA_HH_OK)
            {
                started = TRUE;
                break;
            }
        }

        if (p_rpt->index == BTA_HH_LE_RPT_MAX - 1)
            break;

        p_rpt ++;
    }


    /* if no report reference descriptor */
    if (!started)
    {
        /* explore next char */
        bta_hh_le_search_hid_chars(p_dev_cb);
    }
}
/*******************************************************************************
**
** Function         bta_hh_le_save_rpt_ref
**
** Description      save report reference information and move to next one.
**
** Parameters:
**
*******************************************************************************/
void bta_hh_le_save_rpt_ref(tBTA_HH_DEV_CB *p_dev_cb, tBTA_HH_LE_RPT  *p_rpt,
                            tBTA_GATTC_READ *p_data)
{
    UINT8 *pp;

    /* if the length of the descriptor value is right, parse it */
    if (p_data->status == BTA_GATT_OK &&
        p_data->p_value && p_data->p_value->unformat.len == 2)
    {
        pp = p_data->p_value->unformat.p_value;

        STREAM_TO_UINT8(p_rpt->rpt_id, pp);
        STREAM_TO_UINT8(p_rpt->rpt_type, pp);

        if (p_rpt->rpt_type > BTA_HH_RPTT_FEATURE) /* invalid report type */
            p_rpt->rpt_type = BTA_HH_RPTT_RESRV;

#if BTA_HH_DEBUG == TRUE
        APPL_TRACE_DEBUG("report ID: %d", p_rpt->rpt_id);
#endif
    }

    if (p_rpt->index < BTA_HH_LE_RPT_MAX - 1)
        p_rpt ++;
    else
        p_rpt = NULL;
    /* read next report reference descriptor  */
    bta_hh_le_read_rpt_ref_descr(p_dev_cb, p_rpt);

}
/*******************************************************************************
**
** Function         bta_hh_le_save_rpt_ref
**
** Description      save report reference information and move to next one.
**
** Parameters:
**
*******************************************************************************/
void bta_hh_le_save_ext_rpt_ref(tBTA_HH_DEV_CB *p_dev_cb,
                                tBTA_GATTC_READ *p_data)
{
    UINT8 *pp;

    /* if the length of the descriptor value is right, parse it
      assume it's a 16 bits UUID */
    if (p_data->status == BTA_GATT_OK &&
        p_data->p_value && p_data->p_value->unformat.len == 2)
    {
        pp = p_data->p_value->unformat.p_value;
        STREAM_TO_UINT16(p_dev_cb->hid_srvc[p_dev_cb->cur_srvc_index].ext_rpt_ref, pp);

#if BTA_HH_DEBUG == TRUE
        APPL_TRACE_DEBUG("External Report Reference UUID 0x%04x",
                    p_dev_cb->hid_srvc[p_dev_cb->cur_srvc_index].ext_rpt_ref);
#endif
    }
    bta_hh_le_search_hid_chars(p_dev_cb);

}
/*******************************************************************************
**
** Function         bta_hh_le_register_input_notif
**
** Description      Register for all notifications for the report applicable
**                  for the protocol mode.
**
** Parameters:
**
*******************************************************************************/
void bta_hh_le_register_input_notif(tBTA_HH_DEV_CB *p_dev_cb, UINT8 srvc_inst,
                                    UINT8 proto_mode, BOOLEAN register_ba)
{
    tBTA_HH_LE_RPT  *p_rpt = &p_dev_cb->hid_srvc[srvc_inst].report[0];
    tBTA_GATTC_CHAR_ID  char_id;
    UINT8   i;
    UINT16  srvc_uuid;

#if BTA_HH_DEBUG == TRUE
    APPL_TRACE_DEBUG("bta_hh_le_register_input_notif mode: %d", proto_mode);
#endif

    for (i = 0; i < BTA_HH_LE_RPT_MAX; i ++, p_rpt ++)
    {
        if (p_rpt->rpt_type == BTA_HH_RPTT_INPUT)
        {
            if (p_rpt->uuid == GATT_UUID_BATTERY_LEVEL)
                srvc_uuid = UUID_SERVCLASS_BATTERY;
            else
                srvc_uuid = UUID_SERVCLASS_LE_HID;

            bta_hh_le_fill_16bits_srvc_id(TRUE, BTA_HH_LE_RPT_GET_SRVC_INST_ID(p_rpt->inst_id), srvc_uuid, &char_id.srvc_id);
            bta_hh_le_fill_16bits_char_id(BTA_HH_LE_RPT_GET_RPT_INST_ID(p_rpt->inst_id), p_rpt->uuid, &char_id.char_id);

            if (register_ba && p_rpt->uuid == GATT_UUID_BATTERY_LEVEL)
            {
                BTA_GATTC_RegisterForNotifications(bta_hh_cb.gatt_if,
                                                   p_dev_cb->addr,
                                                   &char_id);
            }
            /* boot mode, deregister report input notification */
            else if (proto_mode == BTA_HH_PROTO_BOOT_MODE)
            {
                if (p_rpt->uuid == GATT_UUID_HID_REPORT &&
                    p_rpt->client_cfg_value == BTA_GATT_CLT_CONFIG_NOTIFICATION)
                {
                    APPL_TRACE_DEBUG("---> Deregister Report ID: %d", p_rpt->rpt_id);
                    BTA_GATTC_DeregisterForNotifications(bta_hh_cb.gatt_if,
                                                       p_dev_cb->addr,
                                                       &char_id);
                }
                /* register boot reports notification */
                else if (p_rpt->uuid == GATT_UUID_HID_BT_KB_INPUT ||
                         p_rpt->uuid == GATT_UUID_HID_BT_MOUSE_INPUT)
                {
                    APPL_TRACE_DEBUG("<--- Register Boot Report ID: %d", p_rpt->rpt_id);
                    BTA_GATTC_RegisterForNotifications(bta_hh_cb.gatt_if,
                                                       p_dev_cb->addr,
                                                       &char_id);
                }
            }
            else if (proto_mode == BTA_HH_PROTO_RPT_MODE)
            {
                if ((p_rpt->uuid == GATT_UUID_HID_BT_KB_INPUT ||
                    p_rpt->uuid == GATT_UUID_HID_BT_MOUSE_INPUT) &&
                    p_rpt->client_cfg_value == BTA_GATT_CLT_CONFIG_NOTIFICATION)
                {

                    APPL_TRACE_DEBUG("---> Deregister Boot Report ID: %d", p_rpt->rpt_id);
                    BTA_GATTC_DeregisterForNotifications(bta_hh_cb.gatt_if,
                                                       p_dev_cb->addr,
                                                       &char_id);
                }
                else if (p_rpt->uuid == GATT_UUID_HID_REPORT &&
                         p_rpt->client_cfg_value == BTA_GATT_CLT_CONFIG_NOTIFICATION)
                {
                    APPL_TRACE_DEBUG("<--- Register Report ID: %d", p_rpt->rpt_id);
                    BTA_GATTC_RegisterForNotifications(bta_hh_cb.gatt_if,
                                                       p_dev_cb->addr,
                                                       &char_id);
                }
            }
            /*
            else unknow protocol mode */
        }
    }
}

/*******************************************************************************
**
** Function         bta_hh_le_open_cmpl
**
** Description      HID over GATT connection sucessfully opened
**
*******************************************************************************/
void bta_hh_le_open_cmpl(tBTA_HH_DEV_CB *p_cb)
{
    if ( p_cb->disc_active == BTA_HH_LE_DISC_NONE)
    {
#if BTA_HH_DEBUG
        bta_hh_le_hid_report_dbg(p_cb);
#endif
        bta_hh_le_register_input_notif(p_cb, 0, p_cb->mode, TRUE);
        bta_hh_sm_execute(p_cb, BTA_HH_OPEN_CMPL_EVT, NULL);
#if (BTA_HH_LE_RECONN == TRUE)
        if (p_cb->status == BTA_HH_OK)
        {
            bta_hh_le_add_dev_bg_conn(p_cb, TRUE);
        }
#endif
    }
}
/*******************************************************************************
**
** Function         bta_hh_le_write_char_clt_cfg
**
** Description      Utility function to find and write client configuration of
**                  a characteristic
**
*******************************************************************************/
BOOLEAN bta_hh_le_write_char_clt_cfg(tBTA_HH_DEV_CB *p_cb,
                                     UINT8 srvc_inst_id, UINT16 srvc_uuid16,
                                     UINT8 char_inst_id, UINT16 char_uuid16,
                                     UINT16 clt_cfg_value)
{
    tBTA_GATTC_CHAR_ID          char_id;
    tBT_UUID                    descr_cond;
    tBTA_GATTC_CHAR_DESCR_ID    descr_id;
    tBTA_GATT_UNFMT             value;
    UINT8                      buf[2], *pp = buf;

    bta_hh_le_fill_16bits_srvc_id(TRUE, srvc_inst_id, srvc_uuid16, &char_id.srvc_id);
    bta_hh_le_fill_16bits_char_id(char_inst_id, char_uuid16, &char_id.char_id);

    descr_cond.len       = LEN_UUID_16;
    descr_cond.uu.uuid16 = GATT_UUID_CHAR_CLIENT_CONFIG;

    value.len = 2;
    value.p_value = buf;

    UINT16_TO_STREAM(pp, clt_cfg_value);

    if (BTA_GATTC_GetFirstCharDescr(p_cb->conn_id,
                                    &char_id,
                                    &descr_cond,
                                    &descr_id) == BTA_GATT_OK)
    {
        BTA_GATTC_WriteCharDescr(p_cb->conn_id,
                            &descr_id,
                            BTA_GATTC_TYPE_WRITE,
                            &value,
                            BTA_GATT_AUTH_REQ_NONE);

        return TRUE;
    }
    return FALSE;
}
/*******************************************************************************
**
** Function         bta_hh_le_write_rpt_clt_cfg
**
** Description      write client configuration. This is only for input report
**                  enable all input notification upon connection open.
**
*******************************************************************************/
BOOLEAN bta_hh_le_write_rpt_clt_cfg(tBTA_HH_DEV_CB *p_cb, UINT8 srvc_inst_id)
{
    UINT8           i;
    tBTA_HH_LE_RPT  *p_rpt = &p_cb->hid_srvc[srvc_inst_id].report[p_cb->clt_cfg_idx];
    UINT16          srvc_uuid;

    for (i = p_cb->clt_cfg_idx; i < BTA_HH_LE_RPT_MAX && p_rpt->in_use; i ++, p_rpt ++)
    {
        /* enable notification for all input report, regardless mode */
        if (p_rpt->rpt_type == BTA_HH_RPTT_INPUT)

        {
            if (p_rpt->uuid == GATT_UUID_BATTERY_LEVEL)
                srvc_uuid = UUID_SERVCLASS_BATTERY;
            else
                srvc_uuid = UUID_SERVCLASS_LE_HID;

            if (bta_hh_le_write_char_clt_cfg(p_cb,
                                             BTA_HH_LE_RPT_GET_SRVC_INST_ID(p_rpt->inst_id),
                                             srvc_uuid,
                                             BTA_HH_LE_RPT_GET_RPT_INST_ID(p_rpt->inst_id),
                                             p_rpt->uuid,
                                             BTA_GATT_CLT_CONFIG_NOTIFICATION))
            {
                p_cb->clt_cfg_idx = i;
                return TRUE;
            }
        }

    }
    p_cb->clt_cfg_idx = 0;

    /* client configuration is completed, send open callback */
    if (p_cb->state == BTA_HH_W4_CONN_ST)
    {
        p_cb->disc_active &= ~BTA_HH_LE_DISC_HIDS;

        /* discover scan parameter profile is act as report host */
        bta_hh_le_search_scps(p_cb);
    }
    return FALSE;
}

/*******************************************************************************
**
** Function         bta_hh_le_set_protocol_mode
**
** Description      Set remote device protocol mode.
**
*******************************************************************************/
BOOLEAN bta_hh_le_set_protocol_mode(tBTA_HH_DEV_CB *p_cb, tBTA_HH_PROTO_MODE mode)
{
    tBTA_GATTC_CHAR_ID  char_id;
    tBTA_HH_CBDATA      cback_data ;
    BOOLEAN             exec = TRUE;

    APPL_TRACE_DEBUG("bta_hh_le_set_protocol_mode attempt mode: %s",
                      (mode == BTA_HH_PROTO_RPT_MODE)? "Report": "Boot");

    cback_data.handle  = p_cb->hid_handle;
    /* boot mode is not supported in the remote device */
    if ((p_cb->hid_srvc[BTA_HH_LE_SRVC_DEF].option_char & BTA_HH_LE_PROTO_MODE_BIT) == 0)
    {
        exec        = FALSE;
        p_cb->mode  = BTA_HH_PROTO_RPT_MODE;

        if (mode == BTA_HH_PROTO_BOOT_MODE)
        {
            APPL_TRACE_ERROR("Set Boot Mode failed!! No PROTO_MODE Char!");
            cback_data.status = BTA_HH_ERR;
        }
        else
        {
            /* if set to report mode, need to de-register all input report notification */
            bta_hh_le_register_input_notif(p_cb, 0, p_cb->mode, FALSE);
            cback_data.status = BTA_HH_OK;
        }
        if (p_cb->state == BTA_HH_W4_CONN_ST)
        {
            p_cb->status = (cback_data.status == BTA_HH_OK)? BTA_HH_OK: BTA_HH_ERR_PROTO;
        }
        else
            (* bta_hh_cb.p_cback)(BTA_HH_SET_PROTO_EVT, (tBTA_HH *)&cback_data);
    }
    else
    {
        bta_hh_le_fill_16bits_srvc_id(TRUE, 0, UUID_SERVCLASS_LE_HID, &char_id.srvc_id);
        bta_hh_le_fill_16bits_char_id(0, GATT_UUID_HID_PROTO_MODE, &char_id.char_id);

        p_cb->mode = mode;
        mode = (mode == BTA_HH_PROTO_BOOT_MODE)? BTA_HH_LE_PROTO_BOOT_MODE : BTA_HH_LE_PROTO_REPORT_MODE;

        BTA_GATTC_WriteCharValue(p_cb->conn_id,
                                 &char_id,
                                 BTA_GATTC_TYPE_WRITE_NO_RSP,
                                 1,
                                 &mode,
                                 BTA_GATT_AUTH_REQ_NONE);
    }
    return exec;
}

/*******************************************************************************
**
** Function         bta_hh_le_get_protocol_mode
**
** Description      Get remote device protocol mode.
**
*******************************************************************************/
void bta_hh_le_get_protocol_mode(tBTA_HH_DEV_CB *p_cb)
{
    tBTA_GATTC_CHAR_ID  char_id;
    tBTA_HH_HSDATA    hs_data;
    UINT8 i;

    p_cb->w4_evt = BTA_HH_GET_PROTO_EVT;

    for (i = 0; i< BTA_HH_LE_HID_SRVC_MAX; i ++)
    {
        if (p_cb->hid_srvc[i].in_use &&
            p_cb->hid_srvc[i].option_char & BTA_HH_LE_PROTO_MODE_BIT)
        {
            bta_hh_le_fill_16bits_srvc_id(TRUE, 0, UUID_SERVCLASS_LE_HID, &char_id.srvc_id);
            bta_hh_le_fill_16bits_char_id(0, GATT_UUID_HID_PROTO_MODE, &char_id.char_id);

            BTA_GATTC_ReadCharacteristic(p_cb->conn_id,
                                        &char_id,
                                        BTA_GATT_AUTH_REQ_NONE);
            break;
        }
    }
    /* no service support protocol_mode, by default report mode */
    if (i == BTA_HH_LE_HID_SRVC_MAX)
    {
        hs_data.status  = BTA_HH_OK;
        hs_data.handle  = p_cb->hid_handle;
        hs_data.rsp_data.proto_mode = BTA_HH_PROTO_RPT_MODE;
        p_cb->w4_evt = 0;
        (* bta_hh_cb.p_cback)(BTA_HH_GET_PROTO_EVT, (tBTA_HH *)&hs_data);
    }

}
/*******************************************************************************
**
** Function         bta_hh_le_expl_rpt
**
** Description      explore all report characteristic
**
*******************************************************************************/
void bta_hh_le_expl_rpt(tBTA_HH_DEV_CB *p_dev_cb,
                           tBTA_GATTC_CHAR_ID *p_char_id,
                           tBT_UUID *p_char_cond,
                           tBTA_GATT_CHAR_PROP prop)
{
    tBTA_GATTC_CHAR_ID  char_result;

    do
    {
        if (bta_hh_le_find_alloc_report_entry(p_dev_cb,
                                          p_dev_cb->cur_srvc_index,
                                          GATT_UUID_HID_REPORT,
                                          p_char_id->char_id.inst_id,
                                          prop) == NULL)
        {
            APPL_TRACE_ERROR("Add report entry failed !!!");
            break;
        }

        APPL_TRACE_DEBUG("Find more REPORT");

        if (BTA_GATTC_GetNextChar(p_dev_cb->conn_id,
                          p_char_id,
                          p_char_cond,
                          &char_result,
                          &prop) != BTA_GATT_OK)
            break;

        p_char_id = &char_result;
    }
    while (1);

    APPL_TRACE_ERROR("all report searched");
    bta_hh_le_read_rpt_ref_descr(p_dev_cb,
                                 &p_dev_cb->hid_srvc[p_dev_cb->cur_srvc_index].report[0]);


    return ;
}
/*******************************************************************************
**
** Function         bta_hh_le_expl_boot_rpt
**
** Description      explore boot report
**
*******************************************************************************/
void bta_hh_le_expl_boot_rpt(tBTA_HH_DEV_CB *p_dev_cb, UINT16 char_uuid,
                                tBTA_GATT_CHAR_PROP prop)
{
    if (bta_hh_le_find_alloc_report_entry(p_dev_cb,
                                      p_dev_cb->cur_srvc_index,
                                      char_uuid,
                                      0,
                                      prop) == NULL)

    {
        APPL_TRACE_ERROR("Add report entry failed !!!");
    }

    return;
}
/*******************************************************************************
**
** Function         bta_hh_le_dis_cback
**
** Description      DIS read complete callback
**
** Parameters:
**
*******************************************************************************/
void bta_hh_le_dis_cback(BD_ADDR addr, tDIS_VALUE *p_dis_value)
{
    tBTA_HH_DEV_CB *p_cb = bta_hh_le_find_dev_cb_by_bda(addr);


    if (p_cb == NULL || p_dis_value == NULL)
    {
        APPL_TRACE_ERROR("received unexpected/error DIS callback");
        return;
    }

    p_cb->disc_active &= ~BTA_HH_LE_DISC_DIS;
    /* plug in the PnP info for this device */
    if (p_dis_value->attr_mask & DIS_ATTR_PNP_ID_BIT)
    {
#if BTA_HH_DEBUG == TRUE
        APPL_TRACE_DEBUG("Plug in PnP info: product_id = %02x, vendor_id = %04x, version = %04x",
                p_dis_value->pnp_id.product_id,
                p_dis_value->pnp_id.vendor_id,
                p_dis_value->pnp_id.product_version);
#endif
        p_cb->dscp_info.product_id = p_dis_value->pnp_id.product_id;
        p_cb->dscp_info.vendor_id  = p_dis_value->pnp_id.vendor_id;
        p_cb->dscp_info.version    = p_dis_value->pnp_id.product_version;
    }
    bta_hh_le_open_cmpl(p_cb);
}
/*******************************************************************************
**
** Function         bta_hh_le_pri_service_discovery
**
** Description      Initialize GATT discovery on the remote LE HID device by opening
**                  a GATT connection first.
**
** Parameters:
**
*******************************************************************************/
void bta_hh_le_pri_service_discovery(tBTA_HH_DEV_CB *p_cb)
{
    tBT_UUID        pri_srvc;

    p_cb->disc_active |= (BTA_HH_LE_DISC_HIDS|BTA_HH_LE_DISC_DIS);

    /* read DIS info */
    if (!DIS_ReadDISInfo(p_cb->addr, bta_hh_le_dis_cback, DIS_ATTR_PNP_ID_BIT))
    {
        APPL_TRACE_ERROR("read DIS failed");
        p_cb->disc_active &= ~BTA_HH_LE_DISC_DIS;
    }

    /* in parallel */
    /* start primary service discovery for HID service */
    pri_srvc.len        = LEN_UUID_16;
    pri_srvc.uu.uuid16  = UUID_SERVCLASS_LE_HID;
    BTA_GATTC_ServiceSearchRequest(p_cb->conn_id, &pri_srvc);
    return;
}
/*******************************************************************************
**
** Function         bta_hh_le_encrypt_cback
**
** Description      link encryption complete callback for bond verification.
**
** Returns          None
**
*******************************************************************************/
void bta_hh_le_encrypt_cback(BD_ADDR bd_addr, tBTA_GATT_TRANSPORT transport,
                                    void *p_ref_data, tBTM_STATUS result)
{
    UINT8   idx = bta_hh_find_cb(bd_addr);
    tBTA_HH_DEV_CB *p_dev_cb;
    UNUSED(p_ref_data);
    UNUSED (transport);

    if (idx != BTA_HH_IDX_INVALID)
        p_dev_cb = &bta_hh_cb.kdev[idx];
    else
    {
        APPL_TRACE_ERROR("unexpected encryption callback, ignore");
        return;
    }
    p_dev_cb->status = (result == BTM_SUCCESS) ? BTA_HH_OK : BTA_HH_ERR_SEC;

    bta_hh_sm_execute(p_dev_cb, BTA_HH_ENC_CMPL_EVT, NULL);
}
/*******************************************************************************
**
** Function         bta_hh_security_cmpl
**
** Description      Security check completed, start the service discovery
**                  if no cache available, otherwise report connection open completed
**
** Parameters:
**
*******************************************************************************/
void bta_hh_security_cmpl(tBTA_HH_DEV_CB *p_cb, tBTA_HH_DATA *p_buf)
{
    UNUSED(p_buf);

    if (p_cb->status == BTA_HH_OK)
    {
        /*  discovery has been done for HID service */
        if (p_cb->app_id != 0 && p_cb->hid_srvc[BTA_HH_LE_SRVC_DEF].in_use)
        {
            /* configure protocol mode */
            if (bta_hh_le_set_protocol_mode(p_cb, p_cb->mode) == FALSE)
            {
                APPL_TRACE_ERROR("bta_hh_security_cmpl");
                bta_hh_le_open_cmpl(p_cb);
            }
        }
        /* start primary service discovery for HID service */
        else
        {
            bta_hh_le_pri_service_discovery(p_cb);
        }
    }
    else
        bta_hh_le_api_disc_act(p_cb);

}

/*******************************************************************************
**
** Function         bta_hh_le_notify_enc_cmpl
**
** Description      process GATT encryption complete event
**
** Returns
**
*******************************************************************************/
void bta_hh_le_notify_enc_cmpl(tBTA_HH_DEV_CB *p_cb, tBTA_HH_DATA *p_buf)
{
    if (p_cb == NULL || p_cb->security_pending == FALSE ||
        p_buf == NULL || p_buf->le_enc_cmpl.client_if != bta_hh_cb.gatt_if)
    {
        return;
    }

    p_cb->security_pending = FALSE;
    bta_hh_start_security(p_cb, NULL);
}

/*******************************************************************************
**
** Function         bta_hh_clear_service_cache
**
** Description    clear the service cache
**
** Parameters:
**
*******************************************************************************/
void bta_hh_clear_service_cache(tBTA_HH_DEV_CB *p_cb)
{
    UINT8 i;
    tBTA_HH_LE_HID_SRVC     *p_hid_srvc = &p_cb->hid_srvc[0];

    p_cb->app_id = 0;
    p_cb->total_srvc = 0;
    p_cb->dscp_info.descriptor.dsc_list = NULL;

    for (i = 0; i < BTA_HH_LE_HID_SRVC_MAX; i ++, p_hid_srvc ++)
    {
        utl_freebuf((void **)&p_hid_srvc->rpt_map);
        memset(p_hid_srvc, 0, sizeof(tBTA_HH_LE_HID_SRVC));
    }
}

/*******************************************************************************
**
** Function         bta_hh_start_security
**
** Description      start the security check of the established connection
**
** Parameters:
**
*******************************************************************************/
void bta_hh_start_security(tBTA_HH_DEV_CB *p_cb, tBTA_HH_DATA *p_buf)
{
    UINT8           sec_flag=0;
    tBTM_SEC_DEV_REC  *p_dev_rec;
    UNUSED(p_buf);

    p_dev_rec = btm_find_dev(p_cb->addr);
    if (p_dev_rec)
    {
        if (p_dev_rec->sec_state == BTM_SEC_STATE_ENCRYPTING ||
            p_dev_rec->sec_state == BTM_SEC_STATE_AUTHENTICATING)
        {
            /* if security collision happened, wait for encryption done */
            p_cb->security_pending = TRUE;
            return;
        }
    }

    /* verify bond */
    BTM_GetSecurityFlagsByTransport(p_cb->addr, &sec_flag, BT_TRANSPORT_LE);

    /* if link has been encrypted */
    if (sec_flag & BTM_SEC_FLAG_ENCRYPTED)
    {
        bta_hh_sm_execute(p_cb, BTA_HH_ENC_CMPL_EVT, NULL);
    }
    /* if bonded and link not encrypted */
    else if (sec_flag & BTM_SEC_FLAG_LKEY_KNOWN)
    {
        sec_flag = BTM_BLE_SEC_ENCRYPT;
        p_cb->status = BTA_HH_ERR_AUTH_FAILED;
        BTM_SetEncryption(p_cb->addr, BTA_TRANSPORT_LE, bta_hh_le_encrypt_cback, &sec_flag);
    }
    /* unbonded device, report security error here */
    else if (p_cb->sec_mask != BTA_SEC_NONE)
    {
        sec_flag = BTM_BLE_SEC_ENCRYPT_NO_MITM;
        p_cb->status = BTA_HH_ERR_AUTH_FAILED;
        bta_hh_clear_service_cache(p_cb);
        BTM_SetEncryption(p_cb->addr, BTA_TRANSPORT_LE, bta_hh_le_encrypt_cback, &sec_flag);
    }
    /* otherwise let it go through */
    else
    {
        bta_hh_sm_execute(p_cb, BTA_HH_ENC_CMPL_EVT, NULL);
    }


}
/*******************************************************************************
**
** Function         bta_hh_gatt_open
**
** Description      process GATT open event.
**
** Parameters:
**
*******************************************************************************/
void bta_hh_gatt_open(tBTA_HH_DEV_CB *p_cb, tBTA_HH_DATA *p_buf)
{
    tBTA_GATTC_OPEN *p_data = &p_buf->le_open;
    UINT8           *p2;
    tHID_STATUS     status = BTA_HH_ERR;

    /* if received invalid callback data , ignore it */
    if (p_cb == NULL || p_data == NULL)
        return;

    p2 = p_data->remote_bda;

    APPL_TRACE_DEBUG("bta_hh_gatt_open BTA_GATTC_OPEN_EVT bda= [%08x%04x] status =%d",
                      ((p2[0])<<24)+((p2[1])<<16)+((p2[2])<<8)+(p2[3]),
                      ((p2[4])<<8)+ p2[5],p_data->status);

    if (p_data->status == BTA_GATT_OK)
    {

        p_cb->in_use    = TRUE;
        p_cb->conn_id   = p_data->conn_id;
        p_cb->hid_handle = BTA_HH_GET_LE_DEV_HDL(p_cb->index);

        bta_hh_cb.le_cb_index[BTA_HH_GET_LE_CB_IDX(p_cb->hid_handle)] = p_cb->index;

#if BTA_HH_DEBUG == TRUE
        APPL_TRACE_DEBUG("hid_handle = %2x conn_id = %04x cb_index = %d", p_cb->hid_handle, p_cb->conn_id, p_cb->index);
#endif

        bta_hh_sm_execute(p_cb, BTA_HH_START_ENC_EVT, NULL);

    }
    else /* open failure */
    {
        bta_hh_sm_execute(p_cb, BTA_HH_SDP_CMPL_EVT, (tBTA_HH_DATA *)&status);
    }

}
/*******************************************************************************
**
** Function         bta_hh_le_close
**
** Description      This function process the GATT close event and post it as a
**                  BTA HH internal event
**
** Parameters:
**
*******************************************************************************/
void bta_hh_le_close(tBTA_GATTC_CLOSE * p_data)
{
    tBTA_HH_DEV_CB *p_dev_cb = bta_hh_le_find_dev_cb_by_bda(p_data->remote_bda);
    tBTA_HH_LE_CLOSE    *p_buf = NULL;
    UINT16  sm_event = BTA_HH_GATT_CLOSE_EVT;

    if (p_dev_cb != NULL &&
        (p_buf = (tBTA_HH_LE_CLOSE *)GKI_getbuf(sizeof(tBTA_HH_LE_CLOSE))) != NULL)
    {
        p_buf->hdr.event            = sm_event;
        p_buf->hdr.layer_specific   = (UINT16)p_dev_cb->hid_handle;
        p_buf->conn_id              = p_data->conn_id;
        p_buf->reason               = p_data->reason;

        p_dev_cb->conn_id           = BTA_GATT_INVALID_CONN_ID;
        p_dev_cb->security_pending  = FALSE;
        bta_sys_sendmsg(p_buf);
    }
}

/*******************************************************************************
**
** Function         bta_hh_le_search_result
**
** Description      This function process the GATT service search result.
**
** Parameters:
**
*******************************************************************************/
void bta_hh_le_search_result(tBTA_GATTC_SRVC_RES *p_srvc_result)
{
    tBTA_HH_DEV_CB *p_dev_cb = bta_hh_le_find_dev_cb_by_conn_id(p_srvc_result->conn_id);

    if (p_dev_cb != NULL)
    {
        switch (p_srvc_result->service_uuid.id.uuid.uu.uuid16)
        {
        case UUID_SERVCLASS_LE_HID:
            if (p_srvc_result->service_uuid.is_primary)
            {
                /* found HID primamry service */
                /* TODO: proceed to find battery and device info */
                if (bta_hh_le_add_hid_srvc_entry(p_dev_cb, p_dev_cb->total_srvc))
                    p_dev_cb->total_srvc ++;
                APPL_TRACE_DEBUG("num of hid service: %d", p_dev_cb->total_srvc);
            }
            break;

        case UUID_SERVCLASS_SCAN_PARAM : /* scan parameter service */
            bta_hh_le_search_scps_chars(p_dev_cb);
            break;
        }

    }

}


/*******************************************************************************
**
** Function         bta_hh_le_gatt_disc_cmpl
**
** Description      Check to see if the remote device is a LE only device
**
** Parameters:
**
*******************************************************************************/
void bta_hh_le_gatt_disc_cmpl(tBTA_HH_DEV_CB *p_cb, tBTA_HH_STATUS status)
{
    APPL_TRACE_DEBUG("bta_hh_le_gatt_disc_cmpl ");

    /* if open sucessful or protocol mode not desired, keep the connection open but inform app */
    if (status == BTA_HH_OK || status == BTA_HH_ERR_PROTO)
    {
        /* assign a special APP ID temp, since device type unknown */
        p_cb->app_id = BTA_HH_APP_ID_LE;

        /* set report notification configuration */
        p_cb->clt_cfg_idx = 0;
        bta_hh_le_write_rpt_clt_cfg(p_cb, BTA_HH_LE_SRVC_DEF);
    }
    else /* error, close the GATT connection */
    {
        /* close GATT connection if it's on */
        bta_hh_le_api_disc_act(p_cb);
    }
}

/*******************************************************************************
**
** Function         bta_hh_le_srvc_expl_srvc
**
** Description      This function discover the next avaible HID service.
**
** Parameters:
**
*******************************************************************************/
void bta_hh_le_srvc_expl_srvc(tBTA_HH_DEV_CB *p_dev_cb)
{
#if BTA_HH_DEBUG == TRUE
    APPL_TRACE_DEBUG("bta_hh_le_srvc_expl_srvc cur_srvc_index = %d in_use = %d",
                    p_dev_cb->cur_srvc_index,
                    p_dev_cb->hid_srvc[p_dev_cb->cur_srvc_index].in_use);
#endif

    if (p_dev_cb->cur_srvc_index < BTA_HH_LE_HID_SRVC_MAX &&
        p_dev_cb->hid_srvc[p_dev_cb->cur_srvc_index].in_use)
    {
        if (!p_dev_cb->hid_srvc[p_dev_cb->cur_srvc_index].expl_incl_srvc)
            /* explore included service first */
            {
                bta_hh_le_search_hid_included(p_dev_cb);
            }
        else
        {
            /* explore characterisc */
            p_dev_cb->hid_srvc[p_dev_cb->cur_srvc_index].cur_expl_char_idx = 0;
            bta_hh_le_search_hid_chars(p_dev_cb);
        }
    }
    else /* all service discvery finished */
    {
        bta_hh_le_gatt_disc_cmpl(p_dev_cb, p_dev_cb->status);
    }
}
/*******************************************************************************
**
** Function         bta_hh_le_srvc_search_cmpl
**
** Description      This function process the GATT service search complete.
**
** Parameters:
**
*******************************************************************************/
void bta_hh_le_srvc_search_cmpl(tBTA_GATTC_SEARCH_CMPL *p_data)
{
    tBTA_HH_DEV_CB *p_dev_cb = bta_hh_le_find_dev_cb_by_conn_id(p_data->conn_id);

    /* service search exception or no HID service is supported on remote */
    if (p_dev_cb == NULL)
        return;

    if(p_data->status != BTA_GATT_OK || p_dev_cb->total_srvc == 0)
    {
        p_dev_cb->status = BTA_HH_ERR_SDP;
        /* close the connection and report service discovery complete with error */
        bta_hh_le_api_disc_act(p_dev_cb);
    }
    /* GATT service discovery sucessfully finished */
    else
    {
        if (p_dev_cb->disc_active  & BTA_HH_LE_DISC_SCPS)
        {
            p_dev_cb->disc_active  &= ~BTA_HH_LE_DISC_SCPS;
            bta_hh_le_open_cmpl(p_dev_cb);
        }
        else /* discover HID service */
        {
        p_dev_cb->cur_srvc_index = 0;
        bta_hh_le_srvc_expl_srvc(p_dev_cb);
    }
}
}

/*******************************************************************************
**
** Function         bta_hh_le_search_hid_included
**
** Description      This function search the included service within the HID service.
**
** Parameters:
**
*******************************************************************************/
static void bta_hh_le_search_hid_included(tBTA_HH_DEV_CB *p_dev_cb)
{
    tBT_UUID    srvc_cond, char_cond;
    tBTA_GATTC_INCL_SVC_ID  inc_srvc_result;
    tBTA_GATT_SRVC_ID srvc_id;
    tBTA_GATTC_CHAR_ID  char_result;
    tBTA_GATT_CHAR_PROP prop = 0;

    bta_hh_le_fill_16bits_srvc_id(TRUE, p_dev_cb->cur_srvc_index, UUID_SERVCLASS_LE_HID, &srvc_id);

    srvc_cond.len = LEN_UUID_16;
    srvc_cond.uu.uuid16 = UUID_SERVCLASS_BATTERY;

    if (BTA_GATTC_GetFirstIncludedService(p_dev_cb->conn_id,
                            &srvc_id,
                            &srvc_cond,
                            &inc_srvc_result) == BTA_GATT_OK)
    {
        /* read include service UUID */

        p_dev_cb->hid_srvc[p_dev_cb->cur_srvc_index].incl_srvc_inst = inc_srvc_result.incl_svc_id.id.inst_id;

        char_cond.len = LEN_UUID_16;
        char_cond.uu.uuid16 = GATT_UUID_BATTERY_LEVEL;

        /* find the battery characteristic */
        if (BTA_GATTC_GetFirstChar( p_dev_cb->conn_id,
                                    &inc_srvc_result.incl_svc_id,
                                    &char_cond,
                                    &char_result,
                                    &prop) == BTA_GATT_OK)
        {
            if (bta_hh_le_find_alloc_report_entry(p_dev_cb,
                                                  char_result.srvc_id.id.inst_id,
                                                  GATT_UUID_BATTERY_LEVEL,
                                                  char_result.char_id.inst_id,
                                                  prop) == NULL)
            {
                APPL_TRACE_ERROR("Add battery report entry failed !!!")
            }

            /* read the battery characteristic */
            BTA_GATTC_ReadCharacteristic(p_dev_cb->conn_id,
                                         &char_result,
                                         BTA_GATT_AUTH_REQ_NONE);

            return;

        }
        else
        {
            APPL_TRACE_ERROR("Remote device does not have battery level");
        }
    }

    p_dev_cb->hid_srvc[p_dev_cb->cur_srvc_index].expl_incl_srvc = TRUE;

    bta_hh_le_srvc_expl_srvc(p_dev_cb);

}
/*******************************************************************************
**
** Function         bta_hh_read_battery_level_cmpl
**
** Description      This function process the battery level read
**
** Parameters:
**
*******************************************************************************/
void bta_hh_read_battery_level_cmpl(UINT8 status, tBTA_HH_DEV_CB *p_dev_cb, tBTA_GATTC_READ *p_data)
{
    UNUSED(status);
    UNUSED(p_data);

    p_dev_cb->hid_srvc[p_dev_cb->cur_srvc_index].expl_incl_srvc = TRUE;
    bta_hh_le_srvc_expl_srvc(p_dev_cb);
}
/*******************************************************************************
**
** Function         bta_hh_le_search_hid_chars
**
** Description      This function discover all characteristics a service and
**                  all descriptors available.
**
** Parameters:
**
*******************************************************************************/
static void bta_hh_le_search_hid_chars(tBTA_HH_DEV_CB *p_dev_cb)
{
    tBT_UUID    char_cond;
    tBTA_GATTC_CHAR_ID  char_result;
    tBTA_GATT_CHAR_PROP prop;
    BOOLEAN     next = TRUE;
    UINT16      char_uuid = 0;
    tBTA_GATT_SRVC_ID srvc_id;

    if (p_dev_cb->hid_srvc[p_dev_cb->cur_srvc_index].cur_expl_char_idx == BTA_HH_LE_DISC_CHAR_NUM ||
        (p_dev_cb->status != BTA_HH_OK && p_dev_cb->status != BTA_HH_ERR_PROTO))
    {
        p_dev_cb->hid_srvc[p_dev_cb->cur_srvc_index].cur_expl_char_idx = 0;
        /* explore next service */
        p_dev_cb->cur_srvc_index ++;
        bta_hh_le_srvc_expl_srvc(p_dev_cb);
        return;
    }

    p_dev_cb->hid_srvc[ p_dev_cb->cur_srvc_index].cur_expl_char_idx ++;
    char_uuid = bta_hh_le_disc_char_uuid[p_dev_cb->hid_srvc[p_dev_cb->cur_srvc_index].cur_expl_char_idx - 1];

    char_cond.len = LEN_UUID_16;
    char_cond.uu.uuid16 = char_uuid;

    bta_hh_le_fill_16bits_srvc_id(TRUE, p_dev_cb->cur_srvc_index, UUID_SERVCLASS_LE_HID, &srvc_id);

#if BTA_HH_DEBUG == TRUE
    APPL_TRACE_DEBUG("bta_hh_le_search_hid_chars: looking for %s(0x%04x)",
                       bta_hh_uuid_to_str(char_uuid), char_uuid);
#endif

    if (BTA_GATTC_GetFirstChar( p_dev_cb->conn_id,
                            &srvc_id,
                            &char_cond,
                            &char_result,
                            &prop) == BTA_GATT_OK)
    {
        switch (char_uuid)
        {
        case GATT_UUID_HID_CONTROL_POINT:
            p_dev_cb->hid_srvc[char_result.srvc_id.id.inst_id].option_char |= BTA_HH_LE_CP_BIT;
            next = TRUE;
            break;
        case GATT_UUID_HID_INFORMATION:
        case GATT_UUID_HID_REPORT_MAP:
            /* read the char value */
            BTA_GATTC_ReadCharacteristic(p_dev_cb->conn_id,
                                        &char_result,
                                        BTA_GATT_AUTH_REQ_NONE);
            next = FALSE;
            break;

        case GATT_UUID_HID_PROTO_MODE:
            p_dev_cb->hid_srvc[char_result.srvc_id.id.inst_id].option_char |= BTA_HH_LE_PROTO_MODE_BIT;
            next = !bta_hh_le_set_protocol_mode(p_dev_cb, p_dev_cb->mode);
            break;

        case GATT_UUID_HID_REPORT:
            bta_hh_le_expl_rpt(p_dev_cb, &char_result, &char_cond, prop);
            next = FALSE;
            break;

        /* found boot mode report types */
        case GATT_UUID_HID_BT_KB_OUTPUT:
        case GATT_UUID_HID_BT_MOUSE_INPUT:
        case GATT_UUID_HID_BT_KB_INPUT:
            bta_hh_le_expl_boot_rpt(p_dev_cb, char_uuid, prop);
            break;
        }
    }
    else
    {
        if (char_uuid == GATT_UUID_HID_PROTO_MODE)
            next = !bta_hh_le_set_protocol_mode(p_dev_cb, p_dev_cb->mode);

    }

    if (next == TRUE)
    {
        bta_hh_le_search_hid_chars(p_dev_cb);
    }
}
/*******************************************************************************
**
** Function         bta_hh_le_save_rpt_map
**
** Description      save the report map into the control block.
**
** Parameters:
**
*******************************************************************************/
void bta_hh_le_save_rpt_map(tBTA_HH_DEV_CB *p_dev_cb, tBTA_GATTC_READ *p_data)
{
    UINT8           *pp ;
    tBTA_HH_LE_HID_SRVC *p_srvc = &p_dev_cb->hid_srvc[p_data->srvc_id.id.inst_id];

    pp = p_data->p_value->unformat.p_value;

    /* save report descriptor */
    if (p_srvc->rpt_map != NULL)
        GKI_freebuf((void*)p_srvc->rpt_map);

    if (p_data->p_value->unformat.len > 0)
        p_srvc->rpt_map = (UINT8 *)GKI_getbuf(p_data->p_value->unformat.len);

    if (p_srvc->rpt_map != NULL)
    {
        STREAM_TO_ARRAY(p_srvc->rpt_map, pp, p_data->p_value->unformat.len);
        p_srvc->descriptor.dl_len = p_data->p_value->unformat.len;
        p_srvc->descriptor.dsc_list = p_dev_cb->hid_srvc[p_data->srvc_id.id.inst_id].rpt_map;
    }

    if (bta_hh_le_read_char_dscrpt(p_dev_cb,
                                   UUID_SERVCLASS_LE_HID,
                               p_data->srvc_id.id.inst_id,
                               GATT_UUID_HID_REPORT_MAP,
                               p_data->char_id.inst_id,
                               GATT_UUID_EXT_RPT_REF_DESCR) != BTA_HH_OK)
    {
        bta_hh_le_search_hid_chars(p_dev_cb);
    }


}
/*******************************************************************************
**
** Function         bta_hh_le_proc_get_rpt_cmpl
**
** Description      Process the Read report complete, send GET_REPORT_EVT to application
**                  with the report data.
**
** Parameters:
**
*******************************************************************************/
void bta_hh_le_proc_get_rpt_cmpl(tBTA_HH_DEV_CB *p_dev_cb, tBTA_GATTC_READ *p_data)
{
    BT_HDR              *p_buf = NULL;
    tBTA_HH_LE_RPT      *p_rpt;
    tBTA_HH_HSDATA      hs_data;
    UINT8               *pp ;

    if (p_dev_cb->w4_evt != BTA_HH_GET_RPT_EVT)
    {
        APPL_TRACE_ERROR("Unexpected READ cmpl, w4_evt = %d", p_dev_cb->w4_evt);
        return;
    }

    hs_data.status  = BTA_HH_ERR;
    hs_data.handle  = p_dev_cb->hid_handle;

    if (p_data->status == BTA_GATT_OK)
    {
        p_rpt = bta_hh_le_find_report_entry(p_dev_cb,
                                            p_data->srvc_id.id.inst_id,//BTA_HH_LE_SRVC_DEF,
                                            p_data->char_id.uuid.uu.uuid16,
                                            p_data->char_id.inst_id);

        if (p_rpt != NULL &&
            p_data->p_value != NULL &&
            (p_buf = (BT_HDR *)GKI_getbuf((UINT16)(sizeof(BT_HDR) +p_data->p_value->unformat.len + 1))) != NULL)
        {
            /* pack data send to app */
            hs_data.status  = BTA_HH_OK;
            p_buf->len = p_data->p_value->unformat.len + 1;
            p_buf->layer_specific = 0;
            p_buf->offset = 0;

            /* attach report ID as the first byte of the report before sending it to USB HID driver */
            pp = (UINT8*)(p_buf + 1);
            UINT8_TO_STREAM(pp, p_rpt->rpt_id);
            memcpy(pp, p_data->p_value->unformat.p_value, p_data->p_value->unformat.len);

            hs_data.rsp_data.p_rpt_data =p_buf;
        }
    }

    p_dev_cb->w4_evt = 0;
    (* bta_hh_cb.p_cback)(BTA_HH_GET_RPT_EVT, (tBTA_HH *)&hs_data);

    utl_freebuf((void **)&p_buf);

}
/*******************************************************************************
**
** Function         bta_hh_le_proc_read_proto_mode
**
** Description      Process the Read protocol mode, send GET_PROTO_EVT to application
**                  with the protocol mode.
**
*******************************************************************************/
void bta_hh_le_proc_read_proto_mode(tBTA_HH_DEV_CB *p_dev_cb, tBTA_GATTC_READ *p_data)
{
    tBTA_HH_HSDATA      hs_data;

    hs_data.status  = BTA_HH_ERR;
    hs_data.handle  = p_dev_cb->hid_handle;
    hs_data.rsp_data.proto_mode = p_dev_cb->mode;

    if (p_data->status == BTA_GATT_OK && p_data->p_value)
    {
        hs_data.status  = BTA_HH_OK;
        /* match up BTE/BTA report/boot mode def*/
        hs_data.rsp_data.proto_mode = *(p_data->p_value->unformat.p_value);
        /* LE repot mode is the opposite value of BR/EDR report mode, flip it here */
        if (hs_data.rsp_data.proto_mode == 0)
            hs_data.rsp_data.proto_mode = BTA_HH_PROTO_BOOT_MODE;
        else
            hs_data.rsp_data.proto_mode = BTA_HH_PROTO_RPT_MODE;

        p_dev_cb->mode = hs_data.rsp_data.proto_mode;
    }
#if BTA_HH_DEBUG
    APPL_TRACE_DEBUG("LE GET_PROTOCOL Mode = [%s]",
                        (hs_data.rsp_data.proto_mode == BTA_HH_PROTO_RPT_MODE)? "Report" : "Boot");
#endif

    p_dev_cb->w4_evt = 0;
    (* bta_hh_cb.p_cback)(BTA_HH_GET_PROTO_EVT, (tBTA_HH *)&hs_data);

}
/*******************************************************************************
**
** Function         bta_hh_w4_le_read_char_cmpl
**
** Description      process the GATT read complete in W4_CONN state.
**
** Parameters:
**
*******************************************************************************/
void bta_hh_w4_le_read_char_cmpl(tBTA_HH_DEV_CB *p_dev_cb, tBTA_HH_DATA *p_buf)
{
    tBTA_GATTC_READ     * p_data = (tBTA_GATTC_READ *)p_buf;
    UINT8               *pp ;

    if (p_data->char_id.uuid.uu.uuid16 == GATT_UUID_BATTERY_LEVEL)
    {
        bta_hh_read_battery_level_cmpl(p_data->status, p_dev_cb, p_data);
    }
    else
    {
        if (p_data->status == BTA_GATT_OK && p_data->p_value)
        {
            pp = p_data->p_value->unformat.p_value;

            switch (p_data->char_id.uuid.uu.uuid16)
            {
           /* save device information */
            case GATT_UUID_HID_INFORMATION:
                STREAM_TO_UINT16(p_dev_cb->dscp_info.version, pp);
                STREAM_TO_UINT8(p_dev_cb->dscp_info.ctry_code, pp);
                STREAM_TO_UINT8(p_dev_cb->dscp_info.flag, pp);
                break;

            case GATT_UUID_HID_REPORT_MAP:
                bta_hh_le_save_rpt_map(p_dev_cb, p_data);
                return;

            default:
#if BTA_HH_DEBUG == TRUE
                APPL_TRACE_ERROR("Unexpected read %s(0x%04x)",
                                bta_hh_uuid_to_str(p_data->char_id.uuid.uu.uuid16),
                                p_data->char_id.uuid.uu.uuid16);
#endif
                break;
            }
        }
        else
        {
#if BTA_HH_DEBUG == TRUE
            APPL_TRACE_ERROR("read uuid %s[0x%04x] error: %d",
                                bta_hh_uuid_to_str(p_data->char_id.uuid.uu.uuid16),
                                p_data->char_id.uuid.uu.uuid16,
                                p_data->status);
#else
            APPL_TRACE_ERROR("read uuid [0x%04x] error: %d", p_data->char_id.uuid.uu.uuid16, p_data->status);
#endif
        }
        bta_hh_le_search_hid_chars(p_dev_cb);
    }

}
/*******************************************************************************
**
** Function         bta_hh_le_read_char_cmpl
**
** Description      a characteristic value is received.
**
** Parameters:
**
*******************************************************************************/
void bta_hh_le_read_char_cmpl (tBTA_HH_DEV_CB *p_dev_cb, tBTA_HH_DATA *p_buf)
{
    tBTA_GATTC_READ * p_data = (tBTA_GATTC_READ *)p_buf;

    switch (p_data->char_id.uuid.uu.uuid16)
    {
    /* GET_REPORT */
    case GATT_UUID_HID_REPORT:
    case GATT_UUID_HID_BT_KB_INPUT:
    case GATT_UUID_HID_BT_KB_OUTPUT:
    case GATT_UUID_HID_BT_MOUSE_INPUT:
    case GATT_UUID_BATTERY_LEVEL: /* read battery level */
        bta_hh_le_proc_get_rpt_cmpl(p_dev_cb, p_data);
        break;

    case GATT_UUID_HID_PROTO_MODE:
        bta_hh_le_proc_read_proto_mode(p_dev_cb, p_data);
        break;

    default:
        APPL_TRACE_ERROR("Unexpected Read UUID: 0x%04x", p_data->char_id.uuid.uu.uuid16);
        break;
    }

}
/*******************************************************************************
**
** Function         bta_hh_le_read_descr_cmpl
**
** Description      read characteristic descriptor is completed in CONN st.
**
** Parameters:
**
*******************************************************************************/
void bta_hh_le_read_descr_cmpl(tBTA_HH_DEV_CB *p_dev_cb, tBTA_HH_DATA *p_buf)
{
    tBTA_HH_LE_RPT  *p_rpt;
    tBTA_GATTC_READ * p_data = (tBTA_GATTC_READ *)p_buf;
    UINT8   *pp;

    /* if a report client configuration */
    if (p_data->descr_type.uuid.uu.uuid16 == GATT_UUID_CHAR_CLIENT_CONFIG)
    {
        if ((p_rpt = bta_hh_le_find_report_entry(p_dev_cb,
                                                 BTA_HH_LE_SRVC_DEF,
                                                 p_data->char_id.uuid.uu.uuid16,
                                                 p_data->char_id.inst_id)) != NULL)
        {
            pp = p_data->p_value->unformat.p_value;
            STREAM_TO_UINT16(p_rpt->client_cfg_value, pp);

            APPL_TRACE_DEBUG("Read Client Configuration: 0x%04x", p_rpt->client_cfg_value);
        }
    }
}

/*******************************************************************************
**
** Function         bta_hh_le_read_battery_level_descr_cmpl
**
** Description      Process report reference descriptor for battery level is completed
**
** Parameters:
**
*******************************************************************************/
void bta_hh_le_read_battery_level_descr_cmpl(tBTA_HH_DEV_CB *p_dev_cb, tBTA_GATTC_READ * p_data)
{
    tBTA_HH_LE_RPT  *p_rpt;
    UINT16 descr_uuid = p_data->descr_type.uuid.uu.uuid16;

    /* read report reference descriptor for battery level is completed */
    if (descr_uuid == GATT_UUID_RPT_REF_DESCR)
    {
        if ((p_rpt = bta_hh_le_find_report_entry(p_dev_cb,
                                            p_data->srvc_id.id.inst_id,
                                            GATT_UUID_BATTERY_LEVEL,
                                            p_data->char_id.inst_id)) == NULL)
        {
            bta_hh_le_search_hid_chars(p_dev_cb);
        }
        else
            bta_hh_le_save_rpt_ref(p_dev_cb, p_rpt, p_data);

    }
}
/*******************************************************************************
**
** Function         bta_hh_w4_le_read_descr_cmpl
**
** Description      read characteristic descriptor is completed in W4_CONN st.
**
** Parameters:
**
*******************************************************************************/
void bta_hh_w4_le_read_descr_cmpl(tBTA_HH_DEV_CB *p_dev_cb, tBTA_HH_DATA *p_buf)
{
    tBTA_HH_LE_RPT  *p_rpt;
    tBTA_GATTC_READ * p_data = (tBTA_GATTC_READ *)p_buf;
    UINT16 char_uuid16;

    if (p_data == NULL)
        return;

    char_uuid16 = p_data->char_id.uuid.uu.uuid16;

#if BTA_HH_DEBUG == TRUE
    APPL_TRACE_DEBUG("bta_hh_w4_le_read_descr_cmpl uuid: %s(0x%04x)",
                        bta_hh_uuid_to_str(p_data->descr_type.uuid.uu.uuid16),
                        p_data->descr_type.uuid.uu.uuid16);
#endif
    switch (char_uuid16)
    {
    case GATT_UUID_HID_REPORT:
        if ((p_rpt = bta_hh_le_find_report_entry(p_dev_cb,
                                            p_data->srvc_id.id.inst_id,
                                            GATT_UUID_HID_REPORT,
                                            p_data->char_id.inst_id)) == NULL)
        {
            bta_hh_le_search_hid_chars(p_dev_cb);
        }
        else
            bta_hh_le_save_rpt_ref(p_dev_cb, p_rpt, p_data);
        break;

    case GATT_UUID_HID_REPORT_MAP:
        bta_hh_le_save_ext_rpt_ref(p_dev_cb, p_data);
        break;

    case GATT_UUID_BATTERY_LEVEL:
        bta_hh_le_read_battery_level_descr_cmpl(p_dev_cb, p_data);
        break;

    default:
        APPL_TRACE_ERROR("unknown descriptor read complete for uuid: 0x%04x", char_uuid16);
        break;
    }
}

/*******************************************************************************
**
** Function         bta_hh_w4_le_write_cmpl
**
** Description      Write charactersitic complete event at W4_CONN st.
**
** Parameters:
**
*******************************************************************************/
void bta_hh_w4_le_write_cmpl(tBTA_HH_DEV_CB *p_dev_cb, tBTA_HH_DATA *p_buf)
{
    tBTA_GATTC_WRITE    *p_data = (tBTA_GATTC_WRITE *)p_buf;

    if (p_data == NULL)
        return;

    if (p_data->char_id.uuid.uu.uuid16 == GATT_UUID_HID_PROTO_MODE)
    {
        p_dev_cb->status = (p_data->status == BTA_GATT_OK) ? BTA_HH_OK : BTA_HH_ERR_PROTO;

        if ((p_dev_cb->disc_active & BTA_HH_LE_DISC_HIDS) != 0)
        {
            bta_hh_le_search_hid_chars(p_dev_cb);
        }
        else
        {
            bta_hh_le_open_cmpl(p_dev_cb);
        }
    }
}
/*******************************************************************************
**
** Function         bta_hh_le_write_cmpl
**
** Description      Write charactersitic complete event at CONN st.
**
** Parameters:
**
*******************************************************************************/
void bta_hh_le_write_cmpl(tBTA_HH_DEV_CB *p_dev_cb, tBTA_HH_DATA *p_buf)
{
    tBTA_GATTC_WRITE    *p_data = (tBTA_GATTC_WRITE *)p_buf;
    tBTA_HH_CBDATA      cback_data ;
    UINT16              cb_evt = p_dev_cb->w4_evt;

    if (p_data == NULL  || cb_evt == 0)
        return;

#if BTA_HH_DEBUG
    APPL_TRACE_DEBUG("bta_hh_le_write_cmpl w4_evt: %d", p_dev_cb->w4_evt);
#endif
    switch (p_data->char_id.uuid.uu.uuid16)
    {
    /* Set protocol finished */
    case GATT_UUID_HID_PROTO_MODE:
        cback_data.handle  = p_dev_cb->hid_handle;
        if (p_data->status == BTA_GATT_OK)
        {
            bta_hh_le_register_input_notif(p_dev_cb, p_data->srvc_id.id.inst_id, p_dev_cb->mode, FALSE);
            cback_data.status = BTA_HH_OK;
        }
        else
            cback_data.status =  BTA_HH_ERR;
        p_dev_cb->w4_evt = 0;
        (* bta_hh_cb.p_cback)(cb_evt, (tBTA_HH *)&cback_data);
        break;

    /* Set Report finished */
    case GATT_UUID_HID_REPORT:
    case GATT_UUID_HID_BT_KB_INPUT:
    case GATT_UUID_HID_BT_MOUSE_INPUT:
    case GATT_UUID_HID_BT_KB_OUTPUT:
        cback_data.handle  = p_dev_cb->hid_handle;
        cback_data.status = (p_data->status == BTA_GATT_OK)? BTA_HH_OK : BTA_HH_ERR;
        p_dev_cb->w4_evt = 0;
        (* bta_hh_cb.p_cback)(cb_evt, (tBTA_HH *)&cback_data);
        break;

    case GATT_UUID_SCAN_INT_WINDOW:
        bta_hh_le_register_scpp_notif(p_dev_cb, p_data->status);
        break;


    default:
        break;
    }

}
/*******************************************************************************
**
** Function         bta_hh_le_write_char_descr_cmpl
**
** Description      Write charactersitic descriptor complete event
**
** Parameters:
**
*******************************************************************************/
void bta_hh_le_write_char_descr_cmpl(tBTA_HH_DEV_CB *p_dev_cb, tBTA_HH_DATA *p_buf)
{
    tBTA_GATTC_WRITE    *p_data = (tBTA_GATTC_WRITE *)p_buf;
    UINT8   srvc_inst_id, hid_inst_id;

    /* only write client configuration possible */
    if (p_data && p_data->descr_type.uuid.uu.uuid16 == GATT_UUID_CHAR_CLIENT_CONFIG)
    {
        srvc_inst_id = p_data->srvc_id.id.inst_id;
        hid_inst_id = srvc_inst_id;
        switch (p_data->char_id.uuid.uu.uuid16)
        {
        case GATT_UUID_BATTERY_LEVEL: /* battery level clt cfg registered */
            hid_inst_id = bta_hh_le_find_service_inst_by_battery_inst_id(p_dev_cb, srvc_inst_id);
            /* fall through */
        case GATT_UUID_HID_BT_KB_INPUT:
        case GATT_UUID_HID_BT_MOUSE_INPUT:
        case GATT_UUID_HID_REPORT:
            if (p_data->status == BTA_GATT_OK)
                p_dev_cb->hid_srvc[hid_inst_id].report[p_dev_cb->clt_cfg_idx ++].client_cfg_value =
                        BTA_GATT_CLT_CONFIG_NOTIFICATION;

            bta_hh_le_write_rpt_clt_cfg(p_dev_cb, hid_inst_id);

            break;

        case GATT_UUID_SCAN_REFRESH:
            bta_hh_le_register_scpp_notif_cmpl(p_dev_cb, p_data->status);
            break;
        default:
            APPL_TRACE_ERROR("Unknown char ID clt cfg: 0x%04x", p_data->char_id.uuid.uu.uuid16);
        }
    }
    else
    {
#if BTA_HH_DEBUG == TRUE
        APPL_TRACE_ERROR("Unexpected write to %s(0x%04x)",
                        bta_hh_uuid_to_str(p_data->descr_type.uuid.uu.uuid16),
                        p_data->descr_type.uuid.uu.uuid16);
#else
        APPL_TRACE_ERROR("Unexpected write to (0x%04x)", p_data->descr_type.uuid.uu.uuid16);
#endif
    }

}
/*******************************************************************************
**
** Function         bta_hh_le_input_rpt_notify
**
** Description      process the notificaton event, most likely for input report.
**
** Parameters:
**
*******************************************************************************/
void bta_hh_le_input_rpt_notify(tBTA_GATTC_NOTIFY *p_data)
{
    tBTA_HH_DEV_CB       *p_dev_cb = bta_hh_le_find_dev_cb_by_conn_id(p_data->conn_id);
    UINT8           app_id;
    UINT8           *p_buf;
    tBTA_HH_LE_RPT  *p_rpt;

    if (p_dev_cb == NULL)
    {
        APPL_TRACE_ERROR("notification received from Unknown device");
        return;
    }

    app_id= p_dev_cb->app_id;

    p_rpt = bta_hh_le_find_report_entry(p_dev_cb,
                                        BTA_HH_LE_SRVC_DEF,
                                        p_data->char_id.char_id.uuid.uu.uuid16,
                                        p_data->char_id.char_id.inst_id);
    if (p_rpt == NULL)
    {
        APPL_TRACE_ERROR("notification received for Unknown Report");
        return;
    }

    if (p_data->char_id.char_id.uuid.uu.uuid16 == GATT_UUID_HID_BT_MOUSE_INPUT)
        app_id = BTA_HH_APP_ID_MI;
    else if (p_data->char_id.char_id.uuid.uu.uuid16 == GATT_UUID_HID_BT_KB_INPUT)
        app_id = BTA_HH_APP_ID_KB;

    APPL_TRACE_DEBUG("Notification received on report ID: %d", p_rpt->rpt_id);

    /* need to append report ID to the head of data */
    if (p_rpt->rpt_id != 0)
    {
        if ((p_buf = (UINT8 *)GKI_getbuf((UINT16)(p_data->len + 1))) == NULL)
        {
            APPL_TRACE_ERROR("No resources to send report data");
            return;
        }

        p_buf[0] = p_rpt->rpt_id;
        memcpy(&p_buf[1], p_data->value, p_data->len);
        ++p_data->len;
    } else {
        p_buf = p_data->value;
    }

    bta_hh_co_data((UINT8)p_dev_cb->hid_handle,
                    p_buf,
                    p_data->len,
                    p_dev_cb->mode,
                    0 , /* no sub class*/
                    p_dev_cb->dscp_info.ctry_code,
                    p_dev_cb->addr,
                    app_id);

    if (p_buf != p_data->value)
        GKI_freebuf(p_buf);
}


/*******************************************************************************
**
** Function         bta_hh_gatt_open_fail
**
** Description      action function to process the open fail
**
** Returns          void
**
*******************************************************************************/
void bta_hh_le_open_fail(tBTA_HH_DEV_CB *p_cb, tBTA_HH_DATA *p_data)
{
    tBTA_HH_CONN            conn_dat ;

    /* open failure in the middle of service discovery, clear all services */
    if (p_cb->disc_active & BTA_HH_LE_DISC_HIDS)
    {
        bta_hh_clear_service_cache(p_cb);
    }

    p_cb->disc_active = BTA_HH_LE_DISC_NONE;
    /* Failure in opening connection or GATT discovery failure */
    conn_dat.handle = p_cb->hid_handle;
    memcpy(conn_dat.bda, p_cb->addr, BD_ADDR_LEN);
    conn_dat.le_hid = TRUE;
    conn_dat.scps_supported = p_cb->scps_supported;

    if (p_cb->status == BTA_HH_OK)
        conn_dat.status = (p_data->le_close.reason == BTA_GATT_CONN_UNKNOWN) ? p_cb->status : BTA_HH_ERR;
    else
        conn_dat.status = p_cb->status;

    /* Report OPEN fail event */
    (*bta_hh_cb.p_cback)(BTA_HH_OPEN_EVT, (tBTA_HH *)&conn_dat);

}
/*******************************************************************************
**
** Function         bta_hh_gatt_close
**
** Description      action function to process the GATT close int he state machine.
**
** Returns          void
**
*******************************************************************************/
void bta_hh_gatt_close(tBTA_HH_DEV_CB *p_cb, tBTA_HH_DATA *p_data)
{
    tBTA_HH_CBDATA          disc_dat = {BTA_HH_OK, 0};

    /* finaliza device driver */
    bta_hh_co_close(p_cb->hid_handle, p_cb->app_id);
    /* update total conn number */
    bta_hh_cb.cnt_num --;

    disc_dat.handle = p_cb->hid_handle;
    disc_dat.status = p_cb->status;

    (*bta_hh_cb.p_cback)(BTA_HH_CLOSE_EVT, (tBTA_HH *)&disc_dat);

    /* if no connection is active and HH disable is signaled, disable service */
    if (bta_hh_cb.cnt_num == 0 && bta_hh_cb.w4_disable)
    {
        bta_hh_disc_cmpl();
    }
    else
    {
#if (BTA_HH_LE_RECONN == TRUE)
    if (p_data->le_close.reason == BTA_GATT_CONN_TIMEOUT)
    {
        bta_hh_le_add_dev_bg_conn(p_cb, FALSE);
    }
#endif
    }

    return;

}
/*******************************************************************************
**
** Function         bta_hh_le_api_disc_act
**
** Description      initaite a Close API to a remote HID device
**
** Returns          void
**
*******************************************************************************/
void bta_hh_le_api_disc_act(tBTA_HH_DEV_CB *p_cb)
{
    if (p_cb->conn_id != BTA_GATT_INVALID_CONN_ID)
        BTA_GATTC_Close(p_cb->conn_id);
}

/*******************************************************************************
**
** Function         bta_hh_le_get_rpt
**
** Description      GET_REPORT on a LE HID Report
**
** Returns          void
**
*******************************************************************************/
void bta_hh_le_get_rpt(tBTA_HH_DEV_CB *p_cb, UINT8 srvc_inst, tBTA_HH_RPT_TYPE r_type, UINT8 rpt_id)
{
    tBTA_HH_LE_RPT  *p_rpt = bta_hh_le_find_rpt_by_idtype(p_cb->hid_srvc[srvc_inst].report, p_cb->mode, r_type, rpt_id);
    tBTA_GATTC_CHAR_ID  char_id;
    UINT16  srvc_uuid = UUID_SERVCLASS_LE_HID;

    if (p_rpt == NULL)
    {
        APPL_TRACE_ERROR("bta_hh_le_get_rpt: no matching report");
        return;
    }
    if (p_rpt->uuid == GATT_UUID_BATTERY_LEVEL)
        srvc_uuid = UUID_SERVCLASS_BATTERY;

    p_cb->w4_evt = BTA_HH_GET_RPT_EVT;

    bta_hh_le_fill_16bits_srvc_id(TRUE, srvc_inst, srvc_uuid, &char_id.srvc_id);
    bta_hh_le_fill_16bits_char_id(p_rpt->inst_id, p_rpt->uuid, &char_id.char_id);

    BTA_GATTC_ReadCharacteristic(p_cb->conn_id,
                                 &char_id,
                                 BTA_GATT_AUTH_REQ_NONE);
}

/*******************************************************************************
**
** Function         bta_hh_le_write_rpt
**
** Description      SET_REPORT/or DATA output on a LE HID Report
**
** Returns          void
**
*******************************************************************************/
void bta_hh_le_write_rpt(tBTA_HH_DEV_CB *p_cb, UINT8 srvc_inst,
                         tBTA_GATTC_WRITE_TYPE   write_type,
                         tBTA_HH_RPT_TYPE r_type,
                         BT_HDR *p_buf, UINT16 w4_evt )
{
    tBTA_HH_LE_RPT  *p_rpt;
    tBTA_GATTC_CHAR_ID  char_id;
    UINT8   *p_value, rpt_id;

    if (p_buf == NULL || p_buf->len == 0)
    {
        APPL_TRACE_ERROR("bta_hh_le_write_rpt: Illegal data");
        return;
    }

    /* strip report ID from the data */
    p_value = (UINT8 *)(p_buf + 1) + p_buf->offset;
    STREAM_TO_UINT8(rpt_id, p_value);
    p_buf->len -= 1;

    p_rpt = bta_hh_le_find_rpt_by_idtype(p_cb->hid_srvc[srvc_inst].report, p_cb->mode, r_type, rpt_id);

    if (p_rpt == NULL)
    {
        APPL_TRACE_ERROR("bta_hh_le_write_rpt: no matching report");
        return;
    }

    APPL_TRACE_ERROR("bta_hh_le_write_rpt: ReportID: 0x%02x Data Len: %d", rpt_id, p_buf->len);

    p_cb->w4_evt = w4_evt;

    bta_hh_le_fill_16bits_srvc_id(TRUE, srvc_inst, UUID_SERVCLASS_LE_HID, &char_id.srvc_id);
    bta_hh_le_fill_16bits_char_id(p_rpt->inst_id, p_rpt->uuid, &char_id.char_id);

    BTA_GATTC_WriteCharValue(p_cb->conn_id,
                             &char_id,
                             write_type, /* default to use write request */
                             p_buf->len,
                             p_value,
                             BTA_GATT_AUTH_REQ_NONE);

}
/*******************************************************************************
**
** Function         bta_hh_le_suspend
**
** Description      send LE suspend or exit suspend mode to remote device.
**
** Returns          void
**
*******************************************************************************/
void bta_hh_le_suspend(tBTA_HH_DEV_CB *p_cb, tBTA_HH_TRANS_CTRL_TYPE ctrl_type)
{
    UINT8 i;
    tBTA_GATTC_CHAR_ID  char_id;

    ctrl_type -= BTA_HH_CTRL_SUSPEND;

    for (i = 0; i < BTA_HH_LE_HID_SRVC_MAX; i ++)
    {
        bta_hh_le_fill_16bits_srvc_id(TRUE, i, UUID_SERVCLASS_LE_HID, &char_id.srvc_id);
        bta_hh_le_fill_16bits_char_id(0, GATT_UUID_HID_CONTROL_POINT, &char_id.char_id);

        BTA_GATTC_WriteCharValue(p_cb->conn_id,
                                 &char_id,
                                 BTA_GATTC_TYPE_WRITE_NO_RSP, /* default to use write request */
                                 1,
                                 &ctrl_type,
                                 BTA_GATT_AUTH_REQ_NONE);
    }
}

/*******************************************************************************
**
** Function         bta_hh_le_write_dev_act
**
** Description      Write LE device action. can be SET/GET/DATA transaction.
**
** Returns          void
**
*******************************************************************************/
void bta_hh_le_write_dev_act(tBTA_HH_DEV_CB *p_cb, tBTA_HH_DATA *p_data)
{
    switch(p_data->api_sndcmd.t_type)
    {
        case HID_TRANS_SET_PROTOCOL:
            p_cb->w4_evt = BTA_HH_SET_PROTO_EVT;
            bta_hh_le_set_protocol_mode(p_cb, p_data->api_sndcmd.param);
            break;

        case HID_TRANS_GET_PROTOCOL:
            bta_hh_le_get_protocol_mode(p_cb);
            break;

        case HID_TRANS_GET_REPORT:
            bta_hh_le_get_rpt(p_cb,
                              BTA_HH_LE_SRVC_DEF,
                              p_data->api_sndcmd.param,
                              p_data->api_sndcmd.rpt_id);
            break;

        case HID_TRANS_SET_REPORT:
            bta_hh_le_write_rpt(p_cb,
                                BTA_HH_LE_SRVC_DEF,
                                BTA_GATTC_TYPE_WRITE,
                                p_data->api_sndcmd.param,
                                p_data->api_sndcmd.p_data,
                                BTA_HH_SET_RPT_EVT);
            break;

        case HID_TRANS_DATA:  /* output report */

            bta_hh_le_write_rpt(p_cb,
                                BTA_HH_LE_SRVC_DEF,
                                BTA_GATTC_TYPE_WRITE_NO_RSP,
                                p_data->api_sndcmd.param,
                                p_data->api_sndcmd.p_data,
                                BTA_HH_DATA_EVT);
            break;

        case HID_TRANS_CONTROL:
            /* no handshake event will be generated */
            /* if VC_UNPLUG is issued, set flag */
            if (p_data->api_sndcmd.param == BTA_HH_CTRL_SUSPEND ||
                p_data->api_sndcmd.param == BTA_HH_CTRL_EXIT_SUSPEND)
            {
                bta_hh_le_suspend(p_cb, p_data->api_sndcmd.param);
            }
            break;

        default:
            APPL_TRACE_ERROR("unsupported trsanction for LE HID device: %d", p_data->api_sndcmd.t_type);
            break;
    }

}
/*******************************************************************************
**
** Function         bta_hh_le_get_dscp_act
**
** Description      Send ReportDescriptor to application for all HID services.
**
** Returns          void
**
*******************************************************************************/
void bta_hh_le_get_dscp_act(tBTA_HH_DEV_CB *p_cb)
{
    UINT8 i;

    for (i = 0 ;i < BTA_HH_LE_HID_SRVC_MAX; i ++)
    {
        if (p_cb->hid_srvc[i].in_use)
        {
            p_cb->dscp_info.descriptor.dl_len = p_cb->hid_srvc[i].descriptor.dl_len;
            p_cb->dscp_info.descriptor.dsc_list = p_cb->hid_srvc[i].descriptor.dsc_list;

            (*bta_hh_cb.p_cback)(BTA_HH_GET_DSCP_EVT, (tBTA_HH *)&p_cb->dscp_info);
        }
        else
            break;
    }
}

/*******************************************************************************
**
** Function         bta_hh_le_add_dev_bg_conn
**
** Description      Remove a LE HID device from back ground connection procedure.
**
** Returns          void
**
*******************************************************************************/
static void bta_hh_le_add_dev_bg_conn(tBTA_HH_DEV_CB *p_cb, BOOLEAN check_bond)
{
    UINT8           sec_flag=0;
    BOOLEAN         to_add = TRUE;

    if (check_bond)
    {
        /* start reconnection if remote is a bonded device */
        /* verify bond */
        BTM_GetSecurityFlagsByTransport(p_cb->addr, &sec_flag, BT_TRANSPORT_LE);

        if ((sec_flag & BTM_SEC_FLAG_LKEY_KNOWN) == 0)
            to_add = FALSE;
    }

    if (/*p_cb->dscp_info.flag & BTA_HH_LE_NORMAL_CONN &&*/
        !p_cb->in_bg_conn && to_add)
    {
        /* add device into BG connection to accept remote initiated connection */
        BTA_GATTC_Open(bta_hh_cb.gatt_if, p_cb->addr, FALSE, BTA_GATT_TRANSPORT_LE);
        p_cb->in_bg_conn = TRUE;

        BTA_DmBleSetBgConnType(BTA_DM_BLE_CONN_AUTO, NULL);
    }
    return;
}

/*******************************************************************************
**
** Function         bta_hh_le_add_device
**
** Description      Add a LE HID device as a known device, and also add the address
**                  into back ground connection WL for incoming connection.
**
** Returns          void
**
*******************************************************************************/
UINT8 bta_hh_le_add_device(tBTA_HH_DEV_CB *p_cb, tBTA_HH_MAINT_DEV *p_dev_info)
{
    p_cb->hid_handle = BTA_HH_GET_LE_DEV_HDL(p_cb->index);
    bta_hh_cb.le_cb_index[BTA_HH_GET_LE_CB_IDX(p_cb->hid_handle)] = p_cb->index;

    /* update DI information */
    bta_hh_update_di_info(p_cb,
                          p_dev_info->dscp_info.vendor_id,
                          p_dev_info->dscp_info.product_id,
                          p_dev_info->dscp_info.version,
                          p_dev_info->dscp_info.flag);

    /* add to BTA device list */
    bta_hh_add_device_to_list(p_cb, p_cb->hid_handle,
                              p_dev_info->attr_mask,
                              &p_dev_info->dscp_info.descriptor,
                              p_dev_info->sub_class,
                              p_dev_info->dscp_info.ssr_max_latency,
                              p_dev_info->dscp_info.ssr_min_tout,
                              p_dev_info->app_id);

    bta_hh_le_add_dev_bg_conn(p_cb, FALSE);

    return p_cb->hid_handle;
}

/*******************************************************************************
**
** Function         bta_hh_le_remove_dev_bg_conn
**
** Description      Remove a LE HID device from back ground connection procedure.
**
** Returns          void
**
*******************************************************************************/
void bta_hh_le_remove_dev_bg_conn(tBTA_HH_DEV_CB *p_dev_cb)
{
    if (p_dev_cb->in_bg_conn)
    {
        p_dev_cb->in_bg_conn = FALSE;

        BTA_GATTC_CancelOpen(bta_hh_cb.gatt_if, p_dev_cb->addr, FALSE);
    }
}
/*******************************************************************************
**
** Function         bta_hh_le_update_scpp
**
** Description      action function to update the scan parameters on remote HID
**                  device
**
** Parameters:
**
*******************************************************************************/
void bta_hh_le_update_scpp(tBTA_HH_DEV_CB *p_dev_cb, tBTA_HH_DATA *p_buf)
{
    tBTA_GATTC_CHAR_ID  char_id;
    UINT8   value[4], *p = value;
    tBTA_HH_CBDATA      cback_data ;

    if (!p_dev_cb->is_le_device ||
        p_dev_cb->mode != BTA_HH_PROTO_RPT_MODE ||
        p_dev_cb->scps_supported == FALSE)
    {
        APPL_TRACE_ERROR("Can not set ScPP scan paramter as boot host, or remote does not support ScPP ");

        cback_data.handle = p_dev_cb->hid_handle;
        cback_data.status = BTA_HH_ERR;
        (* bta_hh_cb.p_cback)(BTA_HH_UPDATE_SCPP_EVT, (tBTA_HH *)&cback_data);

        return;
    }

    p_dev_cb->w4_evt = BTA_HH_UPDATE_SCPP_EVT;

    UINT16_TO_STREAM(p, p_buf->le_scpp_update.scan_int);
    UINT16_TO_STREAM(p, p_buf->le_scpp_update.scan_win);

    bta_hh_le_fill_16bits_srvc_id(TRUE, BTA_HH_SCPP_INST_DEF, UUID_SERVCLASS_SCAN_PARAM, &char_id.srvc_id);
    bta_hh_le_fill_16bits_char_id(BTA_HH_SCPP_INST_DEF, GATT_UUID_SCAN_INT_WINDOW, &char_id.char_id);

    BTA_GATTC_WriteCharValue(p_dev_cb->conn_id,
                             &char_id,
                             BTA_GATTC_TYPE_WRITE_NO_RSP,
                             2,
                             value,
                             BTA_GATT_AUTH_REQ_NONE);

}
/*******************************************************************************
**
** Function         bta_hh_gattc_callback
**
** Description      This is GATT client callback function used in BTA HH.
**
** Parameters:
**
*******************************************************************************/
static void bta_hh_gattc_callback(tBTA_GATTC_EVT event, tBTA_GATTC *p_data)
{
    tBTA_HH_DEV_CB *p_dev_cb;
    UINT16          evt;
#if BTA_HH_DEBUG
    APPL_TRACE_DEBUG("bta_hh_gattc_callback event = %d", event);
#endif
    if (p_data == NULL)
        return;

    switch (event)
    {
        case BTA_GATTC_REG_EVT: /* 0 */
            bta_hh_le_register_cmpl(&p_data->reg_oper);
            break;

        case BTA_GATTC_DEREG_EVT: /* 1 */
            bta_hh_cleanup_disable(p_data->reg_oper.status);
            break;

        case BTA_GATTC_OPEN_EVT: /* 2 */
            p_dev_cb = bta_hh_le_find_dev_cb_by_bda(p_data->open.remote_bda);
            if (p_dev_cb) {
                bta_hh_sm_execute(p_dev_cb, BTA_HH_GATT_OPEN_EVT, (tBTA_HH_DATA *)&p_data->open);
            }
            break;

        case BTA_GATTC_READ_CHAR_EVT: /* 3 */
        case BTA_GATTC_READ_DESCR_EVT: /* 8 */
            p_dev_cb = bta_hh_le_find_dev_cb_by_conn_id(p_data->read.conn_id);
            if (event == BTA_GATTC_READ_CHAR_EVT)
                evt = BTA_HH_GATT_READ_CHAR_CMPL_EVT;
            else
                evt = BTA_HH_GATT_READ_DESCR_CMPL_EVT;

            bta_hh_sm_execute(p_dev_cb, evt, (tBTA_HH_DATA *)&p_data->read);
            break;

        case BTA_GATTC_WRITE_DESCR_EVT: /* 9 */
        case BTA_GATTC_WRITE_CHAR_EVT: /* 4 */
            p_dev_cb = bta_hh_le_find_dev_cb_by_conn_id(p_data->write.conn_id);
            if (event == BTA_GATTC_WRITE_CHAR_EVT)
                evt = BTA_HH_GATT_WRITE_CHAR_CMPL_EVT;
            else
                evt = BTA_HH_GATT_WRITE_DESCR_CMPL_EVT;

            bta_hh_sm_execute(p_dev_cb, evt, (tBTA_HH_DATA *)&p_data->write);
            break;

        case BTA_GATTC_CLOSE_EVT: /* 5 */
            bta_hh_le_close(&p_data->close);
            break;

        case BTA_GATTC_SEARCH_CMPL_EVT: /* 6 */
            bta_hh_le_srvc_search_cmpl(&p_data->search_cmpl);
            break;

        case BTA_GATTC_SEARCH_RES_EVT: /* 7 */
            bta_hh_le_search_result(&p_data->srvc_res);
            break;



        case BTA_GATTC_NOTIF_EVT: /* 10 */
            bta_hh_le_input_rpt_notify(&p_data->notify);
            break;

        case BTA_GATTC_ENC_CMPL_CB_EVT: /* 17 */
            p_dev_cb = bta_hh_le_find_dev_cb_by_bda(p_data->enc_cmpl.remote_bda);
            if (p_dev_cb) {
                bta_hh_sm_execute(p_dev_cb, BTA_HH_GATT_ENC_CMPL_EVT,
                              (tBTA_HH_DATA *)&p_data->enc_cmpl);
            }
            break;

        default:
            break;
    }
}

/*******************************************************************************
**
** Function         bta_hh_le_hid_read_rpt_clt_cfg
**
** Description      a test command to read report descriptor client configuration
**
** Returns          void
**
*******************************************************************************/
void bta_hh_le_hid_read_rpt_clt_cfg(BD_ADDR bd_addr, UINT8 rpt_id)
{
    tBTA_HH_DEV_CB *p_cb = NULL;
    tBTA_HH_LE_RPT *p_rpt ;
    UINT8           index = BTA_HH_IDX_INVALID;

    index = bta_hh_find_cb(bd_addr);
    if ((index = bta_hh_find_cb(bd_addr))== BTA_HH_IDX_INVALID)
    {
        APPL_TRACE_ERROR("unknown device");
        return;
    }

    p_cb = &bta_hh_cb.kdev[index];

    p_rpt = bta_hh_le_find_rpt_by_idtype(p_cb->hid_srvc[BTA_HH_LE_SRVC_DEF].report, p_cb->mode, BTA_HH_RPTT_INPUT, rpt_id);

    if (p_rpt == NULL)
    {
        APPL_TRACE_ERROR("bta_hh_le_write_rpt: no matching report");
        return;
    }

    bta_hh_le_read_char_dscrpt(p_cb,
                               UUID_SERVCLASS_LE_HID,
                               BTA_HH_LE_SRVC_DEF,
                               p_rpt->uuid,
                               p_rpt->inst_id,
                               GATT_UUID_CHAR_CLIENT_CONFIG);



    return;
}
/*******************************************************************************
**
** Function         bta_hh_le_search_scps
**
** Description      discovery scan parameter service if act as report host, otherwise
**                  finish LE connection.
**
** Parameters:
**
*******************************************************************************/
static void bta_hh_le_search_scps(tBTA_HH_DEV_CB *p_cb)
{
    tBT_UUID        pri_srvc;

    if ( p_cb->mode == BTA_HH_PROTO_RPT_MODE)
    {
        p_cb->disc_active  |= BTA_HH_LE_DISC_SCPS;
        /* start  service discovery for Scan Parameter service */
        pri_srvc.len        = LEN_UUID_16;
        pri_srvc.uu.uuid16  = UUID_SERVCLASS_SCAN_PARAM;

        BTA_GATTC_ServiceSearchRequest(p_cb->conn_id, &pri_srvc);
    }
    else
        bta_hh_le_open_cmpl(p_cb);
}
/*******************************************************************************
**
** Function         bta_hh_le_search_scps_chars
**
** Description      find ScPS optional characteristics scan refresh
**
** Parameters:
**
*******************************************************************************/
static void bta_hh_le_search_scps_chars(tBTA_HH_DEV_CB *p_cb)
{
    tBTA_GATT_SRVC_ID   srvc_id;
    tBT_UUID            char_cond;
    tBTA_GATTC_CHAR_ID  char_result;
    tBTA_GATT_CHAR_PROP prop;

    p_cb->scps_supported = TRUE;
    bta_hh_le_fill_16bits_srvc_id(TRUE, 0, UUID_SERVCLASS_SCAN_PARAM, &srvc_id);

    char_cond.len   = LEN_UUID_16;
    char_cond.uu.uuid16 = GATT_UUID_SCAN_REFRESH;

    /* look for scan refresh */
    if (BTA_GATTC_GetFirstChar( p_cb->conn_id,
                                &srvc_id,
                                &char_cond,
                                &char_result,
                                &prop) == BTA_GATT_OK)
    {
        if (prop & BTA_GATT_CHAR_PROP_BIT_NOTIFY)
            p_cb->scps_notify |= BTA_HH_LE_SCPS_NOTIFY_SPT;
        else
            p_cb->scps_notify = BTA_HH_LE_SCPS_NOTIFY_NONE;

    }
}

/*******************************************************************************
**
** Function         bta_hh_le_register_scpp_notif
**
** Description      register scan parameter refresh notitication complete
**
**
** Parameters:
**
*******************************************************************************/
static void bta_hh_le_register_scpp_notif(tBTA_HH_DEV_CB *p_dev_cb, tBTA_GATT_STATUS status)
{
    UINT8               sec_flag=0;
    tBTA_GATTC_CHAR_ID  char_id;

    /* if write scan parameter sucessful */
    /* if bonded and notification is not enabled, configure the client configuration */
    if (status == BTA_GATT_OK &&
        (p_dev_cb->scps_notify & BTA_HH_LE_SCPS_NOTIFY_SPT) != 0 &&
        (p_dev_cb->scps_notify & BTA_HH_LE_SCPS_NOTIFY_ENB) == 0)
    {
        BTM_GetSecurityFlags(p_dev_cb->addr, &sec_flag);
        if ((sec_flag & BTM_SEC_FLAG_LKEY_KNOWN))
        {
            if (bta_hh_le_write_char_clt_cfg (p_dev_cb,
                                              BTA_HH_SCPP_INST_DEF,
                                              UUID_SERVCLASS_SCAN_PARAM,
                                              BTA_HH_SCPP_INST_DEF,
                                              GATT_UUID_SCAN_REFRESH,
                                              BTA_GATT_CLT_CONFIG_NOTIFICATION))
            {
                bta_hh_le_fill_16bits_srvc_id(TRUE, BTA_HH_SCPP_INST_DEF, UUID_SERVCLASS_SCAN_PARAM, &char_id.srvc_id);
                bta_hh_le_fill_16bits_char_id(BTA_HH_SCPP_INST_DEF, GATT_UUID_SCAN_REFRESH, &char_id.char_id);

                BTA_GATTC_RegisterForNotifications(bta_hh_cb.gatt_if,
                                                   p_dev_cb->addr,
                                                   &char_id);
                return;
            }
        }
    }
    bta_hh_le_register_scpp_notif_cmpl(p_dev_cb, status);
}
/*******************************************************************************
**
** Function         bta_hh_le_register_scpp_notif_cmpl
**
** Description      action function to register scan parameter refresh notitication
**
** Parameters:
**
*******************************************************************************/
static void bta_hh_le_register_scpp_notif_cmpl(tBTA_HH_DEV_CB *p_dev_cb, tBTA_GATT_STATUS status)
{
    tBTA_HH_CBDATA      cback_data ;
    UINT16              cb_evt = p_dev_cb->w4_evt;

    if (status == BTA_GATT_OK)
        p_dev_cb->scps_notify = (BTA_HH_LE_SCPS_NOTIFY_ENB | BTA_HH_LE_SCPS_NOTIFY_SPT);

    cback_data.handle  = p_dev_cb->hid_handle;
    cback_data.status = (status == BTA_GATT_OK)? BTA_HH_OK : BTA_HH_ERR;
    p_dev_cb->w4_evt = 0;
    (* bta_hh_cb.p_cback)(cb_evt, (tBTA_HH *)&cback_data);


}
#endif




