1 /* 2 * Copyright (C) 2015 The Android Open Source Project 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License. 15 */ 16 #define LOG_TAG "pn54x" 17 18 #ifdef ESE_NFC_SYNCHRONIZATION 19 #include <linux/ese-nfc-sync.h> 20 #endif 21 #include <fcntl.h> 22 #include <sys/ioctl.h> 23 #include <sys/time.h> 24 25 #include <log/log.h> 26 27 #include <phNxpExtns_MifareStd.h> 28 #include <phNxpLog.h> 29 #include <phNxpConfig.h> 30 31 phNxpExtns_Context_t gphNxpExtns_Context; 32 extern phFriNfc_NdefMap_t *NdefMap; 33 extern phNci_mfc_auth_cmd_t gAuthCmdBuf; 34 35 static NFCSTATUS phNxpExtns_ProcessSysMessage (phLibNfc_Message_t *msg); 36 static NFCSTATUS phNxpExtns_SendMsg (phLibNfc_Message_t *sysmsg); 37 38 #ifdef ESE_NFC_SYNCHRONIZATION 39 /* timing calculation structure*/ 40 typedef struct time_cal 41 { 42 struct timeval tv1; 43 struct timeval tv2; 44 } TimeCal; 45 static int fd_ese_nfc_sync; /*file descriptor to hold sync driver handle*/ 46 #endif 47 48 /******************************************************************************* 49 ** 50 ** Function EXTNS_Init 51 ** 52 ** Description This function Initializes Mifare Classic Extns. Allocates 53 ** required memory and initializes the Mifare Classic Vars 54 ** 55 ** Returns NFCSTATUS_SUCCESS if successfully initialized 56 ** NFCSTATUS_FAILED otherwise 57 ** 58 *******************************************************************************/ 59 NFCSTATUS EXTNS_Init (tNFA_DM_CBACK *p_nfa_dm_cback, 60 tNFA_CONN_CBACK *p_nfa_conn_cback) 61 { 62 NFCSTATUS status = NFCSTATUS_FAILED; 63 64 /* reset config cache */ 65 resetNxpConfig (); 66 67 /* Initialize Log level */ 68 phNxpLog_InitializeLogLevel (); 69 70 /* Validate parameters */ 71 if ((!p_nfa_dm_cback) || (!p_nfa_conn_cback)) 72 { 73 NXPLOG_EXTNS_E ("EXTNS_Init(): error null callback"); 74 goto clean_and_return; 75 } 76 77 gphNxpExtns_Context.p_dm_cback = p_nfa_dm_cback; 78 gphNxpExtns_Context.p_conn_cback = p_nfa_conn_cback; 79 80 if (NFCSTATUS_SUCCESS != phNxpExtns_MfcModuleInit ()) 81 { 82 NXPLOG_EXTNS_E ("ERROR: MFC Module Init Failed"); 83 goto clean_and_return; 84 } 85 gphNxpExtns_Context.Extns_status = EXTNS_STATUS_OPEN; 86 87 status = NFCSTATUS_SUCCESS; 88 return status; 89 90 clean_and_return: 91 gphNxpExtns_Context.Extns_status = EXTNS_STATUS_CLOSE; 92 return status; 93 } 94 95 /******************************************************************************* 96 ** 97 ** Function EXTNS_Close 98 ** 99 ** Description This function de-initializes Mifare Classic Extns. 100 ** De-allocates memory 101 ** 102 ** Returns None 103 ** 104 *******************************************************************************/ 105 void EXTNS_Close (void) 106 { 107 gphNxpExtns_Context.Extns_status = EXTNS_STATUS_CLOSE; 108 phNxpExtns_MfcModuleDeInit (); 109 return; 110 } 111 112 /******************************************************************************* 113 ** 114 ** Function EXTNS_MfcCallBack 115 ** 116 ** Description Decodes Mifare Classic Tag Response 117 ** This is called from NFA_SendRaw Callback 118 ** 119 ** Returns: 120 ** NFCSTATUS_SUCCESS if successfully initiated 121 ** NFCSTATUS_FAILED otherwise 122 ** 123 *******************************************************************************/ 124 NFCSTATUS EXTNS_MfcCallBack (uint8_t *buf, uint32_t buflen) 125 { 126 NFCSTATUS status = NFCSTATUS_SUCCESS; 127 128 phLibNfc_Message_t msg; 129 130 msg.eMsgType = PH_NXPEXTNS_RX_DATA; 131 msg.pMsgData = buf; 132 msg.Size = buflen; 133 134 status = phNxpExtns_SendMsg (&msg); 135 if (NFCSTATUS_SUCCESS != status) 136 { 137 NXPLOG_EXTNS_E ("Error Sending msg to Extension Thread"); 138 } 139 return status; 140 } 141 142 /******************************************************************************* 143 ** 144 ** Function EXTNS_MfcCheckNDef 145 ** 146 ** Description Performs NDEF detection for Mifare Classic Tag 147 ** 148 ** Upon successful completion of NDEF detection, a 149 ** NFA_NDEF_DETECT_EVT will be sent, to notify the application 150 ** of the NDEF attributes (NDEF total memory size, current 151 ** size, etc.). 152 ** 153 ** Returns: 154 ** NFCSTATUS_SUCCESS if successfully initiated 155 ** NFCSTATUS_FAILED otherwise 156 ** 157 *******************************************************************************/ 158 NFCSTATUS EXTNS_MfcCheckNDef (void) 159 { 160 NFCSTATUS status = NFCSTATUS_SUCCESS; 161 phLibNfc_Message_t msg; 162 163 msg.eMsgType = PH_NXPEXTNS_MIFARE_CHECK_NDEF; 164 msg.pMsgData = NULL; 165 msg.Size = 0; 166 167 status = phNxpExtns_SendMsg (&msg); 168 if (NFCSTATUS_SUCCESS != status) 169 { 170 NXPLOG_EXTNS_E ("Error Sending msg to Extension Thread"); 171 } 172 173 return status; 174 } 175 176 /******************************************************************************* 177 ** 178 ** Function EXTNS_MfcReadNDef 179 ** 180 ** Description Reads NDEF message from Mifare Classic Tag. 181 ** 182 ** Upon receiving the NDEF message, the message will be sent to 183 ** the handler registered with EXTNS_MfcRegisterNDefTypeHandler. 184 ** 185 ** Returns: 186 ** NFCSTATUS_SUCCESS if successfully initiated 187 ** NFCSTATUS_FAILED otherwise 188 ** 189 *******************************************************************************/ 190 NFCSTATUS EXTNS_MfcReadNDef (void) 191 { 192 NFCSTATUS status = NFCSTATUS_SUCCESS; 193 194 phLibNfc_Message_t msg; 195 196 msg.eMsgType = PH_NXPEXTNS_MIFARE_READ_NDEF; 197 msg.pMsgData = NULL; 198 msg.Size = 0; 199 200 status = phNxpExtns_SendMsg (&msg); 201 if (NFCSTATUS_SUCCESS != status) 202 { 203 NXPLOG_EXTNS_E("Error Sending msg to Extension Thread"); 204 } 205 206 return status; 207 } 208 /******************************************************************************* 209 ** 210 ** Function EXTNS_MfcPresenceCheck 211 ** 212 ** Description Do the check presence for Mifare Classic Tag. 213 ** 214 ** 215 ** Returns: 216 ** NFCSTATUS_SUCCESS if successfully initiated 217 ** NFCSTATUS_FAILED otherwise 218 ** 219 *******************************************************************************/ 220 NFCSTATUS EXTNS_MfcPresenceCheck (void) 221 { 222 NFCSTATUS status = NFCSTATUS_SUCCESS; 223 224 phLibNfc_Message_t msg; 225 226 msg.eMsgType = PH_NXPEXTNS_MIFARE_PRESENCE_CHECK; 227 msg.pMsgData = NULL; 228 msg.Size = 0; 229 230 gAuthCmdBuf.status = NFCSTATUS_FAILED; 231 if (sem_init (&gAuthCmdBuf.semPresenceCheck, 0, 0) == -1) 232 { 233 ALOGE("%s: semaphore creation failed (errno=%d)", __func__, errno); 234 return NFCSTATUS_FAILED; 235 } 236 237 status = phNxpExtns_SendMsg (&msg); 238 if (NFCSTATUS_SUCCESS != status) 239 { 240 NXPLOG_EXTNS_E ("Error Sending msg to Extension Thread"); 241 sem_destroy (&gAuthCmdBuf.semPresenceCheck); 242 } 243 244 return status; 245 } 246 247 /******************************************************************************* 248 ** 249 ** Function EXTNS_MfcSetReadOnly 250 ** 251 ** 252 ** Description: 253 ** Sets tag as read only. 254 ** 255 ** When tag is set as read only, or if an error occurs, the app will be 256 ** notified with NFA_SET_TAG_RO_EVT. 257 ** 258 ** Returns: 259 ** NFCSTATUS_SUCCESS if successfully initiated 260 ** NFCSTATUS_FAILED otherwise 261 ** 262 *******************************************************************************/ 263 NFCSTATUS EXTNS_MfcSetReadOnly (uint8_t *key, uint8_t len) 264 { 265 NFCSTATUS status = NFCSTATUS_SUCCESS; 266 267 phLibNfc_Message_t msg; 268 269 msg.eMsgType = PH_NXPEXTNS_MIFARE_READ_ONLY; 270 msg.pMsgData = key; 271 msg.Size = len; 272 273 status = phNxpExtns_SendMsg (&msg); 274 if (NFCSTATUS_SUCCESS != status) 275 { 276 NXPLOG_EXTNS_E ("Error Sending msg to Extension Thread"); 277 } 278 279 return status; 280 } 281 282 /******************************************************************************* 283 ** 284 ** Function EXTNS_MfcWriteNDef 285 ** 286 ** Description Writes NDEF data to Mifare Classic Tag. 287 ** 288 ** When the entire message has been written, or if an error 289 ** occurs, the app will be notified with NFA_WRITE_CPLT_EVT. 290 ** 291 ** p_data needs to be persistent until NFA_WRITE_CPLT_EVT 292 ** 293 ** Returns: 294 ** NFCSTATUS_SUCCESS if successfully initiated 295 ** NFCSTATUS_FAILED otherwise 296 ** 297 *******************************************************************************/ 298 NFCSTATUS EXTNS_MfcWriteNDef (uint8_t *p_data, uint32_t len) 299 { 300 NFCSTATUS status = NFCSTATUS_SUCCESS; 301 302 phLibNfc_Message_t msg; 303 304 msg.eMsgType = PH_NXPEXTNS_MIFARE_WRITE_NDEF; 305 msg.pMsgData = p_data; 306 msg.Size = len; 307 308 status = phNxpExtns_SendMsg (&msg); 309 if (NFCSTATUS_SUCCESS != status) 310 { 311 NXPLOG_EXTNS_E ("Error Sending msg to Extension Thread"); 312 } 313 314 return status; 315 } 316 317 /***************************************************************************** 318 ** 319 ** Function EXTNS_MfcFormatTag 320 ** 321 ** Description Formats Mifare Classic Tag. 322 ** 323 ** The NFA_RW_FORMAT_CPLT_EVT, status is used to 324 ** indicate if tag is successfully formated or not 325 ** 326 ** Returns 327 ** NFCSTATUS_SUCCESS if successfully initiated 328 ** NFCSTATUS_FAILED otherwise 329 ** 330 *****************************************************************************/ 331 NFCSTATUS EXTNS_MfcFormatTag (uint8_t *key, uint8_t len) 332 { 333 NFCSTATUS status = NFCSTATUS_SUCCESS; 334 335 phLibNfc_Message_t msg; 336 337 msg.eMsgType = PH_NXPEXTNS_MIFARE_FORMAT_NDEF; 338 msg.pMsgData = key; 339 msg.Size = len; 340 341 status = phNxpExtns_SendMsg (&msg); 342 if (NFCSTATUS_SUCCESS != status) 343 { 344 NXPLOG_EXTNS_E ("Error Sending msg to Extension Thread"); 345 } 346 347 return status; 348 } 349 350 /***************************************************************************** 351 ** 352 ** Function EXTNS_MfcDisconnect 353 ** 354 ** Description Disconnects Mifare Classic Tag. 355 ** 356 ** Returns 357 ** NFCSTATUS_SUCCESS if successfully initiated 358 ** NFCSTATUS_FAILED otherwise 359 ** 360 *****************************************************************************/ 361 NFCSTATUS EXTNS_MfcDisconnect (void) 362 { 363 NFCSTATUS status = NFCSTATUS_SUCCESS; 364 365 phLibNfc_Message_t msg; 366 367 msg.eMsgType = PH_NXPEXTNS_DISCONNECT; 368 msg.pMsgData = NULL; 369 msg.Size = 0; 370 371 status = phNxpExtns_SendMsg (&msg); 372 if (NFCSTATUS_SUCCESS != status) 373 { 374 NXPLOG_EXTNS_E ("Error Sending msg to Extension Thread"); 375 } 376 377 return status; 378 } 379 380 /***************************************************************************** 381 ** 382 ** Function EXTNS_MfcActivated 383 ** 384 ** Description Activates Mifare Classic Tag. 385 ** 386 ** Returns 387 ** NFCSTATUS_SUCCESS if successfully initiated 388 ** NFCSTATUS_FAILED otherwise 389 ** 390 *****************************************************************************/ 391 NFCSTATUS EXTNS_MfcActivated (void) 392 { 393 NFCSTATUS status = NFCSTATUS_SUCCESS; 394 phLibNfc_Message_t msg; 395 396 msg.eMsgType = PH_NXPEXTNS_ACTIVATED; 397 msg.pMsgData = NULL; 398 msg.Size = 0; 399 400 status = phNxpExtns_SendMsg (&msg); 401 if (NFCSTATUS_SUCCESS != status) 402 { 403 NXPLOG_EXTNS_E ("Error Sending msg to Extension Thread"); 404 } 405 406 return status; 407 } 408 409 /******************************************************************************* 410 ** 411 ** Function EXTNS_MfcTransceive 412 ** 413 ** Description Sends raw frame to Mifare Classic Tag. 414 ** 415 ** Returns NFCSTATUS_SUCCESS if successfully initiated 416 ** NFCSTATUS_FAILED otherwise 417 ** 418 *******************************************************************************/ 419 NFCSTATUS EXTNS_MfcTransceive (uint8_t *p_data, uint32_t len) 420 { 421 NFCSTATUS status = NFCSTATUS_SUCCESS; 422 423 phLibNfc_Message_t msg; 424 425 msg.eMsgType = PH_NXPEXTNS_MIFARE_TRANSCEIVE; 426 msg.pMsgData = p_data; 427 msg.Size = len; 428 429 status = phNxpExtns_SendMsg (&msg); 430 if (NFCSTATUS_SUCCESS != status) 431 { 432 NXPLOG_EXTNS_E ("Error Sending msg to Extension Thread"); 433 } 434 435 return status; 436 } 437 438 /******************************************************************************* 439 ** 440 ** Function EXTNS_MfcInit 441 ** 442 ** Description This function is used to Init Mifare Classic Extns. 443 ** This function should be called when the tag detected is 444 ** Mifare Classic. 445 ** 446 ** Returns NFCSTATUS_SUCCESS 447 ** 448 *******************************************************************************/ 449 NFCSTATUS EXTNS_MfcInit (tNFA_ACTIVATED activationData) 450 { 451 tNFC_ACTIVATE_DEVT rfDetail = activationData.activate_ntf; 452 453 NdefMap->psRemoteDevInfo->RemoteDevInfo.Iso14443A_Info.Sak = rfDetail.rf_tech_param.param.pa.sel_rsp; 454 NdefMap->psRemoteDevInfo->RemoteDevInfo.Iso14443A_Info.AtqA [0] = rfDetail.rf_tech_param.param.pa.sens_res[0]; 455 NdefMap->psRemoteDevInfo->RemoteDevInfo.Iso14443A_Info.AtqA [1] = rfDetail.rf_tech_param.param.pa.sens_res[1]; 456 457 return NFCSTATUS_SUCCESS; 458 } 459 460 /******************************************************************************* 461 ** 462 ** Function phNxpExtns_ProcessSysMessage 463 ** 464 ** Description Internal function to route the request from JNI and Callback 465 ** from NFA_SendRawFrame to right function 466 ** 467 ** Returns NFCSTATUS_SUCCESS if valid request 468 ** NFCSTATUS_FAILED otherwise 469 ** 470 *******************************************************************************/ 471 static NFCSTATUS phNxpExtns_ProcessSysMessage (phLibNfc_Message_t *msg) 472 { 473 NFCSTATUS status = NFCSTATUS_SUCCESS; 474 475 if (gphNxpExtns_Context.Extns_status == EXTNS_STATUS_CLOSE) 476 { 477 return NFCSTATUS_FAILED; 478 } 479 480 switch (msg->eMsgType) 481 { 482 case PH_NXPEXTNS_RX_DATA: 483 status = Mfc_RecvPacket (msg->pMsgData, msg->Size); 484 break; 485 486 case PH_NXPEXTNS_MIFARE_CHECK_NDEF: 487 pthread_mutex_init (&gAuthCmdBuf.syncmutex, NULL); 488 pthread_mutex_lock (&gAuthCmdBuf.syncmutex); 489 status = Mfc_CheckNdef (); 490 pthread_mutex_unlock (&gAuthCmdBuf.syncmutex); 491 pthread_mutex_destroy (&gAuthCmdBuf.syncmutex); 492 break; 493 494 case PH_NXPEXTNS_MIFARE_READ_NDEF: 495 status = Mfc_ReadNdef (); 496 break; 497 498 case PH_NXPEXTNS_MIFARE_WRITE_NDEF: 499 status = Mfc_WriteNdef (msg->pMsgData, msg->Size); 500 break; 501 502 case PH_NXPEXTNS_MIFARE_FORMAT_NDEF: 503 status = Mfc_FormatNdef (msg->pMsgData, msg->Size); 504 break; 505 506 case PH_NXPEXTNS_DISCONNECT: 507 Mfc_DeactivateCbackSelect (); 508 break; 509 510 case PH_NXPEXTNS_ACTIVATED: 511 Mfc_ActivateCback (); 512 break; 513 514 case PH_NXPEXTNS_MIFARE_TRANSCEIVE: 515 status = Mfc_Transceive (msg->pMsgData, msg->Size); 516 break; 517 518 case PH_NXPEXTNS_MIFARE_READ_ONLY: 519 status = Mfc_SetReadOnly (msg->pMsgData, msg->Size); 520 break; 521 case PH_NXPEXTNS_MIFARE_PRESENCE_CHECK: 522 pthread_mutex_init (&gAuthCmdBuf.syncmutex, NULL); 523 pthread_mutex_lock (&gAuthCmdBuf.syncmutex); 524 status = Mfc_PresenceCheck (); 525 pthread_mutex_unlock (&gAuthCmdBuf.syncmutex); 526 pthread_mutex_destroy (&gAuthCmdBuf.syncmutex); 527 break; 528 default: 529 status = NFCSTATUS_FAILED; 530 NXPLOG_EXTNS_E ("Illegal Command for Extension"); 531 break; 532 } 533 534 return status; 535 } 536 537 /******************************************************************************* 538 ** 539 ** Function phNxpExtns_SendMsg 540 ** 541 ** Description unlocks phNxpExtns_ProcessSysMessage with a valid message 542 ** 543 ** Returns NFCSTATUS_SUCCESS if successfully initiated 544 ** NFCSTATUS_FAILED otherwise 545 ** 546 *******************************************************************************/ 547 static NFCSTATUS phNxpExtns_SendMsg (phLibNfc_Message_t *sysmsg) 548 { 549 NFCSTATUS status = NFCSTATUS_SUCCESS; 550 551 status = phNxpExtns_ProcessSysMessage (sysmsg); 552 553 return status; 554 } 555 556 /******************************************************************************* 557 ** 558 ** Function EXTNS_MfcRegisterNDefTypeHandler 559 ** 560 ** Description This function allows the applications to register for 561 ** specific types of NDEF records. 562 ** 563 ** For records types which were not registered, the record will 564 ** be sent to the default handler. 565 ** 566 ** Returns NFCSTATUS_SUCCESS 567 ** 568 *******************************************************************************/ 569 NFCSTATUS EXTNS_MfcRegisterNDefTypeHandler (tNFA_NDEF_CBACK *ndefHandlerCallback) 570 { 571 572 NFCSTATUS status = NFCSTATUS_FAILED; 573 if (NULL != ndefHandlerCallback) 574 { 575 gphNxpExtns_Context.p_ndef_cback = ndefHandlerCallback; 576 status = NFCSTATUS_SUCCESS; 577 } 578 579 return status; 580 } 581 582 /******************************************************************************* 583 ** Synchronizing Functions ** 584 ** Synchronizes Callback in JNI and MFC Extns ** 585 *******************************************************************************/ 586 587 bool_t EXTNS_GetConnectFlag (void) 588 { 589 return (gphNxpExtns_Context.ExtnsConnect); 590 } 591 592 void EXTNS_SetConnectFlag (bool_t flagval) 593 { 594 gphNxpExtns_Context.ExtnsConnect = flagval; 595 } 596 597 bool_t EXTNS_GetDeactivateFlag (void) 598 { 599 return (gphNxpExtns_Context.ExtnsDeactivate); 600 } 601 602 void EXTNS_SetDeactivateFlag (bool_t flagval) 603 { 604 gphNxpExtns_Context.ExtnsDeactivate = flagval; 605 } 606 607 bool_t EXTNS_GetCallBackFlag (void) 608 { 609 return (gphNxpExtns_Context.ExtnsCallBack); 610 } 611 612 void EXTNS_SetCallBackFlag (bool_t flagval) 613 { 614 gphNxpExtns_Context.ExtnsCallBack = flagval; 615 616 } 617 NFCSTATUS EXTNS_GetPresenceCheckStatus (void) 618 { 619 struct timespec ts; 620 621 clock_gettime (CLOCK_REALTIME, &ts); 622 ts.tv_sec += 0; 623 ts.tv_nsec += 100*1000*1000; // 100 milisec 624 if (ts.tv_nsec >= 1000 * 1000 * 1000) 625 { 626 ts.tv_sec += 1; 627 ts.tv_nsec = ts.tv_nsec - (1000 * 1000 * 1000); 628 } 629 630 if (sem_timedwait (&gAuthCmdBuf.semPresenceCheck, &ts)) 631 { 632 ALOGE("%s: failed to wait (errno=%d)", __func__, errno); 633 sem_destroy (&gAuthCmdBuf.semPresenceCheck); 634 gAuthCmdBuf.auth_sent = false; 635 return NFCSTATUS_FAILED; 636 } 637 if (sem_destroy (&gAuthCmdBuf.semPresenceCheck)) 638 { 639 ALOGE("%s: Failed to destroy check Presence semaphore (errno=%d)", __func__, errno); 640 } 641 return gAuthCmdBuf.status; 642 } 643 644 void MfcPresenceCheckResult (NFCSTATUS status) 645 { 646 gAuthCmdBuf.status = status; 647 EXTNS_SetCallBackFlag (true); 648 sem_post (&gAuthCmdBuf.semPresenceCheck); 649 } 650 void MfcResetPresenceCheckStatus (void) 651 { 652 gAuthCmdBuf.auth_sent = false; 653 } 654 /******************************************************************************* 655 ** 656 ** Function EXTNS_CheckMfcResponse 657 ** 658 ** Description This function is called from JNI Transceive for Mifare 659 ** Classic Tag status interpretation and to send the required 660 ** status to application 661 ** 662 ** Returns NFCSTATUS_SUCCESS 663 ** NFCSTATUS_FAILED 664 ** 665 *******************************************************************************/ 666 NFCSTATUS EXTNS_CheckMfcResponse (uint8_t** sTransceiveData, uint32_t *sTransceiveDataLen) 667 { 668 NFCSTATUS status = NFCSTATUS_SUCCESS; 669 670 if (*sTransceiveDataLen == 3) 671 { 672 if((*sTransceiveData) [0] == 0x10 && (*sTransceiveData) [1] != 0x0A) 673 { 674 NXPLOG_EXTNS_E ("Mifare Error in payload response"); 675 *sTransceiveDataLen = 0x1; 676 *sTransceiveData += 1; 677 return NFCSTATUS_FAILED; 678 } 679 } 680 if ((*sTransceiveData) [0] == 0x40) 681 { 682 *sTransceiveData += 1; 683 *sTransceiveDataLen = 0x01; 684 if((*sTransceiveData) [0] == 0x03) 685 { 686 *sTransceiveDataLen = 0x00; 687 status = NFCSTATUS_FAILED; 688 } 689 } 690 else if ((*sTransceiveData) [0] == 0x10) 691 { 692 *sTransceiveData += 1; 693 *sTransceiveDataLen = 0x10; 694 } 695 696 return status; 697 } 698 699