hidh_conn.c revision 8f322bfe42a57902e7c45713a5c6215dfbe2494a
15738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project/******************************************************************************
25738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project *
35738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project *  Copyright (C) 2002-2012 Broadcom Corporation
45738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project *
55738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project *  Licensed under the Apache License, Version 2.0 (the "License");
65738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project *  you may not use this file except in compliance with the License.
75738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project *  You may obtain a copy of the License at:
85738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project *
95738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project *  http://www.apache.org/licenses/LICENSE-2.0
105738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project *
115738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project *  Unless required by applicable law or agreed to in writing, software
125738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project *  distributed under the License is distributed on an "AS IS" BASIS,
135738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
145738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project *  See the License for the specific language governing permissions and
155738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project *  limitations under the License.
165738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project *
175738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project ******************************************************************************/
185738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
195738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project/******************************************************************************
205738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project *
215738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project *  this file contains the connection interface functions
225738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project *
235738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project ******************************************************************************/
245738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
255738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project#include <stdlib.h>
265738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project#include <string.h>
275738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project#include <stdio.h>
285738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
295738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
305738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project#include "gki.h"
315738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project#include "bt_types.h"
325738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
335738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project#include "l2cdefs.h"
345738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project#include "l2c_api.h"
355738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
365738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project#include "btu.h"
375738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project#include "btm_api.h"
385738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project#include "btm_int.h"
395738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
405738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project#include "hiddefs.h"
415738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
425738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project#include "hidh_api.h"
435738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project#include "hidh_int.h"
445cd8bff2dd0337cb52bf48f312e3d2d55a8882fbMike J. Chen#include "bt_utils.h"
455738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
465738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Projectstatic UINT8 find_conn_by_cid (UINT16 cid);
475738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Projectstatic void hidh_conn_retry (UINT8 dhandle);
485738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
495738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project/********************************************************************************/
505738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project/*              L O C A L    F U N C T I O N     P R O T O T Y P E S            */
515738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project/********************************************************************************/
525738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Projectstatic void hidh_l2cif_connect_ind (BD_ADDR  bd_addr, UINT16 l2cap_cid,
535738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project                                    UINT16 psm, UINT8 l2cap_id);
545738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Projectstatic void hidh_l2cif_connect_cfm (UINT16 l2cap_cid, UINT16 result);
555738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Projectstatic void hidh_l2cif_config_ind (UINT16 l2cap_cid, tL2CAP_CFG_INFO *p_cfg);
565738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Projectstatic void hidh_l2cif_config_cfm (UINT16 l2cap_cid, tL2CAP_CFG_INFO *p_cfg);
575738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Projectstatic void hidh_l2cif_disconnect_ind (UINT16 l2cap_cid, BOOLEAN ack_needed);
585738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Projectstatic void hidh_l2cif_data_ind (UINT16 l2cap_cid, BT_HDR *p_msg);
595738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Projectstatic void hidh_l2cif_disconnect_cfm (UINT16 l2cap_cid, UINT16 result);
605738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Projectstatic void hidh_l2cif_cong_ind (UINT16 l2cap_cid, BOOLEAN congested);
615738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
625738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Projectstatic const tL2CAP_APPL_INFO hst_reg_info =
635738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project{
645738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    hidh_l2cif_connect_ind,
655738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    hidh_l2cif_connect_cfm,
665738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    NULL,
675738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    hidh_l2cif_config_ind,
685738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    hidh_l2cif_config_cfm,
695738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    hidh_l2cif_disconnect_ind,
705738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    hidh_l2cif_disconnect_cfm,
715738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    NULL,
725738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    hidh_l2cif_data_ind,
735738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    hidh_l2cif_cong_ind,
745738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    NULL                        /* tL2CA_TX_COMPLETE_CB */
755738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project};
765738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
775738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project/*******************************************************************************
785738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
795738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project** Function         hidh_l2cif_reg
805738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
815738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project** Description      This function initializes the SDP unit.
825738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
835738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project** Returns          void
845738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
855738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project*******************************************************************************/
865738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source ProjecttHID_STATUS hidh_conn_reg (void)
875738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project{
885738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    int xx;
895738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
905738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    /* Initialize the L2CAP configuration. We only care about MTU and flush */
915738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    memset(&hh_cb.l2cap_cfg, 0, sizeof(tL2CAP_CFG_INFO));
925738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
935738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    hh_cb.l2cap_cfg.mtu_present          = TRUE;
945738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    hh_cb.l2cap_cfg.mtu                  = HID_HOST_MTU;
955738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    hh_cb.l2cap_cfg.flush_to_present     = TRUE;
965738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    hh_cb.l2cap_cfg.flush_to             = HID_HOST_FLUSH_TO;
975738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
985738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    /* Now, register with L2CAP */
995738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    if (!L2CA_Register (HID_PSM_CONTROL, (tL2CAP_APPL_INFO *) &hst_reg_info))
1005738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    {
1017f7d49370a7527052995c0f1ce355f72b073510dHemant Gupta        HIDH_TRACE_ERROR0 ("HID-Host Control Registration failed");
1025738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        return (HID_ERR_L2CAP_FAILED) ;
1035738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    }
1045738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    if (!L2CA_Register (HID_PSM_INTERRUPT, (tL2CAP_APPL_INFO *) &hst_reg_info))
1055738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    {
1065738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        L2CA_Deregister( HID_PSM_CONTROL ) ;
1077f7d49370a7527052995c0f1ce355f72b073510dHemant Gupta        HIDH_TRACE_ERROR0 ("HID-Host Interrupt Registration failed");
1085738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        return (HID_ERR_L2CAP_FAILED) ;
1095738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    }
1105738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
1115738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    for (xx = 0; xx < HID_HOST_MAX_DEVICES; xx++)
1125738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    {
1135738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        hh_cb.devices[xx].in_use = FALSE ;
1145738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        hh_cb.devices[xx].conn.conn_state = HID_CONN_STATE_UNUSED;
1155738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    }
1165738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
1175738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    return (HID_SUCCESS);
1185738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project}
1195738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
1205738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project/*******************************************************************************
1215738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
1225738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project** Function         hidh_conn_disconnect
1235738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
1245738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project** Description      This function disconnects a connection.
1255738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
1265738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project** Returns          TRUE if disconnect started, FALSE if already disconnected
1275738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
1285738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project*******************************************************************************/
1295738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source ProjecttHID_STATUS hidh_conn_disconnect (UINT8 dhandle)
1305738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project{
1315738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    tHID_CONN *p_hcon = &hh_cb.devices[dhandle].conn;
1325738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
1332e7fa68bfd9723b7ec7b6b0b128d89f31a2e06eeAndre Eisenbach    HIDH_TRACE_EVENT0 ("HID-Host disconnect");
1345738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
1355738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    if ((p_hcon->ctrl_cid != 0) || (p_hcon->intr_cid != 0))
1365738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    {
1375738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        p_hcon->conn_state = HID_CONN_STATE_DISCONNECTING;
1385738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
1391747956ba052b1538c29fe7793403dc4f13ba525Hemant Gupta        /* Set l2cap idle timeout to 0 (so ACL link is disconnected
1401747956ba052b1538c29fe7793403dc4f13ba525Hemant Gupta         * immediately after last channel is closed) */
1411747956ba052b1538c29fe7793403dc4f13ba525Hemant Gupta        L2CA_SetIdleTimeoutByBdAddr(hh_cb.devices[dhandle].addr, 0);
1425738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        /* Disconnect both interrupt and control channels */
1435738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        if (p_hcon->intr_cid)
1445738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            L2CA_DisconnectReq (p_hcon->intr_cid);
145bf51271f145204a0489597ccd9c851daa7ee0ad7Hemant Gupta        else if (p_hcon->ctrl_cid)
1465738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            L2CA_DisconnectReq (p_hcon->ctrl_cid);
1475738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    }
1485738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    else
1495738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    {
1505738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        p_hcon->conn_state = HID_CONN_STATE_UNUSED;
1515738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    }
1525738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
1535738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    return (HID_SUCCESS);
1545738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project}
1555738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
1565738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project/*******************************************************************************
1575738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
1585738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project** Function         hidh_sec_check_complete_term
1595738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
1605738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project** Description      HID security check complete callback function.
1615738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
1625738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project** Returns          Send L2CA_ConnectRsp OK if secutiry check succeed; otherwise
1635738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**                  send security block L2C connection response.
1645738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
1655738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project*******************************************************************************/
1665738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Projectvoid hidh_sec_check_complete_term (BD_ADDR bd_addr, void *p_ref_data, UINT8 res)
1675738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project{
1685738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    tHID_HOST_DEV_CTB *p_dev= (tHID_HOST_DEV_CTB *) p_ref_data;
1695cd8bff2dd0337cb52bf48f312e3d2d55a8882fbMike J. Chen    UNUSED(bd_addr);
1705738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
1715738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    if( res == BTM_SUCCESS && p_dev->conn.conn_state == HID_CONN_STATE_SECURITY )
1725738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    {
1735738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        p_dev->conn.disc_reason = HID_SUCCESS;  /* Authentication passed. Reset disc_reason (from HID_ERR_AUTH_FAILED) */
1745738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
1755738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        p_dev->conn.conn_state = HID_CONN_STATE_CONNECTING_INTR;
1765738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
1775738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        /* Send response to the L2CAP layer. */
1785738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        L2CA_ConnectRsp (p_dev->addr, p_dev->conn.ctrl_id, p_dev->conn.ctrl_cid, L2CAP_CONN_OK, L2CAP_CONN_OK);
1795738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
1805738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        /* Send a Configuration Request. */
1815738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        L2CA_ConfigReq (p_dev->conn.ctrl_cid, &hh_cb.l2cap_cfg);
1825738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
1835738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    }
1845738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    /* security check fail */
1855738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    else if (res != BTM_SUCCESS)
1865738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    {
1875738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        p_dev->conn.disc_reason = HID_ERR_AUTH_FAILED;      /* Save reason for disconnecting */
1885738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        p_dev->conn.conn_state = HID_CONN_STATE_UNUSED;
1895738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        L2CA_ConnectRsp (p_dev->addr, p_dev->conn.ctrl_id, p_dev->conn.ctrl_cid, L2CAP_CONN_SECURITY_BLOCK, L2CAP_CONN_OK);
1905738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    }
1915738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project}
1925738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
1935738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project/*******************************************************************************
1945738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
1955738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project** Function         hidh_l2cif_connect_ind
1965738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
1975738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project** Description      This function handles an inbound connection indication
1985738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**                  from L2CAP. This is the case where we are acting as a
1995738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**                  server.
2005738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
2015738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project** Returns          void
2025738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
2035738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project*******************************************************************************/
2045738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Projectstatic void hidh_l2cif_connect_ind (BD_ADDR  bd_addr, UINT16 l2cap_cid, UINT16 psm, UINT8 l2cap_id)
2055738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project{
2065738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    tHID_CONN    *p_hcon;
2075738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    BOOLEAN      bAccept = TRUE;
2082e7fa68bfd9723b7ec7b6b0b128d89f31a2e06eeAndre Eisenbach    UINT8        i = HID_HOST_MAX_DEVICES;
2095738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    tHID_HOST_DEV_CTB *p_dev;
2105738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
2112e7fa68bfd9723b7ec7b6b0b128d89f31a2e06eeAndre Eisenbach    HIDH_TRACE_EVENT2 ("HID-Host Rcvd L2CAP conn ind, PSM: 0x%04x  CID 0x%x", psm, l2cap_cid);
2125738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
2132e7fa68bfd9723b7ec7b6b0b128d89f31a2e06eeAndre Eisenbach    /* always add incoming connection device into HID database by default */
2142e7fa68bfd9723b7ec7b6b0b128d89f31a2e06eeAndre Eisenbach    if (HID_HostAddDev(bd_addr, HID_SEC_REQUIRED, &i) != HID_SUCCESS)
2155738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    {
2165738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        L2CA_ConnectRsp (bd_addr, l2cap_id, l2cap_cid, L2CAP_CONN_SECURITY_BLOCK, 0);
2175738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        return;
2185738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    }
2195738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
2205738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    p_hcon = &hh_cb.devices[i].conn;
2215738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    p_dev  = &hh_cb.devices[i];
2225738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
2235738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    /* Check we are in the correct state for this */
2245738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    if (psm == HID_PSM_INTERRUPT)
2255738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    {
2265738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        if (p_hcon->ctrl_cid == 0)
2275738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        {
2282e7fa68bfd9723b7ec7b6b0b128d89f31a2e06eeAndre Eisenbach            HIDH_TRACE_WARNING0 ("HID-Host Rcvd INTR L2CAP conn ind, but no CTL channel");
2295738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            bAccept = FALSE;
2305738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        }
2315738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        if (p_hcon->conn_state != HID_CONN_STATE_CONNECTING_INTR)
2325738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        {
2332e7fa68bfd9723b7ec7b6b0b128d89f31a2e06eeAndre Eisenbach            HIDH_TRACE_WARNING1 ("HID-Host Rcvd INTR L2CAP conn ind, wrong state: %d",
2342e7fa68bfd9723b7ec7b6b0b128d89f31a2e06eeAndre Eisenbach                                 p_hcon->conn_state);
2355738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            bAccept = FALSE;
2365738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        }
2375738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    }
2385738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    else /* CTRL channel */
2395738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    {
2405738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project#if defined(HID_HOST_ACPT_NEW_CONN) && (HID_HOST_ACPT_NEW_CONN == TRUE)
2415738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        p_hcon->ctrl_cid = p_hcon->intr_cid = 0;
2425738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        p_hcon->conn_state = HID_CONN_STATE_UNUSED;
2435738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project#else
2445738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        if (p_hcon->conn_state != HID_CONN_STATE_UNUSED)
2455738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        {
2462e7fa68bfd9723b7ec7b6b0b128d89f31a2e06eeAndre Eisenbach            HIDH_TRACE_WARNING1 ("HID-Host - Rcvd CTL L2CAP conn ind, wrong state: %d",
2472e7fa68bfd9723b7ec7b6b0b128d89f31a2e06eeAndre Eisenbach                                 p_hcon->conn_state);
2485738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            bAccept = FALSE;
2495738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        }
2505738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project#endif
2515738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    }
2525738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
2535738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    if (!bAccept)
2545738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    {
2555738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        L2CA_ConnectRsp (bd_addr, l2cap_id, l2cap_cid, L2CAP_CONN_NO_RESOURCES, 0);
2565738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        return;
2575738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    }
2585738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
2595738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    if (psm == HID_PSM_CONTROL)
2605738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    {
2615738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        p_hcon->conn_flags = 0;
2625738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        p_hcon->ctrl_cid   = l2cap_cid;
2635738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        p_hcon->ctrl_id    = l2cap_id;
2645738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        p_hcon->disc_reason = HID_L2CAP_CONN_FAIL;  /* In case disconnection occurs before security is completed, then set CLOSE_EVT reason code to 'connection failure' */
2655738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
2665738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        p_hcon->conn_state = HID_CONN_STATE_SECURITY;
2675738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        if(btm_sec_mx_access_request (p_dev->addr, HID_PSM_CONTROL,
2685738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            FALSE, BTM_SEC_PROTO_HID,
2695738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            (p_dev->attr_mask & HID_SEC_REQUIRED) ? HID_SEC_CHN : HID_NOSEC_CHN,
2705738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            &hidh_sec_check_complete_term, p_dev) == BTM_CMD_STARTED)
2715738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        {
2725738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            L2CA_ConnectRsp (bd_addr, l2cap_id, l2cap_cid, L2CAP_CONN_PENDING, L2CAP_CONN_OK);
2735738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        }
2745738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
2755738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        return;
2765738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    }
2775738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
2785738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    /* Transition to the next appropriate state, configuration */
2795738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    p_hcon->conn_state = HID_CONN_STATE_CONFIG;
2805738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    p_hcon->intr_cid   = l2cap_cid;
2815738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
2825738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    /* Send response to the L2CAP layer. */
2835738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    L2CA_ConnectRsp (bd_addr, l2cap_id, l2cap_cid, L2CAP_CONN_OK, L2CAP_CONN_OK);
2845738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
2855738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    /* Send a Configuration Request. */
2865738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    L2CA_ConfigReq (l2cap_cid, &hh_cb.l2cap_cfg);
2875738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
2882e7fa68bfd9723b7ec7b6b0b128d89f31a2e06eeAndre Eisenbach    HIDH_TRACE_EVENT2 ("HID-Host Rcvd L2CAP conn ind, sent config req, PSM: 0x%04x  CID 0x%x",
2892e7fa68bfd9723b7ec7b6b0b128d89f31a2e06eeAndre Eisenbach                       psm, l2cap_cid);
2905738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project}
2915738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
2925738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project/*******************************************************************************
2935738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
2945738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project** Function         hidh_proc_repage_timeout
2955738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
2965738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project** Description      This function handles timeout (to page device).
2975738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
2985738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project** Returns          void
2995738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
3005738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project*******************************************************************************/
3015738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Projectvoid hidh_proc_repage_timeout (TIMER_LIST_ENT *p_tle)
3025738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project{
3035738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    hidh_conn_initiate( (UINT8) p_tle->param ) ;
3045738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    hh_cb.devices[p_tle->param].conn_tries++;
3052e7fa68bfd9723b7ec7b6b0b128d89f31a2e06eeAndre Eisenbach    hh_cb.callback( (UINT8) p_tle->param, hh_cb.devices[p_tle->param].addr,
3062e7fa68bfd9723b7ec7b6b0b128d89f31a2e06eeAndre Eisenbach                    HID_HDEV_EVT_RETRYING, hh_cb.devices[p_tle->param].conn_tries, NULL ) ;
3075738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project}
3085738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
3095738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project/*******************************************************************************
3105738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
3115738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project** Function         hidh_sec_check_complete_orig
3125738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
3135738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project** Description      This function checks to see if security procedures are being
3145738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**                  carried out or not..
3155738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
3165738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project** Returns          void
3175738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
3185738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project*******************************************************************************/
3195738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Projectvoid hidh_sec_check_complete_orig (BD_ADDR bd_addr, void *p_ref_data, UINT8 res)
3205738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project{
3215738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    tHID_HOST_DEV_CTB *p_dev = (tHID_HOST_DEV_CTB *) p_ref_data;
3225738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    UINT8 dhandle;
3235738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project#if (HID_HOST_MAX_CONN_RETRY > 0)
3245738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    UINT32 cb_res = HID_ERR_AUTH_FAILED;
3255738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project#endif
3265738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    UINT32 reason;
3275cd8bff2dd0337cb52bf48f312e3d2d55a8882fbMike J. Chen    UNUSED(bd_addr);
3285738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
329ead3cde4bac0c3e32cd31f149093f004eef8ceebGanesh Ganapathi Batta    dhandle = ((UINT32)p_dev - (UINT32)&(hh_cb.devices[0]))/ sizeof(tHID_HOST_DEV_CTB);
3305738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    if( res == BTM_SUCCESS && p_dev->conn.conn_state == HID_CONN_STATE_SECURITY )
3315738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    {
3322e7fa68bfd9723b7ec7b6b0b128d89f31a2e06eeAndre Eisenbach        HIDH_TRACE_EVENT0 ("HID-Host Originator security pass.");
3335738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        p_dev->conn.disc_reason = HID_SUCCESS;  /* Authentication passed. Reset disc_reason (from HID_ERR_AUTH_FAILED) */
3345738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
3357f7d49370a7527052995c0f1ce355f72b073510dHemant Gupta        /* Transition to the next appropriate state, configuration */
3367f7d49370a7527052995c0f1ce355f72b073510dHemant Gupta        p_dev->conn.conn_state = HID_CONN_STATE_CONFIG;
3377f7d49370a7527052995c0f1ce355f72b073510dHemant Gupta        L2CA_ConfigReq (p_dev->conn.ctrl_cid, &hh_cb.l2cap_cfg);
3387f7d49370a7527052995c0f1ce355f72b073510dHemant Gupta        HIDH_TRACE_EVENT1 ("HID-Host Got Control conn cnf, sent cfg req, CID: 0x%x", p_dev->conn.ctrl_cid);
3397f7d49370a7527052995c0f1ce355f72b073510dHemant Gupta
3405738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    }
3415738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
3425738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    if( res != BTM_SUCCESS && p_dev->conn.conn_state == HID_CONN_STATE_SECURITY )
3435738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    {
3445738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project#if (HID_HOST_MAX_CONN_RETRY > 0)
3455738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        if( res == BTM_DEVICE_TIMEOUT )
3465738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        {
3475738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            if( p_dev->conn_tries <= HID_HOST_MAX_CONN_RETRY )
3485738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            {
3495738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project                hidh_conn_retry (dhandle);
3505738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project                return;
3515738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            }
3525738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            else
3535738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project                cb_res = HID_L2CAP_CONN_FAIL | HCI_ERR_PAGE_TIMEOUT ;
3545738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        }
3555738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project#endif
3565738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        p_dev->conn.disc_reason = HID_ERR_AUTH_FAILED;      /* Save reason for disconnecting */
3575738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        hidh_conn_disconnect(dhandle);
3585738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    }
3595738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
3605738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project}
3615738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
3625738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project/*******************************************************************************
3635738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
3645738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project** Function         hidh_l2cif_connect_cfm
3655738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
3665738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project** Description      This function handles the connect confirm events
3675738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**                  from L2CAP. This is the case when we are acting as a
3685738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**                  client and have sent a connect request.
3695738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
3705738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project** Returns          void
3715738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
3725738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project*******************************************************************************/
3735738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Projectstatic void hidh_l2cif_connect_cfm (UINT16 l2cap_cid, UINT16 result)
3745738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project{
3755738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    UINT8 dhandle;
3765738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    tHID_CONN    *p_hcon = NULL;
3775738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    UINT32  reason;
3785738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    tHID_HOST_DEV_CTB *p_dev = NULL;
3795738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
3805738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    /* Find CCB based on CID, and verify we are in a state to accept this message */
3815738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    if( (dhandle = find_conn_by_cid(l2cap_cid)) < HID_HOST_MAX_DEVICES )
3825738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    {
3835738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        p_dev = &hh_cb.devices[dhandle];
3845738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        p_hcon = &hh_cb.devices[dhandle].conn;
3855738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    }
3865738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
3875738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    if ((p_hcon == NULL)
3885738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project     || (!(p_hcon->conn_flags & HID_CONN_FLAGS_IS_ORIG))
3895738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project     || ((l2cap_cid == p_hcon->ctrl_cid) && (p_hcon->conn_state != HID_CONN_STATE_CONNECTING_CTRL))
390742d9fa575cd1ea12c7d4413f1bec62863b07cabHemant Gupta     || ((l2cap_cid == p_hcon->intr_cid) && (p_hcon->conn_state != HID_CONN_STATE_CONNECTING_INTR)
391742d9fa575cd1ea12c7d4413f1bec62863b07cabHemant Gupta     && (p_hcon->conn_state != HID_CONN_STATE_DISCONNECTING)))
3925738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    {
3932e7fa68bfd9723b7ec7b6b0b128d89f31a2e06eeAndre Eisenbach        HIDH_TRACE_WARNING1 ("HID-Host Rcvd unexpected conn cnf, CID 0x%x ", l2cap_cid);
3945738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        return;
3955738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    }
3965738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
3975738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    if (result != L2CAP_CONN_OK)
3985738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    {
3995738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        if (l2cap_cid == p_hcon->ctrl_cid)
4005738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            p_hcon->ctrl_cid = 0;
4015738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        else
4025738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            p_hcon->intr_cid = 0;
4035738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
4045738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        hidh_conn_disconnect(dhandle);
4055738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
4065738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project#if (HID_HOST_MAX_CONN_RETRY > 0)
4075738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        if( (hh_cb.devices[dhandle].conn_tries <= HID_HOST_MAX_CONN_RETRY) &&
4085738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            (result == HCI_ERR_CONNECTION_TOUT || result == HCI_ERR_UNSPECIFIED ||
4095738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project             result == HCI_ERR_PAGE_TIMEOUT) )
4105738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        {
4115738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            hidh_conn_retry(dhandle);
4125738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        }
4135738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        else
4145738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project#endif
4155738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        {
4165738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            reason = HID_L2CAP_CONN_FAIL | (UINT32) result ;
4172e7fa68bfd9723b7ec7b6b0b128d89f31a2e06eeAndre Eisenbach            hh_cb.callback( dhandle, hh_cb.devices[dhandle].addr, HID_HDEV_EVT_CLOSE, reason, NULL ) ;
4185738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        }
4195738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        return;
4205738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    }
4215738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    /* receive Control Channel connect confirmation */
4225738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    if (l2cap_cid == p_hcon->ctrl_cid)
4235738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    {
4245738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        /* check security requirement */
4255738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        p_hcon->conn_state = HID_CONN_STATE_SECURITY;
4265738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        p_hcon->disc_reason = HID_L2CAP_CONN_FAIL;  /* In case disconnection occurs before security is completed, then set CLOSE_EVT reason code to "connection failure" */
4275738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
4285738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        btm_sec_mx_access_request (p_dev->addr, HID_PSM_CONTROL,
4295738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            TRUE, BTM_SEC_PROTO_HID,
4305738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            (p_dev->attr_mask & HID_SEC_REQUIRED) ? HID_SEC_CHN : HID_NOSEC_CHN,
4315738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            &hidh_sec_check_complete_orig, p_dev);
4325738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    }
4335738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    else
4345738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    {
4355738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        p_hcon->conn_state = HID_CONN_STATE_CONFIG;
4367f7d49370a7527052995c0f1ce355f72b073510dHemant Gupta        /* Send a Configuration Request. */
4377f7d49370a7527052995c0f1ce355f72b073510dHemant Gupta        L2CA_ConfigReq (l2cap_cid, &hh_cb.l2cap_cfg);
4387f7d49370a7527052995c0f1ce355f72b073510dHemant Gupta        HIDH_TRACE_EVENT1 ("HID-Host got Interrupt conn cnf, sent cfg req, CID: 0x%x", l2cap_cid);
4395738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    }
4405738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
4415738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    return;
4425738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project}
4435738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
4445738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project/*******************************************************************************
4455738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
4465738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project** Function         hidh_l2cif_config_ind
4475738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
4485738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project** Description      This function processes the L2CAP configuration indication
4495738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**                  event.
4505738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
4515738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project** Returns          void
4525738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
4535738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project*******************************************************************************/
4545738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Projectstatic void hidh_l2cif_config_ind (UINT16 l2cap_cid, tL2CAP_CFG_INFO *p_cfg)
4555738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project{
4565738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    UINT8 dhandle;
4575738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    tHID_CONN    *p_hcon = NULL;
4585738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    tHID_HOST_DEV_CTB *p_dev;
4597f7d49370a7527052995c0f1ce355f72b073510dHemant Gupta    UINT32  reason;
4605738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
4615738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    /* Find CCB based on CID */
4625738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    if( (dhandle = find_conn_by_cid(l2cap_cid)) < HID_HOST_MAX_DEVICES )
4635738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    {
4645738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        p_dev = &hh_cb.devices[dhandle];
4655738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        p_hcon = &hh_cb.devices[dhandle].conn;
4665738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    }
4675738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
4685738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    if (p_hcon == NULL)
4695738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    {
4702e7fa68bfd9723b7ec7b6b0b128d89f31a2e06eeAndre Eisenbach        HIDH_TRACE_WARNING1 ("HID-Host Rcvd L2CAP cfg ind, unknown CID: 0x%x", l2cap_cid);
4715738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        return;
4725738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    }
4735738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
4742e7fa68bfd9723b7ec7b6b0b128d89f31a2e06eeAndre Eisenbach    HIDH_TRACE_EVENT1 ("HID-Host Rcvd cfg ind, sent cfg cfm, CID: 0x%x", l2cap_cid);
4755738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
4765738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    /* Remember the remote MTU size */
4775738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    if ((!p_cfg->mtu_present) || (p_cfg->mtu > HID_HOST_MTU))
4785738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        p_hcon->rem_mtu_size = HID_HOST_MTU;
4795738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    else
4805738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        p_hcon->rem_mtu_size = p_cfg->mtu;
4815738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
4825738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    /* For now, always accept configuration from the other side */
4835738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    p_cfg->flush_to_present = FALSE;
4845738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    p_cfg->mtu_present      = FALSE;
4855738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    p_cfg->result           = L2CAP_CFG_OK;
4865738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
4875738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    L2CA_ConfigRsp (l2cap_cid, p_cfg);
4885738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
4895738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    if (l2cap_cid == p_hcon->ctrl_cid)
4907f7d49370a7527052995c0f1ce355f72b073510dHemant Gupta    {
4915738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        p_hcon->conn_flags |= HID_CONN_FLAGS_HIS_CTRL_CFG_DONE;
4927f7d49370a7527052995c0f1ce355f72b073510dHemant Gupta        if ((p_hcon->conn_flags & HID_CONN_FLAGS_IS_ORIG) &&
4937f7d49370a7527052995c0f1ce355f72b073510dHemant Gupta           (p_hcon->conn_flags & HID_CONN_FLAGS_MY_CTRL_CFG_DONE))
4947f7d49370a7527052995c0f1ce355f72b073510dHemant Gupta        {
4957f7d49370a7527052995c0f1ce355f72b073510dHemant Gupta            /* Connect interrupt channel */
4967f7d49370a7527052995c0f1ce355f72b073510dHemant Gupta            p_hcon->disc_reason = HID_L2CAP_CONN_FAIL;	/* Reset initial reason for CLOSE_EVT: Connection Attempt was made but failed */
4977f7d49370a7527052995c0f1ce355f72b073510dHemant Gupta            if ((p_hcon->intr_cid = L2CA_ConnectReq (HID_PSM_INTERRUPT, hh_cb.devices[dhandle].addr)) == 0)
4987f7d49370a7527052995c0f1ce355f72b073510dHemant Gupta            {
4997f7d49370a7527052995c0f1ce355f72b073510dHemant Gupta                HIDH_TRACE_WARNING0 ("HID-Host INTR Originate failed");
5007f7d49370a7527052995c0f1ce355f72b073510dHemant Gupta                reason = HID_L2CAP_REQ_FAIL ;
5017f7d49370a7527052995c0f1ce355f72b073510dHemant Gupta                p_hcon->conn_state = HID_CONN_STATE_UNUSED;
5027f7d49370a7527052995c0f1ce355f72b073510dHemant Gupta                hidh_conn_disconnect (dhandle);
5037f7d49370a7527052995c0f1ce355f72b073510dHemant Gupta                hh_cb.callback( dhandle, hh_cb.devices[dhandle].addr, HID_HDEV_EVT_CLOSE, reason, NULL ) ;
5047f7d49370a7527052995c0f1ce355f72b073510dHemant Gupta                return;
5057f7d49370a7527052995c0f1ce355f72b073510dHemant Gupta            }
5067f7d49370a7527052995c0f1ce355f72b073510dHemant Gupta            else
5077f7d49370a7527052995c0f1ce355f72b073510dHemant Gupta            {
5087f7d49370a7527052995c0f1ce355f72b073510dHemant Gupta                /* Transition to the next appropriate state, waiting for connection confirm on interrupt channel. */
5097f7d49370a7527052995c0f1ce355f72b073510dHemant Gupta                p_hcon->conn_state = HID_CONN_STATE_CONNECTING_INTR;
5107f7d49370a7527052995c0f1ce355f72b073510dHemant Gupta            }
5117f7d49370a7527052995c0f1ce355f72b073510dHemant Gupta        }
5127f7d49370a7527052995c0f1ce355f72b073510dHemant Gupta    }
5135738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    else
5145738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        p_hcon->conn_flags |= HID_CONN_FLAGS_HIS_INTR_CFG_DONE;
5155738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
5165738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    /* If all configuration is complete, change state and tell management we are up */
5175738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    if (((p_hcon->conn_flags & HID_CONN_FLAGS_ALL_CONFIGURED) == HID_CONN_FLAGS_ALL_CONFIGURED)
5185738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project     && (p_hcon->conn_state == HID_CONN_STATE_CONFIG))
5195738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    {
5205738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        p_hcon->conn_state = HID_CONN_STATE_CONNECTED;
5218f322bfe42a57902e7c45713a5c6215dfbe2494aHemant Gupta        /* Reset disconnect reason to success, as connection successful */
5228f322bfe42a57902e7c45713a5c6215dfbe2494aHemant Gupta        p_hcon->disc_reason = HID_SUCCESS;
5235738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
5245738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        hh_cb.devices[dhandle].state = HID_DEV_CONNECTED;
5252e7fa68bfd9723b7ec7b6b0b128d89f31a2e06eeAndre Eisenbach        hh_cb.callback( dhandle,  hh_cb.devices[dhandle].addr, HID_HDEV_EVT_OPEN, 0, NULL ) ;
5265738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    }
5275738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project}
5285738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
5295738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
5305738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project/*******************************************************************************
5315738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
5325738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project** Function         hidh_l2cif_config_cfm
5335738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
5345738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project** Description      This function processes the L2CAP configuration confirmation
5355738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**                  event.
5365738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
5375738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project** Returns          void
5385738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
5395738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project*******************************************************************************/
5405738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Projectstatic void hidh_l2cif_config_cfm (UINT16 l2cap_cid, tL2CAP_CFG_INFO *p_cfg)
5415738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project{
5425738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    UINT8 dhandle;
5435738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    tHID_CONN    *p_hcon = NULL;
5445738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    UINT32  reason;
5455738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
5462e7fa68bfd9723b7ec7b6b0b128d89f31a2e06eeAndre Eisenbach    HIDH_TRACE_EVENT2 ("HID-Host Rcvd cfg cfm, CID: 0x%x  Result: %d", l2cap_cid, p_cfg->result);
5475738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
5485738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    /* Find CCB based on CID */
5495738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    if( (dhandle = find_conn_by_cid(l2cap_cid)) < HID_HOST_MAX_DEVICES )
5505738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        p_hcon = &hh_cb.devices[dhandle].conn;
5515738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
5525738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    if (p_hcon == NULL)
5535738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    {
5542e7fa68bfd9723b7ec7b6b0b128d89f31a2e06eeAndre Eisenbach        HIDH_TRACE_WARNING1 ("HID-Host Rcvd L2CAP cfg ind, unknown CID: 0x%x", l2cap_cid);
5555738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        return;
5565738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    }
5575738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
5585738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    /* If configuration failed, disconnect the channel(s) */
5595738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    if (p_cfg->result != L2CAP_CFG_OK)
5605738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    {
5615738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        hidh_conn_disconnect (dhandle);
5625738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        reason = HID_L2CAP_CFG_FAIL | (UINT32) p_cfg->result ;
5632e7fa68bfd9723b7ec7b6b0b128d89f31a2e06eeAndre Eisenbach        hh_cb.callback( dhandle, hh_cb.devices[dhandle].addr, HID_HDEV_EVT_CLOSE, reason, NULL ) ;
5645738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        return;
5655738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    }
5665738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
5675738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    if (l2cap_cid == p_hcon->ctrl_cid)
5687f7d49370a7527052995c0f1ce355f72b073510dHemant Gupta    {
5695738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        p_hcon->conn_flags |= HID_CONN_FLAGS_MY_CTRL_CFG_DONE;
5707f7d49370a7527052995c0f1ce355f72b073510dHemant Gupta        if ((p_hcon->conn_flags & HID_CONN_FLAGS_IS_ORIG) &&
5717f7d49370a7527052995c0f1ce355f72b073510dHemant Gupta           (p_hcon->conn_flags & HID_CONN_FLAGS_HIS_CTRL_CFG_DONE))
5727f7d49370a7527052995c0f1ce355f72b073510dHemant Gupta        {
5737f7d49370a7527052995c0f1ce355f72b073510dHemant Gupta            /* Connect interrupt channel */
5747f7d49370a7527052995c0f1ce355f72b073510dHemant Gupta            p_hcon->disc_reason = HID_L2CAP_CONN_FAIL;  /* Reset initial reason for CLOSE_EVT: Connection Attempt was made but failed */
5757f7d49370a7527052995c0f1ce355f72b073510dHemant Gupta            if ((p_hcon->intr_cid = L2CA_ConnectReq (HID_PSM_INTERRUPT, hh_cb.devices[dhandle].addr)) == 0)
5767f7d49370a7527052995c0f1ce355f72b073510dHemant Gupta            {
5777f7d49370a7527052995c0f1ce355f72b073510dHemant Gupta                HIDH_TRACE_WARNING0 ("HID-Host INTR Originate failed");
5787f7d49370a7527052995c0f1ce355f72b073510dHemant Gupta                reason = HID_L2CAP_REQ_FAIL ;
5797f7d49370a7527052995c0f1ce355f72b073510dHemant Gupta                p_hcon->conn_state = HID_CONN_STATE_UNUSED;
5807f7d49370a7527052995c0f1ce355f72b073510dHemant Gupta                hidh_conn_disconnect (dhandle);
5817f7d49370a7527052995c0f1ce355f72b073510dHemant Gupta                hh_cb.callback( dhandle, hh_cb.devices[dhandle].addr, HID_HDEV_EVT_CLOSE, reason, NULL ) ;
5827f7d49370a7527052995c0f1ce355f72b073510dHemant Gupta                return;
5837f7d49370a7527052995c0f1ce355f72b073510dHemant Gupta            }
5847f7d49370a7527052995c0f1ce355f72b073510dHemant Gupta            else
5857f7d49370a7527052995c0f1ce355f72b073510dHemant Gupta            {
5867f7d49370a7527052995c0f1ce355f72b073510dHemant Gupta                /* Transition to the next appropriate state, waiting for connection confirm on interrupt channel. */
5877f7d49370a7527052995c0f1ce355f72b073510dHemant Gupta                p_hcon->conn_state = HID_CONN_STATE_CONNECTING_INTR;
5887f7d49370a7527052995c0f1ce355f72b073510dHemant Gupta            }
5897f7d49370a7527052995c0f1ce355f72b073510dHemant Gupta        }
5907f7d49370a7527052995c0f1ce355f72b073510dHemant Gupta    }
5915738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    else
5925738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        p_hcon->conn_flags |= HID_CONN_FLAGS_MY_INTR_CFG_DONE;
5935738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
5945738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    /* If all configuration is complete, change state and tell management we are up */
5955738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    if (((p_hcon->conn_flags & HID_CONN_FLAGS_ALL_CONFIGURED) == HID_CONN_FLAGS_ALL_CONFIGURED)
5965738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project     && (p_hcon->conn_state == HID_CONN_STATE_CONFIG))
5975738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    {
5985738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        p_hcon->conn_state = HID_CONN_STATE_CONNECTED;
5998f322bfe42a57902e7c45713a5c6215dfbe2494aHemant Gupta        /* Reset disconnect reason to success, as connection successful */
6008f322bfe42a57902e7c45713a5c6215dfbe2494aHemant Gupta        p_hcon->disc_reason = HID_SUCCESS;
6015738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
6025738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        hh_cb.devices[dhandle].state = HID_DEV_CONNECTED;
6032e7fa68bfd9723b7ec7b6b0b128d89f31a2e06eeAndre Eisenbach        hh_cb.callback( dhandle, hh_cb.devices[dhandle].addr, HID_HDEV_EVT_OPEN, 0, NULL ) ;
6045738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    }
6055738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project}
6065738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
6075738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
6085738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project/*******************************************************************************
6095738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
6105738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project** Function         hidh_l2cif_disconnect_ind
6115738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
6125738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project** Description      This function handles a disconnect event from L2CAP. If
6135738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**                  requested to, we ack the disconnect before dropping the CCB
6145738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
6155738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project** Returns          void
6165738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
6175738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project*******************************************************************************/
6185738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Projectstatic void hidh_l2cif_disconnect_ind (UINT16 l2cap_cid, BOOLEAN ack_needed)
6195738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project{
6205738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    UINT8 dhandle;
6215738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    tHID_CONN    *p_hcon = NULL;
6225738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    UINT16 disc_res = HCI_SUCCESS;
6235738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    UINT16 hid_close_evt_reason;
6245738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
6255738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    /* Find CCB based on CID */
6265738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    if( (dhandle = find_conn_by_cid(l2cap_cid)) < HID_HOST_MAX_DEVICES )
6275738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        p_hcon = &hh_cb.devices[dhandle].conn;
6285738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
6295738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    if (p_hcon == NULL)
6305738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    {
6312e7fa68bfd9723b7ec7b6b0b128d89f31a2e06eeAndre Eisenbach        HIDH_TRACE_WARNING1 ("HID-Host Rcvd L2CAP disc, unknown CID: 0x%x", l2cap_cid);
6325738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        return;
6335738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    }
6345738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
6355738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    if (ack_needed)
6365738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        L2CA_DisconnectRsp (l2cap_cid);
6375738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
6382e7fa68bfd9723b7ec7b6b0b128d89f31a2e06eeAndre Eisenbach    HIDH_TRACE_EVENT1 ("HID-Host Rcvd L2CAP disc, CID: 0x%x", l2cap_cid);
6395738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
6405738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    p_hcon->conn_state = HID_CONN_STATE_DISCONNECTING;
6415738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
6425738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    if (l2cap_cid == p_hcon->ctrl_cid)
6435738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        p_hcon->ctrl_cid = 0;
6445738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    else
6455738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        p_hcon->intr_cid = 0;
6465738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
6475738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    if ((p_hcon->ctrl_cid == 0) && (p_hcon->intr_cid == 0))
6485738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    {
6495738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        hh_cb.devices[dhandle].state = HID_DEV_NO_CONN;
6505738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        p_hcon->conn_state = HID_CONN_STATE_UNUSED;
6515738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
6525738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        if( !ack_needed )
6535738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            disc_res = btm_get_acl_disc_reason_code();
6545738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
6555738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project#if (HID_HOST_MAX_CONN_RETRY > 0)
6565738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        if( (disc_res == HCI_ERR_CONNECTION_TOUT || disc_res == HCI_ERR_UNSPECIFIED) &&
6575738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            (!(hh_cb.devices[dhandle].attr_mask & HID_RECONN_INIT)) &&
6585738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            (hh_cb.devices[dhandle].attr_mask & HID_NORMALLY_CONNECTABLE))
6595738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        {
6605738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            hh_cb.devices[dhandle].conn_tries = 0;
6615738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            hh_cb.devices[dhandle].conn.timer_entry.param = (UINT32) dhandle;
6625738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            btu_start_timer (&(hh_cb.devices[dhandle].conn.timer_entry), BTU_TTYPE_HID_HOST_REPAGE_TO, HID_HOST_REPAGE_WIN);
6635738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        }
6645738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        else
6655738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project#endif
6665738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        {
6675738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            /* Set reason code for HID_HDEV_EVT_CLOSE */
6685738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            hid_close_evt_reason = p_hcon->disc_reason;
6695738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
6705738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            /* If we got baseband sent HCI_DISCONNECT_COMPLETE_EVT due to security failure, then set reason to HID_ERR_AUTH_FAILED */
6715738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            if ((disc_res == HCI_ERR_AUTH_FAILURE)                        ||
6725738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project                (disc_res == HCI_ERR_KEY_MISSING)                         ||
6735738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project                (disc_res == HCI_ERR_HOST_REJECT_SECURITY)                ||
6745738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project                (disc_res == HCI_ERR_PAIRING_NOT_ALLOWED)                 ||
6755738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project                (disc_res == HCI_ERR_UNIT_KEY_USED)                       ||
6765738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project                (disc_res == HCI_ERR_PAIRING_WITH_UNIT_KEY_NOT_SUPPORTED) ||
6775738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project                (disc_res == HCI_ERR_ENCRY_MODE_NOT_ACCEPTABLE)           ||
6785738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project                (disc_res == HCI_ERR_REPEATED_ATTEMPTS))
6795738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            {
6805738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project                hid_close_evt_reason = HID_ERR_AUTH_FAILED;
6815738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            }
6825738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
6832e7fa68bfd9723b7ec7b6b0b128d89f31a2e06eeAndre Eisenbach            hh_cb.callback( dhandle,  hh_cb.devices[dhandle].addr, HID_HDEV_EVT_CLOSE, hid_close_evt_reason, NULL ) ;
6845738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        }
6855738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    }
6865738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project}
6875738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
6885738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
6895738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project/*******************************************************************************
6905738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
6915738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project** Function         hidh_l2cif_disconnect_cfm
6925738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
6935738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project** Description      This function handles a disconnect confirm event from L2CAP.
6945738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
6955738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project** Returns          void
6965738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
6975738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project*******************************************************************************/
6985738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Projectstatic void hidh_l2cif_disconnect_cfm (UINT16 l2cap_cid, UINT16 result)
6995738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project{
7005738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    UINT8 dhandle;
7015738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    tHID_CONN    *p_hcon = NULL;
7025cd8bff2dd0337cb52bf48f312e3d2d55a8882fbMike J. Chen    UNUSED(result);
7035738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
7045738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    /* Find CCB based on CID */
7055738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    if( (dhandle = find_conn_by_cid(l2cap_cid)) < HID_HOST_MAX_DEVICES )
7065738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        p_hcon = &hh_cb.devices[dhandle].conn;
7075738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
7085738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    if (p_hcon == NULL)
7095738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    {
7102e7fa68bfd9723b7ec7b6b0b128d89f31a2e06eeAndre Eisenbach        HIDH_TRACE_WARNING1 ("HID-Host Rcvd L2CAP disc cfm, unknown CID: 0x%x", l2cap_cid);
7115738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        return;
7125738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    }
7135738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
7142e7fa68bfd9723b7ec7b6b0b128d89f31a2e06eeAndre Eisenbach    HIDH_TRACE_EVENT1 ("HID-Host Rcvd L2CAP disc cfm, CID: 0x%x", l2cap_cid);
7155738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
7165738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    if (l2cap_cid == p_hcon->ctrl_cid)
7175738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        p_hcon->ctrl_cid = 0;
7185738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    else
719bf51271f145204a0489597ccd9c851daa7ee0ad7Hemant Gupta    {
7205738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        p_hcon->intr_cid = 0;
721bf51271f145204a0489597ccd9c851daa7ee0ad7Hemant Gupta        if (p_hcon->ctrl_cid)
722bf51271f145204a0489597ccd9c851daa7ee0ad7Hemant Gupta        {
723bf51271f145204a0489597ccd9c851daa7ee0ad7Hemant Gupta            HIDH_TRACE_EVENT0 ("HID-Host Initiating L2CAP Ctrl disconnection");
724bf51271f145204a0489597ccd9c851daa7ee0ad7Hemant Gupta            L2CA_DisconnectReq (p_hcon->ctrl_cid);
725bf51271f145204a0489597ccd9c851daa7ee0ad7Hemant Gupta        }
726bf51271f145204a0489597ccd9c851daa7ee0ad7Hemant Gupta    }
7275738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
7285738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    if ((p_hcon->ctrl_cid == 0) && (p_hcon->intr_cid == 0))
7295738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    {
7305738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        hh_cb.devices[dhandle].state = HID_DEV_NO_CONN;
7315738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        p_hcon->conn_state = HID_CONN_STATE_UNUSED;
7322e7fa68bfd9723b7ec7b6b0b128d89f31a2e06eeAndre Eisenbach        hh_cb.callback( dhandle, hh_cb.devices[dhandle].addr, HID_HDEV_EVT_CLOSE, p_hcon->disc_reason, NULL ) ;
7335738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    }
7345738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project}
7355738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
7365738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
7375738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project/*******************************************************************************
7385738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
7395738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project** Function         hidh_l2cif_cong_ind
7405738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
7415738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project** Description      This function handles a congestion status event from L2CAP.
7425738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
7435738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project** Returns          void
7445738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
7455738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project*******************************************************************************/
7465738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Projectstatic void hidh_l2cif_cong_ind (UINT16 l2cap_cid, BOOLEAN congested)
7475738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project{
7485738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    UINT8 dhandle;
7495738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    tHID_CONN    *p_hcon = NULL;
7505738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
7515738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    /* Find CCB based on CID */
7525738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    if( (dhandle = find_conn_by_cid(l2cap_cid)) < HID_HOST_MAX_DEVICES )
7535738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        p_hcon = &hh_cb.devices[dhandle].conn;
7545738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
7555738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    if (p_hcon == NULL)
7565738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    {
7572e7fa68bfd9723b7ec7b6b0b128d89f31a2e06eeAndre Eisenbach        HIDH_TRACE_WARNING1 ("HID-Host Rcvd L2CAP congestion status, unknown CID: 0x%x", l2cap_cid);
7585738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        return;
7595738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    }
7605738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
7612e7fa68bfd9723b7ec7b6b0b128d89f31a2e06eeAndre Eisenbach    HIDH_TRACE_EVENT2 ("HID-Host Rcvd L2CAP congestion status, CID: 0x%x  Cong: %d", l2cap_cid, congested);
7625738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
7635738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    if (congested)
7645738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        p_hcon->conn_flags |= HID_CONN_FLAGS_CONGESTED;
7655738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    else
7665738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    {
7675738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        p_hcon->conn_flags &= ~HID_CONN_FLAGS_CONGESTED;
7685738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
7695738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    }
7705738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project}
7715738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
7725738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
7735738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project/*******************************************************************************
7745738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
7755738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project** Function         hidh_l2cif_data_ind
7765738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
7775738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project** Description      This function is called when data is received from L2CAP.
7785738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**                  if we are the originator of the connection, we are the SDP
7795738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**                  client, and the received message is queued up for the client.
7805738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
7815738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**                  If we are the destination of the connection, we are the SDP
7825738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**                  server, so the message is passed to the server processing
7835738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**                  function.
7845738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
7855738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project** Returns          void
7865738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
7875738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project*******************************************************************************/
7885738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Projectstatic void hidh_l2cif_data_ind (UINT16 l2cap_cid, BT_HDR *p_msg)
7895738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project{
7905738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    UINT8           *p_data = (UINT8 *)(p_msg + 1) + p_msg->offset;
7915738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    UINT8           ttype, param, rep_type, evt;
7925738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    UINT8 dhandle;
7935738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    tHID_CONN    *p_hcon = NULL;
7945738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
7952e7fa68bfd9723b7ec7b6b0b128d89f31a2e06eeAndre Eisenbach    HIDH_TRACE_DEBUG1 ("HID-Host hidh_l2cif_data_ind [l2cap_cid=0x%04x]", l2cap_cid);
7965738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
7975738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    /* Find CCB based on CID */
7985738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project     if ((dhandle = find_conn_by_cid(l2cap_cid)) < HID_HOST_MAX_DEVICES)
7995738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        p_hcon = &hh_cb.devices[dhandle].conn;
8005738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
8015738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    if (p_hcon == NULL)
8025738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    {
8032e7fa68bfd9723b7ec7b6b0b128d89f31a2e06eeAndre Eisenbach        HIDH_TRACE_WARNING1 ("HID-Host Rcvd L2CAP data, unknown CID: 0x%x", l2cap_cid);
8045738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        GKI_freebuf (p_msg);
8055738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        return;
8065738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    }
8075738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
8085738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
8095738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    ttype    = HID_GET_TRANS_FROM_HDR(*p_data);
8105738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    param    = HID_GET_PARAM_FROM_HDR(*p_data);
8115738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    rep_type = param & HID_PAR_REP_TYPE_MASK;
8125738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    p_data++;
8135738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
8145738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    /* Get rid of the data type */
8155738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    p_msg->len--;
8165738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    p_msg->offset++;
8175738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
8185738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    switch (ttype)
8195738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    {
8205738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    case HID_TRANS_HANDSHAKE:
8212e7fa68bfd9723b7ec7b6b0b128d89f31a2e06eeAndre Eisenbach        hh_cb.callback(dhandle,  hh_cb.devices[dhandle].addr, HID_HDEV_EVT_HANDSHAKE, param, NULL);
8225738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        GKI_freebuf (p_msg);
8235738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        break;
8245738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
8255738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    case HID_TRANS_CONTROL:
8265738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        switch (param)
8275738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        {
8285738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        case HID_PAR_CONTROL_VIRTUAL_CABLE_UNPLUG:
8295738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            hidh_conn_disconnect( dhandle ) ;
8305738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            /* Device is unplugging from us. Tell USB */
8312e7fa68bfd9723b7ec7b6b0b128d89f31a2e06eeAndre Eisenbach            hh_cb.callback(dhandle,  hh_cb.devices[dhandle].addr, HID_HDEV_EVT_VC_UNPLUG, 0, NULL);
8325738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            break;
8335738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
8345738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        default:
8355738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            break;
8365738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        }
8375738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        GKI_freebuf (p_msg);
8385738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        break;
8395738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
8405738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
8415738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    case HID_TRANS_DATA:
8425738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        evt = (hh_cb.devices[dhandle].conn.intr_cid == l2cap_cid) ?
8435738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project                    HID_HDEV_EVT_INTR_DATA : HID_HDEV_EVT_CTRL_DATA;
8442e7fa68bfd9723b7ec7b6b0b128d89f31a2e06eeAndre Eisenbach        hh_cb.callback(dhandle, hh_cb.devices[dhandle].addr, evt, rep_type, p_msg);
8455738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        break;
8465738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
8475738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    case HID_TRANS_DATAC:
8485738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        evt = (hh_cb.devices[dhandle].conn.intr_cid == l2cap_cid) ?
8495738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project                    HID_HDEV_EVT_INTR_DATC : HID_HDEV_EVT_CTRL_DATC;
8502e7fa68bfd9723b7ec7b6b0b128d89f31a2e06eeAndre Eisenbach        hh_cb.callback(dhandle,  hh_cb.devices[dhandle].addr, evt, rep_type, p_msg);
8515738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        break;
8525738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
8535738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    default:
8545738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        GKI_freebuf (p_msg);
8555738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        break;
8565738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    }
8575738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
8585738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project}
8595738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
8605738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project/*******************************************************************************
8615738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
8625738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project** Function         hidh_conn_snd_data
8635738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
8645738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project** Description      This function is sends out data.
8655738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
8665738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project** Returns          tHID_STATUS
8675738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
8685738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project*******************************************************************************/
8695738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source ProjecttHID_STATUS hidh_conn_snd_data (UINT8 dhandle, UINT8 trans_type, UINT8 param,
8705738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project                                UINT16 data, UINT8 report_id, BT_HDR *buf)
8715738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project{
8725738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    tHID_CONN   *p_hcon = &hh_cb.devices[dhandle].conn;
8735738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    BT_HDR      *p_buf;
8745738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    UINT8       *p_out;
8755738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    UINT16      bytes_copied;
8765738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    BOOLEAN     seg_req = FALSE;
8775738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    UINT16      data_size;
8785738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    UINT16      cid;
8795738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    UINT8       pool_id;
8805738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    UINT8       use_data = 0 ;
8815738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    BOOLEAN     blank_datc = FALSE;
8825738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
8835738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    if (p_hcon->conn_flags & HID_CONN_FLAGS_CONGESTED)
8845738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    {
8855738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        if (buf)
8865738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            GKI_freebuf ((void *)buf);
8875738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        return( HID_ERR_CONGESTED );
8885738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    }
8895738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
8905738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    switch( trans_type )
8915738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    {
8925738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    case HID_TRANS_CONTROL:
8935738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    case HID_TRANS_GET_REPORT:
8945738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    case HID_TRANS_SET_REPORT:
8955738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    case HID_TRANS_GET_PROTOCOL:
8965738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    case HID_TRANS_SET_PROTOCOL:
8975738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    case HID_TRANS_GET_IDLE:
8985738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    case HID_TRANS_SET_IDLE:
8995738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        cid = p_hcon->ctrl_cid;
9005738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        pool_id = HID_CONTROL_POOL_ID;
9015738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        break;
9025738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    case HID_TRANS_DATA:
9035738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        cid = p_hcon->intr_cid;
9045738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        pool_id = HID_INTERRUPT_POOL_ID;
9055738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        break;
9065738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    default:
9075738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        return (HID_ERR_INVALID_PARAM) ;
9085738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    }
9095738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
9105738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    if( trans_type == HID_TRANS_SET_IDLE )
9115738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        use_data = 1;
9125738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    else if( (trans_type == HID_TRANS_GET_REPORT) && (param & 0x08) )
9135738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        use_data = 2;
9145738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
9155738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    do
9165738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    {
9175738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        if ( buf == NULL || blank_datc )
9185738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        {
9195738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            if((p_buf = (BT_HDR *)GKI_getpoolbuf (pool_id)) == NULL)
9205738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project                return (HID_ERR_NO_RESOURCES);
9215738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
9225738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            p_buf->offset = L2CAP_MIN_OFFSET;
9235738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            seg_req = FALSE;
9245738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            data_size = 0;
9255738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            bytes_copied = 0;
9265738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            blank_datc = FALSE;
9275738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        }
9285738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        else if ( (buf->len > (p_hcon->rem_mtu_size - 1)))
9295738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        {
9305738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            if((p_buf = (BT_HDR *)GKI_getpoolbuf (pool_id)) == NULL)
9315738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project                return (HID_ERR_NO_RESOURCES);
9325738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
9335738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            p_buf->offset = L2CAP_MIN_OFFSET;
9345738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            seg_req = TRUE;
9355738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            data_size = buf->len;
9365738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            bytes_copied = p_hcon->rem_mtu_size - 1;
9375738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        }
9385738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        else
9395738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        {
9405738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            p_buf = buf ;
9415738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            p_buf->offset -= 1;
9425738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            seg_req = FALSE;
9435738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            data_size = buf->len;
9445738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            bytes_copied = buf->len;
9455738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        }
9465738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
9475738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        p_out         = (UINT8 *)(p_buf + 1) + p_buf->offset;
9485738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        *p_out++      = HID_BUILD_HDR(trans_type, param);
9495738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
9505738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        /* If report ID required for this device */
9515738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        if( (trans_type == HID_TRANS_GET_REPORT) && (report_id != 0) )
9525738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        {
9535738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            *p_out = report_id;
9545738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            data_size = bytes_copied = 1;
9555738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        }
9565738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
9575738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
9585738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        if (seg_req)
9595738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        {
9605738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            memcpy (p_out, (((UINT8 *)(buf+1)) + buf->offset), bytes_copied);
9615738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            buf->offset += bytes_copied;
9625738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            buf->len -= bytes_copied;
9635738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        }
9645738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        else if( use_data == 1)
9655738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        {
9665738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            *(p_out+bytes_copied) = data & 0xff;
9675738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        }
9685738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        else if( use_data == 2 )
9695738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        {
9705738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            *(p_out+bytes_copied) = data & 0xff;
9715738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            *(p_out+bytes_copied+1) = (data >> 8) & 0xff ;
9725738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        }
9735738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
9745738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        p_buf->len   = bytes_copied + 1 + use_data;
9755738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        data_size    -= bytes_copied;
9765738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
9775738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        /* Send the buffer through L2CAP */
9785738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        if ((p_hcon->conn_flags & HID_CONN_FLAGS_CONGESTED) || (!L2CA_DataWrite (cid, p_buf)))
9795738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            return (HID_ERR_CONGESTED);
9805738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
9815738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        if (data_size)
9825738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            trans_type = HID_TRANS_DATAC;
9835738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        else if( bytes_copied == (p_hcon->rem_mtu_size - 1) )
9845738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        {
9855738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            trans_type = HID_TRANS_DATAC;
9865738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            blank_datc = TRUE;
9875738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        }
9885738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
9895738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    } while ((data_size != 0) || blank_datc ) ;
9905738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
9915738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    return (HID_SUCCESS);
9925738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project}
9935738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project/*******************************************************************************
9945738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
9955738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project** Function         hidh_conn_initiate
9965738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
9975738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project** Description      This function is called by the management to create a connection.
9985738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
9995738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project** Returns          void
10005738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
10015738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project*******************************************************************************/
10025738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source ProjecttHID_STATUS hidh_conn_initiate (UINT8 dhandle)
10035738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project{
10042e7fa68bfd9723b7ec7b6b0b128d89f31a2e06eeAndre Eisenbach    UINT8   service_id = BTM_SEC_SERVICE_HIDH_NOSEC_CTRL;
10055738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    UINT32  mx_chan_id = HID_NOSEC_CHN;
10065738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
10075738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    tHID_HOST_DEV_CTB *p_dev = &hh_cb.devices[dhandle];
10085738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
10095738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    if( p_dev->conn.conn_state != HID_CONN_STATE_UNUSED )
10105738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        return( HID_ERR_CONN_IN_PROCESS );
10115738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
10125738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    p_dev->conn.ctrl_cid = 0;
10135738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    p_dev->conn.intr_cid = 0;
10145738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    p_dev->conn.disc_reason = HID_L2CAP_CONN_FAIL;  /* Reset initial reason for CLOSE_EVT: Connection Attempt was made but failed */
10155738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
10165738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    /* We are the originator of this connection */
10175738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    p_dev->conn.conn_flags = HID_CONN_FLAGS_IS_ORIG;
10185738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
10195738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    if(p_dev->attr_mask & HID_SEC_REQUIRED)
10205738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    {
10212e7fa68bfd9723b7ec7b6b0b128d89f31a2e06eeAndre Eisenbach        service_id = BTM_SEC_SERVICE_HIDH_SEC_CTRL;
10225738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        mx_chan_id = HID_SEC_CHN;
10235738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    }
10245738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    BTM_SetOutService (p_dev->addr, service_id, mx_chan_id);
10255738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
10265738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    /* Check if L2CAP started the connection process */
10275738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    if ((p_dev->conn.ctrl_cid = L2CA_ConnectReq (HID_PSM_CONTROL, p_dev->addr)) == 0)
10285738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    {
10292e7fa68bfd9723b7ec7b6b0b128d89f31a2e06eeAndre Eisenbach        HIDH_TRACE_WARNING0 ("HID-Host Originate failed");
10302e7fa68bfd9723b7ec7b6b0b128d89f31a2e06eeAndre Eisenbach        hh_cb.callback( dhandle,  hh_cb.devices[dhandle].addr, HID_HDEV_EVT_CLOSE,
10312e7fa68bfd9723b7ec7b6b0b128d89f31a2e06eeAndre Eisenbach                                HID_ERR_L2CAP_FAILED, NULL ) ;
10325738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    }
10335738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    else
10345738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    {
10355738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        /* Transition to the next appropriate state, waiting for connection confirm on control channel. */
10365738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        p_dev->conn.conn_state = HID_CONN_STATE_CONNECTING_CTRL;
10375738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    }
10385738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
10395738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    return( HID_SUCCESS );
10405738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project}
10415738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
10425738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
10435738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project/*******************************************************************************
10445738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
10455738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project** Function         find_conn_by_cid
10465738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
10475738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project** Description      This function finds a connection control block based on CID
10485738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
10495738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project** Returns          address of control block, or NULL if not found
10505738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
10515738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project*******************************************************************************/
10525738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Projectstatic UINT8 find_conn_by_cid (UINT16 cid)
10535738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project{
10545738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    UINT8      xx;
10555738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
10565738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    for (xx = 0; xx < HID_HOST_MAX_DEVICES; xx++)
10575738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    {
10585738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        if ((hh_cb.devices[xx].in_use) && (hh_cb.devices[xx].conn.conn_state != HID_CONN_STATE_UNUSED)
10595738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            && ((hh_cb.devices[xx].conn.ctrl_cid == cid) || (hh_cb.devices[xx].conn.intr_cid == cid)))
10605738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project            break;
10615738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    }
10625738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
10635738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    return (xx);
10645738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project}
10655738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
10665738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Projectvoid hidh_conn_dereg( void )
10675738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project{
10685738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    L2CA_Deregister (HID_PSM_CONTROL);
10695738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    L2CA_Deregister (HID_PSM_INTERRUPT);
10705738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project}
10715738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
10725738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project/*******************************************************************************
10735738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
10745738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project** Function         hidh_conn_retry
10755738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
10765738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project** Description      This function is called to retry a failed connection.
10775738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
10785738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project** Returns          void
10795738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project**
10805738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project*******************************************************************************/
10815738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Projectstatic void hidh_conn_retry(  UINT8 dhandle )
10825738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project{
10835738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    tHID_HOST_DEV_CTB *p_dev = &hh_cb.devices[dhandle];
10845738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
10855738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    p_dev->conn.conn_state = HID_CONN_STATE_UNUSED;
10865738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    p_dev->conn.timer_entry.param = (UINT32) dhandle;
10875738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project#if (HID_HOST_REPAGE_WIN > 0)
10885738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    btu_start_timer (&(p_dev->conn.timer_entry), BTU_TTYPE_HID_HOST_REPAGE_TO, HID_HOST_REPAGE_WIN);
10895738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project#else
10905738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    hidh_proc_repage_timeout( &(p_dev->conn.timer_entry) );
10915738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project#endif
10925738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project}
1093