1 /******************************************************************************
2 *
3 * Copyright (C) 1999-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 * This file contains functions that interface with the NFC NCI transport.
22 * On the receive side, it routes events to the appropriate handler
23 * (callback). On the transmit side, it manages the command transmission.
24 *
25 ******************************************************************************/
26 #include <android-base/stringprintf.h>
27 #include <base/logging.h>
28
29 #include "bt_types.h"
30 #include "nfc_api.h"
31 #include "nfc_int.h"
32
33 using android::base::StringPrintf;
34
35 extern bool nfc_debug_enabled;
36
37 /*******************************************************************************
38 **
39 ** Function nfc_alloc_conn_cb
40 **
41 ** Description This function is called to allocation a control block for
42 ** NCI logical connection
43 **
44 ** Returns The allocated control block or NULL
45 **
46 *******************************************************************************/
nfc_alloc_conn_cb(tNFC_CONN_CBACK * p_cback)47 tNFC_CONN_CB* nfc_alloc_conn_cb(tNFC_CONN_CBACK* p_cback) {
48 int xx, max = NCI_MAX_CONN_CBS;
49 tNFC_CONN_CB* p_conn_cb = nullptr;
50
51 NFC_CHECK_MAX_CONN();
52 for (xx = 0; xx < max; xx++) {
53 if (nfc_cb.conn_cb[xx].conn_id == NFC_ILLEGAL_CONN_ID) {
54 nfc_cb.conn_cb[xx].conn_id =
55 NFC_PEND_CONN_ID; /* to indicate this cb is used */
56 p_conn_cb = &nfc_cb.conn_cb[xx];
57 p_conn_cb->p_cback = p_cback;
58 break;
59 }
60 }
61 return p_conn_cb;
62 }
63
64 /*******************************************************************************
65 **
66 ** Function nfc_set_conn_id
67 **
68 ** Description This function is called to set the connection id to the
69 ** connection control block and the id mapping table
70 **
71 ** Returns void
72 **
73 *******************************************************************************/
nfc_set_conn_id(tNFC_CONN_CB * p_cb,uint8_t conn_id)74 void nfc_set_conn_id(tNFC_CONN_CB* p_cb, uint8_t conn_id) {
75 uint8_t handle;
76
77 if (p_cb == nullptr) return;
78
79 p_cb->conn_id = conn_id;
80 handle = (uint8_t)(p_cb - nfc_cb.conn_cb + 1);
81 nfc_cb.conn_id[conn_id] = handle;
82 DLOG_IF(INFO, nfc_debug_enabled)
83 << StringPrintf("nfc_set_conn_id conn_id:%d, handle:%d", conn_id, handle);
84 }
85
86 /*******************************************************************************
87 **
88 ** Function nfc_find_conn_cb_by_handle
89 **
90 ** Description This function is called to locate the control block for
91 ** loopback test.
92 **
93 ** Returns The loopback test control block or NULL
94 **
95 *******************************************************************************/
nfc_find_conn_cb_by_handle(uint8_t id)96 tNFC_CONN_CB* nfc_find_conn_cb_by_handle(uint8_t id) {
97 int xx;
98 tNFC_CONN_CB* p_conn_cb = nullptr;
99
100 for (xx = 0; xx < NCI_MAX_CONN_CBS; xx++) {
101 if (nfc_cb.conn_cb[xx].id == id) {
102 p_conn_cb = &nfc_cb.conn_cb[xx];
103 break;
104 }
105 }
106 return p_conn_cb;
107 }
108
109 /*******************************************************************************
110 **
111 ** Function nfc_find_conn_cb_by_conn_id
112 **
113 ** Description This function is called to locate the control block for
114 ** the given connection id
115 **
116 ** Returns The control block or NULL
117 **
118 *******************************************************************************/
nfc_find_conn_cb_by_conn_id(uint8_t conn_id)119 tNFC_CONN_CB* nfc_find_conn_cb_by_conn_id(uint8_t conn_id) {
120 tNFC_CONN_CB* p_conn_cb = nullptr;
121 uint8_t handle;
122 uint8_t id;
123 int xx;
124
125 if (conn_id == NFC_PEND_CONN_ID) {
126 for (xx = 0; xx < NCI_MAX_CONN_CBS; xx++) {
127 if (nfc_cb.conn_cb[xx].conn_id == NFC_PEND_CONN_ID) {
128 p_conn_cb = &nfc_cb.conn_cb[xx];
129 break;
130 }
131 }
132 } else {
133 id = conn_id & NFC_CONN_ID_ID_MASK;
134 if (id < NFC_MAX_CONN_ID) {
135 handle = nfc_cb.conn_id[id];
136 if (handle > 0) p_conn_cb = &nfc_cb.conn_cb[handle - 1];
137 }
138 }
139
140 return p_conn_cb;
141 }
142
143 /*******************************************************************************
144 **
145 ** Function nfc_free_conn_cb
146 **
147 ** Description This function is called to free the control block and
148 ** resources and id mapping table
149 **
150 ** Returns void
151 **
152 *******************************************************************************/
nfc_free_conn_cb(tNFC_CONN_CB * p_cb)153 void nfc_free_conn_cb(tNFC_CONN_CB* p_cb) {
154 void* p_buf;
155
156 if (p_cb == nullptr) return;
157
158 while ((p_buf = GKI_dequeue(&p_cb->rx_q)) != nullptr) GKI_freebuf(p_buf);
159
160 while ((p_buf = GKI_dequeue(&p_cb->tx_q)) != nullptr) GKI_freebuf(p_buf);
161
162 if (p_cb->conn_id <= NFC_MAX_CONN_ID) {
163 nfc_cb.conn_id[p_cb->conn_id] = 0;
164 } else {
165 LOG(ERROR) << StringPrintf("invalid conn_id.");
166 }
167 p_cb->p_cback = nullptr;
168 p_cb->conn_id = NFC_ILLEGAL_CONN_ID;
169 }
170
171 /*******************************************************************************
172 **
173 ** Function nfc_reset_all_conn_cbs
174 **
175 ** Description This function is called to free all the control blocks and
176 ** resources and id mapping table
177 **
178 ** Returns void
179 **
180 *******************************************************************************/
nfc_reset_all_conn_cbs(void)181 extern void nfc_reset_all_conn_cbs(void) {
182 int xx;
183 tNFC_CONN_CB* p_conn_cb = &nfc_cb.conn_cb[0];
184 tNFC_DEACTIVATE_DEVT deact = tNFC_DEACTIVATE_DEVT();
185
186 deact.status = NFC_STATUS_NOT_INITIALIZED;
187 deact.type = NFC_DEACTIVATE_TYPE_IDLE;
188 deact.is_ntf = TRUE;
189 for (xx = 0; xx < NCI_MAX_CONN_CBS; xx++, p_conn_cb++) {
190 if (p_conn_cb->conn_id != NFC_ILLEGAL_CONN_ID) {
191 if (p_conn_cb->p_cback) {
192 tNFC_CONN nfc_conn;
193 nfc_conn.deactivate = deact;
194 (*p_conn_cb->p_cback)(p_conn_cb->conn_id, NFC_DEACTIVATE_CEVT,
195 &nfc_conn);
196 }
197 nfc_free_conn_cb(p_conn_cb);
198 }
199 }
200 }
201