U8 L2CA_ConnectReq(L2capConnectRequest *parms) { BtStatus status = BT_STATUS_SUCCESS; BD_ADDR bd_addr; U16 l2ChannelId; /* Establish the ACL link */ memcpy((U8 *)bd_addr.addr, (U8 *)parms->bd_addr,6); (void)CMGR_RegisterHandler(&L2CAPTS(cmgrHandler), l2capTesterCmgrCallback); status = CMGR_CreateDataLink(&L2CAPTS(cmgrHandler), &bd_addr); L2CAPTS(pending_command) = L2CAP_TESTER_CONNECT_REQ; if (status == BT_STATUS_SUCCESS) { status = L2CAP_ConnectReq(&L2CAPTS(Protocol), BT_PSM_TESTING, L2CAPTS(cmgrHandler).remDev, 0, &l2ChannelId); } return status; }
/*--------------------------------------------------------------------------- * HidCmgrCallback() *--------------------------------------------------------------------------- * * Synopsis: Called by connection manager with link state events. * * Return: (See header file) * */ void HidCmgrCallback(CmgrHandler *Handler, CmgrEvent Event, BtStatus Status) { BtStatus ret; HidChannel *channel = ContainingRecord(Handler, HidChannel, cmgrHandler); kal_trace(BT_TRACE_G2_PROFILES,HIDCMGRCALLBACKx02X ,Event); switch (Event) { case CMEVENT_DATA_LINK_CON_CNF: if (channel == NULL) { kal_trace(BT_TRACE_G2_PROFILES,HID_NOT_THE_CONNECT_BD_ADDR); return; } if(channel->cmgrHandler.bdc == 0) { kal_trace(BT_TRACE_G2_PROFILES,HIDCHANNELCMGRHANDLERBDC0); return; } kal_trace(BT_TRACE_G2_PROFILES,HID_STATUSx02X ,Status); if (Status != BT_STATUS_SUCCESS) { /* Indicate the query response failure to the application */ HidClearConnection(channel, Status, 0); return; } else { #ifdef __BT_4_0_BLE__ kal_trace(BT_TRACE_BLE_PROFILES, HID_CMGRCALLBACK_DEVTYPE, channel->cmgrHandler.bdc->devType); if (channel->cmgrHandler.bdc->devType == BT_DEV_TYPE_LE) { ret = GattClientConnect(channel->cmgrHandler.remDev); Report(("[HID] GattClientConnect ret: %d", ret)); /* Since HID Gatt callback will be called even if connection is existed, there is unnecessary to handle return success case here. */ /* if (ret == BT_STATUS_SUCCESS) { ret = HidStartGattServiceQuery(channel); if (ret != BT_STATUS_PENDING) { channel->flags &= ~CHNL_FLAG_SERVICE_QUERY; HidAppCallback(channel, HIDEVENT_QUERY_CNF, ret, &channel->queryRsp, (U16)(sizeof(HidQueryRsp))); } } */ } else #endif { if (channel->flags & CHNL_FLAG_SERVICE_QUERY) { HidStartServiceQuery(channel); } else { kal_trace(BT_TRACE_G2_PROFILES,HID_START_L2CAP_CONNECTION); /* Start the L2CAP connection */ if (L2CAP_ConnectReq(&HID(hidCtrlPsm), BT_PSM_HID_CTRL, channel->cmgrHandler.remDev, 0, &(channel->ctrlCid)) == BT_STATUS_PENDING) { channel->state = HID_STATE_CONN_PENDING; channel->flags |= CHNL_FLAG_INITIATOR; break; } } } } break; case CMEVENT_DATA_LINK_DIS: { HidClearConnection(channel, Status, 0); return; } default: break; } }
/*--------------------------------------------------------------------------- * HidStateConnPending() *--------------------------------------------------------------------------- * * Synopsis: Connection Pending state for the HID channel. * * Return: void */ void HidStateConnPending(HidChannel *Channel, L2capChannelId Cid, L2capCallbackParms *Parms) { //BtSniffInfo sniffInfo; BtStatus status; kal_trace(BT_TRACE_G2_PROFILES,HIDSTATECONNPENDINGx02X ,Parms->event); switch (Parms->event) { case L2EVENT_CONNECT_AUTORIZED: L2Cap_AuthorizeConnectRsp(Cid, TRUE); break; case L2EVENT_CONNECT_IND: /* A second connection was requested */ status = L2CAP_ConnectRsp(Cid, L2CONN_ACCEPTED, 0); kal_trace(BT_TRACE_G2_PROFILES,L2CAP_CONNECTRSPx02X ,status); break; case L2EVENT_CONNECTED: /* A connection is up */ //Assert(Channel->conCount < 2); if(Channel->conCount >= 2){ bt_prompt_trace(MOD_BT,"[HID]Channel->conCount >= 2"); return; } Channel->conCount++; CMGR_HidNoRoleSwitch(1); if (Channel->conCount == 2) { /* Notify the application */ Channel->state = HID_STATE_OPEN; HidAppCallback(Channel, HIDEVENT_OPEN, BT_STATUS_SUCCESS, Channel->cmgrHandler.remDev, sizeof(BtRemoteDevice)); /* Put it on the list of registered handlers */ CMGR_SetDeviceAsMaster(&Channel->cmgrHandler); // CMGR_ActivateSniffTimer(&Channel->cmgrHandler); } else if (Channel->flags & CHNL_FLAG_INITIATOR) { /* The channel initiated the connection, establish the * interrupt channel */ if (Channel->intrCid == Cid) { /* This means control channel has broken before interrupt channel established */ L2CAP_DisconnectReq(Cid); break; } if (L2CAP_ConnectReq(&HID(hidIntrPsm), BT_PSM_HID_INTR, Channel->cmgrHandler.remDev, 0, &(Channel->intrCid)) != BT_STATUS_PENDING) { /* Connect request failed, tear down the first connection */ status = L2CAP_DisconnectReq(Channel->ctrlCid); kal_trace(BT_TRACE_G2_PROFILES,HID_L2CAP_DISCONNECT_REQ_CID_CIDx02X_STATUSx02X ,Channel->ctrlCid, status); } } break; case L2EVENT_DISCONNECTED: /* Connection is going down */ CMGR_HidNoRoleSwitch(0); HidStateDiscPending(Channel, Cid, Parms); break; default: /* Ignore any other events */ kal_trace(BT_TRACE_G2_PROFILES,HID_CHANNEL_CONN_PENDING_STATE_RECEIVED_AN_UNEXPECTED_EVENT_x02X , Parms->event); } }
void l2capTesterCmgrCallback(CmgrHandler *cHandler, CmgrEvent Event, BtStatus Status) { L2capChannelId l2ChannelId; BtStatus status; //add by stanley:2006-0721 local_para_struct* msg; bt_test_cmd_rsp_struct *param_ptr; switch (Event) { case CMEVENT_DATA_LINK_CON_CNF: if (Status == BT_STATUS_SUCCESS) { /* ACL is connected, start SDP Query */ switch(L2CAPTS(pending_command)) { case L2CAP_TESTER_CONNECT_REQ: cHandler->remDev->discFlag = FALSE; status = L2CAP_ConnectReq(&L2CAPTS(Protocol), BT_PSM_TESTING, cHandler->remDev, 0, &l2ChannelId); bt_trace(BT_TRACE_G1_PROTOCOL, BT_L2CAPTS_CONNECTREQ,l2ChannelId); L2CAPTS(cid) = l2ChannelId; //add by stanley:2006-0721 param_ptr = (bt_test_cmd_rsp_struct *)construct_local_para( (U16)sizeof(bt_test_cmd_rsp_struct), TD_CTRL); memset(param_ptr->test_cmd_rsp_buf,0,256); param_ptr->test_cmd_rsp_buf[0]=0x03; //logs type param_ptr->test_cmd_rsp_buf[1]=0x02; //L2cap category kal_sprintf((kal_char*)(param_ptr->test_cmd_rsp_buf+4),"L2CA_ConnectReq,using cid=%d",l2ChannelId); Report(("str data send to L4C:%s",param_ptr->test_cmd_rsp_buf+4)); param_ptr->length= strlen((kal_char*)param_ptr->test_cmd_rsp_buf+4); bt_trace(TRACE_GROUP_1,STR_DATA_LENxD ,param_ptr->length); //fill the data length field of string data for rsp param_ptr->test_cmd_rsp_buf[2]= (U8)(param_ptr->length & 0x00ff); param_ptr->test_cmd_rsp_buf[3]= (U8)((param_ptr->length >> 8) & 0x00ff); //rsp_buf's total length = param_ptr->length + 4 bytes header param_ptr->length += 4; msg = (local_para_struct*)param_ptr; bt_trace(TRACE_GROUP_1,CALL_BTTESTER_SENDMSG); #if 0 btTester_sendMsg(MSG_ID_BT_L4C_TEST_CMD_CNF, #ifdef __GEMINI__ Get_DualSim_Uart_Default_Owner(), #else MOD_ATCI, #endif INVALID_SAP, msg, NULL); #endif return; case L2CAP_TESTER_PING_REQ: memset( (U8 *)L2CAPTS(common_data), 0x55, sizeof(L2CAPTS(common_data))); status = L2CAP_Ping( &(L2CAPTS(Protocol)), L2CAPTS(cmgrHandler).remDev, (U8 *)L2CAPTS(common_data), sizeof(L2CAPTS(common_data))); return; case L2CAP_TESTER_INFO_REQ: status = L2CAP_GetInfo(&(L2CAPTS(Protocol)), L2CAPTS(cmgrHandler).remDev, L2CAPTS(info_type)); return; default: status = BT_STATUS_FAILED; break; } if (Status == BT_STATUS_PENDING) { return; } } /* Disconnect and call the application */ (void)CMGR_RemoveDataLink(&L2CAPTS(cmgrHandler)); (void)CMGR_DeregisterHandler(&L2CAPTS(cmgrHandler)); break; } }