• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
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  *  This file contains the action functions the NFA_RW state machine.
22  *
23  ******************************************************************************/
24 #include <android-base/stringprintf.h>
25 #include <base/logging.h>
26 #include <log/log.h>
27 #include <string.h>
28 
29 #include "ndef_utils.h"
30 #include "nfa_dm_int.h"
31 #include "nfa_mem_co.h"
32 #include "nfa_rw_int.h"
33 
34 using android::base::StringPrintf;
35 
36 extern bool nfc_debug_enabled;
37 
38 #define NFA_RW_OPTION_INVALID 0xFF
39 
40 /* Tag sleep req cmd*/
41 uint8_t NFA_RW_TAG_SLP_REQ[] = {0x50, 0x00};
42 
43 /* Local static function prototypes */
44 static tNFC_STATUS nfa_rw_start_ndef_read(void);
45 static tNFC_STATUS nfa_rw_start_ndef_write(void);
46 static tNFC_STATUS nfa_rw_start_ndef_detection(void);
47 static tNFC_STATUS nfa_rw_config_tag_ro(bool b_hard_lock);
48 static bool nfa_rw_op_req_while_busy(tNFA_RW_MSG* p_data);
49 static bool nfa_rw_op_req_while_inactive(tNFA_RW_MSG* p_data);
50 static void nfa_rw_error_cleanup(uint8_t event);
51 static void nfa_rw_presence_check(tNFA_RW_MSG* p_data);
52 static void nfa_rw_handle_t2t_evt(tRW_EVENT event, tRW_DATA* p_rw_data);
53 static bool nfa_rw_detect_ndef(void);
54 static void nfa_rw_cback(tRW_EVENT event, tRW_DATA* p_rw_data);
55 static void nfa_rw_handle_mfc_evt(tRW_EVENT event, tRW_DATA* p_rw_data);
56 
57 extern void rw_t4t_handle_isodep_nak_fallback();
58 
59 /*******************************************************************************
60 **
61 ** Function         nfa_rw_free_ndef_rx_buf
62 **
63 ** Description      Free buffer allocated to hold incoming NDEF message
64 **
65 ** Returns          Nothing
66 **
67 *******************************************************************************/
nfa_rw_free_ndef_rx_buf(void)68 void nfa_rw_free_ndef_rx_buf(void) {
69   if (nfa_rw_cb.p_ndef_buf) {
70     nfa_mem_co_free(nfa_rw_cb.p_ndef_buf);
71     nfa_rw_cb.p_ndef_buf = nullptr;
72   }
73 }
74 
75 /*******************************************************************************
76 **
77 ** Function         nfa_rw_store_ndef_rx_buf
78 **
79 ** Description      Store data into NDEF buffer
80 **
81 ** Returns          Nothing
82 **
83 *******************************************************************************/
nfa_rw_store_ndef_rx_buf(tRW_DATA * p_rw_data)84 static void nfa_rw_store_ndef_rx_buf(tRW_DATA* p_rw_data) {
85   uint8_t* p;
86 
87   p = (uint8_t*)(p_rw_data->data.p_data + 1) + p_rw_data->data.p_data->offset;
88 
89   if ((nfa_rw_cb.ndef_rd_offset + p_rw_data->data.p_data->len) <=
90       nfa_rw_cb.ndef_cur_size) {
91     /* Save data into buffer */
92     memcpy(&nfa_rw_cb.p_ndef_buf[nfa_rw_cb.ndef_rd_offset], p,
93            p_rw_data->data.p_data->len);
94     nfa_rw_cb.ndef_rd_offset += p_rw_data->data.p_data->len;
95   } else {
96     LOG(ERROR) << StringPrintf("Exceed ndef_cur_size error");
97     android_errorWriteLog(0x534e4554, "123583388");
98   }
99 
100   GKI_freebuf(p_rw_data->data.p_data);
101   p_rw_data->data.p_data = nullptr;
102 }
103 
104 /*******************************************************************************
105 **
106 ** Function         nfa_rw_send_data_to_upper
107 **
108 ** Description      Send data to upper layer
109 **
110 ** Returns          Nothing
111 **
112 *******************************************************************************/
nfa_rw_send_data_to_upper(tRW_DATA * p_rw_data)113 static void nfa_rw_send_data_to_upper(tRW_DATA* p_rw_data) {
114   tNFA_CONN_EVT_DATA conn_evt_data;
115 
116   if ((p_rw_data->status == NFC_STATUS_TIMEOUT) ||
117       (p_rw_data->data.p_data == nullptr))
118     return;
119 
120   DLOG_IF(INFO, nfc_debug_enabled)
121       << StringPrintf("nfa_rw_send_data_to_upper: Len [0x%X] Status [%s]",
122                       p_rw_data->data.p_data->len,
123                       NFC_GetStatusName(p_rw_data->data.status).c_str());
124 
125   /* Notify conn cback of NFA_DATA_EVT */
126   conn_evt_data.data.status = p_rw_data->data.status;
127   conn_evt_data.data.p_data =
128       (uint8_t*)(p_rw_data->data.p_data + 1) + p_rw_data->data.p_data->offset;
129   conn_evt_data.data.len = p_rw_data->data.p_data->len;
130 
131   nfa_dm_act_conn_cback_notify(NFA_DATA_EVT, &conn_evt_data);
132 
133   GKI_freebuf(p_rw_data->data.p_data);
134   p_rw_data->data.p_data = nullptr;
135 }
136 
137 /*******************************************************************************
138 **
139 ** Function         nfa_rw_error_cleanup
140 **
141 ** Description      Handle failure - signal command complete and notify app
142 **
143 ** Returns          Nothing
144 **
145 *******************************************************************************/
nfa_rw_error_cleanup(uint8_t event)146 static void nfa_rw_error_cleanup(uint8_t event) {
147   tNFA_CONN_EVT_DATA conn_evt_data;
148 
149   nfa_rw_command_complete();
150 
151   conn_evt_data.status = NFA_STATUS_FAILED;
152 
153   nfa_dm_act_conn_cback_notify(event, &conn_evt_data);
154 }
155 
156 /*******************************************************************************
157 **
158 ** Function         nfa_rw_check_start_presence_check_timer
159 **
160 ** Description      Start timer to wait for specified time before presence check
161 **
162 ** Returns          Nothing
163 **
164 *******************************************************************************/
nfa_rw_check_start_presence_check_timer(uint16_t presence_check_start_delay)165 static void nfa_rw_check_start_presence_check_timer(
166     uint16_t presence_check_start_delay) {
167   if (!p_nfa_dm_cfg->auto_presence_check) return;
168 
169   if (nfa_rw_cb.flags & NFA_RW_FL_NOT_EXCL_RF_MODE) {
170     if (presence_check_start_delay) {
171       DLOG_IF(INFO, nfc_debug_enabled)
172           << StringPrintf("Starting presence check timer...");
173       nfa_sys_start_timer(&nfa_rw_cb.tle, NFA_RW_PRESENCE_CHECK_TICK_EVT,
174                           presence_check_start_delay);
175     } else {
176       /* Presence check now */
177       nfa_rw_presence_check(nullptr);
178     }
179   }
180 }
181 
182 /*******************************************************************************
183 **
184 ** Function         nfa_rw_stop_presence_check_timer
185 **
186 ** Description      Stop timer for presence check
187 **
188 ** Returns          Nothing
189 **
190 *******************************************************************************/
nfa_rw_stop_presence_check_timer(void)191 void nfa_rw_stop_presence_check_timer(void) {
192   nfa_sys_stop_timer(&nfa_rw_cb.tle);
193   DLOG_IF(INFO, nfc_debug_enabled)
194       << StringPrintf("Stopped presence check timer (if started)");
195 }
196 
197 /*******************************************************************************
198 **
199 ** Function         nfa_rw_handle_ndef_detect
200 **
201 ** Description      Handler for NDEF detection reader/writer event
202 **
203 ** Returns          Nothing
204 **
205 *******************************************************************************/
nfa_rw_handle_ndef_detect(tRW_DATA * p_rw_data)206 static void nfa_rw_handle_ndef_detect(tRW_DATA* p_rw_data) {
207   tNFA_CONN_EVT_DATA conn_evt_data;
208 
209   DLOG_IF(INFO, nfc_debug_enabled) << StringPrintf(
210       "NDEF Detection completed: cur_size=%i, max_size=%i, flags=0x%x",
211       p_rw_data->ndef.cur_size, p_rw_data->ndef.max_size,
212       p_rw_data->ndef.flags);
213 
214   /* Check if NDEF detection succeeded */
215   if (p_rw_data->ndef.status == NFC_STATUS_OK) {
216     /* Set NDEF detection state */
217     nfa_rw_cb.ndef_st = NFA_RW_NDEF_ST_TRUE;
218     nfa_rw_cb.flags |= NFA_RW_FL_NDEF_OK;
219 
220     /* Store ndef properties */
221     conn_evt_data.ndef_detect.status = NFA_STATUS_OK;
222     conn_evt_data.ndef_detect.protocol = p_rw_data->ndef.protocol;
223     conn_evt_data.ndef_detect.cur_size = nfa_rw_cb.ndef_cur_size =
224         p_rw_data->ndef.cur_size;
225     conn_evt_data.ndef_detect.max_size = nfa_rw_cb.ndef_max_size =
226         p_rw_data->ndef.max_size;
227     conn_evt_data.ndef_detect.flags = p_rw_data->ndef.flags;
228 
229     if (p_rw_data->ndef.flags & RW_NDEF_FL_READ_ONLY)
230       nfa_rw_cb.flags |= NFA_RW_FL_TAG_IS_READONLY;
231     else
232       nfa_rw_cb.flags &= ~NFA_RW_FL_TAG_IS_READONLY;
233 
234     /* Determine what operation triggered the NDEF detection procedure */
235     if (nfa_rw_cb.cur_op == NFA_RW_OP_READ_NDEF) {
236       /* if ndef detection was done as part of ndef-read operation, then perform
237        * ndef read now */
238       conn_evt_data.status = nfa_rw_start_ndef_read();
239       if (conn_evt_data.status != NFA_STATUS_OK) {
240         /* Failed to start NDEF Read */
241 
242         /* Command complete - perform cleanup, notify app */
243         nfa_rw_command_complete();
244         nfa_dm_act_conn_cback_notify(NFA_READ_CPLT_EVT, &conn_evt_data);
245       }
246     } else if (nfa_rw_cb.cur_op == NFA_RW_OP_WRITE_NDEF) {
247       /* if ndef detection was done as part of ndef-write operation, then
248        * perform ndef write now */
249       conn_evt_data.status = nfa_rw_start_ndef_write();
250       if (conn_evt_data.status != NFA_STATUS_OK) {
251         /* Failed to start NDEF Write.  */
252 
253         /* Command complete - perform cleanup, notify app */
254         nfa_rw_command_complete();
255         nfa_dm_act_conn_cback_notify(NFA_WRITE_CPLT_EVT, &conn_evt_data);
256       }
257     } else {
258       /* current op was stand-alone NFA_DetectNDef. Command complete - perform
259        * cleanup and notify app */
260       nfa_rw_cb.cur_op = NFA_RW_OP_MAX;
261       nfa_rw_command_complete();
262 
263       nfa_dm_act_conn_cback_notify(NFA_NDEF_DETECT_EVT, &conn_evt_data);
264     }
265   } else {
266     /* NDEF detection failed... */
267 
268     /* Command complete - perform cleanup, notify app */
269     nfa_rw_command_complete();
270     nfa_rw_cb.ndef_st = NFA_RW_NDEF_ST_FALSE;
271     conn_evt_data.status = p_rw_data->ndef.status;
272 
273     if (nfa_rw_cb.cur_op == NFA_RW_OP_READ_NDEF) {
274       /* if ndef detection was done as part of ndef-read operation, then notify
275        * NDEF handlers of failure */
276       nfa_dm_ndef_handle_message(NFA_STATUS_FAILED, nullptr, 0);
277 
278       /* Notify app of read status */
279       nfa_dm_act_conn_cback_notify(NFA_READ_CPLT_EVT, &conn_evt_data);
280     } else if (nfa_rw_cb.cur_op == NFA_RW_OP_WRITE_NDEF) {
281       /* if ndef detection was done as part of ndef-write operation, then notify
282        * app of failure */
283       nfa_dm_act_conn_cback_notify(NFA_WRITE_CPLT_EVT, &conn_evt_data);
284     } else if (nfa_rw_cb.cur_op == NFA_RW_OP_DETECT_NDEF) {
285       conn_evt_data.ndef_detect.protocol = p_rw_data->ndef.protocol;
286       /* current op was stand-alone NFA_DetectNDef. Notify app of failure */
287       if (p_rw_data->ndef.status == NFC_STATUS_TIMEOUT) {
288         /* Tag could have moved away */
289         conn_evt_data.ndef_detect.cur_size = 0;
290         conn_evt_data.ndef_detect.max_size = 0;
291         conn_evt_data.ndef_detect.flags = RW_NDEF_FL_UNKNOWN;
292         conn_evt_data.ndef_detect.status = NFA_STATUS_TIMEOUT;
293       } else {
294         /* NDEF Detection failed for other reasons */
295         conn_evt_data.ndef_detect.cur_size = nfa_rw_cb.ndef_cur_size =
296             p_rw_data->ndef.cur_size;
297         conn_evt_data.ndef_detect.max_size = nfa_rw_cb.ndef_max_size =
298             p_rw_data->ndef.max_size;
299         conn_evt_data.ndef_detect.flags = p_rw_data->ndef.flags;
300       }
301       nfa_dm_act_conn_cback_notify(NFA_NDEF_DETECT_EVT, &conn_evt_data);
302     }
303 
304     nfa_rw_cb.cur_op = NFA_RW_OP_MAX; /* clear current operation */
305   }
306 }
307 
308 /*******************************************************************************
309 **
310 ** Function         nfa_rw_handle_tlv_detect
311 **
312 ** Description      Handler for TLV detection reader/writer event
313 **
314 ** Returns          Nothing
315 **
316 *******************************************************************************/
nfa_rw_handle_tlv_detect(tRW_DATA * p_rw_data)317 static void nfa_rw_handle_tlv_detect(tRW_DATA* p_rw_data) {
318   tNFA_CONN_EVT_DATA conn_evt_data;
319 
320   /* Set TLV detection state */
321   if (nfa_rw_cb.cur_op == NFA_RW_OP_SET_TAG_RO) {
322     if (nfa_rw_cb.tlv_st == NFA_RW_TLV_DETECT_ST_OP_NOT_STARTED) {
323       nfa_rw_cb.tlv_st = NFA_RW_TLV_DETECT_ST_LOCK_TLV_OP_COMPLETE;
324     } else {
325       nfa_rw_cb.tlv_st = NFA_RW_TLV_DETECT_ST_COMPLETE;
326     }
327   } else {
328     if (nfa_rw_cb.cur_op == NFA_RW_OP_DETECT_LOCK_TLV) {
329       nfa_rw_cb.tlv_st |= NFA_RW_TLV_DETECT_ST_LOCK_TLV_OP_COMPLETE;
330     } else if (nfa_rw_cb.cur_op == NFA_RW_OP_DETECT_MEM_TLV) {
331       nfa_rw_cb.tlv_st |= NFA_RW_TLV_DETECT_ST_MEM_TLV_OP_COMPLETE;
332     }
333   }
334 
335   /* Check if TLV detection succeeded */
336   if (p_rw_data->tlv.status == NFC_STATUS_OK) {
337     DLOG_IF(INFO, nfc_debug_enabled) << StringPrintf(
338         "TLV Detection succeeded: num_bytes=%i", p_rw_data->tlv.num_bytes);
339 
340     /* Store tlv properties */
341     conn_evt_data.tlv_detect.status = NFA_STATUS_OK;
342     conn_evt_data.tlv_detect.protocol = p_rw_data->tlv.protocol;
343     conn_evt_data.tlv_detect.num_bytes = p_rw_data->tlv.num_bytes;
344 
345     /* Determine what operation triggered the TLV detection procedure */
346     if (nfa_rw_cb.cur_op == NFA_RW_OP_SET_TAG_RO) {
347       if (nfa_rw_config_tag_ro(nfa_rw_cb.b_hard_lock) != NFC_STATUS_OK) {
348         /* Failed to set tag read only */
349         conn_evt_data.tlv_detect.status = NFA_STATUS_FAILED;
350         nfa_dm_act_conn_cback_notify(NFA_SET_TAG_RO_EVT, &conn_evt_data);
351       }
352     } else {
353       /* current op was stand-alone NFA_DetectTlv. Command complete - perform
354        * cleanup and notify app */
355       nfa_rw_command_complete();
356       nfa_dm_act_conn_cback_notify(NFA_TLV_DETECT_EVT, &conn_evt_data);
357     }
358   }
359 
360   /* Handle failures */
361   if (p_rw_data->tlv.status != NFC_STATUS_OK) {
362     /* Command complete - perform cleanup, notify the app */
363     nfa_rw_command_complete();
364 
365     conn_evt_data.tlv_detect.status = NFA_STATUS_FAILED;
366     if ((nfa_rw_cb.cur_op == NFA_RW_OP_DETECT_LOCK_TLV) ||
367         (nfa_rw_cb.cur_op == NFA_RW_OP_DETECT_MEM_TLV)) {
368       nfa_dm_act_conn_cback_notify(NFA_TLV_DETECT_EVT, &conn_evt_data);
369     } else if (nfa_rw_cb.cur_op == NFA_RW_OP_SET_TAG_RO) {
370       if (nfa_rw_config_tag_ro(nfa_rw_cb.b_hard_lock) != NFC_STATUS_OK) {
371         /* Failed to set tag read only */
372         conn_evt_data.tlv_detect.status = NFA_STATUS_FAILED;
373         nfa_dm_act_conn_cback_notify(NFA_SET_TAG_RO_EVT, &conn_evt_data);
374       }
375     }
376   }
377 }
378 
379 /*******************************************************************************
380 **
381 ** Function         nfa_rw_handle_sleep_wakeup_rsp
382 **
383 ** Description      Handl sleep wakeup
384 **
385 ** Returns          Nothing
386 **
387 *******************************************************************************/
nfa_rw_handle_sleep_wakeup_rsp(tNFC_STATUS status)388 void nfa_rw_handle_sleep_wakeup_rsp(tNFC_STATUS status) {
389   tNFC_ACTIVATE_DEVT activate_params;
390   tRW_EVENT event;
391 
392   if ((nfa_rw_cb.halt_event != RW_T2T_MAX_EVT) &&
393       (nfa_rw_cb.activated_tech_mode == NFC_DISCOVERY_TYPE_POLL_A) &&
394       (nfa_rw_cb.protocol == NFC_PROTOCOL_T2T) &&
395       (nfa_rw_cb.pa_sel_res == NFC_SEL_RES_NFC_FORUM_T2T)) {
396     DLOG_IF(INFO, nfc_debug_enabled) << StringPrintf(
397         "nfa_rw_handle_sleep_wakeup_rsp; Attempt to wake up Type 2 tag from "
398         "HALT State is complete");
399     if (status == NFC_STATUS_OK) {
400       /* Type 2 Tag is wakeup from HALT state */
401       DLOG_IF(INFO, nfc_debug_enabled) << StringPrintf(
402           "nfa_rw_handle_sleep_wakeup_rsp; Handle the NACK rsp received now");
403       /* Initialize control block */
404       activate_params.protocol = nfa_rw_cb.protocol;
405       activate_params.rf_tech_param.param.pa.sel_rsp = nfa_rw_cb.pa_sel_res;
406       activate_params.rf_tech_param.mode = nfa_rw_cb.activated_tech_mode;
407 
408       /* Initialize RW module */
409       if ((RW_SetActivatedTagType(&activate_params, nfa_rw_cback)) !=
410           NFC_STATUS_OK) {
411         /* Log error (stay in NFA_RW_ST_ACTIVATED state until deactivation) */
412         LOG(ERROR) << StringPrintf("RW_SetActivatedTagType failed.");
413         if (nfa_rw_cb.halt_event == RW_T2T_READ_CPLT_EVT) {
414           if (nfa_rw_cb.rw_data.data.p_data)
415             GKI_freebuf(nfa_rw_cb.rw_data.data.p_data);
416           nfa_rw_cb.rw_data.data.p_data = nullptr;
417         }
418         /* Do not try to detect NDEF again but just notify current operation
419          * failed */
420         nfa_rw_cb.halt_event = RW_T2T_MAX_EVT;
421       }
422     }
423 
424     /* The current operation failed with NACK rsp from type 2 tag */
425     nfa_rw_cb.rw_data.status = NFC_STATUS_FAILED;
426     event = nfa_rw_cb.halt_event;
427 
428     /* Got NACK rsp during presence check and legacy presence check performed */
429     if (nfa_rw_cb.cur_op == NFA_RW_OP_PRESENCE_CHECK)
430       nfa_rw_cb.rw_data.status = status;
431 
432     /* If cannot Sleep wakeup tag, then NDEF Detect operation is complete */
433     if ((status != NFC_STATUS_OK) &&
434         (nfa_rw_cb.halt_event == RW_T2T_NDEF_DETECT_EVT))
435       nfa_rw_cb.halt_event = RW_T2T_MAX_EVT;
436 
437     nfa_rw_handle_t2t_evt(event, &nfa_rw_cb.rw_data);
438     nfa_rw_cb.halt_event = RW_T2T_MAX_EVT;
439 
440     /* If Type 2 tag sleep wakeup failed and If in normal mode (not-exclusive RF
441      * mode) then deactivate the link if sleep wakeup failed */
442     if ((nfa_rw_cb.flags & NFA_RW_FL_NOT_EXCL_RF_MODE) &&
443         (status != NFC_STATUS_OK)) {
444       DLOG_IF(INFO, nfc_debug_enabled)
445           << StringPrintf("Sleep wakeup failed. Deactivating...");
446       nfa_dm_rf_deactivate(NFA_DEACTIVATE_TYPE_DISCOVERY);
447     }
448   } else {
449     DLOG_IF(INFO, nfc_debug_enabled) << StringPrintf(
450         "nfa_rw_handle_sleep_wakeup_rsp; Legacy presence check performed");
451     /* Legacy presence check performed */
452     nfa_rw_handle_presence_check_rsp(status);
453   }
454 }
455 
456 /*******************************************************************************
457 **
458 ** Function         nfa_rw_handle_presence_check_rsp
459 **
460 ** Description      Handler RW_T#t_PRESENCE_CHECK_EVT
461 **
462 ** Returns          Nothing
463 **
464 *******************************************************************************/
nfa_rw_handle_presence_check_rsp(tNFC_STATUS status)465 void nfa_rw_handle_presence_check_rsp(tNFC_STATUS status) {
466   NFC_HDR* p_pending_msg;
467 
468   /* Stop the presence check timer - timer may have been started when presence
469    * check started */
470   nfa_rw_stop_presence_check_timer();
471   // The CLF can report more detailed information on the failure cases,
472   // some failures can be considered as success presence check.
473   if ((status == NFA_STATUS_RF_UNEXPECTED_DATA) ||
474       (status == NFA_STATUS_RF_PROTOCOL_ERR)) {
475     DLOG_IF(INFO, nfc_debug_enabled) << StringPrintf(
476         "%s - status %x, consider card present", __func__, status);
477     status = NFA_STATUS_OK;
478   }
479   if (status == NFA_STATUS_OK) {
480     /* Clear the BUSY flag and restart the presence-check timer */
481     nfa_rw_command_complete();
482     if (nfa_rw_cb.pres_check_tag && (nfa_rw_cb.pres_check_tag_err_count != 0)) {
483       nfa_rw_cb.pres_check_tag_err_count = 0;
484     }
485   } else {
486     /* If presence check failed just clear the BUSY flag */
487     nfa_rw_cb.flags &= ~NFA_RW_FL_API_BUSY;
488   }
489 
490   /* Handle presence check due to auto-presence-check  */
491   if (nfa_rw_cb.flags & NFA_RW_FL_AUTO_PRESENCE_CHECK_BUSY) {
492     nfa_rw_cb.flags &= ~NFA_RW_FL_AUTO_PRESENCE_CHECK_BUSY;
493 
494     /* If an API was called during auto-presence-check, then handle it now */
495     if (nfa_rw_cb.p_pending_msg) {
496       /* If NFA_RwPresenceCheck was called during auto-presence-check, notify
497        * app of result */
498       if (nfa_rw_cb.p_pending_msg->op_req.op == NFA_RW_OP_PRESENCE_CHECK) {
499         /* Notify app of presence check status */
500         tNFA_CONN_EVT_DATA nfa_conn_evt_data;
501         nfa_conn_evt_data.status = status;
502         nfa_dm_act_conn_cback_notify(NFA_PRESENCE_CHECK_EVT,
503                                      &nfa_conn_evt_data);
504         GKI_freebuf(nfa_rw_cb.p_pending_msg);
505         nfa_rw_cb.p_pending_msg = nullptr;
506       }
507       /* For all other APIs called during auto-presence check, perform the
508          command now (if tag is still present) */
509       else if (status == NFC_STATUS_OK) {
510         DLOG_IF(INFO, nfc_debug_enabled) << StringPrintf(
511             "Performing deferred operation after presence check...");
512         p_pending_msg = (NFC_HDR*)nfa_rw_cb.p_pending_msg;
513         nfa_rw_cb.p_pending_msg = nullptr;
514         nfa_rw_handle_event(p_pending_msg);
515         GKI_freebuf(p_pending_msg);
516       } else {
517         /* Tag no longer present. Free command for pending API command */
518         GKI_freebuf(nfa_rw_cb.p_pending_msg);
519         nfa_rw_cb.p_pending_msg = nullptr;
520       }
521     }
522 
523     /* Auto-presence check failed. Deactivate */
524     if (status != NFC_STATUS_OK) {
525       DLOG_IF(INFO, nfc_debug_enabled)
526           << StringPrintf("Auto presence check failed. Deactivating...");
527       nfa_dm_rf_deactivate(NFA_DEACTIVATE_TYPE_DISCOVERY);
528     }
529   }
530   /* Handle presence check due to NFA_RwPresenceCheck API call */
531   else {
532     if (status != NFA_STATUS_OK) {
533       nfa_rw_cb.pres_check_iso_dep_nak_err_cnt++;
534 
535       if ((nfa_rw_cb.pres_check_iso_dep_nak == true) &&
536           (nfa_rw_cb.pres_check_iso_dep_nak_err_cnt <= 3)) {
537         DLOG_IF(INFO, nfc_debug_enabled) << StringPrintf(
538             "%s - ISO_DEP_NAK presence check failed, try up to 3 times "
539             "(attempt nb #%d)",
540             __func__, nfa_rw_cb.pres_check_iso_dep_nak_err_cnt);
541         if (nfa_rw_cb.pres_check_iso_dep_nak_count == 1) {
542           // If status failed on 3 first attempts, then switch to alternative
543           // method
544           nfa_rw_cb.pres_check_iso_dep_nak_count = 0;
545         }
546       }
547     } else {
548       nfa_rw_cb.pres_check_iso_dep_nak_err_cnt = 0;
549     }
550     /* Notify app of presence check status */
551     tNFA_CONN_EVT_DATA nfa_conn_evt_data;
552     nfa_conn_evt_data.status = status;
553     nfa_dm_act_conn_cback_notify(NFA_PRESENCE_CHECK_EVT, &nfa_conn_evt_data);
554 
555     /* If in normal mode (not-exclusive RF mode) then deactivate the link if
556      * presence check failed */
557     if ((nfa_rw_cb.flags & NFA_RW_FL_NOT_EXCL_RF_MODE) &&
558         (nfa_conn_evt_data.status != NFC_STATUS_OK)) {
559       // If ISO-DEP NAK pres check AND
560       // First attempt or less than 3 retries
561       // Return tag to IDLE state, new command will come from JNI
562       if ((nfa_rw_cb.pres_check_iso_dep_nak == true) &&
563           ((nfa_rw_cb.pres_check_iso_dep_nak_count == 1) ||
564            (nfa_rw_cb.pres_check_iso_dep_nak_err_cnt <= 3))) {
565         DLOG_IF(INFO, nfc_debug_enabled) << StringPrintf(
566             "%s - ISO_DEP_NAK presence check retry nb #%d failed, do not "
567             "deactivate",
568             __func__, nfa_rw_cb.pres_check_iso_dep_nak_err_cnt);
569         rw_t4t_handle_isodep_nak_fallback();
570         return;
571       } else if ((nfa_rw_cb.pres_check_tag == true) &&
572                  ((++nfa_rw_cb.pres_check_tag_err_count) <= 3)) {
573         DLOG_IF(INFO, nfc_debug_enabled) << StringPrintf(
574             "%s - presence check failed, try up to 3 times (attempt nb #%d)",
575             __func__, nfa_rw_cb.pres_check_tag_err_count);
576 
577         return;
578       }
579       DLOG_IF(INFO, nfc_debug_enabled)
580           << StringPrintf("Presence check failed. Deactivating...");
581       nfa_dm_rf_deactivate(NFA_DEACTIVATE_TYPE_DISCOVERY);
582     }
583   }
584 }
585 
586 /*******************************************************************************
587 **
588 ** Function         nfa_rw_handle_t1t_evt
589 **
590 ** Description      Handler for Type-1 tag reader/writer events
591 **
592 ** Returns          Nothing
593 **
594 *******************************************************************************/
nfa_rw_handle_t1t_evt(tRW_EVENT event,tRW_DATA * p_rw_data)595 static void nfa_rw_handle_t1t_evt(tRW_EVENT event, tRW_DATA* p_rw_data) {
596   tNFA_CONN_EVT_DATA conn_evt_data;
597   tNFA_TAG_PARAMS tag_params;
598   uint8_t* p_rid_rsp;
599   tNFA_STATUS activation_status;
600 
601   conn_evt_data.status = p_rw_data->data.status;
602   switch (event) {
603     case RW_T1T_RID_EVT:
604       if (p_rw_data->data.p_data != nullptr) {
605         /* Assume the data is just the response byte sequence */
606         p_rid_rsp = (uint8_t*)(p_rw_data->data.p_data + 1) +
607                     p_rw_data->data.p_data->offset;
608         /* Fetch HR from RID response message */
609         STREAM_TO_ARRAY(tag_params.t1t.hr, p_rid_rsp, T1T_HR_LEN);
610         /* Fetch UID0-3 from RID response message */
611         STREAM_TO_ARRAY(tag_params.t1t.uid, p_rid_rsp, T1T_CMD_UID_LEN);
612         GKI_freebuf(p_rw_data->data.p_data);
613         p_rw_data->data.p_data = nullptr;
614       }
615 
616       /* Command complete - perform cleanup, notify the app */
617       nfa_rw_command_complete();
618 
619       if (p_rw_data->status == NFC_STATUS_TIMEOUT) {
620         activation_status = NFA_STATUS_TIMEOUT;
621       } else {
622         activation_status = NFA_STATUS_OK;
623       }
624 
625       nfa_dm_notify_activation_status(activation_status, &tag_params);
626       break;
627 
628     case RW_T1T_RALL_CPLT_EVT:
629     case RW_T1T_READ_CPLT_EVT:
630     case RW_T1T_RSEG_CPLT_EVT:
631     case RW_T1T_READ8_CPLT_EVT:
632       nfa_rw_send_data_to_upper(p_rw_data);
633 
634       /* Command complete - perform cleanup, notify the app */
635       nfa_rw_command_complete();
636       nfa_dm_act_conn_cback_notify(NFA_READ_CPLT_EVT, &conn_evt_data);
637       break;
638 
639     case RW_T1T_WRITE_E_CPLT_EVT:
640     case RW_T1T_WRITE_NE_CPLT_EVT:
641     case RW_T1T_WRITE_E8_CPLT_EVT:
642     case RW_T1T_WRITE_NE8_CPLT_EVT:
643       nfa_rw_send_data_to_upper(p_rw_data);
644 
645       /* Command complete - perform cleanup, notify the app */
646       nfa_rw_command_complete();
647       nfa_dm_act_conn_cback_notify(NFA_WRITE_CPLT_EVT, &conn_evt_data);
648       break;
649 
650     case RW_T1T_TLV_DETECT_EVT:
651       nfa_rw_handle_tlv_detect(p_rw_data);
652       break;
653 
654     case RW_T1T_NDEF_DETECT_EVT:
655       nfa_rw_cb.tlv_st = NFA_RW_TLV_DETECT_ST_COMPLETE;
656 
657       if ((p_rw_data->status != NFC_STATUS_OK) &&
658           (nfa_rw_cb.cur_op == NFA_RW_OP_WRITE_NDEF) &&
659           (p_rw_data->ndef.flags & NFA_RW_NDEF_FL_FORMATABLE) &&
660           (!(p_rw_data->ndef.flags & NFA_RW_NDEF_FL_FORMATED)) &&
661           (p_rw_data->ndef.flags & NFA_RW_NDEF_FL_SUPPORTED)) {
662         /* Tag is in Initialized state, Format the tag first and then Write NDEF
663          */
664         if (RW_T1tFormatNDef() == NFC_STATUS_OK) break;
665       }
666 
667       nfa_rw_handle_ndef_detect(p_rw_data);
668 
669       break;
670 
671     case RW_T1T_NDEF_READ_EVT:
672       nfa_rw_cb.tlv_st = NFA_RW_TLV_DETECT_ST_COMPLETE;
673       if (p_rw_data->status == NFC_STATUS_OK) {
674         /* Process the ndef record */
675         nfa_dm_ndef_handle_message(NFA_STATUS_OK, nfa_rw_cb.p_ndef_buf,
676                                    nfa_rw_cb.ndef_cur_size);
677       } else {
678         /* Notify app of failure */
679         if (nfa_rw_cb.cur_op == NFA_RW_OP_READ_NDEF) {
680           /* If current operation is READ_NDEF, then notify ndef handlers of
681            * failure */
682           nfa_dm_ndef_handle_message(NFA_STATUS_FAILED, nullptr, 0);
683         }
684       }
685 
686       /* Command complete - perform cleanup, notify the app */
687       nfa_rw_command_complete();
688       nfa_dm_act_conn_cback_notify(NFA_READ_CPLT_EVT, &conn_evt_data);
689 
690       /* Free ndef buffer */
691       nfa_rw_free_ndef_rx_buf();
692       break;
693 
694     case RW_T1T_NDEF_WRITE_EVT:
695       if (p_rw_data->data.status != NFA_STATUS_OK)
696         nfa_rw_cb.ndef_st = NFA_RW_NDEF_ST_UNKNOWN;
697       nfa_rw_cb.tlv_st = NFA_RW_TLV_DETECT_ST_COMPLETE;
698 
699       /* Command complete - perform cleanup, notify the app */
700       nfa_rw_command_complete();
701 
702       /* Notify app */
703       conn_evt_data.status = (p_rw_data->data.status == NFC_STATUS_OK)
704                                  ? NFA_STATUS_OK
705                                  : NFA_STATUS_FAILED;
706       if (nfa_rw_cb.cur_op == NFA_RW_OP_WRITE_NDEF) {
707         /* Update local cursize of ndef message */
708         nfa_rw_cb.ndef_cur_size = nfa_rw_cb.ndef_wr_len;
709       }
710 
711       /* Notify app of ndef write complete status */
712       nfa_dm_act_conn_cback_notify(NFA_WRITE_CPLT_EVT, &conn_evt_data);
713       break;
714 
715     case RW_T1T_SET_TAG_RO_EVT:
716       /* Command complete - perform cleanup, notify the app */
717       nfa_rw_command_complete();
718       nfa_dm_act_conn_cback_notify(NFA_SET_TAG_RO_EVT, &conn_evt_data);
719       break;
720 
721     case RW_T1T_RAW_FRAME_EVT:
722       nfa_rw_send_data_to_upper(p_rw_data);
723       /* Command complete - perform cleanup */
724       nfa_rw_command_complete();
725       break;
726 
727     case RW_T1T_PRESENCE_CHECK_EVT: /* Presence check completed */
728       nfa_rw_handle_presence_check_rsp(p_rw_data->status);
729       break;
730 
731     case RW_T1T_FORMAT_CPLT_EVT:
732 
733       if (p_rw_data->data.status == NFA_STATUS_OK)
734         nfa_rw_cb.ndef_st = NFA_RW_NDEF_ST_UNKNOWN;
735 
736       if (nfa_rw_cb.cur_op == NFA_RW_OP_WRITE_NDEF) {
737         /* if format operation was done as part of ndef-write operation, now
738          * start NDEF Write */
739         if ((p_rw_data->data.status != NFA_STATUS_OK) ||
740             ((conn_evt_data.status = RW_T1tDetectNDef()) != NFC_STATUS_OK)) {
741           /* Command complete - perform cleanup, notify app */
742           nfa_rw_command_complete();
743           nfa_rw_cb.ndef_st = NFA_RW_NDEF_ST_FALSE;
744 
745           /* if format operation failed or ndef detection did not start, then
746            * notify app of ndef-write operation failure */
747           conn_evt_data.status = NFA_STATUS_FAILED;
748           nfa_dm_act_conn_cback_notify(NFA_WRITE_CPLT_EVT, &conn_evt_data);
749         }
750       } else {
751         /* Command complete - perform cleanup, notify the app */
752         nfa_rw_command_complete();
753         nfa_dm_act_conn_cback_notify(NFA_FORMAT_CPLT_EVT, &conn_evt_data);
754       }
755       break;
756 
757     case RW_T1T_INTF_ERROR_EVT:
758       nfa_dm_act_conn_cback_notify(NFA_RW_INTF_ERROR_EVT, &conn_evt_data);
759       break;
760   }
761 }
762 
763 /*******************************************************************************
764 **
765 ** Function         nfa_rw_handle_t2t_evt
766 **
767 ** Description      Handler for Type-2 tag reader/writer events
768 **
769 ** Returns          Nothing
770 **
771 *******************************************************************************/
nfa_rw_handle_t2t_evt(tRW_EVENT event,tRW_DATA * p_rw_data)772 static void nfa_rw_handle_t2t_evt(tRW_EVENT event, tRW_DATA* p_rw_data) {
773   tNFA_CONN_EVT_DATA conn_evt_data;
774 
775   conn_evt_data.status = p_rw_data->status;
776 
777   if (p_rw_data->status == NFC_STATUS_REJECTED) {
778     DLOG_IF(INFO, nfc_debug_enabled) << StringPrintf(
779         "; Waking the tag first before handling the "
780         "response!");
781     /* Received NACK. Let DM wakeup the tag first (by putting tag to sleep and
782      * then waking it up) */
783     p_rw_data->status = nfa_dm_disc_sleep_wakeup();
784     if (p_rw_data->status == NFC_STATUS_OK) {
785       nfa_rw_cb.halt_event = event;
786       memcpy(&nfa_rw_cb.rw_data, p_rw_data, sizeof(tRW_DATA));
787       return;
788     }
789   }
790 
791   switch (event) {
792     case RW_T2T_READ_CPLT_EVT: /* Read completed          */
793       nfa_rw_send_data_to_upper(p_rw_data);
794       /* Command complete - perform cleanup, notify the app */
795       nfa_rw_command_complete();
796       nfa_dm_act_conn_cback_notify(NFA_READ_CPLT_EVT, &conn_evt_data);
797       break;
798 
799     case RW_T2T_WRITE_CPLT_EVT: /* Write completed         */
800       /* Command complete - perform cleanup, notify the app */
801       nfa_rw_command_complete();
802       nfa_dm_act_conn_cback_notify(NFA_WRITE_CPLT_EVT, &conn_evt_data);
803       break;
804 
805     case RW_T2T_SELECT_CPLT_EVT: /* Sector select completed */
806       /* Command complete - perform cleanup, notify the app */
807       nfa_rw_command_complete();
808       nfa_dm_act_conn_cback_notify(NFA_SELECT_CPLT_EVT, &conn_evt_data);
809       break;
810 
811     case RW_T2T_NDEF_DETECT_EVT: /* NDEF detection complete */
812       if ((p_rw_data->status == NFC_STATUS_OK) ||
813           ((p_rw_data->status == NFC_STATUS_FAILED) &&
814            ((p_rw_data->ndef.flags == NFA_RW_NDEF_FL_UNKNOWN) ||
815             (nfa_rw_cb.halt_event == RW_T2T_MAX_EVT))) ||
816           (nfa_rw_cb.skip_dyn_locks == true)) {
817         /* NDEF Detection is complete */
818         nfa_rw_cb.skip_dyn_locks = false;
819         nfa_rw_handle_ndef_detect(p_rw_data);
820       } else {
821         /* Try to detect NDEF again, this time without reading dynamic lock
822          * bytes */
823         nfa_rw_cb.skip_dyn_locks = true;
824         nfa_rw_detect_ndef();
825       }
826       break;
827 
828     case RW_T2T_TLV_DETECT_EVT: /* Lock control/Mem/Prop tlv detection complete
829                                  */
830       nfa_rw_handle_tlv_detect(p_rw_data);
831       break;
832 
833     case RW_T2T_NDEF_READ_EVT: /* NDEF read completed     */
834       if (p_rw_data->status == NFC_STATUS_OK) {
835         /* Process the ndef record */
836         nfa_dm_ndef_handle_message(NFA_STATUS_OK, nfa_rw_cb.p_ndef_buf,
837                                    nfa_rw_cb.ndef_cur_size);
838       } else {
839         /* Notify app of failure */
840         if (nfa_rw_cb.cur_op == NFA_RW_OP_READ_NDEF) {
841           /* If current operation is READ_NDEF, then notify ndef handlers of
842            * failure */
843           nfa_dm_ndef_handle_message(NFA_STATUS_FAILED, nullptr, 0);
844         }
845       }
846 
847       /* Notify app of read status */
848       conn_evt_data.status = p_rw_data->status;
849       nfa_dm_act_conn_cback_notify(NFA_READ_CPLT_EVT, &conn_evt_data);
850       /* Free ndef buffer */
851       nfa_rw_free_ndef_rx_buf();
852 
853       /* Command complete - perform cleanup */
854       nfa_rw_command_complete();
855       break;
856 
857     case RW_T2T_NDEF_WRITE_EVT: /* NDEF write complete     */
858 
859       /* Command complete - perform cleanup, notify the app */
860       nfa_rw_command_complete();
861 
862       /* Notify app */
863       conn_evt_data.status = (p_rw_data->data.status == NFC_STATUS_OK)
864                                  ? NFA_STATUS_OK
865                                  : NFA_STATUS_FAILED;
866       if (nfa_rw_cb.cur_op == NFA_RW_OP_WRITE_NDEF) {
867         /* Update local cursize of ndef message */
868         nfa_rw_cb.ndef_cur_size = nfa_rw_cb.ndef_wr_len;
869       }
870 
871       /* Notify app of ndef write complete status */
872       nfa_dm_act_conn_cback_notify(NFA_WRITE_CPLT_EVT, &conn_evt_data);
873 
874       break;
875 
876     case RW_T2T_SET_TAG_RO_EVT:
877       /* Command complete - perform cleanup, notify the app */
878       nfa_rw_command_complete();
879       nfa_dm_act_conn_cback_notify(NFA_SET_TAG_RO_EVT, &conn_evt_data);
880       break;
881 
882     case RW_T2T_RAW_FRAME_EVT:
883       nfa_rw_send_data_to_upper(p_rw_data);
884       /* Command complete - perform cleanup */
885       if (p_rw_data->status != NFC_STATUS_CONTINUE) {
886         nfa_rw_command_complete();
887       }
888       break;
889 
890     case RW_T2T_PRESENCE_CHECK_EVT: /* Presence check completed */
891       nfa_rw_handle_presence_check_rsp(p_rw_data->status);
892       break;
893 
894     case RW_T2T_FORMAT_CPLT_EVT:
895       if (p_rw_data->data.status == NFA_STATUS_OK)
896         nfa_rw_cb.ndef_st = NFA_RW_NDEF_ST_UNKNOWN;
897 
898       /* Command complete - perform cleanup, notify the app */
899       nfa_rw_command_complete();
900       nfa_dm_act_conn_cback_notify(NFA_FORMAT_CPLT_EVT, &conn_evt_data);
901       break;
902 
903     case RW_T2T_INTF_ERROR_EVT:
904       nfa_dm_act_conn_cback_notify(NFA_RW_INTF_ERROR_EVT, &conn_evt_data);
905       break;
906   }
907 }
908 
909 /*******************************************************************************
910 **
911 ** Function         nfa_rw_handle_t3t_evt
912 **
913 ** Description      Handler for Type-3 tag reader/writer events
914 **
915 ** Returns          Nothing
916 **
917 *******************************************************************************/
nfa_rw_handle_t3t_evt(tRW_EVENT event,tRW_DATA * p_rw_data)918 static void nfa_rw_handle_t3t_evt(tRW_EVENT event, tRW_DATA* p_rw_data) {
919   tNFA_CONN_EVT_DATA conn_evt_data;
920   tNFA_TAG_PARAMS tag_params;
921 
922   switch (event) {
923     case RW_T3T_NDEF_DETECT_EVT: /* NDEF detection complete */
924       nfa_rw_handle_ndef_detect(p_rw_data);
925       break;
926 
927     case RW_T3T_UPDATE_CPLT_EVT: /* Write completed */
928       /* Command complete - perform cleanup, notify the app */
929       nfa_rw_command_complete();
930 
931       /* Notify app */
932       conn_evt_data.status = (p_rw_data->data.status == NFC_STATUS_OK)
933                                  ? NFA_STATUS_OK
934                                  : NFA_STATUS_FAILED;
935       if (nfa_rw_cb.cur_op == NFA_RW_OP_WRITE_NDEF) {
936         /* Update local cursize of ndef message */
937         nfa_rw_cb.ndef_cur_size = nfa_rw_cb.ndef_wr_len;
938       }
939 
940       /* Notify app of ndef write complete status */
941       nfa_dm_act_conn_cback_notify(NFA_WRITE_CPLT_EVT, &conn_evt_data);
942 
943       break;
944 
945     case RW_T3T_CHECK_CPLT_EVT: /* Read completed */
946       if (p_rw_data->status == NFC_STATUS_OK) {
947         /* Process the ndef record */
948         nfa_dm_ndef_handle_message(NFA_STATUS_OK, nfa_rw_cb.p_ndef_buf,
949                                    nfa_rw_cb.ndef_cur_size);
950       } else {
951         /* Notify app of failure */
952         if (nfa_rw_cb.cur_op == NFA_RW_OP_READ_NDEF) {
953           /* If current operation is READ_NDEF, then notify ndef handlers of
954            * failure */
955           nfa_dm_ndef_handle_message(NFA_STATUS_FAILED, nullptr, 0);
956         }
957       }
958 
959       /* Free ndef buffer */
960       nfa_rw_free_ndef_rx_buf();
961 
962       /* Command complete - perform cleanup, notify the app */
963       nfa_rw_command_complete();
964       conn_evt_data.status = p_rw_data->status;
965       nfa_dm_act_conn_cback_notify(NFA_READ_CPLT_EVT, &conn_evt_data);
966       break;
967 
968     case RW_T3T_CHECK_EVT: /* Segment of data received from type 3 tag */
969       if (nfa_rw_cb.cur_op == NFA_RW_OP_READ_NDEF) {
970         nfa_rw_store_ndef_rx_buf(p_rw_data);
971       } else {
972         nfa_rw_send_data_to_upper(p_rw_data);
973       }
974       break;
975 
976     case RW_T3T_RAW_FRAME_EVT: /* SendRawFrame response */
977       nfa_rw_send_data_to_upper(p_rw_data);
978 
979       if (p_rw_data->status != NFC_STATUS_CONTINUE) {
980         /* Command complete - perform cleanup */
981         nfa_rw_command_complete();
982       }
983       break;
984 
985     case RW_T3T_PRESENCE_CHECK_EVT: /* Presence check completed */
986       nfa_rw_handle_presence_check_rsp(p_rw_data->status);
987       break;
988 
989     case RW_T3T_GET_SYSTEM_CODES_EVT: /* Presence check completed */
990       /* Command complete - perform cleanup */
991       nfa_rw_command_complete();
992 
993       /* System codes retrieved - notify app of ACTIVATION */
994       if (p_rw_data->status == NFC_STATUS_OK) {
995         tag_params.t3t.num_system_codes = p_rw_data->t3t_sc.num_system_codes;
996         tag_params.t3t.p_system_codes = p_rw_data->t3t_sc.p_system_codes;
997       } else {
998         tag_params.t3t.num_system_codes = 0;
999         tag_params.t3t.p_system_codes = nullptr;
1000       }
1001 
1002       nfa_dm_notify_activation_status(NFA_STATUS_OK, &tag_params);
1003       break;
1004 
1005     case RW_T3T_FORMAT_CPLT_EVT: /* Format completed */
1006       /* Command complete - perform cleanup, notify the app */
1007       nfa_rw_command_complete();
1008 
1009       /* Notify app */
1010       conn_evt_data.status = (p_rw_data->data.status == NFC_STATUS_OK)
1011                                  ? NFA_STATUS_OK
1012                                  : NFA_STATUS_FAILED;
1013 
1014       /* Notify app of ndef write complete status */
1015       nfa_dm_act_conn_cback_notify(NFA_FORMAT_CPLT_EVT, &conn_evt_data);
1016       break;
1017 
1018     case RW_T3T_INTF_ERROR_EVT:
1019       DLOG_IF(INFO, nfc_debug_enabled)
1020           << StringPrintf("%s; send deactivate", __func__);
1021       nfa_dm_rf_deactivate(NFA_DEACTIVATE_TYPE_DISCOVERY);
1022       conn_evt_data.status = p_rw_data->status;
1023       nfa_dm_act_conn_cback_notify(NFA_RW_INTF_ERROR_EVT, &conn_evt_data);
1024       break;
1025 
1026     case RW_T3T_SET_READ_ONLY_CPLT_EVT:
1027       /* Command complete - perform cleanup, notify the app */
1028       nfa_rw_command_complete();
1029 
1030       conn_evt_data.status = p_rw_data->status;
1031       nfa_dm_act_conn_cback_notify(NFA_SET_TAG_RO_EVT, &conn_evt_data);
1032       break;
1033 
1034     default:
1035       DLOG_IF(INFO, nfc_debug_enabled)
1036           << StringPrintf("; Unhandled RW event 0x%X", event);
1037       break;
1038   }
1039 }
1040 
1041 /*******************************************************************************
1042 **
1043 ** Function         nfa_rw_handle_t4t_evt
1044 **
1045 ** Description      Handler for Type-4 tag reader/writer events
1046 **
1047 ** Returns          Nothing
1048 **
1049 *******************************************************************************/
nfa_rw_handle_t4t_evt(tRW_EVENT event,tRW_DATA * p_rw_data)1050 static void nfa_rw_handle_t4t_evt(tRW_EVENT event, tRW_DATA* p_rw_data) {
1051   tNFA_CONN_EVT_DATA conn_evt_data;
1052 
1053   switch (event) {
1054     case RW_T4T_NDEF_DETECT_EVT: /* Result of NDEF detection procedure */
1055       nfa_rw_handle_ndef_detect(p_rw_data);
1056       break;
1057 
1058     case RW_T4T_NDEF_FORMAT_CPLT_EVT:
1059       /* Command complete - perform cleanup, notify the app */
1060       nfa_rw_command_complete();
1061       nfa_rw_cb.cur_op = NFA_RW_OP_MAX;
1062       nfa_rw_cb.ndef_cur_size = p_rw_data->ndef.cur_size;
1063       nfa_rw_cb.ndef_max_size = p_rw_data->ndef.max_size;
1064       conn_evt_data.status = (p_rw_data->status == NFC_STATUS_OK)
1065                                  ? NFA_STATUS_OK
1066                                  : NFA_STATUS_FAILED;
1067 
1068       nfa_dm_act_conn_cback_notify(NFA_FORMAT_CPLT_EVT, &conn_evt_data);
1069       break;
1070 
1071     case RW_T4T_NDEF_READ_EVT: /* Segment of data received from type 4 tag */
1072       if (nfa_rw_cb.cur_op == NFA_RW_OP_READ_NDEF) {
1073         nfa_rw_store_ndef_rx_buf(p_rw_data);
1074       } else {
1075         nfa_rw_send_data_to_upper(p_rw_data);
1076       }
1077       break;
1078 
1079     case RW_T4T_NDEF_READ_CPLT_EVT: /* Read operation completed           */
1080       if (nfa_rw_cb.cur_op == NFA_RW_OP_READ_NDEF) {
1081         nfa_rw_store_ndef_rx_buf(p_rw_data);
1082 
1083         /* Process the ndef record */
1084         nfa_dm_ndef_handle_message(NFA_STATUS_OK, nfa_rw_cb.p_ndef_buf,
1085                                    nfa_rw_cb.ndef_cur_size);
1086 
1087         /* Free ndef buffer */
1088         nfa_rw_free_ndef_rx_buf();
1089       } else {
1090         nfa_rw_send_data_to_upper(p_rw_data);
1091       }
1092 
1093       /* Command complete - perform cleanup, notify the app */
1094       nfa_rw_command_complete();
1095       nfa_rw_cb.cur_op = NFA_RW_OP_MAX;
1096       conn_evt_data.status = NFC_STATUS_OK;
1097       nfa_dm_act_conn_cback_notify(NFA_READ_CPLT_EVT, &conn_evt_data);
1098       break;
1099 
1100     case RW_T4T_NDEF_READ_FAIL_EVT: /* Read operation failed              */
1101       if (nfa_rw_cb.cur_op == NFA_RW_OP_READ_NDEF) {
1102         /* If current operation is READ_NDEF, then notify ndef handlers of
1103          * failure */
1104         nfa_dm_ndef_handle_message(NFA_STATUS_FAILED, nullptr, 0);
1105 
1106         /* Free ndef buffer */
1107         nfa_rw_free_ndef_rx_buf();
1108       }
1109 
1110       /* Command complete - perform cleanup, notify the app */
1111       nfa_rw_command_complete();
1112       nfa_rw_cb.cur_op = NFA_RW_OP_MAX;
1113       conn_evt_data.status = NFA_STATUS_FAILED;
1114       nfa_dm_act_conn_cback_notify(NFA_READ_CPLT_EVT, &conn_evt_data);
1115       break;
1116 
1117     case RW_T4T_NDEF_UPDATE_CPLT_EVT: /* Update operation completed         */
1118     case RW_T4T_NDEF_UPDATE_FAIL_EVT: /* Update operation failed            */
1119 
1120       if (nfa_rw_cb.cur_op == NFA_RW_OP_WRITE_NDEF) {
1121         /* Update local cursize of ndef message */
1122         nfa_rw_cb.ndef_cur_size = nfa_rw_cb.ndef_wr_len;
1123       }
1124 
1125       /* Notify app */
1126       if (event == RW_T4T_NDEF_UPDATE_CPLT_EVT)
1127         conn_evt_data.status = NFA_STATUS_OK;
1128       else
1129         conn_evt_data.status = NFA_STATUS_FAILED;
1130 
1131       /* Command complete - perform cleanup, notify the app */
1132       nfa_rw_command_complete();
1133       nfa_rw_cb.cur_op = NFA_RW_OP_MAX;
1134       nfa_dm_act_conn_cback_notify(NFA_WRITE_CPLT_EVT, &conn_evt_data);
1135       break;
1136 
1137     case RW_T4T_RAW_FRAME_EVT: /* Raw Frame data event         */
1138       nfa_rw_send_data_to_upper(p_rw_data);
1139 
1140       if (p_rw_data->status != NFC_STATUS_CONTINUE) {
1141         /* Command complete - perform cleanup */
1142         nfa_rw_command_complete();
1143         nfa_rw_cb.cur_op = NFA_RW_OP_MAX;
1144       }
1145       break;
1146 
1147     case RW_T4T_SET_TO_RO_EVT: /* Tag is set as read only          */
1148       conn_evt_data.status = p_rw_data->status;
1149       nfa_dm_act_conn_cback_notify(NFA_SET_TAG_RO_EVT, &conn_evt_data);
1150 
1151       nfa_rw_command_complete();
1152       nfa_rw_cb.cur_op = NFA_RW_OP_MAX;
1153       break;
1154 
1155     case RW_T4T_INTF_ERROR_EVT: /* RF Interface error event         */
1156       conn_evt_data.status = p_rw_data->status;
1157       nfa_dm_act_conn_cback_notify(NFA_RW_INTF_ERROR_EVT, &conn_evt_data);
1158 
1159       nfa_rw_command_complete();
1160       nfa_rw_cb.cur_op = NFA_RW_OP_MAX;
1161       break;
1162 
1163     case RW_T4T_PRESENCE_CHECK_EVT: /* Presence check completed */
1164       nfa_rw_handle_presence_check_rsp(p_rw_data->status);
1165       break;
1166 
1167     default:
1168       DLOG_IF(INFO, nfc_debug_enabled)
1169           << StringPrintf("; Unhandled RW event 0x%X", event);
1170       break;
1171   }
1172 }
1173 
1174 /*******************************************************************************
1175 **
1176 ** Function         nfa_rw_handle_i93_evt
1177 **
1178 ** Description      Handler for ISO 15693 tag reader/writer events
1179 **
1180 ** Returns          Nothing
1181 **
1182 *******************************************************************************/
nfa_rw_handle_i93_evt(tRW_EVENT event,tRW_DATA * p_rw_data)1183 static void nfa_rw_handle_i93_evt(tRW_EVENT event, tRW_DATA* p_rw_data) {
1184   tNFA_CONN_EVT_DATA conn_evt_data;
1185   tNFA_TAG_PARAMS i93_params;
1186 
1187   switch (event) {
1188     case RW_I93_NDEF_DETECT_EVT: /* Result of NDEF detection procedure */
1189       nfa_rw_handle_ndef_detect(p_rw_data);
1190       break;
1191 
1192     case RW_I93_NDEF_READ_EVT: /* Segment of data received from type 4 tag */
1193       if (nfa_rw_cb.cur_op == NFA_RW_OP_READ_NDEF) {
1194         nfa_rw_store_ndef_rx_buf(p_rw_data);
1195       } else {
1196         nfa_rw_send_data_to_upper(p_rw_data);
1197       }
1198       break;
1199 
1200     case RW_I93_NDEF_READ_CPLT_EVT: /* Read operation completed           */
1201       if (nfa_rw_cb.cur_op == NFA_RW_OP_READ_NDEF) {
1202         nfa_rw_store_ndef_rx_buf(p_rw_data);
1203 
1204         /* Process the ndef record */
1205         nfa_dm_ndef_handle_message(NFA_STATUS_OK, nfa_rw_cb.p_ndef_buf,
1206                                    nfa_rw_cb.ndef_cur_size);
1207 
1208         /* Free ndef buffer */
1209         nfa_rw_free_ndef_rx_buf();
1210       } else {
1211         nfa_rw_send_data_to_upper(p_rw_data);
1212       }
1213 
1214       /* Command complete - perform cleanup, notify app */
1215       nfa_rw_command_complete();
1216       nfa_rw_cb.cur_op = NFA_RW_OP_MAX; /* clear current operation */
1217       conn_evt_data.status = NFC_STATUS_OK;
1218       nfa_dm_act_conn_cback_notify(NFA_READ_CPLT_EVT, &conn_evt_data);
1219       break;
1220 
1221     case RW_I93_NDEF_READ_FAIL_EVT: /* Read operation failed              */
1222       if (nfa_rw_cb.cur_op == NFA_RW_OP_READ_NDEF) {
1223         /* If current operation is READ_NDEF, then notify ndef handlers of
1224          * failure */
1225         nfa_dm_ndef_handle_message(NFA_STATUS_FAILED, nullptr, 0);
1226 
1227         /* Free ndef buffer */
1228         nfa_rw_free_ndef_rx_buf();
1229       }
1230 
1231       /* Command complete - perform cleanup, notify app */
1232       nfa_rw_command_complete();
1233       nfa_rw_cb.cur_op = NFA_RW_OP_MAX; /* clear current operation */
1234       conn_evt_data.status = NFA_STATUS_FAILED;
1235       nfa_dm_act_conn_cback_notify(NFA_READ_CPLT_EVT, &conn_evt_data);
1236       break;
1237 
1238     case RW_I93_NDEF_UPDATE_CPLT_EVT: /* Update operation completed         */
1239     case RW_I93_NDEF_UPDATE_FAIL_EVT: /* Update operation failed            */
1240 
1241       if (nfa_rw_cb.cur_op == NFA_RW_OP_WRITE_NDEF) {
1242         /* Update local cursize of ndef message */
1243         nfa_rw_cb.ndef_cur_size = nfa_rw_cb.ndef_wr_len;
1244       }
1245 
1246       /* Command complete - perform cleanup, notify app */
1247       nfa_rw_command_complete();
1248       nfa_rw_cb.cur_op = NFA_RW_OP_MAX; /* clear current operation */
1249 
1250       if (event == RW_I93_NDEF_UPDATE_CPLT_EVT)
1251         conn_evt_data.status = NFA_STATUS_OK;
1252       else
1253         conn_evt_data.status = NFA_STATUS_FAILED;
1254 
1255       /* Notify app of ndef write complete status */
1256       nfa_dm_act_conn_cback_notify(NFA_WRITE_CPLT_EVT, &conn_evt_data);
1257       break;
1258 
1259     case RW_I93_RAW_FRAME_EVT: /* Raw Frame data event         */
1260       nfa_rw_send_data_to_upper(p_rw_data);
1261       if (p_rw_data->status != NFC_STATUS_CONTINUE) {
1262         /* Command complete - perform cleanup */
1263         nfa_rw_command_complete();
1264       }
1265       break;
1266 
1267     case RW_I93_INTF_ERROR_EVT: /* RF Interface error event         */
1268       /* Command complete - perform cleanup, notify app */
1269       nfa_rw_command_complete();
1270 
1271       if (nfa_rw_cb.flags & NFA_RW_FL_ACTIVATION_NTF_PENDING) {
1272         nfa_rw_cb.flags &= ~NFA_RW_FL_ACTIVATION_NTF_PENDING;
1273 
1274         memset(&i93_params, 0x00, sizeof(tNFA_TAG_PARAMS));
1275         memcpy(i93_params.i93.uid, nfa_rw_cb.i93_uid, I93_UID_BYTE_LEN);
1276 
1277         nfa_dm_notify_activation_status(NFA_STATUS_OK, &i93_params);
1278       } else {
1279         conn_evt_data.status = p_rw_data->status;
1280         nfa_dm_act_conn_cback_notify(NFA_RW_INTF_ERROR_EVT, &conn_evt_data);
1281       }
1282 
1283       nfa_rw_cb.cur_op = NFA_RW_OP_MAX; /* clear current operation */
1284       break;
1285 
1286     case RW_I93_PRESENCE_CHECK_EVT: /* Presence check completed */
1287       nfa_rw_handle_presence_check_rsp(p_rw_data->status);
1288       break;
1289 
1290     case RW_I93_FORMAT_CPLT_EVT: /* Format procedure complete          */
1291       if (p_rw_data->data.status == NFA_STATUS_OK)
1292         nfa_rw_cb.ndef_st = NFA_RW_NDEF_ST_UNKNOWN;
1293 
1294       /* Command complete - perform cleanup, notify app */
1295       nfa_rw_command_complete();
1296       nfa_rw_cb.cur_op = NFA_RW_OP_MAX; /* clear current operation */
1297       conn_evt_data.status = p_rw_data->status;
1298       nfa_dm_act_conn_cback_notify(NFA_FORMAT_CPLT_EVT, &conn_evt_data);
1299       break;
1300 
1301     case RW_I93_SET_TAG_RO_EVT: /* Set read-only procedure complete   */
1302       nfa_rw_cb.flags |= NFA_RW_FL_TAG_IS_READONLY;
1303 
1304       /* Command complete - perform cleanup, notify app */
1305       nfa_rw_command_complete();
1306       nfa_rw_cb.cur_op = NFA_RW_OP_MAX; /* clear current operation */
1307       conn_evt_data.status = p_rw_data->status;
1308       nfa_dm_act_conn_cback_notify(NFA_SET_TAG_RO_EVT, &conn_evt_data);
1309       break;
1310 
1311     case RW_I93_INVENTORY_EVT: /* Response of Inventory              */
1312 
1313       /* Command complete - perform cleanup, notify app */
1314       nfa_rw_command_complete();
1315 
1316       conn_evt_data.i93_cmd_cplt.status = p_rw_data->i93_inventory.status;
1317       conn_evt_data.i93_cmd_cplt.sent_command = I93_CMD_INVENTORY;
1318 
1319       conn_evt_data.i93_cmd_cplt.params.inventory.dsfid =
1320           p_rw_data->i93_inventory.dsfid;
1321       memcpy(conn_evt_data.i93_cmd_cplt.params.inventory.uid,
1322              p_rw_data->i93_inventory.uid, I93_UID_BYTE_LEN);
1323 
1324       nfa_dm_act_conn_cback_notify(NFA_I93_CMD_CPLT_EVT, &conn_evt_data);
1325 
1326       nfa_rw_cb.cur_op = NFA_RW_OP_MAX; /* clear current operation */
1327       break;
1328 
1329     case RW_I93_DATA_EVT: /* Response of Read, Get Multi Security */
1330 
1331       /* Command complete - perform cleanup, notify app */
1332       nfa_rw_command_complete();
1333 
1334       conn_evt_data.data.p_data = (uint8_t*)(p_rw_data->i93_data.p_data + 1) +
1335                                   p_rw_data->i93_data.p_data->offset;
1336 
1337       if (nfa_rw_cb.flags & NFA_RW_FL_ACTIVATION_NTF_PENDING) {
1338         nfa_rw_cb.flags &= ~NFA_RW_FL_ACTIVATION_NTF_PENDING;
1339 
1340         i93_params.i93.info_flags =
1341             (I93_INFO_FLAG_DSFID | I93_INFO_FLAG_MEM_SIZE | I93_INFO_FLAG_AFI);
1342         i93_params.i93.afi =
1343             *(conn_evt_data.data.p_data +
1344               nfa_rw_cb.i93_afi_location % nfa_rw_cb.i93_block_size);
1345         i93_params.i93.dsfid = nfa_rw_cb.i93_dsfid;
1346         i93_params.i93.block_size = nfa_rw_cb.i93_block_size;
1347         i93_params.i93.num_block = nfa_rw_cb.i93_num_block;
1348         memcpy(i93_params.i93.uid, nfa_rw_cb.i93_uid, I93_UID_BYTE_LEN);
1349 
1350         nfa_dm_notify_activation_status(NFA_STATUS_OK, &i93_params);
1351       } else {
1352         conn_evt_data.data.len = p_rw_data->i93_data.p_data->len;
1353 
1354         nfa_dm_act_conn_cback_notify(NFA_DATA_EVT, &conn_evt_data);
1355       }
1356 
1357       GKI_freebuf(p_rw_data->i93_data.p_data);
1358       p_rw_data->i93_data.p_data = nullptr;
1359 
1360       nfa_rw_cb.cur_op = NFA_RW_OP_MAX; /* clear current operation */
1361       break;
1362 
1363     case RW_I93_SYS_INFO_EVT: /* Response of System Information     */
1364 
1365       /* Command complete - perform cleanup, notify app */
1366       nfa_rw_command_complete();
1367 
1368       if (nfa_rw_cb.flags & NFA_RW_FL_ACTIVATION_NTF_PENDING) {
1369         nfa_rw_cb.flags &= ~NFA_RW_FL_ACTIVATION_NTF_PENDING;
1370 
1371         nfa_rw_cb.i93_block_size = p_rw_data->i93_sys_info.block_size;
1372         nfa_rw_cb.i93_num_block = p_rw_data->i93_sys_info.num_block;
1373 
1374         i93_params.i93.info_flags = p_rw_data->i93_sys_info.info_flags;
1375         i93_params.i93.dsfid = p_rw_data->i93_sys_info.dsfid;
1376         i93_params.i93.afi = p_rw_data->i93_sys_info.afi;
1377         i93_params.i93.num_block = p_rw_data->i93_sys_info.num_block;
1378         i93_params.i93.block_size = p_rw_data->i93_sys_info.block_size;
1379         i93_params.i93.IC_reference = p_rw_data->i93_sys_info.IC_reference;
1380         memcpy(i93_params.i93.uid, p_rw_data->i93_sys_info.uid,
1381                I93_UID_BYTE_LEN);
1382 
1383         nfa_dm_notify_activation_status(NFA_STATUS_OK, &i93_params);
1384       } else {
1385         conn_evt_data.i93_cmd_cplt.status = p_rw_data->i93_sys_info.status;
1386         conn_evt_data.i93_cmd_cplt.sent_command = I93_CMD_GET_SYS_INFO;
1387 
1388         conn_evt_data.i93_cmd_cplt.params.sys_info.info_flags =
1389             p_rw_data->i93_sys_info.info_flags;
1390         memcpy(conn_evt_data.i93_cmd_cplt.params.sys_info.uid,
1391                p_rw_data->i93_sys_info.uid, I93_UID_BYTE_LEN);
1392         conn_evt_data.i93_cmd_cplt.params.sys_info.dsfid =
1393             p_rw_data->i93_sys_info.dsfid;
1394         conn_evt_data.i93_cmd_cplt.params.sys_info.afi =
1395             p_rw_data->i93_sys_info.afi;
1396         conn_evt_data.i93_cmd_cplt.params.sys_info.num_block =
1397             p_rw_data->i93_sys_info.num_block;
1398         conn_evt_data.i93_cmd_cplt.params.sys_info.block_size =
1399             p_rw_data->i93_sys_info.block_size;
1400         conn_evt_data.i93_cmd_cplt.params.sys_info.IC_reference =
1401             p_rw_data->i93_sys_info.IC_reference;
1402 
1403         /* store tag memory information for writing blocks */
1404         nfa_rw_cb.i93_block_size = p_rw_data->i93_sys_info.block_size;
1405         nfa_rw_cb.i93_num_block = p_rw_data->i93_sys_info.num_block;
1406 
1407         nfa_dm_act_conn_cback_notify(NFA_I93_CMD_CPLT_EVT, &conn_evt_data);
1408       }
1409 
1410       nfa_rw_cb.cur_op = NFA_RW_OP_MAX; /* clear current operation */
1411       break;
1412 
1413     case RW_I93_CMD_CMPL_EVT: /* Command complete                   */
1414       /* Command complete - perform cleanup, notify app */
1415       nfa_rw_command_complete();
1416 
1417       if (nfa_rw_cb.flags & NFA_RW_FL_ACTIVATION_NTF_PENDING) {
1418         /* Reader got error code from tag */
1419 
1420         nfa_rw_cb.flags &= ~NFA_RW_FL_ACTIVATION_NTF_PENDING;
1421 
1422         memset(&i93_params, 0x00, sizeof(i93_params));
1423         memcpy(i93_params.i93.uid, nfa_rw_cb.i93_uid, I93_UID_BYTE_LEN);
1424 
1425         nfa_dm_notify_activation_status(NFA_STATUS_OK, &i93_params);
1426       } else {
1427         conn_evt_data.i93_cmd_cplt.status = p_rw_data->i93_cmd_cmpl.status;
1428         conn_evt_data.i93_cmd_cplt.sent_command =
1429             p_rw_data->i93_cmd_cmpl.command;
1430 
1431         if (conn_evt_data.i93_cmd_cplt.status != NFC_STATUS_OK)
1432           conn_evt_data.i93_cmd_cplt.params.error_code =
1433               p_rw_data->i93_cmd_cmpl.error_code;
1434 
1435         nfa_dm_act_conn_cback_notify(NFA_I93_CMD_CPLT_EVT, &conn_evt_data);
1436       }
1437 
1438       nfa_rw_cb.cur_op = NFA_RW_OP_MAX; /* clear current operation */
1439       break;
1440 
1441     default:
1442       DLOG_IF(INFO, nfc_debug_enabled)
1443           << StringPrintf("; Unhandled RW event 0x%X", event);
1444       break;
1445   }
1446 }
1447 
1448 /*******************************************************************************
1449 **
1450 ** Function         nfa_rw_handle_mfc_evt
1451 **
1452 ** Description      Handler for Mifare Classic tag reader/writer events
1453 **
1454 ** Returns          Nothing
1455 **
1456 *******************************************************************************/
nfa_rw_handle_mfc_evt(tRW_EVENT event,tRW_DATA * p_rw_data)1457 static void nfa_rw_handle_mfc_evt(tRW_EVENT event, tRW_DATA* p_rw_data) {
1458   tNFA_CONN_EVT_DATA conn_evt_data;
1459 
1460   conn_evt_data.status = p_rw_data->status;
1461   DLOG_IF(INFO, nfc_debug_enabled)
1462       << StringPrintf("nfa_rw_handle_mfc_evt() event = 0x%X", event);
1463 
1464   switch (event) {
1465     /* Read completed */
1466     case RW_MFC_NDEF_READ_CPLT_EVT:
1467       nfa_rw_send_data_to_upper(p_rw_data);
1468       /* Command complete - perform cleanup, notify the app */
1469       nfa_rw_command_complete();
1470       nfa_dm_act_conn_cback_notify(NFA_READ_CPLT_EVT, &conn_evt_data);
1471       break;
1472 
1473     /* NDEF detection complete */
1474     case RW_MFC_NDEF_DETECT_EVT:
1475       nfa_rw_handle_ndef_detect(p_rw_data);
1476       break;
1477 
1478     /* NDEF read completed */
1479     case RW_MFC_NDEF_READ_EVT:
1480       if (p_rw_data->status == NFC_STATUS_OK) {
1481         /* Process the ndef record */
1482         nfa_dm_ndef_handle_message(NFA_STATUS_OK, nfa_rw_cb.p_ndef_buf,
1483                                    nfa_rw_cb.ndef_cur_size);
1484       } else {
1485         /* Notify app of failure */
1486         if (nfa_rw_cb.cur_op == NFA_RW_OP_READ_NDEF) {
1487           /* If current operation is READ_NDEF, then notify ndef handlers of
1488            * failure */
1489           nfa_dm_ndef_handle_message(NFA_STATUS_FAILED, NULL, 0);
1490         }
1491       }
1492 
1493       /* Notify app of read status */
1494       conn_evt_data.status = p_rw_data->status;
1495       nfa_dm_act_conn_cback_notify(NFA_READ_CPLT_EVT, &conn_evt_data);
1496       /* Free ndef buffer */
1497       nfa_rw_free_ndef_rx_buf();
1498 
1499       /* Command complete - perform cleanup */
1500       nfa_rw_command_complete();
1501       break;
1502 
1503     /* Raw Frame data event */
1504     case RW_MFC_RAW_FRAME_EVT:
1505       nfa_rw_send_data_to_upper(p_rw_data);
1506 
1507       if (p_rw_data->status != NFC_STATUS_CONTINUE) {
1508         /* Command complete - perform cleanup */
1509         nfa_rw_command_complete();
1510         nfa_rw_cb.cur_op = NFA_RW_OP_MAX;
1511       }
1512       break;
1513 
1514     /* RF Interface error event */
1515     case RW_MFC_INTF_ERROR_EVT:
1516       nfa_dm_act_conn_cback_notify(NFA_RW_INTF_ERROR_EVT, &conn_evt_data);
1517       break;
1518 
1519     case RW_MFC_NDEF_FORMAT_CPLT_EVT:
1520       /* Command complete - perform cleanup, notify the app */
1521       nfa_rw_command_complete();
1522       nfa_dm_act_conn_cback_notify(NFA_FORMAT_CPLT_EVT, &conn_evt_data);
1523       break;
1524 
1525     /* NDEF write completed or failed*/
1526     case RW_MFC_NDEF_WRITE_CPLT_EVT:
1527       if (nfa_rw_cb.cur_op == NFA_RW_OP_WRITE_NDEF) {
1528         /* Update local cursize of ndef message */
1529         nfa_rw_cb.ndef_cur_size = nfa_rw_cb.ndef_wr_len;
1530       }
1531       FALLTHROUGH_INTENDED;
1532 
1533     case RW_MFC_NDEF_WRITE_FAIL_EVT:
1534       /* Command complete - perform cleanup, notify the app */
1535       nfa_rw_command_complete();
1536       nfa_dm_act_conn_cback_notify(NFA_WRITE_CPLT_EVT, &conn_evt_data);
1537       break;
1538 
1539     default:
1540       DLOG_IF(INFO, nfc_debug_enabled)
1541           << StringPrintf("; Unhandled RW event 0x%X", event);
1542   }
1543 }
1544 
1545 /*******************************************************************************
1546 **
1547 ** Function         nfa_rw_cback
1548 **
1549 ** Description      Callback for reader/writer event notification
1550 **
1551 ** Returns          Nothing
1552 **
1553 *******************************************************************************/
nfa_rw_cback(tRW_EVENT event,tRW_DATA * p_rw_data)1554 static void nfa_rw_cback(tRW_EVENT event, tRW_DATA* p_rw_data) {
1555   DLOG_IF(INFO, nfc_debug_enabled)
1556       << StringPrintf("nfa_rw_cback: event=0x%02x", event);
1557 
1558   /* Call appropriate event handler for tag type */
1559   if (event < RW_T1T_MAX_EVT) {
1560     /* Handle Type-1 tag events */
1561     nfa_rw_handle_t1t_evt(event, p_rw_data);
1562   } else if (event < RW_T2T_MAX_EVT) {
1563     /* Handle Type-2 tag events */
1564     nfa_rw_handle_t2t_evt(event, p_rw_data);
1565   } else if (event < RW_T3T_MAX_EVT) {
1566     /* Handle Type-3 tag events */
1567     nfa_rw_handle_t3t_evt(event, p_rw_data);
1568   } else if (event < RW_T4T_MAX_EVT) {
1569     /* Handle Type-4 tag events */
1570     nfa_rw_handle_t4t_evt(event, p_rw_data);
1571   } else if (event < RW_I93_MAX_EVT) {
1572     /* Handle ISO 15693 tag events */
1573     nfa_rw_handle_i93_evt(event, p_rw_data);
1574   } else if (event < RW_MFC_MAX_EVT) {
1575     /* Handle Mifare Classic tag events */
1576     nfa_rw_handle_mfc_evt(event, p_rw_data);
1577   } else {
1578     LOG(ERROR) << StringPrintf("nfa_rw_cback: unhandled event=0x%02x", event);
1579   }
1580 }
1581 
1582 /*******************************************************************************
1583 **
1584 ** Function         nfa_rw_start_ndef_detection
1585 **
1586 ** Description      Start NDEF detection on activated tag
1587 **
1588 ** Returns          Nothing
1589 **
1590 *******************************************************************************/
nfa_rw_start_ndef_detection(void)1591 static tNFC_STATUS nfa_rw_start_ndef_detection(void) {
1592   tNFC_PROTOCOL protocol = nfa_rw_cb.protocol;
1593   tNFC_STATUS status = NFC_STATUS_FAILED;
1594 
1595   if (NFC_PROTOCOL_T1T == protocol) {
1596     /* Type1Tag    - NFC-A */
1597     status = RW_T1tDetectNDef();
1598   } else if (NFC_PROTOCOL_T2T == protocol) {
1599     /* Type2Tag    - NFC-A */
1600     if (nfa_rw_cb.pa_sel_res == NFC_SEL_RES_NFC_FORUM_T2T) {
1601       status = RW_T2tDetectNDef(nfa_rw_cb.skip_dyn_locks);
1602     }
1603   } else if (NFC_PROTOCOL_T3T == protocol) {
1604     /* Type3Tag    - NFC-F */
1605     status = RW_T3tDetectNDef();
1606   } else if (NFC_PROTOCOL_ISO_DEP == protocol) {
1607     /* ISODEP/4A,4B- NFC-A or NFC-B */
1608     status = RW_T4tDetectNDef();
1609   } else if (NFC_PROTOCOL_T5T == protocol) {
1610     /* ISO 15693 */
1611     status = RW_I93DetectNDef();
1612   } else if (NFC_PROTOCOL_MIFARE == protocol) {
1613     status = RW_MfcDetectNDef();
1614   }
1615 
1616   return (status);
1617 }
1618 
1619 /*******************************************************************************
1620 **
1621 ** Function         nfa_rw_start_ndef_read
1622 **
1623 ** Description      Start NDEF read on activated tag
1624 **
1625 ** Returns          Nothing
1626 **
1627 *******************************************************************************/
nfa_rw_start_ndef_read(void)1628 static tNFC_STATUS nfa_rw_start_ndef_read(void) {
1629   tNFC_PROTOCOL protocol = nfa_rw_cb.protocol;
1630   tNFC_STATUS status = NFC_STATUS_FAILED;
1631   tNFA_CONN_EVT_DATA conn_evt_data;
1632 
1633   /* Handle zero length NDEF message */
1634   if (nfa_rw_cb.ndef_cur_size == 0) {
1635     DLOG_IF(INFO, nfc_debug_enabled)
1636         << StringPrintf("NDEF message is zero-length");
1637 
1638     /* Send zero-lengh NDEF message to ndef callback */
1639     nfa_dm_ndef_handle_message(NFA_STATUS_OK, nullptr, 0);
1640 
1641     /* Command complete - perform cleanup, notify app */
1642     nfa_rw_command_complete();
1643     conn_evt_data.status = NFA_STATUS_OK;
1644     nfa_dm_act_conn_cback_notify(NFA_READ_CPLT_EVT, &conn_evt_data);
1645     return NFC_STATUS_OK;
1646   }
1647 
1648   /* Allocate buffer for incoming NDEF message (free previous NDEF rx buffer, if
1649    * needed) */
1650   nfa_rw_free_ndef_rx_buf();
1651   nfa_rw_cb.p_ndef_buf = (uint8_t*)nfa_mem_co_alloc(nfa_rw_cb.ndef_cur_size);
1652   if (nfa_rw_cb.p_ndef_buf == nullptr) {
1653     LOG(ERROR) << StringPrintf(
1654         "Unable to allocate a buffer for reading NDEF (size=%i)",
1655         nfa_rw_cb.ndef_cur_size);
1656 
1657     /* Command complete - perform cleanup, notify app */
1658     nfa_rw_command_complete();
1659     conn_evt_data.status = NFA_STATUS_FAILED;
1660     nfa_dm_act_conn_cback_notify(NFA_READ_CPLT_EVT, &conn_evt_data);
1661     return NFC_STATUS_FAILED;
1662   }
1663   nfa_rw_cb.ndef_rd_offset = 0;
1664 
1665   if (NFC_PROTOCOL_T1T == protocol) {
1666     /* Type1Tag    - NFC-A */
1667     status =
1668         RW_T1tReadNDef(nfa_rw_cb.p_ndef_buf, (uint16_t)nfa_rw_cb.ndef_cur_size);
1669   } else if (NFC_PROTOCOL_T2T == protocol) {
1670     /* Type2Tag    - NFC-A */
1671     if (nfa_rw_cb.pa_sel_res == NFC_SEL_RES_NFC_FORUM_T2T) {
1672       status = RW_T2tReadNDef(nfa_rw_cb.p_ndef_buf,
1673                               (uint16_t)nfa_rw_cb.ndef_cur_size);
1674     }
1675   } else if (NFC_PROTOCOL_T3T == protocol) {
1676     /* Type3Tag    - NFC-F */
1677     status = RW_T3tCheckNDef();
1678   } else if (NFC_PROTOCOL_ISO_DEP == protocol) {
1679     /* ISODEP/4A,4B- NFC-A or NFC-B */
1680     status = RW_T4tReadNDef();
1681   } else if (NFC_PROTOCOL_T5T == protocol) {
1682     /* ISO 15693 */
1683     status = RW_I93ReadNDef();
1684   } else if (NFC_PROTOCOL_MIFARE == protocol) {
1685     /* Mifare Classic*/
1686     status =
1687         RW_MfcReadNDef(nfa_rw_cb.p_ndef_buf, (uint16_t)nfa_rw_cb.ndef_cur_size);
1688   }
1689 
1690   return (status);
1691 }
1692 
1693 /*******************************************************************************
1694 **
1695 ** Function         nfa_rw_detect_ndef
1696 **
1697 ** Description      Handler for NFA_RW_API_DETECT_NDEF_EVT
1698 **
1699 ** Returns          TRUE (message buffer to be freed by caller)
1700 **
1701 *******************************************************************************/
nfa_rw_detect_ndef()1702 static bool nfa_rw_detect_ndef() {
1703   tNFA_CONN_EVT_DATA conn_evt_data;
1704   DLOG_IF(INFO, nfc_debug_enabled) << __func__;
1705 
1706   conn_evt_data.ndef_detect.status = nfa_rw_start_ndef_detection();
1707   if (conn_evt_data.ndef_detect.status != NFC_STATUS_OK) {
1708     /* Command complete - perform cleanup, notify app */
1709     nfa_rw_command_complete();
1710     conn_evt_data.ndef_detect.cur_size = 0;
1711     conn_evt_data.ndef_detect.max_size = 0;
1712     conn_evt_data.ndef_detect.flags = RW_NDEF_FL_UNKNOWN;
1713     nfa_dm_act_conn_cback_notify(NFA_NDEF_DETECT_EVT, &conn_evt_data);
1714   }
1715 
1716   return true;
1717 }
1718 
1719 /*******************************************************************************
1720 **
1721 ** Function         nfa_rw_start_ndef_write
1722 **
1723 ** Description      Start NDEF write on activated tag
1724 **
1725 ** Returns          Nothing
1726 **
1727 *******************************************************************************/
nfa_rw_start_ndef_write(void)1728 static tNFC_STATUS nfa_rw_start_ndef_write(void) {
1729   tNFC_PROTOCOL protocol = nfa_rw_cb.protocol;
1730   tNFC_STATUS status = NFC_STATUS_FAILED;
1731 
1732   if (nfa_rw_cb.flags & NFA_RW_FL_TAG_IS_READONLY) {
1733     /* error: ndef tag is read-only */
1734     status = NFC_STATUS_FAILED;
1735     LOG(ERROR) << StringPrintf("Unable to write NDEF. Tag is read-only");
1736   } else if (nfa_rw_cb.ndef_max_size < nfa_rw_cb.ndef_wr_len) {
1737     /* error: ndef tag size is too small */
1738     status = NFC_STATUS_BUFFER_FULL;
1739     LOG(ERROR) << StringPrintf(
1740         "Unable to write NDEF. Tag maxsize=%i, request write size=%i",
1741         nfa_rw_cb.ndef_max_size, nfa_rw_cb.ndef_wr_len);
1742   } else {
1743     if (NFC_PROTOCOL_T1T == protocol) {
1744       /* Type1Tag    - NFC-A */
1745       status = RW_T1tWriteNDef((uint16_t)nfa_rw_cb.ndef_wr_len,
1746                                nfa_rw_cb.p_ndef_wr_buf);
1747     } else if (NFC_PROTOCOL_T2T == protocol) {
1748       /* Type2Tag    - NFC-A */
1749       if (nfa_rw_cb.pa_sel_res == NFC_SEL_RES_NFC_FORUM_T2T) {
1750         status = RW_T2tWriteNDef((uint16_t)nfa_rw_cb.ndef_wr_len,
1751                                  nfa_rw_cb.p_ndef_wr_buf);
1752       }
1753     } else if (NFC_PROTOCOL_T3T == protocol) {
1754       /* Type3Tag    - NFC-F */
1755       status = RW_T3tUpdateNDef(nfa_rw_cb.ndef_wr_len, nfa_rw_cb.p_ndef_wr_buf);
1756     } else if (NFC_PROTOCOL_ISO_DEP == protocol) {
1757       /* ISODEP/4A,4B- NFC-A or NFC-B */
1758       status = RW_T4tUpdateNDef(nfa_rw_cb.ndef_wr_len, nfa_rw_cb.p_ndef_wr_buf);
1759     } else if (NFC_PROTOCOL_T5T == protocol) {
1760       /* ISO 15693 */
1761       status = RW_I93UpdateNDef((uint16_t)nfa_rw_cb.ndef_wr_len,
1762                                 nfa_rw_cb.p_ndef_wr_buf);
1763     } else if (NFC_PROTOCOL_MIFARE == protocol) {
1764       /* Mifare Tag */
1765       status = RW_MfcWriteNDef((uint16_t)nfa_rw_cb.ndef_wr_len,
1766                                nfa_rw_cb.p_ndef_wr_buf);
1767     }
1768   }
1769 
1770   return (status);
1771 }
1772 
1773 /*******************************************************************************
1774 **
1775 ** Function         nfa_rw_read_ndef
1776 **
1777 ** Description      Handler for NFA_RW_API_READ_NDEF_EVT
1778 **
1779 ** Returns          TRUE (message buffer to be freed by caller)
1780 **
1781 *******************************************************************************/
nfa_rw_read_ndef()1782 static bool nfa_rw_read_ndef() {
1783   tNFA_STATUS status = NFA_STATUS_OK;
1784   tNFA_CONN_EVT_DATA conn_evt_data;
1785 
1786   DLOG_IF(INFO, nfc_debug_enabled) << __func__;
1787 
1788   /* Check if ndef detection has been performed yet */
1789   if (nfa_rw_cb.ndef_st == NFA_RW_NDEF_ST_UNKNOWN) {
1790     /* Perform ndef detection first */
1791     status = nfa_rw_start_ndef_detection();
1792   } else if (nfa_rw_cb.ndef_st == NFA_RW_NDEF_ST_FALSE) {
1793     /* Tag is not NDEF */
1794     status = NFA_STATUS_FAILED;
1795   } else {
1796     /* Perform the NDEF read operation */
1797     status = nfa_rw_start_ndef_read();
1798   }
1799 
1800   /* Handle failure */
1801   if (status != NFA_STATUS_OK) {
1802     /* Command complete - perform cleanup, notify app */
1803     nfa_rw_command_complete();
1804     conn_evt_data.status = status;
1805     nfa_dm_act_conn_cback_notify(NFA_READ_CPLT_EVT, &conn_evt_data);
1806   }
1807 
1808   return true;
1809 }
1810 
1811 /*******************************************************************************
1812 **
1813 ** Function         nfa_rw_write_ndef
1814 **
1815 ** Description      Handler for NFA_RW_API_WRITE_NDEF_EVT
1816 **
1817 ** Returns          TRUE (message buffer to be freed by caller)
1818 **
1819 *******************************************************************************/
nfa_rw_write_ndef(tNFA_RW_MSG * p_data)1820 static bool nfa_rw_write_ndef(tNFA_RW_MSG* p_data) {
1821   tNDEF_STATUS ndef_status;
1822   tNFA_STATUS write_status = NFA_STATUS_OK;
1823   tNFA_CONN_EVT_DATA conn_evt_data;
1824   DLOG_IF(INFO, nfc_debug_enabled) << __func__;
1825 
1826   /* Validate NDEF message */
1827   ndef_status = NDEF_MsgValidate(p_data->op_req.params.write_ndef.p_data,
1828                                  p_data->op_req.params.write_ndef.len, false);
1829   if (ndef_status != NDEF_OK) {
1830     LOG(ERROR) << StringPrintf(
1831         "Invalid NDEF message. NDEF_MsgValidate returned %i", ndef_status);
1832 
1833     /* Command complete - perform cleanup, notify app */
1834     nfa_rw_command_complete();
1835     conn_evt_data.status = NFA_STATUS_FAILED;
1836     nfa_dm_act_conn_cback_notify(NFA_WRITE_CPLT_EVT, &conn_evt_data);
1837     return true;
1838   }
1839 
1840   /* Store pointer to source NDEF */
1841   nfa_rw_cb.p_ndef_wr_buf = p_data->op_req.params.write_ndef.p_data;
1842   nfa_rw_cb.ndef_wr_len = p_data->op_req.params.write_ndef.len;
1843 
1844   /* Check if ndef detection has been performed yet */
1845   if (nfa_rw_cb.ndef_st == NFA_RW_NDEF_ST_UNKNOWN) {
1846     /* Perform ndef detection first */
1847     write_status = nfa_rw_start_ndef_detection();
1848   } else if (nfa_rw_cb.ndef_st == NFA_RW_NDEF_ST_FALSE) {
1849     if (nfa_rw_cb.protocol == NFC_PROTOCOL_T1T) {
1850       /* For Type 1 tag, NDEF can be written on Initialized tag
1851        *  Perform ndef detection first to check if tag is in Initialized state
1852        * to Write NDEF */
1853       write_status = nfa_rw_start_ndef_detection();
1854     } else {
1855       /* Tag is not NDEF */
1856       write_status = NFA_STATUS_FAILED;
1857     }
1858   } else {
1859     /* Perform the NDEF read operation */
1860     write_status = nfa_rw_start_ndef_write();
1861   }
1862 
1863   /* Handle failure */
1864   if (write_status != NFA_STATUS_OK) {
1865     /* Command complete - perform cleanup, notify app */
1866     nfa_rw_command_complete();
1867     conn_evt_data.status = write_status;
1868     nfa_dm_act_conn_cback_notify(NFA_WRITE_CPLT_EVT, &conn_evt_data);
1869   }
1870 
1871   return true;
1872 }
1873 
1874 /*******************************************************************************
1875 **
1876 ** Function         nfa_rw_presence_check
1877 **
1878 ** Description      Handler for NFA_RW_API_PRESENCE_CHECK
1879 **
1880 ** Returns          Nothing
1881 **
1882 *******************************************************************************/
nfa_rw_presence_check(tNFA_RW_MSG * p_data)1883 void nfa_rw_presence_check(tNFA_RW_MSG* p_data) {
1884   tNFC_PROTOCOL protocol = nfa_rw_cb.protocol;
1885   uint8_t sel_res = nfa_rw_cb.pa_sel_res;
1886   tNFC_STATUS status = NFC_STATUS_FAILED;
1887   bool unsupported = false;
1888   uint8_t option = NFA_RW_OPTION_INVALID;
1889   tNFA_RW_PRES_CHK_OPTION op_param = NFA_RW_PRES_CHK_DEFAULT;
1890 
1891   if (NFC_PROTOCOL_T1T == protocol) {
1892     /* Type1Tag    - NFC-A */
1893     nfa_rw_cb.pres_check_tag = true;
1894     status = RW_T1tPresenceCheck();
1895   } else if (NFC_PROTOCOL_T2T == protocol) {
1896     /* If T2T NFC-Forum, then let RW handle presence check */
1897     if (sel_res == NFC_SEL_RES_NFC_FORUM_T2T) {
1898       /* Type 2 tag have not sent NACK after activation */
1899       nfa_rw_cb.pres_check_tag = true;
1900       status = RW_T2tPresenceCheck();
1901     } else {
1902       /* Will fall back to deactivate/reactivate */
1903       unsupported = true;
1904     }
1905   } else if (NFC_PROTOCOL_T3T == protocol) {
1906     /* Type3Tag    - NFC-F */
1907     nfa_rw_cb.pres_check_tag = true;
1908     status = RW_T3tPresenceCheck();
1909   } else if (NFC_PROTOCOL_ISO_DEP == protocol) {
1910     /* ISODEP/4A,4B- NFC-A or NFC-B */
1911     if (p_data) {
1912       op_param = p_data->op_req.params.option;
1913     }
1914 
1915     nfa_rw_cb.pres_check_iso_dep_nak = false;
1916     switch (op_param) {
1917       case NFA_RW_PRES_CHK_I_BLOCK:
1918         option = RW_T4T_CHK_EMPTY_I_BLOCK;
1919         break;
1920 
1921       case NFA_RW_PRES_CHK_ISO_DEP_NAK:
1922         if (NFC_GetNCIVersion() == NCI_VERSION_2_0) {
1923           nfa_rw_cb.pres_check_iso_dep_nak = true;
1924           nfa_rw_cb.pres_check_iso_dep_nak_count++;
1925           option = RW_T4T_CHK_ISO_DEP_NAK_PRES_CHK;
1926         }
1927         break;
1928       default:
1929         /* empty I block */
1930         option = RW_T4T_CHK_EMPTY_I_BLOCK;
1931     }
1932 
1933     if (option != NFA_RW_OPTION_INVALID) {
1934       /* use the presence check with the chosen option */
1935       status = RW_T4tPresenceCheck(option);
1936     } else {
1937       /* use sleep/wake for presence check */
1938       unsupported = true;
1939     }
1940   } else if (NFC_PROTOCOL_T5T == protocol) {
1941     /* T5T/ISO 15693 */
1942     nfa_rw_cb.pres_check_tag = true;
1943     status = RW_I93PresenceCheck();
1944   } else {
1945     /* Protocol unsupported by RW module... */
1946     unsupported = true;
1947   }
1948 
1949   if (unsupported) {
1950     if (nfa_rw_cb.activated_tech_mode == NFC_DISCOVERY_TYPE_POLL_KOVIO) {
1951       /* start Kovio presence check (deactivate and wait for activation) */
1952       status = nfa_dm_disc_start_kovio_presence_check();
1953     } else {
1954       /* Let DM perform presence check (by putting tag to sleep and then waking
1955        * it up) */
1956       status = nfa_dm_disc_sleep_wakeup();
1957     }
1958   }
1959 
1960   /* Handle presence check failure */
1961   if (status != NFC_STATUS_OK)
1962     nfa_rw_handle_presence_check_rsp(NFC_STATUS_FAILED);
1963   else if (!unsupported) {
1964     nfa_sys_start_timer(&nfa_rw_cb.tle, NFA_RW_PRESENCE_CHECK_TIMEOUT_EVT,
1965                         p_nfa_dm_cfg->presence_check_timeout);
1966   }
1967 }
1968 
1969 /*******************************************************************************
1970 **
1971 ** Function         nfa_rw_presence_check_tick
1972 **
1973 ** Description      Called on expiration of NFA_RW_PRESENCE_CHECK_INTERVAL
1974 **                  Initiate presence check
1975 **
1976 ** Returns          TRUE (caller frees message buffer)
1977 **
1978 *******************************************************************************/
nfa_rw_presence_check_tick(tNFA_RW_MSG * p_data)1979 bool nfa_rw_presence_check_tick(__attribute__((unused)) tNFA_RW_MSG* p_data) {
1980   /* Store the current operation */
1981   nfa_rw_cb.cur_op = NFA_RW_OP_PRESENCE_CHECK;
1982   nfa_rw_cb.flags |= NFA_RW_FL_AUTO_PRESENCE_CHECK_BUSY;
1983   DLOG_IF(INFO, nfc_debug_enabled)
1984       << StringPrintf("Auto-presence check starting...");
1985 
1986   /* Perform presence check */
1987   nfa_rw_presence_check(nullptr);
1988 
1989   return true;
1990 }
1991 
1992 /*******************************************************************************
1993 **
1994 ** Function         nfa_rw_presence_check_timeout
1995 **
1996 ** Description      presence check timeout: report presence check failure
1997 **
1998 ** Returns          TRUE (caller frees message buffer)
1999 **
2000 *******************************************************************************/
nfa_rw_presence_check_timeout(tNFA_RW_MSG * p_data)2001 bool nfa_rw_presence_check_timeout(__attribute__((unused))
2002                                    tNFA_RW_MSG* p_data) {
2003   nfa_rw_handle_presence_check_rsp(NFC_STATUS_FAILED);
2004   return true;
2005 }
2006 
2007 /*******************************************************************************
2008 **
2009 ** Function         nfa_rw_format_tag
2010 **
2011 ** Description      Handler for NFA_RW_API_FORMAT_TAG
2012 **
2013 ** Returns          Nothing
2014 **
2015 *******************************************************************************/
nfa_rw_format_tag()2016 static void nfa_rw_format_tag() {
2017   tNFC_PROTOCOL protocol = nfa_rw_cb.protocol;
2018   tNFC_STATUS status = NFC_STATUS_FAILED;
2019 
2020   if (protocol == NFC_PROTOCOL_T1T) {
2021     status = RW_T1tFormatNDef();
2022   } else if ((protocol == NFC_PROTOCOL_T2T) &&
2023              (nfa_rw_cb.pa_sel_res == NFC_SEL_RES_NFC_FORUM_T2T)) {
2024     status = RW_T2tFormatNDef();
2025   } else if (protocol == NFC_PROTOCOL_T3T) {
2026     status = RW_T3tFormatNDef();
2027   } else if (protocol == NFC_PROTOCOL_T5T) {
2028     status = RW_I93FormatNDef();
2029   } else if (protocol == NFC_PROTOCOL_ISO_DEP) {
2030     status = RW_T4tFormatNDef();
2031   } else if (protocol == NFC_PROTOCOL_MIFARE) {
2032     status = RW_MfcFormatNDef();
2033   }
2034 
2035   /* If unable to format NDEF, notify the app */
2036   if (status != NFC_STATUS_OK) nfa_rw_error_cleanup(NFA_FORMAT_CPLT_EVT);
2037 }
2038 
2039 /*******************************************************************************
2040 **
2041 ** Function         nfa_rw_detect_tlv
2042 **
2043 ** Description      Handler for NFA_RW_API_DETECT_NDEF_EVT
2044 **
2045 ** Returns          TRUE (message buffer to be freed by caller)
2046 **
2047 *******************************************************************************/
nfa_rw_detect_tlv(uint8_t tlv)2048 static bool nfa_rw_detect_tlv(uint8_t tlv) {
2049   DLOG_IF(INFO, nfc_debug_enabled) << __func__;
2050 
2051   switch (nfa_rw_cb.protocol) {
2052     case NFC_PROTOCOL_T1T:
2053       if (RW_T1tLocateTlv(tlv) != NFC_STATUS_OK)
2054         nfa_rw_error_cleanup(NFA_TLV_DETECT_EVT);
2055       break;
2056 
2057     case NFC_PROTOCOL_T2T:
2058       if (nfa_rw_cb.pa_sel_res == NFC_SEL_RES_NFC_FORUM_T2T) {
2059         if (RW_T2tLocateTlv(tlv) != NFC_STATUS_OK)
2060           nfa_rw_error_cleanup(NFA_TLV_DETECT_EVT);
2061       }
2062       break;
2063 
2064     default:
2065       break;
2066   }
2067 
2068   return true;
2069 }
2070 
2071 /*******************************************************************************
2072 **
2073 ** Function         nfa_rw_config_tag_ro
2074 **
2075 ** Description      Handler for NFA_RW_OP_SET_TAG_RO
2076 **
2077 ** Returns          TRUE (message buffer to be freed by caller)
2078 **
2079 *******************************************************************************/
nfa_rw_config_tag_ro(bool b_hard_lock)2080 static tNFC_STATUS nfa_rw_config_tag_ro(bool b_hard_lock) {
2081   tNFC_PROTOCOL protocol = nfa_rw_cb.protocol;
2082   tNFC_STATUS status = NFC_STATUS_FAILED;
2083 
2084   DLOG_IF(INFO, nfc_debug_enabled) << __func__;
2085 
2086   if (NFC_PROTOCOL_T1T == protocol) {
2087     /* Type1Tag    - NFC-A */
2088     if ((nfa_rw_cb.tlv_st == NFA_RW_TLV_DETECT_ST_OP_NOT_STARTED) ||
2089         (nfa_rw_cb.tlv_st == NFA_RW_TLV_DETECT_ST_MEM_TLV_OP_COMPLETE)) {
2090       status = RW_T1tLocateTlv(TAG_LOCK_CTRL_TLV);
2091       return (status);
2092     } else {
2093       status = RW_T1tSetTagReadOnly(b_hard_lock);
2094     }
2095   } else if (NFC_PROTOCOL_T2T == protocol) {
2096     /* Type2Tag    - NFC-A */
2097     if (nfa_rw_cb.pa_sel_res == NFC_SEL_RES_NFC_FORUM_T2T) {
2098       status = RW_T2tSetTagReadOnly(b_hard_lock);
2099     }
2100   } else if (NFC_PROTOCOL_T3T == protocol) {
2101     /* Type3Tag    - NFC-F */
2102     status = RW_T3tSetReadOnly(b_hard_lock);
2103   } else if (NFC_PROTOCOL_ISO_DEP == protocol) {
2104     /* ISODEP/4A,4B- NFC-A or NFC-B */
2105     status = RW_T4tSetNDefReadOnly();
2106   } else if (NFC_PROTOCOL_T5T == protocol) {
2107     /* ISO 15693 */
2108     status = RW_I93SetTagReadOnly();
2109   }
2110 
2111   if (status == NFC_STATUS_OK) {
2112     nfa_rw_cb.ndef_st = NFA_RW_NDEF_ST_UNKNOWN;
2113   } else {
2114     nfa_rw_error_cleanup(NFA_SET_TAG_RO_EVT);
2115   }
2116 
2117   return (status);
2118 }
2119 
2120 /*******************************************************************************
2121 **
2122 ** Function         nfa_rw_t1t_rid
2123 **
2124 ** Description      Handler for T1T_RID API
2125 **
2126 ** Returns          TRUE (message buffer to be freed by caller)
2127 **
2128 *******************************************************************************/
nfa_rw_t1t_rid()2129 static bool nfa_rw_t1t_rid() {
2130   if (RW_T1tRid() != NFC_STATUS_OK) nfa_rw_error_cleanup(NFA_READ_CPLT_EVT);
2131 
2132   return true;
2133 }
2134 
2135 /*******************************************************************************
2136 **
2137 ** Function         nfa_rw_t1t_rall
2138 **
2139 ** Description      Handler for T1T_ReadAll API
2140 **
2141 ** Returns          TRUE (message buffer to be freed by caller)
2142 **
2143 *******************************************************************************/
nfa_rw_t1t_rall()2144 static bool nfa_rw_t1t_rall() {
2145   if (RW_T1tReadAll() != NFC_STATUS_OK) nfa_rw_error_cleanup(NFA_READ_CPLT_EVT);
2146 
2147   return true;
2148 }
2149 
2150 /*******************************************************************************
2151 **
2152 ** Function         nfa_rw_t1t_read
2153 **
2154 ** Description      Handler for T1T_Read API
2155 **
2156 ** Returns          TRUE (message buffer to be freed by caller)
2157 **
2158 *******************************************************************************/
nfa_rw_t1t_read(tNFA_RW_MSG * p_data)2159 static bool nfa_rw_t1t_read(tNFA_RW_MSG* p_data) {
2160   tNFA_RW_OP_PARAMS_T1T_READ* p_t1t_read =
2161       (tNFA_RW_OP_PARAMS_T1T_READ*)&(p_data->op_req.params.t1t_read);
2162 
2163   if (RW_T1tRead(p_t1t_read->block_number, p_t1t_read->index) != NFC_STATUS_OK)
2164     nfa_rw_error_cleanup(NFA_READ_CPLT_EVT);
2165 
2166   return true;
2167 }
2168 
2169 /*******************************************************************************
2170 **
2171 ** Function         nfa_rw_t1t_write
2172 **
2173 ** Description      Handler for T1T_WriteErase/T1T_WriteNoErase API
2174 **
2175 ** Returns          TRUE (message buffer to be freed by caller)
2176 **
2177 *******************************************************************************/
nfa_rw_t1t_write(tNFA_RW_MSG * p_data)2178 static bool nfa_rw_t1t_write(tNFA_RW_MSG* p_data) {
2179   tNFA_RW_OP_PARAMS_T1T_WRITE* p_t1t_write =
2180       (tNFA_RW_OP_PARAMS_T1T_WRITE*)&(p_data->op_req.params.t1t_write);
2181   tNFC_STATUS status;
2182 
2183   if (p_t1t_write->b_erase) {
2184     status = RW_T1tWriteErase(p_t1t_write->block_number, p_t1t_write->index,
2185                               p_t1t_write->p_block_data[0]);
2186   } else {
2187     status = RW_T1tWriteNoErase(p_t1t_write->block_number, p_t1t_write->index,
2188                                 p_t1t_write->p_block_data[0]);
2189   }
2190 
2191   if (status != NFC_STATUS_OK) {
2192     nfa_rw_error_cleanup(NFA_WRITE_CPLT_EVT);
2193   } else {
2194     if (p_t1t_write->block_number == 0x01)
2195       nfa_rw_cb.ndef_st = NFA_RW_NDEF_ST_UNKNOWN;
2196   }
2197 
2198   return true;
2199 }
2200 
2201 /*******************************************************************************
2202 **
2203 ** Function         nfa_rw_t1t_rseg
2204 **
2205 ** Description      Handler for T1t_ReadSeg API
2206 **
2207 ** Returns          TRUE (message buffer to be freed by caller)
2208 **
2209 *******************************************************************************/
nfa_rw_t1t_rseg(tNFA_RW_MSG * p_data)2210 static bool nfa_rw_t1t_rseg(tNFA_RW_MSG* p_data) {
2211   tNFA_RW_OP_PARAMS_T1T_READ* p_t1t_read =
2212       (tNFA_RW_OP_PARAMS_T1T_READ*)&(p_data->op_req.params.t1t_read);
2213 
2214   if (RW_T1tReadSeg(p_t1t_read->segment_number) != NFC_STATUS_OK)
2215     nfa_rw_error_cleanup(NFA_READ_CPLT_EVT);
2216 
2217   return true;
2218 }
2219 
2220 /*******************************************************************************
2221 **
2222 ** Function         nfa_rw_t1t_read8
2223 **
2224 ** Description      Handler for T1T_Read8 API
2225 **
2226 ** Returns          TRUE (message buffer to be freed by caller)
2227 **
2228 *******************************************************************************/
nfa_rw_t1t_read8(tNFA_RW_MSG * p_data)2229 static bool nfa_rw_t1t_read8(tNFA_RW_MSG* p_data) {
2230   tNFA_RW_OP_PARAMS_T1T_READ* p_t1t_read =
2231       (tNFA_RW_OP_PARAMS_T1T_READ*)&(p_data->op_req.params.t1t_read);
2232 
2233   if (RW_T1tRead8(p_t1t_read->block_number) != NFC_STATUS_OK)
2234     nfa_rw_error_cleanup(NFA_READ_CPLT_EVT);
2235 
2236   return true;
2237 }
2238 
2239 /*******************************************************************************
2240 **
2241 ** Function         nfa_rw_t1t_write8
2242 **
2243 ** Description      Handler for T1T_WriteErase8/T1T_WriteNoErase8 API
2244 **
2245 ** Returns          TRUE (message buffer to be freed by caller)
2246 **
2247 *******************************************************************************/
nfa_rw_t1t_write8(tNFA_RW_MSG * p_data)2248 static bool nfa_rw_t1t_write8(tNFA_RW_MSG* p_data) {
2249   tNFA_RW_OP_PARAMS_T1T_WRITE* p_t1t_write =
2250       (tNFA_RW_OP_PARAMS_T1T_WRITE*)&(p_data->op_req.params.t1t_write);
2251   tNFC_STATUS status;
2252 
2253   if (p_t1t_write->b_erase) {
2254     status =
2255         RW_T1tWriteErase8(p_t1t_write->block_number, p_t1t_write->p_block_data);
2256   } else {
2257     status = RW_T1tWriteNoErase8(p_t1t_write->block_number,
2258                                  p_t1t_write->p_block_data);
2259   }
2260 
2261   if (status != NFC_STATUS_OK) {
2262     nfa_rw_error_cleanup(NFA_WRITE_CPLT_EVT);
2263   } else {
2264     if (p_t1t_write->block_number == 0x01)
2265       nfa_rw_cb.ndef_st = NFA_RW_NDEF_ST_UNKNOWN;
2266   }
2267 
2268   return true;
2269 }
2270 
2271 /*******************************************************************************
2272 **
2273 ** Function         nfa_rw_t2t_read
2274 **
2275 ** Description      Handler for T2T_Read API
2276 **
2277 ** Returns          TRUE (message buffer to be freed by caller)
2278 **
2279 *******************************************************************************/
nfa_rw_t2t_read(tNFA_RW_MSG * p_data)2280 static bool nfa_rw_t2t_read(tNFA_RW_MSG* p_data) {
2281   tNFA_RW_OP_PARAMS_T2T_READ* p_t2t_read =
2282       (tNFA_RW_OP_PARAMS_T2T_READ*)&(p_data->op_req.params.t2t_read);
2283   tNFC_STATUS status = NFC_STATUS_FAILED;
2284 
2285   if (nfa_rw_cb.pa_sel_res == NFC_SEL_RES_NFC_FORUM_T2T)
2286     status = RW_T2tRead(p_t2t_read->block_number);
2287 
2288   if (status != NFC_STATUS_OK) nfa_rw_error_cleanup(NFA_READ_CPLT_EVT);
2289 
2290   return true;
2291 }
2292 
2293 /*******************************************************************************
2294 **
2295 ** Function         nfa_rw_t2t_write
2296 **
2297 ** Description      Handler for T2T_Write API
2298 **
2299 ** Returns          TRUE (message buffer to be freed by caller)
2300 **
2301 *******************************************************************************/
nfa_rw_t2t_write(tNFA_RW_MSG * p_data)2302 static bool nfa_rw_t2t_write(tNFA_RW_MSG* p_data) {
2303   tNFA_RW_OP_PARAMS_T2T_WRITE* p_t2t_write =
2304       (tNFA_RW_OP_PARAMS_T2T_WRITE*)&(p_data->op_req.params.t2t_write);
2305 
2306   if (RW_T2tWrite(p_t2t_write->block_number, p_t2t_write->p_block_data) !=
2307       NFC_STATUS_OK) {
2308     nfa_rw_error_cleanup(NFA_WRITE_CPLT_EVT);
2309   } else {
2310     if (p_t2t_write->block_number == 0x03)
2311       nfa_rw_cb.ndef_st = NFA_RW_NDEF_ST_UNKNOWN;
2312   }
2313 
2314   return true;
2315 }
2316 
2317 /*******************************************************************************
2318 **
2319 ** Function         nfa_rw_t2t_sector_select
2320 **
2321 ** Description      Handler for T2T_Sector_Select API
2322 **
2323 ** Returns          TRUE (message buffer to be freed by caller)
2324 **
2325 *******************************************************************************/
nfa_rw_t2t_sector_select(tNFA_RW_MSG * p_data)2326 static bool nfa_rw_t2t_sector_select(tNFA_RW_MSG* p_data) {
2327   tNFA_RW_OP_PARAMS_T2T_SECTOR_SELECT* p_t2t_sector_select =
2328       (tNFA_RW_OP_PARAMS_T2T_SECTOR_SELECT*)&(
2329           p_data->op_req.params.t2t_sector_select);
2330 
2331   if (RW_T2tSectorSelect(p_t2t_sector_select->sector_number) != NFC_STATUS_OK)
2332     nfa_rw_error_cleanup(NFA_SELECT_CPLT_EVT);
2333 
2334   return true;
2335 }
2336 
2337 /*******************************************************************************
2338 **
2339 ** Function         nfa_rw_t3t_read
2340 **
2341 ** Description      Handler for T3T_Read API
2342 **
2343 ** Returns          TRUE (message buffer to be freed by caller)
2344 **
2345 *******************************************************************************/
nfa_rw_t3t_read(tNFA_RW_MSG * p_data)2346 static bool nfa_rw_t3t_read(tNFA_RW_MSG* p_data) {
2347   tNFA_RW_OP_PARAMS_T3T_READ* p_t3t_read =
2348       (tNFA_RW_OP_PARAMS_T3T_READ*)&(p_data->op_req.params.t3t_read);
2349 
2350   if (RW_T3tCheck(p_t3t_read->num_blocks,
2351                   (tT3T_BLOCK_DESC*)p_t3t_read->p_block_desc) != NFC_STATUS_OK)
2352     nfa_rw_error_cleanup(NFA_READ_CPLT_EVT);
2353 
2354   return true;
2355 }
2356 
2357 /*******************************************************************************
2358 **
2359 ** Function         nfa_rw_t3t_write
2360 **
2361 ** Description      Handler for T3T_Write API
2362 **
2363 ** Returns          TRUE (message buffer to be freed by caller)
2364 **
2365 *******************************************************************************/
nfa_rw_t3t_write(tNFA_RW_MSG * p_data)2366 static bool nfa_rw_t3t_write(tNFA_RW_MSG* p_data) {
2367   tNFA_RW_OP_PARAMS_T3T_WRITE* p_t3t_write =
2368       (tNFA_RW_OP_PARAMS_T3T_WRITE*)&(p_data->op_req.params.t3t_write);
2369 
2370   if (RW_T3tUpdate(p_t3t_write->num_blocks,
2371                    (tT3T_BLOCK_DESC*)p_t3t_write->p_block_desc,
2372                    p_t3t_write->p_block_data) != NFC_STATUS_OK)
2373     nfa_rw_error_cleanup(NFA_WRITE_CPLT_EVT);
2374 
2375   return true;
2376 }
2377 
2378 /*******************************************************************************
2379 **
2380 ** Function         nfa_rw_t3t_get_system_codes
2381 **
2382 ** Description      Get system codes (initiated by NFA after activation)
2383 **
2384 ** Returns          TRUE (message buffer to be freed by caller)
2385 **
2386 *******************************************************************************/
nfa_rw_t3t_get_system_codes()2387 static bool nfa_rw_t3t_get_system_codes() {
2388   tNFC_STATUS status;
2389   tNFA_TAG_PARAMS tag_params;
2390 
2391   status = RW_T3tGetSystemCodes();
2392 
2393   if (status != NFC_STATUS_OK) {
2394     /* Command complete - perform cleanup, notify app */
2395     nfa_rw_command_complete();
2396     tag_params.t3t.num_system_codes = 0;
2397     tag_params.t3t.p_system_codes = nullptr;
2398 
2399     nfa_dm_notify_activation_status(NFA_STATUS_OK, &tag_params);
2400   }
2401 
2402   return true;
2403 }
2404 
2405 /*******************************************************************************
2406 **
2407 ** Function         nfa_rw_i93_command
2408 **
2409 ** Description      Handler for ISO 15693 command
2410 **
2411 ** Returns          TRUE (message buffer to be freed by caller)
2412 **
2413 *******************************************************************************/
nfa_rw_i93_command(tNFA_RW_MSG * p_data)2414 static bool nfa_rw_i93_command(tNFA_RW_MSG* p_data) {
2415   tNFA_CONN_EVT_DATA conn_evt_data;
2416   tNFC_STATUS status = NFC_STATUS_OK;
2417   uint8_t i93_command = I93_CMD_STAY_QUIET;
2418 
2419   switch (p_data->op_req.op) {
2420     case NFA_RW_OP_I93_INVENTORY:
2421       i93_command = I93_CMD_INVENTORY;
2422       if (p_data->op_req.params.i93_cmd.uid_present) {
2423         status = RW_I93Inventory(p_data->op_req.params.i93_cmd.afi_present,
2424                                  p_data->op_req.params.i93_cmd.afi,
2425                                  p_data->op_req.params.i93_cmd.uid);
2426       } else {
2427         status = RW_I93Inventory(p_data->op_req.params.i93_cmd.afi_present,
2428                                  p_data->op_req.params.i93_cmd.afi, nullptr);
2429       }
2430       break;
2431 
2432     case NFA_RW_OP_I93_STAY_QUIET:
2433       i93_command = I93_CMD_STAY_QUIET;
2434       status = RW_I93StayQuiet(p_data->op_req.params.i93_cmd.uid);
2435       break;
2436 
2437     case NFA_RW_OP_I93_READ_SINGLE_BLOCK:
2438       i93_command = I93_CMD_READ_SINGLE_BLOCK;
2439       status = RW_I93ReadSingleBlock(
2440           p_data->op_req.params.i93_cmd.first_block_number);
2441       break;
2442 
2443     case NFA_RW_OP_I93_WRITE_SINGLE_BLOCK:
2444       i93_command = I93_CMD_WRITE_SINGLE_BLOCK;
2445       status = RW_I93WriteSingleBlock(
2446           p_data->op_req.params.i93_cmd.first_block_number,
2447           p_data->op_req.params.i93_cmd.p_data);
2448       break;
2449 
2450     case NFA_RW_OP_I93_LOCK_BLOCK:
2451       i93_command = I93_CMD_LOCK_BLOCK;
2452       status = RW_I93LockBlock(
2453           (uint8_t)p_data->op_req.params.i93_cmd.first_block_number);
2454       break;
2455 
2456     case NFA_RW_OP_I93_READ_MULTI_BLOCK:
2457       i93_command = I93_CMD_READ_MULTI_BLOCK;
2458       status = RW_I93ReadMultipleBlocks(
2459           p_data->op_req.params.i93_cmd.first_block_number,
2460           p_data->op_req.params.i93_cmd.number_blocks);
2461       break;
2462 
2463     case NFA_RW_OP_I93_WRITE_MULTI_BLOCK:
2464       i93_command = I93_CMD_WRITE_MULTI_BLOCK;
2465       status = RW_I93WriteMultipleBlocks(
2466           (uint8_t)p_data->op_req.params.i93_cmd.first_block_number,
2467           p_data->op_req.params.i93_cmd.number_blocks,
2468           p_data->op_req.params.i93_cmd.p_data);
2469       break;
2470 
2471     case NFA_RW_OP_I93_SELECT:
2472       i93_command = I93_CMD_SELECT;
2473       status = RW_I93Select(p_data->op_req.params.i93_cmd.p_data);
2474       break;
2475 
2476     case NFA_RW_OP_I93_RESET_TO_READY:
2477       i93_command = I93_CMD_RESET_TO_READY;
2478       status = RW_I93ResetToReady();
2479       break;
2480 
2481     case NFA_RW_OP_I93_WRITE_AFI:
2482       i93_command = I93_CMD_WRITE_AFI;
2483       status = RW_I93WriteAFI(p_data->op_req.params.i93_cmd.afi);
2484       break;
2485 
2486     case NFA_RW_OP_I93_LOCK_AFI:
2487       i93_command = I93_CMD_LOCK_AFI;
2488       status = RW_I93LockAFI();
2489       break;
2490 
2491     case NFA_RW_OP_I93_WRITE_DSFID:
2492       i93_command = I93_CMD_WRITE_DSFID;
2493       status = RW_I93WriteDSFID(p_data->op_req.params.i93_cmd.dsfid);
2494       break;
2495 
2496     case NFA_RW_OP_I93_LOCK_DSFID:
2497       i93_command = I93_CMD_LOCK_DSFID;
2498       status = RW_I93LockDSFID();
2499       break;
2500 
2501     case NFA_RW_OP_I93_GET_SYS_INFO:
2502       i93_command = I93_CMD_GET_SYS_INFO;
2503       if (p_data->op_req.params.i93_cmd.uid_present) {
2504         status = RW_I93GetSysInfo(p_data->op_req.params.i93_cmd.uid);
2505       } else {
2506         status = RW_I93GetSysInfo(nullptr);
2507       }
2508       break;
2509 
2510     case NFA_RW_OP_I93_GET_MULTI_BLOCK_STATUS:
2511       i93_command = I93_CMD_GET_MULTI_BLK_SEC;
2512       status = RW_I93GetMultiBlockSecurityStatus(
2513           p_data->op_req.params.i93_cmd.first_block_number,
2514           p_data->op_req.params.i93_cmd.number_blocks);
2515       break;
2516 
2517     case NFA_RW_OP_I93_SET_ADDR_MODE:
2518       i93_command = I93_CMD_SET_ADDR_MODE;
2519       DLOG_IF(INFO, nfc_debug_enabled) << StringPrintf(
2520           "%s - T5T addressing mode (0: addressed, "
2521           "1: non-addressed) is %d",
2522           __func__, p_data->op_req.params.i93_cmd.addr_mode);
2523 
2524       status = RW_I93SetAddressingMode(p_data->op_req.params.i93_cmd.addr_mode);
2525       if (status != NFC_STATUS_OK) {
2526         break;
2527       }
2528 
2529       /* Command complete - perform cleanup, notify app */
2530       nfa_rw_command_complete();
2531       conn_evt_data.i93_cmd_cplt.status = NFA_STATUS_OK;
2532       conn_evt_data.i93_cmd_cplt.sent_command = i93_command;
2533       nfa_dm_act_conn_cback_notify(NFA_I93_CMD_CPLT_EVT, &conn_evt_data);
2534       break;
2535 
2536     default:
2537       break;
2538   }
2539 
2540   if (status != NFC_STATUS_OK) {
2541     /* Command complete - perform cleanup, notify app */
2542     nfa_rw_command_complete();
2543 
2544     conn_evt_data.i93_cmd_cplt.status = NFA_STATUS_FAILED;
2545     conn_evt_data.i93_cmd_cplt.sent_command = i93_command;
2546 
2547     nfa_dm_act_conn_cback_notify(NFA_I93_CMD_CPLT_EVT, &conn_evt_data);
2548   }
2549 
2550   return true;
2551 }
2552 
2553 /*******************************************************************************
2554 **
2555 ** Function         nfa_rw_raw_mode_data_cback
2556 **
2557 ** Description      Handler for incoming tag data for unsupported tag protocols
2558 **                  (forward data to upper layer)
2559 **
2560 ** Returns          nothing
2561 **
2562 *******************************************************************************/
nfa_rw_raw_mode_data_cback(uint8_t conn_id,tNFC_CONN_EVT event,tNFC_CONN * p_data)2563 static void nfa_rw_raw_mode_data_cback(__attribute__((unused)) uint8_t conn_id,
2564                                        tNFC_CONN_EVT event, tNFC_CONN* p_data) {
2565   NFC_HDR* p_msg;
2566   tNFA_CONN_EVT_DATA evt_data;
2567 
2568   DLOG_IF(INFO, nfc_debug_enabled) << StringPrintf("event = 0x%X", event);
2569 
2570   if ((event == NFC_DATA_CEVT) &&
2571       ((p_data->data.status == NFC_STATUS_OK) ||
2572        (p_data->data.status == NFC_STATUS_CONTINUE))) {
2573     p_msg = (NFC_HDR*)p_data->data.p_data;
2574 
2575     if (p_msg) {
2576       evt_data.data.status = p_data->data.status;
2577       evt_data.data.p_data = (uint8_t*)(p_msg + 1) + p_msg->offset;
2578       evt_data.data.len = p_msg->len;
2579 
2580       nfa_dm_conn_cback_event_notify(NFA_DATA_EVT, &evt_data);
2581 
2582       GKI_freebuf(p_msg);
2583     } else {
2584       LOG(ERROR) << StringPrintf(
2585           "received NFC_DATA_CEVT with NULL data pointer");
2586     }
2587   } else if (event == NFC_DEACTIVATE_CEVT) {
2588     NFC_SetStaticRfCback(nullptr);
2589   }
2590 }
2591 
2592 /*******************************************************************************
2593 **
2594 ** Function         nfa_rw_activate_ntf
2595 **
2596 ** Description      Handler for NFA_RW_ACTIVATE_NTF
2597 **
2598 ** Returns          TRUE (message buffer to be freed by caller)
2599 **
2600 *******************************************************************************/
nfa_rw_activate_ntf(tNFA_RW_MSG * p_data)2601 bool nfa_rw_activate_ntf(tNFA_RW_MSG* p_data) {
2602   tNFC_ACTIVATE_DEVT* p_activate_params =
2603       p_data->activate_ntf.p_activate_params;
2604   tNFA_TAG_PARAMS tag_params;
2605   bool activate_notify = true;
2606   uint8_t* p;
2607 
2608   if ((nfa_rw_cb.halt_event != RW_T2T_MAX_EVT) &&
2609       (nfa_rw_cb.activated_tech_mode == NFC_DISCOVERY_TYPE_POLL_A) &&
2610       (nfa_rw_cb.protocol == NFC_PROTOCOL_T2T) &&
2611       (nfa_rw_cb.pa_sel_res == NFC_SEL_RES_NFC_FORUM_T2T)) {
2612     /* Type 2 tag is wake up from HALT State */
2613     if (nfa_dm_cb.p_activate_ntf != nullptr) {
2614       GKI_freebuf(nfa_dm_cb.p_activate_ntf);
2615       nfa_dm_cb.p_activate_ntf = nullptr;
2616     }
2617     DLOG_IF(INFO, nfc_debug_enabled)
2618         << StringPrintf("- Type 2 tag wake up from HALT State");
2619     return true;
2620   }
2621 
2622   DLOG_IF(INFO, nfc_debug_enabled) << __func__;
2623 
2624   /* Initialize control block */
2625   nfa_rw_cb.protocol = p_activate_params->protocol;
2626   nfa_rw_cb.intf_type = p_activate_params->intf_param.type;
2627   nfa_rw_cb.pa_sel_res = p_activate_params->rf_tech_param.param.pa.sel_rsp;
2628   nfa_rw_cb.activated_tech_mode = p_activate_params->rf_tech_param.mode;
2629   nfa_rw_cb.flags = NFA_RW_FL_ACTIVATED;
2630   nfa_rw_cb.cur_op = NFA_RW_OP_MAX;
2631   nfa_rw_cb.halt_event = RW_T2T_MAX_EVT;
2632   nfa_rw_cb.skip_dyn_locks = false;
2633   nfa_rw_cb.ndef_st = NFA_RW_NDEF_ST_UNKNOWN;
2634   nfa_rw_cb.tlv_st = NFA_RW_TLV_DETECT_ST_OP_NOT_STARTED;
2635 
2636   nfa_rw_cb.pres_check_iso_dep_nak = false;
2637   nfa_rw_cb.pres_check_iso_dep_nak_count = 0;
2638   nfa_rw_cb.pres_check_iso_dep_nak_err_cnt = 0;
2639   nfa_rw_cb.pres_check_tag = false;
2640   nfa_rw_cb.pres_check_tag_err_count = 0;
2641 
2642   memset(&tag_params, 0, sizeof(tNFA_TAG_PARAMS));
2643 
2644   /* Check if we are in exclusive RF mode */
2645   if (p_data->activate_ntf.excl_rf_not_active) {
2646     /* Not in exclusive RF mode */
2647     nfa_rw_cb.flags |= NFA_RW_FL_NOT_EXCL_RF_MODE;
2648   }
2649 
2650   /* check if the protocol is activated with supported interface */
2651   if (p_activate_params->intf_param.type == NCI_INTERFACE_FRAME) {
2652     if ((p_activate_params->protocol != NFA_PROTOCOL_T1T) &&
2653         (p_activate_params->protocol != NFA_PROTOCOL_T2T) &&
2654         (p_activate_params->protocol != NFA_PROTOCOL_T3T) &&
2655         (p_activate_params->protocol != NFA_PROTOCOL_T5T)) {
2656       nfa_rw_cb.protocol = NFA_PROTOCOL_INVALID;
2657     }
2658   } else if (p_activate_params->intf_param.type == NCI_INTERFACE_ISO_DEP) {
2659     if (p_activate_params->protocol != NFA_PROTOCOL_ISO_DEP) {
2660       nfa_rw_cb.protocol = NFA_PROTOCOL_INVALID;
2661     }
2662   }
2663 
2664   if (nfa_rw_cb.protocol == NFA_PROTOCOL_INVALID) {
2665     /* Only sending raw frame and presence check are supported in this state */
2666 
2667     NFC_SetStaticRfCback(nfa_rw_raw_mode_data_cback);
2668 
2669     /* Notify app of NFA_ACTIVATED_EVT and start presence check timer */
2670     nfa_dm_notify_activation_status(NFA_STATUS_OK, nullptr);
2671     nfa_rw_check_start_presence_check_timer(NFA_RW_PRESENCE_CHECK_INTERVAL);
2672     return true;
2673   }
2674 
2675   /* If protocol not supported by RW module, notify app of NFA_ACTIVATED_EVT and
2676    * start presence check if needed */
2677   if (!nfa_dm_is_protocol_supported(
2678           p_activate_params->protocol,
2679           p_activate_params->rf_tech_param.param.pa.sel_rsp)) {
2680     /* Notify upper layer of NFA_ACTIVATED_EVT if needed, and start presence
2681      * check timer */
2682     /* Set data callback (pass all incoming data to upper layer using
2683      * NFA_DATA_EVT) */
2684     NFC_SetStaticRfCback(nfa_rw_raw_mode_data_cback);
2685 
2686     /* Notify app of NFA_ACTIVATED_EVT and start presence check timer */
2687     nfa_dm_notify_activation_status(NFA_STATUS_OK, nullptr);
2688     nfa_rw_check_start_presence_check_timer(NFA_RW_PRESENCE_CHECK_INTERVAL);
2689     return true;
2690   }
2691 
2692   /* Initialize RW module */
2693   if ((RW_SetActivatedTagType(p_activate_params, nfa_rw_cback)) !=
2694       NFC_STATUS_OK) {
2695     /* Log error (stay in NFA_RW_ST_ACTIVATED state until deactivation) */
2696     LOG(ERROR) << StringPrintf("RW_SetActivatedTagType failed.");
2697     return true;
2698   }
2699 
2700   /* Perform protocol-specific actions */
2701   if (NFC_PROTOCOL_T1T == nfa_rw_cb.protocol) {
2702     /* Retrieve HR and UID fields from activation notification */
2703     memcpy(tag_params.t1t.uid, p_activate_params->rf_tech_param.param.pa.nfcid1,
2704            p_activate_params->rf_tech_param.param.pa.nfcid1_len);
2705 
2706     if (NFC_GetNCIVersion() == NCI_VERSION_2_0) {
2707       memcpy(tag_params.t1t.hr, p_activate_params->rf_tech_param.param.pa.hr,
2708              NFA_T1T_HR_LEN);
2709     } else {
2710       memcpy(tag_params.t1t.hr,
2711              p_activate_params->intf_param.intf_param.frame.param,
2712              NFA_T1T_HR_LEN);
2713       tNFA_RW_MSG msg;
2714       msg.op_req.op = NFA_RW_OP_T1T_RID;
2715       bool free_buf = nfa_rw_handle_op_req(&msg);
2716       CHECK(free_buf)
2717           << "nfa_rw_handle_op_req is holding on to soon-garbage stack memory.";
2718       /* Delay notifying upper layer of NFA_ACTIVATED_EVT
2719          until HR0/HR1 is received */
2720       activate_notify = false;
2721     }
2722   } else if (NFC_PROTOCOL_T2T == nfa_rw_cb.protocol) {
2723     /* Retrieve UID fields from activation notification */
2724     memcpy(tag_params.t2t.uid, p_activate_params->rf_tech_param.param.pa.nfcid1,
2725            p_activate_params->rf_tech_param.param.pa.nfcid1_len);
2726   } else if (NFC_PROTOCOL_T3T == nfa_rw_cb.protocol) {
2727     /* Delay notifying upper layer of NFA_ACTIVATED_EVT until system codes
2728      * are retrieved */
2729     activate_notify = false;
2730 
2731     /* Issue command to get Felica system codes */
2732     tNFA_RW_MSG msg;
2733     msg.op_req.op = NFA_RW_OP_T3T_GET_SYSTEM_CODES;
2734     bool free_buf = nfa_rw_handle_op_req(&msg);
2735     CHECK(free_buf)
2736         << "nfa_rw_handle_op_req is holding on to soon-garbage stack memory.";
2737   } else if (NFA_PROTOCOL_T5T == nfa_rw_cb.protocol) {
2738     /* Delay notifying upper layer of NFA_ACTIVATED_EVT to retrieve additional
2739      * tag infomation */
2740     nfa_rw_cb.flags |= NFA_RW_FL_ACTIVATION_NTF_PENDING;
2741     activate_notify = false;
2742 
2743     /* store DSFID and UID from activation NTF */
2744     nfa_rw_cb.i93_dsfid = p_activate_params->rf_tech_param.param.pi93.dsfid;
2745 
2746     p = nfa_rw_cb.i93_uid;
2747     ARRAY8_TO_STREAM(p, p_activate_params->rf_tech_param.param.pi93.uid);
2748 
2749     if ((nfa_rw_cb.i93_uid[1] == I93_UID_IC_MFG_CODE_TI) &&
2750         (((nfa_rw_cb.i93_uid[2] & I93_UID_TAG_IT_HF_I_PRODUCT_ID_MASK) ==
2751           I93_UID_TAG_IT_HF_I_STD_CHIP_INLAY) ||
2752          ((nfa_rw_cb.i93_uid[2] & I93_UID_TAG_IT_HF_I_PRODUCT_ID_MASK) ==
2753           I93_UID_TAG_IT_HF_I_PRO_CHIP_INLAY))) {
2754       /* these don't support Get System Information Command */
2755       nfa_rw_cb.i93_block_size = I93_TAG_IT_HF_I_STD_PRO_CHIP_INLAY_BLK_SIZE;
2756       nfa_rw_cb.i93_afi_location =
2757           I93_TAG_IT_HF_I_STD_PRO_CHIP_INLAY_AFI_LOCATION;
2758 
2759       if ((nfa_rw_cb.i93_uid[2] & I93_UID_TAG_IT_HF_I_PRODUCT_ID_MASK) ==
2760           I93_UID_TAG_IT_HF_I_STD_CHIP_INLAY) {
2761         nfa_rw_cb.i93_num_block = I93_TAG_IT_HF_I_STD_CHIP_INLAY_NUM_TOTAL_BLK;
2762       } else {
2763         nfa_rw_cb.i93_num_block = I93_TAG_IT_HF_I_PRO_CHIP_INLAY_NUM_TOTAL_BLK;
2764       }
2765 
2766       /* read AFI */
2767       if (RW_I93ReadSingleBlock((uint8_t)(nfa_rw_cb.i93_afi_location /
2768                                           nfa_rw_cb.i93_block_size)) !=
2769           NFC_STATUS_OK) {
2770         /* notify activation without AFI/IC-Ref */
2771         nfa_rw_cb.flags &= ~NFA_RW_FL_ACTIVATION_NTF_PENDING;
2772         activate_notify = true;
2773 
2774         tag_params.i93.info_flags =
2775             (I93_INFO_FLAG_DSFID | I93_INFO_FLAG_MEM_SIZE);
2776         tag_params.i93.dsfid = nfa_rw_cb.i93_dsfid;
2777         tag_params.i93.block_size = nfa_rw_cb.i93_block_size;
2778         tag_params.i93.num_block = nfa_rw_cb.i93_num_block;
2779         memcpy(tag_params.i93.uid, nfa_rw_cb.i93_uid, I93_UID_BYTE_LEN);
2780       }
2781     } else {
2782       /* All of ICODE supports Get System Information Command */
2783       /* Tag-it HF-I Plus Chip/Inlay supports Get System Information Command */
2784       /* just try for others */
2785 
2786       if (!appl_dta_mode_flag) {
2787         if (RW_I93GetSysInfo(nfa_rw_cb.i93_uid) != NFC_STATUS_OK) {
2788           /* notify activation without AFI/MEM size/IC-Ref */
2789           nfa_rw_cb.flags &= ~NFA_RW_FL_ACTIVATION_NTF_PENDING;
2790           activate_notify = true;
2791 
2792           tag_params.i93.info_flags = I93_INFO_FLAG_DSFID;
2793           tag_params.i93.dsfid = nfa_rw_cb.i93_dsfid;
2794           tag_params.i93.block_size = 0;
2795           tag_params.i93.num_block = 0;
2796           memcpy(tag_params.i93.uid, nfa_rw_cb.i93_uid, I93_UID_BYTE_LEN);
2797         } else {
2798           /* reset memory size */
2799           nfa_rw_cb.i93_block_size = 0;
2800           nfa_rw_cb.i93_num_block = 0;
2801         }
2802       } else {
2803         nfa_rw_cb.flags &= ~NFA_RW_FL_ACTIVATION_NTF_PENDING;
2804         activate_notify = true;
2805 
2806         tag_params.i93.info_flags = I93_INFO_FLAG_DSFID;
2807         tag_params.i93.dsfid = nfa_rw_cb.i93_dsfid;
2808         tag_params.i93.block_size = 0;
2809         tag_params.i93.num_block = 0;
2810         memcpy(tag_params.i93.uid, nfa_rw_cb.i93_uid, I93_UID_BYTE_LEN);
2811       }
2812     }
2813   }
2814 
2815   /* Notify upper layer of NFA_ACTIVATED_EVT if needed, and start presence check
2816    * timer */
2817   if (activate_notify) {
2818     nfa_dm_notify_activation_status(NFA_STATUS_OK, &tag_params);
2819     nfa_rw_check_start_presence_check_timer(NFA_RW_PRESENCE_CHECK_INTERVAL);
2820   }
2821 
2822   return true;
2823 }
2824 
2825 /*******************************************************************************
2826 **
2827 ** Function         nfa_rw_deactivate_ntf
2828 **
2829 ** Description      Handler for NFA_RW_DEACTIVATE_NTF
2830 **
2831 ** Returns          TRUE (message buffer to be freed by caller)
2832 **
2833 *******************************************************************************/
nfa_rw_deactivate_ntf(tNFA_RW_MSG * p_data)2834 bool nfa_rw_deactivate_ntf(__attribute__((unused)) tNFA_RW_MSG* p_data) {
2835   /* Clear the activated flag */
2836   nfa_rw_cb.flags &= ~NFA_RW_FL_ACTIVATED;
2837 
2838   /* Free buffer for incoming NDEF message, in case we were in the middle of a
2839    * read operation */
2840   nfa_rw_free_ndef_rx_buf();
2841 
2842   /* If there is a pending command message, then free it */
2843   if (nfa_rw_cb.p_pending_msg) {
2844     if ((nfa_rw_cb.p_pending_msg->op_req.op == NFA_RW_OP_SEND_RAW_FRAME) &&
2845         (nfa_rw_cb.p_pending_msg->op_req.params.send_raw_frame.p_data)) {
2846       GKI_freebuf(nfa_rw_cb.p_pending_msg->op_req.params.send_raw_frame.p_data);
2847     }
2848 
2849     GKI_freebuf(nfa_rw_cb.p_pending_msg);
2850     nfa_rw_cb.p_pending_msg = nullptr;
2851   }
2852 
2853   /* If we are in the process of waking up tag from HALT state */
2854   if (nfa_rw_cb.halt_event == RW_T2T_READ_CPLT_EVT) {
2855     if (nfa_rw_cb.rw_data.data.p_data)
2856       GKI_freebuf(nfa_rw_cb.rw_data.data.p_data);
2857     nfa_rw_cb.rw_data.data.p_data = nullptr;
2858   }
2859 
2860   /* Stop presence check timer (if started) */
2861   nfa_rw_stop_presence_check_timer();
2862 
2863   return true;
2864 }
2865 
2866 /*******************************************************************************
2867 **
2868 ** Function         nfa_rw_handle_op_req
2869 **
2870 ** Description      Handler for NFA_RW_OP_REQUEST_EVT, operation request
2871 **
2872 ** Returns          TRUE if caller should free p_data
2873 **                  FALSE if caller does not need to free p_data
2874 **
2875 *******************************************************************************/
nfa_rw_handle_op_req(tNFA_RW_MSG * p_data)2876 bool nfa_rw_handle_op_req(tNFA_RW_MSG* p_data) {
2877   tNFA_CONN_EVT_DATA conn_evt_data;
2878   bool freebuf = true;
2879   uint16_t presence_check_start_delay = 0;
2880 
2881   /* Check if activated */
2882   if (!(nfa_rw_cb.flags & NFA_RW_FL_ACTIVATED)) {
2883     LOG(ERROR) << StringPrintf("nfa_rw_handle_op_req: not activated");
2884     return (nfa_rw_op_req_while_inactive(p_data));
2885   }
2886   /* Check if currently busy with another API call */
2887   else if (nfa_rw_cb.flags & NFA_RW_FL_API_BUSY) {
2888     return (nfa_rw_op_req_while_busy(p_data));
2889   }
2890   /* Check if currently busy with auto-presence check */
2891   else if (nfa_rw_cb.flags & NFA_RW_FL_AUTO_PRESENCE_CHECK_BUSY) {
2892     /* Cache the command (will be handled once auto-presence check is completed)
2893      */
2894     DLOG_IF(INFO, nfc_debug_enabled) << StringPrintf(
2895         "Deferring operation %i until after auto-presence check is completed",
2896         p_data->op_req.op);
2897     nfa_rw_cb.p_pending_msg = p_data;
2898     nfa_rw_cb.flags |= NFA_RW_FL_API_BUSY;
2899     return false;
2900   }
2901 
2902   DLOG_IF(INFO, nfc_debug_enabled)
2903       << StringPrintf("nfa_rw_handle_op_req: op=0x%02x", p_data->op_req.op);
2904 
2905   nfa_rw_cb.flags |= NFA_RW_FL_API_BUSY;
2906 
2907   /* Stop the presence check timer */
2908   nfa_rw_stop_presence_check_timer();
2909 
2910   /* Store the current operation */
2911   nfa_rw_cb.cur_op = p_data->op_req.op;
2912 
2913   /* Call appropriate handler for requested operation */
2914   switch (p_data->op_req.op) {
2915     case NFA_RW_OP_DETECT_NDEF:
2916       nfa_rw_detect_ndef();
2917       break;
2918 
2919     case NFA_RW_OP_READ_NDEF:
2920       nfa_rw_read_ndef();
2921       break;
2922 
2923     case NFA_RW_OP_WRITE_NDEF:
2924       nfa_rw_write_ndef(p_data);
2925       break;
2926 
2927     case NFA_RW_OP_SEND_RAW_FRAME:
2928       presence_check_start_delay =
2929           p_data->op_req.params.send_raw_frame.p_data->layer_specific;
2930 
2931       NFC_SendData(NFC_RF_CONN_ID, p_data->op_req.params.send_raw_frame.p_data);
2932 
2933       /* Clear the busy flag */
2934       nfa_rw_cb.flags &= ~NFA_RW_FL_API_BUSY;
2935 
2936       /* Start presence_check after specified delay */
2937       nfa_rw_check_start_presence_check_timer(presence_check_start_delay);
2938       break;
2939 
2940     case NFA_RW_OP_PRESENCE_CHECK:
2941       nfa_rw_presence_check(p_data);
2942       break;
2943 
2944     case NFA_RW_OP_FORMAT_TAG:
2945       nfa_rw_format_tag();
2946       break;
2947 
2948     case NFA_RW_OP_DETECT_LOCK_TLV:
2949       nfa_rw_detect_tlv(TAG_LOCK_CTRL_TLV);
2950       break;
2951 
2952     case NFA_RW_OP_DETECT_MEM_TLV:
2953       nfa_rw_detect_tlv(TAG_MEM_CTRL_TLV);
2954       break;
2955 
2956     case NFA_RW_OP_SET_TAG_RO:
2957       nfa_rw_cb.b_hard_lock = p_data->op_req.params.set_readonly.b_hard_lock;
2958       nfa_rw_config_tag_ro(nfa_rw_cb.b_hard_lock);
2959       break;
2960 
2961     case NFA_RW_OP_T1T_RID:
2962       nfa_rw_t1t_rid();
2963       break;
2964 
2965     case NFA_RW_OP_T1T_RALL:
2966       nfa_rw_t1t_rall();
2967       break;
2968 
2969     case NFA_RW_OP_T1T_READ:
2970       nfa_rw_t1t_read(p_data);
2971       break;
2972 
2973     case NFA_RW_OP_T1T_WRITE:
2974       nfa_rw_t1t_write(p_data);
2975       break;
2976 
2977     case NFA_RW_OP_T1T_RSEG:
2978       nfa_rw_t1t_rseg(p_data);
2979       break;
2980 
2981     case NFA_RW_OP_T1T_READ8:
2982       nfa_rw_t1t_read8(p_data);
2983       break;
2984 
2985     case NFA_RW_OP_T1T_WRITE8:
2986       nfa_rw_t1t_write8(p_data);
2987       break;
2988 
2989     /* Type-2 tag commands */
2990     case NFA_RW_OP_T2T_READ:
2991       nfa_rw_t2t_read(p_data);
2992       break;
2993 
2994     case NFA_RW_OP_T2T_WRITE:
2995       nfa_rw_t2t_write(p_data);
2996       break;
2997 
2998     case NFA_RW_OP_T2T_SECTOR_SELECT:
2999       nfa_rw_t2t_sector_select(p_data);
3000       break;
3001 
3002     case NFA_RW_OP_T2T_READ_DYN_LOCKS:
3003       if (p_data->op_req.params.t2t_read_dyn_locks.read_dyn_locks == true) {
3004         nfa_rw_cb.skip_dyn_locks = false;
3005       } else {
3006         nfa_rw_cb.skip_dyn_locks = true;
3007       }
3008       DLOG_IF(INFO, nfc_debug_enabled)
3009           << StringPrintf("%s - Skip reading of dynamic lock bytes: %d",
3010                           __func__, nfa_rw_cb.skip_dyn_locks);
3011 
3012       /* Command complete - perform cleanup, notify app */
3013       nfa_rw_command_complete();
3014       conn_evt_data.status = NFA_STATUS_OK;
3015       nfa_dm_act_conn_cback_notify(NFA_T2T_CMD_CPLT_EVT, &conn_evt_data);
3016       break;
3017 
3018     /* Type-3 tag commands */
3019     case NFA_RW_OP_T3T_READ:
3020       nfa_rw_t3t_read(p_data);
3021       break;
3022 
3023     case NFA_RW_OP_T3T_WRITE:
3024       nfa_rw_t3t_write(p_data);
3025       break;
3026 
3027     case NFA_RW_OP_T3T_GET_SYSTEM_CODES:
3028       nfa_rw_t3t_get_system_codes();
3029       break;
3030 
3031     /* ISO 15693 tag commands */
3032     case NFA_RW_OP_I93_INVENTORY:
3033     case NFA_RW_OP_I93_STAY_QUIET:
3034     case NFA_RW_OP_I93_READ_SINGLE_BLOCK:
3035     case NFA_RW_OP_I93_WRITE_SINGLE_BLOCK:
3036     case NFA_RW_OP_I93_LOCK_BLOCK:
3037     case NFA_RW_OP_I93_READ_MULTI_BLOCK:
3038     case NFA_RW_OP_I93_WRITE_MULTI_BLOCK:
3039     case NFA_RW_OP_I93_SELECT:
3040     case NFA_RW_OP_I93_RESET_TO_READY:
3041     case NFA_RW_OP_I93_WRITE_AFI:
3042     case NFA_RW_OP_I93_LOCK_AFI:
3043     case NFA_RW_OP_I93_WRITE_DSFID:
3044     case NFA_RW_OP_I93_LOCK_DSFID:
3045     case NFA_RW_OP_I93_GET_SYS_INFO:
3046     case NFA_RW_OP_I93_GET_MULTI_BLOCK_STATUS:
3047     case NFA_RW_OP_I93_SET_ADDR_MODE:
3048       nfa_rw_i93_command(p_data);
3049       break;
3050 
3051     default:
3052       LOG(ERROR) << StringPrintf("nfa_rw_handle_api: unhandled operation: %i",
3053                                  p_data->op_req.op);
3054       break;
3055   }
3056 
3057   return (freebuf);
3058 }
3059 
3060 /*******************************************************************************
3061 **
3062 ** Function         nfa_rw_op_req_while_busy
3063 **
3064 ** Description      Handle operation request while busy
3065 **
3066 ** Returns          TRUE if caller should free p_data
3067 **                  FALSE if caller does not need to free p_data
3068 **
3069 *******************************************************************************/
nfa_rw_op_req_while_busy(tNFA_RW_MSG * p_data)3070 static bool nfa_rw_op_req_while_busy(tNFA_RW_MSG* p_data) {
3071   bool freebuf = true;
3072   tNFA_CONN_EVT_DATA conn_evt_data;
3073   uint8_t event;
3074 
3075   LOG(ERROR) << StringPrintf("nfa_rw_op_req_while_busy: unable to handle API");
3076 
3077   /* Return appropriate event for requested API, with status=BUSY */
3078   conn_evt_data.status = NFA_STATUS_BUSY;
3079 
3080   switch (p_data->op_req.op) {
3081     case NFA_RW_OP_DETECT_NDEF:
3082       conn_evt_data.ndef_detect.cur_size = 0;
3083       conn_evt_data.ndef_detect.max_size = 0;
3084       conn_evt_data.ndef_detect.flags = RW_NDEF_FL_UNKNOWN;
3085       event = NFA_NDEF_DETECT_EVT;
3086       break;
3087     case NFA_RW_OP_READ_NDEF:
3088     case NFA_RW_OP_T1T_RID:
3089     case NFA_RW_OP_T1T_RALL:
3090     case NFA_RW_OP_T1T_READ:
3091     case NFA_RW_OP_T1T_RSEG:
3092     case NFA_RW_OP_T1T_READ8:
3093     case NFA_RW_OP_T2T_READ:
3094     case NFA_RW_OP_T3T_READ:
3095       event = NFA_READ_CPLT_EVT;
3096       break;
3097     case NFA_RW_OP_WRITE_NDEF:
3098     case NFA_RW_OP_T1T_WRITE:
3099     case NFA_RW_OP_T1T_WRITE8:
3100     case NFA_RW_OP_T2T_WRITE:
3101     case NFA_RW_OP_T3T_WRITE:
3102       event = NFA_WRITE_CPLT_EVT;
3103       break;
3104     case NFA_RW_OP_FORMAT_TAG:
3105       event = NFA_FORMAT_CPLT_EVT;
3106       break;
3107     case NFA_RW_OP_DETECT_LOCK_TLV:
3108     case NFA_RW_OP_DETECT_MEM_TLV:
3109       event = NFA_TLV_DETECT_EVT;
3110       break;
3111     case NFA_RW_OP_SET_TAG_RO:
3112       event = NFA_SET_TAG_RO_EVT;
3113       break;
3114     case NFA_RW_OP_T2T_SECTOR_SELECT:
3115       event = NFA_SELECT_CPLT_EVT;
3116       break;
3117     case NFA_RW_OP_I93_INVENTORY:
3118     case NFA_RW_OP_I93_STAY_QUIET:
3119     case NFA_RW_OP_I93_READ_SINGLE_BLOCK:
3120     case NFA_RW_OP_I93_WRITE_SINGLE_BLOCK:
3121     case NFA_RW_OP_I93_LOCK_BLOCK:
3122     case NFA_RW_OP_I93_READ_MULTI_BLOCK:
3123     case NFA_RW_OP_I93_WRITE_MULTI_BLOCK:
3124     case NFA_RW_OP_I93_SELECT:
3125     case NFA_RW_OP_I93_RESET_TO_READY:
3126     case NFA_RW_OP_I93_WRITE_AFI:
3127     case NFA_RW_OP_I93_LOCK_AFI:
3128     case NFA_RW_OP_I93_WRITE_DSFID:
3129     case NFA_RW_OP_I93_LOCK_DSFID:
3130     case NFA_RW_OP_I93_GET_SYS_INFO:
3131     case NFA_RW_OP_I93_GET_MULTI_BLOCK_STATUS:
3132       event = NFA_I93_CMD_CPLT_EVT;
3133       break;
3134     default:
3135       return (freebuf);
3136   }
3137   nfa_dm_act_conn_cback_notify(event, &conn_evt_data);
3138 
3139   return (freebuf);
3140 }
3141 
3142 /*******************************************************************************
3143 **
3144 ** Function         nfa_rw_op_req_while_inactive
3145 **
3146 ** Description      Handle operation request while inactive
3147 **
3148 ** Returns          TRUE if caller should free p_data
3149 **                  FALSE if caller does not need to free p_data
3150 **
3151 *******************************************************************************/
nfa_rw_op_req_while_inactive(tNFA_RW_MSG * p_data)3152 static bool nfa_rw_op_req_while_inactive(tNFA_RW_MSG* p_data) {
3153   bool freebuf = true;
3154   tNFA_CONN_EVT_DATA conn_evt_data;
3155   uint8_t event;
3156 
3157   LOG(ERROR) << StringPrintf(
3158       "nfa_rw_op_req_while_inactive: unable to handle API");
3159 
3160   /* Return appropriate event for requested API, with status=REJECTED */
3161   conn_evt_data.status = NFA_STATUS_REJECTED;
3162 
3163   switch (p_data->op_req.op) {
3164     case NFA_RW_OP_DETECT_NDEF:
3165       conn_evt_data.ndef_detect.cur_size = 0;
3166       conn_evt_data.ndef_detect.max_size = 0;
3167       conn_evt_data.ndef_detect.flags = RW_NDEF_FL_UNKNOWN;
3168       event = NFA_NDEF_DETECT_EVT;
3169       break;
3170     case NFA_RW_OP_READ_NDEF:
3171     case NFA_RW_OP_T1T_RID:
3172     case NFA_RW_OP_T1T_RALL:
3173     case NFA_RW_OP_T1T_READ:
3174     case NFA_RW_OP_T1T_RSEG:
3175     case NFA_RW_OP_T1T_READ8:
3176     case NFA_RW_OP_T2T_READ:
3177     case NFA_RW_OP_T3T_READ:
3178       event = NFA_READ_CPLT_EVT;
3179       break;
3180     case NFA_RW_OP_WRITE_NDEF:
3181     case NFA_RW_OP_T1T_WRITE:
3182     case NFA_RW_OP_T1T_WRITE8:
3183     case NFA_RW_OP_T2T_WRITE:
3184     case NFA_RW_OP_T3T_WRITE:
3185       event = NFA_WRITE_CPLT_EVT;
3186       break;
3187     case NFA_RW_OP_FORMAT_TAG:
3188       event = NFA_FORMAT_CPLT_EVT;
3189       break;
3190     case NFA_RW_OP_DETECT_LOCK_TLV:
3191     case NFA_RW_OP_DETECT_MEM_TLV:
3192       event = NFA_TLV_DETECT_EVT;
3193       break;
3194     case NFA_RW_OP_SET_TAG_RO:
3195       event = NFA_SET_TAG_RO_EVT;
3196       break;
3197     case NFA_RW_OP_T2T_SECTOR_SELECT:
3198       event = NFA_SELECT_CPLT_EVT;
3199       break;
3200     case NFA_RW_OP_I93_INVENTORY:
3201     case NFA_RW_OP_I93_STAY_QUIET:
3202     case NFA_RW_OP_I93_READ_SINGLE_BLOCK:
3203     case NFA_RW_OP_I93_WRITE_SINGLE_BLOCK:
3204     case NFA_RW_OP_I93_LOCK_BLOCK:
3205     case NFA_RW_OP_I93_READ_MULTI_BLOCK:
3206     case NFA_RW_OP_I93_WRITE_MULTI_BLOCK:
3207     case NFA_RW_OP_I93_SELECT:
3208     case NFA_RW_OP_I93_RESET_TO_READY:
3209     case NFA_RW_OP_I93_WRITE_AFI:
3210     case NFA_RW_OP_I93_LOCK_AFI:
3211     case NFA_RW_OP_I93_WRITE_DSFID:
3212     case NFA_RW_OP_I93_LOCK_DSFID:
3213     case NFA_RW_OP_I93_GET_SYS_INFO:
3214     case NFA_RW_OP_I93_GET_MULTI_BLOCK_STATUS:
3215       event = NFA_I93_CMD_CPLT_EVT;
3216       break;
3217     default:
3218       return (freebuf);
3219   }
3220   nfa_dm_act_conn_cback_notify(event, &conn_evt_data);
3221 
3222   return (freebuf);
3223 }
3224 
3225 /*******************************************************************************
3226 **
3227 ** Function         nfa_rw_command_complete
3228 **
3229 ** Description      Handle command complete: clear the busy flag,
3230 **                  and start the presence check timer if applicable.
3231 **
3232 ** Returns          None
3233 **
3234 *******************************************************************************/
nfa_rw_command_complete(void)3235 void nfa_rw_command_complete(void) {
3236   /* Clear the busy flag */
3237   nfa_rw_cb.flags &= ~NFA_RW_FL_API_BUSY;
3238 
3239   /* Restart presence_check timer */
3240   nfa_rw_check_start_presence_check_timer(NFA_RW_PRESENCE_CHECK_INTERVAL);
3241 }
3242