1/****************************************************************************** 2 * 3 * Copyright (C) 2010-2014 Broadcom Corporation 4 * 5 * Licensed under the Apache License, Version 2.0 (the "License"); 6 * you may not use this file except in compliance with the License. 7 * You may obtain a copy of the License at: 8 * 9 * http://www.apache.org/licenses/LICENSE-2.0 10 * 11 * Unless required by applicable law or agreed to in writing, software 12 * distributed under the License is distributed on an "AS IS" BASIS, 13 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 14 * See the License for the specific language governing permissions and 15 * limitations under the License. 16 * 17 ******************************************************************************/ 18 19 20/****************************************************************************** 21 * 22 * This is the main implementation file for the NFA HCI. 23 * 24 ******************************************************************************/ 25#include <string.h> 26#include "nfc_api.h" 27#include "nfa_sys.h" 28#include "nfa_sys_int.h" 29#include "nfa_dm_int.h" 30#include "nfa_hci_api.h" 31#include "nfa_hci_int.h" 32#include "nfa_ee_api.h" 33#include "nfa_ee_int.h" 34#include "nfa_nv_co.h" 35#include "nfa_mem_co.h" 36#include "nfa_hci_defs.h" 37#include "trace_api.h" 38 39 40/***************************************************************************** 41** Global Variables 42*****************************************************************************/ 43 44tNFA_HCI_CB nfa_hci_cb; 45 46#ifndef NFA_HCI_NV_READ_TIMEOUT_VAL 47#define NFA_HCI_NV_READ_TIMEOUT_VAL 1000 48#endif 49 50#ifndef NFA_HCI_CON_CREATE_TIMEOUT_VAL 51#define NFA_HCI_CON_CREATE_TIMEOUT_VAL 1000 52#endif 53 54/***************************************************************************** 55** Static Functions 56*****************************************************************************/ 57 58/* event handler function type */ 59static BOOLEAN nfa_hci_evt_hdlr (BT_HDR *p_msg); 60 61static void nfa_hci_sys_enable (void); 62static void nfa_hci_sys_disable (void); 63static void nfa_hci_rsp_timeout (tNFA_HCI_EVENT_DATA *p_evt_data); 64static void nfa_hci_conn_cback (UINT8 conn_id, tNFC_CONN_EVT event, tNFC_CONN *p_data); 65static void nfa_hci_set_receive_buf (UINT8 pipe); 66static void nfa_hci_assemble_msg (UINT8 *p_data, UINT16 data_len); 67static void nfa_hci_handle_nv_read (UINT8 block, tNFA_STATUS status); 68 69/***************************************************************************** 70** Constants 71*****************************************************************************/ 72static const tNFA_SYS_REG nfa_hci_sys_reg = 73{ 74 nfa_hci_sys_enable, 75 nfa_hci_evt_hdlr, 76 nfa_hci_sys_disable, 77 nfa_hci_proc_nfcc_power_mode 78}; 79 80/******************************************************************************* 81** 82** Function nfa_hci_ee_info_cback 83** 84** Description Callback function 85** 86** Returns None 87** 88*******************************************************************************/ 89void nfa_hci_ee_info_cback (tNFA_EE_DISC_STS status) 90{ 91 UINT8 num_nfcee = 3; 92 tNFA_EE_INFO ee_info[3]; 93 94 NFA_TRACE_DEBUG1 ("nfa_hci_ee_info_cback (): %d", status); 95 96 switch (status) 97 { 98 case NFA_EE_DISC_STS_ON: 99 if ( (!nfa_hci_cb.ee_disc_cmplt) 100 &&((nfa_hci_cb.hci_state == NFA_HCI_STATE_STARTUP) || (nfa_hci_cb.hci_state == NFA_HCI_STATE_RESTORE)) ) 101 { 102 /* NFCEE Discovery is in progress */ 103 nfa_hci_cb.ee_disc_cmplt = TRUE; 104 nfa_hci_cb.num_ee_dis_req_ntf = 0; 105 nfa_hci_cb.num_hot_plug_evts = 0; 106 nfa_hci_cb.conn_id = 0; 107 nfa_hci_startup (); 108 } 109 break; 110 111 case NFA_EE_DISC_STS_OFF: 112 if (nfa_hci_cb.ee_disable_disc) 113 break; 114 nfa_hci_cb.ee_disable_disc = TRUE; 115 /* Discovery operation is complete, retrieve discovery result */ 116 NFA_EeGetInfo (&num_nfcee, ee_info); 117 nfa_hci_cb.num_nfcee = num_nfcee; 118 119 if ( (nfa_hci_cb.hci_state == NFA_HCI_STATE_WAIT_NETWK_ENABLE) 120 ||(nfa_hci_cb.hci_state == NFA_HCI_STATE_RESTORE_NETWK_ENABLE) ) 121 { 122 if ( (nfa_hci_cb.num_nfcee <= 1) 123 ||(nfa_hci_cb.num_ee_dis_req_ntf == (nfa_hci_cb.num_nfcee - 1)) 124 ||(nfa_hci_cb.num_hot_plug_evts == (nfa_hci_cb.num_nfcee - 1)) ) 125 { 126 /* No UICC Host is detected or 127 * HOT_PLUG_EVT(s) and or EE DISC REQ Ntf(s) are already received 128 * Get Host list and notify SYS on Initialization complete */ 129 nfa_sys_stop_timer (&nfa_hci_cb.timer); 130 if ( (nfa_hci_cb.num_nfcee > 1) 131 &&(nfa_hci_cb.num_ee_dis_req_ntf != (nfa_hci_cb.num_nfcee - 1)) ) 132 { 133 /* Received HOT PLUG EVT, we will also wait for EE DISC REQ Ntf(s) */ 134 nfa_sys_start_timer (&nfa_hci_cb.timer, NFA_HCI_RSP_TIMEOUT_EVT, p_nfa_hci_cfg->hci_netwk_enable_timeout); 135 } 136 else 137 { 138 nfa_hci_cb.w4_hci_netwk_init = FALSE; 139 nfa_hciu_send_get_param_cmd (NFA_HCI_ADMIN_PIPE, NFA_HCI_HOST_LIST_INDEX); 140 } 141 } 142 } 143 else if (nfa_hci_cb.num_nfcee <= 1) 144 { 145 /* No UICC Host is detected, HCI NETWORK is enabled */ 146 nfa_hci_cb.w4_hci_netwk_init = FALSE; 147 } 148 break; 149 150 case NFA_EE_DISC_STS_REQ: 151 nfa_hci_cb.num_ee_dis_req_ntf++; 152 153 if (nfa_hci_cb.ee_disable_disc) 154 { 155 /* Already received Discovery Ntf */ 156 if ( (nfa_hci_cb.hci_state == NFA_HCI_STATE_WAIT_NETWK_ENABLE) 157 ||(nfa_hci_cb.hci_state == NFA_HCI_STATE_RESTORE_NETWK_ENABLE) ) 158 { 159 /* Received DISC REQ Ntf while waiting for other Host in the network to bootup after DH host bootup is complete */ 160 if (nfa_hci_cb.num_ee_dis_req_ntf == (nfa_hci_cb.num_nfcee - 1)) 161 { 162 /* Received expected number of EE DISC REQ Ntf(s) */ 163 nfa_sys_stop_timer (&nfa_hci_cb.timer); 164 nfa_hci_cb.w4_hci_netwk_init = FALSE; 165 nfa_hciu_send_get_param_cmd (NFA_HCI_ADMIN_PIPE, NFA_HCI_HOST_LIST_INDEX); 166 } 167 } 168 else if ( (nfa_hci_cb.hci_state == NFA_HCI_STATE_STARTUP) 169 ||(nfa_hci_cb.hci_state == NFA_HCI_STATE_RESTORE) ) 170 { 171 /* Received DISC REQ Ntf during DH host bootup */ 172 if (nfa_hci_cb.num_ee_dis_req_ntf == (nfa_hci_cb.num_nfcee - 1)) 173 { 174 /* Received expected number of EE DISC REQ Ntf(s) */ 175 nfa_hci_cb.w4_hci_netwk_init = FALSE; 176 } 177 } 178 } 179 break; 180 } 181} 182 183/******************************************************************************* 184** 185** Function nfa_hci_init 186** 187** Description Initialize NFA HCI 188** 189** Returns None 190** 191*******************************************************************************/ 192void nfa_hci_init (void) 193{ 194 NFA_TRACE_DEBUG0 ("nfa_hci_init ()"); 195 196 /* initialize control block */ 197 memset (&nfa_hci_cb, 0, sizeof (tNFA_HCI_CB)); 198 199 nfa_hci_cb.hci_state = NFA_HCI_STATE_STARTUP; 200 201 /* register message handler on NFA SYS */ 202 nfa_sys_register (NFA_ID_HCI, &nfa_hci_sys_reg); 203} 204 205/******************************************************************************* 206** 207** Function nfa_hci_is_valid_cfg 208** 209** Description Validate hci control block config parameters 210** 211** Returns None 212** 213*******************************************************************************/ 214BOOLEAN nfa_hci_is_valid_cfg (void) 215{ 216 UINT8 xx,yy,zz; 217 tNFA_HANDLE reg_app[NFA_HCI_MAX_APP_CB]; 218 UINT8 valid_gate[NFA_HCI_MAX_GATE_CB]; 219 UINT8 app_count = 0; 220 UINT8 gate_count = 0; 221 UINT32 pipe_inx_mask = 0; 222 223 /* First, see if valid values are stored in app names, send connectivity events flag */ 224 for (xx = 0; xx < NFA_HCI_MAX_APP_CB; xx++) 225 { 226 /* Check if app name is valid with null terminated string */ 227 if (strlen (&nfa_hci_cb.cfg.reg_app_names[xx][0]) > NFA_MAX_HCI_APP_NAME_LEN) 228 return FALSE; 229 230 /* Send Connectivity event flag can be either TRUE or FALSE */ 231 if ( (nfa_hci_cb.cfg.b_send_conn_evts[xx] != TRUE) 232 &&(nfa_hci_cb.cfg.b_send_conn_evts[xx] != FALSE)) 233 return FALSE; 234 235 if (nfa_hci_cb.cfg.reg_app_names[xx][0] != 0) 236 { 237 /* Check if the app name is present more than one time in the control block */ 238 for (yy = xx + 1; yy < NFA_HCI_MAX_APP_CB; yy++) 239 { 240 if ( (nfa_hci_cb.cfg.reg_app_names[yy][0] != 0) 241 &&(!strncmp (&nfa_hci_cb.cfg.reg_app_names[xx][0], &nfa_hci_cb.cfg.reg_app_names[yy][0], strlen (nfa_hci_cb.cfg.reg_app_names[xx]))) ) 242 { 243 /* Two app cannot have the same name , NVRAM is corrupted */ 244 NFA_TRACE_EVENT2 ("nfa_hci_is_valid_cfg (%s) Reusing: %u", &nfa_hci_cb.cfg.reg_app_names[xx][0], xx); 245 return FALSE; 246 } 247 } 248 /* Collect list of hci handle */ 249 reg_app[app_count++] = (tNFA_HANDLE) (xx | NFA_HANDLE_GROUP_HCI); 250 } 251 } 252 253 /* Validate Gate Control block */ 254 for (xx = 0; xx < NFA_HCI_MAX_GATE_CB; xx++) 255 { 256 if (nfa_hci_cb.cfg.dyn_gates[xx].gate_id != 0) 257 { 258 if ( ( (nfa_hci_cb.cfg.dyn_gates[xx].gate_id != NFA_HCI_LOOP_BACK_GATE) 259 &&(nfa_hci_cb.cfg.dyn_gates[xx].gate_id != NFA_HCI_IDENTITY_MANAGEMENT_GATE) 260 &&(nfa_hci_cb.cfg.dyn_gates[xx].gate_id < NFA_HCI_FIRST_HOST_SPECIFIC_GENERIC_GATE)) 261 ||(nfa_hci_cb.cfg.dyn_gates[xx].gate_id > NFA_HCI_LAST_PROP_GATE)) 262 return FALSE; 263 264 /* Check if the same gate id is present more than once in the control block */ 265 for (yy = xx + 1; yy < NFA_HCI_MAX_GATE_CB; yy++) 266 { 267 if ( (nfa_hci_cb.cfg.dyn_gates[yy].gate_id != 0) 268 &&(nfa_hci_cb.cfg.dyn_gates[xx].gate_id == nfa_hci_cb.cfg.dyn_gates[yy].gate_id) ) 269 { 270 NFA_TRACE_EVENT1 ("nfa_hci_is_valid_cfg Reusing: %u", nfa_hci_cb.cfg.dyn_gates[xx].gate_id); 271 return FALSE; 272 } 273 } 274 if ((nfa_hci_cb.cfg.dyn_gates[xx].gate_owner & (~NFA_HANDLE_GROUP_HCI)) >= NFA_HCI_MAX_APP_CB) 275 { 276 NFA_TRACE_EVENT1 ("nfa_hci_is_valid_cfg Invalid Gate owner: %u", nfa_hci_cb.cfg.dyn_gates[xx].gate_owner); 277 return FALSE; 278 } 279 if (nfa_hci_cb.cfg.dyn_gates[xx].gate_id != NFA_HCI_CONNECTIVITY_GATE) 280 { 281 /* The gate owner should be one of the registered application */ 282 for (zz = 0; zz < app_count; zz++) 283 { 284 if (nfa_hci_cb.cfg.dyn_gates[xx].gate_owner == reg_app[zz]) 285 break; 286 } 287 if (zz == app_count) 288 { 289 NFA_TRACE_EVENT1 ("nfa_hci_is_valid_cfg Invalid Gate owner: %u", nfa_hci_cb.cfg.dyn_gates[xx].gate_owner); 290 return FALSE; 291 } 292 } 293 /* Collect list of allocated gates */ 294 valid_gate[gate_count++] = nfa_hci_cb.cfg.dyn_gates[xx].gate_id; 295 296 /* No two gates can own a same pipe */ 297 if ((pipe_inx_mask & nfa_hci_cb.cfg.dyn_gates[xx].pipe_inx_mask) != 0) 298 return FALSE; 299 /* Collect the list of pipes on this gate */ 300 pipe_inx_mask |= nfa_hci_cb.cfg.dyn_gates[xx].pipe_inx_mask; 301 } 302 } 303 304 for (xx = 0; (pipe_inx_mask && (xx < NFA_HCI_MAX_PIPE_CB)); xx++,pipe_inx_mask >>= 1) 305 { 306 /* Every bit set in pipe increment mask indicates a valid pipe */ 307 if (pipe_inx_mask & 1) 308 { 309 /* Check if the pipe is valid one */ 310 if (nfa_hci_cb.cfg.dyn_pipes[xx].pipe_id < NFA_HCI_FIRST_DYNAMIC_PIPE) 311 return FALSE; 312 } 313 } 314 315 if (xx == NFA_HCI_MAX_PIPE_CB) 316 return FALSE; 317 318 /* Validate Gate Control block */ 319 for (xx = 0; xx < NFA_HCI_MAX_PIPE_CB; xx++) 320 { 321 if (nfa_hci_cb.cfg.dyn_pipes[xx].pipe_id != 0) 322 { 323 /* Check if pipe id is valid */ 324 if (nfa_hci_cb.cfg.dyn_pipes[xx].pipe_id < NFA_HCI_FIRST_DYNAMIC_PIPE) 325 return FALSE; 326 327 /* Check if pipe state is valid */ 328 if ( (nfa_hci_cb.cfg.dyn_pipes[xx].pipe_state != NFA_HCI_PIPE_OPENED) 329 &&(nfa_hci_cb.cfg.dyn_pipes[xx].pipe_state != NFA_HCI_PIPE_CLOSED)) 330 return FALSE; 331 332 /* Check if local gate on which the pipe is created is valid */ 333 if ( (((nfa_hci_cb.cfg.dyn_pipes[xx].local_gate != NFA_HCI_LOOP_BACK_GATE) && (nfa_hci_cb.cfg.dyn_pipes[xx].local_gate != NFA_HCI_IDENTITY_MANAGEMENT_GATE)) && (nfa_hci_cb.cfg.dyn_pipes[xx].local_gate < NFA_HCI_FIRST_HOST_SPECIFIC_GENERIC_GATE)) 334 ||(nfa_hci_cb.cfg.dyn_pipes[xx].local_gate > NFA_HCI_LAST_PROP_GATE)) 335 return FALSE; 336 337 /* Check if the peer gate on which the pipe is created is valid */ 338 if ( (((nfa_hci_cb.cfg.dyn_pipes[xx].dest_gate != NFA_HCI_LOOP_BACK_GATE) && (nfa_hci_cb.cfg.dyn_pipes[xx].dest_gate != NFA_HCI_IDENTITY_MANAGEMENT_GATE)) && (nfa_hci_cb.cfg.dyn_pipes[xx].dest_gate < NFA_HCI_FIRST_HOST_SPECIFIC_GENERIC_GATE)) 339 ||(nfa_hci_cb.cfg.dyn_pipes[xx].dest_gate > NFA_HCI_LAST_PROP_GATE)) 340 return FALSE; 341 342 /* Check if the same pipe is present more than once in the control block */ 343 for (yy = xx + 1; yy < NFA_HCI_MAX_PIPE_CB; yy++) 344 { 345 if ( (nfa_hci_cb.cfg.dyn_pipes[yy].pipe_id != 0) 346 &&(nfa_hci_cb.cfg.dyn_pipes[xx].pipe_id == nfa_hci_cb.cfg.dyn_pipes[yy].pipe_id) ) 347 { 348 NFA_TRACE_EVENT1 ("nfa_hci_is_valid_cfg Reusing: %u", nfa_hci_cb.cfg.dyn_pipes[xx].pipe_id); 349 return FALSE; 350 } 351 } 352 /* The local gate should be one of the element in gate control block */ 353 for (zz = 0; zz < gate_count; zz++) 354 { 355 if (nfa_hci_cb.cfg.dyn_pipes[xx].local_gate == valid_gate[zz]) 356 break; 357 } 358 if (zz == gate_count) 359 { 360 NFA_TRACE_EVENT1 ("nfa_hci_is_valid_cfg Invalid Gate: %u", nfa_hci_cb.cfg.dyn_pipes[xx].local_gate); 361 return FALSE; 362 } 363 } 364 } 365 366 /* Check if admin pipe state is valid */ 367 if ( (nfa_hci_cb.cfg.admin_gate.pipe01_state != NFA_HCI_PIPE_OPENED) 368 &&(nfa_hci_cb.cfg.admin_gate.pipe01_state != NFA_HCI_PIPE_CLOSED)) 369 return FALSE; 370 371 /* Check if link management pipe state is valid */ 372 if ( (nfa_hci_cb.cfg.link_mgmt_gate.pipe00_state != NFA_HCI_PIPE_OPENED) 373 &&(nfa_hci_cb.cfg.link_mgmt_gate.pipe00_state != NFA_HCI_PIPE_CLOSED)) 374 return FALSE; 375 376 pipe_inx_mask = nfa_hci_cb.cfg.id_mgmt_gate.pipe_inx_mask; 377 for (xx = 0; (pipe_inx_mask && (xx < NFA_HCI_MAX_PIPE_CB)); xx++,pipe_inx_mask >>= 1) 378 { 379 /* Every bit set in pipe increment mask indicates a valid pipe */ 380 if (pipe_inx_mask & 1) 381 { 382 /* Check if the pipe is valid one */ 383 if (nfa_hci_cb.cfg.dyn_pipes[xx].pipe_id < NFA_HCI_FIRST_DYNAMIC_PIPE) 384 return FALSE; 385 /* Check if the pipe is connected to Identity management gate */ 386 if (nfa_hci_cb.cfg.dyn_pipes[xx].local_gate != NFA_HCI_IDENTITY_MANAGEMENT_GATE) 387 return FALSE; 388 } 389 } 390 if (xx == NFA_HCI_MAX_PIPE_CB) 391 return FALSE; 392 393 return TRUE; 394} 395 396/******************************************************************************* 397** 398** Function nfa_hci_cfg_default 399** 400** Description Configure default values for hci control block 401** 402** Returns None 403** 404*******************************************************************************/ 405void nfa_hci_restore_default_config (UINT8 *p_session_id) 406{ 407 memset (&nfa_hci_cb.cfg, 0, sizeof (nfa_hci_cb.cfg)); 408 memcpy (nfa_hci_cb.cfg.admin_gate.session_id, p_session_id, NFA_HCI_SESSION_ID_LEN); 409 nfa_hci_cb.nv_write_needed = TRUE; 410} 411 412/******************************************************************************* 413** 414** Function nfa_hci_proc_nfcc_power_mode 415** 416** Description Restore NFA HCI sub-module 417** 418** Returns None 419** 420*******************************************************************************/ 421void nfa_hci_proc_nfcc_power_mode (UINT8 nfcc_power_mode) 422{ 423 NFA_TRACE_DEBUG1 ("nfa_hci_proc_nfcc_power_mode () nfcc_power_mode=%d", nfcc_power_mode); 424 425 /* if NFCC power mode is change to full power */ 426 if (nfcc_power_mode == NFA_DM_PWR_MODE_FULL) 427 { 428 nfa_hci_cb.b_low_power_mode = FALSE; 429 if (nfa_hci_cb.hci_state == NFA_HCI_STATE_IDLE) 430 { 431 nfa_hci_cb.hci_state = NFA_HCI_STATE_RESTORE; 432 nfa_hci_cb.ee_disc_cmplt = FALSE; 433 nfa_hci_cb.ee_disable_disc = TRUE; 434 if (nfa_hci_cb.num_nfcee > 1) 435 nfa_hci_cb.w4_hci_netwk_init = TRUE; 436 else 437 nfa_hci_cb.w4_hci_netwk_init = FALSE; 438 nfa_hci_cb.conn_id = 0; 439 nfa_hci_cb.num_ee_dis_req_ntf = 0; 440 nfa_hci_cb.num_hot_plug_evts = 0; 441 } 442 else 443 { 444 NFA_TRACE_ERROR0 ("nfa_hci_proc_nfcc_power_mode (): Cannot restore now"); 445 nfa_sys_cback_notify_nfcc_power_mode_proc_complete (NFA_ID_HCI); 446 } 447 } 448 else 449 { 450 nfa_hci_cb.hci_state = NFA_HCI_STATE_IDLE; 451 nfa_hci_cb.w4_rsp_evt = FALSE; 452 nfa_hci_cb.conn_id = 0; 453 nfa_sys_stop_timer (&nfa_hci_cb.timer); 454 nfa_hci_cb.b_low_power_mode = TRUE; 455 nfa_sys_cback_notify_nfcc_power_mode_proc_complete (NFA_ID_HCI); 456 } 457} 458 459/******************************************************************************* 460** 461** Function nfa_hci_dh_startup_complete 462** 463** Description Initialization of terminal host in HCI Network is completed 464** Wait for other host in the network to initialize 465** 466** Returns None 467** 468*******************************************************************************/ 469void nfa_hci_dh_startup_complete (void) 470{ 471 if (nfa_hci_cb.w4_hci_netwk_init) 472 { 473 if (nfa_hci_cb.hci_state == NFA_HCI_STATE_STARTUP) 474 { 475 nfa_hci_cb.hci_state = NFA_HCI_STATE_WAIT_NETWK_ENABLE; 476 /* Wait for EE Discovery to complete */ 477 nfa_sys_start_timer (&nfa_hci_cb.timer, NFA_HCI_RSP_TIMEOUT_EVT, NFA_EE_DISCV_TIMEOUT_VAL); 478 } 479 else if (nfa_hci_cb.hci_state == NFA_HCI_STATE_RESTORE) 480 { 481 nfa_hci_cb.hci_state = NFA_HCI_STATE_RESTORE_NETWK_ENABLE; 482 /* No HCP packet to DH for a specified period of time indicates all host in the network is initialized */ 483 nfa_sys_start_timer (&nfa_hci_cb.timer, NFA_HCI_RSP_TIMEOUT_EVT, p_nfa_hci_cfg->hci_netwk_enable_timeout); 484 } 485 } 486 else if ( (nfa_hci_cb.num_nfcee > 1) 487 &&(nfa_hci_cb.num_ee_dis_req_ntf != (nfa_hci_cb.num_nfcee - 1)) ) 488 { 489 if (nfa_hci_cb.hci_state == NFA_HCI_STATE_RESTORE) 490 nfa_hci_cb.ee_disable_disc = TRUE; 491 /* Received HOT PLUG EVT, we will also wait for EE DISC REQ Ntf(s) */ 492 nfa_sys_start_timer (&nfa_hci_cb.timer, NFA_HCI_RSP_TIMEOUT_EVT, p_nfa_hci_cfg->hci_netwk_enable_timeout); 493 } 494 else 495 { 496 /* Received EE DISC REQ Ntf(s) */ 497 nfa_hciu_send_get_param_cmd (NFA_HCI_ADMIN_PIPE, NFA_HCI_HOST_LIST_INDEX); 498 } 499} 500 501/******************************************************************************* 502** 503** Function nfa_hci_startup_complete 504** 505** Description HCI network initialization is completed 506** 507** Returns None 508** 509*******************************************************************************/ 510void nfa_hci_startup_complete (tNFA_STATUS status) 511{ 512 tNFA_HCI_EVT_DATA evt_data; 513 514 NFA_TRACE_EVENT1 ("nfa_hci_startup_complete (): Status: %u", status); 515 516 nfa_sys_stop_timer (&nfa_hci_cb.timer); 517 518 if ( (nfa_hci_cb.hci_state == NFA_HCI_STATE_RESTORE) 519 ||(nfa_hci_cb.hci_state == NFA_HCI_STATE_RESTORE_NETWK_ENABLE) ) 520 { 521 nfa_ee_proc_hci_info_cback (); 522 nfa_sys_cback_notify_nfcc_power_mode_proc_complete (NFA_ID_HCI); 523 } 524 else 525 { 526 evt_data.hci_init.status = status; 527 528 nfa_hciu_send_to_all_apps (NFA_HCI_INIT_EVT, &evt_data); 529 nfa_sys_cback_notify_enable_complete (NFA_ID_HCI); 530 } 531 532 if (status == NFA_STATUS_OK) 533 nfa_hci_cb.hci_state = NFA_HCI_STATE_IDLE; 534 535 else 536 nfa_hci_cb.hci_state = NFA_HCI_STATE_DISABLED; 537} 538 539/******************************************************************************* 540** 541** Function nfa_hci_startup 542** 543** Description Perform HCI startup 544** 545** Returns None 546** 547*******************************************************************************/ 548void nfa_hci_startup (void) 549{ 550 tNFA_STATUS status = NFA_STATUS_FAILED; 551 tNFA_EE_INFO ee_info[2]; 552 UINT8 num_nfcee = 2; 553 UINT8 target_handle; 554 UINT8 count = 0; 555 BOOLEAN found = FALSE; 556 557 if (HCI_LOOPBACK_DEBUG) 558 { 559 /* First step in initialization is to open the admin pipe */ 560 nfa_hciu_send_open_pipe_cmd (NFA_HCI_ADMIN_PIPE); 561 return; 562 } 563 564 /* We can only start up if NV Ram is read and EE discovery is complete */ 565 if (nfa_hci_cb.nv_read_cmplt && nfa_hci_cb.ee_disc_cmplt && (nfa_hci_cb.conn_id == 0)) 566 { 567 NFA_EeGetInfo (&num_nfcee, ee_info); 568 569 while ((count < num_nfcee) && (!found)) 570 { 571 target_handle = (UINT8) ee_info[count].ee_handle; 572 573 if(ee_info[count].ee_interface[0] == NFA_EE_INTERFACE_HCI_ACCESS) 574 { 575 found = TRUE; 576 577 if (ee_info[count].ee_status == NFA_EE_STATUS_INACTIVE) 578 { 579 NFC_NfceeModeSet (target_handle, NFC_MODE_ACTIVATE); 580 } 581 if ((status = NFC_ConnCreate (NCI_DEST_TYPE_NFCEE, target_handle, NFA_EE_INTERFACE_HCI_ACCESS, nfa_hci_conn_cback)) == NFA_STATUS_OK) 582 nfa_sys_start_timer (&nfa_hci_cb.timer, NFA_HCI_RSP_TIMEOUT_EVT, NFA_HCI_CON_CREATE_TIMEOUT_VAL); 583 else 584 { 585 nfa_hci_cb.hci_state = NFA_HCI_STATE_DISABLED; 586 NFA_TRACE_ERROR0 ("nfa_hci_startup - Failed to Create Logical connection. HCI Initialization/Restore failed"); 587 nfa_hci_startup_complete (NFA_STATUS_FAILED); 588 } 589 } 590 count++; 591 } 592 if (!found) 593 { 594 NFA_TRACE_ERROR0 ("nfa_hci_startup - HCI ACCESS Interface not discovered. HCI Initialization/Restore failed"); 595 nfa_hci_startup_complete (NFA_STATUS_FAILED); 596 } 597 } 598} 599 600/******************************************************************************* 601** 602** Function nfa_hci_sys_enable 603** 604** Description Enable NFA HCI 605** 606** Returns None 607** 608*******************************************************************************/ 609static void nfa_hci_sys_enable (void) 610{ 611 NFA_TRACE_DEBUG0 ("nfa_hci_sys_enable ()"); 612 nfa_ee_reg_cback_enable_done (&nfa_hci_ee_info_cback); 613 614 nfa_nv_co_read ((UINT8 *)&nfa_hci_cb.cfg, sizeof (nfa_hci_cb.cfg),DH_NV_BLOCK); 615 nfa_sys_start_timer (&nfa_hci_cb.timer, NFA_HCI_RSP_TIMEOUT_EVT, NFA_HCI_NV_READ_TIMEOUT_VAL); 616} 617 618/******************************************************************************* 619** 620** Function nfa_hci_sys_disable 621** 622** Description Disable NFA HCI 623** 624** Returns None 625** 626*******************************************************************************/ 627static void nfa_hci_sys_disable (void) 628{ 629 tNFA_HCI_EVT_DATA evt_data; 630 631 nfa_sys_stop_timer (&nfa_hci_cb.timer); 632 633 if (nfa_hci_cb.conn_id) 634 { 635 if (nfa_sys_is_graceful_disable ()) 636 { 637 /* Tell all applications stack is down */ 638 nfa_hciu_send_to_all_apps (NFA_HCI_EXIT_EVT, &evt_data); 639 NFC_ConnClose (nfa_hci_cb.conn_id); 640 return; 641 } 642 nfa_hci_cb.conn_id = 0; 643 } 644 645 nfa_hci_cb.hci_state = NFA_HCI_STATE_DISABLED; 646 /* deregister message handler on NFA SYS */ 647 nfa_sys_deregister (NFA_ID_HCI); 648} 649 650/******************************************************************************* 651** 652** Function nfa_hci_conn_cback 653** 654** Description This function Process event from NCI 655** 656** Returns None 657** 658*******************************************************************************/ 659static void nfa_hci_conn_cback (UINT8 conn_id, tNFC_CONN_EVT event, tNFC_CONN *p_data) 660{ 661 UINT8 *p; 662 BT_HDR *p_pkt = (BT_HDR *) p_data->data.p_data; 663 UINT8 chaining_bit; 664 UINT8 pipe; 665 UINT16 pkt_len; 666#if (BT_TRACE_VERBOSE == TRUE) 667 char buff[100]; 668#endif 669 670 if (event == NFC_CONN_CREATE_CEVT) 671 { 672 nfa_hci_cb.conn_id = conn_id; 673 nfa_hci_cb.buff_size = p_data->conn_create.buff_size; 674 675 if (nfa_hci_cb.hci_state == NFA_HCI_STATE_STARTUP) 676 { 677 nfa_hci_cb.w4_hci_netwk_init = TRUE; 678 nfa_hciu_alloc_gate (NFA_HCI_CONNECTIVITY_GATE,0); 679 } 680 681 if (nfa_hci_cb.cfg.admin_gate.pipe01_state == NFA_HCI_PIPE_CLOSED) 682 { 683 /* First step in initialization/restore is to open the admin pipe */ 684 nfa_hciu_send_open_pipe_cmd (NFA_HCI_ADMIN_PIPE); 685 } 686 else 687 { 688 /* Read session id, to know DH session id is correct */ 689 nfa_hciu_send_get_param_cmd (NFA_HCI_ADMIN_PIPE, NFA_HCI_SESSION_IDENTITY_INDEX); 690 } 691 } 692 else if (event == NFC_CONN_CLOSE_CEVT) 693 { 694 nfa_hci_cb.conn_id = 0; 695 nfa_hci_cb.hci_state = NFA_HCI_STATE_DISABLED; 696 /* deregister message handler on NFA SYS */ 697 nfa_sys_deregister (NFA_ID_HCI); 698 } 699 700 if ((event != NFC_DATA_CEVT) || (p_pkt == NULL)) 701 return; 702 703 if ( (nfa_hci_cb.hci_state == NFA_HCI_STATE_WAIT_NETWK_ENABLE) 704 ||(nfa_hci_cb.hci_state == NFA_HCI_STATE_RESTORE_NETWK_ENABLE) ) 705 { 706 /* Received HCP Packet before timeout, Other Host initialization is not complete */ 707 nfa_sys_stop_timer (&nfa_hci_cb.timer); 708 if (nfa_hci_cb.w4_hci_netwk_init) 709 nfa_sys_start_timer (&nfa_hci_cb.timer, NFA_HCI_RSP_TIMEOUT_EVT, p_nfa_hci_cfg->hci_netwk_enable_timeout); 710 } 711 712 p = (UINT8 *) (p_pkt + 1) + p_pkt->offset; 713 pkt_len = p_pkt->len; 714 715#if (BT_TRACE_PROTOCOL == TRUE) 716 DispHcp (p, pkt_len, TRUE, (BOOLEAN) !nfa_hci_cb.assembling); 717#endif 718 719 chaining_bit = ((*p) >> 0x07) & 0x01; 720 pipe = (*p++) & 0x7F; 721 if (pkt_len != 0) 722 pkt_len--; 723 724 if (nfa_hci_cb.assembling == FALSE) 725 { 726 /* First Segment of a packet */ 727 nfa_hci_cb.type = ((*p) >> 0x06) & 0x03; 728 nfa_hci_cb.inst = (*p++ & 0x3F); 729 if (pkt_len != 0) 730 pkt_len--; 731 nfa_hci_cb.assembly_failed = FALSE; 732 nfa_hci_cb.msg_len = 0; 733 734 if (chaining_bit == NFA_HCI_MESSAGE_FRAGMENTATION) 735 { 736 nfa_hci_cb.assembling = TRUE; 737 nfa_hci_set_receive_buf (pipe); 738 nfa_hci_assemble_msg (p, pkt_len); 739 } 740 else 741 { 742 if ((pipe >= NFA_HCI_FIRST_DYNAMIC_PIPE) && (nfa_hci_cb.type == NFA_HCI_EVENT_TYPE)) 743 { 744 nfa_hci_set_receive_buf (pipe); 745 nfa_hci_assemble_msg (p, pkt_len); 746 p = nfa_hci_cb.p_msg_data; 747 } 748 } 749 } 750 else 751 { 752 if (nfa_hci_cb.assembly_failed) 753 { 754 /* If Reassembly failed because of insufficient buffer, just drop the new segmented packets */ 755 NFA_TRACE_ERROR1 ("nfa_hci_conn_cback (): Insufficient buffer to Reassemble HCP packet! Dropping :%u bytes", pkt_len); 756 } 757 else 758 { 759 /* Reassemble the packet */ 760 nfa_hci_assemble_msg (p, pkt_len); 761 } 762 763 if (chaining_bit == NFA_HCI_NO_MESSAGE_FRAGMENTATION) 764 { 765 /* Just added the last segment in the chain. Reset pointers */ 766 nfa_hci_cb.assembling = FALSE; 767 p = nfa_hci_cb.p_msg_data; 768 pkt_len = nfa_hci_cb.msg_len; 769 } 770 } 771 772#if (BT_TRACE_VERBOSE == TRUE) 773 NFA_TRACE_EVENT5 ("nfa_hci_conn_cback Recvd data pipe:%d %s chain:%d assmbl:%d len:%d", 774 (UINT8)pipe, nfa_hciu_get_type_inst_names (pipe, nfa_hci_cb.type, nfa_hci_cb.inst, buff), 775 (UINT8)chaining_bit, (UINT8)nfa_hci_cb.assembling, p_pkt->len); 776#else 777 NFA_TRACE_EVENT6 ("nfa_hci_conn_cback Recvd data pipe:%d Type: %u Inst: %u chain:%d reassm:%d len:%d", 778 pipe, nfa_hci_cb.type, nfa_hci_cb.inst, chaining_bit, nfa_hci_cb.assembling, p_pkt->len); 779#endif 780 781 782 /* If still reassembling fragments, just return */ 783 if (nfa_hci_cb.assembling) 784 { 785 /* if not last packet, release GKI buffer */ 786 GKI_freebuf (p_pkt); 787 return; 788 } 789 790 /* If we got a response, cancel the response timer. Also, if waiting for */ 791 /* a single response, we can go back to idle state */ 792 if ( (nfa_hci_cb.hci_state == NFA_HCI_STATE_WAIT_RSP) 793 &&((nfa_hci_cb.type == NFA_HCI_RESPONSE_TYPE) || (nfa_hci_cb.w4_rsp_evt && (nfa_hci_cb.type == NFA_HCI_EVENT_TYPE))) ) 794 { 795 nfa_sys_stop_timer (&nfa_hci_cb.timer); 796 nfa_hci_cb.hci_state = NFA_HCI_STATE_IDLE; 797 } 798 799 switch (pipe) 800 { 801 case NFA_HCI_ADMIN_PIPE: 802 /* Check if data packet is a command, response or event */ 803 if (nfa_hci_cb.type == NFA_HCI_COMMAND_TYPE) 804 { 805 nfa_hci_handle_admin_gate_cmd (p); 806 } 807 else if (nfa_hci_cb.type == NFA_HCI_RESPONSE_TYPE) 808 { 809 nfa_hci_handle_admin_gate_rsp (p, (UINT8) pkt_len); 810 } 811 else if (nfa_hci_cb.type == NFA_HCI_EVENT_TYPE) 812 { 813 nfa_hci_handle_admin_gate_evt (p); 814 } 815 break; 816 817 case NFA_HCI_LINK_MANAGEMENT_PIPE: 818 /* We don't send Link Management commands, we only get them */ 819 if (nfa_hci_cb.type == NFA_HCI_COMMAND_TYPE) 820 nfa_hci_handle_link_mgm_gate_cmd (p); 821 break; 822 823 default: 824 if (pipe >= NFA_HCI_FIRST_DYNAMIC_PIPE) 825 nfa_hci_handle_dyn_pipe_pkt (pipe, p, pkt_len); 826 break; 827 } 828 829 if ((nfa_hci_cb.type == NFA_HCI_RESPONSE_TYPE) || (nfa_hci_cb.w4_rsp_evt && (nfa_hci_cb.type == NFA_HCI_EVENT_TYPE))) 830 { 831 nfa_hci_cb.w4_rsp_evt = FALSE; 832 } 833 834 /* Send a message to ouselves to check for anything to do */ 835 p_pkt->event = NFA_HCI_CHECK_QUEUE_EVT; 836 p_pkt->len = 0; 837 nfa_sys_sendmsg (p_pkt); 838} 839 840/******************************************************************************* 841** 842** Function nfa_hci_handle_nv_read 843** 844** Description handler function for nv read complete event 845** 846** Returns None 847** 848*******************************************************************************/ 849void nfa_hci_handle_nv_read (UINT8 block, tNFA_STATUS status) 850{ 851 UINT8 session_id[NFA_HCI_SESSION_ID_LEN]; 852 UINT8 default_session[NFA_HCI_SESSION_ID_LEN] = {0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF}; 853 UINT8 reset_session[NFA_HCI_SESSION_ID_LEN] = {0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00}; 854 UINT32 os_tick; 855 856 if (block == DH_NV_BLOCK) 857 { 858 /* Stop timer as NVDATA Read Completed */ 859 nfa_sys_stop_timer (&nfa_hci_cb.timer); 860 nfa_hci_cb.nv_read_cmplt = TRUE; 861 if ( (status != NFA_STATUS_OK) 862 ||(!nfa_hci_is_valid_cfg ()) 863 ||(!(memcmp (nfa_hci_cb.cfg.admin_gate.session_id, default_session, NFA_HCI_SESSION_ID_LEN))) 864 ||(!(memcmp (nfa_hci_cb.cfg.admin_gate.session_id, reset_session, NFA_HCI_SESSION_ID_LEN))) ) 865 { 866 nfa_hci_cb.b_hci_netwk_reset = TRUE; 867 /* Set a new session id so that we clear all pipes later after seeing a difference with the HC Session ID */ 868 memcpy (&session_id[(NFA_HCI_SESSION_ID_LEN / 2)], nfa_hci_cb.cfg.admin_gate.session_id, (NFA_HCI_SESSION_ID_LEN / 2)); 869 os_tick = GKI_get_os_tick_count (); 870 memcpy (session_id, (UINT8 *)&os_tick, (NFA_HCI_SESSION_ID_LEN / 2)); 871 nfa_hci_restore_default_config (session_id); 872 } 873 nfa_hci_startup (); 874 } 875} 876 877/******************************************************************************* 878** 879** Function nfa_hci_rsp_timeout 880** 881** Description action function to process timeout 882** 883** Returns None 884** 885*******************************************************************************/ 886void nfa_hci_rsp_timeout (tNFA_HCI_EVENT_DATA *p_evt_data) 887{ 888 tNFA_HCI_EVT evt = 0; 889 tNFA_HCI_EVT_DATA evt_data; 890 UINT8 delete_pipe; 891 892 NFA_TRACE_EVENT2 ("nfa_hci_rsp_timeout () State: %u Cmd: %u", nfa_hci_cb.hci_state, nfa_hci_cb.cmd_sent); 893 894 evt_data.status = NFA_STATUS_FAILED; 895 896 switch (nfa_hci_cb.hci_state) 897 { 898 case NFA_HCI_STATE_STARTUP: 899 case NFA_HCI_STATE_RESTORE: 900 NFA_TRACE_ERROR0 ("nfa_hci_rsp_timeout - Initialization failed!"); 901 nfa_hci_startup_complete (NFA_STATUS_TIMEOUT); 902 break; 903 904 case NFA_HCI_STATE_WAIT_NETWK_ENABLE: 905 case NFA_HCI_STATE_RESTORE_NETWK_ENABLE: 906 907 if (nfa_hci_cb.w4_hci_netwk_init) 908 { 909 /* HCI Network is enabled */ 910 nfa_hci_cb.w4_hci_netwk_init = FALSE; 911 nfa_hciu_send_get_param_cmd (NFA_HCI_ADMIN_PIPE, NFA_HCI_HOST_LIST_INDEX); 912 } 913 else 914 { 915 nfa_hci_startup_complete (NFA_STATUS_FAILED); 916 } 917 break; 918 919 case NFA_HCI_STATE_REMOVE_GATE: 920 /* Something wrong, NVRAM data could be corrupt */ 921 if (nfa_hci_cb.cmd_sent == NFA_HCI_ADM_DELETE_PIPE) 922 { 923 nfa_hciu_send_clear_all_pipe_cmd (); 924 } 925 else 926 { 927 nfa_hciu_remove_all_pipes_from_host (0); 928 nfa_hci_api_dealloc_gate (NULL); 929 } 930 break; 931 932 case NFA_HCI_STATE_APP_DEREGISTER: 933 /* Something wrong, NVRAM data could be corrupt */ 934 if (nfa_hci_cb.cmd_sent == NFA_HCI_ADM_DELETE_PIPE) 935 { 936 nfa_hciu_send_clear_all_pipe_cmd (); 937 } 938 else 939 { 940 nfa_hciu_remove_all_pipes_from_host (0); 941 nfa_hci_api_deregister (NULL); 942 } 943 break; 944 945 case NFA_HCI_STATE_WAIT_RSP: 946 nfa_hci_cb.hci_state = NFA_HCI_STATE_IDLE; 947 948 if (nfa_hci_cb.w4_rsp_evt) 949 { 950 nfa_hci_cb.w4_rsp_evt = FALSE; 951 evt = NFA_HCI_EVENT_RCVD_EVT; 952 evt_data.rcvd_evt.pipe = nfa_hci_cb.pipe_in_use; 953 evt_data.rcvd_evt.evt_code = 0; 954 evt_data.rcvd_evt.evt_len = 0; 955 evt_data.rcvd_evt.p_evt_buf = NULL; 956 nfa_hci_cb.rsp_buf_size = 0; 957 nfa_hci_cb.p_rsp_buf = NULL; 958 959 break; 960 } 961 962 delete_pipe = 0; 963 switch (nfa_hci_cb.cmd_sent) 964 { 965 case NFA_HCI_ANY_SET_PARAMETER: 966 /* 967 * As no response to the command sent on this pipe, we may assume the pipe is 968 * deleted already and release the pipe. But still send delete pipe command to be safe. 969 */ 970 delete_pipe = nfa_hci_cb.pipe_in_use; 971 evt_data.registry.pipe = nfa_hci_cb.pipe_in_use; 972 evt_data.registry.data_len = 0; 973 evt_data.registry.index = nfa_hci_cb.param_in_use; 974 evt = NFA_HCI_SET_REG_RSP_EVT; 975 break; 976 977 case NFA_HCI_ANY_GET_PARAMETER: 978 /* 979 * As no response to the command sent on this pipe, we may assume the pipe is 980 * deleted already and release the pipe. But still send delete pipe command to be safe. 981 */ 982 delete_pipe = nfa_hci_cb.pipe_in_use; 983 evt_data.registry.pipe = nfa_hci_cb.pipe_in_use; 984 evt_data.registry.data_len = 0; 985 evt_data.registry.index = nfa_hci_cb.param_in_use; 986 evt = NFA_HCI_GET_REG_RSP_EVT; 987 break; 988 989 case NFA_HCI_ANY_OPEN_PIPE: 990 /* 991 * As no response to the command sent on this pipe, we may assume the pipe is 992 * deleted already and release the pipe. But still send delete pipe command to be safe. 993 */ 994 delete_pipe = nfa_hci_cb.pipe_in_use; 995 evt_data.opened.pipe = nfa_hci_cb.pipe_in_use; 996 evt = NFA_HCI_OPEN_PIPE_EVT; 997 break; 998 999 case NFA_HCI_ANY_CLOSE_PIPE: 1000 /* 1001 * As no response to the command sent on this pipe, we may assume the pipe is 1002 * deleted already and release the pipe. But still send delete pipe command to be safe. 1003 */ 1004 delete_pipe = nfa_hci_cb.pipe_in_use; 1005 evt_data.closed.pipe = nfa_hci_cb.pipe_in_use; 1006 evt = NFA_HCI_CLOSE_PIPE_EVT; 1007 break; 1008 1009 case NFA_HCI_ADM_CREATE_PIPE: 1010 evt_data.created.pipe = nfa_hci_cb.pipe_in_use; 1011 evt_data.created.source_gate = nfa_hci_cb.local_gate_in_use; 1012 evt_data.created.dest_host = nfa_hci_cb.remote_host_in_use; 1013 evt_data.created.dest_gate = nfa_hci_cb.remote_gate_in_use; 1014 evt = NFA_HCI_CREATE_PIPE_EVT; 1015 break; 1016 1017 case NFA_HCI_ADM_DELETE_PIPE: 1018 /* 1019 * As no response to the command sent on this pipe, we may assume the pipe is 1020 * deleted already. Just release the pipe. 1021 */ 1022 if (nfa_hci_cb.pipe_in_use <= NFA_HCI_LAST_DYNAMIC_PIPE) 1023 nfa_hciu_release_pipe (nfa_hci_cb.pipe_in_use); 1024 evt_data.deleted.pipe = nfa_hci_cb.pipe_in_use; 1025 evt = NFA_HCI_DELETE_PIPE_EVT; 1026 break; 1027 1028 default: 1029 /* 1030 * As no response to the command sent on this pipe, we may assume the pipe is 1031 * deleted already and release the pipe. But still send delete pipe command to be safe. 1032 */ 1033 delete_pipe = nfa_hci_cb.pipe_in_use; 1034 break; 1035 } 1036 if (delete_pipe && (delete_pipe <= NFA_HCI_LAST_DYNAMIC_PIPE)) 1037 { 1038 nfa_hciu_send_delete_pipe_cmd (delete_pipe); 1039 nfa_hciu_release_pipe (delete_pipe); 1040 } 1041 break; 1042 case NFA_HCI_STATE_DISABLED: 1043 default: 1044 NFA_TRACE_DEBUG0 ("nfa_hci_rsp_timeout () Timeout in DISABLED/ Invalid state"); 1045 break; 1046 } 1047 if (evt != 0) 1048 nfa_hciu_send_to_app (evt, &evt_data, nfa_hci_cb.app_in_use); 1049} 1050 1051/******************************************************************************* 1052** 1053** Function nfa_hci_set_receive_buf 1054** 1055** Description Set reassembly buffer for incoming message 1056** 1057** Returns status 1058** 1059*******************************************************************************/ 1060static void nfa_hci_set_receive_buf (UINT8 pipe) 1061{ 1062 if ( (pipe >= NFA_HCI_FIRST_DYNAMIC_PIPE) 1063 &&(nfa_hci_cb.type == NFA_HCI_EVENT_TYPE) ) 1064 { 1065 if ( (nfa_hci_cb.rsp_buf_size) 1066 &&(nfa_hci_cb.p_rsp_buf != NULL) ) 1067 { 1068 nfa_hci_cb.p_msg_data = nfa_hci_cb.p_rsp_buf; 1069 nfa_hci_cb.max_msg_len = nfa_hci_cb.rsp_buf_size; 1070 return; 1071 } 1072 } 1073 nfa_hci_cb.p_msg_data = nfa_hci_cb.msg_data; 1074 nfa_hci_cb.max_msg_len = NFA_MAX_HCI_EVENT_LEN; 1075} 1076 1077/******************************************************************************* 1078** 1079** Function nfa_hci_assemble_msg 1080** 1081** Description Reassemble the incoming message 1082** 1083** Returns None 1084** 1085*******************************************************************************/ 1086static void nfa_hci_assemble_msg (UINT8 *p_data, UINT16 data_len) 1087{ 1088 if ((nfa_hci_cb.msg_len + data_len) > nfa_hci_cb.max_msg_len) 1089 { 1090 /* Fill the buffer as much it can hold */ 1091 memcpy (&nfa_hci_cb.p_msg_data[nfa_hci_cb.msg_len], p_data, (nfa_hci_cb.max_msg_len - nfa_hci_cb.msg_len)); 1092 nfa_hci_cb.msg_len = nfa_hci_cb.max_msg_len; 1093 /* Set Reassembly failed */ 1094 nfa_hci_cb.assembly_failed = TRUE; 1095 NFA_TRACE_ERROR1 ("nfa_hci_assemble_msg (): Insufficient buffer to Reassemble HCP packet! Dropping :%u bytes", ((nfa_hci_cb.msg_len + data_len) - nfa_hci_cb.max_msg_len)); 1096 } 1097 else 1098 { 1099 memcpy (&nfa_hci_cb.p_msg_data[nfa_hci_cb.msg_len], p_data, data_len); 1100 nfa_hci_cb.msg_len += data_len; 1101 } 1102} 1103 1104/******************************************************************************* 1105** 1106** Function nfa_hci_evt_hdlr 1107** 1108** Description Processing all event for NFA HCI 1109** 1110** Returns TRUE if p_msg needs to be deallocated 1111** 1112*******************************************************************************/ 1113static BOOLEAN nfa_hci_evt_hdlr (BT_HDR *p_msg) 1114{ 1115 tNFA_HCI_EVENT_DATA *p_evt_data = (tNFA_HCI_EVENT_DATA *)p_msg; 1116 1117#if (BT_TRACE_VERBOSE == TRUE) 1118 NFA_TRACE_EVENT4 ("nfa_hci_evt_hdlr state: %s (%d) event: %s (0x%04x)", 1119 nfa_hciu_get_state_name (nfa_hci_cb.hci_state), nfa_hci_cb.hci_state, 1120 nfa_hciu_get_event_name (p_evt_data->hdr.event), p_evt_data->hdr.event); 1121#else 1122 NFA_TRACE_EVENT2 ("nfa_hci_evt_hdlr state: %d event: 0x%04x", nfa_hci_cb.hci_state, p_evt_data->hdr.event); 1123#endif 1124 1125 /* If this is an API request, queue it up */ 1126 if ((p_msg->event >= NFA_HCI_FIRST_API_EVENT) && (p_msg->event <= NFA_HCI_LAST_API_EVENT)) 1127 { 1128 GKI_enqueue (&nfa_hci_cb.hci_api_q, p_msg); 1129 } 1130 else 1131 { 1132 switch (p_msg->event) 1133 { 1134 case NFA_HCI_RSP_NV_READ_EVT: 1135 nfa_hci_handle_nv_read (p_evt_data->nv_read.block, p_evt_data->nv_read.status); 1136 break; 1137 1138 case NFA_HCI_RSP_NV_WRITE_EVT: 1139 /* NV Ram write completed - nothing to do... */ 1140 break; 1141 1142 case NFA_HCI_RSP_TIMEOUT_EVT: 1143 nfa_hci_rsp_timeout ((tNFA_HCI_EVENT_DATA *)p_msg); 1144 break; 1145 1146 case NFA_HCI_CHECK_QUEUE_EVT: 1147 if (HCI_LOOPBACK_DEBUG) 1148 { 1149 if (p_msg->len != 0) 1150 { 1151 tNFC_DATA_CEVT xx; 1152 xx.p_data = p_msg; 1153 nfa_hci_conn_cback (0, NFC_DATA_CEVT, (tNFC_CONN *)&xx); 1154 return FALSE; 1155 } 1156 } 1157 break; 1158 } 1159 } 1160 1161 if ((p_msg->event > NFA_HCI_LAST_API_EVENT)) 1162 GKI_freebuf (p_msg); 1163 1164 nfa_hci_check_api_requests (); 1165 1166 if (nfa_hciu_is_no_host_resetting ()) 1167 nfa_hci_check_pending_api_requests (); 1168 1169 if ((nfa_hci_cb.hci_state == NFA_HCI_STATE_IDLE) && (nfa_hci_cb.nv_write_needed)) 1170 { 1171 nfa_hci_cb.nv_write_needed = FALSE; 1172 nfa_nv_co_write ((UINT8 *)&nfa_hci_cb.cfg, sizeof (nfa_hci_cb.cfg),DH_NV_BLOCK); 1173 } 1174 1175 return FALSE; 1176} 1177 1178