1 /******************************************************************************
2 *
3 * Copyright (C) 2010-2014 Broadcom Corporation
4 *
5 * Licensed under the Apache License, Version 2.0 (the "License");
6 * you may not use this file except in compliance with the License.
7 * You may obtain a copy of the License at:
8 *
9 * http://www.apache.org/licenses/LICENSE-2.0
10 *
11 * Unless required by applicable law or agreed to in writing, software
12 * distributed under the License is distributed on an "AS IS" BASIS,
13 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14 * See the License for the specific language governing permissions and
15 * limitations under the License.
16 *
17 ******************************************************************************/
18
19 /******************************************************************************
20 *
21 * This file contains the implementation for Type 2 tag in Reader/Writer
22 * mode.
23 *
24 ******************************************************************************/
25 #include <string.h>
26 #include "bt_types.h"
27 #include "nfc_target.h"
28
29 #include "gki.h"
30 #include "nci_hmsgs.h"
31 #include "nfc_api.h"
32 #include "nfc_int.h"
33 #include "rw_api.h"
34 #include "rw_int.h"
35
36 /* Static local functions */
37 static void rw_t2t_proc_data(uint8_t conn_id, tNFC_DATA_CEVT* p_data);
38 static tNFC_STATUS rw_t2t_send_cmd(uint8_t opcode, uint8_t* p_dat);
39 static void rw_t2t_process_error(void);
40 static void rw_t2t_process_frame_error(void);
41 static void rw_t2t_handle_presence_check_rsp(tNFC_STATUS status);
42 static void rw_t2t_resume_op(void);
43
44 #if (BT_TRACE_VERBOSE == TRUE)
45 static char* rw_t2t_get_state_name(uint8_t state);
46 static char* rw_t2t_get_substate_name(uint8_t substate);
47 #endif
48
49 /*******************************************************************************
50 **
51 ** Function rw_t2t_proc_data
52 **
53 ** Description This function handles data evt received from NFC Controller.
54 **
55 ** Returns none
56 **
57 *******************************************************************************/
rw_t2t_proc_data(uint8_t conn_id,tNFC_DATA_CEVT * p_data)58 static void rw_t2t_proc_data(uint8_t conn_id, tNFC_DATA_CEVT* p_data) {
59 tRW_EVENT rw_event = RW_RAW_FRAME_EVT;
60 tRW_T2T_CB* p_t2t = &rw_cb.tcb.t2t;
61 NFC_HDR* p_pkt = p_data->p_data;
62 bool b_notify = true;
63 bool b_release = true;
64 uint8_t* p;
65 tRW_READ_DATA evt_data = {
66 0,
67 };
68 tT2T_CMD_RSP_INFO* p_cmd_rsp_info =
69 (tT2T_CMD_RSP_INFO*)rw_cb.tcb.t2t.p_cmd_rsp_info;
70 tRW_DETECT_NDEF_DATA ndef_data;
71 #if (BT_TRACE_VERBOSE == TRUE)
72 uint8_t begin_state = p_t2t->state;
73 #endif
74
75 if ((p_t2t->state == RW_T2T_STATE_IDLE) || (p_cmd_rsp_info == NULL)) {
76 #if (BT_TRACE_VERBOSE == TRUE)
77 RW_TRACE_DEBUG2("RW T2T Raw Frame: Len [0x%X] Status [%s]", p_pkt->len,
78 NFC_GetStatusName(p_data->status));
79 #else
80 RW_TRACE_DEBUG2("RW T2T Raw Frame: Len [0x%X] Status [0x%X]", p_pkt->len,
81 p_data->status);
82 #endif
83 evt_data.status = p_data->status;
84 evt_data.p_data = p_pkt;
85 (*rw_cb.p_cback)(RW_T2T_RAW_FRAME_EVT, (tRW_DATA*)&evt_data);
86 return;
87 }
88 #if (RW_STATS_INCLUDED == TRUE)
89 /* Update rx stats */
90 rw_main_update_rx_stats(p_pkt->len);
91 #endif
92 /* Stop timer as response is received */
93 nfc_stop_quick_timer(&p_t2t->t2_timer);
94
95 RW_TRACE_EVENT2("RW RECV [%s]:0x%x RSP", t2t_info_to_str(p_cmd_rsp_info),
96 p_cmd_rsp_info->opcode);
97
98 if (((p_pkt->len != p_cmd_rsp_info->rsp_len) &&
99 (p_pkt->len != p_cmd_rsp_info->nack_rsp_len) &&
100 (p_t2t->substate != RW_T2T_SUBSTATE_WAIT_SELECT_SECTOR)) ||
101 (p_t2t->state == RW_T2T_STATE_HALT)) {
102 #if (BT_TRACE_VERBOSE == TRUE)
103 RW_TRACE_ERROR1("T2T Frame error. state=%s ",
104 rw_t2t_get_state_name(p_t2t->state));
105 #else
106 RW_TRACE_ERROR1("T2T Frame error. state=0x%02X command=0x%02X ",
107 p_t2t->state);
108 #endif
109 if (p_t2t->state != RW_T2T_STATE_HALT) {
110 /* Retrasmit the last sent command if retry-count < max retry */
111 rw_t2t_process_frame_error();
112 p_t2t->check_tag_halt = false;
113 }
114 GKI_freebuf(p_pkt);
115 return;
116 }
117 rw_cb.cur_retry = 0;
118
119 /* Assume the data is just the response byte sequence */
120 p = (uint8_t*)(p_pkt + 1) + p_pkt->offset;
121
122 RW_TRACE_EVENT4(
123 "rw_t2t_proc_data State: %u conn_id: %u len: %u data[0]: 0x%02x",
124 p_t2t->state, conn_id, p_pkt->len, *p);
125
126 evt_data.p_data = NULL;
127
128 if (p_t2t->substate == RW_T2T_SUBSTATE_WAIT_SELECT_SECTOR_SUPPORT) {
129 /* The select process happens in two steps */
130 if ((*p & 0x0f) == T2T_RSP_ACK) {
131 if (rw_t2t_sector_change(p_t2t->select_sector) == NFC_STATUS_OK)
132 b_notify = false;
133 else
134 evt_data.status = NFC_STATUS_FAILED;
135 } else {
136 RW_TRACE_EVENT1(
137 "rw_t2t_proc_data - Received NACK response(0x%x) to SEC-SELCT CMD",
138 (*p & 0x0f));
139 evt_data.status = NFC_STATUS_REJECTED;
140 }
141 } else if (p_t2t->substate == RW_T2T_SUBSTATE_WAIT_SELECT_SECTOR) {
142 evt_data.status = NFC_STATUS_FAILED;
143 } else if ((p_pkt->len != p_cmd_rsp_info->rsp_len) ||
144 ((p_cmd_rsp_info->opcode == T2T_CMD_WRITE) &&
145 ((*p & 0x0f) != T2T_RSP_ACK))) {
146 /* Received NACK response */
147 evt_data.p_data = p_pkt;
148 if (p_t2t->state == RW_T2T_STATE_READ) b_release = false;
149
150 RW_TRACE_EVENT1("rw_t2t_proc_data - Received NACK response(0x%x)",
151 (*p & 0x0f));
152
153 if (!p_t2t->check_tag_halt) {
154 /* Just received first NACK. Retry just one time to find if tag went in to
155 * HALT State */
156 b_notify = false;
157 rw_t2t_process_error();
158 /* Assume Tag is in HALT State, untill we get response to retry command */
159 p_t2t->check_tag_halt = true;
160 } else {
161 p_t2t->check_tag_halt = false;
162 /* Got consecutive NACK so tag not really halt after first NACK, but
163 * current operation failed */
164 evt_data.status = NFC_STATUS_FAILED;
165 }
166 } else {
167 /* If the response length indicates positive response or cannot be known
168 * from length then assume success */
169 evt_data.status = NFC_STATUS_OK;
170 p_t2t->check_tag_halt = false;
171
172 /* The response data depends on what the current operation was */
173 switch (p_t2t->state) {
174 case RW_T2T_STATE_CHECK_PRESENCE:
175 b_notify = false;
176 rw_t2t_handle_presence_check_rsp(NFC_STATUS_OK);
177 break;
178
179 case RW_T2T_STATE_READ:
180 evt_data.p_data = p_pkt;
181 b_release = false;
182 if (p_t2t->block_read == 0) {
183 p_t2t->b_read_hdr = true;
184 memcpy(p_t2t->tag_hdr, p, T2T_READ_DATA_LEN);
185 }
186 break;
187
188 case RW_T2T_STATE_WRITE:
189 /* Write operation completed successfully */
190 break;
191
192 default:
193 /* NDEF/other Tlv Operation/Format-Tag/Config Tag as Read only */
194 b_notify = false;
195 rw_t2t_handle_rsp(p);
196 break;
197 }
198 }
199
200 if (b_notify) {
201 rw_event = rw_t2t_info_to_event(p_cmd_rsp_info);
202
203 if (rw_event == RW_T2T_NDEF_DETECT_EVT) {
204 ndef_data.status = evt_data.status;
205 ndef_data.protocol = NFC_PROTOCOL_T2T;
206 ndef_data.flags = RW_NDEF_FL_UNKNOWN;
207 if (p_t2t->substate == RW_T2T_SUBSTATE_WAIT_READ_LOCKS)
208 ndef_data.flags = RW_NDEF_FL_FORMATED;
209 ndef_data.max_size = 0;
210 ndef_data.cur_size = 0;
211 /* Move back to idle state */
212 rw_t2t_handle_op_complete();
213 (*rw_cb.p_cback)(rw_event, (tRW_DATA*)&ndef_data);
214 } else {
215 /* Move back to idle state */
216 rw_t2t_handle_op_complete();
217 (*rw_cb.p_cback)(rw_event, (tRW_DATA*)&evt_data);
218 }
219 }
220
221 if (b_release) GKI_freebuf(p_pkt);
222
223 #if (BT_TRACE_VERBOSE == TRUE)
224 if (begin_state != p_t2t->state) {
225 RW_TRACE_DEBUG2("RW T2T state changed:<%s> -> <%s>",
226 rw_t2t_get_state_name(begin_state),
227 rw_t2t_get_state_name(p_t2t->state));
228 }
229 #endif
230 }
231
232 /*******************************************************************************
233 **
234 ** Function rw_t2t_conn_cback
235 **
236 ** Description This callback function receives events/data from NFCC.
237 **
238 ** Returns none
239 **
240 *******************************************************************************/
rw_t2t_conn_cback(uint8_t conn_id,tNFC_CONN_EVT event,tNFC_CONN * p_data)241 void rw_t2t_conn_cback(uint8_t conn_id, tNFC_CONN_EVT event,
242 tNFC_CONN* p_data) {
243 tRW_T2T_CB* p_t2t = &rw_cb.tcb.t2t;
244 tRW_READ_DATA evt_data;
245
246 RW_TRACE_DEBUG2("rw_t2t_conn_cback: conn_id=%i, evt=%i", conn_id, event);
247 /* Only handle static conn_id */
248 if (conn_id != NFC_RF_CONN_ID) {
249 return;
250 }
251
252 switch (event) {
253 case NFC_CONN_CREATE_CEVT:
254 case NFC_CONN_CLOSE_CEVT:
255 break;
256
257 case NFC_DEACTIVATE_CEVT:
258 #if (RW_STATS_INCLUDED == TRUE)
259 /* Display stats */
260 rw_main_log_stats();
261 #endif
262 /* Stop t2t timer (if started) */
263 nfc_stop_quick_timer(&p_t2t->t2_timer);
264
265 /* Free cmd buf for retransmissions */
266 if (p_t2t->p_cur_cmd_buf) {
267 GKI_freebuf(p_t2t->p_cur_cmd_buf);
268 p_t2t->p_cur_cmd_buf = NULL;
269 }
270 /* Free cmd buf used to hold command before sector change */
271 if (p_t2t->p_sec_cmd_buf) {
272 GKI_freebuf(p_t2t->p_sec_cmd_buf);
273 p_t2t->p_sec_cmd_buf = NULL;
274 }
275
276 p_t2t->state = RW_T2T_STATE_NOT_ACTIVATED;
277 NFC_SetStaticRfCback(NULL);
278 break;
279
280 case NFC_DATA_CEVT:
281 if (p_data != NULL) {
282 if ((p_data->data.status == NFC_STATUS_OK) ||
283 (p_data->data.status == NFC_STATUS_CONTINUE)) {
284 rw_t2t_proc_data(conn_id, &(p_data->data));
285 break;
286 } else if (p_data->data.p_data != NULL) {
287 /* Free the response buffer in case of error response */
288 GKI_freebuf((NFC_HDR*)(p_data->data.p_data));
289 p_data->data.p_data = NULL;
290 }
291 }
292 /* Data event with error status...fall through to NFC_ERROR_CEVT case */
293
294 case NFC_ERROR_CEVT:
295 if ((p_t2t->state == RW_T2T_STATE_NOT_ACTIVATED) ||
296 (p_t2t->state == RW_T2T_STATE_IDLE) ||
297 (p_t2t->state == RW_T2T_STATE_HALT)) {
298 #if (RW_STATS_INCLUDED == TRUE)
299 rw_main_update_trans_error_stats();
300 #endif /* RW_STATS_INCLUDED */
301 if (event == NFC_ERROR_CEVT)
302 evt_data.status = (tNFC_STATUS)(*(uint8_t*)p_data);
303 else if (p_data)
304 evt_data.status = p_data->status;
305 else
306 evt_data.status = NFC_STATUS_FAILED;
307
308 evt_data.p_data = NULL;
309 (*rw_cb.p_cback)(RW_T2T_INTF_ERROR_EVT, (tRW_DATA*)&evt_data);
310 break;
311 }
312 nfc_stop_quick_timer(&p_t2t->t2_timer);
313 #if (RW_STATS_INCLUDED == TRUE)
314 rw_main_update_trans_error_stats();
315 #endif
316 if (p_t2t->state == RW_T2T_STATE_CHECK_PRESENCE) {
317 if (p_t2t->check_tag_halt) {
318 p_t2t->state = RW_T2T_STATE_HALT;
319 rw_t2t_handle_presence_check_rsp(NFC_STATUS_REJECTED);
320 } else {
321 /* Move back to idle state */
322 rw_t2t_handle_presence_check_rsp(NFC_STATUS_FAILED);
323 }
324 } else {
325 rw_t2t_process_error();
326 }
327 break;
328
329 default:
330 break;
331 }
332 }
333
334 /*******************************************************************************
335 **
336 ** Function rw_t2t_send_cmd
337 **
338 ** Description This function composes a Type 2 Tag command and send it via
339 ** NCI to NFCC.
340 **
341 ** Returns NFC_STATUS_OK if the command is successfuly sent to NCI
342 ** otherwise, error status
343 **
344 *******************************************************************************/
rw_t2t_send_cmd(uint8_t opcode,uint8_t * p_dat)345 tNFC_STATUS rw_t2t_send_cmd(uint8_t opcode, uint8_t* p_dat) {
346 tNFC_STATUS status = NFC_STATUS_FAILED;
347 tRW_T2T_CB* p_t2t = &rw_cb.tcb.t2t;
348 const tT2T_CMD_RSP_INFO* p_cmd_rsp_info = t2t_cmd_to_rsp_info(opcode);
349 NFC_HDR* p_data;
350 uint8_t* p;
351
352 if (p_cmd_rsp_info) {
353 /* a valid opcode for RW */
354 p_data = (NFC_HDR*)GKI_getpoolbuf(NFC_RW_POOL_ID);
355 if (p_data) {
356 p_t2t->p_cmd_rsp_info = (tT2T_CMD_RSP_INFO*)p_cmd_rsp_info;
357 p_data->offset = NCI_MSG_OFFSET_SIZE + NCI_DATA_HDR_SIZE;
358 p = (uint8_t*)(p_data + 1) + p_data->offset;
359
360 UINT8_TO_STREAM(p, opcode);
361
362 if (p_dat) {
363 ARRAY_TO_STREAM(p, p_dat, (p_cmd_rsp_info->cmd_len - 1));
364 }
365
366 p_data->len = p_cmd_rsp_info->cmd_len;
367
368 /* Indicate first attempt to send command, back up cmd buffer in case
369 * needed for retransmission */
370 rw_cb.cur_retry = 0;
371 memcpy(p_t2t->p_cur_cmd_buf, p_data,
372 sizeof(NFC_HDR) + p_data->offset + p_data->len);
373
374 #if (RW_STATS_INCLUDED == TRUE)
375 /* Update stats */
376 rw_main_update_tx_stats(p_data->len, false);
377 #endif
378 RW_TRACE_EVENT2("RW SENT [%s]:0x%x CMD", t2t_info_to_str(p_cmd_rsp_info),
379 p_cmd_rsp_info->opcode);
380
381 status = NFC_SendData(NFC_RF_CONN_ID, p_data);
382 if (status == NFC_STATUS_OK) {
383 nfc_start_quick_timer(
384 &p_t2t->t2_timer, NFC_TTYPE_RW_T2T_RESPONSE,
385 (RW_T2T_TOUT_RESP * QUICK_TIMER_TICKS_PER_SEC) / 1000);
386 } else {
387 #if (BT_TRACE_VERBOSE == TRUE)
388 RW_TRACE_ERROR2("T2T NFC Send data failed. state=%s substate=%s ",
389 rw_t2t_get_state_name(p_t2t->state),
390 rw_t2t_get_substate_name(p_t2t->substate));
391 #else
392 RW_TRACE_ERROR2(
393 "T2T NFC Send data failed. state=0x%02X substate=0x%02X ",
394 p_t2t->state, p_t2t->substate);
395 #endif
396 }
397 } else {
398 status = NFC_STATUS_NO_BUFFERS;
399 }
400 }
401 return status;
402 }
403
404 /*******************************************************************************
405 **
406 ** Function rw_t2t_process_timeout
407 **
408 ** Description handles timeout event
409 **
410 ** Returns none
411 **
412 *******************************************************************************/
rw_t2t_process_timeout(TIMER_LIST_ENT * p_tle)413 void rw_t2t_process_timeout(TIMER_LIST_ENT* p_tle) {
414 tRW_READ_DATA evt_data;
415 tRW_T2T_CB* p_t2t = &rw_cb.tcb.t2t;
416
417 if (p_t2t->state == RW_T2T_STATE_CHECK_PRESENCE) {
418 if (p_t2t->check_tag_halt) {
419 p_t2t->state = RW_T2T_STATE_HALT;
420 rw_t2t_handle_presence_check_rsp(NFC_STATUS_REJECTED);
421 } else {
422 /* Move back to idle state */
423 rw_t2t_handle_presence_check_rsp(NFC_STATUS_FAILED);
424 }
425 return;
426 }
427
428 if (p_t2t->substate == RW_T2T_SUBSTATE_WAIT_SELECT_SECTOR) {
429 p_t2t->sector = p_t2t->select_sector;
430 /* Here timeout is an acknowledgment for successfull sector change */
431 if (p_t2t->state == RW_T2T_STATE_SELECT_SECTOR) {
432 /* Notify that select sector op is successfull */
433 rw_t2t_handle_op_complete();
434 evt_data.status = NFC_STATUS_OK;
435 evt_data.p_data = NULL;
436 (*rw_cb.p_cback)(RW_T2T_SELECT_CPLT_EVT, (tRW_DATA*)&evt_data);
437 } else {
438 /* Resume operation from where we stopped before sector change */
439 rw_t2t_resume_op();
440 }
441 } else if (p_t2t->state != RW_T2T_STATE_IDLE) {
442 #if (BT_TRACE_VERBOSE == TRUE)
443 RW_TRACE_ERROR1("T2T timeout. state=%s ",
444 rw_t2t_get_state_name(p_t2t->state));
445 #else
446 RW_TRACE_ERROR1("T2T timeout. state=0x%02X ", p_t2t->state);
447 #endif
448 /* Handle timeout error as no response to the command sent */
449 rw_t2t_process_error();
450 }
451 }
452
453 /*******************************************************************************
454 **
455 ** Function rw_t2t_process_frame_error
456 **
457 ** Description handles frame crc error
458 **
459 ** Returns none
460 **
461 *******************************************************************************/
rw_t2t_process_frame_error(void)462 static void rw_t2t_process_frame_error(void) {
463 #if (RW_STATS_INCLUDED == TRUE)
464 /* Update stats */
465 rw_main_update_crc_error_stats();
466 #endif
467 /* Process the error */
468 rw_t2t_process_error();
469 }
470
471 /*******************************************************************************
472 **
473 ** Function rw_t2t_process_error
474 **
475 ** Description Process error including Timeout, Frame error. This function
476 ** will retry atleast till RW_MAX_RETRIES before give up and
477 ** sending negative notification to upper layer
478 **
479 ** Returns none
480 **
481 *******************************************************************************/
rw_t2t_process_error(void)482 static void rw_t2t_process_error(void) {
483 tRW_READ_DATA evt_data;
484 tRW_EVENT rw_event;
485 NFC_HDR* p_cmd_buf;
486 tRW_T2T_CB* p_t2t = &rw_cb.tcb.t2t;
487 tT2T_CMD_RSP_INFO* p_cmd_rsp_info =
488 (tT2T_CMD_RSP_INFO*)rw_cb.tcb.t2t.p_cmd_rsp_info;
489 tRW_DETECT_NDEF_DATA ndef_data;
490
491 RW_TRACE_DEBUG1("rw_t2t_process_error () State: %u", p_t2t->state);
492
493 /* Retry sending command if retry-count < max */
494 if ((!p_t2t->check_tag_halt) && (rw_cb.cur_retry < RW_MAX_RETRIES)) {
495 /* retry sending the command */
496 rw_cb.cur_retry++;
497
498 RW_TRACE_DEBUG2("T2T retransmission attempt %i of %i", rw_cb.cur_retry,
499 RW_MAX_RETRIES);
500
501 /* allocate a new buffer for message */
502 p_cmd_buf = (NFC_HDR*)GKI_getpoolbuf(NFC_RW_POOL_ID);
503 if (p_cmd_buf != NULL) {
504 memcpy(p_cmd_buf, p_t2t->p_cur_cmd_buf,
505 sizeof(NFC_HDR) + p_t2t->p_cur_cmd_buf->offset +
506 p_t2t->p_cur_cmd_buf->len);
507 #if (RW_STATS_INCLUDED == TRUE)
508 /* Update stats */
509 rw_main_update_tx_stats(p_cmd_buf->len, true);
510 #endif
511 if (NFC_SendData(NFC_RF_CONN_ID, p_cmd_buf) == NFC_STATUS_OK) {
512 /* Start timer for waiting for response */
513 nfc_start_quick_timer(
514 &p_t2t->t2_timer, NFC_TTYPE_RW_T2T_RESPONSE,
515 (RW_T2T_TOUT_RESP * QUICK_TIMER_TICKS_PER_SEC) / 1000);
516
517 return;
518 }
519 }
520 } else {
521 if (p_t2t->check_tag_halt) {
522 RW_TRACE_DEBUG0("T2T Went to HALT State!");
523 } else {
524 RW_TRACE_DEBUG1("T2T maximum retransmission attempts reached (%i)",
525 RW_MAX_RETRIES);
526 }
527 }
528 rw_event = rw_t2t_info_to_event(p_cmd_rsp_info);
529 #if (RW_STATS_INCLUDED == TRUE)
530 /* update failure count */
531 rw_main_update_fail_stats();
532 #endif
533 if (p_t2t->check_tag_halt) {
534 evt_data.status = NFC_STATUS_REJECTED;
535 p_t2t->state = RW_T2T_STATE_HALT;
536 } else {
537 evt_data.status = NFC_STATUS_TIMEOUT;
538 }
539
540 if (rw_event == RW_T2T_NDEF_DETECT_EVT) {
541 ndef_data.status = evt_data.status;
542 ndef_data.protocol = NFC_PROTOCOL_T2T;
543 ndef_data.flags = RW_NDEF_FL_UNKNOWN;
544 if (p_t2t->substate == RW_T2T_SUBSTATE_WAIT_READ_LOCKS)
545 ndef_data.flags = RW_NDEF_FL_FORMATED;
546 ndef_data.max_size = 0;
547 ndef_data.cur_size = 0;
548 /* If not Halt move to idle state */
549 rw_t2t_handle_op_complete();
550
551 (*rw_cb.p_cback)(rw_event, (tRW_DATA*)&ndef_data);
552 } else {
553 evt_data.p_data = NULL;
554 /* If activated and not Halt move to idle state */
555 if (p_t2t->state != RW_T2T_STATE_NOT_ACTIVATED) rw_t2t_handle_op_complete();
556
557 p_t2t->substate = RW_T2T_SUBSTATE_NONE;
558 (*rw_cb.p_cback)(rw_event, (tRW_DATA*)&evt_data);
559 }
560 }
561
562 /*****************************************************************************
563 **
564 ** Function rw_t2t_handle_presence_check_rsp
565 **
566 ** Description Handle response to presence check
567 **
568 ** Returns Nothing
569 **
570 *****************************************************************************/
rw_t2t_handle_presence_check_rsp(tNFC_STATUS status)571 void rw_t2t_handle_presence_check_rsp(tNFC_STATUS status) {
572 tRW_READ_DATA evt_data;
573
574 /* Notify, Tag is present or not */
575 evt_data.status = status;
576 rw_t2t_handle_op_complete();
577
578 (*rw_cb.p_cback)(RW_T2T_PRESENCE_CHECK_EVT, (tRW_DATA*)&evt_data);
579 }
580
581 /*******************************************************************************
582 **
583 ** Function rw_t2t_resume_op
584 **
585 ** Description This function will continue operation after moving to new
586 ** sector
587 **
588 ** Returns tNFC_STATUS
589 **
590 *******************************************************************************/
rw_t2t_resume_op(void)591 static void rw_t2t_resume_op(void) {
592 tRW_T2T_CB* p_t2t = &rw_cb.tcb.t2t;
593 tRW_READ_DATA evt_data;
594 NFC_HDR* p_cmd_buf;
595 tRW_EVENT event;
596 const tT2T_CMD_RSP_INFO* p_cmd_rsp_info =
597 (tT2T_CMD_RSP_INFO*)rw_cb.tcb.t2t.p_cmd_rsp_info;
598 uint8_t* p;
599
600 /* Move back to the substate where we were before changing sector */
601 p_t2t->substate = p_t2t->prev_substate;
602
603 p = (uint8_t*)(p_t2t->p_sec_cmd_buf + 1) + p_t2t->p_sec_cmd_buf->offset;
604 p_cmd_rsp_info = t2t_cmd_to_rsp_info((uint8_t)*p);
605 p_t2t->p_cmd_rsp_info = (tT2T_CMD_RSP_INFO*)p_cmd_rsp_info;
606
607 /* allocate a new buffer for message */
608 p_cmd_buf = (NFC_HDR*)GKI_getpoolbuf(NFC_RW_POOL_ID);
609 if (p_cmd_buf != NULL) {
610 memcpy(p_cmd_buf, p_t2t->p_sec_cmd_buf,
611 sizeof(NFC_HDR) + p_t2t->p_sec_cmd_buf->offset +
612 p_t2t->p_sec_cmd_buf->len);
613 memcpy(p_t2t->p_cur_cmd_buf, p_t2t->p_sec_cmd_buf,
614 sizeof(NFC_HDR) + p_t2t->p_sec_cmd_buf->offset +
615 p_t2t->p_sec_cmd_buf->len);
616
617 #if (RW_STATS_INCLUDED == TRUE)
618 /* Update stats */
619 rw_main_update_tx_stats(p_cmd_buf->len, true);
620 #endif
621 if (NFC_SendData(NFC_RF_CONN_ID, p_cmd_buf) == NFC_STATUS_OK) {
622 /* Start timer for waiting for response */
623 nfc_start_quick_timer(
624 &p_t2t->t2_timer, NFC_TTYPE_RW_T2T_RESPONSE,
625 (RW_T2T_TOUT_RESP * QUICK_TIMER_TICKS_PER_SEC) / 1000);
626 } else {
627 /* failure - could not send buffer */
628 evt_data.p_data = NULL;
629 evt_data.status = NFC_STATUS_FAILED;
630 event = rw_t2t_info_to_event(p_cmd_rsp_info);
631 rw_t2t_handle_op_complete();
632 (*rw_cb.p_cback)(event, (tRW_DATA*)&evt_data);
633 }
634 }
635 }
636
637 /*******************************************************************************
638 **
639 ** Function rw_t2t_sector_change
640 **
641 ** Description This function issues Type 2 Tag SECTOR-SELECT command
642 ** packet 1.
643 **
644 ** Returns tNFC_STATUS
645 **
646 *******************************************************************************/
rw_t2t_sector_change(uint8_t sector)647 tNFC_STATUS rw_t2t_sector_change(uint8_t sector) {
648 tNFC_STATUS status;
649 NFC_HDR* p_data;
650 uint8_t* p;
651 tRW_T2T_CB* p_t2t = &rw_cb.tcb.t2t;
652
653 p_data = (NFC_HDR*)GKI_getpoolbuf(NFC_RW_POOL_ID);
654 if (p_data == NULL) {
655 RW_TRACE_ERROR0("rw_t2t_sector_change - No buffer");
656 return (NFC_STATUS_NO_BUFFERS);
657 }
658
659 p_data->offset = NCI_MSG_OFFSET_SIZE + NCI_DATA_HDR_SIZE;
660 p = (uint8_t*)(p_data + 1) + p_data->offset;
661
662 UINT8_TO_BE_STREAM(p, sector);
663 UINT8_TO_BE_STREAM(p, 0x00);
664 UINT8_TO_BE_STREAM(p, 0x00);
665 UINT8_TO_BE_STREAM(p, 0x00);
666
667 p_data->len = 4;
668
669 status = NFC_SendData(NFC_RF_CONN_ID, p_data);
670 if (status == NFC_STATUS_OK) {
671 /* Passive rsp command and suppose not to get response to this command */
672 p_t2t->p_cmd_rsp_info = NULL;
673 p_t2t->substate = RW_T2T_SUBSTATE_WAIT_SELECT_SECTOR;
674
675 RW_TRACE_EVENT0("rw_t2t_sector_change Sent Second Command");
676 nfc_start_quick_timer(
677 &p_t2t->t2_timer, NFC_TTYPE_RW_T2T_RESPONSE,
678 (RW_T2T_SEC_SEL_TOUT_RESP * QUICK_TIMER_TICKS_PER_SEC) / 1000);
679 } else {
680 RW_TRACE_ERROR1(
681 "rw_t2t_sector_change Send failed at rw_t2t_send_cmd, error: %u",
682 status);
683 }
684
685 return status;
686 }
687
688 /*******************************************************************************
689 **
690 ** Function rw_t2t_read
691 **
692 ** Description This function issues Type 2 Tag READ command for the
693 ** specified block. If the specified block is in different
694 ** sector then it first sends command to move to new sector
695 ** and after the tag moves to new sector it issues the read
696 ** command for the block.
697 **
698 ** Returns tNFC_STATUS
699 **
700 *******************************************************************************/
rw_t2t_read(uint16_t block)701 tNFC_STATUS rw_t2t_read(uint16_t block) {
702 tNFC_STATUS status;
703 uint8_t* p;
704 tRW_T2T_CB* p_t2t = &rw_cb.tcb.t2t;
705 uint8_t sector_byte2[1];
706 uint8_t read_cmd[1];
707
708 read_cmd[0] = block % T2T_BLOCKS_PER_SECTOR;
709 if (p_t2t->sector != block / T2T_BLOCKS_PER_SECTOR) {
710 sector_byte2[0] = 0xFF;
711 /* First Move to new sector before sending Read command */
712 status = rw_t2t_send_cmd(T2T_CMD_SEC_SEL, sector_byte2);
713 if (status == NFC_STATUS_OK) {
714 /* Prepare command that needs to be sent after sector change op is
715 * completed */
716 p_t2t->select_sector = (uint8_t)(block / T2T_BLOCKS_PER_SECTOR);
717 p_t2t->p_sec_cmd_buf->offset = NCI_MSG_OFFSET_SIZE + NCI_DATA_HDR_SIZE;
718
719 p = (uint8_t*)(p_t2t->p_sec_cmd_buf + 1) + p_t2t->p_sec_cmd_buf->offset;
720 UINT8_TO_BE_STREAM(p, T2T_CMD_READ);
721 UINT8_TO_BE_STREAM(p, read_cmd[0]);
722 p_t2t->p_sec_cmd_buf->len = 2;
723 p_t2t->block_read = block;
724
725 /* Backup the current substate to move back to this substate after
726 * changing sector */
727 p_t2t->prev_substate = p_t2t->substate;
728 p_t2t->substate = RW_T2T_SUBSTATE_WAIT_SELECT_SECTOR_SUPPORT;
729 return NFC_STATUS_OK;
730 }
731 return NFC_STATUS_FAILED;
732 }
733
734 /* Send Read command as sector change is not needed */
735 status = rw_t2t_send_cmd(T2T_CMD_READ, (uint8_t*)read_cmd);
736 if (status == NFC_STATUS_OK) {
737 p_t2t->block_read = block;
738 RW_TRACE_EVENT1("rw_t2t_read Sent Command for Block: %u", block);
739 }
740
741 return status;
742 }
743
744 /*******************************************************************************
745 **
746 ** Function rw_t2t_write
747 **
748 ** Description This function issues Type 2 Tag WRITE command for the
749 ** specified block. If the specified block is in different
750 ** sector then it first sends command to move to new sector
751 ** and after the tag moves to new sector it issues the write
752 ** command for the block.
753 **
754 ** Returns tNFC_STATUS
755 **
756 *******************************************************************************/
rw_t2t_write(uint16_t block,uint8_t * p_write_data)757 tNFC_STATUS rw_t2t_write(uint16_t block, uint8_t* p_write_data) {
758 tNFC_STATUS status;
759 uint8_t* p;
760 tRW_T2T_CB* p_t2t = &rw_cb.tcb.t2t;
761 uint8_t write_cmd[T2T_WRITE_DATA_LEN + 1];
762 uint8_t sector_byte2[1];
763
764 p_t2t->block_written = block;
765 write_cmd[0] = (uint8_t)(block % T2T_BLOCKS_PER_SECTOR);
766 memcpy(&write_cmd[1], p_write_data, T2T_WRITE_DATA_LEN);
767
768 if (p_t2t->sector != block / T2T_BLOCKS_PER_SECTOR) {
769 sector_byte2[0] = 0xFF;
770 /* First Move to new sector before sending Write command */
771 status = rw_t2t_send_cmd(T2T_CMD_SEC_SEL, sector_byte2);
772 if (status == NFC_STATUS_OK) {
773 /* Prepare command that needs to be sent after sector change op is
774 * completed */
775 p_t2t->select_sector = (uint8_t)(block / T2T_BLOCKS_PER_SECTOR);
776 p_t2t->p_sec_cmd_buf->offset = NCI_MSG_OFFSET_SIZE + NCI_DATA_HDR_SIZE;
777 p = (uint8_t*)(p_t2t->p_sec_cmd_buf + 1) + p_t2t->p_sec_cmd_buf->offset;
778 UINT8_TO_BE_STREAM(p, T2T_CMD_WRITE);
779 memcpy(p, write_cmd, T2T_WRITE_DATA_LEN + 1);
780 p_t2t->p_sec_cmd_buf->len = 2 + T2T_WRITE_DATA_LEN;
781 p_t2t->block_written = block;
782
783 /* Backup the current substate to move back to this substate after
784 * changing sector */
785 p_t2t->prev_substate = p_t2t->substate;
786 p_t2t->substate = RW_T2T_SUBSTATE_WAIT_SELECT_SECTOR_SUPPORT;
787 return NFC_STATUS_OK;
788 }
789 return NFC_STATUS_FAILED;
790 }
791
792 /* Send Write command as sector change is not needed */
793 status = rw_t2t_send_cmd(T2T_CMD_WRITE, write_cmd);
794 if (status == NFC_STATUS_OK) {
795 RW_TRACE_EVENT1("rw_t2t_write Sent Command for Block: %u", block);
796 }
797
798 return status;
799 }
800
801 /*******************************************************************************
802 **
803 ** Function rw_t2t_select
804 **
805 ** Description This function selects type 2 tag.
806 **
807 ** Returns Tag selection status
808 **
809 *******************************************************************************/
rw_t2t_select(void)810 tNFC_STATUS rw_t2t_select(void) {
811 tRW_T2T_CB* p_t2t = &rw_cb.tcb.t2t;
812
813 p_t2t->state = RW_T2T_STATE_IDLE;
814 p_t2t->ndef_status = T2T_NDEF_NOT_DETECTED;
815
816 /* Alloc cmd buf for retransmissions */
817 if (p_t2t->p_cur_cmd_buf == NULL) {
818 p_t2t->p_cur_cmd_buf = (NFC_HDR*)GKI_getpoolbuf(NFC_RW_POOL_ID);
819 if (p_t2t->p_cur_cmd_buf == NULL) {
820 RW_TRACE_ERROR0(
821 "rw_t2t_select: unable to allocate buffer for retransmission");
822 return (NFC_STATUS_FAILED);
823 }
824 }
825 /* Alloc cmd buf for holding a command untill sector changes */
826 if (p_t2t->p_sec_cmd_buf == NULL) {
827 p_t2t->p_sec_cmd_buf = (NFC_HDR*)GKI_getpoolbuf(NFC_RW_POOL_ID);
828 if (p_t2t->p_sec_cmd_buf == NULL) {
829 RW_TRACE_ERROR0(
830 "rw_t2t_select: unable to allocate buffer used during sector change");
831 return (NFC_STATUS_FAILED);
832 }
833 }
834
835 NFC_SetStaticRfCback(rw_t2t_conn_cback);
836 rw_t2t_handle_op_complete();
837 p_t2t->check_tag_halt = false;
838
839 return NFC_STATUS_OK;
840 }
841
842 /*****************************************************************************
843 **
844 ** Function rw_t2t_handle_op_complete
845 **
846 ** Description Reset to IDLE state
847 **
848 ** Returns Nothing
849 **
850 *****************************************************************************/
rw_t2t_handle_op_complete(void)851 void rw_t2t_handle_op_complete(void) {
852 tRW_T2T_CB* p_t2t = &rw_cb.tcb.t2t;
853
854 if ((p_t2t->state == RW_T2T_STATE_READ_NDEF) ||
855 (p_t2t->state == RW_T2T_STATE_WRITE_NDEF)) {
856 p_t2t->b_read_data = false;
857 }
858
859 if (p_t2t->state != RW_T2T_STATE_HALT) p_t2t->state = RW_T2T_STATE_IDLE;
860 p_t2t->substate = RW_T2T_SUBSTATE_NONE;
861 return;
862 }
863
864 /*****************************************************************************
865 **
866 ** Function RW_T2tPresenceCheck
867 **
868 ** Description
869 ** Check if the tag is still in the field.
870 **
871 ** The RW_T2T_PRESENCE_CHECK_EVT w/ status is used to indicate presence
872 ** or non-presence.
873 **
874 ** Returns
875 ** NFC_STATUS_OK, if raw data frame sent
876 ** NFC_STATUS_NO_BUFFERS: unable to allocate a buffer for this operation
877 ** NFC_STATUS_FAILED: other error
878 **
879 *****************************************************************************/
RW_T2tPresenceCheck(void)880 tNFC_STATUS RW_T2tPresenceCheck(void) {
881 tNFC_STATUS retval = NFC_STATUS_OK;
882 tRW_DATA evt_data;
883 tRW_CB* p_rw_cb = &rw_cb;
884 uint8_t sector_blk = 0; /* block 0 of current sector */
885
886 RW_TRACE_API0("RW_T2tPresenceCheck");
887
888 /* If RW_SelectTagType was not called (no conn_callback) return failure */
889 if (!p_rw_cb->p_cback) {
890 retval = NFC_STATUS_FAILED;
891 }
892 /* If we are not activated, then RW_T2T_PRESENCE_CHECK_EVT status=FAIL */
893 else if (p_rw_cb->tcb.t2t.state == RW_T2T_STATE_NOT_ACTIVATED) {
894 evt_data.status = NFC_STATUS_FAILED;
895 (*p_rw_cb->p_cback)(RW_T2T_PRESENCE_CHECK_EVT, &evt_data);
896 }
897 /* If command is pending, assume tag is still present */
898 else if (p_rw_cb->tcb.t2t.state != RW_T2T_STATE_IDLE) {
899 evt_data.status = NFC_STATUS_OK;
900 (*p_rw_cb->p_cback)(RW_T2T_PRESENCE_CHECK_EVT, &evt_data);
901 } else {
902 /* IDLE state: send a READ command to block 0 of the current sector */
903 retval = rw_t2t_send_cmd(T2T_CMD_READ, §or_blk);
904 if (retval == NFC_STATUS_OK) {
905 p_rw_cb->tcb.t2t.state = RW_T2T_STATE_CHECK_PRESENCE;
906 }
907 }
908
909 return (retval);
910 }
911
912 /*******************************************************************************
913 **
914 ** Function RW_T2tRead
915 **
916 ** Description This function issues the Type 2 Tag READ command. When the
917 ** operation is complete the callback function will be called
918 ** with a RW_T2T_READ_EVT.
919 **
920 ** Returns tNFC_STATUS
921 **
922 *******************************************************************************/
RW_T2tRead(uint16_t block)923 tNFC_STATUS RW_T2tRead(uint16_t block) {
924 tRW_T2T_CB* p_t2t = &rw_cb.tcb.t2t;
925 tNFC_STATUS status;
926
927 if (p_t2t->state != RW_T2T_STATE_IDLE) {
928 RW_TRACE_ERROR1("Error: Type 2 tag not activated or Busy - State: %u",
929 p_t2t->state);
930 return (NFC_STATUS_FAILED);
931 }
932
933 status = rw_t2t_read(block);
934 if (status == NFC_STATUS_OK) {
935 p_t2t->state = RW_T2T_STATE_READ;
936 RW_TRACE_EVENT0("RW_T2tRead Sent Read command");
937 }
938
939 return status;
940 }
941
942 /*******************************************************************************
943 **
944 ** Function RW_T2tWrite
945 **
946 ** Description This function issues the Type 2 Tag WRITE command. When the
947 ** operation is complete the callback function will be called
948 ** with a RW_T2T_WRITE_EVT.
949 **
950 ** p_new_bytes points to the array of 4 bytes to be written
951 **
952 ** Returns tNFC_STATUS
953 **
954 *******************************************************************************/
RW_T2tWrite(uint16_t block,uint8_t * p_write_data)955 tNFC_STATUS RW_T2tWrite(uint16_t block, uint8_t* p_write_data) {
956 tRW_T2T_CB* p_t2t = &rw_cb.tcb.t2t;
957 tNFC_STATUS status;
958
959 if (p_t2t->state != RW_T2T_STATE_IDLE) {
960 RW_TRACE_ERROR1("Error: Type 2 tag not activated or Busy - State: %u",
961 p_t2t->state);
962 return (NFC_STATUS_FAILED);
963 }
964
965 status = rw_t2t_write(block, p_write_data);
966 if (status == NFC_STATUS_OK) {
967 p_t2t->state = RW_T2T_STATE_WRITE;
968 if (block < T2T_FIRST_DATA_BLOCK)
969 p_t2t->b_read_hdr = false;
970 else if (block < (T2T_FIRST_DATA_BLOCK + T2T_READ_BLOCKS))
971 p_t2t->b_read_data = false;
972 RW_TRACE_EVENT0("RW_T2tWrite Sent Write command");
973 }
974
975 return status;
976 }
977
978 /*******************************************************************************
979 **
980 ** Function RW_T2tSectorSelect
981 **
982 ** Description This function issues the Type 2 Tag SECTOR-SELECT command
983 ** packet 1. If a NACK is received as the response, the
984 ** callback function will be called with a
985 ** RW_T2T_SECTOR_SELECT_EVT. If an ACK is received as the
986 ** response, the command packet 2 with the given sector number
987 ** is sent to the peer device. When the response for packet 2
988 ** is received, the callback function will be called with a
989 ** RW_T2T_SECTOR_SELECT_EVT.
990 **
991 ** A sector is 256 contiguous blocks (1024 bytes).
992 **
993 ** Returns tNFC_STATUS
994 **
995 *******************************************************************************/
RW_T2tSectorSelect(uint8_t sector)996 tNFC_STATUS RW_T2tSectorSelect(uint8_t sector) {
997 tNFC_STATUS status;
998 tRW_T2T_CB* p_t2t = &rw_cb.tcb.t2t;
999 uint8_t sector_byte2[1];
1000
1001 if (p_t2t->state != RW_T2T_STATE_IDLE) {
1002 RW_TRACE_ERROR1("Error: Type 2 tag not activated or Busy - State: %u",
1003 p_t2t->state);
1004 return (NFC_STATUS_FAILED);
1005 }
1006
1007 if (sector >= T2T_MAX_SECTOR) {
1008 RW_TRACE_ERROR2(
1009 "RW_T2tSectorSelect - Invalid sector: %u, T2 Max supported sector "
1010 "value: %u",
1011 sector, T2T_MAX_SECTOR - 1);
1012 return (NFC_STATUS_FAILED);
1013 }
1014
1015 sector_byte2[0] = 0xFF;
1016
1017 status = rw_t2t_send_cmd(T2T_CMD_SEC_SEL, sector_byte2);
1018 if (status == NFC_STATUS_OK) {
1019 p_t2t->state = RW_T2T_STATE_SELECT_SECTOR;
1020 p_t2t->select_sector = sector;
1021 p_t2t->substate = RW_T2T_SUBSTATE_WAIT_SELECT_SECTOR_SUPPORT;
1022
1023 RW_TRACE_EVENT0("RW_T2tSectorSelect Sent Sector select first command");
1024 }
1025
1026 return status;
1027 }
1028
1029 #if (BT_TRACE_VERBOSE == TRUE)
1030 /*******************************************************************************
1031 **
1032 ** Function rw_t2t_get_state_name
1033 **
1034 ** Description This function returns the state name.
1035 **
1036 ** NOTE conditionally compiled to save memory.
1037 **
1038 ** Returns pointer to the name
1039 **
1040 *******************************************************************************/
rw_t2t_get_state_name(uint8_t state)1041 static char* rw_t2t_get_state_name(uint8_t state) {
1042 switch (state) {
1043 case RW_T2T_STATE_NOT_ACTIVATED:
1044 return ("NOT_ACTIVATED");
1045 case RW_T2T_STATE_IDLE:
1046 return ("IDLE");
1047 case RW_T2T_STATE_READ:
1048 return ("APP_READ");
1049 case RW_T2T_STATE_WRITE:
1050 return ("APP_WRITE");
1051 case RW_T2T_STATE_SELECT_SECTOR:
1052 return ("SECTOR_SELECT");
1053 case RW_T2T_STATE_DETECT_TLV:
1054 return ("TLV_DETECT");
1055 case RW_T2T_STATE_READ_NDEF:
1056 return ("READ_NDEF");
1057 case RW_T2T_STATE_WRITE_NDEF:
1058 return ("WRITE_NDEF");
1059 case RW_T2T_STATE_SET_TAG_RO:
1060 return ("SET_TAG_RO");
1061 case RW_T2T_STATE_CHECK_PRESENCE:
1062 return ("CHECK_PRESENCE");
1063 default:
1064 return ("???? UNKNOWN STATE");
1065 }
1066 }
1067
1068 /*******************************************************************************
1069 **
1070 ** Function rw_t2t_get_substate_name
1071 **
1072 ** Description This function returns the substate name.
1073 **
1074 ** NOTE conditionally compiled to save memory.
1075 **
1076 ** Returns pointer to the name
1077 **
1078 *******************************************************************************/
rw_t2t_get_substate_name(uint8_t substate)1079 static char* rw_t2t_get_substate_name(uint8_t substate) {
1080 switch (substate) {
1081 case RW_T2T_SUBSTATE_NONE:
1082 return ("RW_T2T_SUBSTATE_NONE");
1083 case RW_T2T_SUBSTATE_WAIT_SELECT_SECTOR_SUPPORT:
1084 return ("RW_T2T_SUBSTATE_WAIT_SELECT_SECTOR_SUPPORT");
1085 case RW_T2T_SUBSTATE_WAIT_SELECT_SECTOR:
1086 return ("RW_T2T_SUBSTATE_WAIT_SELECT_SECTOR");
1087 case RW_T2T_SUBSTATE_WAIT_READ_CC:
1088 return ("RW_T2T_SUBSTATE_WAIT_READ_CC");
1089 case RW_T2T_SUBSTATE_WAIT_TLV_DETECT:
1090 return ("RW_T2T_SUBSTATE_WAIT_TLV_DETECT");
1091 case RW_T2T_SUBSTATE_WAIT_FIND_LEN_FIELD_LEN:
1092 return ("RW_T2T_SUBSTATE_WAIT_FIND_LEN_FIELD_LEN");
1093 case RW_T2T_SUBSTATE_WAIT_READ_TLV_LEN0:
1094 return ("RW_T2T_SUBSTATE_WAIT_READ_TLV_LEN0");
1095 case RW_T2T_SUBSTATE_WAIT_READ_TLV_LEN1:
1096 return ("RW_T2T_SUBSTATE_WAIT_READ_TLV_LEN1");
1097 case RW_T2T_SUBSTATE_WAIT_READ_TLV_VALUE:
1098 return ("RW_T2T_SUBSTATE_WAIT_READ_TLV_VALUE");
1099 case RW_T2T_SUBSTATE_WAIT_READ_LOCKS:
1100 return ("RW_T2T_SUBSTATE_WAIT_READ_LOCKS");
1101 case RW_T2T_SUBSTATE_WAIT_READ_NDEF_FIRST_BLOCK:
1102 return ("RW_T2T_SUBSTATE_WAIT_READ_NDEF_FIRST_BLOCK");
1103 case RW_T2T_SUBSTATE_WAIT_READ_NDEF_LAST_BLOCK:
1104 return ("RW_T2T_SUBSTATE_WAIT_READ_NDEF_LAST_BLOCK");
1105 case RW_T2T_SUBSTATE_WAIT_READ_TERM_TLV_BLOCK:
1106 return ("RW_T2T_SUBSTATE_WAIT_READ_TERM_TLV_BLOCK");
1107 case RW_T2T_SUBSTATE_WAIT_READ_NDEF_NEXT_BLOCK:
1108 return ("RW_T2T_SUBSTATE_WAIT_READ_NDEF_NEXT_BLOCK");
1109 case RW_T2T_SUBSTATE_WAIT_WRITE_NDEF_NEXT_BLOCK:
1110 return ("RW_T2T_SUBSTATE_WAIT_WRITE_NDEF_NEXT_BLOCK");
1111 case RW_T2T_SUBSTATE_WAIT_WRITE_NDEF_LAST_BLOCK:
1112 return ("RW_T2T_SUBSTATE_WAIT_WRITE_NDEF_LAST_BLOCK");
1113 case RW_T2T_SUBSTATE_WAIT_READ_NDEF_LEN_BLOCK:
1114 return ("RW_T2T_SUBSTATE_WAIT_READ_NDEF_LEN_BLOCK");
1115 case RW_T2T_SUBSTATE_WAIT_WRITE_NDEF_LEN_BLOCK:
1116 return ("RW_T2T_SUBSTATE_WAIT_WRITE_NDEF_LEN_BLOCK");
1117 case RW_T2T_SUBSTATE_WAIT_WRITE_NDEF_LEN_NEXT_BLOCK:
1118 return ("RW_T2T_SUBSTATE_WAIT_WRITE_NDEF_LEN_NEXT_BLOCK");
1119 case RW_T2T_SUBSTATE_WAIT_WRITE_TERM_TLV_CMPLT:
1120 return ("RW_T2T_SUBSTATE_WAIT_WRITE_TERM_TLV_CMPLT");
1121 default:
1122 return ("???? UNKNOWN SUBSTATE");
1123 }
1124 }
1125
1126 #endif /* (BT_TRACE_VERBOSE == TRUE) */
1127