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