• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /******************************************************************************
2  *
3  *  Copyright (C) 2011-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 implementation for ISO 15693 in Reader/Writer
22  *  mode.
23  *
24  ******************************************************************************/
25 #include <log/log.h>
26 #include <string.h>
27 
28 #include <android-base/stringprintf.h>
29 #include <base/logging.h>
30 
31 #include "nfc_target.h"
32 
33 #include "bt_types.h"
34 #include "nfc_api.h"
35 #include "nfc_int.h"
36 #include "rw_api.h"
37 #include "rw_int.h"
38 
39 using android::base::StringPrintf;
40 
41 extern bool nfc_debug_enabled;
42 extern unsigned char appl_dta_mode_flag;
43 
44 /* Response timeout     */
45 #define RW_I93_TOUT_RESP 1000
46 /* stay quiet timeout   */
47 #define RW_I93_TOUT_STAY_QUIET 200
48 /* max reading data if read multi block is supported */
49 #define RW_I93_READ_MULTI_BLOCK_SIZE 128
50 /* CC, zero length NDEF, Terminator TLV              */
51 #define RW_I93_FORMAT_DATA_LEN 8
52 /* max getting lock status if get multi block sec is supported */
53 #define RW_I93_GET_MULTI_BLOCK_SEC_SIZE 253
54 
55 static std::string rw_i93_get_tag_name(uint8_t product_version);
56 
57 static void rw_i93_data_cback(uint8_t conn_id, tNFC_CONN_EVT event,
58                               tNFC_CONN* p_data);
59 void rw_i93_handle_error(tNFC_STATUS status);
60 tNFC_STATUS rw_i93_send_cmd_get_sys_info(uint8_t* p_uid, uint8_t extra_flag);
61 tNFC_STATUS rw_i93_send_cmd_get_ext_sys_info(uint8_t* p_uid);
62 
63 /*******************************************************************************
64 **
65 ** Function         rw_i93_get_product_version
66 **
67 ** Description      Get product version from UID
68 **
69 ** Returns          void
70 **
71 *******************************************************************************/
rw_i93_get_product_version(uint8_t * p_uid)72 void rw_i93_get_product_version(uint8_t* p_uid) {
73   tRW_I93_CB* p_i93 = &rw_cb.tcb.i93;
74 
75   if (!memcmp(p_i93->uid, p_uid, I93_UID_BYTE_LEN)) {
76     return;
77   }
78 
79   DLOG_IF(INFO, nfc_debug_enabled) << __func__;
80 
81   memcpy(p_i93->uid, p_uid, I93_UID_BYTE_LEN);
82 
83   if (p_uid[1] == I93_UID_IC_MFG_CODE_NXP) {
84     if (p_uid[2] == I93_UID_ICODE_SLI)
85       p_i93->product_version = RW_I93_ICODE_SLI;
86     else if (p_uid[2] == I93_UID_ICODE_SLI_S)
87       p_i93->product_version = RW_I93_ICODE_SLI_S;
88     else if (p_uid[2] == I93_UID_ICODE_SLI_L)
89       p_i93->product_version = RW_I93_ICODE_SLI_L;
90     else
91       p_i93->product_version = RW_I93_UNKNOWN_PRODUCT;
92   } else if (p_uid[1] == I93_UID_IC_MFG_CODE_TI) {
93     if ((p_uid[2] & I93_UID_TAG_IT_HF_I_PRODUCT_ID_MASK) ==
94         I93_UID_TAG_IT_HF_I_PLUS_INLAY)
95       p_i93->product_version = RW_I93_TAG_IT_HF_I_PLUS_INLAY;
96     else if ((p_uid[2] & I93_UID_TAG_IT_HF_I_PRODUCT_ID_MASK) ==
97              I93_UID_TAG_IT_HF_I_PLUS_CHIP)
98       p_i93->product_version = RW_I93_TAG_IT_HF_I_PLUS_CHIP;
99     else if ((p_uid[2] & I93_UID_TAG_IT_HF_I_PRODUCT_ID_MASK) ==
100              I93_UID_TAG_IT_HF_I_STD_CHIP_INLAY)
101       p_i93->product_version = RW_I93_TAG_IT_HF_I_STD_CHIP_INLAY;
102     else if ((p_uid[2] & I93_UID_TAG_IT_HF_I_PRODUCT_ID_MASK) ==
103              I93_UID_TAG_IT_HF_I_PRO_CHIP_INLAY)
104       p_i93->product_version = RW_I93_TAG_IT_HF_I_PRO_CHIP_INLAY;
105     else
106       p_i93->product_version = RW_I93_UNKNOWN_PRODUCT;
107   } else if ((p_uid[1] == I93_UID_IC_MFG_CODE_STM) &&
108              (p_i93->info_flags & I93_INFO_FLAG_IC_REF)) {
109     if (p_i93->ic_reference == I93_IC_REF_STM_M24LR04E_R)
110       p_i93->product_version = RW_I93_STM_M24LR04E_R;
111     else if (p_i93->ic_reference == I93_IC_REF_STM_M24LR16E_R)
112       p_i93->product_version = RW_I93_STM_M24LR16E_R;
113     else if (p_i93->ic_reference == I93_IC_REF_STM_M24LR16D_W)
114       p_i93->product_version = RW_I93_STM_M24LR16D_W;
115     else if (p_i93->ic_reference == I93_IC_REF_STM_M24LR64E_R)
116       p_i93->product_version = RW_I93_STM_M24LR64E_R;
117     else if (p_i93->ic_reference == I93_IC_REF_STM_ST25DVHIK)
118       p_i93->product_version = RW_I93_STM_ST25DVHIK;
119     else if (p_i93->ic_reference == I93_IC_REF_STM_ST25DV04K)
120       p_i93->product_version = RW_I93_STM_ST25DV04K;
121     else {
122       switch (p_i93->ic_reference & I93_IC_REF_STM_MASK) {
123         case I93_IC_REF_STM_LRI1K:
124           p_i93->product_version = RW_I93_STM_LRI1K;
125           break;
126         case I93_IC_REF_STM_LRI2K:
127           p_i93->product_version = RW_I93_STM_LRI2K;
128           break;
129         case I93_IC_REF_STM_LRIS2K:
130           p_i93->product_version = RW_I93_STM_LRIS2K;
131           break;
132         case I93_IC_REF_STM_LRIS64K:
133           p_i93->product_version = RW_I93_STM_LRIS64K;
134           break;
135         case I93_IC_REF_STM_M24LR64_R:
136           p_i93->product_version = RW_I93_STM_M24LR64_R;
137           break;
138         default:
139           p_i93->product_version = RW_I93_UNKNOWN_PRODUCT;
140           break;
141       }
142     }
143   } else if ((p_uid[1] == I93_UID_IC_MFG_CODE_ONS) &&
144              (p_i93->info_flags & I93_INFO_FLAG_IC_REF)) {
145       switch (p_i93->ic_reference) {
146         case I93_IC_REF_ONS_N36RW02:
147           p_i93->product_version = RW_I93_ONS_N36RW02;
148           break;
149         case I93_IC_REF_ONS_N24RF04:
150           p_i93->product_version = RW_I93_ONS_N24RF04;
151           break;
152         case I93_IC_REF_ONS_N24RF04E:
153           p_i93->product_version = RW_I93_ONS_N24RF04E;
154           break;
155         case I93_IC_REF_ONS_N24RF16:
156           p_i93->product_version = RW_I93_ONS_N24RF16;
157           break;
158         case I93_IC_REF_ONS_N24RF16E:
159           p_i93->product_version = RW_I93_ONS_N24RF16E;
160           break;
161         case I93_IC_REF_ONS_N24RF64:
162           p_i93->product_version = RW_I93_ONS_N24RF64;
163           break;
164         case I93_IC_REF_ONS_N24RF64E:
165           p_i93->product_version = RW_I93_ONS_N24RF64E;
166           break;
167         default:
168           p_i93->product_version = RW_I93_UNKNOWN_PRODUCT;
169         break;
170       }
171   } else {
172     p_i93->product_version = RW_I93_UNKNOWN_PRODUCT;
173   }
174 
175   DLOG_IF(INFO, nfc_debug_enabled)
176       << StringPrintf("product_version = <%s>",
177                       rw_i93_get_tag_name(p_i93->product_version).c_str());
178 
179   switch (p_i93->product_version) {
180     case RW_I93_TAG_IT_HF_I_STD_CHIP_INLAY:
181     case RW_I93_TAG_IT_HF_I_PRO_CHIP_INLAY:
182       /* these don't support Get System Information Command */
183       /* these support only Inventory, Stay Quiet, Read Single Block, Write
184        * Single Block, Lock Block */
185       p_i93->block_size = I93_TAG_IT_HF_I_STD_PRO_CHIP_INLAY_BLK_SIZE;
186       p_i93->num_block = I93_TAG_IT_HF_I_STD_PRO_CHIP_INLAY_NUM_USER_BLK;
187       break;
188     default:
189       break;
190   }
191 }
192 
193 /*******************************************************************************
194 **
195 ** Function         rw_i93_process_ext_sys_info
196 **
197 ** Description      Store extended system information of tag
198 **
199 ** Returns          FALSE if retrying with protocol extension flag
200 **
201 *******************************************************************************/
rw_i93_process_ext_sys_info(uint8_t * p_data,uint16_t length)202 bool rw_i93_process_ext_sys_info(uint8_t* p_data, uint16_t length) {
203   uint8_t* p = p_data;
204   tRW_I93_CB* p_i93 = &rw_cb.tcb.i93;
205   uint8_t uid[I93_UID_BYTE_LEN], *p_uid;
206 
207   DLOG_IF(INFO, nfc_debug_enabled) << __func__;
208 
209   if (length < (I93_UID_BYTE_LEN + 1)) {
210     android_errorWriteLog(0x534e4554, "122316913");
211     return false;
212   }
213 
214   STREAM_TO_UINT8(p_i93->info_flags, p);
215   length--;
216 
217   p_uid = uid;
218   STREAM_TO_ARRAY8(p_uid, p);
219   length -= I93_UID_BYTE_LEN;
220 
221   if (p_i93->info_flags & I93_INFO_FLAG_DSFID) {
222     if (length < I93_INFO_DSFID_LEN) {
223       android_errorWriteLog(0x534e4554, "122316913");
224       return false;
225     }
226     STREAM_TO_UINT8(p_i93->dsfid, p);
227     length--;
228   }
229   if (p_i93->info_flags & I93_INFO_FLAG_AFI) {
230     if (length < I93_INFO_AFI_LEN) {
231       android_errorWriteLog(0x534e4554, "122316913");
232       return false;
233     }
234     STREAM_TO_UINT8(p_i93->afi, p);
235     length--;
236   }
237   if (p_i93->info_flags & I93_INFO_FLAG_MEM_SIZE) {
238     if (length < I93_INFO_16BIT_NUM_BLOCK_LEN + I93_INFO_BLOCK_SIZE_LEN) {
239       android_errorWriteLog(0x534e4554, "122316913");
240       return false;
241     }
242     STREAM_TO_UINT16(p_i93->num_block, p);
243     length -= I93_INFO_16BIT_NUM_BLOCK_LEN;
244 
245     /* it is one less than actual number of bytes */
246     p_i93->num_block += 1;
247 
248     STREAM_TO_UINT8(p_i93->block_size, p);
249     length--;
250     /* it is one less than actual number of blocks */
251     p_i93->block_size = (p_i93->block_size & 0x1F) + 1;
252   }
253   if (p_i93->info_flags & I93_INFO_FLAG_IC_REF) {
254     if (length < I93_INFO_IC_REF_LEN) {
255       android_errorWriteLog(0x534e4554, "122316913");
256       return false;
257     }
258     STREAM_TO_UINT8(p_i93->ic_reference, p);
259     length--;
260 
261     /* clear existing UID to set product version */
262     p_i93->uid[0] = 0x00;
263 
264     /* store UID and get product version */
265     rw_i93_get_product_version(p_uid);
266 
267     if (p_i93->uid[0] == I93_UID_FIRST_BYTE) {
268       if ((p_i93->uid[1] == I93_UID_IC_MFG_CODE_STM) || (p_i93->uid[1] == I93_UID_IC_MFG_CODE_ONS)){
269         /* STM & ONS supports more than 2040 bytes */
270         p_i93->intl_flags |= RW_I93_FLAG_EXT_COMMANDS;
271       }
272     }
273   }
274   return true;
275 }
276 
277 /*******************************************************************************
278 **
279 ** Function         rw_i93_process_sys_info
280 **
281 ** Description      Store system information of tag
282 **
283 ** Returns          FALSE if retrying with protocol extension flag
284 **
285 *******************************************************************************/
rw_i93_process_sys_info(uint8_t * p_data,uint16_t length)286 bool rw_i93_process_sys_info(uint8_t* p_data, uint16_t length) {
287   uint8_t* p = p_data;
288   tRW_I93_CB* p_i93 = &rw_cb.tcb.i93;
289   uint8_t uid[I93_UID_BYTE_LEN], *p_uid;
290 
291   DLOG_IF(INFO, nfc_debug_enabled) << __func__;
292 
293   if (length < (I93_UID_BYTE_LEN + 1)) {
294     android_errorWriteLog(0x534e4554, "121259048");
295     return false;
296   }
297   STREAM_TO_UINT8(p_i93->info_flags, p);
298   length--;
299 
300   p_uid = uid;
301   STREAM_TO_ARRAY8(p_uid, p);
302   length -= I93_UID_BYTE_LEN;
303 
304   if (p_i93->info_flags & I93_INFO_FLAG_DSFID) {
305     if (length == 0) {
306       android_errorWriteLog(0x534e4554, "121259048");
307       return false;
308     }
309     STREAM_TO_UINT8(p_i93->dsfid, p);
310     length--;
311   }
312   if (p_i93->info_flags & I93_INFO_FLAG_AFI) {
313     if (length == 0) {
314       android_errorWriteLog(0x534e4554, "121259048");
315       return false;
316     }
317     STREAM_TO_UINT8(p_i93->afi, p);
318     length--;
319   }
320   if (p_i93->info_flags & I93_INFO_FLAG_MEM_SIZE) {
321     bool block_16_bit = p_i93->intl_flags & RW_I93_FLAG_16BIT_NUM_BLOCK;
322     if (block_16_bit && length > 2) {
323       STREAM_TO_UINT16(p_i93->num_block, p);
324       length -= 2;
325     } else if (!block_16_bit && length > 1) {
326       STREAM_TO_UINT8(p_i93->num_block, p);
327       length--;
328     } else {
329       android_errorWriteLog(0x534e4554, "121259048");
330       return false;
331     }
332     /* it is one less than actual number of bytes */
333     p_i93->num_block += 1;
334 
335     STREAM_TO_UINT8(p_i93->block_size, p);
336     length--;
337     /* it is one less than actual number of blocks */
338     p_i93->block_size = (p_i93->block_size & 0x1F) + 1;
339   }
340   if (p_i93->info_flags & I93_INFO_FLAG_IC_REF) {
341     if (length == 0) {
342       android_errorWriteLog(0x534e4554, "121259048");
343       return false;
344     }
345     STREAM_TO_UINT8(p_i93->ic_reference, p);
346 
347     /* clear existing UID to set product version */
348     p_i93->uid[0] = 0x00;
349 
350     /* store UID and get product version */
351     rw_i93_get_product_version(p_uid);
352 
353     if (p_i93->uid[0] == I93_UID_FIRST_BYTE) {
354       if ((p_i93->uid[1] == I93_UID_IC_MFG_CODE_NXP) &&
355           (p_i93->ic_reference == I93_IC_REF_ICODE_SLI_L)) {
356         p_i93->num_block = 8;
357         p_i93->block_size = 4;
358       } else if (p_i93->uid[1] == I93_UID_IC_MFG_CODE_STM) {
359         /*
360         **  LRI1K:      010000xx(b), blockSize: 4, numberBlocks: 0x20
361         **  LRI2K:      001000xx(b), blockSize: 4, numberBlocks: 0x40
362         **  LRIS2K:     001010xx(b), blockSize: 4, numberBlocks: 0x40
363         **  LRIS64K:    010001xx(b), blockSize: 4, numberBlocks: 0x800
364         **  M24LR64-R:  001011xx(b), blockSize: 4, numberBlocks: 0x800
365         **  M24LR04E-R: 01011010(b), blockSize: 4, numberBlocks: 0x80
366         **  M24LR16E-R: 01001110(b), blockSize: 4, numberBlocks: 0x200
367         **  M24LR16D-W: 01001101(b), blockSize: 4, numberBlocks: 0x200
368         **  M24LR64E-R: 01011110(b), blockSize: 4, numberBlocks: 0x800
369         */
370         if ((p_i93->product_version == RW_I93_STM_M24LR16E_R) ||
371             (p_i93->product_version == RW_I93_STM_M24LR16D_W) ||
372             (p_i93->product_version == RW_I93_STM_M24LR64E_R)) {
373           /*
374           ** M24LR16E-R or M24LR16D-W or M24LR64E-R returns system information
375           ** without memory size, if option flag is not set.
376           ** LRIS64K and M24LR64-R return error if option flag is not
377           ** set.
378           */
379           if (!(p_i93->intl_flags & RW_I93_FLAG_16BIT_NUM_BLOCK)) {
380             /* get memory size with protocol extension flag */
381             if (rw_i93_send_cmd_get_sys_info(nullptr, I93_FLAG_PROT_EXT_YES) ==
382                 NFC_STATUS_OK) {
383               /* STM supports more than 2040 bytes */
384               p_i93->intl_flags |= RW_I93_FLAG_16BIT_NUM_BLOCK;
385 
386               return false;
387             }
388           }
389         } else if ((p_i93->product_version == RW_I93_STM_LRI2K) &&
390                    (p_i93->ic_reference == 0x21)) {
391           /* workaround of byte order in memory size information */
392           p_i93->num_block = 64;
393           p_i93->block_size = 4;
394         } else if (!(p_i93->info_flags & I93_INFO_FLAG_MEM_SIZE)) {
395           if (!(p_i93->intl_flags & RW_I93_FLAG_EXT_COMMANDS)) {
396             if (rw_i93_send_cmd_get_ext_sys_info(nullptr) == NFC_STATUS_OK) {
397               /* STM supports more than 2040 bytes */
398               p_i93->intl_flags |= RW_I93_FLAG_EXT_COMMANDS;
399 
400               return false;
401             }
402           }
403         }
404       } else if (p_i93->uid[1] == I93_UID_IC_MFG_CODE_ONS) {
405         /*
406         **  N36RW02:  00011010(b), blockSize: 4, numberBlocks: 0x40
407         **  N24RF04:  00101110(b), blockSize: 4, numberBlocks: 0x80
408         **  N24RF04E: 00101010(b), blockSize: 4, numberBlocks: 0x80
409         **  N24RF16:  01001010(b), blockSize: 4, numberBlocks: 0x200
410         **  N24RF16E: 01001110(b), blockSize: 4, numberBlocks: 0x200
411         **  N24RF64:  01101010(b), blockSize: 4, numberBlocks: 0x800
412         **  N24RF64E: 01101110(b), blockSize: 4, numberBlocks: 0x800
413         */
414           p_i93->block_size = 4;
415           switch (p_i93->product_version){
416             case RW_I93_ONS_N36RW02:
417                  p_i93->num_block = 0x40;
418                  break;
419             case RW_I93_ONS_N24RF04:
420             case RW_I93_ONS_N24RF04E:
421                  p_i93->num_block = 0x80;
422                  break;
423             case RW_I93_ONS_N24RF16:
424             case RW_I93_ONS_N24RF16E:
425                  p_i93->num_block = 0x200;
426                  p_i93->intl_flags |= RW_I93_FLAG_16BIT_NUM_BLOCK;
427                  break;
428             case RW_I93_ONS_N24RF64:
429             case RW_I93_ONS_N24RF64E:
430                  p_i93->num_block = 0x800;
431                  p_i93->intl_flags |= RW_I93_FLAG_16BIT_NUM_BLOCK;
432                  break;
433             default:
434                  return false;
435           }
436       }
437     }
438   }
439 
440   return true;
441 }
442 
443 /*******************************************************************************
444 **
445 ** Function         rw_i93_check_sys_info_prot_ext
446 **
447 ** Description      Check if need to set protocol extension flag to get system
448 **                  info
449 **
450 ** Returns          TRUE if sent Get System Info with protocol extension flag
451 **
452 *******************************************************************************/
rw_i93_check_sys_info_prot_ext(uint8_t error_code)453 bool rw_i93_check_sys_info_prot_ext(uint8_t error_code) {
454   tRW_I93_CB* p_i93 = &rw_cb.tcb.i93;
455 
456   DLOG_IF(INFO, nfc_debug_enabled) << __func__;
457 
458   if (((p_i93->uid[1] == I93_UID_IC_MFG_CODE_STM) || (p_i93->uid[1] == I93_UID_IC_MFG_CODE_ONS)) &&
459       (p_i93->sent_cmd == I93_CMD_GET_SYS_INFO) &&
460       (error_code == I93_ERROR_CODE_OPTION_NOT_SUPPORTED) &&
461       (rw_i93_send_cmd_get_sys_info(nullptr, I93_FLAG_PROT_EXT_YES) ==
462        NFC_STATUS_OK)) {
463     return true;
464   } else {
465     return false;
466   }
467 }
468 
469 /*******************************************************************************
470 **
471 ** Function         rw_i93_send_to_upper
472 **
473 ** Description      Send response to upper layer
474 **
475 ** Returns          void
476 **
477 *******************************************************************************/
rw_i93_send_to_upper(NFC_HDR * p_resp)478 void rw_i93_send_to_upper(NFC_HDR* p_resp) {
479   uint8_t *p = (uint8_t*)(p_resp + 1) + p_resp->offset, *p_uid;
480   uint16_t length = p_resp->len;
481   tRW_I93_CB* p_i93 = &rw_cb.tcb.i93;
482   tRW_DATA rw_data;
483   uint8_t event = RW_I93_MAX_EVT;
484   uint8_t flags;
485   NFC_HDR* p_buff;
486 
487   DLOG_IF(INFO, nfc_debug_enabled) << __func__;
488 
489   if (length == 0) {
490     android_errorWriteLog(0x534e4554, "121035878");
491     rw_data.i93_cmd_cmpl.status = NFC_STATUS_FAILED;
492     rw_data.i93_cmd_cmpl.command = p_i93->sent_cmd;
493     rw_cb.tcb.i93.sent_cmd = 0;
494     (*(rw_cb.p_cback))(RW_I93_CMD_CMPL_EVT, &rw_data);
495     return;
496   }
497 
498   STREAM_TO_UINT8(flags, p);
499   length--;
500 
501   if (flags & I93_FLAG_ERROR_DETECTED) {
502     if ((length) && (rw_i93_check_sys_info_prot_ext(*p))) {
503       /* getting system info with protocol extension flag */
504       /* This STM & ONS tag supports more than 2040 bytes */
505       p_i93->intl_flags |= RW_I93_FLAG_16BIT_NUM_BLOCK;
506       p_i93->state = RW_I93_STATE_BUSY;
507     } else if (length) {
508       /* notify error to upper layer */
509       rw_data.i93_cmd_cmpl.status = NFC_STATUS_FAILED;
510       rw_data.i93_cmd_cmpl.command = p_i93->sent_cmd;
511       STREAM_TO_UINT8(rw_data.i93_cmd_cmpl.error_code, p);
512 
513       rw_cb.tcb.i93.sent_cmd = 0;
514       (*(rw_cb.p_cback))(RW_I93_CMD_CMPL_EVT, &rw_data);
515     }
516     return;
517   }
518 
519   switch (p_i93->sent_cmd) {
520     case I93_CMD_INVENTORY:
521       if (length < I93_INFO_DSFID_LEN + I93_UID_BYTE_LEN) return;
522 
523       /* forward inventory response */
524       rw_data.i93_inventory.status = NFC_STATUS_OK;
525       STREAM_TO_UINT8(rw_data.i93_inventory.dsfid, p);
526 
527       p_uid = rw_data.i93_inventory.uid;
528       STREAM_TO_ARRAY8(p_uid, p);
529 
530       /* store UID and get product version */
531       rw_i93_get_product_version(p_uid);
532 
533       event = RW_I93_INVENTORY_EVT;
534       break;
535 
536     case I93_CMD_READ_SINGLE_BLOCK:
537     case I93_CMD_EXT_READ_SINGLE_BLOCK:
538     case I93_CMD_READ_MULTI_BLOCK:
539     case I93_CMD_EXT_READ_MULTI_BLOCK:
540     case I93_CMD_GET_MULTI_BLK_SEC:
541     case I93_CMD_EXT_GET_MULTI_BLK_SEC:
542 
543       if (UINT16_MAX - length < NFC_HDR_SIZE) {
544         rw_data.i93_cmd_cmpl.status = NFC_STATUS_FAILED;
545         rw_data.i93_cmd_cmpl.command = p_i93->sent_cmd;
546         rw_cb.tcb.i93.sent_cmd = 0;
547 
548         event = RW_I93_CMD_CMPL_EVT;
549         break;
550       }
551 
552       /* forward tag data or security status */
553       p_buff = (NFC_HDR*)GKI_getbuf((uint16_t)(length + NFC_HDR_SIZE));
554 
555       if (p_buff) {
556         p_buff->offset = 0;
557         p_buff->len = length;
558 
559         memcpy((p_buff + 1), p, length);
560 
561         rw_data.i93_data.status = NFC_STATUS_OK;
562         rw_data.i93_data.command = p_i93->sent_cmd;
563         rw_data.i93_data.p_data = p_buff;
564 
565         event = RW_I93_DATA_EVT;
566       } else {
567         rw_data.i93_cmd_cmpl.status = NFC_STATUS_NO_BUFFERS;
568         rw_data.i93_cmd_cmpl.command = p_i93->sent_cmd;
569         rw_data.i93_cmd_cmpl.error_code = 0;
570 
571         event = RW_I93_CMD_CMPL_EVT;
572       }
573       break;
574 
575     case I93_CMD_WRITE_SINGLE_BLOCK:
576     case I93_CMD_EXT_WRITE_SINGLE_BLOCK:
577     case I93_CMD_LOCK_BLOCK:
578     case I93_CMD_EXT_LOCK_BLOCK:
579     case I93_CMD_WRITE_MULTI_BLOCK:
580     case I93_CMD_EXT_WRITE_MULTI_BLOCK:
581     case I93_CMD_SELECT:
582     case I93_CMD_RESET_TO_READY:
583     case I93_CMD_WRITE_AFI:
584     case I93_CMD_LOCK_AFI:
585     case I93_CMD_WRITE_DSFID:
586     case I93_CMD_LOCK_DSFID:
587 
588       /* notify the complete of command */
589       rw_data.i93_cmd_cmpl.status = NFC_STATUS_OK;
590       rw_data.i93_cmd_cmpl.command = p_i93->sent_cmd;
591       rw_data.i93_cmd_cmpl.error_code = 0;
592 
593       event = RW_I93_CMD_CMPL_EVT;
594       break;
595 
596     case I93_CMD_GET_SYS_INFO:
597 
598       if (rw_i93_process_sys_info(p, length)) {
599         rw_data.i93_sys_info.status = NFC_STATUS_OK;
600         rw_data.i93_sys_info.info_flags = p_i93->info_flags;
601         rw_data.i93_sys_info.dsfid = p_i93->dsfid;
602         rw_data.i93_sys_info.afi = p_i93->afi;
603         rw_data.i93_sys_info.num_block = p_i93->num_block;
604         rw_data.i93_sys_info.block_size = p_i93->block_size;
605         rw_data.i93_sys_info.IC_reference = p_i93->ic_reference;
606 
607         memcpy(rw_data.i93_sys_info.uid, p_i93->uid, I93_UID_BYTE_LEN);
608 
609         p_i93->i93_t5t_mode = RW_I93_GET_SYS_INFO_MEM_INFO;
610         event = RW_I93_SYS_INFO_EVT;
611       } else {
612         /* retrying with protocol extension flag */
613         p_i93->state = RW_I93_STATE_BUSY;
614         return;
615       }
616       break;
617 
618     case I93_CMD_EXT_GET_SYS_INFO:
619 
620       if (rw_i93_process_ext_sys_info(p, length)) {
621         rw_data.i93_sys_info.status = NFC_STATUS_OK;
622         rw_data.i93_sys_info.info_flags = p_i93->info_flags;
623         rw_data.i93_sys_info.dsfid = p_i93->dsfid;
624         rw_data.i93_sys_info.afi = p_i93->afi;
625         rw_data.i93_sys_info.num_block = p_i93->num_block;
626         rw_data.i93_sys_info.block_size = p_i93->block_size;
627         rw_data.i93_sys_info.IC_reference = p_i93->ic_reference;
628 
629         memcpy(rw_data.i93_sys_info.uid, p_i93->uid, I93_UID_BYTE_LEN);
630 
631         p_i93->i93_t5t_mode = RW_I93_GET_SYS_INFO_MEM_INFO;
632         event = RW_I93_SYS_INFO_EVT;
633       } else {
634         /* retrying with protocol extension flag or with extended sys info
635          * command */
636         p_i93->state = RW_I93_STATE_BUSY;
637         return;
638       }
639       break;
640 
641     default:
642       break;
643   }
644 
645   rw_cb.tcb.i93.sent_cmd = 0;
646   if (event != RW_I93_MAX_EVT) {
647     (*(rw_cb.p_cback))(event, &rw_data);
648   } else {
649     LOG(ERROR) << StringPrintf("Invalid response");
650   }
651 }
652 
653 /*******************************************************************************
654 **
655 ** Function         rw_i93_send_to_lower
656 **
657 ** Description      Send Request frame to lower layer
658 **
659 ** Returns          TRUE if success
660 **
661 *******************************************************************************/
rw_i93_send_to_lower(NFC_HDR * p_msg)662 bool rw_i93_send_to_lower(NFC_HDR* p_msg) {
663   /* store command for retransmitting */
664   if (rw_cb.tcb.i93.p_retry_cmd) {
665     GKI_freebuf(rw_cb.tcb.i93.p_retry_cmd);
666     rw_cb.tcb.i93.p_retry_cmd = nullptr;
667   }
668 
669   uint16_t msg_size = sizeof(NFC_HDR) + p_msg->offset + p_msg->len;
670 
671   rw_cb.tcb.i93.p_retry_cmd = (NFC_HDR*)GKI_getpoolbuf(NFC_RW_POOL_ID);
672 
673   if (rw_cb.tcb.i93.p_retry_cmd &&
674       GKI_get_pool_bufsize(NFC_RW_POOL_ID) >= msg_size) {
675     memcpy(rw_cb.tcb.i93.p_retry_cmd, p_msg, msg_size);
676   } else {
677     LOG(ERROR) << StringPrintf("Memory allocation error");
678     android_errorWriteLog(0x534e4554, "157650357");
679     return false;
680   }
681 
682   if (NFC_SendData(NFC_RF_CONN_ID, p_msg) != NFC_STATUS_OK) {
683     LOG(ERROR) << StringPrintf("failed");
684     return false;
685   }
686 
687   nfc_start_quick_timer(&rw_cb.tcb.i93.timer, NFC_TTYPE_RW_I93_RESPONSE,
688                         (RW_I93_TOUT_RESP * QUICK_TIMER_TICKS_PER_SEC) / 1000);
689 
690   return true;
691 }
692 
693 /*******************************************************************************
694 **
695 ** Function         rw_i93_send_cmd_inventory
696 **
697 ** Description      Send Inventory Request to VICC
698 **
699 ** Returns          tNFC_STATUS
700 **
701 *******************************************************************************/
rw_i93_send_cmd_inventory(uint8_t * p_uid,bool including_afi,uint8_t afi)702 tNFC_STATUS rw_i93_send_cmd_inventory(uint8_t* p_uid, bool including_afi,
703                                       uint8_t afi) {
704   NFC_HDR* p_cmd;
705   uint8_t *p, flags;
706 
707   DLOG_IF(INFO, nfc_debug_enabled)
708       << StringPrintf("including_afi:%d, AFI:0x%02X", including_afi, afi);
709 
710   p_cmd = (NFC_HDR*)GKI_getpoolbuf(NFC_RW_POOL_ID);
711 
712   if (!p_cmd) {
713     LOG(ERROR) << StringPrintf("Cannot allocate buffer");
714     return NFC_STATUS_NO_BUFFERS;
715   }
716 
717   p_cmd->offset = NCI_MSG_OFFSET_SIZE + NCI_DATA_HDR_SIZE;
718   p_cmd->len = 3;
719   p = (uint8_t*)(p_cmd + 1) + p_cmd->offset;
720 
721   /* Flags */
722   flags = (I93_FLAG_SLOT_ONE | I93_FLAG_INVENTORY_SET |
723            RW_I93_FLAG_SUB_CARRIER | RW_I93_FLAG_DATA_RATE);
724   if (including_afi) {
725     flags |= I93_FLAG_AFI_PRESENT;
726   }
727 
728   UINT8_TO_STREAM(p, flags);
729 
730   /* Command Code */
731   UINT8_TO_STREAM(p, I93_CMD_INVENTORY);
732 
733   if (including_afi) {
734     /* Parameters */
735     UINT8_TO_STREAM(p, afi); /* Optional AFI */
736     p_cmd->len++;
737   }
738 
739   if (p_uid) {
740     UINT8_TO_STREAM(p, I93_UID_BYTE_LEN * 8); /* Mask Length */
741     ARRAY8_TO_STREAM(p, p_uid);               /* UID */
742     p_cmd->len += I93_UID_BYTE_LEN;
743   } else {
744     UINT8_TO_STREAM(p, 0x00); /* Mask Length */
745   }
746 
747   if (rw_i93_send_to_lower(p_cmd)) {
748     rw_cb.tcb.i93.sent_cmd = I93_CMD_INVENTORY;
749     return NFC_STATUS_OK;
750   } else {
751     return NFC_STATUS_FAILED;
752   }
753 }
754 
755 /*******************************************************************************
756 **
757 ** Function         rw_i93_send_cmd_stay_quiet
758 **
759 ** Description      Send Stay Quiet Request to VICC
760 **
761 ** Returns          tNFC_STATUS
762 **
763 *******************************************************************************/
rw_i93_send_cmd_stay_quiet(uint8_t * p_uid)764 tNFC_STATUS rw_i93_send_cmd_stay_quiet(uint8_t* p_uid) {
765   NFC_HDR* p_cmd;
766   uint8_t* p;
767 
768   DLOG_IF(INFO, nfc_debug_enabled) << __func__;
769 
770   p_cmd = (NFC_HDR*)GKI_getpoolbuf(NFC_RW_POOL_ID);
771 
772   if (!p_cmd) {
773     LOG(ERROR) << StringPrintf("Cannot allocate buffer");
774     return NFC_STATUS_NO_BUFFERS;
775   }
776 
777   p_cmd->offset = NCI_MSG_OFFSET_SIZE + NCI_DATA_HDR_SIZE;
778   p_cmd->len = 10;
779   p = (uint8_t*)(p_cmd + 1) + p_cmd->offset;
780 
781   /* Flags */
782   UINT8_TO_STREAM(p, (I93_FLAG_ADDRESS_SET | RW_I93_FLAG_SUB_CARRIER |
783                       RW_I93_FLAG_DATA_RATE));
784 
785   /* Command Code */
786   UINT8_TO_STREAM(p, I93_CMD_STAY_QUIET);
787 
788   /* Parameters */
789   /* Beware the UID is provided with the same order as the transmission
790      one (LSB first) */
791   ARRAY_TO_STREAM(p, p_uid, I93_UID_BYTE_LEN); /* UID */
792 
793   if (rw_i93_send_to_lower(p_cmd)) {
794     rw_cb.tcb.i93.sent_cmd = I93_CMD_STAY_QUIET;
795 
796     /* restart timer for stay quiet */
797     nfc_start_quick_timer(
798         &rw_cb.tcb.i93.timer, NFC_TTYPE_RW_I93_RESPONSE,
799         (RW_I93_TOUT_STAY_QUIET * QUICK_TIMER_TICKS_PER_SEC) / 1000);
800     return NFC_STATUS_OK;
801   } else {
802     return NFC_STATUS_FAILED;
803   }
804 }
805 
806 /*******************************************************************************
807 **
808 ** Function         rw_i93_send_cmd_read_single_block
809 **
810 ** Description      Send Read Single Block Request to VICC
811 **
812 ** Returns          tNFC_STATUS
813 **
814 *******************************************************************************/
rw_i93_send_cmd_read_single_block(uint16_t block_number,bool read_security)815 tNFC_STATUS rw_i93_send_cmd_read_single_block(uint16_t block_number,
816                                               bool read_security) {
817   NFC_HDR* p_cmd;
818   uint8_t *p, flags;
819   tRW_I93_CB* p_i93 = &rw_cb.tcb.i93;
820 
821   DLOG_IF(INFO, nfc_debug_enabled) << __func__;
822 
823   p_cmd = (NFC_HDR*)GKI_getpoolbuf(NFC_RW_POOL_ID);
824 
825   if (!p_cmd) {
826     LOG(ERROR) << StringPrintf("Cannot allocate buffer");
827     return NFC_STATUS_NO_BUFFERS;
828   }
829 
830   p_cmd->offset = NCI_MSG_OFFSET_SIZE + NCI_DATA_HDR_SIZE;
831   if (p_i93->addr_mode == RW_I93_MODE_ADDRESSED)
832     p_cmd->len = 11;
833   else
834     p_cmd->len = 3;
835   p = (uint8_t*)(p_cmd + 1) + p_cmd->offset;
836 
837   /* Flags */
838   if (p_i93->addr_mode == RW_I93_MODE_ADDRESSED) {
839     flags = (I93_FLAG_ADDRESS_SET | RW_I93_FLAG_SUB_CARRIER |
840              RW_I93_FLAG_DATA_RATE);
841   } else {
842     flags = (RW_I93_FLAG_SUB_CARRIER | RW_I93_FLAG_DATA_RATE);
843 
844     if (rw_cb.tcb.i93.intl_flags & RW_I93_FLAG_SELECTED_STATE)
845       flags |= I93_FLAG_SELECT_SET;
846   }
847   if (read_security) flags |= I93_FLAG_OPTION_SET;
848 
849   if (rw_cb.tcb.i93.intl_flags & RW_I93_FLAG_16BIT_NUM_BLOCK)
850     flags |= I93_FLAG_PROT_EXT_YES;
851 
852   UINT8_TO_STREAM(p, flags);
853 
854   /* Command Code */
855   if (rw_cb.tcb.i93.intl_flags & RW_I93_FLAG_EXT_COMMANDS) {
856     UINT8_TO_STREAM(p, I93_CMD_EXT_READ_SINGLE_BLOCK);
857   } else {
858     UINT8_TO_STREAM(p, I93_CMD_READ_SINGLE_BLOCK);
859   }
860 
861   /* Parameters */
862   if (flags & I93_FLAG_ADDRESS_SET)
863     ARRAY8_TO_STREAM(p, rw_cb.tcb.i93.uid); /* UID */
864 
865   if (rw_cb.tcb.i93.intl_flags & RW_I93_FLAG_16BIT_NUM_BLOCK ||
866       rw_cb.tcb.i93.intl_flags & RW_I93_FLAG_EXT_COMMANDS) {
867     UINT16_TO_STREAM(p, block_number); /* Block number */
868     p_cmd->len++;
869   } else {
870     UINT8_TO_STREAM(p, block_number); /* Block number */
871   }
872 
873   if (rw_i93_send_to_lower(p_cmd)) {
874     if (rw_cb.tcb.i93.intl_flags & RW_I93_FLAG_EXT_COMMANDS)
875       rw_cb.tcb.i93.sent_cmd = I93_CMD_EXT_READ_SINGLE_BLOCK;
876     else
877       rw_cb.tcb.i93.sent_cmd = I93_CMD_READ_SINGLE_BLOCK;
878     return NFC_STATUS_OK;
879   } else {
880     return NFC_STATUS_FAILED;
881   }
882 }
883 
884 /*******************************************************************************
885 **
886 ** Function         rw_i93_send_cmd_write_single_block
887 **
888 ** Description      Send Write Single Block Request to VICC
889 **
890 ** Returns          tNFC_STATUS
891 **
892 *******************************************************************************/
rw_i93_send_cmd_write_single_block(uint16_t block_number,uint8_t * p_data)893 tNFC_STATUS rw_i93_send_cmd_write_single_block(uint16_t block_number,
894                                                uint8_t* p_data) {
895   NFC_HDR* p_cmd;
896   uint8_t *p, flags;
897   tRW_I93_CB* p_i93 = &rw_cb.tcb.i93;
898 
899   DLOG_IF(INFO, nfc_debug_enabled) << __func__;
900 
901   p_cmd = (NFC_HDR*)GKI_getpoolbuf(NFC_RW_POOL_ID);
902 
903   if (!p_cmd) {
904     LOG(ERROR) << StringPrintf("Cannot allocate buffer");
905     return NFC_STATUS_NO_BUFFERS;
906   }
907 
908   p_cmd->offset = NCI_MSG_OFFSET_SIZE + NCI_DATA_HDR_SIZE;
909   if (p_i93->addr_mode == RW_I93_MODE_ADDRESSED)
910     p_cmd->len = 11 + rw_cb.tcb.i93.block_size;
911   else
912     p_cmd->len = 3 + rw_cb.tcb.i93.block_size;
913   p = (uint8_t*)(p_cmd + 1) + p_cmd->offset;
914 
915   /* Flags */
916   if ((rw_cb.tcb.i93.product_version == RW_I93_TAG_IT_HF_I_PLUS_INLAY) ||
917       (rw_cb.tcb.i93.product_version == RW_I93_TAG_IT_HF_I_PLUS_CHIP) ||
918       (rw_cb.tcb.i93.product_version == RW_I93_TAG_IT_HF_I_STD_CHIP_INLAY) ||
919       (rw_cb.tcb.i93.product_version == RW_I93_TAG_IT_HF_I_PRO_CHIP_INLAY)) {
920     /* Option must be set for TI tag */
921     flags = (I93_FLAG_ADDRESS_SET | I93_FLAG_OPTION_SET |
922              RW_I93_FLAG_SUB_CARRIER | RW_I93_FLAG_DATA_RATE);
923   } else {
924     if (p_i93->addr_mode == RW_I93_MODE_ADDRESSED) {
925       flags = (I93_FLAG_ADDRESS_SET | RW_I93_FLAG_SUB_CARRIER |
926                RW_I93_FLAG_DATA_RATE);
927     } else {
928       flags = (RW_I93_FLAG_SUB_CARRIER | RW_I93_FLAG_DATA_RATE);
929       if (rw_cb.tcb.i93.intl_flags & RW_I93_FLAG_SELECTED_STATE)
930         flags |= I93_FLAG_SELECT_SET;
931     }
932 
933     if (rw_cb.tcb.i93.intl_flags & RW_I93_FLAG_SPECIAL_FRAME) {
934       /* Option Flag bit must be set */
935       flags |= I93_FLAG_OPTION_SET;
936     }
937   }
938 
939   if (rw_cb.tcb.i93.intl_flags & RW_I93_FLAG_16BIT_NUM_BLOCK)
940     flags |= I93_FLAG_PROT_EXT_YES;
941 
942   UINT8_TO_STREAM(p, flags);
943 
944   /* Command Code */
945   if (rw_cb.tcb.i93.intl_flags & RW_I93_FLAG_EXT_COMMANDS) {
946     UINT8_TO_STREAM(p, I93_CMD_EXT_WRITE_SINGLE_BLOCK);
947   } else {
948     UINT8_TO_STREAM(p, I93_CMD_WRITE_SINGLE_BLOCK);
949   }
950 
951   /* Parameters */
952   if (flags & I93_FLAG_ADDRESS_SET)
953     ARRAY8_TO_STREAM(p, rw_cb.tcb.i93.uid); /* UID */
954 
955   if (rw_cb.tcb.i93.intl_flags & RW_I93_FLAG_16BIT_NUM_BLOCK ||
956       rw_cb.tcb.i93.intl_flags & RW_I93_FLAG_EXT_COMMANDS) {
957     UINT16_TO_STREAM(p, block_number); /* Block number */
958     p_cmd->len++;
959   } else {
960     UINT8_TO_STREAM(p, block_number); /* Block number */
961   }
962 
963   /* Data */
964   ARRAY_TO_STREAM(p, p_data, rw_cb.tcb.i93.block_size);
965 
966   if (rw_i93_send_to_lower(p_cmd)) {
967     if (rw_cb.tcb.i93.intl_flags & RW_I93_FLAG_EXT_COMMANDS)
968       rw_cb.tcb.i93.sent_cmd = I93_CMD_EXT_WRITE_SINGLE_BLOCK;
969     else
970       rw_cb.tcb.i93.sent_cmd = I93_CMD_WRITE_SINGLE_BLOCK;
971     return NFC_STATUS_OK;
972   } else {
973     return NFC_STATUS_FAILED;
974   }
975 }
976 
977 /*******************************************************************************
978 **
979 ** Function         rw_i93_send_cmd_lock_block
980 **
981 ** Description      Send Lock Block Request to VICC
982 **
983 **                  STM LRIS64K, M24LR64-R, M24LR04E-R, M24LR16E-R, M24LR64E-R,
984 **                  M24LR16D-W do not support.
985 **
986 ** Returns          tNFC_STATUS
987 **
988 *******************************************************************************/
rw_i93_send_cmd_lock_block(uint16_t block_number)989 tNFC_STATUS rw_i93_send_cmd_lock_block(uint16_t block_number) {
990   NFC_HDR* p_cmd;
991   uint8_t* p;
992   tRW_I93_CB* p_i93 = &rw_cb.tcb.i93;
993   uint8_t flags;
994 
995   DLOG_IF(INFO, nfc_debug_enabled) << __func__;
996 
997   p_cmd = (NFC_HDR*)GKI_getpoolbuf(NFC_RW_POOL_ID);
998 
999   if (!p_cmd) {
1000     LOG(ERROR) << StringPrintf("Cannot allocate buffer");
1001     return NFC_STATUS_NO_BUFFERS;
1002   }
1003 
1004   p_cmd->offset = NCI_MSG_OFFSET_SIZE + NCI_DATA_HDR_SIZE;
1005   if (p_i93->addr_mode == RW_I93_MODE_ADDRESSED)
1006     p_cmd->len = 11;
1007   else
1008     p_cmd->len = 3;
1009   p = (uint8_t*)(p_cmd + 1) + p_cmd->offset;
1010 
1011   /* Flags */
1012   if ((rw_cb.tcb.i93.product_version == RW_I93_TAG_IT_HF_I_PLUS_INLAY) ||
1013       (rw_cb.tcb.i93.product_version == RW_I93_TAG_IT_HF_I_PLUS_CHIP) ||
1014       (rw_cb.tcb.i93.product_version == RW_I93_TAG_IT_HF_I_STD_CHIP_INLAY) ||
1015       (rw_cb.tcb.i93.product_version == RW_I93_TAG_IT_HF_I_PRO_CHIP_INLAY)) {
1016     /* Option must be set for TI tag */
1017     UINT8_TO_STREAM(p, (I93_FLAG_ADDRESS_SET | I93_FLAG_OPTION_SET |
1018                         RW_I93_FLAG_SUB_CARRIER | RW_I93_FLAG_DATA_RATE));
1019   } else {
1020     if (p_i93->addr_mode == RW_I93_MODE_ADDRESSED) {
1021       /* Address Mode Selector must be set */
1022       flags = I93_FLAG_ADDRESS_SET | RW_I93_FLAG_SUB_CARRIER |
1023               RW_I93_FLAG_DATA_RATE;
1024     } else {
1025       flags = RW_I93_FLAG_SUB_CARRIER | RW_I93_FLAG_DATA_RATE;
1026 
1027       if (rw_cb.tcb.i93.intl_flags & RW_I93_FLAG_SELECTED_STATE)
1028         flags |= I93_FLAG_SELECT_SET;
1029     }
1030     if (rw_cb.tcb.i93.intl_flags & RW_I93_FLAG_SPECIAL_FRAME) {
1031       /* Option Flag bit must be set */
1032       flags |= I93_FLAG_OPTION_SET;
1033     }
1034     UINT8_TO_STREAM(p, flags);
1035   }
1036 
1037   /* Command Code */
1038   if (rw_cb.tcb.i93.intl_flags & RW_I93_FLAG_EXT_COMMANDS) {
1039     UINT8_TO_STREAM(p, I93_CMD_EXT_LOCK_BLOCK);
1040   } else {
1041     UINT8_TO_STREAM(p, I93_CMD_LOCK_BLOCK);
1042   }
1043 
1044   /* Parameters */
1045   if (p_i93->addr_mode == RW_I93_MODE_ADDRESSED)
1046     ARRAY8_TO_STREAM(p, rw_cb.tcb.i93.uid); /* UID */
1047 
1048   if (rw_cb.tcb.i93.intl_flags & RW_I93_FLAG_EXT_COMMANDS) {
1049     UINT16_TO_STREAM(p, block_number); /* Block number */
1050     p_cmd->len++;
1051   } else {
1052     UINT8_TO_STREAM(p, block_number); /* Block number */
1053   }
1054 
1055   if (rw_i93_send_to_lower(p_cmd)) {
1056     if (rw_cb.tcb.i93.intl_flags & RW_I93_FLAG_EXT_COMMANDS)
1057       rw_cb.tcb.i93.sent_cmd = I93_CMD_EXT_LOCK_BLOCK;
1058     else
1059       rw_cb.tcb.i93.sent_cmd = I93_CMD_LOCK_BLOCK;
1060     return NFC_STATUS_OK;
1061   } else {
1062     return NFC_STATUS_FAILED;
1063   }
1064 }
1065 
1066 /*******************************************************************************
1067 **
1068 ** Function         rw_i93_send_cmd_read_multi_blocks
1069 **
1070 ** Description      Send Read Multiple Blocks Request to VICC
1071 **
1072 ** Returns          tNFC_STATUS
1073 **
1074 *******************************************************************************/
rw_i93_send_cmd_read_multi_blocks(uint16_t first_block_number,uint16_t number_blocks)1075 tNFC_STATUS rw_i93_send_cmd_read_multi_blocks(uint16_t first_block_number,
1076                                               uint16_t number_blocks) {
1077   NFC_HDR* p_cmd;
1078   uint8_t *p, flags;
1079   tRW_I93_CB* p_i93 = &rw_cb.tcb.i93;
1080 
1081   DLOG_IF(INFO, nfc_debug_enabled) << __func__;
1082 
1083   p_cmd = (NFC_HDR*)GKI_getpoolbuf(NFC_RW_POOL_ID);
1084 
1085   if (!p_cmd) {
1086     LOG(ERROR) << StringPrintf("Cannot allocate buffer");
1087     return NFC_STATUS_NO_BUFFERS;
1088   }
1089 
1090   p_cmd->offset = NCI_MSG_OFFSET_SIZE + NCI_DATA_HDR_SIZE;
1091   if (p_i93->addr_mode == RW_I93_MODE_ADDRESSED)
1092     p_cmd->len = 12;
1093   else
1094     p_cmd->len = 4;
1095   p = (uint8_t*)(p_cmd + 1) + p_cmd->offset;
1096 
1097   /* Flags */
1098   if (p_i93->addr_mode == RW_I93_MODE_ADDRESSED) {
1099     flags = (I93_FLAG_ADDRESS_SET | RW_I93_FLAG_SUB_CARRIER |
1100              RW_I93_FLAG_DATA_RATE);
1101   } else {
1102     flags = (RW_I93_FLAG_SUB_CARRIER | RW_I93_FLAG_DATA_RATE);
1103 
1104     if (rw_cb.tcb.i93.intl_flags & RW_I93_FLAG_SELECTED_STATE)
1105       flags |= I93_FLAG_SELECT_SET;
1106   }
1107 
1108   if (rw_cb.tcb.i93.intl_flags & RW_I93_FLAG_16BIT_NUM_BLOCK) {
1109     flags |= I93_FLAG_PROT_EXT_YES;
1110   }
1111 
1112   UINT8_TO_STREAM(p, flags);
1113 
1114   /* Command Code */
1115   if (rw_cb.tcb.i93.intl_flags & RW_I93_FLAG_EXT_COMMANDS) {
1116     UINT8_TO_STREAM(p, I93_CMD_EXT_READ_MULTI_BLOCK);
1117   } else {
1118     UINT8_TO_STREAM(p, I93_CMD_READ_MULTI_BLOCK);
1119   }
1120 
1121   /* Parameters */
1122   if (flags & I93_FLAG_ADDRESS_SET)
1123     ARRAY8_TO_STREAM(p, rw_cb.tcb.i93.uid); /* UID */
1124 
1125   if (rw_cb.tcb.i93.intl_flags & RW_I93_FLAG_16BIT_NUM_BLOCK ||
1126       rw_cb.tcb.i93.intl_flags & RW_I93_FLAG_EXT_COMMANDS) {
1127     UINT16_TO_STREAM(p, first_block_number); /* First block number */
1128     p_cmd->len++;
1129   } else {
1130     UINT8_TO_STREAM(p, first_block_number); /* First block number */
1131   }
1132 
1133   if (rw_cb.tcb.i93.intl_flags & RW_I93_FLAG_EXT_COMMANDS) {
1134     UINT16_TO_STREAM(
1135         p, number_blocks - 1); /* Number of blocks, 0x00 to read one block */
1136     p_cmd->len++;
1137   } else {
1138     UINT8_TO_STREAM(
1139         p, number_blocks - 1); /* Number of blocks, 0x00 to read one block */
1140   }
1141 
1142   if (rw_i93_send_to_lower(p_cmd)) {
1143     if (rw_cb.tcb.i93.intl_flags & RW_I93_FLAG_EXT_COMMANDS)
1144       rw_cb.tcb.i93.sent_cmd = I93_CMD_EXT_READ_MULTI_BLOCK;
1145     else
1146       rw_cb.tcb.i93.sent_cmd = I93_CMD_READ_MULTI_BLOCK;
1147     return NFC_STATUS_OK;
1148   } else {
1149     return NFC_STATUS_FAILED;
1150   }
1151 }
1152 
1153 /*******************************************************************************
1154 **
1155 ** Function         rw_i93_send_cmd_write_multi_blocks
1156 **
1157 ** Description      Send Write Multiple Blocks Request to VICC
1158 **
1159 ** Returns          tNFC_STATUS
1160 **
1161 *******************************************************************************/
rw_i93_send_cmd_write_multi_blocks(uint16_t first_block_number,uint16_t number_blocks,uint8_t * p_data)1162 tNFC_STATUS rw_i93_send_cmd_write_multi_blocks(uint16_t first_block_number,
1163                                                uint16_t number_blocks,
1164                                                uint8_t* p_data) {
1165   NFC_HDR* p_cmd;
1166   uint8_t* p;
1167 
1168   DLOG_IF(INFO, nfc_debug_enabled) << __func__;
1169 
1170   if (number_blocks * rw_cb.tcb.i93.block_size >
1171       GKI_get_pool_bufsize(NFC_RW_POOL_ID) - NCI_MSG_OFFSET_SIZE -
1172           NCI_DATA_HDR_SIZE - 1 -
1173           (rw_cb.tcb.i93.intl_flags & RW_I93_FLAG_EXT_COMMANDS ? 2 : 0) - 12) {
1174     android_errorWriteLog(0x534e4554, "157650365");
1175     return NFC_STATUS_FAILED;
1176   }
1177   p_cmd = (NFC_HDR*)GKI_getpoolbuf(NFC_RW_POOL_ID);
1178 
1179   if (!p_cmd) {
1180     LOG(ERROR) << StringPrintf("Cannot allocate buffer");
1181     return NFC_STATUS_NO_BUFFERS;
1182   }
1183 
1184   p_cmd->offset = NCI_MSG_OFFSET_SIZE + NCI_DATA_HDR_SIZE;
1185   p_cmd->len = 12 + number_blocks * rw_cb.tcb.i93.block_size;
1186   p = (uint8_t*)(p_cmd + 1) + p_cmd->offset;
1187 
1188   /* Flags */
1189   UINT8_TO_STREAM(p, (I93_FLAG_ADDRESS_SET | RW_I93_FLAG_SUB_CARRIER |
1190                       RW_I93_FLAG_DATA_RATE));
1191 
1192   /* Command Code */
1193   if (rw_cb.tcb.i93.intl_flags & RW_I93_FLAG_EXT_COMMANDS) {
1194     INT8_TO_STREAM(p, I93_CMD_EXT_WRITE_MULTI_BLOCK);
1195   } else {
1196     UINT8_TO_STREAM(p, I93_CMD_WRITE_MULTI_BLOCK);
1197   }
1198 
1199   /* Parameters */
1200   ARRAY8_TO_STREAM(p, rw_cb.tcb.i93.uid); /* UID */
1201   if (rw_cb.tcb.i93.intl_flags & RW_I93_FLAG_EXT_COMMANDS) {
1202     UINT16_TO_STREAM(p, first_block_number); /* Block number */
1203     UINT16_TO_STREAM(
1204         p, number_blocks - 1); /* Number of blocks, 0x00 to read one block */
1205     p_cmd->len += 2;
1206   } else {
1207     UINT8_TO_STREAM(p, first_block_number); /* Block number */
1208     UINT8_TO_STREAM(
1209         p, number_blocks - 1); /* Number of blocks, 0x00 to read one block */
1210   }
1211 
1212   /* Data */
1213   ARRAY_TO_STREAM(p, p_data, number_blocks * rw_cb.tcb.i93.block_size);
1214 
1215   if (rw_i93_send_to_lower(p_cmd)) {
1216     if (rw_cb.tcb.i93.intl_flags & RW_I93_FLAG_EXT_COMMANDS)
1217       rw_cb.tcb.i93.sent_cmd = I93_CMD_EXT_WRITE_MULTI_BLOCK;
1218     else
1219       rw_cb.tcb.i93.sent_cmd = I93_CMD_WRITE_MULTI_BLOCK;
1220     return NFC_STATUS_OK;
1221   } else {
1222     return NFC_STATUS_FAILED;
1223   }
1224 }
1225 
1226 /*******************************************************************************
1227 **
1228 ** Function         rw_i93_send_cmd_select
1229 **
1230 ** Description      Send Select Request to VICC
1231 **
1232 ** Returns          tNFC_STATUS
1233 **
1234 *******************************************************************************/
rw_i93_send_cmd_select(uint8_t * p_uid)1235 tNFC_STATUS rw_i93_send_cmd_select(uint8_t* p_uid) {
1236   NFC_HDR* p_cmd;
1237   uint8_t* p;
1238 
1239   DLOG_IF(INFO, nfc_debug_enabled) << __func__;
1240 
1241   p_cmd = (NFC_HDR*)GKI_getpoolbuf(NFC_RW_POOL_ID);
1242 
1243   if (!p_cmd) {
1244     LOG(ERROR) << StringPrintf("Cannot allocate buffer");
1245     return NFC_STATUS_NO_BUFFERS;
1246   }
1247 
1248   p_cmd->offset = NCI_MSG_OFFSET_SIZE + NCI_DATA_HDR_SIZE;
1249   p_cmd->len = 10;
1250   p = (uint8_t*)(p_cmd + 1) + p_cmd->offset;
1251 
1252   /* Flags */
1253   UINT8_TO_STREAM(p, (I93_FLAG_ADDRESS_SET | RW_I93_FLAG_SUB_CARRIER |
1254                       RW_I93_FLAG_DATA_RATE));
1255 
1256   /* Command Code */
1257   UINT8_TO_STREAM(p, I93_CMD_SELECT);
1258 
1259   /* Parameters */
1260   /* Beware the UID is provided with the same order as the transmission
1261      one (LSB first) */
1262   ARRAY_TO_STREAM(p, p_uid, I93_UID_BYTE_LEN); /* UID */
1263 
1264   if (rw_i93_send_to_lower(p_cmd)) {
1265     rw_cb.tcb.i93.sent_cmd = I93_CMD_SELECT;
1266     return NFC_STATUS_OK;
1267   } else {
1268     return NFC_STATUS_FAILED;
1269   }
1270 }
1271 
1272 /*******************************************************************************
1273 **
1274 ** Function         rw_i93_send_cmd_reset_to_ready
1275 **
1276 ** Description      Send Reset to Ready Request to VICC
1277 **
1278 ** Returns          tNFC_STATUS
1279 **
1280 *******************************************************************************/
rw_i93_send_cmd_reset_to_ready(void)1281 tNFC_STATUS rw_i93_send_cmd_reset_to_ready(void) {
1282   NFC_HDR* p_cmd;
1283   uint8_t* p;
1284 
1285   DLOG_IF(INFO, nfc_debug_enabled) << __func__;
1286 
1287   p_cmd = (NFC_HDR*)GKI_getpoolbuf(NFC_RW_POOL_ID);
1288 
1289   if (!p_cmd) {
1290     LOG(ERROR) << StringPrintf("Cannot allocate buffer");
1291     return NFC_STATUS_NO_BUFFERS;
1292   }
1293 
1294   p_cmd->offset = NCI_MSG_OFFSET_SIZE + NCI_DATA_HDR_SIZE;
1295   p_cmd->len = 10;
1296   p = (uint8_t*)(p_cmd + 1) + p_cmd->offset;
1297 
1298   /* Flags */
1299   UINT8_TO_STREAM(p, (I93_FLAG_ADDRESS_SET | RW_I93_FLAG_SUB_CARRIER |
1300                       RW_I93_FLAG_DATA_RATE));
1301 
1302   /* Command Code */
1303   UINT8_TO_STREAM(p, I93_CMD_RESET_TO_READY);
1304 
1305   /* Parameters */
1306   ARRAY8_TO_STREAM(p, rw_cb.tcb.i93.uid); /* UID */
1307 
1308   if (rw_i93_send_to_lower(p_cmd)) {
1309     rw_cb.tcb.i93.sent_cmd = I93_CMD_RESET_TO_READY;
1310     return NFC_STATUS_OK;
1311   } else {
1312     return NFC_STATUS_FAILED;
1313   }
1314 }
1315 
1316 /*******************************************************************************
1317 **
1318 ** Function         rw_i93_send_cmd_write_afi
1319 **
1320 ** Description      Send Write AFI Request to VICC
1321 **
1322 ** Returns          tNFC_STATUS
1323 **
1324 *******************************************************************************/
rw_i93_send_cmd_write_afi(uint8_t afi)1325 tNFC_STATUS rw_i93_send_cmd_write_afi(uint8_t afi) {
1326   NFC_HDR* p_cmd;
1327   uint8_t* p;
1328 
1329   DLOG_IF(INFO, nfc_debug_enabled) << __func__;
1330 
1331   p_cmd = (NFC_HDR*)GKI_getpoolbuf(NFC_RW_POOL_ID);
1332 
1333   if (!p_cmd) {
1334     LOG(ERROR) << StringPrintf("Cannot allocate buffer");
1335     return NFC_STATUS_NO_BUFFERS;
1336   }
1337 
1338   p_cmd->offset = NCI_MSG_OFFSET_SIZE + NCI_DATA_HDR_SIZE;
1339   p_cmd->len = 11;
1340   p = (uint8_t*)(p_cmd + 1) + p_cmd->offset;
1341 
1342   /* Flags */
1343   UINT8_TO_STREAM(p, (I93_FLAG_ADDRESS_SET | RW_I93_FLAG_SUB_CARRIER |
1344                       RW_I93_FLAG_DATA_RATE));
1345 
1346   /* Command Code */
1347   UINT8_TO_STREAM(p, I93_CMD_WRITE_AFI);
1348 
1349   /* Parameters */
1350   ARRAY8_TO_STREAM(p, rw_cb.tcb.i93.uid); /* UID */
1351   UINT8_TO_STREAM(p, afi);                /* AFI */
1352 
1353   if (rw_i93_send_to_lower(p_cmd)) {
1354     rw_cb.tcb.i93.sent_cmd = I93_CMD_WRITE_AFI;
1355     return NFC_STATUS_OK;
1356   } else {
1357     return NFC_STATUS_FAILED;
1358   }
1359 }
1360 
1361 /*******************************************************************************
1362 **
1363 ** Function         rw_i93_send_cmd_lock_afi
1364 **
1365 ** Description      Send Lock AFI Request to VICC
1366 **
1367 ** Returns          tNFC_STATUS
1368 **
1369 *******************************************************************************/
rw_i93_send_cmd_lock_afi(void)1370 tNFC_STATUS rw_i93_send_cmd_lock_afi(void) {
1371   NFC_HDR* p_cmd;
1372   uint8_t* p;
1373 
1374   DLOG_IF(INFO, nfc_debug_enabled) << __func__;
1375 
1376   p_cmd = (NFC_HDR*)GKI_getpoolbuf(NFC_RW_POOL_ID);
1377 
1378   if (!p_cmd) {
1379     LOG(ERROR) << StringPrintf("Cannot allocate buffer");
1380     return NFC_STATUS_NO_BUFFERS;
1381   }
1382 
1383   p_cmd->offset = NCI_MSG_OFFSET_SIZE + NCI_DATA_HDR_SIZE;
1384   p_cmd->len = 10;
1385   p = (uint8_t*)(p_cmd + 1) + p_cmd->offset;
1386 
1387   /* Flags */
1388   UINT8_TO_STREAM(p, (I93_FLAG_ADDRESS_SET | RW_I93_FLAG_SUB_CARRIER |
1389                       RW_I93_FLAG_DATA_RATE));
1390 
1391   /* Command Code */
1392   UINT8_TO_STREAM(p, I93_CMD_LOCK_AFI);
1393 
1394   /* Parameters */
1395   ARRAY8_TO_STREAM(p, rw_cb.tcb.i93.uid); /* UID */
1396 
1397   if (rw_i93_send_to_lower(p_cmd)) {
1398     rw_cb.tcb.i93.sent_cmd = I93_CMD_LOCK_AFI;
1399     return NFC_STATUS_OK;
1400   } else {
1401     return NFC_STATUS_FAILED;
1402   }
1403 }
1404 
1405 /*******************************************************************************
1406 **
1407 ** Function         rw_i93_send_cmd_write_dsfid
1408 **
1409 ** Description      Send Write DSFID Request to VICC
1410 **
1411 ** Returns          tNFC_STATUS
1412 **
1413 *******************************************************************************/
rw_i93_send_cmd_write_dsfid(uint8_t dsfid)1414 tNFC_STATUS rw_i93_send_cmd_write_dsfid(uint8_t dsfid) {
1415   NFC_HDR* p_cmd;
1416   uint8_t* p;
1417 
1418   DLOG_IF(INFO, nfc_debug_enabled) << __func__;
1419 
1420   p_cmd = (NFC_HDR*)GKI_getpoolbuf(NFC_RW_POOL_ID);
1421 
1422   if (!p_cmd) {
1423     LOG(ERROR) << StringPrintf("Cannot allocate buffer");
1424     return NFC_STATUS_NO_BUFFERS;
1425   }
1426 
1427   p_cmd->offset = NCI_MSG_OFFSET_SIZE + NCI_DATA_HDR_SIZE;
1428   p_cmd->len = 11;
1429   p = (uint8_t*)(p_cmd + 1) + p_cmd->offset;
1430 
1431   /* Flags */
1432   UINT8_TO_STREAM(p, (I93_FLAG_ADDRESS_SET | RW_I93_FLAG_SUB_CARRIER |
1433                       RW_I93_FLAG_DATA_RATE));
1434 
1435   /* Command Code */
1436   UINT8_TO_STREAM(p, I93_CMD_WRITE_DSFID);
1437 
1438   /* Parameters */
1439   ARRAY8_TO_STREAM(p, rw_cb.tcb.i93.uid); /* UID */
1440   UINT8_TO_STREAM(p, dsfid);              /* DSFID */
1441 
1442   if (rw_i93_send_to_lower(p_cmd)) {
1443     rw_cb.tcb.i93.sent_cmd = I93_CMD_WRITE_DSFID;
1444     return NFC_STATUS_OK;
1445   } else {
1446     return NFC_STATUS_FAILED;
1447   }
1448 }
1449 
1450 /*******************************************************************************
1451 **
1452 ** Function         rw_i93_send_cmd_lock_dsfid
1453 **
1454 ** Description      Send Lock DSFID Request to VICC
1455 **
1456 ** Returns          tNFC_STATUS
1457 **
1458 *******************************************************************************/
rw_i93_send_cmd_lock_dsfid(void)1459 tNFC_STATUS rw_i93_send_cmd_lock_dsfid(void) {
1460   NFC_HDR* p_cmd;
1461   uint8_t* p;
1462 
1463   DLOG_IF(INFO, nfc_debug_enabled) << __func__;
1464 
1465   p_cmd = (NFC_HDR*)GKI_getpoolbuf(NFC_RW_POOL_ID);
1466 
1467   if (!p_cmd) {
1468     LOG(ERROR) << StringPrintf("Cannot allocate buffer");
1469     return NFC_STATUS_NO_BUFFERS;
1470   }
1471 
1472   p_cmd->offset = NCI_MSG_OFFSET_SIZE + NCI_DATA_HDR_SIZE;
1473   p_cmd->len = 10;
1474   p = (uint8_t*)(p_cmd + 1) + p_cmd->offset;
1475 
1476   /* Flags */
1477   UINT8_TO_STREAM(p, (I93_FLAG_ADDRESS_SET | RW_I93_FLAG_SUB_CARRIER |
1478                       RW_I93_FLAG_DATA_RATE));
1479 
1480   /* Command Code */
1481   UINT8_TO_STREAM(p, I93_CMD_LOCK_DSFID);
1482 
1483   /* Parameters */
1484   ARRAY8_TO_STREAM(p, rw_cb.tcb.i93.uid); /* UID */
1485 
1486   if (rw_i93_send_to_lower(p_cmd)) {
1487     rw_cb.tcb.i93.sent_cmd = I93_CMD_LOCK_DSFID;
1488     return NFC_STATUS_OK;
1489   } else {
1490     return NFC_STATUS_FAILED;
1491   }
1492 }
1493 
1494 /*******************************************************************************
1495 **
1496 ** Function         rw_i93_send_cmd_get_ext_sys_info
1497 **
1498 ** Description      Send Get Extended System Information Request to VICC
1499 **
1500 ** Returns          tNFC_STATUS
1501 **
1502 *******************************************************************************/
rw_i93_send_cmd_get_ext_sys_info(uint8_t * p_uid)1503 tNFC_STATUS rw_i93_send_cmd_get_ext_sys_info(uint8_t* p_uid) {
1504   NFC_HDR* p_cmd;
1505   uint8_t* p;
1506 
1507   DLOG_IF(INFO, nfc_debug_enabled) << __func__;
1508 
1509   p_cmd = (NFC_HDR*)GKI_getpoolbuf(NFC_RW_POOL_ID);
1510 
1511   if (!p_cmd) {
1512     DLOG_IF(INFO, nfc_debug_enabled) << __func__ << "Cannot allocate buffer";
1513     return NFC_STATUS_NO_BUFFERS;
1514   }
1515 
1516   p_cmd->offset = NCI_MSG_OFFSET_SIZE + NCI_DATA_HDR_SIZE;
1517   p_cmd->len = 11;
1518   p = (uint8_t*)(p_cmd + 1) + p_cmd->offset;
1519 
1520   /* Flags */
1521   UINT8_TO_STREAM(p, (I93_FLAG_ADDRESS_SET | RW_I93_FLAG_SUB_CARRIER |
1522                       RW_I93_FLAG_DATA_RATE));
1523 
1524   /* Command Code */
1525   UINT8_TO_STREAM(p, I93_CMD_EXT_GET_SYS_INFO);
1526 
1527   /* Parameters request field */
1528   UINT8_TO_STREAM(p,
1529                   (I93_INFO_FLAG_MOI | I93_INFO_FLAG_DSFID | I93_INFO_FLAG_AFI |
1530                    I93_INFO_FLAG_MEM_SIZE | I93_INFO_FLAG_IC_REF));
1531 
1532   /* Parameters */
1533   if (p_uid) {
1534     ARRAY8_TO_STREAM(p, p_uid); /* UID */
1535   } else {
1536     ARRAY8_TO_STREAM(p, rw_cb.tcb.i93.uid); /* UID */
1537   }
1538 
1539   if (rw_i93_send_to_lower(p_cmd)) {
1540     rw_cb.tcb.i93.sent_cmd = I93_CMD_EXT_GET_SYS_INFO;
1541     return NFC_STATUS_OK;
1542   } else {
1543     return NFC_STATUS_FAILED;
1544   }
1545 }
1546 
1547 /*******************************************************************************
1548 **
1549 ** Function         rw_i93_send_cmd_get_sys_info
1550 **
1551 ** Description      Send Get System Information Request to VICC
1552 **
1553 ** Returns          tNFC_STATUS
1554 **
1555 *******************************************************************************/
rw_i93_send_cmd_get_sys_info(uint8_t * p_uid,uint8_t extra_flags)1556 tNFC_STATUS rw_i93_send_cmd_get_sys_info(uint8_t* p_uid, uint8_t extra_flags) {
1557   NFC_HDR* p_cmd;
1558   uint8_t* p;
1559 
1560   DLOG_IF(INFO, nfc_debug_enabled) << __func__;
1561 
1562   p_cmd = (NFC_HDR*)GKI_getpoolbuf(NFC_RW_POOL_ID);
1563 
1564   if (!p_cmd) {
1565     LOG(ERROR) << StringPrintf("Cannot allocate buffer");
1566     return NFC_STATUS_NO_BUFFERS;
1567   }
1568 
1569   p_cmd->offset = NCI_MSG_OFFSET_SIZE + NCI_DATA_HDR_SIZE;
1570   p_cmd->len = 10;
1571   p = (uint8_t*)(p_cmd + 1) + p_cmd->offset;
1572 
1573   /* Flags */
1574   UINT8_TO_STREAM(p, (I93_FLAG_ADDRESS_SET | RW_I93_FLAG_SUB_CARRIER |
1575                       RW_I93_FLAG_DATA_RATE | extra_flags));
1576 
1577   /* Command Code */
1578   UINT8_TO_STREAM(p, I93_CMD_GET_SYS_INFO);
1579 
1580   /* Parameters */
1581   if (p_uid) {
1582     ARRAY8_TO_STREAM(p, p_uid); /* UID */
1583   } else {
1584     ARRAY8_TO_STREAM(p, rw_cb.tcb.i93.uid); /* UID */
1585   }
1586 
1587   if (rw_i93_send_to_lower(p_cmd)) {
1588     rw_cb.tcb.i93.sent_cmd = I93_CMD_GET_SYS_INFO;
1589     return NFC_STATUS_OK;
1590   } else {
1591     return NFC_STATUS_FAILED;
1592   }
1593 }
1594 
1595 /*******************************************************************************
1596 **
1597 ** Function         rw_i93_send_cmd_get_multi_block_sec
1598 **
1599 ** Description      Send Get Multiple Block Security Status Request to VICC
1600 **
1601 ** Returns          tNFC_STATUS
1602 **
1603 *******************************************************************************/
rw_i93_send_cmd_get_multi_block_sec(uint16_t first_block_number,uint16_t number_blocks)1604 tNFC_STATUS rw_i93_send_cmd_get_multi_block_sec(uint16_t first_block_number,
1605                                                 uint16_t number_blocks) {
1606   NFC_HDR* p_cmd;
1607   uint8_t *p, flags;
1608 
1609   DLOG_IF(INFO, nfc_debug_enabled) << __func__;
1610 
1611   p_cmd = (NFC_HDR*)GKI_getpoolbuf(NFC_RW_POOL_ID);
1612 
1613   if (!p_cmd) {
1614     LOG(ERROR) << StringPrintf("Cannot allocate buffer");
1615     return NFC_STATUS_NO_BUFFERS;
1616   }
1617 
1618   p_cmd->offset = NCI_MSG_OFFSET_SIZE + NCI_DATA_HDR_SIZE;
1619   p_cmd->len = 12;
1620   p = (uint8_t*)(p_cmd + 1) + p_cmd->offset;
1621 
1622   /* Flags */
1623   flags =
1624       (I93_FLAG_ADDRESS_SET | RW_I93_FLAG_SUB_CARRIER | RW_I93_FLAG_DATA_RATE);
1625 
1626   if (rw_cb.tcb.i93.intl_flags & RW_I93_FLAG_16BIT_NUM_BLOCK)
1627     flags |= I93_FLAG_PROT_EXT_YES;
1628 
1629   UINT8_TO_STREAM(p, flags);
1630 
1631   /* Command Code */
1632   if (rw_cb.tcb.i93.intl_flags & RW_I93_FLAG_EXT_COMMANDS) {
1633     UINT8_TO_STREAM(p, I93_CMD_EXT_GET_MULTI_BLK_SEC);
1634   } else {
1635     UINT8_TO_STREAM(p, I93_CMD_GET_MULTI_BLK_SEC);
1636   }
1637 
1638   /* Parameters */
1639   ARRAY8_TO_STREAM(p, rw_cb.tcb.i93.uid); /* UID */
1640 
1641   if (rw_cb.tcb.i93.intl_flags & RW_I93_FLAG_16BIT_NUM_BLOCK ||
1642       rw_cb.tcb.i93.intl_flags & RW_I93_FLAG_EXT_COMMANDS) {
1643     UINT16_TO_STREAM(p, first_block_number); /* First block number */
1644     UINT16_TO_STREAM(
1645         p, number_blocks - 1); /* Number of blocks, 0x00 to read one block */
1646     p_cmd->len += 2;
1647   } else {
1648     UINT8_TO_STREAM(p, first_block_number); /* First block number */
1649     UINT8_TO_STREAM(
1650         p, number_blocks - 1); /* Number of blocks, 0x00 to read one block */
1651   }
1652 
1653   if (rw_i93_send_to_lower(p_cmd)) {
1654     if (rw_cb.tcb.i93.intl_flags & RW_I93_FLAG_EXT_COMMANDS)
1655       rw_cb.tcb.i93.sent_cmd = I93_CMD_EXT_GET_MULTI_BLK_SEC;
1656     else
1657       rw_cb.tcb.i93.sent_cmd = I93_CMD_GET_MULTI_BLK_SEC;
1658     return NFC_STATUS_OK;
1659   } else {
1660     return NFC_STATUS_FAILED;
1661   }
1662 }
1663 
1664 /*******************************************************************************
1665 **
1666 ** Function         rw_i93_get_next_blocks
1667 **
1668 ** Description      Read as many blocks as possible (up to
1669 **                  RW_I93_READ_MULTI_BLOCK_SIZE)
1670 **
1671 ** Returns          tNFC_STATUS
1672 **
1673 *******************************************************************************/
rw_i93_get_next_blocks(uint16_t offset)1674 tNFC_STATUS rw_i93_get_next_blocks(uint16_t offset) {
1675   tRW_I93_CB* p_i93 = &rw_cb.tcb.i93;
1676   uint16_t first_block;
1677   uint16_t num_block;
1678 
1679   DLOG_IF(INFO, nfc_debug_enabled) << __func__;
1680 
1681   first_block = offset / p_i93->block_size;
1682 
1683   /* more blocks, more efficent but more error rate */
1684 
1685   if (p_i93->intl_flags & RW_I93_FLAG_READ_MULTI_BLOCK) {
1686     num_block = RW_I93_READ_MULTI_BLOCK_SIZE / p_i93->block_size;
1687 
1688     // first_block is an offset related to the beginning of the T5T_Area for T5T
1689     // tags but physical memory for ISO15693 tags
1690     if (p_i93->i93_t5t_mode == RW_I93_GET_SYS_INFO_MEM_INFO) {
1691       if (num_block + first_block > p_i93->num_block)
1692         num_block = p_i93->num_block - first_block;
1693     } else {
1694       if (num_block + first_block >
1695           p_i93->num_block + p_i93->t5t_area_start_block)
1696         num_block =
1697             p_i93->num_block - first_block + p_i93->t5t_area_start_block;
1698     }
1699 
1700     if (p_i93->uid[1] == I93_UID_IC_MFG_CODE_STM) {
1701       /* LRIS64K, M24LR64-R, M24LR04E-R, M24LR16E-R, M24LR16D-W, M24LR64E-R
1702       ** require
1703       ** - The max number of blocks is 32 and they are all located in the
1704       **   same sector.
1705       ** - The sector is 32 blocks of 4 bytes.
1706       */
1707       if ((p_i93->product_version == RW_I93_STM_LRIS64K) ||
1708           (p_i93->product_version == RW_I93_STM_M24LR64_R) ||
1709           (p_i93->product_version == RW_I93_STM_M24LR04E_R) ||
1710           (p_i93->product_version == RW_I93_STM_M24LR16E_R) ||
1711           (p_i93->product_version == RW_I93_STM_M24LR16D_W) ||
1712           (p_i93->product_version == RW_I93_STM_M24LR64E_R)) {
1713         if (num_block > I93_STM_MAX_BLOCKS_PER_READ)
1714           num_block = I93_STM_MAX_BLOCKS_PER_READ;
1715 
1716         if ((first_block / I93_STM_BLOCKS_PER_SECTOR) !=
1717             ((first_block + num_block - 1) / I93_STM_BLOCKS_PER_SECTOR)) {
1718           num_block = I93_STM_BLOCKS_PER_SECTOR -
1719                       (first_block % I93_STM_BLOCKS_PER_SECTOR);
1720         }
1721       }
1722     }
1723 
1724     if (p_i93->uid[1] == I93_UID_IC_MFG_CODE_ONS) {
1725       /* N24RF04, N24RF04E, N24RF16, N24RF16E, N24RF64, N24RF64E requires
1726       ** - The max number of blocks is 32 and they are all located in the
1727       **   same sector.
1728       ** - The sector is 32 blocks of 4 bytes.
1729       */
1730       if ((p_i93->product_version == RW_I93_ONS_N36RW02) ||
1731           (p_i93->product_version == RW_I93_ONS_N24RF04) ||
1732           (p_i93->product_version == RW_I93_ONS_N24RF04E)||
1733           (p_i93->product_version == RW_I93_ONS_N24RF16) ||
1734           (p_i93->product_version == RW_I93_ONS_N24RF16E)||
1735           (p_i93->product_version == RW_I93_ONS_N24RF64) ||
1736           (p_i93->product_version == RW_I93_ONS_N24RF64E)) {
1737         if (num_block > I93_ONS_MAX_BLOCKS_PER_READ)
1738           num_block = I93_ONS_MAX_BLOCKS_PER_READ;
1739 
1740         if ((first_block / I93_ONS_BLOCKS_PER_SECTOR) !=
1741             ((first_block + num_block - 1) / I93_ONS_BLOCKS_PER_SECTOR)) {
1742           num_block = I93_ONS_BLOCKS_PER_SECTOR -
1743                       (first_block % I93_ONS_BLOCKS_PER_SECTOR);
1744         }
1745       }
1746     }
1747 
1748     if (num_block == 0) {
1749       /* only one remaining block to read */
1750       return rw_i93_send_cmd_read_single_block(first_block, false);
1751     }
1752 
1753     return rw_i93_send_cmd_read_multi_blocks(first_block, num_block);
1754   } else {
1755     return rw_i93_send_cmd_read_single_block(first_block, false);
1756   }
1757 }
1758 
1759 /*******************************************************************************
1760 **
1761 ** Function         rw_i93_get_next_block_sec
1762 **
1763 ** Description      Get as many security of blocks as possible from
1764 **                  p_i93->rw_offset (up to RW_I93_GET_MULTI_BLOCK_SEC_SIZE)
1765 **
1766 ** Returns          tNFC_STATUS
1767 **
1768 *******************************************************************************/
rw_i93_get_next_block_sec(void)1769 tNFC_STATUS rw_i93_get_next_block_sec(void) {
1770   tRW_I93_CB* p_i93 = &rw_cb.tcb.i93;
1771   uint16_t num_blocks;
1772 
1773   DLOG_IF(INFO, nfc_debug_enabled) << __func__;
1774 
1775   if (p_i93->num_block <= p_i93->rw_offset) {
1776     LOG(ERROR) << StringPrintf(
1777         "rw_offset(0x%x) must be less than num_block(0x%x)", p_i93->rw_offset,
1778         p_i93->num_block);
1779     return NFC_STATUS_FAILED;
1780   }
1781 
1782   num_blocks = p_i93->num_block - p_i93->rw_offset;
1783 
1784   if (num_blocks > RW_I93_GET_MULTI_BLOCK_SEC_SIZE)
1785     num_blocks = RW_I93_GET_MULTI_BLOCK_SEC_SIZE;
1786 
1787   DLOG_IF(INFO, nfc_debug_enabled)
1788       << StringPrintf("%s intl_flags=%d", __func__, rw_cb.tcb.i93.intl_flags);
1789   return rw_i93_send_cmd_get_multi_block_sec(p_i93->rw_offset, num_blocks);
1790 }
1791 
1792 /*******************************************************************************
1793 **
1794 ** Function         rw_i93_sm_detect_ndef
1795 **
1796 ** Description      Process NDEF detection procedure
1797 **
1798 **                  1. Get UID if not having yet
1799 **                  2. Get System Info if not having yet
1800 **                  3. Read first block for CC
1801 **                  4. Search NDEF Type and length
1802 **                  5. Get block status to get max NDEF size and read-only
1803 **                     status
1804 **
1805 ** Returns          void
1806 **
1807 *******************************************************************************/
rw_i93_sm_detect_ndef(NFC_HDR * p_resp)1808 void rw_i93_sm_detect_ndef(NFC_HDR* p_resp) {
1809   uint8_t *p = (uint8_t*)(p_resp + 1) + p_resp->offset, *p_uid;
1810   uint8_t flags, u8 = 0, cc[4];
1811   uint16_t length = p_resp->len, xx, block, first_block, last_block, num_blocks;
1812   tRW_I93_CB* p_i93 = &rw_cb.tcb.i93;
1813   tRW_DATA rw_data;
1814   tNFC_STATUS status = NFC_STATUS_FAILED;
1815 
1816   DLOG_IF(INFO, nfc_debug_enabled) << StringPrintf(
1817       "%s - sub_state:%s (0x%x)", __func__,
1818       rw_i93_get_sub_state_name(p_i93->sub_state).c_str(), p_i93->sub_state);
1819 
1820   if (length == 0) {
1821     android_errorWriteLog(0x534e4554, "121260197");
1822     rw_i93_handle_error(NFC_STATUS_FAILED);
1823     return;
1824   }
1825   STREAM_TO_UINT8(flags, p);
1826   length--;
1827 
1828   if (flags & I93_FLAG_ERROR_DETECTED) {
1829     if ((length) && (rw_i93_check_sys_info_prot_ext(*p))) {
1830       /* getting system info with protocol extension flag */
1831       /* This STM & ONS tag supports more than 2040 bytes */
1832       p_i93->intl_flags |= RW_I93_FLAG_16BIT_NUM_BLOCK;
1833     } else {
1834       DLOG_IF(INFO, nfc_debug_enabled)
1835           << StringPrintf("%s - Got error flags (0x%02x)", __func__, flags);
1836       rw_i93_handle_error(NFC_STATUS_FAILED);
1837     }
1838     return;
1839   }
1840 
1841   switch (p_i93->sub_state) {
1842     case RW_I93_SUBSTATE_WAIT_UID:
1843 
1844       if (length < (I93_UID_BYTE_LEN + 1)) {
1845         android_errorWriteLog(0x534e4554, "121260197");
1846         rw_i93_handle_error(NFC_STATUS_FAILED);
1847         return;
1848       }
1849       STREAM_TO_UINT8(u8, p); /* DSFID */
1850       p_uid = p_i93->uid;
1851       STREAM_TO_ARRAY8(p_uid, p);
1852 
1853       if (u8 != I93_DFS_UNSUPPORTED) {
1854         /* if Data Storage Format is unknown */
1855         DLOG_IF(INFO, nfc_debug_enabled)
1856             << StringPrintf("%s - Got unknown DSFID (0x%02x)", __func__, u8);
1857         rw_i93_handle_error(NFC_STATUS_FAILED);
1858       } else {
1859         /* get system information to get memory size */
1860         if (rw_i93_send_cmd_get_sys_info(nullptr, I93_FLAG_PROT_EXT_NO) ==
1861             NFC_STATUS_OK) {
1862           p_i93->sub_state = RW_I93_SUBSTATE_WAIT_SYS_INFO;
1863         } else {
1864           rw_i93_handle_error(NFC_STATUS_FAILED);
1865         }
1866       }
1867       break;
1868 
1869     case RW_I93_SUBSTATE_WAIT_SYS_INFO:
1870 
1871       p_i93->block_size = 0;
1872       p_i93->num_block = 0;
1873 
1874       if (!rw_i93_process_sys_info(p, length)) {
1875         /* retrying with protocol extension flag */
1876         break;
1877       }
1878 
1879       if ((p_i93->block_size == 0) || (p_i93->num_block == 0)) {
1880         DLOG_IF(INFO, nfc_debug_enabled)
1881             << StringPrintf("%s - Unable to get tag memory size", __func__);
1882         rw_i93_handle_error(status);
1883       } else {
1884         /* read CC in the first block */
1885         if (rw_i93_send_cmd_read_single_block(0x0000, false) == NFC_STATUS_OK) {
1886           p_i93->sub_state = RW_I93_SUBSTATE_WAIT_CC;
1887         } else {
1888           rw_i93_handle_error(NFC_STATUS_FAILED);
1889         }
1890       }
1891       break;
1892 
1893     case RW_I93_SUBSTATE_WAIT_CC:
1894 
1895       if (length < RW_I93_CC_SIZE) {
1896         android_errorWriteLog(0x534e4554, "139188579");
1897         rw_i93_handle_error(NFC_STATUS_FAILED);
1898         return;
1899       }
1900 
1901       /* assume block size is more than RW_I93_CC_SIZE 4 */
1902       STREAM_TO_ARRAY(cc, p, RW_I93_CC_SIZE);
1903 
1904       status = NFC_STATUS_FAILED;
1905 
1906       /*
1907       ** Capability Container (CC)
1908       **
1909       ** CC[0] : magic number (0xE1)
1910       ** CC[1] : Bit 7-6:Major version number
1911       **       : Bit 5-4:Minor version number
1912       **       : Bit 3-2:Read access condition (00b: read access granted
1913       **         without any security)
1914       **       : Bit 1-0:Write access condition (00b: write access granted
1915       **         without any security)
1916       ** CC[2] : Memory size in 8 bytes (Ex. 0x04 is 32 bytes) [STM, ONS set
1917       **         to 0xFF if more than 2040bytes]
1918       ** CC[3] : Bit 0:Read multiple blocks is supported [NXP, STM, ONS]
1919       **       : Bit 1:Inventory page read is supported [NXP]
1920       **       : Bit 2:More than 2040 bytes are supported [STM, ONS]
1921       */
1922 
1923       DLOG_IF(INFO, nfc_debug_enabled)
1924           << StringPrintf("%s - cc[0-3]: 0x%02X 0x%02X 0x%02X 0x%02X", __func__,
1925                           cc[0], cc[1], cc[2], cc[3]);
1926 
1927       DLOG_IF(INFO, nfc_debug_enabled)
1928           << StringPrintf("%s - Total blocks:0x%04X, Block size:0x%02X",
1929                           __func__, p_i93->num_block, p_i93->block_size);
1930 
1931       if ((cc[0] == I93_ICODE_CC_MAGIC_NUMER_E1) ||
1932           (cc[0] == I93_ICODE_CC_MAGIC_NUMER_E2)) {
1933         if ((cc[1] & 0xC0) > I93_VERSION_1_x) {
1934           DLOG_IF(INFO, nfc_debug_enabled) << StringPrintf(
1935               "%s - Major mapping version above 1 %d.x", __func__, cc[1] >> 6);
1936           /* major mapping version above 1 not supported */
1937           rw_i93_handle_error(NFC_STATUS_FAILED);
1938           break;
1939         }
1940         if ((cc[1] & I93_ICODE_CC_READ_ACCESS_MASK) ==
1941             I93_ICODE_CC_READ_ACCESS_GRANTED) {
1942           if ((cc[1] & I93_ICODE_CC_WRITE_ACCESS_MASK) !=
1943               I93_ICODE_CC_WRITE_ACCESS_GRANTED) {
1944             /* read-only or password required to write */
1945             p_i93->intl_flags |= RW_I93_FLAG_READ_ONLY;
1946           }
1947           if (cc[3] & I93_ICODE_CC_MBREAD_MASK) {
1948             /* tag supports read multiple blocks command */
1949             p_i93->intl_flags |= RW_I93_FLAG_READ_MULTI_BLOCK;
1950           }
1951           if (cc[3] & I93_ICODE_CC_SPECIAL_FRAME_MASK) {
1952             /* tag supports Special Frame for Write-Alike commands */
1953             p_i93->intl_flags |= RW_I93_FLAG_SPECIAL_FRAME;
1954           }
1955           if (cc[0] == I93_ICODE_CC_MAGIC_NUMER_E2) {
1956             p_i93->intl_flags |= RW_I93_FLAG_EXT_COMMANDS;
1957           }
1958           status = NFC_STATUS_OK;
1959         }
1960       }
1961 
1962       if (status == NFC_STATUS_OK) {
1963         /* seach NDEF TLV from offset 4 when CC file coded on 4 bytes NFC Forum
1964          */
1965         if (cc[2] != 0)
1966           p_i93->rw_offset = 4;
1967         else
1968           p_i93->rw_offset = 8;
1969 
1970         if (rw_i93_get_next_blocks(p_i93->rw_offset) == NFC_STATUS_OK) {
1971           p_i93->sub_state = RW_I93_SUBSTATE_SEARCH_NDEF_TLV;
1972           p_i93->tlv_detect_state = RW_I93_TLV_DETECT_STATE_TYPE;
1973         } else {
1974           rw_i93_handle_error(NFC_STATUS_FAILED);
1975         }
1976       } else {
1977         rw_i93_handle_error(NFC_STATUS_FAILED);
1978       }
1979       break;
1980 
1981     case RW_I93_SUBSTATE_SEARCH_NDEF_TLV:
1982 
1983       /* search TLV within read blocks */
1984       for (xx = 0; xx < length; xx++) {
1985         /* if looking for type */
1986         if (p_i93->tlv_detect_state == RW_I93_TLV_DETECT_STATE_TYPE) {
1987           if (*(p + xx) == I93_ICODE_TLV_TYPE_NULL) {
1988             continue;
1989           } else if ((*(p + xx) == I93_ICODE_TLV_TYPE_NDEF) ||
1990                      (*(p + xx) == I93_ICODE_TLV_TYPE_PROP)) {
1991             /* store found type and get length field */
1992             p_i93->tlv_type = *(p + xx);
1993             p_i93->ndef_tlv_start_offset = p_i93->rw_offset + xx;
1994 
1995             p_i93->tlv_detect_state = RW_I93_TLV_DETECT_STATE_LENGTH_1;
1996           } else if (*(p + xx) == I93_ICODE_TLV_TYPE_TERM) {
1997             /* no NDEF TLV found */
1998             p_i93->tlv_type = I93_ICODE_TLV_TYPE_TERM;
1999             break;
2000           } else {
2001             DLOG_IF(INFO, nfc_debug_enabled) << StringPrintf(
2002                 "%s - Invalid type: 0x%02x", __func__, *(p + xx));
2003             rw_i93_handle_error(NFC_STATUS_FAILED);
2004             return;
2005           }
2006         } else if (p_i93->tlv_detect_state ==
2007                    RW_I93_TLV_DETECT_STATE_LENGTH_1) {
2008           /* if 3 bytes length field */
2009           if (*(p + xx) == 0xFF) {
2010             /* need 2 more bytes for length field */
2011             p_i93->tlv_detect_state = RW_I93_TLV_DETECT_STATE_LENGTH_2;
2012           } else {
2013             p_i93->tlv_length = *(p + xx);
2014             p_i93->tlv_detect_state = RW_I93_TLV_DETECT_STATE_VALUE;
2015 
2016             if (p_i93->tlv_type == I93_ICODE_TLV_TYPE_NDEF) {
2017               p_i93->ndef_tlv_last_offset =
2018                   p_i93->ndef_tlv_start_offset + 1 + p_i93->tlv_length;
2019               break;
2020             }
2021           }
2022         } else if (p_i93->tlv_detect_state ==
2023                    RW_I93_TLV_DETECT_STATE_LENGTH_2) {
2024           /* the second byte of 3 bytes length field */
2025           p_i93->tlv_length = *(p + xx);
2026           p_i93->tlv_detect_state = RW_I93_TLV_DETECT_STATE_LENGTH_3;
2027         } else if (p_i93->tlv_detect_state ==
2028                    RW_I93_TLV_DETECT_STATE_LENGTH_3) {
2029           /* the last byte of 3 bytes length field */
2030           p_i93->tlv_length = (p_i93->tlv_length << 8) + *(p + xx);
2031           p_i93->tlv_detect_state = RW_I93_TLV_DETECT_STATE_VALUE;
2032 
2033           if (p_i93->tlv_type == I93_ICODE_TLV_TYPE_NDEF) {
2034             p_i93->ndef_tlv_last_offset =
2035                 p_i93->ndef_tlv_start_offset + 3 + p_i93->tlv_length;
2036             break;
2037           }
2038         } else if (p_i93->tlv_detect_state == RW_I93_TLV_DETECT_STATE_VALUE) {
2039           /* this is other than NDEF TLV */
2040           if (p_i93->tlv_length <= length - xx) {
2041             /* skip value field */
2042             xx += (uint8_t)p_i93->tlv_length;
2043             p_i93->tlv_detect_state = RW_I93_TLV_DETECT_STATE_TYPE;
2044           } else {
2045             /* read more data */
2046             p_i93->tlv_length -= (length - xx);
2047             break;
2048           }
2049         }
2050       }
2051 
2052       /* found NDEF TLV and read length field */
2053       if ((p_i93->tlv_type == I93_ICODE_TLV_TYPE_NDEF) &&
2054           (p_i93->tlv_detect_state == RW_I93_TLV_DETECT_STATE_VALUE)) {
2055         p_i93->ndef_length = p_i93->tlv_length;
2056 
2057         /* get lock status to see if read-only */
2058         if ((p_i93->product_version == RW_I93_TAG_IT_HF_I_STD_CHIP_INLAY) ||
2059             (p_i93->product_version == RW_I93_TAG_IT_HF_I_PRO_CHIP_INLAY) ||
2060             ((p_i93->uid[1] == I93_UID_IC_MFG_CODE_NXP) &&
2061              (p_i93->ic_reference & I93_ICODE_IC_REF_MBREAD_MASK))) {
2062           /* these doesn't support GetMultiBlockSecurityStatus */
2063 
2064           p_i93->rw_offset = p_i93->ndef_tlv_start_offset;
2065           first_block = p_i93->ndef_tlv_start_offset / p_i93->block_size;
2066 
2067           /* read block to get lock status */
2068           rw_i93_send_cmd_read_single_block(first_block, true);
2069           p_i93->sub_state = RW_I93_SUBSTATE_CHECK_LOCK_STATUS;
2070         } else {
2071           /* block offset for read-only check */
2072           p_i93->rw_offset = 0;
2073 
2074           if (rw_i93_get_next_block_sec() == NFC_STATUS_OK) {
2075             p_i93->sub_state = RW_I93_SUBSTATE_CHECK_LOCK_STATUS;
2076           } else {
2077             rw_i93_handle_error(NFC_STATUS_FAILED);
2078           }
2079         }
2080       } else {
2081         /* read more data */
2082         p_i93->rw_offset += length;
2083 
2084         if (p_i93->rw_offset >= p_i93->block_size * p_i93->num_block) {
2085           rw_i93_handle_error(NFC_STATUS_FAILED);
2086         } else if (rw_i93_get_next_blocks(p_i93->rw_offset) == NFC_STATUS_OK) {
2087           p_i93->sub_state = RW_I93_SUBSTATE_SEARCH_NDEF_TLV;
2088         } else {
2089           rw_i93_handle_error(NFC_STATUS_FAILED);
2090         }
2091       }
2092       break;
2093 
2094     case RW_I93_SUBSTATE_CHECK_LOCK_STATUS:
2095 
2096       if ((p_i93->product_version == RW_I93_TAG_IT_HF_I_STD_CHIP_INLAY) ||
2097           (p_i93->product_version == RW_I93_TAG_IT_HF_I_PRO_CHIP_INLAY) ||
2098           ((p_i93->uid[1] == I93_UID_IC_MFG_CODE_NXP) &&
2099            (p_i93->ic_reference & I93_ICODE_IC_REF_MBREAD_MASK))) {
2100         /* these doesn't support GetMultiBlockSecurityStatus */
2101 
2102         block = (p_i93->rw_offset / p_i93->block_size);
2103         last_block = (p_i93->ndef_tlv_last_offset / p_i93->block_size);
2104 
2105         if (length == 0) {
2106           rw_i93_handle_error(NFC_STATUS_FAILED);
2107         }
2108         if ((*p) & I93_BLOCK_LOCKED) {
2109           if (block <= last_block) {
2110             p_i93->intl_flags |= RW_I93_FLAG_READ_ONLY;
2111           }
2112         } else {
2113           /* if we need to check more user blocks */
2114           if (block + 1 < p_i93->num_block) {
2115             p_i93->rw_offset += p_i93->block_size;
2116 
2117             /* read block to get lock status */
2118             rw_i93_send_cmd_read_single_block(
2119                 (uint16_t)(p_i93->rw_offset / p_i93->block_size), true);
2120             break;
2121           }
2122         }
2123 
2124         p_i93->max_ndef_length =
2125             p_i93->ndef_length
2126             /* add available bytes including the last block of NDEF TLV */
2127             + (p_i93->block_size * (block - last_block) + 1) -
2128             (p_i93->ndef_tlv_last_offset % p_i93->block_size) - 1;
2129       } else {
2130         if (p_i93->rw_offset == 0) {
2131           p_i93->max_ndef_length =
2132               p_i93->ndef_length
2133               /* add available bytes in the last block of NDEF TLV */
2134               + p_i93->block_size -
2135               (p_i93->ndef_tlv_last_offset % p_i93->block_size) - 1;
2136 
2137           first_block = (p_i93->ndef_tlv_start_offset / p_i93->block_size);
2138         } else {
2139           first_block = 0;
2140         }
2141 
2142         last_block = (p_i93->ndef_tlv_last_offset / p_i93->block_size);
2143         num_blocks = length;
2144 
2145         for (block = first_block; block < num_blocks; block++) {
2146           /* if any block of NDEF TLV is locked */
2147           if ((block + p_i93->rw_offset) <= last_block) {
2148             if (*(p + block) & I93_BLOCK_LOCKED) {
2149               p_i93->intl_flags |= RW_I93_FLAG_READ_ONLY;
2150               break;
2151             }
2152           } else {
2153             if (*(p + block) & I93_BLOCK_LOCKED) {
2154               /* no more consecutive unlocked block */
2155               break;
2156             } else {
2157               /* add block size if not locked */
2158               p_i93->max_ndef_length += p_i93->block_size;
2159             }
2160           }
2161         }
2162 
2163         /* update next security of block to check */
2164         p_i93->rw_offset += num_blocks;
2165 
2166         /* if need to check more */
2167         if (p_i93->num_block > p_i93->rw_offset) {
2168           if (rw_i93_get_next_block_sec() != NFC_STATUS_OK) {
2169             rw_i93_handle_error(NFC_STATUS_FAILED);
2170           }
2171           break;
2172         }
2173       }
2174 
2175       /* check if need to adjust max NDEF length */
2176       if ((p_i93->ndef_length < 0xFF) && (p_i93->max_ndef_length >= 0xFF)) {
2177         /* 3 bytes length field must be used */
2178         p_i93->max_ndef_length -= 2;
2179       }
2180 
2181       rw_data.ndef.status = NFC_STATUS_OK;
2182       rw_data.ndef.protocol = NFC_PROTOCOL_T5T;
2183       rw_data.ndef.flags = 0;
2184       rw_data.ndef.flags |= RW_NDEF_FL_SUPPORTED;
2185       rw_data.ndef.flags |= RW_NDEF_FL_FORMATED;
2186       rw_data.ndef.flags |= RW_NDEF_FL_FORMATABLE;
2187       rw_data.ndef.cur_size = p_i93->ndef_length;
2188 
2189       if (p_i93->intl_flags & RW_I93_FLAG_READ_ONLY) {
2190         rw_data.ndef.flags |= RW_NDEF_FL_READ_ONLY;
2191         rw_data.ndef.max_size = p_i93->ndef_length;
2192       } else {
2193         rw_data.ndef.flags |= RW_NDEF_FL_HARD_LOCKABLE;
2194         rw_data.ndef.max_size = p_i93->max_ndef_length;
2195       }
2196 
2197       p_i93->state = RW_I93_STATE_IDLE;
2198       p_i93->sent_cmd = 0;
2199 
2200       DLOG_IF(INFO, nfc_debug_enabled) << StringPrintf(
2201           "%s - NDEF cur_size(%d),max_size (%d), flags (0x%x)", __func__,
2202           rw_data.ndef.cur_size, rw_data.ndef.max_size, rw_data.ndef.flags);
2203 
2204       (*(rw_cb.p_cback))(RW_I93_NDEF_DETECT_EVT, &rw_data);
2205       break;
2206 
2207     default:
2208       break;
2209   }
2210 }
2211 
2212 /*******************************************************************************
2213 **
2214 ** Function         rw_i93_sm_read_ndef
2215 **
2216 ** Description      Process NDEF read procedure
2217 **
2218 ** Returns          void
2219 **
2220 *******************************************************************************/
rw_i93_sm_read_ndef(NFC_HDR * p_resp)2221 void rw_i93_sm_read_ndef(NFC_HDR* p_resp) {
2222   uint8_t* p = (uint8_t*)(p_resp + 1) + p_resp->offset;
2223   uint8_t flags;
2224   uint16_t offset, length = p_resp->len;
2225   tRW_I93_CB* p_i93 = &rw_cb.tcb.i93;
2226   tRW_DATA rw_data;
2227 
2228   DLOG_IF(INFO, nfc_debug_enabled) << __func__;
2229 
2230   if (length == 0) {
2231     android_errorWriteLog(0x534e4554, "122035770");
2232     rw_i93_handle_error(NFC_STATUS_FAILED);
2233     return;
2234   }
2235 
2236   STREAM_TO_UINT8(flags, p);
2237   length--;
2238 
2239   if (flags & I93_FLAG_ERROR_DETECTED) {
2240     DLOG_IF(INFO, nfc_debug_enabled)
2241         << StringPrintf("%s - Got error flags (0x%02x)", __func__, flags);
2242     rw_i93_handle_error(NFC_STATUS_FAILED);
2243     return;
2244   }
2245 
2246   /* if this is the first block */
2247   if (p_i93->rw_length == 0) {
2248     /* get start of NDEF in the first block */
2249     offset = p_i93->ndef_tlv_start_offset % p_i93->block_size;
2250 
2251     if (p_i93->ndef_length < 0xFF) {
2252       offset += 2;
2253     } else {
2254       offset += 4;
2255     }
2256 
2257     /* adjust offset if read more blocks because the first block doesn't have
2258      * NDEF */
2259     offset -= (p_i93->rw_offset - p_i93->ndef_tlv_start_offset);
2260   } else {
2261     offset = 0;
2262   }
2263 
2264   /* if read enough data to skip type and length field for the beginning */
2265   if (offset < length) {
2266     offset++; /* flags */
2267     p_resp->offset += offset;
2268     p_resp->len -= offset;
2269 
2270     rw_data.data.status = NFC_STATUS_OK;
2271     rw_data.data.p_data = p_resp;
2272 
2273     p_i93->rw_length += p_resp->len;
2274   } else {
2275     /* in case of no Ndef data included */
2276     p_resp->len = 0;
2277   }
2278 
2279   /* if read all of NDEF data */
2280   if (p_i93->rw_length >= p_i93->ndef_length) {
2281     /* remove extra btyes in the last block */
2282     p_resp->len -= (p_i93->rw_length - p_i93->ndef_length);
2283 
2284     p_i93->state = RW_I93_STATE_IDLE;
2285     p_i93->sent_cmd = 0;
2286 
2287     DLOG_IF(INFO, nfc_debug_enabled)
2288         << StringPrintf("%s - NDEF read complete read (%d)/total (%d)",
2289                         __func__, p_resp->len, p_i93->ndef_length);
2290 
2291     (*(rw_cb.p_cback))(RW_I93_NDEF_READ_CPLT_EVT, &rw_data);
2292   } else {
2293     DLOG_IF(INFO, nfc_debug_enabled)
2294         << StringPrintf("%s - NDEF read segment read (%d)/total (%d)", __func__,
2295                         p_resp->len, p_i93->ndef_length);
2296 
2297     if (p_resp->len > 0) {
2298       (*(rw_cb.p_cback))(RW_I93_NDEF_READ_EVT, &rw_data);
2299     } else {
2300        // free buffer, if len == 0
2301        GKI_freebuf(p_resp);
2302     }
2303 
2304     /* this will make read data from next block */
2305     p_i93->rw_offset += length;
2306 
2307     if (rw_i93_get_next_blocks(p_i93->rw_offset) != NFC_STATUS_OK) {
2308       rw_i93_handle_error(NFC_STATUS_FAILED);
2309     }
2310   }
2311 }
2312 
2313 /*******************************************************************************
2314 **
2315 ** Function         rw_i93_sm_update_ndef
2316 **
2317 ** Description      Process NDEF update procedure
2318 **
2319 **                  1. Set length field to zero
2320 **                  2. Write NDEF and Terminator TLV
2321 **                  3. Set length field to NDEF length
2322 **
2323 ** Returns          void
2324 **
2325 *******************************************************************************/
rw_i93_sm_update_ndef(NFC_HDR * p_resp)2326 void rw_i93_sm_update_ndef(NFC_HDR* p_resp) {
2327   uint8_t* p = (uint8_t*)(p_resp + 1) + p_resp->offset;
2328   uint8_t flags, xx, length_offset, buff[I93_MAX_BLOCK_LENGH];
2329   uint16_t length = p_resp->len, block_number;
2330   tRW_I93_CB* p_i93 = &rw_cb.tcb.i93;
2331   tRW_DATA rw_data;
2332 
2333   DLOG_IF(INFO, nfc_debug_enabled) << StringPrintf(
2334       "%s - sub_state:%s (0x%x)", __func__,
2335       rw_i93_get_sub_state_name(p_i93->sub_state).c_str(), p_i93->sub_state);
2336 
2337   if (length == 0 || p_i93->block_size > I93_MAX_BLOCK_LENGH) {
2338     android_errorWriteLog(0x534e4554, "122320256");
2339     rw_i93_handle_error(NFC_STATUS_FAILED);
2340     return;
2341   }
2342 
2343   STREAM_TO_UINT8(flags, p);
2344   length--;
2345 
2346   if (flags & I93_FLAG_ERROR_DETECTED) {
2347     if (((p_i93->product_version == RW_I93_TAG_IT_HF_I_PLUS_INLAY) ||
2348          (p_i93->product_version == RW_I93_TAG_IT_HF_I_PLUS_CHIP) ||
2349          (p_i93->product_version == RW_I93_TAG_IT_HF_I_STD_CHIP_INLAY) ||
2350          (p_i93->product_version == RW_I93_TAG_IT_HF_I_PRO_CHIP_INLAY)) &&
2351         (*p == I93_ERROR_CODE_BLOCK_FAIL_TO_WRITE)) {
2352       /* ignore error */
2353     } else {
2354       DLOG_IF(INFO, nfc_debug_enabled)
2355           << StringPrintf("%s - Got error flags (0x%02x)", __func__, flags);
2356       rw_i93_handle_error(NFC_STATUS_FAILED);
2357       return;
2358     }
2359   }
2360 
2361   switch (p_i93->sub_state) {
2362     case RW_I93_SUBSTATE_RESET_LEN:
2363 
2364       /* get offset of length field */
2365       length_offset = (p_i93->ndef_tlv_start_offset + 1) % p_i93->block_size;
2366 
2367       if (length < length_offset) {
2368         android_errorWriteLog(0x534e4554, "122320256");
2369         rw_i93_handle_error(NFC_STATUS_FAILED);
2370         return;
2371       }
2372 
2373       /* set length to zero */
2374       *(p + length_offset) = 0x00;
2375 
2376       if (p_i93->ndef_length > 0) {
2377         /* if 3 bytes length field is needed */
2378         if (p_i93->ndef_length >= 0xFF) {
2379           xx = length_offset + 3;
2380         } else {
2381           xx = length_offset + 1;
2382         }
2383 
2384         /* write the first part of NDEF in the same block */
2385         for (; xx < p_i93->block_size; xx++) {
2386           if (xx > length || p_i93->rw_length > p_i93->ndef_length) {
2387             android_errorWriteLog(0x534e4554, "122320256");
2388             rw_i93_handle_error(NFC_STATUS_FAILED);
2389             return;
2390           }
2391           if (p_i93->rw_length < p_i93->ndef_length) {
2392             *(p + xx) = *(p_i93->p_update_data + p_i93->rw_length++);
2393           } else {
2394             *(p + xx) = I93_ICODE_TLV_TYPE_NULL;
2395           }
2396         }
2397       }
2398 
2399       block_number = (p_i93->ndef_tlv_start_offset + 1) / p_i93->block_size;
2400 
2401       if (length < p_i93->block_size) {
2402         android_errorWriteLog(0x534e4554, "143109193");
2403         rw_i93_handle_error(NFC_STATUS_FAILED);
2404       } else if (rw_i93_send_cmd_write_single_block(block_number, p) ==
2405                  NFC_STATUS_OK) {
2406         /* update next writing offset */
2407         p_i93->rw_offset = (block_number + 1) * p_i93->block_size;
2408         p_i93->sub_state = RW_I93_SUBSTATE_WRITE_NDEF;
2409       } else {
2410         rw_i93_handle_error(NFC_STATUS_FAILED);
2411       }
2412       break;
2413 
2414     case RW_I93_SUBSTATE_WRITE_NDEF:
2415 
2416       /* if it's not the end of tag memory */
2417       if (p_i93->rw_offset < p_i93->block_size * p_i93->num_block) {
2418         block_number = p_i93->rw_offset / p_i93->block_size;
2419 
2420         /* if we have more data to write */
2421         if (p_i93->rw_length < p_i93->ndef_length) {
2422           p = p_i93->p_update_data + p_i93->rw_length;
2423 
2424           p_i93->rw_offset += p_i93->block_size;
2425           p_i93->rw_length += p_i93->block_size;
2426 
2427           /* if this is the last block of NDEF TLV */
2428           if (p_i93->rw_length > p_i93->ndef_length) {
2429             /* length of NDEF TLV in the block */
2430             xx = (uint8_t)(p_i93->block_size -
2431                            (p_i93->rw_length - p_i93->ndef_length));
2432 
2433             /* set NULL TLV in the unused part of block */
2434             memset(buff, I93_ICODE_TLV_TYPE_NULL, p_i93->block_size);
2435             memcpy(buff, p, xx);
2436             p = buff;
2437 
2438             /* if it's the end of tag memory */
2439             if ((p_i93->rw_offset >= p_i93->block_size * p_i93->num_block) &&
2440                 (xx < p_i93->block_size)) {
2441               buff[xx] = I93_ICODE_TLV_TYPE_TERM;
2442             }
2443 
2444             p_i93->ndef_tlv_last_offset =
2445                 p_i93->rw_offset - p_i93->block_size + xx - 1;
2446           }
2447 
2448           if (rw_i93_send_cmd_write_single_block(block_number, p) !=
2449               NFC_STATUS_OK) {
2450             rw_i93_handle_error(NFC_STATUS_FAILED);
2451           }
2452         } else {
2453           /* if this is the very next block of NDEF TLV */
2454           if (block_number ==
2455               (p_i93->ndef_tlv_last_offset / p_i93->block_size) + 1) {
2456             p_i93->rw_offset += p_i93->block_size;
2457 
2458             /* write Terminator TLV and NULL TLV */
2459             memset(buff, I93_ICODE_TLV_TYPE_NULL, p_i93->block_size);
2460             buff[0] = I93_ICODE_TLV_TYPE_TERM;
2461             p = buff;
2462 
2463             if (rw_i93_send_cmd_write_single_block(block_number, p) !=
2464                 NFC_STATUS_OK) {
2465               rw_i93_handle_error(NFC_STATUS_FAILED);
2466             }
2467           } else {
2468             /* finished writing NDEF and Terminator TLV */
2469             /* read length field to update length       */
2470             block_number =
2471                 (p_i93->ndef_tlv_start_offset + 1) / p_i93->block_size;
2472 
2473             if (rw_i93_send_cmd_read_single_block(block_number, false) ==
2474                 NFC_STATUS_OK) {
2475               /* set offset to length field */
2476               p_i93->rw_offset = p_i93->ndef_tlv_start_offset + 1;
2477 
2478               /* get size of length field */
2479               if (p_i93->ndef_length >= 0xFF) {
2480                 p_i93->rw_length = 3;
2481               } else if (p_i93->ndef_length > 0) {
2482                 p_i93->rw_length = 1;
2483               } else {
2484                 p_i93->rw_length = 0;
2485               }
2486 
2487               p_i93->sub_state = RW_I93_SUBSTATE_UPDATE_LEN;
2488             } else {
2489               rw_i93_handle_error(NFC_STATUS_FAILED);
2490             }
2491           }
2492         }
2493       } else {
2494         /* if we have no more data to write */
2495         if (p_i93->rw_length >= p_i93->ndef_length) {
2496           /* finished writing NDEF and Terminator TLV */
2497           /* read length field to update length       */
2498           block_number = (p_i93->ndef_tlv_start_offset + 1) / p_i93->block_size;
2499 
2500           if (rw_i93_send_cmd_read_single_block(block_number, false) ==
2501               NFC_STATUS_OK) {
2502             /* set offset to length field */
2503             p_i93->rw_offset = p_i93->ndef_tlv_start_offset + 1;
2504 
2505             /* get size of length field */
2506             if (p_i93->ndef_length >= 0xFF) {
2507               p_i93->rw_length = 3;
2508             } else if (p_i93->ndef_length > 0) {
2509               p_i93->rw_length = 1;
2510             } else {
2511               p_i93->rw_length = 0;
2512             }
2513 
2514             p_i93->sub_state = RW_I93_SUBSTATE_UPDATE_LEN;
2515             break;
2516           }
2517         }
2518         rw_i93_handle_error(NFC_STATUS_FAILED);
2519       }
2520       break;
2521 
2522     case RW_I93_SUBSTATE_UPDATE_LEN:
2523 
2524       /* if we have more length field to write */
2525       if (p_i93->rw_length > 0) {
2526         /* if we got ack for writing, read next block to update rest of length
2527          * field */
2528         if (length == 0) {
2529           block_number = p_i93->rw_offset / p_i93->block_size;
2530 
2531           if (rw_i93_send_cmd_read_single_block(block_number, false) !=
2532               NFC_STATUS_OK) {
2533             rw_i93_handle_error(NFC_STATUS_FAILED);
2534           }
2535         } else {
2536           length_offset = p_i93->rw_offset % p_i93->block_size;
2537 
2538           /* update length field within the read block */
2539           for (xx = length_offset; xx < p_i93->block_size; xx++) {
2540             if (xx > length) {
2541               android_errorWriteLog(0x534e4554, "122320256");
2542               rw_i93_handle_error(NFC_STATUS_FAILED);
2543               return;
2544             }
2545 
2546             if (p_i93->rw_length == 3)
2547               *(p + xx) = 0xFF;
2548             else if (p_i93->rw_length == 2)
2549               *(p + xx) = (uint8_t)((p_i93->ndef_length >> 8) & 0xFF);
2550             else if (p_i93->rw_length == 1)
2551               *(p + xx) = (uint8_t)(p_i93->ndef_length & 0xFF);
2552 
2553             p_i93->rw_length--;
2554             if (p_i93->rw_length == 0) break;
2555           }
2556 
2557           block_number = (p_i93->rw_offset / p_i93->block_size);
2558 
2559           if (length < p_i93->block_size) {
2560             android_errorWriteLog(0x534e4554, "143155861");
2561             rw_i93_handle_error(NFC_STATUS_FAILED);
2562           } else if (rw_i93_send_cmd_write_single_block(block_number, p) ==
2563                      NFC_STATUS_OK) {
2564             /* set offset to the beginning of next block */
2565             p_i93->rw_offset +=
2566                 p_i93->block_size - (p_i93->rw_offset % p_i93->block_size);
2567           } else {
2568             rw_i93_handle_error(NFC_STATUS_FAILED);
2569           }
2570         }
2571       } else {
2572         DLOG_IF(INFO, nfc_debug_enabled) << StringPrintf(
2573             "%s - NDEF update complete, %d bytes, (%d-%d)", __func__,
2574             p_i93->ndef_length, p_i93->ndef_tlv_start_offset,
2575             p_i93->ndef_tlv_last_offset);
2576 
2577         p_i93->state = RW_I93_STATE_IDLE;
2578         p_i93->sent_cmd = 0;
2579         p_i93->p_update_data = nullptr;
2580 
2581         rw_data.status = NFC_STATUS_OK;
2582         (*(rw_cb.p_cback))(RW_I93_NDEF_UPDATE_CPLT_EVT, &rw_data);
2583       }
2584       break;
2585 
2586     default:
2587       break;
2588   }
2589 }
2590 
2591 /*******************************************************************************
2592 **
2593 ** Function         rw_i93_sm_format
2594 **
2595 ** Description      Process format procedure
2596 **
2597 **                  1. Get UID
2598 **                  2. Get sys info for memory size (reset AFI/DSFID)
2599 **                  3. Get block status to get read-only status
2600 **                  4. Write CC and empty NDEF
2601 **
2602 ** Returns          void
2603 **
2604 *******************************************************************************/
rw_i93_sm_format(NFC_HDR * p_resp)2605 void rw_i93_sm_format(NFC_HDR* p_resp) {
2606   uint8_t *p = (uint8_t*)(p_resp + 1) + p_resp->offset, *p_uid;
2607   uint8_t flags;
2608   uint16_t length = p_resp->len, xx, block_number;
2609   tRW_I93_CB* p_i93 = &rw_cb.tcb.i93;
2610   tRW_DATA rw_data;
2611   tNFC_STATUS status = NFC_STATUS_FAILED;
2612 
2613   DLOG_IF(INFO, nfc_debug_enabled) << StringPrintf(
2614       "sub_state:%s (0x%x)",
2615       rw_i93_get_sub_state_name(p_i93->sub_state).c_str(), p_i93->sub_state);
2616 
2617   if (length == 0) {
2618     android_errorWriteLog(0x534e4554, "122323053");
2619     return;
2620   }
2621   STREAM_TO_UINT8(flags, p);
2622   length--;
2623 
2624   if (flags & I93_FLAG_ERROR_DETECTED) {
2625     if (((p_i93->product_version == RW_I93_TAG_IT_HF_I_PLUS_INLAY) ||
2626          (p_i93->product_version == RW_I93_TAG_IT_HF_I_PLUS_CHIP) ||
2627          (p_i93->product_version == RW_I93_TAG_IT_HF_I_STD_CHIP_INLAY) ||
2628          (p_i93->product_version == RW_I93_TAG_IT_HF_I_PRO_CHIP_INLAY)) &&
2629         (*p == I93_ERROR_CODE_BLOCK_FAIL_TO_WRITE)) {
2630       /* ignore error */
2631     } else if ((length) && (rw_i93_check_sys_info_prot_ext(*p))) {
2632       /* getting system info with protocol extension flag */
2633       /* This STM & ONS tag supports more than 2040 bytes */
2634       p_i93->intl_flags |= RW_I93_FLAG_16BIT_NUM_BLOCK;
2635       return;
2636     } else {
2637       DLOG_IF(INFO, nfc_debug_enabled)
2638           << StringPrintf("Got error flags (0x%02x)", flags);
2639       rw_i93_handle_error(NFC_STATUS_FAILED);
2640       return;
2641     }
2642   }
2643 
2644   switch (p_i93->sub_state) {
2645     case RW_I93_SUBSTATE_WAIT_UID:
2646 
2647       if (length < (I93_UID_BYTE_LEN + 1)) {
2648         android_errorWriteLog(0x534e4554, "122323053");
2649         return;
2650       }
2651       p++; /* skip DSFID */
2652       p_uid = p_i93->uid;
2653       STREAM_TO_ARRAY8(p_uid, p); /* store UID */
2654 
2655       /* get system information to get memory size */
2656       if (rw_i93_send_cmd_get_sys_info(nullptr, I93_FLAG_PROT_EXT_NO) ==
2657           NFC_STATUS_OK) {
2658         p_i93->sub_state = RW_I93_SUBSTATE_WAIT_SYS_INFO;
2659       } else {
2660         rw_i93_handle_error(NFC_STATUS_FAILED);
2661       }
2662       break;
2663 
2664     case RW_I93_SUBSTATE_WAIT_SYS_INFO:
2665 
2666       p_i93->block_size = 0;
2667       p_i93->num_block = 0;
2668 
2669       if (!rw_i93_process_sys_info(p, length)) {
2670         /* retrying with protocol extension flag */
2671         break;
2672       }
2673 
2674       if (p_i93->info_flags & I93_INFO_FLAG_DSFID) {
2675         /* DSFID, if any DSFID then reset */
2676         if (p_i93->dsfid != I93_DFS_UNSUPPORTED) {
2677           p_i93->intl_flags |= RW_I93_FLAG_RESET_DSFID;
2678         }
2679       }
2680       if (p_i93->info_flags & I93_INFO_FLAG_AFI) {
2681         /* AFI, reset to 0 */
2682         if (p_i93->afi != 0x00) {
2683           p_i93->intl_flags |= RW_I93_FLAG_RESET_AFI;
2684         }
2685       }
2686 
2687       if ((p_i93->block_size == 0) || (p_i93->num_block == 0)) {
2688         DLOG_IF(INFO, nfc_debug_enabled)
2689             << StringPrintf("Unable to get tag memory size");
2690         rw_i93_handle_error(status);
2691       } else if (p_i93->intl_flags & RW_I93_FLAG_RESET_DSFID) {
2692         if (rw_i93_send_cmd_write_dsfid(I93_DFS_UNSUPPORTED) == NFC_STATUS_OK) {
2693           p_i93->sub_state = RW_I93_SUBSTATE_WAIT_RESET_DSFID_AFI;
2694         } else {
2695           rw_i93_handle_error(NFC_STATUS_FAILED);
2696         }
2697       } else if (p_i93->intl_flags & RW_I93_FLAG_RESET_AFI) {
2698         if (rw_i93_send_cmd_write_afi(0x00) == NFC_STATUS_OK) {
2699           p_i93->sub_state = RW_I93_SUBSTATE_WAIT_RESET_DSFID_AFI;
2700         } else {
2701           rw_i93_handle_error(NFC_STATUS_FAILED);
2702         }
2703       } else {
2704         /* get lock status to see if read-only */
2705         if ((p_i93->uid[1] == I93_UID_IC_MFG_CODE_NXP) &&
2706             (p_i93->ic_reference & I93_ICODE_IC_REF_MBREAD_MASK)) {
2707           /* these doesn't support GetMultiBlockSecurityStatus */
2708 
2709           rw_cb.tcb.i93.rw_offset = 0;
2710 
2711           /* read blocks with option flag to get block security status */
2712           if (rw_i93_send_cmd_read_single_block(0x0000, true) ==
2713               NFC_STATUS_OK) {
2714             p_i93->sub_state = RW_I93_SUBSTATE_CHECK_READ_ONLY;
2715           } else {
2716             rw_i93_handle_error(NFC_STATUS_FAILED);
2717           }
2718         } else {
2719           /* block offset for read-only check */
2720           p_i93->rw_offset = 0;
2721 
2722           if (rw_i93_get_next_block_sec() == NFC_STATUS_OK) {
2723             p_i93->sub_state = RW_I93_SUBSTATE_CHECK_READ_ONLY;
2724           } else {
2725             rw_i93_handle_error(NFC_STATUS_FAILED);
2726           }
2727         }
2728       }
2729 
2730       break;
2731 
2732     case RW_I93_SUBSTATE_WAIT_RESET_DSFID_AFI:
2733 
2734       if (p_i93->sent_cmd == I93_CMD_WRITE_DSFID) {
2735         p_i93->intl_flags &= ~RW_I93_FLAG_RESET_DSFID;
2736       } else if (p_i93->sent_cmd == I93_CMD_WRITE_AFI) {
2737         p_i93->intl_flags &= ~RW_I93_FLAG_RESET_AFI;
2738       }
2739 
2740       if (p_i93->intl_flags & RW_I93_FLAG_RESET_DSFID) {
2741         if (rw_i93_send_cmd_write_dsfid(I93_DFS_UNSUPPORTED) == NFC_STATUS_OK) {
2742           p_i93->sub_state = RW_I93_SUBSTATE_WAIT_RESET_DSFID_AFI;
2743         } else {
2744           rw_i93_handle_error(NFC_STATUS_FAILED);
2745         }
2746       } else if (p_i93->intl_flags & RW_I93_FLAG_RESET_AFI) {
2747         if (rw_i93_send_cmd_write_afi(0x00) == NFC_STATUS_OK) {
2748           p_i93->sub_state = RW_I93_SUBSTATE_WAIT_RESET_DSFID_AFI;
2749         } else {
2750           rw_i93_handle_error(NFC_STATUS_FAILED);
2751         }
2752       } else {
2753         /* get lock status to see if read-only */
2754         if ((p_i93->uid[1] == I93_UID_IC_MFG_CODE_NXP) &&
2755             (p_i93->ic_reference & I93_ICODE_IC_REF_MBREAD_MASK)) {
2756           /* these doesn't support GetMultiBlockSecurityStatus */
2757 
2758           rw_cb.tcb.i93.rw_offset = 0;
2759 
2760           /* read blocks with option flag to get block security status */
2761           if (rw_i93_send_cmd_read_single_block(0x0000, true) ==
2762               NFC_STATUS_OK) {
2763             p_i93->sub_state = RW_I93_SUBSTATE_CHECK_READ_ONLY;
2764           } else {
2765             rw_i93_handle_error(NFC_STATUS_FAILED);
2766           }
2767         } else {
2768           /* block offset for read-only check */
2769           p_i93->rw_offset = 0;
2770 
2771           if (rw_i93_get_next_block_sec() == NFC_STATUS_OK) {
2772             p_i93->sub_state = RW_I93_SUBSTATE_CHECK_READ_ONLY;
2773           } else {
2774             rw_i93_handle_error(NFC_STATUS_FAILED);
2775           }
2776         }
2777       }
2778       break;
2779 
2780     case RW_I93_SUBSTATE_CHECK_READ_ONLY:
2781 
2782       if ((p_i93->product_version == RW_I93_TAG_IT_HF_I_STD_CHIP_INLAY) ||
2783           (p_i93->product_version == RW_I93_TAG_IT_HF_I_PRO_CHIP_INLAY) ||
2784           ((p_i93->uid[1] == I93_UID_IC_MFG_CODE_NXP) &&
2785            (p_i93->ic_reference & I93_ICODE_IC_REF_MBREAD_MASK))) {
2786         if (length == 0 || ((*p) & I93_BLOCK_LOCKED)) {
2787           rw_i93_handle_error(NFC_STATUS_FAILED);
2788           break;
2789         }
2790 
2791         /* if we checked all of user blocks */
2792         if ((p_i93->rw_offset / p_i93->block_size) + 1 == p_i93->num_block) {
2793           if ((p_i93->product_version == RW_I93_TAG_IT_HF_I_STD_CHIP_INLAY) ||
2794               (p_i93->product_version == RW_I93_TAG_IT_HF_I_PRO_CHIP_INLAY)) {
2795             /* read the block which has AFI */
2796             p_i93->rw_offset = I93_TAG_IT_HF_I_STD_PRO_CHIP_INLAY_AFI_LOCATION;
2797             rw_i93_send_cmd_read_single_block(
2798                 (uint16_t)(p_i93->rw_offset / p_i93->block_size), true);
2799             break;
2800           }
2801         } else if (p_i93->rw_offset ==
2802                    I93_TAG_IT_HF_I_STD_PRO_CHIP_INLAY_AFI_LOCATION) {
2803           /* no block is locked */
2804         } else {
2805           p_i93->rw_offset += p_i93->block_size;
2806           rw_i93_send_cmd_read_single_block(
2807               (uint16_t)(p_i93->rw_offset / p_i93->block_size), true);
2808           break;
2809         }
2810       } else {
2811         /* if any block is locked, we cannot format it */
2812         for (xx = 0; xx < length; xx++) {
2813           if (*(p + xx) & I93_BLOCK_LOCKED) {
2814             rw_i93_handle_error(NFC_STATUS_FAILED);
2815             break;
2816           }
2817         }
2818 
2819         /* update block offset for read-only check */
2820         p_i93->rw_offset += length;
2821 
2822         /* if need to get more lock status of blocks */
2823         if (p_i93->num_block > p_i93->rw_offset) {
2824           if (rw_i93_get_next_block_sec() != NFC_STATUS_OK) {
2825             rw_i93_handle_error(NFC_STATUS_FAILED);
2826           }
2827           break;
2828         }
2829       }
2830 
2831       /* get buffer to store CC, zero length NDEF TLV and Terminator TLV */
2832       /* Block size could be either 4 or 8 or 16 or 32 bytes */
2833       /* Get buffer for the largest block size I93_MAX_BLOCK_LENGH */
2834       p_i93->p_update_data = (uint8_t*)GKI_getbuf(I93_MAX_BLOCK_LENGH);
2835 
2836       if (!p_i93->p_update_data) {
2837         LOG(ERROR) << StringPrintf("Cannot allocate buffer");
2838         rw_i93_handle_error(NFC_STATUS_FAILED);
2839         break;
2840       } else {
2841         switch (p_i93->block_size) {
2842           case 4:
2843           case 8:
2844             break;
2845           case 16:
2846           case 32: /* initialize unpopulated buffer b/139738828 */
2847             memset(p_i93->p_update_data, I93_ICODE_TLV_TYPE_NULL,
2848                    I93_MAX_BLOCK_LENGH);
2849             break;
2850           default:
2851             android_errorWriteLog(0x534e4554, "157650336");
2852             rw_i93_handle_error(NFC_STATUS_FAILED);
2853             return;
2854         }
2855       }
2856 
2857       p = p_i93->p_update_data;
2858 
2859       /* Capability Container */
2860       *(p++) = I93_ICODE_CC_MAGIC_NUMER_E1; /* magic number */
2861       *(p++) = 0x40;                     /* version 1.0, read/write */
2862 
2863       /* if memory size is less than 2048 bytes */
2864       if (((p_i93->num_block * p_i93->block_size) / 8) < 0x100)
2865         *(p++) = (uint8_t)((p_i93->num_block * p_i93->block_size) /
2866                            8); /* memory size */
2867       else
2868         *(p++) = 0xFF;
2869 
2870       if ((p_i93->product_version == RW_I93_ICODE_SLI) ||
2871           (p_i93->product_version == RW_I93_ICODE_SLI_S) ||
2872           (p_i93->product_version == RW_I93_ICODE_SLI_L)) {
2873         if (p_i93->ic_reference & I93_ICODE_IC_REF_MBREAD_MASK)
2874           *(p++) = I93_ICODE_CC_IPREAD_MASK; /* IPREAD */
2875         else
2876           *(p++) = I93_ICODE_CC_MBREAD_MASK; /* MBREAD, read multi block command
2877                                                 supported */
2878       } else if ((p_i93->product_version == RW_I93_TAG_IT_HF_I_PLUS_INLAY) ||
2879                  (p_i93->product_version == RW_I93_TAG_IT_HF_I_PLUS_CHIP)) {
2880         *(p++) = I93_ICODE_CC_MBREAD_MASK; /* MBREAD, read multi block command
2881                                               supported */
2882       } else if ((p_i93->product_version ==
2883                   RW_I93_TAG_IT_HF_I_STD_CHIP_INLAY) ||
2884                  (p_i93->product_version ==
2885                   RW_I93_TAG_IT_HF_I_PRO_CHIP_INLAY)) {
2886         *(p++) = 0;
2887       } else {
2888         /* STM except LRIS2K, ONS, Broadcom supports read multi block command */
2889 
2890         /* if memory size is more than 2040 bytes (which is not LRIS2K) */
2891         if (((p_i93->num_block * p_i93->block_size) / 8) > 0xFF)
2892           *(p++) = (I93_ICODE_CC_MBREAD_MASK | I93_STM_CC_OVERFLOW_MASK);
2893         else if (p_i93->product_version == RW_I93_STM_LRIS2K)
2894           *(p++) = 0x00;
2895         else
2896           *(p++) = I93_ICODE_CC_MBREAD_MASK;
2897       }
2898 
2899       /* zero length NDEF and Terminator TLV */
2900       *(p++) = I93_ICODE_TLV_TYPE_NDEF;
2901       *(p++) = 0x00;
2902       *(p++) = I93_ICODE_TLV_TYPE_TERM;
2903       *(p++) = I93_ICODE_TLV_TYPE_NULL;
2904 
2905       /* start from block 0 */
2906       p_i93->rw_offset = 0;
2907 
2908       if (rw_i93_send_cmd_write_single_block(0, p_i93->p_update_data) ==
2909           NFC_STATUS_OK) {
2910         p_i93->sub_state = RW_I93_SUBSTATE_WRITE_CC_NDEF_TLV;
2911         p_i93->rw_offset += p_i93->block_size;
2912       } else {
2913         rw_i93_handle_error(NFC_STATUS_FAILED);
2914       }
2915       break;
2916 
2917     case RW_I93_SUBSTATE_WRITE_CC_NDEF_TLV:
2918 
2919       /* if we have more data to write */
2920       if (p_i93->rw_offset < RW_I93_FORMAT_DATA_LEN) {
2921         block_number = (p_i93->rw_offset / p_i93->block_size);
2922         p = p_i93->p_update_data + p_i93->rw_offset;
2923 
2924         if (rw_i93_send_cmd_write_single_block(block_number, p) ==
2925             NFC_STATUS_OK) {
2926           p_i93->sub_state = RW_I93_SUBSTATE_WRITE_CC_NDEF_TLV;
2927           p_i93->rw_offset += p_i93->block_size;
2928         } else {
2929           rw_i93_handle_error(NFC_STATUS_FAILED);
2930         }
2931       } else {
2932         GKI_freebuf(p_i93->p_update_data);
2933         p_i93->p_update_data = nullptr;
2934 
2935         p_i93->state = RW_I93_STATE_IDLE;
2936         p_i93->sent_cmd = 0;
2937 
2938         rw_data.status = NFC_STATUS_OK;
2939         (*(rw_cb.p_cback))(RW_I93_FORMAT_CPLT_EVT, &rw_data);
2940       }
2941       break;
2942 
2943     default:
2944       break;
2945   }
2946 }
2947 
2948 /*******************************************************************************
2949 **
2950 ** Function         rw_i93_sm_set_read_only
2951 **
2952 ** Description      Process read-only procedure
2953 **
2954 **                  1. Update CC as read-only
2955 **                  2. Lock all block of NDEF TLV
2956 **                  3. Lock block of CC
2957 **
2958 ** Returns          void
2959 **
2960 *******************************************************************************/
rw_i93_sm_set_read_only(NFC_HDR * p_resp)2961 void rw_i93_sm_set_read_only(NFC_HDR* p_resp) {
2962   uint8_t* p = (uint8_t*)(p_resp + 1) + p_resp->offset;
2963   uint8_t flags, block_number;
2964   uint16_t length = p_resp->len;
2965   tRW_I93_CB* p_i93 = &rw_cb.tcb.i93;
2966   tRW_DATA rw_data;
2967 
2968   DLOG_IF(INFO, nfc_debug_enabled) << StringPrintf(
2969       "sub_state:%s (0x%x)",
2970       rw_i93_get_sub_state_name(p_i93->sub_state).c_str(), p_i93->sub_state);
2971 
2972   if (length == 0) {
2973     android_errorWriteLog(0x534e4554, "122322613");
2974     rw_i93_handle_error(NFC_STATUS_FAILED);
2975     return;
2976   }
2977 
2978   STREAM_TO_UINT8(flags, p);
2979   length--;
2980 
2981   if (flags & I93_FLAG_ERROR_DETECTED) {
2982     if (((p_i93->product_version == RW_I93_TAG_IT_HF_I_PLUS_INLAY) ||
2983          (p_i93->product_version == RW_I93_TAG_IT_HF_I_PLUS_CHIP) ||
2984          (p_i93->product_version == RW_I93_TAG_IT_HF_I_STD_CHIP_INLAY) ||
2985          (p_i93->product_version == RW_I93_TAG_IT_HF_I_PRO_CHIP_INLAY)) &&
2986         (*p == I93_ERROR_CODE_BLOCK_FAIL_TO_WRITE)) {
2987       /* ignore error */
2988     } else {
2989       DLOG_IF(INFO, nfc_debug_enabled)
2990           << StringPrintf("Got error flags (0x%02x)", flags);
2991       rw_i93_handle_error(NFC_STATUS_FAILED);
2992       return;
2993     }
2994   }
2995 
2996   switch (p_i93->sub_state) {
2997     case RW_I93_SUBSTATE_WAIT_CC:
2998 
2999       if (length < RW_I93_CC_SIZE) {
3000         android_errorWriteLog(0x534e4554, "139188579");
3001         rw_i93_handle_error(NFC_STATUS_FAILED);
3002         return;
3003       }
3004 
3005       /* mark CC as read-only */
3006       *(p + 1) |= I93_ICODE_CC_READ_ONLY;
3007 
3008       if (length < p_i93->block_size) {
3009         android_errorWriteLog(0x534e4554, "143106535");
3010         rw_i93_handle_error(NFC_STATUS_FAILED);
3011       } else if (rw_i93_send_cmd_write_single_block(0, p) == NFC_STATUS_OK) {
3012         p_i93->sub_state = RW_I93_SUBSTATE_WAIT_UPDATE_CC;
3013       } else {
3014         rw_i93_handle_error(NFC_STATUS_FAILED);
3015       }
3016       break;
3017 
3018     case RW_I93_SUBSTATE_WAIT_UPDATE_CC:
3019 
3020       /* successfully write CC then lock all blocks of NDEF TLV */
3021       p_i93->rw_offset = p_i93->ndef_tlv_start_offset;
3022       block_number = (uint8_t)(p_i93->rw_offset / p_i93->block_size);
3023 
3024       if (rw_i93_send_cmd_lock_block(block_number) == NFC_STATUS_OK) {
3025         p_i93->rw_offset += p_i93->block_size;
3026         p_i93->sub_state = RW_I93_SUBSTATE_LOCK_NDEF_TLV;
3027       } else {
3028         rw_i93_handle_error(NFC_STATUS_FAILED);
3029       }
3030       break;
3031 
3032     case RW_I93_SUBSTATE_LOCK_NDEF_TLV:
3033 
3034       /* if we need to lock more blocks */
3035       if (p_i93->rw_offset < p_i93->ndef_tlv_last_offset) {
3036         /* get the next block of NDEF TLV */
3037         block_number = (uint8_t)(p_i93->rw_offset / p_i93->block_size);
3038 
3039         if (rw_i93_send_cmd_lock_block(block_number) == NFC_STATUS_OK) {
3040           p_i93->rw_offset += p_i93->block_size;
3041         } else {
3042           rw_i93_handle_error(NFC_STATUS_FAILED);
3043         }
3044       }
3045       /* if the first block of NDEF TLV is different from block of CC */
3046       else if (p_i93->ndef_tlv_start_offset / p_i93->block_size != 0) {
3047         /* lock block of CC */
3048         if (rw_i93_send_cmd_lock_block(0) == NFC_STATUS_OK) {
3049           p_i93->sub_state = RW_I93_SUBSTATE_WAIT_LOCK_CC;
3050         } else {
3051           rw_i93_handle_error(NFC_STATUS_FAILED);
3052         }
3053       } else {
3054         p_i93->intl_flags |= RW_I93_FLAG_READ_ONLY;
3055         p_i93->state = RW_I93_STATE_IDLE;
3056         p_i93->sent_cmd = 0;
3057 
3058         rw_data.status = NFC_STATUS_OK;
3059         (*(rw_cb.p_cback))(RW_I93_SET_TAG_RO_EVT, &rw_data);
3060       }
3061       break;
3062 
3063     case RW_I93_SUBSTATE_WAIT_LOCK_CC:
3064 
3065       p_i93->intl_flags |= RW_I93_FLAG_READ_ONLY;
3066       p_i93->state = RW_I93_STATE_IDLE;
3067       p_i93->sent_cmd = 0;
3068 
3069       rw_data.status = NFC_STATUS_OK;
3070       (*(rw_cb.p_cback))(RW_I93_SET_TAG_RO_EVT, &rw_data);
3071       break;
3072 
3073     default:
3074       break;
3075   }
3076 }
3077 
3078 /*******************************************************************************
3079 **
3080 ** Function         rw_i93_handle_error
3081 **
3082 ** Description      notify error to application and clean up
3083 **
3084 ** Returns          none
3085 **
3086 *******************************************************************************/
rw_i93_handle_error(tNFC_STATUS status)3087 void rw_i93_handle_error(tNFC_STATUS status) {
3088   tRW_I93_CB* p_i93 = &rw_cb.tcb.i93;
3089   tRW_DATA rw_data;
3090   tRW_EVENT event;
3091 
3092   DLOG_IF(INFO, nfc_debug_enabled) << StringPrintf(
3093       "%s - status:0x%02X, state:0x%X", __func__, status, p_i93->state);
3094 
3095   nfc_stop_quick_timer(&p_i93->timer);
3096 
3097   if (rw_cb.p_cback) {
3098     rw_data.status = status;
3099 
3100     switch (p_i93->state) {
3101       case RW_I93_STATE_IDLE: /* in case of RawFrame */
3102         event = RW_I93_INTF_ERROR_EVT;
3103         break;
3104 
3105       case RW_I93_STATE_BUSY:
3106         if (p_i93->sent_cmd == I93_CMD_STAY_QUIET) {
3107           /* There is no response to Stay Quiet command */
3108           rw_data.i93_cmd_cmpl.status = NFC_STATUS_OK;
3109           rw_data.i93_cmd_cmpl.command = I93_CMD_STAY_QUIET;
3110           rw_data.i93_cmd_cmpl.error_code = 0;
3111           event = RW_I93_CMD_CMPL_EVT;
3112         } else {
3113           event = RW_I93_INTF_ERROR_EVT;
3114         }
3115         break;
3116 
3117       case RW_I93_STATE_DETECT_NDEF:
3118         rw_data.ndef.protocol = NFC_PROTOCOL_T5T;
3119         rw_data.ndef.cur_size = 0;
3120         rw_data.ndef.max_size = 0;
3121         rw_data.ndef.flags = 0;
3122         rw_data.ndef.flags |= RW_NDEF_FL_FORMATABLE;
3123         rw_data.ndef.flags |= RW_NDEF_FL_UNKNOWN;
3124         event = RW_I93_NDEF_DETECT_EVT;
3125         break;
3126 
3127       case RW_I93_STATE_READ_NDEF:
3128         event = RW_I93_NDEF_READ_FAIL_EVT;
3129         break;
3130 
3131       case RW_I93_STATE_UPDATE_NDEF:
3132         p_i93->p_update_data = nullptr;
3133         event = RW_I93_NDEF_UPDATE_FAIL_EVT;
3134         break;
3135 
3136       case RW_I93_STATE_FORMAT:
3137         if (p_i93->p_update_data) {
3138           GKI_freebuf(p_i93->p_update_data);
3139           p_i93->p_update_data = nullptr;
3140         }
3141         event = RW_I93_FORMAT_CPLT_EVT;
3142         break;
3143 
3144       case RW_I93_STATE_SET_READ_ONLY:
3145         event = RW_I93_SET_TAG_RO_EVT;
3146         break;
3147 
3148       case RW_I93_STATE_PRESENCE_CHECK:
3149         event = RW_I93_PRESENCE_CHECK_EVT;
3150         break;
3151 
3152       default:
3153         event = RW_I93_MAX_EVT;
3154         break;
3155     }
3156 
3157     p_i93->state = RW_I93_STATE_IDLE;
3158     p_i93->sent_cmd = 0;
3159 
3160     if (event != RW_I93_MAX_EVT) {
3161       (*(rw_cb.p_cback))(event, &rw_data);
3162     }
3163   } else {
3164     p_i93->state = RW_I93_STATE_IDLE;
3165   }
3166 }
3167 
3168 /*******************************************************************************
3169 **
3170 ** Function         rw_i93_process_timeout
3171 **
3172 ** Description      process timeout event
3173 **
3174 ** Returns          none
3175 **
3176 *******************************************************************************/
rw_i93_process_timeout(TIMER_LIST_ENT * p_tle)3177 void rw_i93_process_timeout(TIMER_LIST_ENT* p_tle) {
3178   NFC_HDR* p_buf;
3179 
3180   DLOG_IF(INFO, nfc_debug_enabled)
3181       << StringPrintf("%s - event=%d", __func__, p_tle->event);
3182 
3183   if (p_tle->event == NFC_TTYPE_RW_I93_RESPONSE) {
3184     if ((rw_cb.tcb.i93.retry_count < RW_MAX_RETRIES) &&
3185         (rw_cb.tcb.i93.p_retry_cmd) &&
3186         (rw_cb.tcb.i93.sent_cmd != I93_CMD_STAY_QUIET)) {
3187       rw_cb.tcb.i93.retry_count++;
3188       LOG(ERROR) << StringPrintf("%s - retry_count = %d", __func__,
3189                                  rw_cb.tcb.i93.retry_count);
3190 
3191       p_buf = rw_cb.tcb.i93.p_retry_cmd;
3192       rw_cb.tcb.i93.p_retry_cmd = nullptr;
3193 
3194       if (rw_i93_send_to_lower(p_buf)) {
3195         return;
3196       }
3197     }
3198 
3199     /* all retrial is done or failed to send command to lower layer */
3200     if (rw_cb.tcb.i93.p_retry_cmd) {
3201       GKI_freebuf(rw_cb.tcb.i93.p_retry_cmd);
3202       rw_cb.tcb.i93.p_retry_cmd = nullptr;
3203       rw_cb.tcb.i93.retry_count = 0;
3204     }
3205     rw_i93_handle_error(NFC_STATUS_TIMEOUT);
3206   } else {
3207     LOG(ERROR) << StringPrintf("%s - unknown event=%d", __func__, p_tle->event);
3208   }
3209 }
3210 
3211 /*******************************************************************************
3212 **
3213 ** Function         rw_i93_data_cback
3214 **
3215 ** Description      This callback function receives the data from NFCC.
3216 **
3217 ** Returns          none
3218 **
3219 *******************************************************************************/
rw_i93_data_cback(uint8_t conn_id,tNFC_CONN_EVT event,tNFC_CONN * p_data)3220 static void rw_i93_data_cback(__attribute__((unused)) uint8_t conn_id,
3221                               tNFC_CONN_EVT event, tNFC_CONN* p_data) {
3222   tRW_I93_CB* p_i93 = &rw_cb.tcb.i93;
3223   NFC_HDR* p_resp;
3224   tRW_DATA rw_data;
3225 
3226   uint8_t begin_state = p_i93->state;
3227 
3228   DLOG_IF(INFO, nfc_debug_enabled)
3229       << StringPrintf("%s - event = 0x%X", __func__, event);
3230 
3231   if ((event == NFC_DEACTIVATE_CEVT) || (event == NFC_ERROR_CEVT) ||
3232       ((event == NFC_DATA_CEVT) && (p_data->status != NFC_STATUS_OK))) {
3233     nfc_stop_quick_timer(&p_i93->timer);
3234 
3235     if (event == NFC_ERROR_CEVT || (p_data->status != NFC_STATUS_OK)) {
3236       if ((p_i93->retry_count < RW_MAX_RETRIES) && (p_i93->p_retry_cmd)) {
3237         p_i93->retry_count++;
3238 
3239         LOG(ERROR) << StringPrintf("%s - retry_count = %d", __func__,
3240                                    p_i93->retry_count);
3241 
3242         p_resp = p_i93->p_retry_cmd;
3243         p_i93->p_retry_cmd = nullptr;
3244         if (rw_i93_send_to_lower(p_resp)) {
3245           if (event == NFC_DATA_CEVT) {
3246             p_resp = (NFC_HDR*)p_data->data.p_data;
3247             GKI_freebuf(p_resp);
3248           }
3249           return;
3250         }
3251       }
3252 
3253       /* all retrial is done or failed to send command to lower layer */
3254       if (p_i93->p_retry_cmd) {
3255         GKI_freebuf(p_i93->p_retry_cmd);
3256         p_i93->p_retry_cmd = nullptr;
3257         p_i93->retry_count = 0;
3258       }
3259 
3260       rw_i93_handle_error((tNFC_STATUS)(*(uint8_t*)p_data));
3261     } else {
3262       /* free retry buffer */
3263       if (p_i93->p_retry_cmd) {
3264         GKI_freebuf(p_i93->p_retry_cmd);
3265         p_i93->p_retry_cmd = nullptr;
3266         p_i93->retry_count = 0;
3267       }
3268       NFC_SetStaticRfCback(nullptr);
3269       p_i93->state = RW_I93_STATE_NOT_ACTIVATED;
3270     }
3271     if ((event == NFC_DATA_CEVT) && (p_data->status != NFC_STATUS_OK)) {
3272       p_resp = (NFC_HDR*)p_data->data.p_data;
3273       GKI_freebuf(p_resp);
3274     }
3275     return;
3276   }
3277 
3278   if (event != NFC_DATA_CEVT) {
3279     return;
3280   }
3281 
3282   p_resp = (NFC_HDR*)p_data->data.p_data;
3283 
3284   nfc_stop_quick_timer(&p_i93->timer);
3285 
3286   /* free retry buffer */
3287   if (p_i93->p_retry_cmd) {
3288     GKI_freebuf(p_i93->p_retry_cmd);
3289     p_i93->p_retry_cmd = nullptr;
3290     p_i93->retry_count = 0;
3291   }
3292 
3293   DLOG_IF(INFO, nfc_debug_enabled) << StringPrintf(
3294       "%s - RW I93 state: <%s (%d)>", __func__,
3295       rw_i93_get_state_name(p_i93->state).c_str(), p_i93->state);
3296 
3297   switch (p_i93->state) {
3298     case RW_I93_STATE_IDLE:
3299       /* Unexpected Response from VICC, it should be raw frame response */
3300       /* forward to upper layer without parsing */
3301       p_i93->sent_cmd = 0;
3302       if (rw_cb.p_cback) {
3303         rw_data.raw_frame.status = p_data->data.status;
3304         rw_data.raw_frame.p_data = p_resp;
3305         (*(rw_cb.p_cback))(RW_I93_RAW_FRAME_EVT, &rw_data);
3306         p_resp = nullptr;
3307       } else {
3308         GKI_freebuf(p_resp);
3309       }
3310       break;
3311     case RW_I93_STATE_BUSY:
3312       p_i93->state = RW_I93_STATE_IDLE;
3313       rw_i93_send_to_upper(p_resp);
3314       GKI_freebuf(p_resp);
3315       break;
3316 
3317     case RW_I93_STATE_DETECT_NDEF:
3318       if (p_i93->i93_t5t_mode == RW_I93_GET_SYS_INFO_MEM_INFO) {
3319         DLOG_IF(INFO, nfc_debug_enabled)
3320             << StringPrintf("%s - rw_i93_sm_detect_ndef()", __func__);
3321         rw_i93_sm_detect_ndef(p_resp);
3322       } else {
3323         DLOG_IF(INFO, nfc_debug_enabled)
3324             << StringPrintf("%s - rw_t5t_sm_detect_ndef()", __func__);
3325         rw_t5t_sm_detect_ndef(p_resp);
3326       }
3327       GKI_freebuf(p_resp);
3328       break;
3329 
3330     case RW_I93_STATE_READ_NDEF:
3331       rw_i93_sm_read_ndef(p_resp);
3332       /* p_resp may send upper lyaer */
3333       break;
3334 
3335     case RW_I93_STATE_UPDATE_NDEF:
3336       if (p_i93->i93_t5t_mode == RW_I93_GET_SYS_INFO_MEM_INFO) {
3337         DLOG_IF(INFO, nfc_debug_enabled)
3338             << StringPrintf("%s - rw_i93_sm_update_ndef()", __func__);
3339         rw_i93_sm_update_ndef(p_resp);
3340       } else {
3341         DLOG_IF(INFO, nfc_debug_enabled)
3342             << StringPrintf("%s - rw_t5t_sm_update_ndef()", __func__);
3343         rw_t5t_sm_update_ndef(p_resp);
3344       }
3345       GKI_freebuf(p_resp);
3346       break;
3347 
3348     case RW_I93_STATE_FORMAT:
3349       rw_i93_sm_format(p_resp);
3350       GKI_freebuf(p_resp);
3351       break;
3352 
3353     case RW_I93_STATE_SET_READ_ONLY:
3354       if (p_i93->i93_t5t_mode == RW_I93_GET_SYS_INFO_MEM_INFO) {
3355         DLOG_IF(INFO, nfc_debug_enabled)
3356             << StringPrintf("%s - rw_i93_sm_set_read_only()", __func__);
3357         rw_i93_sm_set_read_only(p_resp);
3358       } else {
3359         DLOG_IF(INFO, nfc_debug_enabled)
3360             << StringPrintf("%s - rw_t5t_sm_set_read_only()", __func__);
3361         rw_t5t_sm_set_read_only(p_resp);
3362       }
3363       GKI_freebuf(p_resp);
3364       break;
3365 
3366     case RW_I93_STATE_PRESENCE_CHECK:
3367       p_i93->state = RW_I93_STATE_IDLE;
3368       p_i93->sent_cmd = 0;
3369 
3370       /* if any response, send presence check with ok */
3371       rw_data.status = NFC_STATUS_OK;
3372       (*(rw_cb.p_cback))(RW_I93_PRESENCE_CHECK_EVT, &rw_data);
3373       GKI_freebuf(p_resp);
3374       break;
3375 
3376     default:
3377       LOG(ERROR) << StringPrintf("%s - invalid state=%d", __func__,
3378                                  p_i93->state);
3379       GKI_freebuf(p_resp);
3380       break;
3381   }
3382 
3383   if (begin_state != p_i93->state) {
3384     DLOG_IF(INFO, nfc_debug_enabled)
3385         << StringPrintf("%s - RW I93 state changed:<%s> -> <%s>", __func__,
3386                         rw_i93_get_state_name(begin_state).c_str(),
3387                         rw_i93_get_state_name(p_i93->state).c_str());
3388   }
3389 }
3390 
3391 /*******************************************************************************
3392 **
3393 ** Function         rw_i93_select
3394 **
3395 ** Description      Initialise ISO 15693 / T5T RW
3396 **
3397 ** Returns          NFC_STATUS_OK if success
3398 **
3399 *******************************************************************************/
rw_i93_select(uint8_t * p_uid)3400 tNFC_STATUS rw_i93_select(uint8_t* p_uid) {
3401   tRW_I93_CB* p_i93 = &rw_cb.tcb.i93;
3402   uint8_t uid[I93_UID_BYTE_LEN], *p;
3403 
3404   DLOG_IF(INFO, nfc_debug_enabled) << __func__;
3405 
3406   NFC_SetStaticRfCback(rw_i93_data_cback);
3407 
3408   p_i93->state = RW_I93_STATE_IDLE;
3409 
3410   /* convert UID to big endian format - MSB(0xE0) in first byte */
3411   p = uid;
3412   STREAM_TO_ARRAY8(p, p_uid);
3413 
3414   rw_i93_get_product_version(uid);
3415 
3416   return NFC_STATUS_OK;
3417 }
3418 
3419 /*******************************************************************************
3420 **
3421 ** Function         RW_I93Inventory
3422 **
3423 ** Description      This function send Inventory command with/without AFI
3424 **                  If UID is provided then set UID[0]:MSB, ... UID[7]:LSB
3425 **
3426 **                  RW_I93_RESPONSE_EVT will be returned
3427 **
3428 ** Returns          NFC_STATUS_OK if success
3429 **                  NFC_STATUS_NO_BUFFERS if out of buffer
3430 **                  NFC_STATUS_BUSY if busy
3431 **                  NFC_STATUS_FAILED if other error
3432 **
3433 *******************************************************************************/
RW_I93Inventory(bool including_afi,uint8_t afi,uint8_t * p_uid)3434 tNFC_STATUS RW_I93Inventory(bool including_afi, uint8_t afi, uint8_t* p_uid) {
3435   tNFC_STATUS status;
3436 
3437   DLOG_IF(INFO, nfc_debug_enabled)
3438       << StringPrintf(", including_afi:%d, AFI:0x%02X", including_afi, afi);
3439 
3440   if (rw_cb.tcb.i93.state != RW_I93_STATE_IDLE) {
3441     LOG(ERROR) << StringPrintf("Unable to start command at state (0x%X)",
3442                                rw_cb.tcb.i93.state);
3443     return NFC_STATUS_BUSY;
3444   }
3445 
3446   status = rw_i93_send_cmd_inventory(p_uid, including_afi, afi);
3447 
3448   if (status == NFC_STATUS_OK) {
3449     rw_cb.tcb.i93.state = RW_I93_STATE_BUSY;
3450   }
3451 
3452   return (status);
3453 }
3454 
3455 /*******************************************************************************
3456 **
3457 ** Function         RW_I93StayQuiet
3458 **
3459 ** Description      This function send Inventory command
3460 **
3461 **                  RW_I93_CMD_CMPL_EVT will be returned
3462 **
3463 ** Returns          NFC_STATUS_OK if success
3464 **                  NFC_STATUS_NO_BUFFERS if out of buffer
3465 **                  NFC_STATUS_BUSY if busy
3466 **                  NFC_STATUS_FAILED if other error
3467 **
3468 *******************************************************************************/
RW_I93StayQuiet(uint8_t * p_uid)3469 tNFC_STATUS RW_I93StayQuiet(uint8_t* p_uid) {
3470   tNFC_STATUS status = NFC_STATUS_FAILED;
3471 
3472   DLOG_IF(INFO, nfc_debug_enabled) << __func__;
3473 
3474   if (rw_cb.tcb.i93.state != RW_I93_STATE_IDLE) {
3475     LOG(ERROR) << StringPrintf("%s - Unable to start command at state (0x%X)",
3476                                __func__, rw_cb.tcb.i93.state);
3477     return NFC_STATUS_BUSY;
3478   }
3479 
3480   if (p_uid) {
3481     status = rw_i93_send_cmd_stay_quiet(p_uid);
3482     if (status == NFC_STATUS_OK) {
3483       rw_cb.tcb.i93.state = RW_I93_STATE_BUSY;
3484       rw_cb.tcb.i93.addr_mode = RW_I93_MODE_ADDRESSED;
3485     }
3486   }
3487 
3488   return status;
3489 }
3490 
3491 /*******************************************************************************
3492 **
3493 ** Function         RW_I93ReadSingleBlock
3494 **
3495 ** Description      This function send Read Single Block command
3496 **
3497 **                  RW_I93_RESPONSE_EVT will be returned
3498 **
3499 ** Returns          NFC_STATUS_OK if success
3500 **                  NFC_STATUS_NO_BUFFERS if out of buffer
3501 **                  NFC_STATUS_BUSY if busy
3502 **                  NFC_STATUS_FAILED if other error
3503 **
3504 *******************************************************************************/
RW_I93ReadSingleBlock(uint16_t block_number)3505 tNFC_STATUS RW_I93ReadSingleBlock(uint16_t block_number) {
3506   tNFC_STATUS status;
3507 
3508   DLOG_IF(INFO, nfc_debug_enabled)
3509       << StringPrintf("%s - block_number:0x%02X", __func__, block_number);
3510 
3511   if (rw_cb.tcb.i93.state != RW_I93_STATE_IDLE) {
3512     LOG(ERROR) << StringPrintf("Unable to start command at state (0x%X)",
3513                                rw_cb.tcb.i93.state);
3514     return NFC_STATUS_BUSY;
3515   }
3516 
3517   status = rw_i93_send_cmd_read_single_block(block_number, false);
3518   if (status == NFC_STATUS_OK) {
3519     rw_cb.tcb.i93.state = RW_I93_STATE_BUSY;
3520   }
3521 
3522   return status;
3523 }
3524 
3525 /*******************************************************************************
3526 **
3527 ** Function         RW_I93WriteSingleBlock
3528 **
3529 ** Description      This function send Write Single Block command
3530 **                  Application must get block size first by calling
3531 **                  RW_I93GetSysInfo().
3532 **
3533 **                  RW_I93_CMD_CMPL_EVT will be returned
3534 **
3535 ** Returns          NFC_STATUS_OK if success
3536 **                  NFC_STATUS_NO_BUFFERS if out of buffer
3537 **                  NFC_STATUS_BUSY if busy
3538 **                  NFC_STATUS_FAILED if other error
3539 **
3540 *******************************************************************************/
RW_I93WriteSingleBlock(uint16_t block_number,uint8_t * p_data)3541 tNFC_STATUS RW_I93WriteSingleBlock(uint16_t block_number, uint8_t* p_data) {
3542   tNFC_STATUS status;
3543 
3544   DLOG_IF(INFO, nfc_debug_enabled) << __func__;
3545 
3546   if (rw_cb.tcb.i93.state != RW_I93_STATE_IDLE) {
3547     LOG(ERROR) << StringPrintf("Unable to start command at state (0x%X)",
3548                                rw_cb.tcb.i93.state);
3549     return NFC_STATUS_BUSY;
3550   }
3551 
3552   if (rw_cb.tcb.i93.block_size == 0) {
3553     LOG(ERROR) << StringPrintf("Block size is unknown");
3554     return NFC_STATUS_FAILED;
3555   }
3556 
3557   status = rw_i93_send_cmd_write_single_block(block_number, p_data);
3558   if (status == NFC_STATUS_OK) {
3559     rw_cb.tcb.i93.state = RW_I93_STATE_BUSY;
3560   }
3561 
3562   return status;
3563 }
3564 
3565 /*******************************************************************************
3566 **
3567 ** Function         RW_I93LockBlock
3568 **
3569 ** Description      This function send Lock Block command
3570 **
3571 **                  RW_I93_CMD_CMPL_EVT will be returned
3572 **
3573 ** Returns          NFC_STATUS_OK if success
3574 **                  NFC_STATUS_NO_BUFFERS if out of buffer
3575 **                  NFC_STATUS_BUSY if busy
3576 **                  NFC_STATUS_FAILED if other error
3577 **
3578 *******************************************************************************/
RW_I93LockBlock(uint8_t block_number)3579 tNFC_STATUS RW_I93LockBlock(uint8_t block_number) {
3580   tNFC_STATUS status;
3581 
3582   DLOG_IF(INFO, nfc_debug_enabled) << __func__;
3583 
3584   if (rw_cb.tcb.i93.state != RW_I93_STATE_IDLE) {
3585     LOG(ERROR) << StringPrintf("Unable to start command at state (0x%X)",
3586                                rw_cb.tcb.i93.state);
3587     return NFC_STATUS_BUSY;
3588   }
3589 
3590   status = rw_i93_send_cmd_lock_block(block_number);
3591   if (status == NFC_STATUS_OK) {
3592     rw_cb.tcb.i93.state = RW_I93_STATE_BUSY;
3593   }
3594 
3595   return status;
3596 }
3597 
3598 /*******************************************************************************
3599 **
3600 ** Function         RW_I93ReadMultipleBlocks
3601 **
3602 ** Description      This function send Read Multiple Blocks command
3603 **
3604 **                  RW_I93_RESPONSE_EVT will be returned
3605 **
3606 ** Returns          NFC_STATUS_OK if success
3607 **                  NFC_STATUS_NO_BUFFERS if out of buffer
3608 **                  NFC_STATUS_BUSY if busy
3609 **                  NFC_STATUS_FAILED if other error
3610 **
3611 *******************************************************************************/
RW_I93ReadMultipleBlocks(uint16_t first_block_number,uint16_t number_blocks)3612 tNFC_STATUS RW_I93ReadMultipleBlocks(uint16_t first_block_number,
3613                                      uint16_t number_blocks) {
3614   tNFC_STATUS status;
3615 
3616   DLOG_IF(INFO, nfc_debug_enabled) << __func__;
3617 
3618   if (rw_cb.tcb.i93.state != RW_I93_STATE_IDLE) {
3619     LOG(ERROR) << StringPrintf("Unable to start command at state (0x%X)",
3620                                rw_cb.tcb.i93.state);
3621     return NFC_STATUS_BUSY;
3622   }
3623 
3624   status = rw_i93_send_cmd_read_multi_blocks(first_block_number, number_blocks);
3625   if (status == NFC_STATUS_OK) {
3626     rw_cb.tcb.i93.state = RW_I93_STATE_BUSY;
3627   }
3628 
3629   return status;
3630 }
3631 
3632 /*******************************************************************************
3633 **
3634 ** Function         RW_I93WriteMultipleBlocks
3635 **
3636 ** Description      This function send Write Multiple Blocks command
3637 **
3638 **                  RW_I93_CMD_CMPL_EVT will be returned
3639 **
3640 ** Returns          NFC_STATUS_OK if success
3641 **                  NFC_STATUS_NO_BUFFERS if out of buffer
3642 **                  NFC_STATUS_BUSY if busy
3643 **                  NFC_STATUS_FAILED if other error
3644 **
3645 *******************************************************************************/
RW_I93WriteMultipleBlocks(uint16_t first_block_number,uint16_t number_blocks,uint8_t * p_data)3646 tNFC_STATUS RW_I93WriteMultipleBlocks(uint16_t first_block_number,
3647                                       uint16_t number_blocks, uint8_t* p_data) {
3648   tNFC_STATUS status;
3649 
3650   DLOG_IF(INFO, nfc_debug_enabled) << __func__;
3651 
3652   if (rw_cb.tcb.i93.state != RW_I93_STATE_IDLE) {
3653     LOG(ERROR) << StringPrintf("Unable to start command at state (0x%X)",
3654                                rw_cb.tcb.i93.state);
3655     return NFC_STATUS_BUSY;
3656   }
3657 
3658   if (rw_cb.tcb.i93.block_size == 0) {
3659     LOG(ERROR) << StringPrintf("Block size is unknown");
3660     return NFC_STATUS_FAILED;
3661   }
3662 
3663   status = rw_i93_send_cmd_write_multi_blocks(first_block_number, number_blocks,
3664                                               p_data);
3665   if (status == NFC_STATUS_OK) {
3666     rw_cb.tcb.i93.state = RW_I93_STATE_BUSY;
3667   }
3668 
3669   return status;
3670 }
3671 
3672 /*******************************************************************************
3673 **
3674 ** Function         RW_I93Select
3675 **
3676 ** Description      This function send Select command
3677 **
3678 **                  UID[0]: 0xE0, MSB
3679 **                  UID[1]: IC Mfg Code
3680 **                  ...
3681 **                  UID[7]: LSB
3682 **
3683 **                  RW_I93_CMD_CMPL_EVT will be returned
3684 **
3685 ** Returns          NFC_STATUS_OK if success
3686 **                  NFC_STATUS_NO_BUFFERS if out of buffer
3687 **                  NFC_STATUS_BUSY if busy
3688 **                  NFC_STATUS_FAILED if other error
3689 **
3690 *******************************************************************************/
RW_I93Select(uint8_t * p_uid)3691 tNFC_STATUS RW_I93Select(uint8_t* p_uid) {
3692   tNFC_STATUS status;
3693 
3694   DLOG_IF(INFO, nfc_debug_enabled) << __func__;
3695 
3696   if (rw_cb.tcb.i93.state != RW_I93_STATE_IDLE) {
3697     LOG(ERROR) << StringPrintf("%s - Unable to start command at state (0x%X)",
3698                                __func__, rw_cb.tcb.i93.state);
3699     return NFC_STATUS_BUSY;
3700   }
3701 
3702   if (p_uid) {
3703     status = rw_i93_send_cmd_select(p_uid);
3704     if (status == NFC_STATUS_OK) {
3705       rw_cb.tcb.i93.state = RW_I93_STATE_BUSY;
3706       rw_cb.tcb.i93.addr_mode = RW_I93_MODE_NON_ADDRESSED;
3707       rw_cb.tcb.i93.intl_flags |= RW_I93_FLAG_SELECTED_STATE;
3708     }
3709   } else {
3710     LOG(ERROR) << StringPrintf("%s - UID shall be provided", __func__);
3711     status = NFC_STATUS_FAILED;
3712   }
3713 
3714   return status;
3715 }
3716 
3717 /*******************************************************************************
3718 **
3719 ** Function         RW_I93ResetToReady
3720 **
3721 ** Description      This function send Reset To Ready command
3722 **
3723 **                  RW_I93_CMD_CMPL_EVT will be returned
3724 **
3725 ** Returns          NFC_STATUS_OK if success
3726 **                  NFC_STATUS_NO_BUFFERS if out of buffer
3727 **                  NFC_STATUS_BUSY if busy
3728 **                  NFC_STATUS_FAILED if other error
3729 **
3730 *******************************************************************************/
RW_I93ResetToReady(void)3731 tNFC_STATUS RW_I93ResetToReady(void) {
3732   tNFC_STATUS status;
3733 
3734   DLOG_IF(INFO, nfc_debug_enabled) << __func__;
3735 
3736   if (rw_cb.tcb.i93.state != RW_I93_STATE_IDLE) {
3737     LOG(ERROR) << StringPrintf("%s - Unable to start command at state (0x%X)",
3738                                __func__, rw_cb.tcb.i93.state);
3739     return NFC_STATUS_BUSY;
3740   }
3741 
3742   status = rw_i93_send_cmd_reset_to_ready();
3743   if (status == NFC_STATUS_OK) {
3744     rw_cb.tcb.i93.state = RW_I93_STATE_BUSY;
3745   }
3746 
3747   return status;
3748 }
3749 
3750 /*******************************************************************************
3751 **
3752 ** Function         RW_I93WriteAFI
3753 **
3754 ** Description      This function send Write AFI command
3755 **
3756 **                  RW_I93_CMD_CMPL_EVT will be returned
3757 **
3758 ** Returns          NFC_STATUS_OK if success
3759 **                  NFC_STATUS_NO_BUFFERS if out of buffer
3760 **                  NFC_STATUS_BUSY if busy
3761 **                  NFC_STATUS_FAILED if other error
3762 **
3763 *******************************************************************************/
RW_I93WriteAFI(uint8_t afi)3764 tNFC_STATUS RW_I93WriteAFI(uint8_t afi) {
3765   tNFC_STATUS status;
3766 
3767   DLOG_IF(INFO, nfc_debug_enabled) << __func__;
3768 
3769   if (rw_cb.tcb.i93.state != RW_I93_STATE_IDLE) {
3770     LOG(ERROR) << StringPrintf("Unable to start command at state (0x%X)",
3771                                rw_cb.tcb.i93.state);
3772     return NFC_STATUS_BUSY;
3773   }
3774 
3775   status = rw_i93_send_cmd_write_afi(afi);
3776   if (status == NFC_STATUS_OK) {
3777     rw_cb.tcb.i93.state = RW_I93_STATE_BUSY;
3778   }
3779 
3780   return status;
3781 }
3782 
3783 /*******************************************************************************
3784 **
3785 ** Function         RW_I93LockAFI
3786 **
3787 ** Description      This function send Lock AFI command
3788 **
3789 **                  RW_I93_CMD_CMPL_EVT will be returned
3790 **
3791 ** Returns          NFC_STATUS_OK if success
3792 **                  NFC_STATUS_NO_BUFFERS if out of buffer
3793 **                  NFC_STATUS_BUSY if busy
3794 **                  NFC_STATUS_FAILED if other error
3795 **
3796 *******************************************************************************/
RW_I93LockAFI(void)3797 tNFC_STATUS RW_I93LockAFI(void) {
3798   tNFC_STATUS status;
3799 
3800   DLOG_IF(INFO, nfc_debug_enabled) << __func__;
3801 
3802   if (rw_cb.tcb.i93.state != RW_I93_STATE_IDLE) {
3803     LOG(ERROR) << StringPrintf("Unable to start command at state (0x%X)",
3804                                rw_cb.tcb.i93.state);
3805     return NFC_STATUS_BUSY;
3806   }
3807 
3808   status = rw_i93_send_cmd_lock_afi();
3809   if (status == NFC_STATUS_OK) {
3810     rw_cb.tcb.i93.state = RW_I93_STATE_BUSY;
3811   }
3812 
3813   return status;
3814 }
3815 
3816 /*******************************************************************************
3817 **
3818 ** Function         RW_I93WriteDSFID
3819 **
3820 ** Description      This function send Write DSFID command
3821 **
3822 **                  RW_I93_CMD_CMPL_EVT will be returned
3823 **
3824 ** Returns          NFC_STATUS_OK if success
3825 **                  NFC_STATUS_NO_BUFFERS if out of buffer
3826 **                  NFC_STATUS_BUSY if busy
3827 **                  NFC_STATUS_FAILED if other error
3828 **
3829 *******************************************************************************/
RW_I93WriteDSFID(uint8_t dsfid)3830 tNFC_STATUS RW_I93WriteDSFID(uint8_t dsfid) {
3831   tNFC_STATUS status;
3832 
3833   DLOG_IF(INFO, nfc_debug_enabled) << __func__;
3834 
3835   if (rw_cb.tcb.i93.state != RW_I93_STATE_IDLE) {
3836     LOG(ERROR) << StringPrintf("Unable to start command at state (0x%X)",
3837                                rw_cb.tcb.i93.state);
3838     return NFC_STATUS_BUSY;
3839   }
3840 
3841   status = rw_i93_send_cmd_write_dsfid(dsfid);
3842   if (status == NFC_STATUS_OK) {
3843     rw_cb.tcb.i93.state = RW_I93_STATE_BUSY;
3844   }
3845 
3846   return status;
3847 }
3848 
3849 /*******************************************************************************
3850 **
3851 ** Function         RW_I93LockDSFID
3852 **
3853 ** Description      This function send Lock DSFID command
3854 **
3855 **                  RW_I93_CMD_CMPL_EVT will be returned
3856 **
3857 ** Returns          NFC_STATUS_OK if success
3858 **                  NFC_STATUS_NO_BUFFERS if out of buffer
3859 **                  NFC_STATUS_BUSY if busy
3860 **                  NFC_STATUS_FAILED if other error
3861 **
3862 *******************************************************************************/
RW_I93LockDSFID(void)3863 tNFC_STATUS RW_I93LockDSFID(void) {
3864   tNFC_STATUS status;
3865 
3866   DLOG_IF(INFO, nfc_debug_enabled) << __func__;
3867 
3868   if (rw_cb.tcb.i93.state != RW_I93_STATE_IDLE) {
3869     LOG(ERROR) << StringPrintf("Unable to start command at state (0x%X)",
3870                                rw_cb.tcb.i93.state);
3871     return NFC_STATUS_BUSY;
3872   }
3873 
3874   status = rw_i93_send_cmd_lock_dsfid();
3875   if (status == NFC_STATUS_OK) {
3876     rw_cb.tcb.i93.state = RW_I93_STATE_BUSY;
3877   }
3878 
3879   return status;
3880 }
3881 
3882 /*******************************************************************************
3883 **
3884 ** Function         RW_I93GetSysInfo
3885 **
3886 ** Description      This function send Get System Information command
3887 **
3888 **                  RW_I93_RESPONSE_EVT will be returned
3889 **
3890 ** Returns          NFC_STATUS_OK if success
3891 **                  NFC_STATUS_NO_BUFFERS if out of buffer
3892 **                  NFC_STATUS_BUSY if busy
3893 **                  NFC_STATUS_FAILED if other error
3894 **
3895 *******************************************************************************/
RW_I93GetSysInfo(uint8_t * p_uid)3896 tNFC_STATUS RW_I93GetSysInfo(uint8_t* p_uid) {
3897   tNFC_STATUS status;
3898 
3899   DLOG_IF(INFO, nfc_debug_enabled) << __func__;
3900 
3901   if (rw_cb.tcb.i93.state != RW_I93_STATE_IDLE) {
3902     LOG(ERROR) << StringPrintf("%s - Unable to start command at state (0x%X)",
3903                                __func__, rw_cb.tcb.i93.state);
3904     return NFC_STATUS_BUSY;
3905   }
3906 
3907   if (p_uid) {
3908     status = rw_i93_send_cmd_get_sys_info(p_uid, I93_FLAG_PROT_EXT_NO);
3909   } else {
3910     status = rw_i93_send_cmd_get_sys_info(nullptr, I93_FLAG_PROT_EXT_NO);
3911   }
3912 
3913   if (status == NFC_STATUS_OK) {
3914     rw_cb.tcb.i93.state = RW_I93_STATE_BUSY;
3915   }
3916 
3917   return status;
3918 }
3919 
3920 /*******************************************************************************
3921 **
3922 ** Function         RW_I93GetMultiBlockSecurityStatus
3923 **
3924 ** Description      This function send Get Multiple Block Security Status
3925 **                  command
3926 **
3927 **                  RW_I93_RESPONSE_EVT will be returned
3928 **
3929 ** Returns          NFC_STATUS_OK if success
3930 **                  NFC_STATUS_NO_BUFFERS if out of buffer
3931 **                  NFC_STATUS_BUSY if busy
3932 **                  NFC_STATUS_FAILED if other error
3933 **
3934 *******************************************************************************/
RW_I93GetMultiBlockSecurityStatus(uint16_t first_block_number,uint16_t number_blocks)3935 tNFC_STATUS RW_I93GetMultiBlockSecurityStatus(uint16_t first_block_number,
3936                                               uint16_t number_blocks) {
3937   tNFC_STATUS status;
3938 
3939   DLOG_IF(INFO, nfc_debug_enabled) << __func__;
3940 
3941   if (rw_cb.tcb.i93.state != RW_I93_STATE_IDLE) {
3942     LOG(ERROR) << StringPrintf(
3943         "Unable to start command at state "
3944         "(0x%X)",
3945         rw_cb.tcb.i93.state);
3946     return NFC_STATUS_BUSY;
3947   }
3948 
3949   status =
3950       rw_i93_send_cmd_get_multi_block_sec(first_block_number, number_blocks);
3951   if (status == NFC_STATUS_OK) {
3952     rw_cb.tcb.i93.state = RW_I93_STATE_BUSY;
3953   }
3954 
3955   return status;
3956 }
3957 
3958 /*******************************************************************************
3959 **
3960 ** Function         RW_I93DetectNDef
3961 **
3962 ** Description      This function performs NDEF detection procedure
3963 **
3964 **                  RW_I93_NDEF_DETECT_EVT will be returned
3965 **
3966 ** Returns          NFC_STATUS_OK if success
3967 **                  NFC_STATUS_FAILED if busy or other error
3968 **
3969 *******************************************************************************/
RW_I93DetectNDef(void)3970 tNFC_STATUS RW_I93DetectNDef(void) {
3971   tNFC_STATUS status;
3972   tRW_I93_RW_SUBSTATE sub_state;
3973 
3974   DLOG_IF(INFO, nfc_debug_enabled) << __func__;
3975 
3976   if (rw_cb.tcb.i93.state != RW_I93_STATE_IDLE) {
3977     LOG(ERROR) << StringPrintf("%s - Unable to start command at state (0x%X)",
3978                                __func__, rw_cb.tcb.i93.state);
3979     return NFC_STATUS_FAILED;
3980   }
3981 
3982   if (rw_cb.tcb.i93.uid[0] != I93_UID_FIRST_BYTE) {
3983     status = rw_i93_send_cmd_inventory(nullptr, false, 0x00);
3984     sub_state = RW_I93_SUBSTATE_WAIT_UID;
3985 
3986   } else if (((rw_cb.tcb.i93.num_block == 0) ||
3987               (rw_cb.tcb.i93.block_size == 0)) &&
3988              (!appl_dta_mode_flag)) {
3989     status =
3990         rw_i93_send_cmd_get_sys_info(rw_cb.tcb.i93.uid, I93_FLAG_PROT_EXT_NO);
3991     sub_state = RW_I93_SUBSTATE_WAIT_SYS_INFO;
3992 
3993     /* clear all flags */
3994     rw_cb.tcb.i93.intl_flags = 0;
3995   } else {
3996     /* read CC in the first block */
3997     status = rw_i93_send_cmd_read_single_block(0x0000, false);
3998     sub_state = RW_I93_SUBSTATE_WAIT_CC;
3999   }
4000 
4001   if (status == NFC_STATUS_OK) {
4002     rw_cb.tcb.i93.state = RW_I93_STATE_DETECT_NDEF;
4003     rw_cb.tcb.i93.sub_state = sub_state;
4004 
4005     /* clear flags except flag for 2 bytes of number of blocks */
4006     rw_cb.tcb.i93.intl_flags &= RW_I93_FLAG_16BIT_NUM_BLOCK;
4007   }
4008 
4009   return (status);
4010 }
4011 
4012 /*******************************************************************************
4013 **
4014 ** Function         RW_I93ReadNDef
4015 **
4016 ** Description      This function performs NDEF read procedure
4017 **                  Note: RW_I93DetectNDef () must be called before using this
4018 **
4019 **                  The following event will be returned
4020 **                      RW_I93_NDEF_READ_EVT for each segmented NDEF message
4021 **                      RW_I93_NDEF_READ_CPLT_EVT for the last segment or
4022 **                      complete NDEF
4023 **                      RW_I93_NDEF_READ_FAIL_EVT for failure
4024 **
4025 ** Returns          NFC_STATUS_OK if success
4026 **                  NFC_STATUS_FAILED if I93 is busy or other error
4027 **
4028 *******************************************************************************/
RW_I93ReadNDef(void)4029 tNFC_STATUS RW_I93ReadNDef(void) {
4030   DLOG_IF(INFO, nfc_debug_enabled) << __func__;
4031 
4032   if (rw_cb.tcb.i93.state != RW_I93_STATE_IDLE) {
4033     LOG(ERROR) << StringPrintf("%s - Unable to start command at state (0x%X)",
4034                                __func__, rw_cb.tcb.i93.state);
4035     return NFC_STATUS_FAILED;
4036   }
4037 
4038   if ((rw_cb.tcb.i93.tlv_type == I93_ICODE_TLV_TYPE_NDEF) &&
4039       (rw_cb.tcb.i93.ndef_length > 0)) {
4040     rw_cb.tcb.i93.rw_offset = rw_cb.tcb.i93.ndef_tlv_start_offset;
4041     rw_cb.tcb.i93.rw_length = 0;
4042 
4043     if (rw_i93_get_next_blocks(rw_cb.tcb.i93.rw_offset) == NFC_STATUS_OK) {
4044       rw_cb.tcb.i93.state = RW_I93_STATE_READ_NDEF;
4045     } else {
4046       return NFC_STATUS_FAILED;
4047     }
4048   } else {
4049     LOG(ERROR) << StringPrintf("%s - No NDEF detected", __func__);
4050     return NFC_STATUS_FAILED;
4051   }
4052 
4053   return NFC_STATUS_OK;
4054 }
4055 
4056 /*******************************************************************************
4057 **
4058 ** Function         RW_I93UpdateNDef
4059 **
4060 ** Description      This function performs NDEF update procedure
4061 **                  Note: RW_I93DetectNDef () must be called before using this
4062 **                        Updating data must not be removed until returning
4063 **                        event
4064 **
4065 **                  The following event will be returned
4066 **                      RW_I93_NDEF_UPDATE_CPLT_EVT for complete
4067 **                      RW_I93_NDEF_UPDATE_FAIL_EVT for failure
4068 **
4069 ** Returns          NFC_STATUS_OK if success
4070 **                  NFC_STATUS_FAILED if I93 is busy or other error
4071 **
4072 *******************************************************************************/
RW_I93UpdateNDef(uint16_t length,uint8_t * p_data)4073 tNFC_STATUS RW_I93UpdateNDef(uint16_t length, uint8_t* p_data) {
4074   uint16_t block_number;
4075 
4076   DLOG_IF(INFO, nfc_debug_enabled)
4077       << StringPrintf("%s - length:%d", __func__, length);
4078 
4079   if (rw_cb.tcb.i93.state != RW_I93_STATE_IDLE) {
4080     LOG(ERROR) << StringPrintf("%s - Unable to start command at state (0x%X)",
4081                                __func__, rw_cb.tcb.i93.state);
4082     return NFC_STATUS_FAILED;
4083   }
4084 
4085   if (rw_cb.tcb.i93.tlv_type == I93_ICODE_TLV_TYPE_NDEF) {
4086     if (rw_cb.tcb.i93.intl_flags & RW_I93_FLAG_READ_ONLY) {
4087       LOG(ERROR) << StringPrintf("%s - NDEF is read-only", __func__);
4088       return NFC_STATUS_FAILED;
4089     }
4090     if (rw_cb.tcb.i93.max_ndef_length < length) {
4091       LOG(ERROR) << StringPrintf(
4092           "%s - data (%d bytes) is more than max NDEF length "
4093           "(%d)",
4094           __func__, length, rw_cb.tcb.i93.max_ndef_length);
4095       return NFC_STATUS_FAILED;
4096     }
4097 
4098     rw_cb.tcb.i93.ndef_length = length;
4099     rw_cb.tcb.i93.p_update_data = p_data;
4100 
4101     /* read length field */
4102     rw_cb.tcb.i93.rw_offset = rw_cb.tcb.i93.ndef_tlv_start_offset + 1;
4103     rw_cb.tcb.i93.rw_length = 0;
4104 
4105     block_number = rw_cb.tcb.i93.rw_offset / rw_cb.tcb.i93.block_size;
4106 
4107     if (rw_i93_send_cmd_read_single_block(block_number, false) ==
4108         NFC_STATUS_OK) {
4109       rw_cb.tcb.i93.state = RW_I93_STATE_UPDATE_NDEF;
4110       rw_cb.tcb.i93.sub_state = RW_I93_SUBSTATE_RESET_LEN;
4111     } else {
4112       return NFC_STATUS_FAILED;
4113     }
4114   } else {
4115     LOG(ERROR) << StringPrintf("%s - No NDEF detected", __func__);
4116     return NFC_STATUS_FAILED;
4117   }
4118 
4119   return NFC_STATUS_OK;
4120 }
4121 
4122 /*******************************************************************************
4123 **
4124 ** Function         RW_I93FormatNDef
4125 **
4126 ** Description      This function performs formatting procedure
4127 **
4128 **                  RW_I93_FORMAT_CPLT_EVT will be returned
4129 **
4130 ** Returns          NFC_STATUS_OK if success
4131 **                  NFC_STATUS_FAILED if busy or other error
4132 **
4133 *******************************************************************************/
RW_I93FormatNDef(void)4134 tNFC_STATUS RW_I93FormatNDef(void) {
4135   tNFC_STATUS status;
4136   tRW_I93_RW_SUBSTATE sub_state;
4137 
4138   DLOG_IF(INFO, nfc_debug_enabled) << __func__;
4139 
4140   if (rw_cb.tcb.i93.state != RW_I93_STATE_IDLE) {
4141     LOG(ERROR) << StringPrintf("Unable to start command at state (0x%X)",
4142                                rw_cb.tcb.i93.state);
4143     return NFC_STATUS_FAILED;
4144   }
4145 
4146   if ((rw_cb.tcb.i93.product_version == RW_I93_TAG_IT_HF_I_STD_CHIP_INLAY) ||
4147       (rw_cb.tcb.i93.product_version == RW_I93_TAG_IT_HF_I_PRO_CHIP_INLAY)) {
4148     /* These don't support GetSystemInformation and GetMultiBlockSecurityStatus
4149      */
4150     rw_cb.tcb.i93.rw_offset = 0;
4151 
4152     /* read blocks with option flag to get block security status */
4153     status = rw_i93_send_cmd_read_single_block(0x0000, true);
4154     sub_state = RW_I93_SUBSTATE_CHECK_READ_ONLY;
4155   } else {
4156     status = rw_i93_send_cmd_inventory(rw_cb.tcb.i93.uid, false, 0x00);
4157     sub_state = RW_I93_SUBSTATE_WAIT_UID;
4158   }
4159 
4160   if (status == NFC_STATUS_OK) {
4161     rw_cb.tcb.i93.state = RW_I93_STATE_FORMAT;
4162     rw_cb.tcb.i93.sub_state = sub_state;
4163     rw_cb.tcb.i93.intl_flags = 0;
4164   }
4165 
4166   return (status);
4167 }
4168 
4169 /*******************************************************************************
4170 **
4171 ** Function         RW_I93SetTagReadOnly
4172 **
4173 ** Description      This function performs NDEF read-only procedure
4174 **                  Note: RW_I93DetectNDef () must be called before using this
4175 **                        Updating data must not be removed until returning
4176 **                        event
4177 **
4178 **                  The RW_I93_SET_TAG_RO_EVT event will be returned.
4179 **
4180 ** Returns          NFC_STATUS_OK if success
4181 **                  NFC_STATUS_FAILED if I93 is busy or other error
4182 **
4183 *******************************************************************************/
RW_I93SetTagReadOnly(void)4184 tNFC_STATUS RW_I93SetTagReadOnly(void) {
4185   uint8_t cc_blk0[4];
4186 
4187   DLOG_IF(INFO, nfc_debug_enabled) << __func__;
4188 
4189   if (rw_cb.tcb.i93.state != RW_I93_STATE_IDLE) {
4190     LOG(ERROR) << StringPrintf("%s - Unable to start command at state (0x%X)",
4191                                __func__, rw_cb.tcb.i93.state);
4192     return NFC_STATUS_FAILED;
4193   }
4194 
4195   if ((rw_cb.tcb.i93.tlv_type == I93_ICODE_TLV_TYPE_NDEF) &&
4196       (rw_cb.tcb.i93.i93_t5t_mode != RW_T5T_CC_READ_MEM_INFO)) {
4197     if (rw_cb.tcb.i93.intl_flags & RW_I93_FLAG_READ_ONLY) {
4198       LOG(ERROR) << StringPrintf("%s - NDEF is already read-only", __func__);
4199       return NFC_STATUS_FAILED;
4200     }
4201 
4202     /* get CC in the first block */
4203     if (rw_i93_send_cmd_read_single_block(0, false) == NFC_STATUS_OK) {
4204       rw_cb.tcb.i93.state = RW_I93_STATE_SET_READ_ONLY;
4205       rw_cb.tcb.i93.sub_state = RW_I93_SUBSTATE_WAIT_CC;
4206     } else {
4207       return NFC_STATUS_FAILED;
4208     }
4209   } else {
4210     if (rw_cb.tcb.i93.i93_t5t_mode == RW_T5T_CC_READ_MEM_INFO) {
4211       memcpy(cc_blk0, rw_cb.tcb.i93.gre_cc_content, 4);
4212 
4213       /* mark CC as read-only */
4214       *(cc_blk0 + 1) |= I93_ICODE_CC_READ_ONLY;
4215 
4216       DLOG_IF(INFO, nfc_debug_enabled) << StringPrintf(
4217           "%s - Set CC1 to RO - cc[0]=0x%02x, cc[1]=0x%02x, "
4218           "cc[2]=0x%02x, cc[3]=0x%02x",
4219           __func__, *cc_blk0, *(cc_blk0 + 1), *(cc_blk0 + 2), *(cc_blk0 + 3));
4220 
4221       if (rw_i93_send_cmd_write_single_block(0, cc_blk0) == NFC_STATUS_OK) {
4222         rw_cb.tcb.i93.state = RW_I93_STATE_SET_READ_ONLY;
4223         rw_cb.tcb.i93.sub_state = RW_I93_SUBSTATE_WAIT_UPDATE_CC;
4224       } else {
4225         rw_i93_handle_error(NFC_STATUS_FAILED);
4226         return NFC_STATUS_FAILED;
4227       }
4228 
4229       return NFC_STATUS_OK;
4230     }
4231     LOG(ERROR) << StringPrintf("%s - No NDEF detected", __func__);
4232     return NFC_STATUS_FAILED;
4233   }
4234 
4235   return NFC_STATUS_OK;
4236 }
4237 
4238 /*****************************************************************************
4239 **
4240 ** Function         RW_I93PresenceCheck
4241 **
4242 ** Description      Check if the tag is still in the field.
4243 **
4244 **                  The RW_I93_PRESENCE_CHECK_EVT w/ status is used to indicate
4245 **                  presence or non-presence.
4246 **
4247 ** Returns          NFC_STATUS_OK, if raw data frame sent
4248 **                  NFC_STATUS_NO_BUFFERS: unable to allocate a buffer for this
4249 **                  operation
4250 **                  NFC_STATUS_FAILED: other error
4251 **
4252 *****************************************************************************/
RW_I93PresenceCheck(void)4253 tNFC_STATUS RW_I93PresenceCheck(void) {
4254   tNFC_STATUS status;
4255   tRW_DATA evt_data;
4256 
4257   DLOG_IF(INFO, nfc_debug_enabled) << __func__;
4258 
4259   if (!rw_cb.p_cback) {
4260     return NFC_STATUS_FAILED;
4261   } else if (rw_cb.tcb.i93.state == RW_I93_STATE_NOT_ACTIVATED) {
4262     evt_data.status = NFC_STATUS_FAILED;
4263     (*rw_cb.p_cback)(RW_I93_PRESENCE_CHECK_EVT, &evt_data);
4264 
4265     return NFC_STATUS_OK;
4266   } else if (rw_cb.tcb.i93.state != RW_I93_STATE_IDLE) {
4267     return NFC_STATUS_BUSY;
4268   } else {
4269     if (rw_cb.tcb.i93.i93_t5t_mode == RW_I93_GET_SYS_INFO_MEM_INFO) {
4270       /* The support of AFI by the VICC is optional, so do not include AFI */
4271       status = rw_i93_send_cmd_inventory(rw_cb.tcb.i93.uid, false, 0x00);
4272     } else {
4273       /* Extended command not expected for presence check */
4274       rw_cb.tcb.i93.intl_flags &= ~RW_I93_FLAG_EXT_COMMANDS;
4275       status = rw_i93_send_cmd_read_single_block(0, false);
4276     }
4277 
4278     if (status == NFC_STATUS_OK) {
4279       /* do not retry during presence check */
4280       rw_cb.tcb.i93.retry_count = RW_MAX_RETRIES;
4281       rw_cb.tcb.i93.state = RW_I93_STATE_PRESENCE_CHECK;
4282     }
4283   }
4284 
4285   return (status);
4286 }
4287 
4288 /*****************************************************************************
4289 **
4290 ** Function         RW_I93SetAddressingMode
4291 **
4292 ** Description      Set if the tag must be addressed with UID or not.
4293 **
4294 **                  The addressing mode (addressed or non-addressed) must be
4295 **                  done at the module initialization prior to the Tag
4296 **                  activation.
4297 **
4298 ** Returns          NFC_STATUS_OK, if mode is stored
4299 **                  NFC_STATUS_FAILED: other error
4300 **
4301 *****************************************************************************/
RW_I93SetAddressingMode(bool mode)4302 tNFC_STATUS RW_I93SetAddressingMode(bool mode) {
4303   DLOG_IF(INFO, nfc_debug_enabled)
4304       << StringPrintf("%s - I93 state:%d", __func__, rw_cb.tcb.i93.state);
4305 
4306   if (rw_cb.tcb.i93.state == RW_I93_STATE_IDLE) {
4307     DLOG_IF(INFO, nfc_debug_enabled)
4308         << StringPrintf("%s - mode:%d", __func__, mode);
4309     if (mode) {
4310       rw_cb.tcb.i93.addr_mode = RW_I93_MODE_ADDRESSED;
4311     } else {
4312       rw_cb.tcb.i93.addr_mode = RW_I93_MODE_NON_ADDRESSED;
4313     }
4314     return NFC_STATUS_OK;
4315   } else {
4316     return NFC_STATUS_FAILED;
4317   }
4318 }
4319 
4320 /*******************************************************************************
4321 **
4322 ** Function         rw_i93_get_state_name
4323 **
4324 ** Description      This function returns the state name.
4325 **
4326 ** NOTE             conditionally compiled to save memory.
4327 **
4328 ** Returns          pointer to the name
4329 **
4330 *******************************************************************************/
rw_i93_get_state_name(uint8_t state)4331 std::string rw_i93_get_state_name(uint8_t state) {
4332   switch (state) {
4333     case RW_I93_STATE_NOT_ACTIVATED:
4334       return "NOT_ACTIVATED";
4335     case RW_I93_STATE_IDLE:
4336       return "IDLE";
4337     case RW_I93_STATE_BUSY:
4338       return "BUSY";
4339     case RW_I93_STATE_DETECT_NDEF:
4340       return "NDEF_DETECTION";
4341     case RW_I93_STATE_READ_NDEF:
4342       return "READ_NDEF";
4343     case RW_I93_STATE_UPDATE_NDEF:
4344       return "UPDATE_NDEF";
4345     case RW_I93_STATE_FORMAT:
4346       return "FORMAT";
4347     case RW_I93_STATE_SET_READ_ONLY:
4348       return "SET_READ_ONLY";
4349     case RW_I93_STATE_PRESENCE_CHECK:
4350       return "PRESENCE_CHECK";
4351     default:
4352       return "???? UNKNOWN STATE";
4353   }
4354 }
4355 
4356 /*******************************************************************************
4357 **
4358 ** Function         rw_i93_get_sub_state_name
4359 **
4360 ** Description      This function returns the sub_state name.
4361 **
4362 ** NOTE             conditionally compiled to save memory.
4363 **
4364 ** Returns          pointer to the name
4365 **
4366 *******************************************************************************/
rw_i93_get_sub_state_name(uint8_t sub_state)4367 std::string rw_i93_get_sub_state_name(uint8_t sub_state) {
4368   switch (sub_state) {
4369     case RW_I93_SUBSTATE_WAIT_UID:
4370       return "WAIT_UID";
4371     case RW_I93_SUBSTATE_WAIT_SYS_INFO:
4372       return "WAIT_SYS_INFO";
4373     case RW_I93_SUBSTATE_WAIT_CC:
4374       return "WAIT_CC";
4375     case RW_I93_SUBSTATE_WAIT_CC_EXT:
4376       return "WAIT_CC_EXT";
4377     case RW_I93_SUBSTATE_SEARCH_NDEF_TLV:
4378       return "SEARCH_NDEF_TLV";
4379     case RW_I93_SUBSTATE_CHECK_LOCK_STATUS:
4380       return "CHECK_LOCK_STATUS";
4381     case RW_I93_SUBSTATE_RESET_LEN:
4382       return "RESET_LEN";
4383     case RW_I93_SUBSTATE_WRITE_NDEF:
4384       return "WRITE_NDEF";
4385     case RW_I93_SUBSTATE_UPDATE_LEN:
4386       return "UPDATE_LEN";
4387     case RW_I93_SUBSTATE_WAIT_RESET_DSFID_AFI:
4388       return "WAIT_RESET_DSFID_AFI";
4389     case RW_I93_SUBSTATE_CHECK_READ_ONLY:
4390       return "CHECK_READ_ONLY";
4391     case RW_I93_SUBSTATE_WRITE_CC_NDEF_TLV:
4392       return "WRITE_CC_NDEF_TLV";
4393     case RW_I93_SUBSTATE_WAIT_UPDATE_CC:
4394       return "WAIT_UPDATE_CC";
4395     case RW_I93_SUBSTATE_LOCK_NDEF_TLV:
4396       return "LOCK_NDEF_TLV";
4397     case RW_I93_SUBSTATE_WAIT_LOCK_CC:
4398       return "WAIT_LOCK_CC";
4399     case RW_I93_SUBSTATE_LOCK_T5T_AREA:
4400       return "LOCK_T5T_AREA";
4401     default:
4402       return "???? UNKNOWN SUBSTATE";
4403   }
4404 }
4405 
4406 /*******************************************************************************
4407 **
4408 ** Function         rw_i93_get_tag_name
4409 **
4410 ** Description      This function returns the tag name.
4411 **
4412 ** NOTE             conditionally compiled to save memory.
4413 **
4414 ** Returns          pointer to the name
4415 **
4416 *******************************************************************************/
rw_i93_get_tag_name(uint8_t product_version)4417 static std::string rw_i93_get_tag_name(uint8_t product_version) {
4418   switch (product_version) {
4419     case RW_I93_ICODE_SLI:
4420       return "SLI/SLIX";
4421     case RW_I93_ICODE_SLI_S:
4422       return "SLI-S/SLIX-S";
4423     case RW_I93_ICODE_SLI_L:
4424       return "SLI-L/SLIX-L";
4425     case RW_I93_TAG_IT_HF_I_PLUS_INLAY:
4426       return "Tag-it HF-I Plus Inlay";
4427     case RW_I93_TAG_IT_HF_I_PLUS_CHIP:
4428       return "Tag-it HF-I Plus Chip";
4429     case RW_I93_TAG_IT_HF_I_STD_CHIP_INLAY:
4430       return "Tag-it HF-I Standard Chip/Inlyas";
4431     case RW_I93_TAG_IT_HF_I_PRO_CHIP_INLAY:
4432       return "Tag-it HF-I Pro Chip/Inlays";
4433     case RW_I93_STM_LRI1K:
4434       return "LRi1K";
4435     case RW_I93_STM_LRI2K:
4436       return "LRi2K";
4437     case RW_I93_STM_LRIS2K:
4438       return "LRiS2K";
4439     case RW_I93_STM_LRIS64K:
4440       return "LRiS64K";
4441     case RW_I93_STM_M24LR64_R:
4442       return "M24LR64";
4443     case RW_I93_STM_M24LR04E_R:
4444       return "M24LR04E";
4445     case RW_I93_STM_M24LR16E_R:
4446       return "M24LR16E";
4447     case RW_I93_STM_M24LR16D_W:
4448       return "M24LR16D-W";
4449     case RW_I93_STM_M24LR64E_R:
4450       return "M24LR64E";
4451     case RW_I93_STM_ST25DV04K:
4452       return "ST25DV04";
4453     case RW_I93_STM_ST25DVHIK:
4454       return "ST25DV";
4455     case RW_I93_ONS_N36RW02:
4456       return ("N36RW02");
4457     case RW_I93_ONS_N24RF04:
4458       return ("N24RF04");
4459     case RW_I93_ONS_N24RF04E:
4460       return ("N24RF04E");
4461     case RW_I93_ONS_N24RF16:
4462       return ("N24RF16");
4463     case RW_I93_ONS_N24RF16E:
4464       return ("N24RF16E");
4465     case RW_I93_ONS_N24RF64:
4466       return ("N24RF64");
4467     case RW_I93_ONS_N24RF64E:
4468       return ("N24RF64E");
4469     case RW_I93_UNKNOWN_PRODUCT:
4470     default:
4471       return "UNKNOWN";
4472   }
4473 }
4474