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 file contains the utility functions for the NFA HCI. 23 * 24 ******************************************************************************/ 25 #include <string.h> 26 #include "trace_api.h" 27 #include "nfc_api.h" 28 #include "nfa_sys.h" 29 #include "nfa_sys_int.h" 30 #include "nfa_dm_int.h" 31 #include "nfa_hci_api.h" 32 #include "nfa_hci_int.h" 33 #include "nfa_nv_co.h" 34 #include "nfa_mem_co.h" 35 #include "nfa_hci_defs.h" 36 37 static void handle_debug_loopback (BT_HDR *p_buf, UINT8 pipe, UINT8 type, UINT8 instruction); 38 BOOLEAN HCI_LOOPBACK_DEBUG = FALSE; 39 40 /******************************************************************************* 41 ** 42 ** Function nfa_hciu_find_pipe_by_pid 43 ** 44 ** Description look for the pipe control block based on pipe id 45 ** 46 ** Returns pointer to the pipe control block, or NULL if not found 47 ** 48 *******************************************************************************/ 49 tNFA_HCI_DYN_PIPE *nfa_hciu_find_pipe_by_pid (UINT8 pipe_id) 50 { 51 tNFA_HCI_DYN_PIPE *pp = nfa_hci_cb.cfg.dyn_pipes; 52 int xx = 0; 53 54 /* Loop through looking for a match */ 55 for ( ; xx < NFA_HCI_MAX_PIPE_CB; xx++, pp++) 56 { 57 if (pp->pipe_id == pipe_id) 58 return (pp); 59 } 60 61 /* If here, not found */ 62 return (NULL); 63 } 64 65 /******************************************************************************* 66 ** 67 ** Function nfa_hciu_find_gate_by_gid 68 ** 69 ** Description Find the gate control block for the given gate id 70 ** 71 ** Returns pointer to the gate control block, or NULL if not found 72 ** 73 *******************************************************************************/ 74 tNFA_HCI_DYN_GATE *nfa_hciu_find_gate_by_gid (UINT8 gate_id) 75 { 76 tNFA_HCI_DYN_GATE *pg = nfa_hci_cb.cfg.dyn_gates; 77 int xx = 0; 78 79 for ( ; xx < NFA_HCI_MAX_GATE_CB; xx++, pg++) 80 { 81 if (pg->gate_id == gate_id) 82 return (pg); 83 } 84 85 return (NULL); 86 } 87 88 /******************************************************************************* 89 ** 90 ** Function nfa_hciu_find_gate_by_owner 91 ** 92 ** Description Find the the first gate control block for the given owner 93 ** 94 ** Returns pointer to the gate control block, or NULL if not found 95 ** 96 *******************************************************************************/ 97 tNFA_HCI_DYN_GATE *nfa_hciu_find_gate_by_owner (tNFA_HANDLE app_handle) 98 { 99 tNFA_HCI_DYN_GATE *pg = nfa_hci_cb.cfg.dyn_gates; 100 int xx = 0; 101 102 for ( ; xx < NFA_HCI_MAX_GATE_CB; xx++, pg++) 103 { 104 if (pg->gate_owner == app_handle) 105 return (pg); 106 } 107 108 return (NULL); 109 } 110 111 /******************************************************************************* 112 ** 113 ** Function nfa_hciu_find_gate_with_nopipes_by_owner 114 ** 115 ** Description Find the the first gate control block with no pipes 116 ** for the given owner 117 ** 118 ** Returns pointer to the gate control block, or NULL if not found 119 ** 120 *******************************************************************************/ 121 tNFA_HCI_DYN_GATE *nfa_hciu_find_gate_with_nopipes_by_owner (tNFA_HANDLE app_handle) 122 { 123 tNFA_HCI_DYN_GATE *pg = nfa_hci_cb.cfg.dyn_gates; 124 int xx = 0; 125 126 for ( ; xx < NFA_HCI_MAX_GATE_CB; xx++, pg++) 127 { 128 if ( (pg->gate_owner == app_handle) 129 &&(pg->pipe_inx_mask == 0) ) 130 return (pg); 131 } 132 133 return (NULL); 134 } 135 136 /******************************************************************************* 137 ** 138 ** Function nfa_hciu_count_pipes_on_gate 139 ** 140 ** Description Count the number of pipes on the given gate 141 ** 142 ** Returns the number of pipes on the gate 143 ** 144 *******************************************************************************/ 145 UINT8 nfa_hciu_count_pipes_on_gate (tNFA_HCI_DYN_GATE *p_gate) 146 { 147 int xx = 0; 148 UINT32 mask = 1; 149 UINT8 count = 0; 150 151 for ( ; xx < NFA_HCI_MAX_PIPE_CB; xx++) 152 { 153 if ( p_gate->pipe_inx_mask & mask ) 154 count++; 155 156 mask = mask << 1; 157 } 158 159 return (count); 160 } 161 162 /******************************************************************************* 163 ** 164 ** Function nfa_hciu_count_open_pipes_on_gate 165 ** 166 ** Description Count the number of opened pipes on the given gate 167 ** 168 ** Returns the number of pipes in OPENED state on the gate 169 ** 170 *******************************************************************************/ 171 UINT8 nfa_hciu_count_open_pipes_on_gate (tNFA_HCI_DYN_GATE *p_gate) 172 { 173 tNFA_HCI_DYN_PIPE *pp = nfa_hci_cb.cfg.dyn_pipes; 174 int xx = 0; 175 UINT32 mask = 1; 176 UINT8 count = 0; 177 178 for ( ; xx < NFA_HCI_MAX_PIPE_CB; xx++, pp++) 179 { 180 /* For each pipe on this gate, check if it is open */ 181 if ((p_gate->pipe_inx_mask & mask) && (pp->pipe_state == NFA_HCI_PIPE_OPENED)) 182 count++; 183 184 mask = mask << 1; 185 } 186 187 return (count); 188 } 189 190 /******************************************************************************* 191 ** 192 ** Function nfa_hciu_get_gate_owner 193 ** 194 ** Description Find the application that owns a gate 195 ** 196 ** Returns application handle 197 ** 198 *******************************************************************************/ 199 tNFA_HANDLE nfa_hciu_get_gate_owner (UINT8 gate_id) 200 { 201 tNFA_HCI_DYN_GATE *pg; 202 203 if ((pg = nfa_hciu_find_gate_by_gid (gate_id)) == NULL) 204 return (NFA_HANDLE_INVALID); 205 206 return (pg->gate_owner); 207 } 208 209 /******************************************************************************* 210 ** 211 ** Function nfa_hciu_get_pipe_owner 212 ** 213 ** Description Find the application that owns a pipe 214 ** 215 ** Returns application handle 216 ** 217 *******************************************************************************/ 218 tNFA_HANDLE nfa_hciu_get_pipe_owner (UINT8 pipe_id) 219 { 220 tNFA_HCI_DYN_PIPE *pp; 221 tNFA_HCI_DYN_GATE *pg; 222 223 if ((pp = nfa_hciu_find_pipe_by_pid (pipe_id)) == NULL) 224 return (NFA_HANDLE_INVALID); 225 226 if ((pg = nfa_hciu_find_gate_by_gid (pp->local_gate)) == NULL) 227 return (NFA_HANDLE_INVALID); 228 229 return (pg->gate_owner); 230 } 231 232 233 /******************************************************************************* 234 ** 235 ** Function nfa_hciu_alloc_gate 236 ** 237 ** Description Allocate an gate control block 238 ** 239 ** Returns pointer to the allocated gate, or NULL if cannot allocate 240 ** 241 *******************************************************************************/ 242 tNFA_HCI_DYN_GATE *nfa_hciu_alloc_gate (UINT8 gate_id, tNFA_HANDLE app_handle) 243 { 244 tNFA_HCI_DYN_GATE *pg; 245 int xx; 246 UINT8 app_inx = app_handle & NFA_HANDLE_MASK; 247 248 249 /* First, check if the application handle is valid */ 250 if ( (gate_id != NFA_HCI_CONNECTIVITY_GATE) 251 &&(gate_id < NFA_HCI_FIRST_PROP_GATE) 252 &&(( (app_handle & NFA_HANDLE_GROUP_MASK) != NFA_HANDLE_GROUP_HCI) 253 ||(app_inx >= NFA_HCI_MAX_APP_CB) 254 ||(nfa_hci_cb.p_app_cback[app_inx] == NULL)) ) 255 { 256 return (NULL); 257 } 258 259 if (gate_id != 0) 260 { 261 if ((pg = nfa_hciu_find_gate_by_gid (gate_id)) != NULL) 262 return (pg); 263 } 264 else 265 { 266 /* If gate_id is 0, we need to assign a free one */ 267 /* Loop through all possible gate IDs checking if they are already used */ 268 for (gate_id = NFA_HCI_FIRST_HOST_SPECIFIC_GENERIC_GATE; gate_id <= NFA_HCI_LAST_PROP_GATE; gate_id++) 269 { 270 /* Skip connectivity gate */ 271 if (gate_id == NFA_HCI_CONNECTIVITY_GATE) gate_id++; 272 273 /* Check if the gate is already allocated */ 274 if (nfa_hciu_find_gate_by_gid (gate_id) == NULL) 275 break; 276 } 277 if (gate_id > NFA_HCI_LAST_PROP_GATE) 278 { 279 NFA_TRACE_ERROR2 ("nfa_hci_alloc_gate - no free Gate ID: %u App Handle: 0x%04x", gate_id, app_handle); 280 return (NULL); 281 } 282 } 283 284 /* Now look for a free control block */ 285 for (xx = 0, pg = nfa_hci_cb.cfg.dyn_gates; xx < NFA_HCI_MAX_GATE_CB; xx++, pg++) 286 { 287 if (pg->gate_id == 0) 288 { 289 /* Found a free gate control block */ 290 pg->gate_id = gate_id; 291 pg->gate_owner = app_handle; 292 pg->pipe_inx_mask = 0; 293 294 NFA_TRACE_DEBUG2 ("nfa_hciu_alloc_gate id:%d app_handle: 0x%04x", gate_id, app_handle); 295 296 nfa_hci_cb.nv_write_needed = TRUE; 297 return (pg); 298 } 299 } 300 301 /* If here, no free gate control block */ 302 NFA_TRACE_ERROR2 ("nfa_hci_alloc_gate - no CB Gate ID: %u App Handle: 0x%04x", gate_id, app_handle); 303 return (NULL); 304 } 305 306 /******************************************************************************* 307 ** 308 ** Function nfa_hciu_send_msg 309 ** 310 ** Description This function will fragment the given packet, if necessary 311 ** and send it on the given pipe. 312 ** 313 ** Returns status 314 ** 315 *******************************************************************************/ 316 tNFA_STATUS nfa_hciu_send_msg (UINT8 pipe_id, UINT8 type, UINT8 instruction, UINT16 msg_len, UINT8 *p_msg) 317 { 318 BT_HDR *p_buf; 319 UINT8 *p_data; 320 BOOLEAN first_pkt = TRUE; 321 UINT16 data_len; 322 tNFA_STATUS status = NFA_STATUS_OK; 323 UINT16 max_seg_hcp_pkt_size = nfa_hci_cb.buff_size - NCI_DATA_HDR_SIZE; 324 325 #if (BT_TRACE_VERBOSE == TRUE) 326 char buff[100]; 327 328 NFA_TRACE_DEBUG3 ("nfa_hciu_send_msg pipe_id:%d %s len:%d", 329 pipe_id, nfa_hciu_get_type_inst_names (pipe_id, type, instruction, buff), msg_len); 330 #else 331 NFA_TRACE_DEBUG4 ("nfa_hciu_send_msg pipe_id:%d Type: %u Inst: %u len: %d", 332 pipe_id, type, instruction, msg_len); 333 #endif 334 335 if (instruction == NFA_HCI_ANY_GET_PARAMETER) 336 nfa_hci_cb.param_in_use = *p_msg; 337 338 while ((first_pkt == TRUE) || (msg_len != 0)) 339 { 340 if ((p_buf = (BT_HDR *) GKI_getpoolbuf (NFC_RW_POOL_ID)) != NULL) 341 { 342 p_buf->offset = NCI_MSG_OFFSET_SIZE + NCI_DATA_HDR_SIZE; 343 344 /* First packet has a 2-byte header, subsequent fragments have a 1-byte header */ 345 data_len = first_pkt ? (max_seg_hcp_pkt_size - 2) : (max_seg_hcp_pkt_size - 1); 346 347 p_data = (UINT8 *) (p_buf + 1) + p_buf->offset; 348 349 /* Last or only segment has "no fragmentation" bit set */ 350 if (msg_len > data_len) 351 { 352 *p_data++ = (NFA_HCI_MESSAGE_FRAGMENTATION << 7) | (pipe_id & 0x7F); 353 } 354 else 355 { 356 data_len = msg_len; 357 *p_data++ = (NFA_HCI_NO_MESSAGE_FRAGMENTATION << 7) | (pipe_id & 0x7F); 358 } 359 360 p_buf->len = 1; 361 362 /* Message header only goes in the first segment */ 363 if (first_pkt) 364 { 365 first_pkt = FALSE; 366 *p_data++ = (type << 6) | instruction; 367 p_buf->len++; 368 } 369 370 if (data_len != 0) 371 { 372 memcpy (p_data, p_msg, data_len); 373 374 p_buf->len += data_len; 375 msg_len -= data_len; 376 if (msg_len > 0) 377 p_msg += data_len; 378 } 379 380 #if (BT_TRACE_PROTOCOL == TRUE) 381 DispHcp (((UINT8 *) (p_buf + 1) + p_buf->offset), p_buf->len, FALSE, (BOOLEAN) ((p_buf->len - data_len) == 2)); 382 #endif 383 384 if (HCI_LOOPBACK_DEBUG) 385 handle_debug_loopback (p_buf, pipe_id, type, instruction); 386 else 387 status = NFC_SendData (nfa_hci_cb.conn_id, p_buf); 388 } 389 else 390 { 391 NFA_TRACE_ERROR0 ("nfa_hciu_send_data_packet no buffers"); 392 status = NFA_STATUS_NO_BUFFERS; 393 break; 394 } 395 } 396 397 /* Start timer if response to wait for a particular time for the response */ 398 if (type == NFA_HCI_COMMAND_TYPE) 399 { 400 nfa_hci_cb.cmd_sent = instruction; 401 402 if (nfa_hci_cb.hci_state == NFA_HCI_STATE_IDLE) 403 nfa_hci_cb.hci_state = NFA_HCI_STATE_WAIT_RSP; 404 405 nfa_sys_start_timer (&nfa_hci_cb.timer, NFA_HCI_RSP_TIMEOUT_EVT, p_nfa_hci_cfg->hcp_response_timeout); 406 } 407 408 return status; 409 } 410 411 /******************************************************************************* 412 ** 413 ** Function nfa_hciu_get_allocated_gate_list 414 ** 415 ** Description fills in a list of allocated gates 416 ** 417 ** Returns the number of gates 418 ** 419 *******************************************************************************/ 420 UINT8 nfa_hciu_get_allocated_gate_list (UINT8 *p_gate_list) 421 { 422 tNFA_HCI_DYN_GATE *p_cb; 423 int xx; 424 UINT8 count = 0; 425 426 for (xx = 0, p_cb = nfa_hci_cb.cfg.dyn_gates; xx < NFA_HCI_MAX_GATE_CB; xx++, p_cb++) 427 { 428 if (p_cb->gate_id != 0) 429 { 430 *p_gate_list++ = p_cb->gate_id; 431 count++; 432 } 433 } 434 435 NFA_TRACE_DEBUG1 ("nfa_hciu_get_allocated_gate_list () returns: %u", count); 436 437 return (count); 438 } 439 440 /******************************************************************************* 441 ** 442 ** Function nfa_hciu_alloc_pipe 443 ** 444 ** Description Allocate a pipe control block 445 ** 446 ** Returns pointer to the pipe control block, or NULL if 447 ** cannot allocate 448 ** 449 *******************************************************************************/ 450 tNFA_HCI_DYN_PIPE *nfa_hciu_alloc_pipe (UINT8 pipe_id) 451 { 452 UINT8 xx; 453 tNFA_HCI_DYN_PIPE *pp; 454 455 /* If we already have a pipe of the same ID, release it first it */ 456 if ((pp = nfa_hciu_find_pipe_by_pid (pipe_id)) != NULL) 457 { 458 if (pipe_id > NFA_HCI_LAST_DYNAMIC_PIPE) 459 return pp; 460 nfa_hciu_release_pipe (pipe_id); 461 } 462 463 /* Look for a free pipe control block */ 464 for (xx = 0, pp = nfa_hci_cb.cfg.dyn_pipes ; xx < NFA_HCI_MAX_PIPE_CB; xx++, pp++) 465 { 466 if (pp->pipe_id == 0) 467 { 468 NFA_TRACE_DEBUG2 ("nfa_hciu_alloc_pipe:%d, index:%d", pipe_id, xx); 469 pp->pipe_id = pipe_id; 470 471 nfa_hci_cb.nv_write_needed = TRUE; 472 return (pp); 473 } 474 } 475 476 NFA_TRACE_DEBUG1 ("nfa_hciu_alloc_pipe:%d, NO free entries !!", pipe_id); 477 return (NULL); 478 } 479 480 /******************************************************************************* 481 ** 482 ** Function nfa_hciu_release_gate 483 ** 484 ** Description Remove a generic gate from gate list 485 ** 486 ** Returns none 487 ** 488 *******************************************************************************/ 489 void nfa_hciu_release_gate (UINT8 gate_id) 490 { 491 tNFA_HCI_DYN_GATE *p_gate = nfa_hciu_find_gate_by_gid (gate_id); 492 493 if (p_gate != NULL) 494 { 495 NFA_TRACE_DEBUG3 ("nfa_hciu_release_gate () ID: %d owner: 0x%04x pipe_inx_mask: 0x%04x", 496 gate_id, p_gate->gate_owner, p_gate->pipe_inx_mask); 497 498 p_gate->gate_id = 0; 499 p_gate->gate_owner = 0; 500 p_gate->pipe_inx_mask = 0; 501 502 nfa_hci_cb.nv_write_needed = TRUE; 503 } 504 else 505 { 506 NFA_TRACE_WARNING1 ("nfa_hciu_release_gate () ID: %d NOT FOUND", gate_id); 507 } 508 } 509 510 /******************************************************************************* 511 ** 512 ** Function nfa_hciu_add_pipe_to_gate 513 ** 514 ** Description Add pipe to generic gate 515 ** 516 ** Returns NFA_STATUS_OK, if successfully add the pipe on to the gate 517 ** NFA_HCI_ADM_E_NO_PIPES_AVAILABLE, otherwise 518 ** 519 *******************************************************************************/ 520 tNFA_HCI_RESPONSE nfa_hciu_add_pipe_to_gate (UINT8 pipe_id, UINT8 local_gate, 521 UINT8 dest_host, UINT8 dest_gate) 522 { 523 tNFA_HCI_DYN_GATE *p_gate; 524 tNFA_HCI_DYN_PIPE *p_pipe; 525 UINT8 pipe_index; 526 527 p_gate = nfa_hciu_find_gate_by_gid (local_gate); 528 529 if (p_gate != NULL) 530 { 531 /* Allocate a pipe control block */ 532 if ((p_pipe = nfa_hciu_alloc_pipe (pipe_id)) != NULL) 533 { 534 p_pipe->pipe_id = pipe_id; 535 p_pipe->pipe_state = NFA_HCI_PIPE_CLOSED; 536 p_pipe->dest_host = dest_host; 537 p_pipe->dest_gate = dest_gate; 538 p_pipe->local_gate = local_gate; 539 540 /* Save the pipe in the gate that it belongs to */ 541 pipe_index = (UINT8) (p_pipe - nfa_hci_cb.cfg.dyn_pipes); 542 p_gate->pipe_inx_mask |= (UINT32) (1 << pipe_index); 543 544 NFA_TRACE_DEBUG4 ("nfa_hciu_add_pipe_to_gate Gate ID: 0x%02x Pipe ID: 0x%02x pipe_index: %u App Handle: 0x%08x", 545 local_gate, pipe_id, pipe_index, p_gate->gate_owner); 546 return (NFA_HCI_ANY_OK); 547 } 548 } 549 550 NFA_TRACE_DEBUG1 ("nfa_hciu_add_pipe_to_gate: 0x%02x NOT FOUND", local_gate); 551 552 return (NFA_HCI_ADM_E_NO_PIPES_AVAILABLE); 553 } 554 555 /******************************************************************************* 556 ** 557 ** Function nfa_hciu_add_pipe_to_static_gate 558 ** 559 ** Description Add pipe to identity management gate 560 ** 561 ** Returns NFA_HCI_ANY_OK, if successfully add the pipe on to the gate 562 ** NFA_HCI_ADM_E_NO_PIPES_AVAILABLE, otherwise 563 ** 564 *******************************************************************************/ 565 tNFA_HCI_RESPONSE nfa_hciu_add_pipe_to_static_gate (UINT8 local_gate, UINT8 pipe_id, UINT8 dest_host, UINT8 dest_gate) 566 { 567 tNFA_HCI_DYN_PIPE *p_pipe; 568 UINT8 pipe_index; 569 570 NFA_TRACE_EVENT4 ("nfa_hciu_add_pipe_to_static_gate (%u) Pipe: 0x%02x Dest Host: 0x%02x Dest Gate: 0x%02x)", 571 local_gate, pipe_id, dest_host, dest_gate); 572 573 /* Allocate a pipe control block */ 574 if ((p_pipe = nfa_hciu_alloc_pipe (pipe_id)) != NULL) 575 { 576 p_pipe->pipe_id = pipe_id; 577 p_pipe->pipe_state = NFA_HCI_PIPE_CLOSED; 578 p_pipe->dest_host = dest_host; 579 p_pipe->dest_gate = dest_gate; 580 p_pipe->local_gate = local_gate; 581 582 /* If this is the ID gate, save the pipe index in the ID gate info */ 583 /* block. Note that for loopback, it is enough to just create the pipe */ 584 if (local_gate == NFA_HCI_IDENTITY_MANAGEMENT_GATE) 585 { 586 pipe_index = (UINT8) (p_pipe - nfa_hci_cb.cfg.dyn_pipes); 587 nfa_hci_cb.cfg.id_mgmt_gate.pipe_inx_mask |= (UINT32) (1 << pipe_index); 588 } 589 return NFA_HCI_ANY_OK; 590 } 591 592 return NFA_HCI_ADM_E_NO_PIPES_AVAILABLE; 593 } 594 595 /******************************************************************************* 596 ** 597 ** Function nfa_hciu_find_active_pipe_by_owner 598 ** 599 ** Description Find the first pipe associated with the given app 600 ** 601 ** Returns pointer to pipe, or NULL if none found 602 ** 603 *******************************************************************************/ 604 tNFA_HCI_DYN_PIPE *nfa_hciu_find_active_pipe_by_owner (tNFA_HANDLE app_handle) 605 { 606 tNFA_HCI_DYN_GATE *pg; 607 tNFA_HCI_DYN_PIPE *pp; 608 int xx; 609 610 NFA_TRACE_DEBUG1 ("nfa_hciu_find_pipe_by_owner () app_handle:0x%x", app_handle); 611 612 /* Loop through all pipes looking for the owner */ 613 for (xx = 0, pp = nfa_hci_cb.cfg.dyn_pipes; xx < NFA_HCI_MAX_PIPE_CB; xx++, pp++) 614 { 615 if ( (pp->pipe_id != 0) 616 &&(pp->pipe_id >= NFA_HCI_FIRST_DYNAMIC_PIPE) 617 &&(pp->pipe_id <= NFA_HCI_LAST_DYNAMIC_PIPE) 618 &&(nfa_hciu_is_active_host (pp->dest_host)) ) 619 { 620 if ( ((pg = nfa_hciu_find_gate_by_gid (pp->local_gate)) != NULL) 621 &&(pg->gate_owner == app_handle) ) 622 return (pp); 623 } 624 } 625 626 /* If here, not found */ 627 return (NULL); 628 } 629 630 /******************************************************************************* 631 ** 632 ** Function nfa_hciu_check_pipe_between_gates 633 ** 634 ** Description Check if there is a pipe between specified Terminal host 635 ** gate and and the specified UICC gate 636 ** 637 ** Returns TRUE, if there exists a pipe between the two specified gated 638 ** FALSE, otherwise 639 ** 640 *******************************************************************************/ 641 BOOLEAN nfa_hciu_check_pipe_between_gates (UINT8 local_gate, UINT8 dest_host, UINT8 dest_gate) 642 { 643 tNFA_HCI_DYN_PIPE *pp; 644 int xx; 645 646 NFA_TRACE_DEBUG3 ("nfa_hciu_check_pipe_between_gates () Local gate: 0x%02X, Host[0x%02X] gate: 0x%02X", local_gate, dest_host, dest_gate); 647 648 /* Loop through all pipes looking for the owner */ 649 for (xx = 0, pp = nfa_hci_cb.cfg.dyn_pipes; xx < NFA_HCI_MAX_PIPE_CB; xx++, pp++) 650 { 651 if ( (pp->pipe_id != 0) 652 &&(pp->pipe_id >= NFA_HCI_FIRST_DYNAMIC_PIPE) 653 &&(pp->pipe_id <= NFA_HCI_LAST_DYNAMIC_PIPE) 654 &&(pp->local_gate == local_gate) 655 &&(pp->dest_host == dest_host) 656 &&(pp->dest_gate == dest_gate) ) 657 { 658 return (TRUE); 659 } 660 } 661 662 /* If here, not found */ 663 return (FALSE); 664 } 665 666 /******************************************************************************* 667 ** 668 ** Function nfa_hciu_find_pipe_by_owner 669 ** 670 ** Description Find the first pipe associated with the given app 671 ** 672 ** Returns pointer to pipe, or NULL if none found 673 ** 674 *******************************************************************************/ 675 tNFA_HCI_DYN_PIPE *nfa_hciu_find_pipe_by_owner (tNFA_HANDLE app_handle) 676 { 677 tNFA_HCI_DYN_GATE *pg; 678 tNFA_HCI_DYN_PIPE *pp; 679 int xx; 680 681 NFA_TRACE_DEBUG1 ("nfa_hciu_find_pipe_by_owner () app_handle:0x%x", app_handle); 682 683 /* Loop through all pipes looking for the owner */ 684 for (xx = 0, pp = nfa_hci_cb.cfg.dyn_pipes; xx < NFA_HCI_MAX_PIPE_CB; xx++, pp++) 685 { 686 if (pp->pipe_id != 0) 687 { 688 if ( ((pg = nfa_hciu_find_gate_by_gid (pp->local_gate)) != NULL) 689 &&(pg->gate_owner == app_handle) ) 690 return (pp); 691 } 692 } 693 694 /* If here, not found */ 695 return (NULL); 696 } 697 698 /******************************************************************************* 699 ** 700 ** Function nfa_hciu_find_pipe_on_gate 701 ** 702 ** Description Find the first pipe associated with the given gate 703 ** 704 ** Returns pointer to pipe, or NULL if none found 705 ** 706 *******************************************************************************/ 707 tNFA_HCI_DYN_PIPE *nfa_hciu_find_pipe_on_gate (UINT8 gate_id) 708 { 709 tNFA_HCI_DYN_GATE *pg; 710 tNFA_HCI_DYN_PIPE *pp; 711 int xx; 712 713 NFA_TRACE_DEBUG1 ("nfa_hciu_find_pipe_on_gate () Gate:0x%x", gate_id); 714 715 /* Loop through all pipes looking for the owner */ 716 for (xx = 0, pp = nfa_hci_cb.cfg.dyn_pipes; xx < NFA_HCI_MAX_PIPE_CB; xx++, pp++) 717 { 718 if (pp->pipe_id != 0) 719 { 720 if ( ((pg = nfa_hciu_find_gate_by_gid (pp->local_gate)) != NULL) 721 &&(pg->gate_id == gate_id) ) 722 return (pp); 723 } 724 } 725 726 /* If here, not found */ 727 return (NULL); 728 } 729 730 /******************************************************************************* 731 ** 732 ** Function nfa_hciu_is_active_host 733 ** 734 ** Description Check if the host is currently active 735 ** 736 ** Returns TRUE, if the host is active in the host network 737 ** FALSE, if the host is not active in the host network 738 ** 739 *******************************************************************************/ 740 BOOLEAN nfa_hciu_is_active_host (UINT8 host_id) 741 { 742 UINT8 xx; 743 744 for (xx = 0; xx < NFA_HCI_MAX_HOST_IN_NETWORK; xx++) 745 { 746 if (nfa_hci_cb.inactive_host[xx] == host_id) 747 return FALSE; 748 } 749 750 return TRUE; 751 } 752 753 /******************************************************************************* 754 ** 755 ** Function nfa_hciu_is_host_reseting 756 ** 757 ** Description Check if the host is currently reseting 758 ** 759 ** Returns TRUE, if the host is reseting 760 ** FALSE, if the host is not reseting 761 ** 762 *******************************************************************************/ 763 BOOLEAN nfa_hciu_is_host_reseting (UINT8 host_id) 764 { 765 UINT8 xx; 766 767 for (xx = 0; xx < NFA_HCI_MAX_HOST_IN_NETWORK; xx++) 768 { 769 if (nfa_hci_cb.reset_host[xx] == host_id) 770 return TRUE; 771 } 772 773 return FALSE; 774 } 775 776 /******************************************************************************* 777 ** 778 ** Function nfa_hciu_is_no_host_resetting 779 ** 780 ** Description Check if no host is reseting 781 ** 782 ** Returns TRUE, if no host is resetting at this time 783 ** FALSE, if one or more host is resetting 784 ** 785 *******************************************************************************/ 786 BOOLEAN nfa_hciu_is_no_host_resetting (void) 787 { 788 UINT8 xx; 789 790 for (xx = 0; xx < NFA_HCI_MAX_HOST_IN_NETWORK; xx++) 791 { 792 if (nfa_hci_cb.reset_host[xx] != 0) 793 return FALSE; 794 } 795 796 return TRUE; 797 } 798 799 /******************************************************************************* 800 ** 801 ** Function nfa_hciu_find_active_pipe_on_gate 802 ** 803 ** Description Find the first active pipe associated with the given gate 804 ** 805 ** Returns pointer to pipe, or NULL if none found 806 ** 807 *******************************************************************************/ 808 tNFA_HCI_DYN_PIPE *nfa_hciu_find_active_pipe_on_gate (UINT8 gate_id) 809 { 810 tNFA_HCI_DYN_GATE *pg; 811 tNFA_HCI_DYN_PIPE *pp; 812 int xx; 813 814 NFA_TRACE_DEBUG1 ("nfa_hciu_find_active_pipe_on_gate () Gate:0x%x", gate_id); 815 816 /* Loop through all pipes looking for the owner */ 817 for (xx = 0, pp = nfa_hci_cb.cfg.dyn_pipes; xx < NFA_HCI_MAX_PIPE_CB; xx++, pp++) 818 { 819 if ( (pp->pipe_id != 0) 820 &&(pp->pipe_id >= NFA_HCI_FIRST_DYNAMIC_PIPE) 821 &&(pp->pipe_id <= NFA_HCI_LAST_DYNAMIC_PIPE) 822 &&(nfa_hciu_is_active_host (pp->dest_host)) ) 823 { 824 if ( ((pg = nfa_hciu_find_gate_by_gid (pp->local_gate)) != NULL) 825 &&(pg->gate_id == gate_id) ) 826 return (pp); 827 } 828 } 829 830 /* If here, not found */ 831 return (NULL); 832 } 833 834 /******************************************************************************* 835 ** 836 ** Function nfa_hciu_release_pipe 837 ** 838 ** Description remove the specified pipe 839 ** 840 ** Returns NFA_HCI_ANY_OK, if removed 841 ** NFA_HCI_ANY_E_NOK, if otherwise 842 ** 843 *******************************************************************************/ 844 tNFA_HCI_RESPONSE nfa_hciu_release_pipe (UINT8 pipe_id) 845 { 846 tNFA_HCI_DYN_GATE *p_gate; 847 tNFA_HCI_DYN_PIPE *p_pipe; 848 UINT8 pipe_index; 849 850 NFA_TRACE_EVENT1 ("nfa_hciu_release_pipe: %u", pipe_id); 851 852 if ((p_pipe = nfa_hciu_find_pipe_by_pid (pipe_id)) == NULL) 853 return (NFA_HCI_ANY_E_NOK); 854 855 if (pipe_id > NFA_HCI_LAST_DYNAMIC_PIPE) 856 { 857 NFA_TRACE_DEBUG1 ("ignore pipe: %d", pipe_id); 858 return (NFA_HCI_ANY_E_NOK); 859 } 860 861 pipe_index = (UINT8) (p_pipe - nfa_hci_cb.cfg.dyn_pipes); 862 863 if (p_pipe->local_gate == NFA_HCI_IDENTITY_MANAGEMENT_GATE) 864 { 865 /* Remove pipe from ID management gate */ 866 nfa_hci_cb.cfg.id_mgmt_gate.pipe_inx_mask &= ~ (UINT32) (1 << pipe_index); 867 } 868 else 869 { 870 if ((p_gate = nfa_hciu_find_gate_by_gid (p_pipe->local_gate)) == NULL) 871 { 872 /* Mark the pipe control block as free */ 873 p_pipe->pipe_id = 0; 874 return (NFA_HCI_ANY_E_NOK); 875 } 876 877 /* Remove pipe from gate */ 878 p_gate->pipe_inx_mask &= ~ (UINT32) (1 << pipe_index); 879 } 880 881 /* Reset pipe control block */ 882 memset (p_pipe,0,sizeof (tNFA_HCI_DYN_PIPE)); 883 nfa_hci_cb.nv_write_needed = TRUE; 884 return NFA_HCI_ANY_OK; 885 } 886 887 /******************************************************************************* 888 ** 889 ** Function nfa_hciu_remove_all_pipes_from_host 890 ** 891 ** Description remove all the pipes that are connected to a specific host 892 ** 893 ** Returns None 894 ** 895 *******************************************************************************/ 896 void nfa_hciu_remove_all_pipes_from_host (UINT8 host) 897 { 898 tNFA_HCI_DYN_GATE *pg; 899 tNFA_HCI_DYN_PIPE *pp; 900 int xx; 901 tNFA_HCI_EVT_DATA evt_data; 902 903 NFA_TRACE_EVENT1 ("nfa_hciu_remove_all_pipes_from_host (0x%02x)", host); 904 905 /* Remove all pipes from the specified host connected to all generic gates */ 906 for (xx = 0, pp = nfa_hci_cb.cfg.dyn_pipes; xx < NFA_HCI_MAX_PIPE_CB; xx++, pp++) 907 { 908 if ( (pp->pipe_id == 0) 909 || 910 ( (host != 0) 911 &&((pp->dest_host != host) || (pp->pipe_id > NFA_HCI_LAST_DYNAMIC_PIPE))) ) 912 continue; 913 914 if ((pg = nfa_hciu_find_gate_by_gid (pp->local_gate)) != NULL) 915 { 916 evt_data.deleted.status = NFA_STATUS_OK; 917 evt_data.deleted.pipe = pp->pipe_id; 918 919 nfa_hciu_send_to_app (NFA_HCI_DELETE_PIPE_EVT, &evt_data, pg->gate_owner); 920 } 921 nfa_hciu_release_pipe (pp->pipe_id); 922 } 923 } 924 925 /******************************************************************************* 926 ** 927 ** Function nfa_hciu_send_create_pipe_cmd 928 ** 929 ** Description Create dynamic pipe between the specified gates 930 ** 931 ** Returns status 932 ** 933 *******************************************************************************/ 934 tNFA_STATUS nfa_hciu_send_create_pipe_cmd (UINT8 source_gate, UINT8 dest_host, UINT8 dest_gate) 935 { 936 tNFA_STATUS status; 937 UINT8 data[3]; 938 939 data[0] = source_gate; 940 data[1] = dest_host; 941 data[2] = dest_gate; 942 943 NFA_TRACE_DEBUG3 ("nfa_hciu_send_create_pipe_cmd source_gate:%d, dest_host:%d, dest_gate:%d", source_gate, dest_host, dest_gate); 944 945 status = nfa_hciu_send_msg (NFA_HCI_ADMIN_PIPE, NFA_HCI_COMMAND_TYPE, NFA_HCI_ADM_CREATE_PIPE, 3, data); 946 947 return status; 948 } 949 950 /******************************************************************************* 951 ** 952 ** Function nfa_hciu_send_delete_pipe_cmd 953 ** 954 ** Description Delete the dynamic pipe 955 ** 956 ** Returns None 957 ** 958 *******************************************************************************/ 959 tNFA_STATUS nfa_hciu_send_delete_pipe_cmd (UINT8 pipe) 960 { 961 tNFA_STATUS status; 962 963 NFA_TRACE_DEBUG1 ("nfa_hciu_send_delete_pipe_cmd: %d", pipe); 964 965 if (pipe > NFA_HCI_LAST_DYNAMIC_PIPE) 966 { 967 NFA_TRACE_DEBUG1 ("ignore pipe: %d", pipe); 968 return (NFA_HCI_ANY_E_NOK); 969 } 970 nfa_hci_cb.pipe_in_use = pipe; 971 972 status = nfa_hciu_send_msg (NFA_HCI_ADMIN_PIPE, NFA_HCI_COMMAND_TYPE, NFA_HCI_ADM_DELETE_PIPE, 1, &pipe); 973 974 return status; 975 } 976 977 978 /******************************************************************************* 979 ** 980 ** Function nfa_hciu_send_clear_all_pipe_cmd 981 ** 982 ** Description delete all the dynamic pipe connected to device host, 983 ** to close all static pipes connected to device host, 984 ** and to set registry values related to static pipes to 985 ** theri default values. 986 ** 987 ** Returns None 988 ** 989 *******************************************************************************/ 990 tNFA_STATUS nfa_hciu_send_clear_all_pipe_cmd (void) 991 { 992 tNFA_STATUS status; 993 UINT16 id_ref_data = 0x0102; 994 995 NFA_TRACE_DEBUG0 ("nfa_hciu_send_clear_all_pipe_cmd"); 996 997 status = nfa_hciu_send_msg (NFA_HCI_ADMIN_PIPE, NFA_HCI_COMMAND_TYPE, NFA_HCI_ADM_CLEAR_ALL_PIPE, 2, (UINT8 *) &id_ref_data); 998 999 return status; 1000 } 1001 1002 /******************************************************************************* 1003 ** 1004 ** Function nfa_hciu_send_open_pipe_cmd 1005 ** 1006 ** Description Open a closed pipe 1007 ** 1008 ** Returns status 1009 ** 1010 *******************************************************************************/ 1011 tNFA_STATUS nfa_hciu_send_open_pipe_cmd (UINT8 pipe) 1012 { 1013 tNFA_STATUS status; 1014 1015 nfa_hci_cb.pipe_in_use = pipe; 1016 1017 status = nfa_hciu_send_msg (pipe, NFA_HCI_COMMAND_TYPE, NFA_HCI_ANY_OPEN_PIPE, 0, NULL); 1018 1019 return status; 1020 } 1021 1022 /******************************************************************************* 1023 ** 1024 ** Function nfa_hciu_send_close_pipe_cmd 1025 ** 1026 ** Description Close an opened pipe 1027 ** 1028 ** Returns status 1029 ** 1030 *******************************************************************************/ 1031 tNFA_STATUS nfa_hciu_send_close_pipe_cmd (UINT8 pipe) 1032 { 1033 tNFA_STATUS status; 1034 1035 nfa_hci_cb.pipe_in_use = pipe; 1036 1037 status = nfa_hciu_send_msg (pipe, NFA_HCI_COMMAND_TYPE, NFA_HCI_ANY_CLOSE_PIPE, 0, NULL); 1038 1039 return status; 1040 } 1041 1042 /******************************************************************************* 1043 ** 1044 ** Function nfa_hciu_send_get_param_cmd 1045 ** 1046 ** Description Read a parameter value from gate registry 1047 ** 1048 ** Returns None 1049 ** 1050 *******************************************************************************/ 1051 tNFA_STATUS nfa_hciu_send_get_param_cmd (UINT8 pipe, UINT8 index) 1052 { 1053 tNFA_STATUS status; 1054 1055 if ((status = nfa_hciu_send_msg (pipe, NFA_HCI_COMMAND_TYPE, NFA_HCI_ANY_GET_PARAMETER, 1, &index)) == NFC_STATUS_OK) 1056 nfa_hci_cb.param_in_use = index; 1057 1058 return status; 1059 } 1060 1061 /******************************************************************************* 1062 ** 1063 ** Function nfa_hciu_send_set_param_cmd 1064 ** 1065 ** Description Set a parameter value in a gate registry 1066 ** 1067 ** Returns None 1068 ** 1069 *******************************************************************************/ 1070 tNFA_STATUS nfa_hciu_send_set_param_cmd (UINT8 pipe, UINT8 index, UINT8 length, UINT8 *p_data) 1071 { 1072 tNFA_STATUS status; 1073 UINT8 data[255]; 1074 1075 data[0] = index; 1076 1077 memcpy (&data[1], p_data, length); 1078 1079 if ((status = nfa_hciu_send_msg (pipe, NFA_HCI_COMMAND_TYPE, NFA_HCI_ANY_SET_PARAMETER, (UINT16) (length + 1), data)) == NFC_STATUS_OK) 1080 nfa_hci_cb.param_in_use = index; 1081 1082 return status; 1083 } 1084 1085 1086 /******************************************************************************* 1087 ** 1088 ** Function nfa_hciu_send_to_app 1089 ** 1090 ** Description Send an event back to an application 1091 ** 1092 ** Returns none 1093 ** 1094 *******************************************************************************/ 1095 void nfa_hciu_send_to_app (tNFA_HCI_EVT event, tNFA_HCI_EVT_DATA *p_evt, tNFA_HANDLE app_handle) 1096 { 1097 UINT8 app_inx = app_handle & NFA_HANDLE_MASK; 1098 1099 /* First, check if the application handle is valid */ 1100 if ( ((app_handle & NFA_HANDLE_GROUP_MASK) == NFA_HANDLE_GROUP_HCI) 1101 &&(app_inx < NFA_HCI_MAX_APP_CB) ) 1102 { 1103 if (nfa_hci_cb.p_app_cback[app_inx] != NULL) 1104 { 1105 nfa_hci_cb.p_app_cback[app_inx] (event, p_evt); 1106 return; 1107 } 1108 } 1109 1110 if (app_handle != NFA_HANDLE_INVALID) 1111 { 1112 NFA_TRACE_WARNING2 ("nfa_hciu_send_to_app no callback, event: 0x%04x app_handle: 0x%04x", 1113 event, app_handle); 1114 } 1115 } 1116 1117 /******************************************************************************* 1118 ** 1119 ** Function nfa_hciu_send_to_all_apps 1120 ** 1121 ** Description Send an event back to all applications 1122 ** 1123 ** Returns none 1124 ** 1125 *******************************************************************************/ 1126 void nfa_hciu_send_to_all_apps (tNFA_HCI_EVT event, tNFA_HCI_EVT_DATA *p_evt) 1127 { 1128 UINT8 app_inx; 1129 1130 for (app_inx = 0; app_inx < NFA_HCI_MAX_APP_CB; app_inx++) 1131 { 1132 if (nfa_hci_cb.p_app_cback[app_inx] != NULL) 1133 nfa_hci_cb.p_app_cback[app_inx] (event, p_evt); 1134 } 1135 1136 } 1137 1138 /******************************************************************************* 1139 ** 1140 ** Function nfa_hciu_send_to_apps_handling_connectivity_evts 1141 ** 1142 ** Description Send a connectivity event to all the application interested 1143 ** in connectivity events 1144 ** 1145 ** Returns none 1146 ** 1147 *******************************************************************************/ 1148 void nfa_hciu_send_to_apps_handling_connectivity_evts (tNFA_HCI_EVT event, tNFA_HCI_EVT_DATA *p_evt) 1149 { 1150 UINT8 app_inx; 1151 1152 for (app_inx = 0; app_inx < NFA_HCI_MAX_APP_CB; app_inx++) 1153 { 1154 if ( (nfa_hci_cb.p_app_cback[app_inx] != NULL) 1155 &&(nfa_hci_cb.cfg.b_send_conn_evts[app_inx])) 1156 1157 nfa_hci_cb.p_app_cback[app_inx] (event, p_evt); 1158 } 1159 1160 } 1161 1162 #if (BT_TRACE_VERBOSE == TRUE) 1163 /******************************************************************************* 1164 ** 1165 ** Function nfa_hciu_get_response_name 1166 ** 1167 ** Description This function returns the error code name. 1168 ** 1169 ** NOTE conditionally compiled to save memory. 1170 ** 1171 ** Returns pointer to the name 1172 ** 1173 *******************************************************************************/ 1174 char *nfa_hciu_get_response_name (UINT8 rsp_code) 1175 { 1176 switch (rsp_code) 1177 { 1178 case NFA_HCI_ANY_OK: 1179 return ("ANY_OK"); 1180 case NFA_HCI_ANY_E_NOT_CONNECTED: 1181 return ("ANY_E_NOT_CONNECTED"); 1182 case NFA_HCI_ANY_E_CMD_PAR_UNKNOWN: 1183 return ("ANY_E_CMD_PAR_UNKNOWN"); 1184 case NFA_HCI_ANY_E_NOK: 1185 return ("ANY_E_NOK"); 1186 case NFA_HCI_ADM_E_NO_PIPES_AVAILABLE: 1187 return ("ADM_E_NO_PIPES_AVAILABLE"); 1188 case NFA_HCI_ANY_E_REG_PAR_UNKNOWN: 1189 return ("ANY_E_REG_PAR_UNKNOWN"); 1190 case NFA_HCI_ANY_E_PIPE_NOT_OPENED: 1191 return ("ANY_E_PIPE_NOT_OPENED"); 1192 case NFA_HCI_ANY_E_CMD_NOT_SUPPORTED: 1193 return ("ANY_E_CMD_NOT_SUPPORTED"); 1194 case NFA_HCI_ANY_E_INHIBITED: 1195 return ("ANY_E_INHIBITED"); 1196 case NFA_HCI_ANY_E_TIMEOUT: 1197 return ("ANY_E_TIMEOUT"); 1198 case NFA_HCI_ANY_E_REG_ACCESS_DENIED: 1199 return ("ANY_E_REG_ACCESS_DENIED"); 1200 case NFA_HCI_ANY_E_PIPE_ACCESS_DENIED: 1201 return ("ANY_E_PIPE_ACCESS_DENIED"); 1202 default: 1203 return ("UNKNOWN"); 1204 } 1205 } 1206 1207 /******************************************************************************* 1208 ** 1209 ** Function nfa_hciu_type_2_str 1210 ** 1211 ** Description This function returns the type name. 1212 ** 1213 ** Returns pointer to the name 1214 ** 1215 *******************************************************************************/ 1216 char *nfa_hciu_type_2_str(UINT8 type) 1217 { 1218 switch (type) 1219 { 1220 case NFA_HCI_COMMAND_TYPE: 1221 return ("COMMAND"); 1222 case NFA_HCI_EVENT_TYPE: 1223 return ("EVENT"); 1224 case NFA_HCI_RESPONSE_TYPE: 1225 return ("RESPONSE"); 1226 default: 1227 return ("UNKNOWN"); 1228 } 1229 } 1230 1231 /******************************************************************************* 1232 ** 1233 ** Function nfa_hciu_instr_2_str 1234 ** 1235 ** Description This function returns the instruction name. 1236 ** 1237 ** Returns pointer to the name 1238 ** 1239 *******************************************************************************/ 1240 char *nfa_hciu_instr_2_str (UINT8 instruction) 1241 { 1242 switch (instruction) 1243 { 1244 case NFA_HCI_ANY_SET_PARAMETER: 1245 return ("ANY_SET_PARAMETER"); 1246 case NFA_HCI_ANY_GET_PARAMETER: 1247 return ("ANY_GET_PARAMETER"); 1248 case NFA_HCI_ANY_OPEN_PIPE: 1249 return ("ANY_OPEN_PIPE"); 1250 case NFA_HCI_ANY_CLOSE_PIPE: 1251 return ("ANY_CLOSE_PIPE"); 1252 case NFA_HCI_ADM_CREATE_PIPE: 1253 return ("ADM_CREATE_PIPE"); 1254 case NFA_HCI_ADM_DELETE_PIPE: 1255 return ("ADM_DELETE_PIPE"); 1256 case NFA_HCI_ADM_NOTIFY_PIPE_CREATED: 1257 return ("ADM_NOTIFY_PIPE_CREATED"); 1258 case NFA_HCI_ADM_NOTIFY_PIPE_DELETED: 1259 return ("ADM_NOTIFY_PIPE_DELETED"); 1260 case NFA_HCI_ADM_CLEAR_ALL_PIPE: 1261 return ("ADM_CLEAR_ALL_PIPE"); 1262 case NFA_HCI_ADM_NOTIFY_ALL_PIPE_CLEARED: 1263 return ("ADM_NOTIFY_ALL_PIPE_CLEARED"); 1264 default: 1265 return ("UNKNOWN"); 1266 } 1267 } 1268 1269 1270 /******************************************************************************* 1271 ** 1272 ** Function nfa_hciu_get_event_name 1273 ** 1274 ** Description This function returns the event code name. 1275 ** 1276 ** Returns pointer to the name 1277 ** 1278 *******************************************************************************/ 1279 char *nfa_hciu_get_event_name (UINT16 event) 1280 { 1281 switch (event) 1282 { 1283 case NFA_HCI_API_REGISTER_APP_EVT: return ("API_REGISTER"); 1284 case NFA_HCI_API_DEREGISTER_APP_EVT: return ("API_DEREGISTER"); 1285 case NFA_HCI_API_GET_APP_GATE_PIPE_EVT: return ("API_GET_GATE_LIST"); 1286 case NFA_HCI_API_ALLOC_GATE_EVT: return ("API_ALLOC_GATE"); 1287 case NFA_HCI_API_DEALLOC_GATE_EVT: return ("API_DEALLOC_GATE"); 1288 case NFA_HCI_API_GET_HOST_LIST_EVT: return ("API_GET_HOST_LIST"); 1289 case NFA_HCI_API_GET_REGISTRY_EVT: return ("API_GET_REG_VALUE"); 1290 case NFA_HCI_API_SET_REGISTRY_EVT: return ("API_SET_REG_VALUE"); 1291 case NFA_HCI_API_CREATE_PIPE_EVT: return ("API_CREATE_PIPE"); 1292 case NFA_HCI_API_OPEN_PIPE_EVT: return ("API_OPEN_PIPE"); 1293 case NFA_HCI_API_CLOSE_PIPE_EVT: return ("API_CLOSE_PIPE"); 1294 case NFA_HCI_API_DELETE_PIPE_EVT: return ("API_DELETE_PIPE"); 1295 case NFA_HCI_API_SEND_CMD_EVT: return ("API_SEND_COMMAND_EVT"); 1296 case NFA_HCI_API_SEND_RSP_EVT: return ("API_SEND_RESPONSE_EVT"); 1297 case NFA_HCI_API_SEND_EVENT_EVT: return ("API_SEND_EVENT_EVT"); 1298 case NFA_HCI_RSP_NV_READ_EVT: return ("NV_READ_EVT"); 1299 case NFA_HCI_RSP_NV_WRITE_EVT: return ("NV_WRITE_EVT"); 1300 case NFA_HCI_RSP_TIMEOUT_EVT: return ("RESPONSE_TIMEOUT_EVT"); 1301 case NFA_HCI_CHECK_QUEUE_EVT: return ("CHECK_QUEUE"); 1302 1303 default: 1304 return ("UNKNOWN"); 1305 } 1306 } 1307 1308 /******************************************************************************* 1309 ** 1310 ** Function nfa_hciu_get_state_name 1311 ** 1312 ** Description This function returns the state name. 1313 ** 1314 ** Returns pointer to the name 1315 ** 1316 *******************************************************************************/ 1317 char *nfa_hciu_get_state_name (UINT8 state) 1318 { 1319 switch (state) 1320 { 1321 case NFA_HCI_STATE_DISABLED: return ("DISABLED"); 1322 case NFA_HCI_STATE_STARTUP: return ("STARTUP"); 1323 case NFA_HCI_STATE_WAIT_NETWK_ENABLE: return ("WAIT_NETWK_ENABLE"); 1324 case NFA_HCI_STATE_IDLE: return ("IDLE"); 1325 case NFA_HCI_STATE_WAIT_RSP: return ("WAIT_RSP"); 1326 case NFA_HCI_STATE_REMOVE_GATE: return ("REMOVE_GATE"); 1327 case NFA_HCI_STATE_APP_DEREGISTER: return ("APP_DEREGISTER"); 1328 case NFA_HCI_STATE_RESTORE: return ("RESTORE"); 1329 case NFA_HCI_STATE_RESTORE_NETWK_ENABLE: return ("WAIT_NETWK_ENABLE_AFTER_RESTORE"); 1330 1331 default: 1332 return ("UNKNOWN"); 1333 } 1334 } 1335 1336 /******************************************************************************* 1337 ** 1338 ** Function nfa_hciu_get_type_inst_names 1339 ** 1340 ** Description This function returns command/response/event name. 1341 ** 1342 ** Returns none 1343 ** 1344 *******************************************************************************/ 1345 char *nfa_hciu_get_type_inst_names (UINT8 pipe, UINT8 type, UINT8 inst, char *p_buff) 1346 { 1347 int xx; 1348 1349 xx = sprintf (p_buff, "Type: %s [0x%02x] ", nfa_hciu_type_2_str (type), type); 1350 1351 switch (type) 1352 { 1353 case NFA_HCI_COMMAND_TYPE: 1354 sprintf (&p_buff[xx], "Inst: %s [0x%02x] ", nfa_hciu_instr_2_str (inst), inst); 1355 break; 1356 case NFA_HCI_EVENT_TYPE: 1357 sprintf (&p_buff[xx], "Evt: %s [0x%02x] ", nfa_hciu_evt_2_str (pipe, inst), inst); 1358 break; 1359 case NFA_HCI_RESPONSE_TYPE: 1360 sprintf (&p_buff[xx], "Resp: %s [0x%02x] ", nfa_hciu_get_response_name (inst), inst); 1361 break; 1362 default: 1363 sprintf (&p_buff[xx], "Inst: %u ", inst); 1364 break; 1365 } 1366 return (p_buff); 1367 } 1368 1369 /******************************************************************************* 1370 ** 1371 ** Function nfa_hciu_evt_2_str 1372 ** 1373 ** Description This function returns the event name. 1374 ** 1375 ** Returns pointer to the name 1376 ** 1377 *******************************************************************************/ 1378 char *nfa_hciu_evt_2_str (UINT8 pipe_id, UINT8 evt) 1379 { 1380 tNFA_HCI_DYN_PIPE *p_pipe; 1381 1382 if ( (pipe_id != NFA_HCI_ADMIN_PIPE) 1383 &&(pipe_id != NFA_HCI_LINK_MANAGEMENT_PIPE) 1384 &&((p_pipe = nfa_hciu_find_pipe_by_pid (pipe_id)) != NULL) ) 1385 { 1386 if (p_pipe->local_gate == NFA_HCI_CONNECTIVITY_GATE) 1387 { 1388 switch (evt) 1389 { 1390 case NFA_HCI_EVT_CONNECTIVITY: 1391 return ("EVT_CONNECTIVITY"); 1392 case NFA_HCI_EVT_TRANSACTION: 1393 return ("EVT_TRANSACTION"); 1394 case NFA_HCI_EVT_OPERATION_ENDED: 1395 return ("EVT_OPERATION_ENDED"); 1396 default: 1397 return ("UNKNOWN"); 1398 } 1399 } 1400 } 1401 1402 switch (evt) 1403 { 1404 case NFA_HCI_EVT_HCI_END_OF_OPERATION: 1405 return ("EVT_END_OF_OPERATION"); 1406 case NFA_HCI_EVT_POST_DATA: 1407 return ("EVT_POST_DATA"); 1408 case NFA_HCI_EVT_HOT_PLUG: 1409 return ("EVT_HOT_PLUG"); 1410 default: 1411 return ("UNKNOWN"); 1412 } 1413 } 1414 #endif 1415 1416 1417 static void handle_debug_loopback (BT_HDR *p_buf, UINT8 pipe, UINT8 type, UINT8 instruction) 1418 { 1419 UINT8 *p = (UINT8 *) (p_buf + 1) + p_buf->offset; 1420 static UINT8 next_pipe = 0x10; 1421 1422 if (type == NFA_HCI_COMMAND_TYPE) 1423 { 1424 switch (instruction) 1425 { 1426 case NFA_HCI_ADM_CREATE_PIPE: 1427 p[6] = next_pipe++; 1428 p[5] = p[4]; 1429 p[4] = p[3]; 1430 p[3] = p[2]; 1431 p[2] = 3; 1432 p[1] = (NFA_HCI_RESPONSE_TYPE << 6) | NFA_HCI_ANY_OK; 1433 p_buf->len = p_buf->offset + 7; 1434 break; 1435 1436 case NFA_HCI_ANY_GET_PARAMETER: 1437 p[1] = (NFA_HCI_RESPONSE_TYPE << 6) | NFA_HCI_ANY_OK; 1438 memcpy (&p[2], (UINT8 *) nfa_hci_cb.cfg.admin_gate.session_id, NFA_HCI_SESSION_ID_LEN); 1439 p_buf->len = p_buf->offset + 2 + NFA_HCI_SESSION_ID_LEN; 1440 break; 1441 1442 default: 1443 p[1] = (NFA_HCI_RESPONSE_TYPE << 6) | NFA_HCI_ANY_OK; 1444 p_buf->len = p_buf->offset + 2; 1445 break; 1446 } 1447 } 1448 else if (type == NFA_HCI_RESPONSE_TYPE) 1449 { 1450 GKI_freebuf (p_buf); 1451 return; 1452 } 1453 1454 p_buf->event = NFA_HCI_CHECK_QUEUE_EVT; 1455 nfa_sys_sendmsg (p_buf); 1456 } 1457 1458