• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright 2012-2023 NXP
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 
17 #include <EseAdaptation.h>
18 #include <android-base/file.h>
19 #include <android-base/stringprintf.h>
20 #include <dlfcn.h>
21 #include <log/log.h>
22 #include <phDal4Nfc_messageQueueLib.h>
23 #include <phDnldNfc.h>
24 #include <phNxpConfig.h>
25 #include <phNxpLog.h>
26 #include <phNxpNciHal.h>
27 #include <phNxpNciHal_Adaptation.h>
28 #include <phNxpNciHal_Dnld.h>
29 #include <phNxpNciHal_NfcDepSWPrio.h>
30 #include <phNxpNciHal_ext.h>
31 #include <phTmlNfc.h>
32 #include <sys/stat.h>
33 
34 #include "NfccTransportFactory.h"
35 #include "NxpNfcThreadMutex.h"
36 #include "phNxpNciHal_IoctlOperations.h"
37 #include "phNxpNciHal_PowerTrackerIface.h"
38 #include "phNxpNciHal_ULPDet.h"
39 #include "phNxpNciHal_extOperations.h"
40 #include "phNxpNciHal_nciParser.h"
41 
42 using android::base::StringPrintf;
43 using android::base::WriteStringToFile;
44 
45 /*********************** Global Variables *************************************/
46 #define PN547C2_CLOCK_SETTING
47 #define CORE_RES_STATUS_BYTE 3
48 #define MAX_NXP_HAL_EXTN_BYTES 10
49 #define DEFAULT_MINIMAL_FW_VERSION 0x0110DE
50 
51 bool bEnableMfcExtns = false;
52 bool bEnableMfcReader = false;
53 bool bDisableLegacyMfcExtns = true;
54 
55 /* Processing of ISO 15693 EOF */
56 extern uint8_t icode_send_eof;
57 extern uint8_t icode_detected;
58 static uint8_t cmd_icode_eof[] = {0x00, 0x00, 0x00};
59 static const char* rf_block_num[] = {
60     "1",  "2",  "3",  "4",  "5",  "6",  "7",  "8",  "9",  "10", "11",
61     "12", "13", "14", "15", "16", "17", "18", "19", "20", "21", "22",
62     "23", "24", "25", "26", "27", "28", "29", "30", NULL};
63 const char* rf_block_name = "NXP_RF_CONF_BLK_";
64 static uint8_t read_failed_disable_nfc = false;
65 /* FW download success flag */
66 static uint8_t fw_download_success = 0;
67 static uint8_t config_access = false;
68 static uint8_t config_success = true;
69 static NfcHalThreadMutex sHalFnLock;
70 
71 /* NCI HAL Control structure */
72 phNxpNciHal_Control_t nxpncihal_ctrl;
73 
74 /* NXP Poll Profile structure */
75 phNxpNciProfile_Control_t nxpprofile_ctrl;
76 
77 /* TML Context */
78 extern phTmlNfc_Context_t* gpphTmlNfc_Context;
79 extern spTransport gpTransportObj;
80 
81 extern void phTmlNfc_set_fragmentation_enabled(
82     phTmlNfc_i2cfragmentation_t result);
83 
84 extern NFCSTATUS phNxpNciHal_ext_send_sram_config_to_flash();
85 extern NFCSTATUS phNxpNciHal_enableDefaultUICC2SWPline(uint8_t uicc2_sel);
86 extern void phNxpNciHal_conf_nfc_forum_mode();
87 extern void phNxpNciHal_prop_conf_lpcd(bool enableLPCD);
88 extern void phNxpNciHal_prop_conf_rssi();
89 
90 nfc_stack_callback_t* p_nfc_stack_cback_backup;
91 phNxpNci_getCfg_info_t* mGetCfg_info = NULL;
92 bool_t gParserCreated = FALSE;
93 /* global variable to get FW version from NCI response or dl get version
94  * response*/
95 uint32_t wFwVerRsp;
96 EseAdaptation* gpEseAdapt = NULL;
97 #ifdef NXP_BOOTTIME_UPDATE
98 ese_update_state_t ese_update = ESE_UPDATE_COMPLETED;
99 #endif
100 /* External global variable to get FW version */
101 extern uint16_t wFwVer;
102 extern uint8_t gRecFWDwnld;
103 static uint8_t gRecFwRetryCount;  // variable to hold recovery FW retry count
104 static uint8_t write_unlocked_status = NFCSTATUS_SUCCESS;
105 uint8_t wFwUpdateReq = false;
106 uint8_t wRfUpdateReq = false;
107 uint32_t timeoutTimerId = 0;
108 #ifndef FW_DWNLD_FLAG
109 uint8_t fw_dwnld_flag = false;
110 #endif
111 bool nfc_debug_enabled = true;
112 PowerTrackerHandle gPowerTrackerHandle;
113 
114 /*  Used to send Callback Transceive data during Mifare Write.
115  *  If this flag is enabled, no need to send response to Upper layer */
116 bool sendRspToUpperLayer = true;
117 
118 phNxpNciHal_Sem_t config_data;
119 
120 phNxpNciClock_t phNxpNciClock = {0, {0}, false};
121 
122 phNxpNciRfSetting_t phNxpNciRfSet = {false, {0}};
123 
124 phNxpNciMwEepromArea_t phNxpNciMwEepromArea = {false, {0}};
125 
126 volatile bool_t gsIsFirstHalMinOpen = true;
127 volatile bool_t gsIsFwRecoveryRequired = false;
128 
129 void* RfFwRegionDnld_handle = NULL;
130 fpVerInfoStoreInEeprom_t fpVerInfoStoreInEeprom = NULL;
131 fpRegRfFwDndl_t fpRegRfFwDndl = NULL;
132 fpPropConfCover_t fpPropConfCover = NULL;
133 void* phNxpNciHal_client_thread(void* arg);
134 /**************** local methods used in this file only ************************/
135 static void phNxpNciHal_open_complete(NFCSTATUS status);
136 static void phNxpNciHal_MinOpen_complete(NFCSTATUS status);
137 static void phNxpNciHal_write_complete(void* pContext,
138                                        phTmlNfc_TransactInfo_t* pInfo);
139 static void phNxpNciHal_read_complete(void* pContext,
140                                       phTmlNfc_TransactInfo_t* pInfo);
141 static void phNxpNciHal_close_complete(NFCSTATUS status);
142 static void phNxpNciHal_core_initialized_complete(NFCSTATUS status);
143 static void phNxpNciHal_power_cycle_complete(NFCSTATUS status);
144 static void phNxpNciHal_kill_client_thread(
145     phNxpNciHal_Control_t* p_nxpncihal_ctrl);
146 static void phNxpNciHal_nfccClockCfgRead(void);
147 static NFCSTATUS phNxpNciHal_nfccClockCfgApply(void);
148 static void phNxpNciHal_hci_network_reset(void);
149 static NFCSTATUS phNxpNciHal_do_swp_session_reset(void);
150 static void phNxpNciHal_print_res_status(uint8_t* p_rx_data, uint16_t* p_len);
151 static void phNxpNciHal_enable_i2c_fragmentation();
152 static NFCSTATUS phNxpNciHal_get_mw_eeprom(void);
153 static NFCSTATUS phNxpNciHal_set_mw_eeprom(void);
154 static void phNxpNciHal_configNciParser(bool enable);
155 static void phNxpNciHal_gpio_restore(phNxpNciHal_GpioInfoState state);
156 static void phNxpNciHal_initialize_debug_enabled_flag();
157 static void phNxpNciHal_initialize_mifare_flag();
158 static NFCSTATUS phNxpNciHalRFConfigCmdRecSequence();
159 static NFCSTATUS phNxpNciHal_CheckRFCmdRespStatus();
160 static void phNxpNciHal_UpdateFwStatus(HalNfcFwUpdateStatus fwStatus);
161 static NFCSTATUS phNxpNciHal_resetDefaultSettings(uint8_t fw_update_req,
162                                                   bool keep_config);
163 static NFCSTATUS phNxpNciHal_force_fw_download(uint8_t seq_handler_offset = 0,
164                                                bool bIsNfccDlState = false);
165 static int phNxpNciHal_MinOpen_Clean(char* nfc_dev_node);
166 static void phNxpNciHal_CheckAndHandleFwTearDown(void);
167 static NFCSTATUS phNxpNciHal_getChipInfoInFwDnldMode(
168     bool bIsVenResetReqd = false);
169 static uint8_t phNxpNciHal_getSessionInfoInFwDnldMode();
170 static NFCSTATUS phNxpNciHal_dlResetInFwDnldMode();
171 static NFCSTATUS phNxpNciHal_enableTmlRead();
172 
173 /******************************************************************************
174  * Function         onLoadLibrary
175  *
176  * Description      This function as marked with attribute constructor causes
177  *                  the function to be called automatically before execution
178  *                  enters main (). It is useful for initializing execution
179  *                  context  that will be used implicitly during the execution
180  *                  of the program like loading another dynamic library.
181  * PARAM            None
182  * Returns          void
183  *
184  ******************************************************************************/
onLoadLibrary(void)185 static __attribute__((constructor)) void onLoadLibrary(void) {
186   NXPLOG_NCIHAL_D("Initializing power tracker");
187   phNxpNciHal_PowerTrackerInit(&gPowerTrackerHandle);
188 }
189 
190 /******************************************************************************
191  * Function         onUnloadLibrary
192  *
193  * Description      This function as marked with attribute destructor causes
194  *                  the function to be called automatically after execution
195  *                  main () has completed. It is useful for de-initializing
196  *                  execution context  that were be used implicitly during the
197  *                  execution of the program like unloading another dynamic
198  *                  library.
199  * PARAM            None
200  * Returns          void
201  *
202  ******************************************************************************/
onUnloadLibrary(void)203 static __attribute__((destructor)) void onUnloadLibrary(void) {
204   NXPLOG_NCIHAL_D("De-initializing power tracker");
205   phNxpNciHal_PowerTrackerDeinit(&gPowerTrackerHandle);
206 }
207 
208 /******************************************************************************
209  * Function         phNxpNciHal_initialize_debug_enabled_flag
210  *
211  * Description      This function gets the value for nfc_debug_enabled
212  *
213  * Returns          void
214  *
215  ******************************************************************************/
phNxpNciHal_initialize_debug_enabled_flag()216 static void phNxpNciHal_initialize_debug_enabled_flag() {
217   unsigned long num = 0;
218   char valueStr[PROPERTY_VALUE_MAX] = {0};
219   if (GetNxpNumValue(NAME_NFC_DEBUG_ENABLED, &num, sizeof(num))) {
220     nfc_debug_enabled = (num == 0) ? false : true;
221   }
222 
223   int len = property_get("nfc.debug_enabled", valueStr, "");
224   if (len > 0) {
225     // let Android property override .conf variable
226     unsigned debug_enabled = 0;
227     int ret = sscanf(valueStr, "%u", &debug_enabled);
228     if (ret) nfc_debug_enabled = (debug_enabled == 0) ? false : true;
229   }
230   NXPLOG_NCIHAL_D("nfc_debug_enabled : %d", nfc_debug_enabled);
231 }
232 
233 /******************************************************************************
234  * Function         phNxpNciHal_client_thread
235  *
236  * Description      This function is a thread handler which handles all TML and
237  *                  NCI messages.
238  *
239  * Returns          void
240  *
241  ******************************************************************************/
phNxpNciHal_client_thread(void * arg)242 void* phNxpNciHal_client_thread(void* arg) {
243   phNxpNciHal_Control_t* p_nxpncihal_ctrl = (phNxpNciHal_Control_t*)arg;
244   phLibNfc_Message_t msg;
245 
246   NXPLOG_NCIHAL_D("thread started");
247 
248   p_nxpncihal_ctrl->thread_running = 1;
249 
250   while (p_nxpncihal_ctrl->thread_running == 1) {
251     /* Fetch next message from the NFC stack message queue */
252     if (phDal4Nfc_msgrcv(p_nxpncihal_ctrl->gDrvCfg.nClientId, &msg, 0, 0) ==
253         -1) {
254       NXPLOG_NCIHAL_E("NFC client received bad message");
255       continue;
256     }
257 
258     if (p_nxpncihal_ctrl->thread_running == 0) {
259       break;
260     }
261 
262     switch (msg.eMsgType) {
263       case PH_LIBNFC_DEFERREDCALL_MSG: {
264         phLibNfc_DeferredCall_t* deferCall =
265             (phLibNfc_DeferredCall_t*)(msg.pMsgData);
266 
267         REENTRANCE_LOCK();
268         deferCall->pCallback(deferCall->pParameter);
269         REENTRANCE_UNLOCK();
270 
271         break;
272       }
273 
274       case NCI_HAL_OPEN_CPLT_MSG: {
275         REENTRANCE_LOCK();
276         if (nxpncihal_ctrl.p_nfc_stack_cback != NULL) {
277           /* Send the event */
278           (*nxpncihal_ctrl.p_nfc_stack_cback)(HAL_NFC_OPEN_CPLT_EVT,
279                                               HAL_NFC_STATUS_OK);
280         }
281         REENTRANCE_UNLOCK();
282         break;
283       }
284 
285       case NCI_HAL_CLOSE_CPLT_MSG: {
286         REENTRANCE_LOCK();
287         if (nxpncihal_ctrl.p_nfc_stack_cback != NULL) {
288           /* Send the event */
289           (*nxpncihal_ctrl.p_nfc_stack_cback)(HAL_NFC_CLOSE_CPLT_EVT,
290                                               HAL_NFC_STATUS_OK);
291         }
292         phNxpNciHal_kill_client_thread(&nxpncihal_ctrl);
293         REENTRANCE_UNLOCK();
294         break;
295       }
296 
297       case NCI_HAL_POST_INIT_CPLT_MSG: {
298         REENTRANCE_LOCK();
299         if (nxpncihal_ctrl.p_nfc_stack_cback != NULL) {
300           /* Send the event */
301           (*nxpncihal_ctrl.p_nfc_stack_cback)(HAL_NFC_POST_INIT_CPLT_EVT,
302                                               HAL_NFC_STATUS_OK);
303         }
304         REENTRANCE_UNLOCK();
305         break;
306       }
307 
308       case NCI_HAL_PRE_DISCOVER_CPLT_MSG: {
309         REENTRANCE_LOCK();
310         if (nxpncihal_ctrl.p_nfc_stack_cback != NULL) {
311           /* Send the event */
312           (*nxpncihal_ctrl.p_nfc_stack_cback)(HAL_NFC_PRE_DISCOVER_CPLT_EVT,
313                                               HAL_NFC_STATUS_OK);
314         }
315         REENTRANCE_UNLOCK();
316         break;
317       }
318 
319       case NCI_HAL_HCI_NETWORK_RESET_MSG: {
320         REENTRANCE_LOCK();
321         if (nxpncihal_ctrl.p_nfc_stack_cback != NULL) {
322           /* Send the event */
323           (*nxpncihal_ctrl.p_nfc_stack_cback)(
324               (uint32_t)HAL_HCI_NETWORK_RESET_EVT, HAL_NFC_STATUS_OK);
325         }
326         REENTRANCE_UNLOCK();
327         break;
328       }
329 
330       case NCI_HAL_ERROR_MSG: {
331         REENTRANCE_LOCK();
332         if (nxpncihal_ctrl.p_nfc_stack_cback != NULL) {
333           /* Send the event */
334           (*nxpncihal_ctrl.p_nfc_stack_cback)(HAL_NFC_ERROR_EVT,
335                                               HAL_NFC_STATUS_FAILED);
336         }
337         REENTRANCE_UNLOCK();
338         break;
339       }
340 
341       case NCI_HAL_RX_MSG: {
342         REENTRANCE_LOCK();
343         if (nxpncihal_ctrl.p_nfc_stack_data_cback != NULL) {
344           (*nxpncihal_ctrl.p_nfc_stack_data_cback)(nxpncihal_ctrl.rsp_len,
345                                                    nxpncihal_ctrl.p_rsp_data);
346         }
347         REENTRANCE_UNLOCK();
348         break;
349       }
350       case HAL_NFC_FW_UPDATE_STATUS_EVT: {
351         REENTRANCE_LOCK();
352         if (nxpncihal_ctrl.p_nfc_stack_cback != NULL) {
353           /* Send the event */
354           (*nxpncihal_ctrl.p_nfc_stack_cback)(msg.eMsgType,
355                                               *((uint8_t*)msg.pMsgData));
356         }
357         REENTRANCE_UNLOCK();
358         break;
359       }
360     }
361   }
362 
363   NXPLOG_NCIHAL_D("NxpNciHal thread stopped");
364 
365   return NULL;
366 }
367 
368 /******************************************************************************
369  * Function         phNxpNciHal_kill_client_thread
370  *
371  * Description      This function safely kill the client thread and clean all
372  *                  resources.
373  *
374  * Returns          void.
375  *
376  ******************************************************************************/
phNxpNciHal_kill_client_thread(phNxpNciHal_Control_t * p_nxpncihal_ctrl)377 static void phNxpNciHal_kill_client_thread(
378     phNxpNciHal_Control_t* p_nxpncihal_ctrl) {
379   NXPLOG_NCIHAL_D("Terminating phNxpNciHal client thread...");
380 
381   p_nxpncihal_ctrl->p_nfc_stack_cback = NULL;
382   p_nxpncihal_ctrl->p_nfc_stack_data_cback = NULL;
383   p_nxpncihal_ctrl->thread_running = 0;
384 
385   return;
386 }
387 /******************************************************************************
388  * Function         phNxpNciHal_CheckIntegrityRecovery
389  *
390  * Description     This function to enter in recovery if FW download fails with
391  *                 check integrity.
392  *
393  * Returns         NFCSTATUS
394  *
395  ******************************************************************************/
phNxpNciHal_CheckIntegrityRecovery()396 static NFCSTATUS phNxpNciHal_CheckIntegrityRecovery() {
397   NFCSTATUS status = NFCSTATUS_FAILED;
398   if (phNxpNciHal_nfcc_core_reset_init(false) == NFCSTATUS_SUCCESS) {
399     status = phNxpNciHal_fw_download();
400   } else {
401     status = NFCSTATUS_FW_CHECK_INTEGRITY_FAILED;
402   }
403   return status;
404 }
405 /******************************************************************************
406  * Function         phNxpNciHal_force_fw_download
407  *
408  * Description     This function, based on the offset provided, will trigger
409  *                 Secure FW download sequence.
410  *                 It will retry the FW download in case the Check Integrity
411  *                 has been failed.
412  *
413  * Parameters      Offset by which the FW dnld Seq handler shall be triggered.
414  *                 e.g. if we want to send only the Check Integrity command,
415  *                 then the offset shall be 7.
416  *                 bIsNfccDlState : Indicates if current FW State is FW
417  *                 Download/NCI.
418  *
419  * Returns         SUCCESS if FW download is successful else FAIL.
420  *
421  ******************************************************************************/
phNxpNciHal_force_fw_download(uint8_t seq_handler_offset,bool bIsNfccDlState)422 static NFCSTATUS phNxpNciHal_force_fw_download(uint8_t seq_handler_offset,
423                                                bool bIsNfccDlState) {
424   NFCSTATUS wConfigStatus = NFCSTATUS_SUCCESS;
425   NFCSTATUS status = NFCSTATUS_SUCCESS;
426   /*Get FW version from device*/
427   for (int retry = 1; retry >= 0; retry--) {
428     if (phDnldNfc_InitImgInfo() == NFCSTATUS_SUCCESS) {
429       break;
430     } else {
431       phDnldNfc_ReSetHwDevHandle();
432       NXPLOG_NCIHAL_E("Image information extraction Failed!!");
433       if (!retry) return NFCSTATUS_FAILED;
434     }
435   }
436 
437   NXPLOG_NCIHAL_D("FW version for FW file = 0x%x", wFwVer);
438   NXPLOG_NCIHAL_D("FW version from device = 0x%x", wFwVerRsp);
439   if (wFwVerRsp == 0) {
440     status = phNxpNciHal_getChipInfoInFwDnldMode(true);
441     if (status != NFCSTATUS_SUCCESS) {
442       NXPLOG_NCIHAL_E("phNxpNciHal_getChipInfoInFwDnldMode Failed");
443     }
444     bIsNfccDlState = true;
445   }
446   if (NFCSTATUS_SUCCESS == phNxpNciHal_CheckValidFwVersion()) {
447     NXPLOG_NCIHAL_D("FW update required");
448     nxpncihal_ctrl.phNxpNciGpioInfo.state = GPIO_UNKNOWN;
449     if (IS_CHIP_TYPE_L(sn100u)) phNxpNciHal_gpio_restore(GPIO_STORE);
450     fw_download_success = 0;
451     /*We are expecting NFC to be either in NFC or in the FW Download state*/
452     status = phNxpNciHal_fw_download(seq_handler_offset, bIsNfccDlState);
453     if (status == NFCSTATUS_FW_CHECK_INTEGRITY_FAILED) {
454       status = phNxpNciHal_CheckIntegrityRecovery();
455     }
456     property_set("nfc.fw.downloadmode_force", "0");
457     if (status == NFCSTATUS_SUCCESS) {
458       wConfigStatus = NFCSTATUS_SUCCESS;
459       fw_download_success = TRUE;
460     } else if (status == NFCSTATUS_FW_CHECK_INTEGRITY_FAILED ||
461                (phNxpNciHal_fw_mw_ver_check() != NFCSTATUS_SUCCESS)) {
462       phOsalNfc_Timer_Cleanup();
463       phTmlNfc_Shutdown_CleanUp();
464       return NFCSTATUS_CMD_ABORTED;
465     }
466 
467     status = phNxpNciHal_nfcc_core_reset_init();
468     if (status == NFCSTATUS_SUCCESS && IS_CHIP_TYPE_L(sn100u)) {
469       if (status == NFCSTATUS_SUCCESS) {
470         phNxpNciHal_gpio_restore(GPIO_RESTORE);
471       } else {
472         NXPLOG_NCIHAL_E("Failed to restore GPIO values!!!\n");
473       }
474     }
475   }
476   return wConfigStatus;
477 }
478 
479 /******************************************************************************
480  * Function         phNxpNciHal_fw_download
481  *
482  * Description      This function download the PN54X secure firmware to IC. If
483  *                  firmware version in Android filesystem and firmware in the
484  *                  IC is same then firmware download will return with success
485  *                  without downloading the firmware.
486  *
487  * Returns          NFCSTATUS_SUCCESS if firmware download successful
488  *                  NFCSTATUS_FAILED in case of failure
489  *
490  ******************************************************************************/
phNxpNciHal_fw_download(uint8_t seq_handler_offset,bool bIsNfccDlState)491 NFCSTATUS phNxpNciHal_fw_download(uint8_t seq_handler_offset,
492                                   bool bIsNfccDlState) {
493   NFCSTATUS status = NFCSTATUS_SUCCESS;
494   phNxpNciHal_UpdateFwStatus(HAL_NFC_FW_UPDATE_START);
495   phNxpNciHal_nfccClockCfgRead();
496 
497   if (!bIsNfccDlState) {
498     status = phNxpNciHal_write_fw_dw_status(TRUE);
499     if (status != NFCSTATUS_SUCCESS) {
500       NXPLOG_NCIHAL_E("%s: NXP Set FW DW Flag failed", __FUNCTION__);
501     }
502 
503     NXPLOG_NCIHAL_D("nfcFL.nfccFL._NFCC_DWNLD_MODE %x\n",
504                     nfcFL.nfccFL._NFCC_DWNLD_MODE);
505 
506     if (IS_CHIP_TYPE_GE(sn100u)) {
507       uint8_t ven_cfg_low_cmd[] = {0x20, 0x02, 0x05, 0x01,
508                                    0xA0, 0x07, 0x01, 0x00};
509       status =
510           phNxpNciHal_send_ext_cmd(sizeof(ven_cfg_low_cmd), ven_cfg_low_cmd);
511       if (status != NFCSTATUS_SUCCESS) {
512         NXPLOG_NCIHAL_E("Failed to set VEN_CFG to low \n");
513       }
514     }
515     /*Save UICC params */
516     status = phNxpNciHal_save_uicc_params();
517     if (status != NFCSTATUS_SUCCESS) {
518       NXPLOG_NCIHAL_E("Failed to save UICC params \n");
519     }
520 
521     status = phTmlNfc_IoCtl(phTmlNfc_e_EnableDownloadMode);
522     if (NFCSTATUS_SUCCESS != status) {
523       phTmlNfc_EnableFwDnldMode(false);
524       phNxpNciHal_UpdateFwStatus(HAL_NFC_FW_UPDATE_FAILED);
525       return NFCSTATUS_FAILED;
526     }
527   }
528 
529   /* Make sure read thread is pending before updating phTmlNfc_EnableFwDnldMode
530    * to true*/
531   NFCSTATUS readStatus = phNxpNciHal_enableTmlRead();
532   if (readStatus != PHNFCSTVAL(CID_NFC_TML, NFCSTATUS_BUSY)) {
533     NXPLOG_NCIHAL_E("Read Thread is not pending already. status = 0x%x \n",
534                     readStatus);
535   }
536 
537   if (nfcFL.nfccFL._NFCC_DWNLD_MODE == NFCC_DWNLD_WITH_NCI_CMD &&
538       (!bIsNfccDlState)) {
539     nxpncihal_ctrl.isCoreRstForFwDnld = TRUE;
540     /*NCI_RESET_CMD*/
541     static uint8_t cmd_reset_nci_dwnld[] = {0x20, 0x00, 0x01, 0x80};
542     status = phNxpNciHal_send_ext_cmd(sizeof(cmd_reset_nci_dwnld),
543                                       cmd_reset_nci_dwnld);
544     if (status != NFCSTATUS_SUCCESS) {
545       NXPLOG_NCIHAL_E("Core reset FW download command failed \n");
546     }
547     nxpncihal_ctrl.isCoreRstForFwDnld = FALSE;
548   }
549   if (NFCSTATUS_SUCCESS == status) {
550     phTmlNfc_EnableFwDnldMode(true);
551     /* Set the obtained device handle to download module */
552 
553     phDnldNfc_SetHwDevHandle();
554 
555     if (IS_CHIP_TYPE_GE(sn100u)) {
556       phDnldNfc_SetI2CFragmentLength(NCI_CMDRESP_MAX_BUFF_SIZE_SNXXX);
557     } else {
558       phDnldNfc_SetI2CFragmentLength(NCI_CMDRESP_MAX_BUFF_SIZE_PN557);
559     }
560 
561     NXPLOG_NCIHAL_D("Calling Seq handler for FW Download \n");
562     status = phNxpNciHal_fw_download_seq(nxpprofile_ctrl.bClkSrcVal,
563                                          nxpprofile_ctrl.bClkFreqVal,
564                                          seq_handler_offset);
565 
566     if (phNxpNciHal_dlResetInFwDnldMode() != NFCSTATUS_SUCCESS) {
567       NXPLOG_NCIHAL_E("DL Reset failed in FW DN mode");
568     }
569 
570     /* FW download done.Therefore if previous I2C write failed then we can
571      * change the state to NFCSTATUS_SUCCESS*/
572     write_unlocked_status = NFCSTATUS_SUCCESS;
573   } else {
574     phTmlNfc_EnableFwDnldMode(false);
575     status = NFCSTATUS_FAILED;
576   }
577   if (NFCSTATUS_SUCCESS == status) {
578     phNxpNciHal_UpdateFwStatus(HAL_NFC_FW_UPDATE_SCUCCESS);
579   } else {
580     phNxpNciHal_UpdateFwStatus(HAL_NFC_FW_UPDATE_FAILED);
581   }
582   return status;
583 }
584 
585 /******************************************************************************
586  * Function         phNxpNciHal_CheckValidFwVersion
587  *
588  * Description      This function checks the valid FW for Mobile device.
589  *                  If the FW doesn't belong the Mobile device it further
590  *                  checks nxp config file to override.
591  *
592  * Returns          NFCSTATUS_SUCCESS if valid fw version found
593  *                  NFCSTATUS_NOT_ALLOWED in case of FW not valid for mobile
594  *                  device
595  *
596  ******************************************************************************/
phNxpNciHal_CheckValidFwVersion(void)597 NFCSTATUS phNxpNciHal_CheckValidFwVersion(void) {
598   NFCSTATUS status = NFCSTATUS_NOT_ALLOWED;
599   const unsigned char sfw_infra_major_no = 0x02;
600   unsigned char ufw_current_major_no = 0x00;
601   uint8_t rom_version = 0xFF & (wFwVerRsp >> 16);
602   uint8_t fw_maj_ver = 0xFF & (wFwVerRsp >> 8);
603 
604   /* extract the firmware's major no */
605   ufw_current_major_no = ((0x00FF) & (wFwVer >> 8U));
606   NXPLOG_NCIHAL_D("%s current_major_no = 0x%x", __func__, ufw_current_major_no);
607   NXPLOG_NCIHAL_D("%s fw_maj_ver = 0x%x", __func__, fw_maj_ver);
608   if (IS_CHIP_TYPE_EQ(pn557)) {
609     if (ufw_current_major_no >= fw_maj_ver) {
610       /* if file major version is grater than the one from the
611          Nfc init command allow FW download
612       */
613       status = NFCSTATUS_SUCCESS;
614     }
615     return status;
616   }
617 
618   if (wFwVerRsp == 0) {
619     NXPLOG_NCIHAL_E(
620         "FW Version not received by NCI command >>> Force Firmware download");
621     status = NFCSTATUS_SUCCESS;
622   } else if ((ufw_current_major_no == nfcFL._FW_MOBILE_MAJOR_NUMBER) ||
623              ((ufw_current_major_no == FW_MOBILE_MAJOR_NUMBER_PN81A) &&
624               (nxpncihal_ctrl.nci_info.nci_version == NCI_VERSION_2_0))) {
625     NXPLOG_NCIHAL_E("FW Version 2");
626     status = NFCSTATUS_SUCCESS;
627   } else if (ufw_current_major_no == sfw_infra_major_no) {
628     if ((rom_version == FW_MOBILE_ROM_VERSION_PN553 ||
629          rom_version == FW_MOBILE_ROM_VERSION_PN557)) {
630       NXPLOG_NCIHAL_D(" PN557  allow Fw download with major number =  0x%x",
631                       ufw_current_major_no);
632       status = NFCSTATUS_SUCCESS;
633     } else {
634       status = NFCSTATUS_NOT_ALLOWED;
635     }
636   }
637 #ifdef NXP_DUMMY_FW_DNLD
638   else if (gRecFWDwnld == TRUE) {
639     NXPLOG_NCIHAL_E("FW Version 4");
640     status = NFCSTATUS_SUCCESS;
641   }
642 #endif
643   else {
644     NXPLOG_NCIHAL_E("Wrong FW Version >>> Firmware download not allowed");
645   }
646 
647   return status;
648 }
649 
650 /******************************************************************************
651  * Function         phNxpNciHal_MinOpen_Clean
652  *
653  * Description      This function shall be called from phNxpNciHal_MinOpen when
654  *                  any unrecoverable error has encountered which needs to mark
655  *                  min open as failed, HAL status as closed & deallocate any
656  *                  memory if allocated.
657  *
658  * Returns          This function always returns Failure
659  *
660  ******************************************************************************/
phNxpNciHal_MinOpen_Clean(char * nfc_dev_node)661 static int phNxpNciHal_MinOpen_Clean(char* nfc_dev_node) {
662   if (nfc_dev_node != NULL) {
663     free(nfc_dev_node);
664     nfc_dev_node = NULL;
665   }
666   if (mGetCfg_info != NULL) {
667     free(mGetCfg_info);
668     mGetCfg_info = NULL;
669   }
670   /* Report error status */
671   phNxpNciHal_cleanup_monitor();
672   nxpncihal_ctrl.halStatus = HAL_STATUS_CLOSE;
673   return NFCSTATUS_FAILED;
674 }
675 
676 /******************************************************************************
677  * Function         phNxpNciHal_MinOpen
678  *
679  * Description      This function initializes the least required resources to
680  *                  communicate to NFCC.This is mainly used to communicate to
681  *                  NFCC when NFC service is not available.
682  *
683  *
684  * Returns          This function return NFCSTATUS_SUCCESS (0) in case of
685  *                  success In case of failure returns other failure value.
686  *
687  ******************************************************************************/
phNxpNciHal_MinOpen()688 int phNxpNciHal_MinOpen() {
689   phOsalNfc_Config_t tOsalConfig;
690   phTmlNfc_Config_t tTmlConfig;
691   char* nfc_dev_node = NULL;
692   const uint16_t max_len = 260;
693   NFCSTATUS wConfigStatus = NFCSTATUS_SUCCESS;
694   NFCSTATUS status = NFCSTATUS_SUCCESS;
695   int dnld_retry_cnt = 0;
696   NXPLOG_NCIHAL_D("phNxpNci_MinOpen(): enter");
697 
698   NfcHalAutoThreadMutex a(sHalFnLock);
699   if (nxpncihal_ctrl.halStatus == HAL_STATUS_MIN_OPEN) {
700     NXPLOG_NCIHAL_D("phNxpNciHal_MinOpen(): already open");
701     return NFCSTATUS_SUCCESS;
702   }
703   phNxpNciHal_initializeRegRfFwDnld();
704 
705   int8_t ret_val = 0x00;
706 
707   phNxpNciHal_initialize_debug_enabled_flag();
708   /* initialize trace level */
709   phNxpLog_InitializeLogLevel();
710 
711   /* initialize Mifare flags*/
712   phNxpNciHal_initialize_mifare_flag();
713 
714   /*Create the timer for extns write response*/
715   timeoutTimerId = phOsalNfc_Timer_Create();
716 
717   if (phNxpNciHal_init_monitor() == NULL) {
718     NXPLOG_NCIHAL_E("Init monitor failed");
719     return NFCSTATUS_FAILED;
720   }
721 
722   CONCURRENCY_LOCK();
723   memset(&tOsalConfig, 0x00, sizeof(tOsalConfig));
724   memset(&tTmlConfig, 0x00, sizeof(tTmlConfig));
725   memset(&nxpprofile_ctrl, 0, sizeof(phNxpNciProfile_Control_t));
726 
727   /*Init binary semaphore for Spi Nfc synchronization*/
728   if (0 != sem_init(&nxpncihal_ctrl.syncSpiNfc, 0, 1)) {
729     NXPLOG_NCIHAL_E("sem_init() FAiled, errno = 0x%02X", errno);
730     CONCURRENCY_UNLOCK();
731     return phNxpNciHal_MinOpen_Clean(nfc_dev_node);
732   }
733 
734   /* By default HAL status is HAL_STATUS_OPEN */
735   nxpncihal_ctrl.halStatus = HAL_STATUS_OPEN;
736 
737   /*nci version NCI_VERSION_2_0 version by default for SN100 chip type*/
738   nxpncihal_ctrl.nci_info.nci_version = NCI_VERSION_2_0;
739   /* Read the nfc device node name */
740   nfc_dev_node = (char*)malloc(max_len * sizeof(char));
741   if (nfc_dev_node == NULL) {
742     NXPLOG_NCIHAL_D("malloc of nfc_dev_node failed ");
743     CONCURRENCY_UNLOCK();
744     return phNxpNciHal_MinOpen_Clean(nfc_dev_node);
745   } else if (!GetNxpStrValue(NAME_NXP_NFC_DEV_NODE, nfc_dev_node, max_len)) {
746     NXPLOG_NCIHAL_D(
747         "Invalid nfc device node name keeping the default device node "
748         "/dev/pn54x");
749     strlcpy(nfc_dev_node, "/dev/pn54x", (max_len * sizeof(char)));
750   }
751   /* Configure hardware link */
752   nxpncihal_ctrl.gDrvCfg.nClientId = phDal4Nfc_msgget(0, 0600);
753   nxpncihal_ctrl.gDrvCfg.nLinkType = ENUM_LINK_TYPE_I2C; /* For PN54X */
754   tTmlConfig.pDevName = (int8_t*)nfc_dev_node;
755   tOsalConfig.dwCallbackThreadId = (uintptr_t)nxpncihal_ctrl.gDrvCfg.nClientId;
756   tOsalConfig.pLogFile = NULL;
757   tTmlConfig.dwGetMsgThreadId = (uintptr_t)nxpncihal_ctrl.gDrvCfg.nClientId;
758   mGetCfg_info = NULL;
759   mGetCfg_info =
760       (phNxpNci_getCfg_info_t*)nxp_malloc(sizeof(phNxpNci_getCfg_info_t));
761   if (mGetCfg_info == NULL) {
762     CONCURRENCY_UNLOCK();
763     return phNxpNciHal_MinOpen_Clean(nfc_dev_node);
764   }
765   memset(mGetCfg_info, 0x00, sizeof(phNxpNci_getCfg_info_t));
766 
767   /* Set Default Fragment Length */
768   tTmlConfig.fragment_len = NCI_CMDRESP_MAX_BUFF_SIZE_PN557;
769 
770   /* Initialize TML layer */
771   wConfigStatus = phTmlNfc_Init(&tTmlConfig);
772   if (wConfigStatus != NFCSTATUS_SUCCESS) {
773     NXPLOG_NCIHAL_E("phTmlNfc_Init Failed");
774     CONCURRENCY_UNLOCK();
775     return phNxpNciHal_MinOpen_Clean(nfc_dev_node);
776   } else {
777     if (nfc_dev_node != NULL) {
778       free(nfc_dev_node);
779       nfc_dev_node = NULL;
780     }
781   }
782 
783   /* Create the client thread */
784   ret_val = pthread_create(&nxpncihal_ctrl.client_thread, NULL,
785                            phNxpNciHal_client_thread, &nxpncihal_ctrl);
786   if (ret_val != 0) {
787     NXPLOG_NCIHAL_E("pthread_create failed");
788     wConfigStatus = phTmlNfc_Shutdown_CleanUp();
789     CONCURRENCY_UNLOCK();
790     return phNxpNciHal_MinOpen_Clean(nfc_dev_node);
791   }
792 
793   CONCURRENCY_UNLOCK();
794   /* call read pending */
795   status = phTmlNfc_Read(
796       nxpncihal_ctrl.p_rsp_data, NCI_MAX_DATA_LEN,
797       (pphTmlNfc_TransactCompletionCb_t)&phNxpNciHal_read_complete, NULL);
798   if (status != NFCSTATUS_PENDING) {
799     NXPLOG_NCIHAL_E("TML Read status error status = %x", status);
800     wConfigStatus = phTmlNfc_Shutdown_CleanUp();
801     wConfigStatus = NFCSTATUS_FAILED;
802     return phNxpNciHal_MinOpen_Clean(nfc_dev_node);
803   }
804 
805   /* Get the chip-type to know if it is PN557
806    Then don't send the Get version command */
807   unsigned long chipInfo = 0;
808   if (GetNxpNumValue(NAME_NXP_NFC_CHIP, &chipInfo, sizeof(chipInfo))) {
809     NXPLOG_NCIHAL_D("The chip type is %lx", chipInfo);
810   }
811 
812   if (gsIsFirstHalMinOpen) {
813     /*Skip get version command for pn557*/
814     if (chipInfo != pn557) phNxpNciHal_CheckAndHandleFwTearDown();
815   }
816 
817   uint8_t seq_handler_offset = 0x00;
818   uint8_t fw_update_req = 1;
819   uint8_t rf_update_req;
820   bool bVenResetRequired = false;
821   bool bIsNfccDlState = false;
822   phNxpNciHal_ext_init();
823 
824   phTmlNfc_IoCtl(phTmlNfc_e_EnableVen);
825 
826   if (phNxpNciHal_isULPDetSupported()) {
827     status = phTmlNfc_IoCtl(phTmlNfc_e_PullVenHigh);
828     if (NFCSTATUS_SUCCESS == status) {
829       NXPLOG_NCIHAL_D("ULPDET phTmlNfc_e_PullVenHigh - SUCCESS\n");
830     } else {
831       NXPLOG_NCIHAL_D("ULPDET phTmlNfc_e_PullVenHigh - FAILED\n");
832     }
833   }
834 
835   if (wFwVerRsp == 0) {
836     bVenResetRequired = true;
837   }
838   /* reset version info new version info will be fetch */
839   wFwVerRsp = 0x00;
840   wFwVer = 0x00;
841   if (NFCSTATUS_SUCCESS == phNxpNciHal_nfcc_core_reset_init(true)) {
842     setNxpFwConfigPath();
843     if (IS_CHIP_TYPE_L(sn100u)) phNxpNciHal_enable_i2c_fragmentation();
844 
845     status = phNxpNciHal_CheckFwRegFlashRequired(&fw_update_req, &rf_update_req,
846                                                  false);
847     if (status != NFCSTATUS_OK) {
848       NXPLOG_NCIHAL_D(
849           "phNxpNciHal_CheckFwRegFlashRequired() failed:exit status = %x",
850           status);
851       fw_update_req = FALSE;
852       rf_update_req = FALSE;
853     }
854 
855     if (!wFwUpdateReq) {
856       uint8_t is_teared_down = 0x00;
857       status = phNxpNciHal_read_fw_dw_status(is_teared_down);
858       if (status != NFCSTATUS_SUCCESS) {
859         NXPLOG_NCIHAL_E("%s: NXP get FW DW Flag failed", __FUNCTION__);
860       }
861       if (is_teared_down) {
862         seq_handler_offset = PHLIBNFC_DNLD_CHECKINTEGRITY_OFFSET;
863         fw_update_req = TRUE;
864       } else {
865         NXPLOG_NCIHAL_D("FW update not required");
866         property_set("nfc.fw.downloadmode_force", "0");
867         phDnldNfc_ReSetHwDevHandle();
868       }
869     }
870   } else if (bVenResetRequired) {
871     if (NFCSTATUS_SUCCESS == phNxpNciHal_getChipInfoInFwDnldMode(true))
872       bIsNfccDlState = true;
873   }
874 
875   if (gsIsFirstHalMinOpen && gsIsFwRecoveryRequired) {
876     NXPLOG_NCIHAL_E("FW Recovery is required");
877     fw_update_req = true;
878   }
879 
880   do {
881     if (fw_update_req && !fw_download_success) {
882       gsIsFwRecoveryRequired = false;
883       status =
884           phNxpNciHal_force_fw_download(seq_handler_offset, bIsNfccDlState);
885       if (status == NFCSTATUS_CMD_ABORTED) {
886         return phNxpNciHal_MinOpen_Clean(nfc_dev_node);
887       } else if (fw_download_success) {
888         wConfigStatus = NFCSTATUS_SUCCESS;
889       }
890     }
891     status = phNxpNciHal_resetDefaultSettings(
892         fw_update_req, fw_download_success ? false : true);
893 
894     if ((status != NFCSTATUS_SUCCESS && fw_download_success) ||
895         (gsIsFwRecoveryRequired && fw_update_req)) {
896       NXPLOG_NCIHAL_E(
897           "FW Recovery required, Perform Force FW Download "
898           "gsIsFwRecoveryRequired %d",
899           gsIsFwRecoveryRequired);
900       fw_update_req = 1;
901       dnld_retry_cnt++;
902     } else if (status != NFCSTATUS_SUCCESS) {
903       return phNxpNciHal_MinOpen_Clean(nfc_dev_node);
904     } else {
905       break;
906     }
907 
908     if (dnld_retry_cnt > 1) {
909       wConfigStatus = NFCSTATUS_FAILED;
910       break;
911     }
912 
913   } while (status != NFCSTATUS_SUCCESS || gsIsFwRecoveryRequired);
914   /* Call open complete */
915   phNxpNciHal_MinOpen_complete(wConfigStatus);
916   NXPLOG_NCIHAL_D("phNxpNciHal_MinOpen(): exit");
917   return wConfigStatus;
918 }
919 
920 /******************************************************************************
921  * Function         phNxpNciHal_open
922  *
923  * Description      This function is called by libnfc-nci during the
924  *                  initialization of the NFCC. It opens the physical connection
925  *                  with NFCC (PN54X) and creates required client thread for
926  *                  operation.
927  *                  After open is complete, status is informed to libnfc-nci
928  *                  through callback function.
929  *
930  * Returns          This function return NFCSTATUS_SUCCESS (0) in case of
931  *                  success In case of failure returns other failure value.
932  *
933  ******************************************************************************/
phNxpNciHal_open(nfc_stack_callback_t * p_cback,nfc_stack_data_callback_t * p_data_cback)934 int phNxpNciHal_open(nfc_stack_callback_t* p_cback,
935                      nfc_stack_data_callback_t* p_data_cback) {
936   NFCSTATUS wConfigStatus = NFCSTATUS_SUCCESS;
937   NFCSTATUS status = NFCSTATUS_SUCCESS;
938   NXPLOG_NCIHAL_E("phNxpNciHal_open NFC HAL OPEN");
939 #ifdef NXP_BOOTTIME_UPDATE
940   if (ese_update != ESE_UPDATE_COMPLETED) {
941     ALOGD("BLOCK NFC HAL OPEN");
942     if (p_cback != NULL) {
943       p_nfc_stack_cback_backup = p_cback;
944       (*p_cback)(HAL_NFC_OPEN_CPLT_EVT, HAL_NFC_STATUS_FAILED);
945     }
946     return NFCSTATUS_FAILED;
947   }
948 #endif
949   if (nxpncihal_ctrl.halStatus == HAL_STATUS_OPEN) {
950     NXPLOG_NCIHAL_D("phNxpNciHal_open already open");
951     phNxpNciHal_open_complete(wConfigStatus);
952     return wConfigStatus;
953   } else if (nxpncihal_ctrl.halStatus == HAL_STATUS_CLOSE) {
954     memset(&nxpncihal_ctrl, 0x00, sizeof(nxpncihal_ctrl));
955     nxpncihal_ctrl.p_nfc_stack_cback = p_cback;
956     nxpncihal_ctrl.p_nfc_stack_data_cback = p_data_cback;
957     status = phNxpNciHal_MinOpen();
958     if (status != NFCSTATUS_SUCCESS) {
959       NXPLOG_NCIHAL_E("phNxpNciHal_MinOpen failed");
960       goto clean_and_return;
961     } /*else its already in MIN_OPEN state. continue with rest of
962          functionality*/
963   } else {
964     nxpncihal_ctrl.p_nfc_stack_cback = p_cback;
965     nxpncihal_ctrl.p_nfc_stack_data_cback = p_data_cback;
966   }
967   /* Call open complete */
968   phNxpNciHal_open_complete(wConfigStatus);
969 
970   return wConfigStatus;
971 
972 clean_and_return:
973   CONCURRENCY_UNLOCK();
974   /* Report error status */
975   if (p_cback != NULL) {
976     (*p_cback)(HAL_NFC_OPEN_CPLT_EVT, HAL_NFC_STATUS_FAILED);
977   }
978 
979   nxpncihal_ctrl.p_nfc_stack_cback = NULL;
980   nxpncihal_ctrl.p_nfc_stack_data_cback = NULL;
981   phNxpNciHal_cleanup_monitor();
982   nxpncihal_ctrl.halStatus = HAL_STATUS_CLOSE;
983   return NFCSTATUS_FAILED;
984 }
985 
986 /******************************************************************************
987  * Function         phNxpNciHal_fw_mw_check
988  *
989  * Description      This function inform the status of phNxpNciHal_fw_mw_check
990  *                  function to libnfc-nci.
991  *
992  * Returns          int.
993  *
994  ******************************************************************************/
phNxpNciHal_fw_mw_ver_check()995 int phNxpNciHal_fw_mw_ver_check() {
996   NFCSTATUS status = NFCSTATUS_FAILED;
997   uint8_t rom_version = 0xFF & (wFwVerRsp >> 16);
998   uint8_t fw_maj_ver = 0xFF & (wFwVerRsp >> 8);
999 
1000   if (IS_CHIP_TYPE_EQ(pn557) && (rom_version == FW_MOBILE_ROM_VERSION_PN557) &&
1001       (fw_maj_ver == 0x01)) {
1002     status = NFCSTATUS_SUCCESS;
1003   } else if ((IS_CHIP_TYPE_EQ(pn553) || IS_CHIP_TYPE_EQ(pn80T)) &&
1004              (rom_version == 0x11) && (fw_maj_ver == 0x01)) {
1005     status = NFCSTATUS_SUCCESS;
1006   } else if ((IS_CHIP_TYPE_EQ(pn551) || IS_CHIP_TYPE_EQ(pn67T)) &&
1007              (rom_version == 0x10) && (fw_maj_ver == 0x05)) {
1008     status = NFCSTATUS_SUCCESS;
1009   } else if (IS_CHIP_TYPE_EQ(sn100u) && (rom_version == SN1XX_ROM_VERSION) &&
1010              (fw_maj_ver == SN1XX_FW_MAJOR_VERSION)) {
1011     status = NFCSTATUS_SUCCESS;
1012   } else if ((IS_CHIP_TYPE_EQ(sn220u) || IS_CHIP_TYPE_EQ(pn560)) &&
1013              (rom_version == SN2XX_ROM_VERSION) &&
1014              (fw_maj_ver == SN2XX_FW_MAJOR_VERSION)) {
1015     status = NFCSTATUS_SUCCESS;
1016   }
1017   if (NFCSTATUS_SUCCESS != status) {
1018     NXPLOG_NCIHAL_D("Chip Version Middleware Version mismatch!!!!");
1019   }
1020   return status;
1021 }
1022 /******************************************************************************
1023  * Function         phNxpNciHal_MinOpen_complete
1024  *
1025  * Description      This function updates the status of
1026  *phNxpNciHal_MinOpen_complete to halstatus.
1027  *
1028  * Returns          void.
1029  *
1030  ******************************************************************************/
phNxpNciHal_MinOpen_complete(NFCSTATUS status)1031 static void phNxpNciHal_MinOpen_complete(NFCSTATUS status) {
1032   gsIsFirstHalMinOpen = false;
1033   if (status == NFCSTATUS_SUCCESS) {
1034     nxpncihal_ctrl.halStatus = HAL_STATUS_MIN_OPEN;
1035   }
1036 
1037   return;
1038 }
1039 
1040 /******************************************************************************
1041  * Function         phNxpNciHal_open_complete
1042  *
1043  * Description      This function inform the status of phNxpNciHal_open
1044  *                  function to libnfc-nci.
1045  *
1046  * Returns          void.
1047  *
1048  ******************************************************************************/
phNxpNciHal_open_complete(NFCSTATUS status)1049 static void phNxpNciHal_open_complete(NFCSTATUS status) {
1050   static phLibNfc_Message_t msg;
1051 
1052   if (status == NFCSTATUS_SUCCESS) {
1053     msg.eMsgType = NCI_HAL_OPEN_CPLT_MSG;
1054     nxpncihal_ctrl.hal_open_status = true;
1055     nxpncihal_ctrl.halStatus = HAL_STATUS_OPEN;
1056   } else {
1057     msg.eMsgType = NCI_HAL_ERROR_MSG;
1058   }
1059 
1060   msg.pMsgData = NULL;
1061   msg.Size = 0;
1062 
1063   phTmlNfc_DeferredCall(gpphTmlNfc_Context->dwCallbackThreadId,
1064                         (phLibNfc_Message_t*)&msg);
1065 
1066   return;
1067 }
1068 
1069 /******************************************************************************
1070  * Function         phNxpNciHal_write
1071  *
1072  * Description      This function write the data to NFCC through physical
1073  *                  interface (e.g. I2C) using the PN54X driver interface.
1074  *                  Before sending the data to NFCC, phNxpNciHal_write_ext
1075  *                  is called to check if there is any extension processing
1076  *                  is required for the NCI packet being sent out.
1077  *
1078  * Returns          It returns number of bytes successfully written to NFCC.
1079  *
1080  ******************************************************************************/
phNxpNciHal_write(uint16_t data_len,const uint8_t * p_data)1081 int phNxpNciHal_write(uint16_t data_len, const uint8_t* p_data) {
1082   if (bDisableLegacyMfcExtns && bEnableMfcExtns && p_data[0] == 0x00) {
1083     return NxpMfcReaderInstance.Write(data_len, p_data);
1084   }
1085   return phNxpNciHal_write_internal(data_len, p_data);
1086 }
1087 
1088 /******************************************************************************
1089  * Function         phNxpNciHal_write_internal
1090  *
1091  * Description      This function write the data to NFCC through physical
1092  *                  interface (e.g. I2C) using the PN54X driver interface.
1093  *                  Before sending the data to NFCC, phNxpNciHal_write_ext
1094  *                  is called to check if there is any extension processing
1095  *                  is required for the NCI packet being sent out.
1096  *
1097  * Returns          It returns number of bytes successfully written to NFCC.
1098  *
1099  ******************************************************************************/
phNxpNciHal_write_internal(uint16_t data_len,const uint8_t * p_data)1100 int phNxpNciHal_write_internal(uint16_t data_len, const uint8_t* p_data) {
1101   NFCSTATUS status = NFCSTATUS_FAILED;
1102   static phLibNfc_Message_t msg;
1103   if (nxpncihal_ctrl.halStatus != HAL_STATUS_OPEN) {
1104     return NFCSTATUS_FAILED;
1105   }
1106   if ((data_len + MAX_NXP_HAL_EXTN_BYTES) > NCI_MAX_DATA_LEN) {
1107     NXPLOG_NCIHAL_D("cmd_len exceeds limit NCI_MAX_DATA_LEN");
1108     android_errorWriteLog(0x534e4554, "121267042");
1109     goto clean_and_return;
1110   }
1111 
1112   CONCURRENCY_LOCK();
1113   /* Create local copy of cmd_data */
1114   memcpy(nxpncihal_ctrl.p_cmd_data, p_data, data_len);
1115   nxpncihal_ctrl.cmd_len = data_len;
1116 #ifdef P2P_PRIO_LOGIC_HAL_IMP
1117   /* Specific logic to block RF disable when P2P priority logic is busy */
1118   if (p_data[0] == 0x21 && p_data[1] == 0x06 && p_data[2] == 0x01 &&
1119       EnableP2P_PrioLogic == true) {
1120     NXPLOG_NCIHAL_D("P2P priority logic busy: Disable it.");
1121     phNxpNciHal_clean_P2P_Prio();
1122   }
1123 #endif
1124 
1125   /* Check for NXP ext before sending write */
1126   status =
1127       phNxpNciHal_write_ext(&nxpncihal_ctrl.cmd_len, nxpncihal_ctrl.p_cmd_data,
1128                             &nxpncihal_ctrl.rsp_len, nxpncihal_ctrl.p_rsp_data);
1129   if (status != NFCSTATUS_SUCCESS) {
1130     /* Do not send packet to PN54X, send response directly */
1131     msg.eMsgType = NCI_HAL_RX_MSG;
1132     msg.pMsgData = NULL;
1133     msg.Size = 0;
1134 
1135     phTmlNfc_DeferredCall(gpphTmlNfc_Context->dwCallbackThreadId,
1136                           (phLibNfc_Message_t*)&msg);
1137     goto clean_and_return;
1138   }
1139 
1140   data_len = phNxpNciHal_write_unlocked(nxpncihal_ctrl.cmd_len,
1141                                         nxpncihal_ctrl.p_cmd_data, ORIG_LIBNFC);
1142 
1143   if (IS_CHIP_TYPE_L(sn100u) && IS_CHIP_TYPE_NE(pn557) && icode_send_eof == 1) {
1144     usleep(10000);
1145     icode_send_eof = 2;
1146     status = phNxpNciHal_send_ext_cmd(3, cmd_icode_eof);
1147     if (status != NFCSTATUS_SUCCESS) {
1148       NXPLOG_NCIHAL_E("ICODE end of frame command failed");
1149     }
1150   }
1151 
1152 clean_and_return:
1153   /* No data written */
1154   CONCURRENCY_UNLOCK();
1155   return data_len;
1156 }
1157 
1158 /******************************************************************************
1159  * Function         phNxpNciHal_write_unlocked
1160  *
1161  * Description      This is the actual function which is being called by
1162  *                  phNxpNciHal_write. This function writes the data to NFCC.
1163  *                  It waits till write callback provide the result of write
1164  *                  process.
1165  *
1166  * Returns          It returns number of bytes successfully written to NFCC.
1167  *
1168  ******************************************************************************/
phNxpNciHal_write_unlocked(uint16_t data_len,const uint8_t * p_data,int origin)1169 int phNxpNciHal_write_unlocked(uint16_t data_len, const uint8_t* p_data,
1170                                int origin) {
1171   NFCSTATUS status = NFCSTATUS_INVALID_PARAMETER;
1172   phNxpNciHal_Sem_t cb_data;
1173   nxpncihal_ctrl.retry_cnt = 0;
1174   int sem_val = 0;
1175   static uint8_t reset_ntf[] = {0x60, 0x00, 0x06, 0xA0, 0x00,
1176                                 0xC7, 0xD4, 0x00, 0x00};
1177   /* Create the local semaphore */
1178   if (phNxpNciHal_init_cb_data(&cb_data, NULL) != NFCSTATUS_SUCCESS) {
1179     NXPLOG_NCIHAL_D("phNxpNciHal_write_unlocked Create cb data failed");
1180     data_len = 0;
1181     goto clean_and_return;
1182   }
1183 
1184   /* Create local copy of cmd_data */
1185   memcpy(nxpncihal_ctrl.p_cmd_data, p_data, data_len);
1186   nxpncihal_ctrl.cmd_len = data_len;
1187   write_unlocked_status = NFCSTATUS_FAILED;
1188   /* check for write synchronyztion */
1189   if (phNxpNciHal_check_ncicmd_write_window(nxpncihal_ctrl.cmd_len,
1190                                             nxpncihal_ctrl.p_cmd_data) !=
1191       NFCSTATUS_SUCCESS) {
1192     NXPLOG_NCIHAL_D("phNxpNciHal_write_unlocked  CMD window  check failed");
1193     data_len = 0;
1194     goto clean_and_return;
1195   }
1196 
1197   if (origin == ORIG_NXPHAL) HAL_ENABLE_EXT();
1198 
1199 retry:
1200 
1201   data_len = nxpncihal_ctrl.cmd_len;
1202 
1203   status = phTmlNfc_Write(
1204       (uint8_t*)nxpncihal_ctrl.p_cmd_data, (uint16_t)nxpncihal_ctrl.cmd_len,
1205       (pphTmlNfc_TransactCompletionCb_t)&phNxpNciHal_write_complete,
1206       (void*)&cb_data);
1207   if (status != NFCSTATUS_PENDING) {
1208     NXPLOG_NCIHAL_E("write_unlocked status error");
1209     data_len = 0;
1210     goto clean_and_return;
1211   }
1212 
1213   /* Wait for callback response */
1214   if (SEM_WAIT(cb_data)) {
1215     NXPLOG_NCIHAL_E("write_unlocked semaphore error");
1216     data_len = 0;
1217     goto clean_and_return;
1218   }
1219 
1220   if (cb_data.status != NFCSTATUS_SUCCESS) {
1221     data_len = 0;
1222     if (nxpncihal_ctrl.retry_cnt++ < MAX_RETRY_COUNT) {
1223       NXPLOG_NCIHAL_D(
1224           "write_unlocked failed - PN54X Maybe in Standby Mode - Retry");
1225       /* 10ms delay to give NFCC wake up delay */
1226       usleep(1000 * 10);
1227       goto retry;
1228     } else {
1229       NXPLOG_NCIHAL_E(
1230           "write_unlocked failed - PN54X Maybe in Standby Mode (max count = "
1231           "0x%x)",
1232           nxpncihal_ctrl.retry_cnt);
1233 
1234       status = phTmlNfc_IoCtl(phTmlNfc_e_ResetDevice);
1235 
1236       if (NFCSTATUS_SUCCESS == status) {
1237         NXPLOG_NCIHAL_D("PN54X Reset - SUCCESS\n");
1238       } else {
1239         NXPLOG_NCIHAL_D("PN54X Reset - FAILED\n");
1240       }
1241       if (nxpncihal_ctrl.p_nfc_stack_data_cback != NULL &&
1242           nxpncihal_ctrl.hal_open_status == true) {
1243         if (nxpncihal_ctrl.p_rx_data != NULL) {
1244           NXPLOG_NCIHAL_D(
1245               "Send the Core Reset NTF to upper layer, which will trigger the "
1246               "recovery\n");
1247           // Send the Core Reset NTF to upper layer, which will trigger the
1248           // recovery.
1249           abort();
1250           nxpncihal_ctrl.rx_data_len = sizeof(reset_ntf);
1251           memcpy(nxpncihal_ctrl.p_rx_data, reset_ntf, sizeof(reset_ntf));
1252           (*nxpncihal_ctrl.p_nfc_stack_data_cback)(nxpncihal_ctrl.rx_data_len,
1253                                                    nxpncihal_ctrl.p_rx_data);
1254         } else {
1255           (*nxpncihal_ctrl.p_nfc_stack_data_cback)(0x00, NULL);
1256         }
1257         write_unlocked_status = NFCSTATUS_FAILED;
1258       }
1259     }
1260   } else {
1261     write_unlocked_status = NFCSTATUS_SUCCESS;
1262   }
1263 
1264 clean_and_return:
1265   if (write_unlocked_status == NFCSTATUS_FAILED) {
1266     sem_getvalue(&(nxpncihal_ctrl.syncSpiNfc), &sem_val);
1267     if (((nxpncihal_ctrl.p_cmd_data[0] & NCI_MT_MASK) == NCI_MT_CMD) &&
1268         sem_val == 0) {
1269       sem_post(&(nxpncihal_ctrl.syncSpiNfc));
1270       NXPLOG_NCIHAL_D("HAL write  failed CMD window check releasing \n");
1271     }
1272   }
1273   phNxpNciHal_cleanup_cb_data(&cb_data);
1274   return data_len;
1275 }
1276 
1277 /******************************************************************************
1278  * Function         phNxpNciHal_write_complete
1279  *
1280  * Description      This function handles write callback.
1281  *
1282  * Returns          void.
1283  *
1284  ******************************************************************************/
phNxpNciHal_write_complete(void * pContext,phTmlNfc_TransactInfo_t * pInfo)1285 static void phNxpNciHal_write_complete(void* pContext,
1286                                        phTmlNfc_TransactInfo_t* pInfo) {
1287   phNxpNciHal_Sem_t* p_cb_data = (phNxpNciHal_Sem_t*)pContext;
1288   if (pInfo->wStatus == NFCSTATUS_SUCCESS) {
1289     NXPLOG_NCIHAL_D("write successful status = 0x%x", pInfo->wStatus);
1290   } else {
1291     NXPLOG_NCIHAL_D("write error status = 0x%x", pInfo->wStatus);
1292   }
1293 
1294   p_cb_data->status = pInfo->wStatus;
1295 
1296   SEM_POST(p_cb_data);
1297 
1298   return;
1299 }
1300 
1301 /******************************************************************************
1302  * Function         phNxpNciHal_read_complete
1303  *
1304  * Description      This function is called whenever there is an NCI packet
1305  *                  received from NFCC. It could be RSP or NTF packet. This
1306  *                  function provide the received NCI packet to libnfc-nci
1307  *                  using data callback of libnfc-nci.
1308  *                  There is a pending read called from each
1309  *                  phNxpNciHal_read_complete so each a packet received from
1310  *                  NFCC can be provide to libnfc-nci.
1311  *
1312  * Returns          void.
1313  *
1314  ******************************************************************************/
phNxpNciHal_read_complete(void * pContext,phTmlNfc_TransactInfo_t * pInfo)1315 static void phNxpNciHal_read_complete(void* pContext,
1316                                       phTmlNfc_TransactInfo_t* pInfo) {
1317   NFCSTATUS status = NFCSTATUS_FAILED;
1318   int sem_val;
1319   UNUSED_PROP(pContext);
1320   if (nxpncihal_ctrl.read_retry_cnt == 1) {
1321     nxpncihal_ctrl.read_retry_cnt = 0;
1322   }
1323   if (pInfo->wStatus == NFCSTATUS_SUCCESS) {
1324     NXPLOG_NCIHAL_D("read successful status = 0x%x", pInfo->wStatus);
1325 
1326     /*Check the Omapi command response and store in dedicated buffer to solve
1327      * sync issue*/
1328     if (IS_CHIP_TYPE_LE(sn100u) && pInfo->pBuff[0] == 0x4F &&
1329         pInfo->pBuff[1] == 0x01 && pInfo->pBuff[2] == 0x01) {
1330       nxpncihal_ctrl.p_rx_ese_data = pInfo->pBuff;
1331       nxpncihal_ctrl.rx_ese_data_len = pInfo->wLength;
1332       SEM_POST(&(nxpncihal_ctrl.ext_cb_data));
1333     } else {
1334       nxpncihal_ctrl.p_rx_data = pInfo->pBuff;
1335       nxpncihal_ctrl.rx_data_len = pInfo->wLength;
1336       status = phNxpNciHal_process_ext_rsp(nxpncihal_ctrl.p_rx_data,
1337                                            &nxpncihal_ctrl.rx_data_len);
1338       if (nxpncihal_ctrl.hal_ext_enabled && phTmlNfc_IsFwDnldModeEnabled()) {
1339         SEM_POST(&(nxpncihal_ctrl.ext_cb_data));
1340       }
1341     }
1342     phNxpNciHal_print_res_status(pInfo->pBuff, &pInfo->wLength);
1343     if (nxpncihal_ctrl.power_reset_triggered == true) {
1344       nxpncihal_ctrl.power_reset_triggered = false;
1345     }
1346 
1347     /* Check if response should go to hal module only */
1348     if (nxpncihal_ctrl.hal_ext_enabled == TRUE &&
1349         (nxpncihal_ctrl.p_rx_data[0x00] & NCI_MT_MASK) == NCI_MT_RSP) {
1350       if (status == NFCSTATUS_FAILED) {
1351         NXPLOG_NCIHAL_D("enter into NFCC init recovery");
1352         nxpncihal_ctrl.ext_cb_data.status = status;
1353       }
1354       /* Unlock semaphore only for responses*/
1355       if ((nxpncihal_ctrl.p_rx_data[0x00] & NCI_MT_MASK) == NCI_MT_RSP ||
1356           (IS_CHIP_TYPE_L(sn100u) && (icode_detected == true) &&
1357            (icode_send_eof == 3))) {
1358         /* Unlock semaphore */
1359         SEM_POST(&(nxpncihal_ctrl.ext_cb_data));
1360       }
1361     }  // Notification Checking
1362     else if ((nxpncihal_ctrl.hal_ext_enabled == TRUE) &&
1363              ((nxpncihal_ctrl.p_rx_data[0x00] & NCI_MT_MASK) == NCI_MT_NTF) &&
1364              ((nxpncihal_ctrl.p_cmd_data[0x00] & NCI_GID_MASK) ==
1365               (nxpncihal_ctrl.p_rx_data[0x00] & NCI_GID_MASK)) &&
1366              ((nxpncihal_ctrl.p_cmd_data[0x01] & NCI_OID_MASK) ==
1367               (nxpncihal_ctrl.p_rx_data[0x01] & NCI_OID_MASK)) &&
1368              (nxpncihal_ctrl.nci_info.wait_for_ntf == TRUE)) {
1369       /* Unlock semaphore waiting for only  ntf*/
1370       nxpncihal_ctrl.nci_info.wait_for_ntf = FALSE;
1371       SEM_POST(&(nxpncihal_ctrl.ext_cb_data));
1372     } else if (bDisableLegacyMfcExtns && !sendRspToUpperLayer &&
1373                (nxpncihal_ctrl.p_rx_data[0x00] == 0x00)) {
1374       sendRspToUpperLayer = true;
1375       NFCSTATUS mfcRspStatus = NxpMfcReaderInstance.CheckMfcResponse(
1376           nxpncihal_ctrl.p_rx_data, nxpncihal_ctrl.rx_data_len);
1377       NXPLOG_NCIHAL_D("Mfc Response Status = 0x%x", mfcRspStatus);
1378       SEM_POST(&(nxpncihal_ctrl.ext_cb_data));
1379     }
1380     /* Read successful send the event to higher layer */
1381     else if ((nxpncihal_ctrl.p_nfc_stack_data_cback != NULL) &&
1382              (status == NFCSTATUS_SUCCESS)) {
1383       NxpMfcReaderInstance.MfcNotifyOnAckReceived(nxpncihal_ctrl.p_rx_data);
1384       (*nxpncihal_ctrl.p_nfc_stack_data_cback)(nxpncihal_ctrl.rx_data_len,
1385                                                nxpncihal_ctrl.p_rx_data);
1386       // workaround for sync issue between SPI and NFC
1387       if (IS_CHIP_TYPE_EQ(pn557) && nxpncihal_ctrl.p_rx_data[0] == 0x62 &&
1388           nxpncihal_ctrl.p_rx_data[1] == 0x00 &&
1389           nxpncihal_ctrl.p_rx_data[3] == 0xC0 &&
1390           nxpncihal_ctrl.p_rx_data[4] == 0x00) {
1391         uint8_t nfcee_notifiations[3][9] = {
1392             {0x61, 0x0A, 0x06, 0x01, 0x00, 0x03, 0xC0, 0x80, 0x04},
1393             {0x61, 0x0A, 0x06, 0x01, 0x00, 0x03, 0xC0, 0x81, 0x04},
1394             {0x61, 0x0A, 0x06, 0x01, 0x00, 0x03, 0xC0, 0x82, 0x03},
1395         };
1396 
1397         for (int i = 0; i < 3; i++) {
1398           (*nxpncihal_ctrl.p_nfc_stack_data_cback)(
1399               sizeof(nfcee_notifiations[i]), nfcee_notifiations[i]);
1400         }
1401       }
1402     }
1403     /* Unblock next Write Command Window */
1404     sem_getvalue(&(nxpncihal_ctrl.syncSpiNfc), &sem_val);
1405     if (((pInfo->pBuff[0] & NCI_MT_MASK) == NCI_MT_RSP) && sem_val == 0) {
1406       sem_post(&(nxpncihal_ctrl.syncSpiNfc));
1407     }
1408   } else {
1409     NXPLOG_NCIHAL_E("read error status = 0x%x", pInfo->wStatus);
1410   }
1411 
1412   if (nxpncihal_ctrl.halStatus == HAL_STATUS_CLOSE &&
1413       (nxpncihal_ctrl.p_cmd_data[0x00] & NCI_GID_MASK) ==
1414           (nxpncihal_ctrl.p_rx_data[0x00] & NCI_GID_MASK) &&
1415       (nxpncihal_ctrl.p_cmd_data[0x01] & NCI_OID_MASK) ==
1416           (nxpncihal_ctrl.p_rx_data[0x01] & NCI_OID_MASK) &&
1417       nxpncihal_ctrl.nci_info.wait_for_ntf == FALSE) {
1418     NXPLOG_NCIHAL_D(" Ignoring read , HAL close triggered");
1419     return;
1420   }
1421   /* Read again because read must be pending always except FWDNLD.*/
1422   if (!phTmlNfc_IsFwDnldModeEnabled()) {
1423     status = phTmlNfc_Read(
1424         nxpncihal_ctrl.p_rsp_data, NCI_MAX_DATA_LEN,
1425         (pphTmlNfc_TransactCompletionCb_t)&phNxpNciHal_read_complete, NULL);
1426     if (status != NFCSTATUS_PENDING) {
1427       NXPLOG_NCIHAL_E("read status error status = %x", status);
1428       /* TODO: Not sure how to handle this ? */
1429     }
1430   }
1431   return;
1432 }
1433 
1434 /*******************************************************************************
1435  **
1436  ** Function:        phNxpNciHal_lastResetNtfReason()
1437  **
1438  ** Description:     Returns and clears last reset notification reason.
1439  **                      Intended to be called only once during recovery.
1440  **
1441  ** Returns:         reasonCode
1442  **
1443  ********************************************************************************/
phNxpNciHal_lastResetNtfReason(void)1444 uint8_t phNxpNciHal_lastResetNtfReason(void) {
1445   uint8_t reasonCode = nxpncihal_ctrl.nci_info.lastResetNtfReason;
1446 
1447   nxpncihal_ctrl.nci_info.lastResetNtfReason = 0;
1448 
1449   return reasonCode;
1450 }
1451 /******************************************************************************
1452  * Function         phNxpNciHal_enableTmlRead
1453  *
1454  * Description      Invokes TmlNfc Read to make sure always read thread is
1455  *                  pending
1456  *
1457  * Returns          Returns read status
1458  *
1459  ******************************************************************************/
phNxpNciHal_enableTmlRead()1460 NFCSTATUS phNxpNciHal_enableTmlRead() {
1461   /* Read again because read must be pending always.*/
1462   NFCSTATUS status = phTmlNfc_Read(
1463       nxpncihal_ctrl.p_rsp_data, NCI_MAX_DATA_LEN,
1464       (pphTmlNfc_TransactCompletionCb_t)&phNxpNciHal_read_complete, NULL);
1465   if (status != NFCSTATUS_PENDING) {
1466     NXPLOG_NCIHAL_E("read status error status = %x", status);
1467   }
1468   return status;
1469 }
1470 /******************************************************************************
1471  * Function         phNxpNciHal_core_initialized
1472  *
1473  * Description      This function is called by libnfc-nci after successful open
1474  *                  of NFCC. All proprietary setting for PN54X are done here.
1475  *                  After completion of proprietary settings notification is
1476  *                  provided to libnfc-nci through callback function.
1477  *
1478  * Returns          Always returns NFCSTATUS_SUCCESS (0).
1479  *
1480  ******************************************************************************/
phNxpNciHal_core_initialized(uint16_t core_init_rsp_params_len,uint8_t * p_core_init_rsp_params)1481 int phNxpNciHal_core_initialized(uint16_t core_init_rsp_params_len,
1482                                  uint8_t* p_core_init_rsp_params) {
1483   NFCSTATUS status = NFCSTATUS_SUCCESS;
1484   uint8_t* buffer = NULL;
1485   uint8_t isfound = 0;
1486   uint8_t fw_dwnld_flag = false;
1487   uint8_t setConfigAlways = false;
1488 
1489   uint8_t p2p_listen_mode_routing_cmd[] = {0x21, 0x01, 0x07, 0x00, 0x01,
1490                                            0x01, 0x03, 0x00, 0x01, 0x05};
1491 
1492   uint8_t swp_full_pwr_mode_on_cmd[] = {0x20, 0x02, 0x05, 0x01,
1493                                         0xA0, 0xF1, 0x01, 0x01};
1494   uint8_t enable_ce_in_phone_off = 0x01;
1495   uint8_t enable_ven_cfg = 0x01;
1496 
1497   uint8_t swp_switch_timeout_cmd[] = {0x20, 0x02, 0x06, 0x01, 0xA0,
1498                                       0xF3, 0x02, 0x00, 0x00};
1499 
1500   config_success = true;
1501   long bufflen = 260;
1502   long retlen = 0;
1503   phNxpNci_EEPROM_info_t mEEPROM_info = {.request_mode = 0};
1504 #if (NFC_NXP_HFO_SETTINGS == TRUE)
1505   /* Temp fix to re-apply the proper clock setting */
1506   int temp_fix = 1;
1507 #endif
1508   unsigned long num = 0;
1509   /*initialize recovery FW variables*/
1510   gRecFwRetryCount = 0;
1511   gRecFWDwnld = 0;
1512   // recovery --start
1513   /*NCI_INIT_CMD*/
1514   static uint8_t cmd_init_nci[] = {0x20, 0x01, 0x00};
1515   /*NCI_RESET_CMD*/
1516   static uint8_t cmd_reset_nci[] = {0x20, 0x00, 0x01,
1517                                     0x00};  // keep configuration
1518   static uint8_t cmd_init_nci2_0[] = {0x20, 0x01, 0x02, 0x00, 0x00};
1519   /* reset config cache */
1520   uint8_t retry_core_init_cnt = 0;
1521   if (nxpncihal_ctrl.halStatus != HAL_STATUS_OPEN) {
1522     return NFCSTATUS_FAILED;
1523   }
1524   if (core_init_rsp_params_len >= 1 && (*p_core_init_rsp_params > 0) &&
1525       (*p_core_init_rsp_params < 4))  // initializing for recovery.
1526   {
1527   retry_core_init:
1528     config_access = false;
1529     if (mGetCfg_info != NULL) {
1530       mGetCfg_info->isGetcfg = false;
1531     }
1532     if (buffer != NULL) {
1533       free(buffer);
1534       buffer = NULL;
1535     }
1536     if (retry_core_init_cnt > 3) {
1537       return NFCSTATUS_FAILED;
1538     }
1539     if (IS_CHIP_TYPE_L(sn100u)) {
1540       status = phTmlNfc_IoCtl(phTmlNfc_e_ResetDevice);
1541       if (NFCSTATUS_SUCCESS == status) {
1542         NXPLOG_NCIHAL_D("PN54X Reset - SUCCESS\n");
1543       } else {
1544         NXPLOG_NCIHAL_D("PN54X Reset - FAILED\n");
1545       }
1546     }
1547 
1548     status = phNxpNciHal_send_ext_cmd(sizeof(cmd_reset_nci), cmd_reset_nci);
1549     if ((status != NFCSTATUS_SUCCESS) &&
1550         (nxpncihal_ctrl.retry_cnt >= MAX_RETRY_COUNT)) {
1551       NXPLOG_NCIHAL_E("Force FW Download, NFCC not coming out from Standby");
1552       retry_core_init_cnt++;
1553       goto retry_core_init;
1554     } else if (status != NFCSTATUS_SUCCESS) {
1555       NXPLOG_NCIHAL_E("NCI_CORE_RESET: Failed");
1556       retry_core_init_cnt++;
1557       goto retry_core_init;
1558     }
1559 
1560     if (nxpncihal_ctrl.nci_info.nci_version == NCI_VERSION_2_0) {
1561       status =
1562           phNxpNciHal_send_ext_cmd(sizeof(cmd_init_nci2_0), cmd_init_nci2_0);
1563     } else {
1564       status = phNxpNciHal_send_ext_cmd(sizeof(cmd_init_nci), cmd_init_nci);
1565     }
1566     if (status != NFCSTATUS_SUCCESS) {
1567       NXPLOG_NCIHAL_E("NCI_CORE_INIT : Failed");
1568       retry_core_init_cnt++;
1569       goto retry_core_init;
1570     }
1571   }
1572   // recovery --end
1573 
1574   buffer = (uint8_t*)malloc(bufflen * sizeof(uint8_t));
1575   if (NULL == buffer) {
1576     return NFCSTATUS_FAILED;
1577   }
1578   config_access = true;
1579   retlen = 0;
1580   isfound = GetNxpByteArrayValue(NAME_NXP_ACT_PROP_EXTN, (char*)buffer, bufflen,
1581                                  &retlen);
1582   if (isfound > 0 && retlen > 0) {
1583     /* NXP ACT Proprietary Ext */
1584     status = phNxpNciHal_send_ext_cmd(retlen, buffer);
1585     if (status != NFCSTATUS_SUCCESS) {
1586       NXPLOG_NCIHAL_E("NXP ACT Proprietary Ext failed");
1587       retry_core_init_cnt++;
1588       goto retry_core_init;
1589     }
1590   }
1591   if (IS_CHIP_TYPE_EQ(sn100u)) {
1592     uint8_t cmd_get_cfg_dbg_info[] = {0x20, 0x03, 0x0D, 0x06, 0xA0, 0x39,
1593                                       0xA0, 0x1A, 0xA0, 0x1B, 0xA0, 0x1C,
1594                                       0xA0, 0x27, 0xA1, 0x1F};
1595     status = phNxpNciHal_send_ext_cmd(sizeof(cmd_get_cfg_dbg_info),
1596                                       cmd_get_cfg_dbg_info);
1597   } else if (IS_CHIP_TYPE_GE(sn220u) || IS_CHIP_TYPE_EQ(pn557)) {
1598     uint8_t cmd_get_cfg_dbg_info[] = {0x20, 0x03, 0x0B, 0x05, 0xA0, 0x39, 0xA0,
1599                                       0x1A, 0xA0, 0x1B, 0xA0, 0x1C, 0xA0, 0x27};
1600     status = phNxpNciHal_send_ext_cmd(sizeof(cmd_get_cfg_dbg_info),
1601                                       cmd_get_cfg_dbg_info);
1602   }
1603   if (status != NFCSTATUS_SUCCESS) {
1604     NXPLOG_NCIHAL_E("Failed to retrieve NFCC debug info");
1605   }
1606 
1607   if (IS_CHIP_TYPE_GE(sn220u)) {
1608     uint8_t cmd_get_hard_fault_ctr_info[] = {0x20, 0x03, 0x03,
1609                                              0x01, 0xA1, 0x5A};
1610     status = phNxpNciHal_send_ext_cmd(sizeof(cmd_get_hard_fault_ctr_info),
1611                                       cmd_get_hard_fault_ctr_info);
1612     if (status != NFCSTATUS_SUCCESS) {
1613       NXPLOG_NCIHAL_E("Failed to retrieve NFCC hard fault counter debug info");
1614     }
1615   }
1616 
1617   num = 0;
1618   if (GetNxpNumValue("NXP_I3C_MODE", &num, sizeof(num))) {
1619     if (num == 1) {
1620       uint8_t coreStandBy[] = {0x2F, 0x00, 0x01, 0x00};
1621       NXPLOG_NCIHAL_E("Disable NFCC standby");
1622       status = phNxpNciHal_send_ext_cmd(sizeof(coreStandBy), coreStandBy);
1623       if (status != NFCSTATUS_SUCCESS) {
1624         NXPLOG_NCIHAL_E("Failed to set NFCC Standby Disabled");
1625       }
1626     }
1627   }
1628 
1629   status = phNxpNciHal_setAutonomousMode();
1630   if (status != NFCSTATUS_SUCCESS) {
1631     NXPLOG_NCIHAL_E("Set Autonomous enable: Failed");
1632     retry_core_init_cnt++;
1633     goto retry_core_init;
1634   }
1635 
1636   if (IS_CHIP_TYPE_EQ(pn557)) enable_ven_cfg = PN557_VEN_CFG_DEFAULT;
1637 
1638   mEEPROM_info.buffer = &enable_ven_cfg;
1639   mEEPROM_info.bufflen = sizeof(uint8_t);
1640   mEEPROM_info.request_type = EEPROM_ENABLE_VEN_CFG;
1641   mEEPROM_info.request_mode = SET_EEPROM_DATA;
1642   request_EEPROM(&mEEPROM_info);
1643 
1644   if (IS_CHIP_TYPE_GE(sn100u)) {
1645     mEEPROM_info.buffer = &enable_ce_in_phone_off;
1646     mEEPROM_info.bufflen = sizeof(enable_ce_in_phone_off);
1647     mEEPROM_info.request_type = EEPROM_CE_PHONE_OFF_CFG;
1648     mEEPROM_info.request_mode = SET_EEPROM_DATA;
1649     request_EEPROM(&mEEPROM_info);
1650   }
1651 
1652   phNxpNciHal_propConfULPDetMode(false);
1653 
1654   if (gPowerTrackerHandle.start != NULL) {
1655     gPowerTrackerHandle.start(gPowerTrackerHandle.pollDuration);
1656   }
1657   config_access = false;
1658   status = phNxpNciHal_read_fw_dw_status(fw_dwnld_flag);
1659   if (status != NFCSTATUS_SUCCESS) {
1660     NXPLOG_NCIHAL_E("%s: NXP get FW DW Flag failed", __FUNCTION__);
1661   }
1662   fw_dwnld_flag |= (bool)fw_download_success;
1663   if (fw_dwnld_flag == true) {
1664     phNxpNciHal_hci_network_reset();
1665   }
1666   if (IS_CHIP_TYPE_L(sn100u)) {
1667     // Check if firmware download success
1668     status = phNxpNciHal_get_mw_eeprom();
1669     if (status != NFCSTATUS_SUCCESS) {
1670       NXPLOG_NCIHAL_E("NXP GET MW EEPROM AREA Proprietary Ext failed");
1671       retry_core_init_cnt++;
1672       goto retry_core_init;
1673     }
1674   }
1675 
1676   config_access = true;
1677   setConfigAlways = false;
1678   isfound = GetNxpNumValue(NAME_NXP_SET_CONFIG_ALWAYS, &num, sizeof(num));
1679   if (isfound > 0) {
1680     setConfigAlways = num;
1681   }
1682   NXPLOG_NCIHAL_D("EEPROM_fw_dwnld_flag : 0x%02x SetConfigAlways flag : 0x%02x",
1683                   fw_dwnld_flag, setConfigAlways);
1684 
1685   if (isNxpConfigModified() || (fw_dwnld_flag == true)) {
1686     retlen = 0;
1687     fw_download_success = 0;
1688 
1689     /* EEPROM access variables */
1690     mEEPROM_info.request_mode = GET_EEPROM_DATA;
1691     retlen = 0;
1692     memset(buffer, 0x00, bufflen);
1693     isfound = GetNxpByteArrayValue(NAME_NXP_AUTH_TIMEOUT_CFG, (char*)buffer,
1694                                    bufflen, &retlen);
1695 
1696     if ((isfound > 0) && (retlen > 0)) {
1697       uint64_t auth_timeout_buffer_length;
1698       if (IS_CHIP_TYPE_GE(sn100u)) {
1699         auth_timeout_buffer_length = SNXXX_NXP_AUTH_TIMEOUT_BUF_LEN;
1700       } else {
1701         auth_timeout_buffer_length = PN557_NXP_AUTH_TIMEOUT_BUF_LEN;
1702       }
1703       uint8_t auth_timeout_buffer[auth_timeout_buffer_length];
1704       memcpy(&auth_timeout_buffer, buffer, auth_timeout_buffer_length);
1705       mEEPROM_info.request_mode = SET_EEPROM_DATA;
1706       mEEPROM_info.buffer = auth_timeout_buffer;
1707       mEEPROM_info.bufflen = auth_timeout_buffer_length;
1708       mEEPROM_info.request_type = EEPROM_AUTH_CMD_TIMEOUT;
1709       status = request_EEPROM(&mEEPROM_info);
1710       if (NFCSTATUS_SUCCESS == status) {
1711         memcpy(&mGetCfg_info->auth_cmd_timeout, mEEPROM_info.buffer,
1712                mEEPROM_info.bufflen);
1713         mGetCfg_info->auth_cmd_timeoutlen = mEEPROM_info.bufflen;
1714       }
1715     }
1716     NXPLOG_NCIHAL_D("Performing TVDD Settings");
1717     isfound = GetNxpNumValue(NAME_NXP_EXT_TVDD_CFG, &num, sizeof(num));
1718     if (isfound > 0) {
1719       if (num == 1) {
1720         isfound = GetNxpByteArrayValue(NAME_NXP_EXT_TVDD_CFG_1, (char*)buffer,
1721                                        bufflen, &retlen);
1722         if (isfound && retlen > 0) {
1723           status = phNxpNciHal_send_ext_cmd(retlen, buffer);
1724           if (status != NFCSTATUS_SUCCESS) {
1725             NXPLOG_NCIHAL_E("EXT TVDD CFG 1 Settings failed");
1726             retry_core_init_cnt++;
1727             goto retry_core_init;
1728           }
1729         }
1730       } else if (num == 2) {
1731         isfound = GetNxpByteArrayValue(NAME_NXP_EXT_TVDD_CFG_2, (char*)buffer,
1732                                        bufflen, &retlen);
1733         if (isfound && retlen > 0) {
1734           status = phNxpNciHal_send_ext_cmd(retlen, buffer);
1735           if (status != NFCSTATUS_SUCCESS) {
1736             NXPLOG_NCIHAL_E("EXT TVDD CFG 2 Settings failed");
1737             retry_core_init_cnt++;
1738             goto retry_core_init;
1739           }
1740         }
1741       } else if (num == 3) {
1742         isfound = GetNxpByteArrayValue(NAME_NXP_EXT_TVDD_CFG_3, (char*)buffer,
1743                                        bufflen, &retlen);
1744         if (isfound && retlen > 0) {
1745           status = phNxpNciHal_send_ext_cmd(retlen, buffer);
1746           if (status != NFCSTATUS_SUCCESS) {
1747             NXPLOG_NCIHAL_E("EXT TVDD CFG 3 Settings failed");
1748             retry_core_init_cnt++;
1749             goto retry_core_init;
1750           }
1751         }
1752       } else {
1753         NXPLOG_NCIHAL_E("Wrong Configuration Value %ld", num);
1754       }
1755     }
1756   }
1757   if ((true == fw_dwnld_flag) || (true == setConfigAlways) ||
1758       isNxpConfigModified()) {
1759     config_access = true;
1760 
1761     if (IS_CHIP_TYPE_NE(pn547C2)) {
1762       config_access = true;
1763     }
1764 
1765     retlen = 0;
1766     /*Select UICC2/UICC3 SWP line from config param*/
1767     if (GetNxpNumValue(NAME_NXP_DEFAULT_UICC2_SELECT, (void*)&retlen,
1768                        sizeof(retlen))) {
1769       if (retlen > 0) phNxpNciHal_enableDefaultUICC2SWPline((uint8_t)retlen);
1770     }
1771     status = phNxpNciHal_setExtendedFieldMode();
1772     if (status != NFCSTATUS_SUCCESS &&
1773         status != NFCSTATUS_FEATURE_NOT_SUPPORTED) {
1774       NXPLOG_NCIHAL_E("phNxpNciHal_setExtendedFieldMode failed");
1775       retry_core_init_cnt++;
1776       goto retry_core_init;
1777     }
1778     status = phNxpNciHal_setGuardTimer();
1779     if (status != NFCSTATUS_SUCCESS &&
1780         status != NFCSTATUS_FEATURE_NOT_SUPPORTED) {
1781       NXPLOG_NCIHAL_E("phNxpNciHal_setGuardTimer failed");
1782       retry_core_init_cnt++;
1783       goto retry_core_init;
1784     }
1785 #if (NXP_SRD == TRUE)
1786     status = phNxpNciHal_setSrdtimeout();
1787     if (status != NFCSTATUS_SUCCESS &&
1788         status != NFCSTATUS_FEATURE_NOT_SUPPORTED) {
1789       NXPLOG_NCIHAL_E("phNxpNciHal_setSrdtimeout failed");
1790       retry_core_init_cnt++;
1791       goto retry_core_init;
1792     }
1793 #endif
1794     config_access = true;
1795     retlen = 0;
1796     NXPLOG_NCIHAL_D("Performing ndef nfcee config settings");
1797     uint8_t cmd_t4t_nfcee_cfg;
1798 
1799     if (!GetNxpNumValue(NAME_NXP_T4T_NFCEE_ENABLE, (void*)&retlen,
1800                         sizeof(retlen))) {
1801       retlen = 0x00;
1802       NXPLOG_NCIHAL_D(
1803           "T4T_NFCEE_ENABLE not found. Taking default value : 0x%02lx", retlen);
1804     }
1805     cmd_t4t_nfcee_cfg = (uint8_t)retlen;
1806     mEEPROM_info.buffer = &cmd_t4t_nfcee_cfg;
1807     mEEPROM_info.bufflen = sizeof(cmd_t4t_nfcee_cfg);
1808     mEEPROM_info.request_type = EEPROM_T4T_NFCEE_ENABLE;
1809     mEEPROM_info.request_mode = SET_EEPROM_DATA;
1810     request_EEPROM(&mEEPROM_info);
1811     if (IS_CHIP_TYPE_GE(sn100u)) {
1812       if (phNxpNciHal_configure_merge_sak() != NFCSTATUS_SUCCESS) {
1813         NXPLOG_NCIHAL_E("Applying iso_dep sak merge settings failed");
1814       }
1815     }
1816   }
1817   if ((true == fw_dwnld_flag) || (true == setConfigAlways) ||
1818       isNxpConfigModified() || (wRfUpdateReq == true)) {
1819     retlen = 0;
1820     NXPLOG_NCIHAL_D("Performing NAME_NXP_CORE_CONF_EXTN Settings");
1821     isfound = GetNxpByteArrayValue(NAME_NXP_CORE_CONF_EXTN, (char*)buffer,
1822                                    bufflen, &retlen);
1823     if (isfound > 0 && retlen > 0) {
1824       /* NXP ACT Proprietary Ext */
1825       status = phNxpNciHal_send_ext_cmd(retlen, buffer);
1826       if (status != NFCSTATUS_SUCCESS) {
1827         NXPLOG_NCIHAL_E("NXP Core configuration failed");
1828         retry_core_init_cnt++;
1829         goto retry_core_init;
1830       }
1831     }
1832 
1833     NXPLOG_NCIHAL_D("Performing SE Settings");
1834     phNxpNciHal_read_and_update_se_state();
1835 
1836     NXPLOG_NCIHAL_D("Performing NAME_NXP_CORE_CONF Settings");
1837     retlen = 0;
1838     isfound = GetNxpByteArrayValue(NAME_NXP_CORE_CONF, (char*)buffer, bufflen,
1839                                    &retlen);
1840     if (isfound > 0 && retlen > 0) {
1841       /* NXP ACT Proprietary Ext */
1842       status = phNxpNciHal_send_ext_cmd(retlen, buffer);
1843       if (status != NFCSTATUS_SUCCESS) {
1844         NXPLOG_NCIHAL_E("Core Set Config failed");
1845         retry_core_init_cnt++;
1846         goto retry_core_init;
1847       }
1848     }
1849 
1850     if (fpVerInfoStoreInEeprom != NULL) {
1851       fpVerInfoStoreInEeprom();
1852     }
1853   }
1854   config_access = false;
1855   if ((true == fw_dwnld_flag) || (true == setConfigAlways) ||
1856       isNxpRFConfigModified()) {
1857     unsigned long loopcnt = 0;
1858 
1859     do {
1860       char rf_conf_block[22] = {'\0'};
1861       strlcpy(rf_conf_block, rf_block_name, sizeof(rf_conf_block));
1862       retlen = 0;
1863       strlcat(rf_conf_block, rf_block_num[loopcnt++], sizeof(rf_conf_block));
1864       isfound =
1865           GetNxpByteArrayValue(rf_conf_block, (char*)buffer, bufflen, &retlen);
1866       if (isfound > 0 && retlen > 0) {
1867         NXPLOG_NCIHAL_D(" Performing RF Settings BLK %ld", loopcnt);
1868         status = phNxpNciHal_send_ext_cmd(retlen, buffer);
1869 
1870         if (status == NFCSTATUS_SUCCESS) {
1871           status = phNxpNciHal_CheckRFCmdRespStatus();
1872           /*STATUS INVALID PARAM 0x09*/
1873           if (status == 0x09) {
1874             phNxpNciHalRFConfigCmdRecSequence();
1875             retry_core_init_cnt++;
1876             goto retry_core_init;
1877           }
1878         } else if (status != NFCSTATUS_SUCCESS) {
1879           NXPLOG_NCIHAL_E("RF Settings BLK %ld failed", loopcnt);
1880           retry_core_init_cnt++;
1881           goto retry_core_init;
1882         }
1883       }
1884     } while (rf_block_num[loopcnt] != NULL);
1885     loopcnt = 0;
1886     if (phNxpNciHal_nfccClockCfgApply() != NFCSTATUS_SUCCESS) {
1887       NXPLOG_NCIHAL_E("phNxpNciHal_nfccClockCfgApply failed");
1888       retry_core_init_cnt++;
1889       goto retry_core_init;
1890     }
1891   }
1892 
1893   config_access = true;
1894 
1895   retlen = 0;
1896   if (IS_CHIP_TYPE_NE(pn547C2)) {
1897     config_access = false;
1898   }
1899   isfound = GetNxpByteArrayValue(NAME_NXP_CORE_RF_FIELD, (char*)buffer, bufflen,
1900                                  &retlen);
1901   if (isfound > 0 && retlen > 0) {
1902     /* NXP ACT Proprietary Ext */
1903     status = phNxpNciHal_send_ext_cmd(retlen, buffer);
1904     if (status == NFCSTATUS_SUCCESS) {
1905       status = phNxpNciHal_CheckRFCmdRespStatus();
1906       /*STATUS INVALID PARAM 0x09*/
1907       if (status == 0x09) {
1908         phNxpNciHalRFConfigCmdRecSequence();
1909         retry_core_init_cnt++;
1910         goto retry_core_init;
1911       }
1912     } else if (status != NFCSTATUS_SUCCESS) {
1913       NXPLOG_NCIHAL_E("Setting NXP_CORE_RF_FIELD status failed");
1914       retry_core_init_cnt++;
1915       goto retry_core_init;
1916     }
1917   }
1918   config_access = true;
1919 
1920   retlen = 0;
1921   /* NXP SWP switch timeout Setting*/
1922   if (GetNxpNumValue(NAME_NXP_SWP_SWITCH_TIMEOUT, (void*)&retlen,
1923                      sizeof(retlen))) {
1924     // Check the permissible range [0 - 60]
1925     if (0 <= retlen && retlen <= 60) {
1926       if (0 < retlen) {
1927         unsigned int timeout = (uint32_t)retlen * 1000;
1928         unsigned int timeoutHx = 0x0000;
1929 
1930         char tmpbuffer[10] = {0};
1931         snprintf((char*)tmpbuffer, 10, "%04x", timeout);
1932         int ret = sscanf((char*)tmpbuffer, "%x", &timeoutHx);
1933         if (!ret) timeoutHx = 0x0000;
1934 
1935         swp_switch_timeout_cmd[7] = (timeoutHx & 0xFF);
1936         swp_switch_timeout_cmd[8] = ((timeoutHx & 0xFF00) >> 8);
1937       }
1938 
1939       status = phNxpNciHal_send_ext_cmd(sizeof(swp_switch_timeout_cmd),
1940                                         swp_switch_timeout_cmd);
1941       if (status != NFCSTATUS_SUCCESS) {
1942         NXPLOG_NCIHAL_E("SWP switch timeout Setting Failed");
1943         retry_core_init_cnt++;
1944         goto retry_core_init;
1945       }
1946     } else {
1947       NXPLOG_NCIHAL_E("SWP switch timeout Setting Failed - out of range!");
1948     }
1949   }
1950 
1951   status = phNxpNciHal_china_tianjin_rf_setting();
1952   if (status != NFCSTATUS_SUCCESS) {
1953     NXPLOG_NCIHAL_E("phNxpNciHal_china_tianjin_rf_setting failed");
1954     retry_core_init_cnt++;
1955     goto retry_core_init;
1956   }
1957   if (IS_CHIP_TYPE_L(sn100u)) {
1958     // Update eeprom value
1959     status = phNxpNciHal_set_mw_eeprom();
1960     if (status != NFCSTATUS_SUCCESS) {
1961       NXPLOG_NCIHAL_E("NXP Update MW EEPROM Proprietary Ext failed");
1962     }
1963   }
1964 
1965   retlen = 0;
1966   config_access = false;
1967   // if recovery mode and length of last command is 0 then only reset the P2P
1968   // listen mode routing.
1969   if (core_init_rsp_params_len >= 36 && (*p_core_init_rsp_params > 0) &&
1970       (*p_core_init_rsp_params < 4) && p_core_init_rsp_params[35] == 0) {
1971     /* P2P listen mode routing */
1972     status = phNxpNciHal_send_ext_cmd(sizeof(p2p_listen_mode_routing_cmd),
1973                                       p2p_listen_mode_routing_cmd);
1974     if (status != NFCSTATUS_SUCCESS) {
1975       NXPLOG_NCIHAL_E("P2P listen mode routing failed");
1976       retry_core_init_cnt++;
1977       goto retry_core_init;
1978     }
1979   }
1980 
1981   retlen = 0;
1982 
1983   /* SWP FULL PWR MODE SETTING ON */
1984   if (GetNxpNumValue(NAME_NXP_SWP_FULL_PWR_ON, (void*)&retlen,
1985                      sizeof(retlen))) {
1986     if (1 == retlen) {
1987       status = phNxpNciHal_send_ext_cmd(sizeof(swp_full_pwr_mode_on_cmd),
1988                                         swp_full_pwr_mode_on_cmd);
1989       if (status != NFCSTATUS_SUCCESS) {
1990         NXPLOG_NCIHAL_E("SWP FULL PWR MODE SETTING ON CMD FAILED");
1991         retry_core_init_cnt++;
1992         goto retry_core_init;
1993       }
1994     } else {
1995       swp_full_pwr_mode_on_cmd[7] = 0x00;
1996       status = phNxpNciHal_send_ext_cmd(sizeof(swp_full_pwr_mode_on_cmd),
1997                                         swp_full_pwr_mode_on_cmd);
1998       if (status != NFCSTATUS_SUCCESS) {
1999         NXPLOG_NCIHAL_E("SWP FULL PWR MODE SETTING OFF CMD FAILED");
2000         retry_core_init_cnt++;
2001         goto retry_core_init;
2002       }
2003     }
2004   }
2005 
2006   uint8_t gpioCtrl[3] = {0x00, 0x00, 0x00};
2007   long gpioCtrlLen = 0;
2008   isfound = GetNxpByteArrayValue(NAME_CONF_GPIO_CONTROL, (char*)gpioCtrl,
2009                                  sizeof(gpioCtrl), &gpioCtrlLen);
2010   if (isfound > 0 && gpioCtrlLen != 0) {
2011     phNxpNciHal_configGPIOControl(gpioCtrl, gpioCtrlLen);
2012   }
2013 
2014   isfound = GetNxpNumValue(NAME_NXP_NCI_PARSER_LIBRARY, &num, sizeof(num));
2015   if (isfound > 0 && num == 0x01) {
2016     phNxpNciHal_configNciParser(true);
2017     NXPLOG_NCIHAL_D("NCI Parser is enabled");
2018   } else if (isfound > 0 && num == 0x00) {
2019     NXPLOG_NCIHAL_D("Disabling NCI Parser...");
2020     phNxpNciHal_configNciParser(false);
2021   } else {
2022     NXPLOG_NCIHAL_D("NCI Parser is disabled");
2023   }
2024 
2025   if (IS_CHIP_TYPE_EQ(pn557)) {
2026     if (GetNxpNumValue(NAME_NXP_PROP_CE_ACTION_NTF, (void*)&retlen,
2027                        sizeof(retlen))) {
2028       uint8_t value = (uint8_t)retlen;
2029       NXPLOG_NCIHAL_D("Prop CE ACT NTF %x", value);
2030       mEEPROM_info.buffer = &value;
2031       mEEPROM_info.bufflen = sizeof(value);
2032       mEEPROM_info.request_type = EEPROM_CE_ACT_NTF;
2033       mEEPROM_info.request_mode = SET_EEPROM_DATA;
2034       request_EEPROM(&mEEPROM_info);
2035     }
2036   }
2037 
2038   config_access = false;
2039   {
2040     if (isNxpRFConfigModified() || isNxpConfigModified() || fw_dwnld_flag ||
2041         setConfigAlways) {
2042       if (IS_CHIP_TYPE_GE(sn100u)) {
2043         status = phNxpNciHal_ext_send_sram_config_to_flash();
2044         if (status != NFCSTATUS_SUCCESS) {
2045           NXPLOG_NCIHAL_E("Updation of the SRAM contents failed");
2046         }
2047       }
2048       status = phNxpNciHal_send_ext_cmd(sizeof(cmd_reset_nci), cmd_reset_nci);
2049       if (status == NFCSTATUS_SUCCESS) {
2050         if (nxpncihal_ctrl.nci_info.nci_version == NCI_VERSION_2_0) {
2051           status = phNxpNciHal_send_ext_cmd(sizeof(cmd_init_nci2_0),
2052                                             cmd_init_nci2_0);
2053         } else {
2054           status = phNxpNciHal_send_ext_cmd(sizeof(cmd_init_nci), cmd_init_nci);
2055         }
2056       }
2057     }
2058     if (status == NFCSTATUS_SUCCESS) {
2059       status = phNxpNciHal_restore_uicc_params();
2060       if (status != NFCSTATUS_SUCCESS) {
2061         NXPLOG_NCIHAL_E("%s: Restore UICC params failed", __FUNCTION__);
2062       }
2063 
2064       phNxpNciHal_prop_conf_rssi();
2065 
2066       fw_dwnld_flag = false;
2067       status = phNxpNciHal_write_fw_dw_status(fw_dwnld_flag);
2068       if (status != NFCSTATUS_SUCCESS) {
2069         NXPLOG_NCIHAL_E("%s: NXP Set FW Download Flag failed", __FUNCTION__);
2070       }
2071       status = phNxpNciHal_send_get_cfgs();
2072       if (status == NFCSTATUS_SUCCESS) {
2073         NXPLOG_NCIHAL_E("Send get Configs SUCCESS");
2074       } else {
2075         NXPLOG_NCIHAL_E("Send get Configs FAILED");
2076       }
2077     }
2078   }
2079   retry_core_init_cnt = 0;
2080 
2081   if (buffer) {
2082     free(buffer);
2083     buffer = NULL;
2084   }
2085   // initialize recovery FW variables
2086   gRecFWDwnld = 0;
2087   gRecFwRetryCount = 0;
2088 
2089   phNxpNciHal_core_initialized_complete(status);
2090   if (isNxpConfigModified()) {
2091     updateNxpConfigTimestamp();
2092   }
2093   if (isNxpRFConfigModified()) {
2094     updateNxpRfConfigTimestamp();
2095   }
2096   return NFCSTATUS_SUCCESS;
2097 }
2098 /******************************************************************************
2099  * Function         phNxpNciHal_CheckRFCmdRespStatus
2100  *
2101  * Description      This function is called to check the resp status of
2102  *                  RF update commands.
2103  *
2104  * Returns          NFCSTATUS_SUCCESS           if successful,
2105  *                  NFCSTATUS_INVALID_PARAMETER if parameter is inavlid
2106  *                  NFCSTATUS_FAILED            if failed response
2107  *
2108  ******************************************************************************/
phNxpNciHal_CheckRFCmdRespStatus()2109 NFCSTATUS phNxpNciHal_CheckRFCmdRespStatus() {
2110   NFCSTATUS status = NFCSTATUS_SUCCESS;
2111   static uint16_t INVALID_PARAM = 0x09;
2112   if ((nxpncihal_ctrl.rx_data_len > 0) && (nxpncihal_ctrl.p_rx_data[2] > 0)) {
2113     if (nxpncihal_ctrl.p_rx_data[3] == 0x09) {
2114       status = INVALID_PARAM;
2115     } else if (nxpncihal_ctrl.p_rx_data[3] != NFCSTATUS_SUCCESS) {
2116       status = NFCSTATUS_FAILED;
2117     }
2118   }
2119   return status;
2120 }
2121 /******************************************************************************
2122  * Function         phNxpNciHalRFConfigCmdRecSequence
2123  *
2124  * Description      This function is called to handle recovery FW sequence
2125  *                  Whenever RF settings are failed to apply with invalid param
2126  *                  response, recovery mechanism includes recovery firmware
2127  *                  download followed by firmware download and then config
2128  *                  settings. The recovery firmware changes the major number of
2129  *                  the firmware inside NFCC.Then actual firmware dowenload will
2130  *                  be successful. This can be retried maximum three times.
2131  *
2132  * Returns          Always returns NFCSTATUS_SUCCESS
2133  *
2134  ******************************************************************************/
phNxpNciHalRFConfigCmdRecSequence()2135 NFCSTATUS phNxpNciHalRFConfigCmdRecSequence() {
2136   NFCSTATUS status = NFCSTATUS_SUCCESS;
2137   uint16_t recFWState = 1;
2138   gRecFWDwnld = true;
2139   gRecFwRetryCount++;
2140   if (gRecFwRetryCount > 0x03) {
2141     NXPLOG_NCIHAL_D("Max retry count for RF config FW recovery exceeded ");
2142     gRecFWDwnld = false;
2143     return NFCSTATUS_FAILED;
2144   }
2145   do {
2146     status = phTmlNfc_IoCtl(phTmlNfc_e_ResetDevice);
2147     phDnldNfc_InitImgInfo();
2148     if (NFCSTATUS_SUCCESS == phNxpNciHal_CheckValidFwVersion()) {
2149       status = phNxpNciHal_fw_download();
2150       if (status != NFCSTATUS_SUCCESS) {
2151         NXPLOG_NCIHAL_E("error in download = %x", status);
2152       }
2153       break;
2154     }
2155     gRecFWDwnld = false;
2156   } while (recFWState--);
2157   gRecFWDwnld = false;
2158   return status;
2159 }
2160 
2161 /******************************************************************************
2162  * Function         phNxpNciHal_core_initialized_complete
2163  *
2164  * Description      This function is called when phNxpNciHal_core_initialized
2165  *                  complete all proprietary command exchanges. This function
2166  *                  informs libnfc-nci about completion of core initialize
2167  *                  and result of that through callback.
2168  *
2169  * Returns          void.
2170  *
2171  ******************************************************************************/
phNxpNciHal_core_initialized_complete(NFCSTATUS status)2172 static void phNxpNciHal_core_initialized_complete(NFCSTATUS status) {
2173   static phLibNfc_Message_t msg;
2174 
2175   if (status == NFCSTATUS_SUCCESS) {
2176     msg.eMsgType = NCI_HAL_POST_INIT_CPLT_MSG;
2177   } else {
2178     msg.eMsgType = NCI_HAL_ERROR_MSG;
2179   }
2180   msg.pMsgData = NULL;
2181   msg.Size = 0;
2182 
2183   phTmlNfc_DeferredCall(gpphTmlNfc_Context->dwCallbackThreadId,
2184                         (phLibNfc_Message_t*)&msg);
2185   return;
2186 }
2187 
2188 /******************************************************************************
2189  * Function         phNxpNciHal_pre_discover
2190  *
2191  * Description      This function is called by libnfc-nci to perform any
2192  *                  proprietary exchange before RF discovery.
2193  *
2194  * Returns          It always returns NFCSTATUS_SUCCESS (0).
2195  *
2196  ******************************************************************************/
phNxpNciHal_pre_discover(void)2197 int phNxpNciHal_pre_discover(void) {
2198   /* Nothing to do here for initial version */
2199   // This is set to return Failed as no vendor specific pre-discovery action is
2200   // needed in case of HalPrediscover
2201   return NFCSTATUS_FAILED;
2202 }
2203 
2204 /******************************************************************************
2205  * Function         phNxpNciHal_release_info
2206  *
2207  * Description      This function frees allocated memory for mGetCfg_info
2208  *
2209  * Returns          void.
2210  *
2211  ******************************************************************************/
phNxpNciHal_release_info(void)2212 static void phNxpNciHal_release_info(void) {
2213   NXPLOG_NCIHAL_D("phNxpNciHal_release_info mGetCfg_info");
2214   if (mGetCfg_info != NULL) {
2215     free(mGetCfg_info);
2216     mGetCfg_info = NULL;
2217   }
2218 }
2219 /******************************************************************************
2220  * Function         phNxpNciHal_close
2221  *
2222  * Description      This function close the NFCC interface and free all
2223  *                  resources.This is called by libnfc-nci on NFC service stop.
2224  *
2225  * Returns          Always return NFCSTATUS_SUCCESS (0).
2226  *
2227  ******************************************************************************/
phNxpNciHal_close(bool bShutdown)2228 int phNxpNciHal_close(bool bShutdown) {
2229   NFCSTATUS status = NFCSTATUS_FAILED;
2230   uint8_t cmd_ce_discovery_nci[10] = {
2231       0x21,
2232       0x03,
2233   };
2234   uint8_t cmd_reset_nci[] = {0x20, 0x00, 0x01, 0x00};
2235   uint8_t cmd_ce_in_phone_off[] = {0x20, 0x02, 0x05, 0x01,
2236                                    0xA0, 0x8E, 0x01, 0x00};
2237   uint8_t cmd_ce_in_phone_off_pn557[] = {0x20, 0x02, 0x05, 0x01,
2238                                          0xA0, 0x07, 0x01, 0x02};
2239   uint8_t cmd_system_set_service_status[] = {0x2F, 0x01, 0x01, 0x00};
2240   uint8_t length = 0;
2241   uint8_t numPrms = 0;
2242   uint8_t ptr = 4;
2243   unsigned long uiccListenMask = 0x00;
2244   unsigned long eseListenMask = 0x00;
2245   uint8_t retry = 0;
2246 
2247   phNxpNciHal_deinitializeRegRfFwDnld();
2248   NfcHalAutoThreadMutex a(sHalFnLock);
2249   if (nxpncihal_ctrl.halStatus == HAL_STATUS_CLOSE) {
2250     NXPLOG_NCIHAL_D("phNxpNciHal_close is already closed, ignoring close");
2251     return NFCSTATUS_FAILED;
2252   }
2253   if (gPowerTrackerHandle.stop != NULL) {
2254     gPowerTrackerHandle.stop();
2255   }
2256   if (IS_CHIP_TYPE_L(sn100u)) {
2257     if (!(GetNxpNumValue(NAME_NXP_UICC_LISTEN_TECH_MASK, &uiccListenMask,
2258                          sizeof(uiccListenMask)))) {
2259       uiccListenMask = 0x07;
2260       NXPLOG_NCIHAL_D("UICC_LISTEN_TECH_MASK = 0x%0lX", uiccListenMask);
2261     }
2262 
2263     if (!(GetNxpNumValue(NAME_NXP_ESE_LISTEN_TECH_MASK, &eseListenMask,
2264                          sizeof(eseListenMask)))) {
2265       eseListenMask = 0x07;
2266       NXPLOG_NCIHAL_D("NXP_ESE_LISTEN_TECH_MASK = 0x%0lX", eseListenMask);
2267     }
2268   }
2269 
2270   CONCURRENCY_LOCK();
2271   int sem_val;
2272   sem_getvalue(&(nxpncihal_ctrl.syncSpiNfc), &sem_val);
2273   if (sem_val == 0) {
2274     sem_post(&(nxpncihal_ctrl.syncSpiNfc));
2275   }
2276   if (!bShutdown && phNxpNciHal_getULPDetFlag() == false) {
2277     if (IS_CHIP_TYPE_GE(sn100u)) {
2278       status = phNxpNciHal_send_ext_cmd(sizeof(cmd_ce_in_phone_off),
2279                                         cmd_ce_in_phone_off);
2280       if (status != NFCSTATUS_SUCCESS) {
2281         NXPLOG_NCIHAL_E("CMD_CE_IN_PHONE_OFF: Failed");
2282       }
2283       config_ext.autonomous_mode = 0x00;
2284       status = phNxpNciHal_setAutonomousMode();
2285       if (status != NFCSTATUS_SUCCESS) {
2286         NXPLOG_NCIHAL_E("Autonomous mode Disable: Failed");
2287       }
2288     } else {
2289       status = phNxpNciHal_send_ext_cmd(sizeof(cmd_ce_in_phone_off_pn557),
2290                                         cmd_ce_in_phone_off_pn557);
2291       if (status != NFCSTATUS_SUCCESS) {
2292         NXPLOG_NCIHAL_E("CMD_CE_IN_PHONE_OFF: Failed");
2293       }
2294     }
2295   }
2296   if (nfcFL.nfccFL._NFCC_I2C_READ_WRITE_IMPROVEMENT &&
2297       read_failed_disable_nfc) {
2298     read_failed_disable_nfc = false;
2299     goto close_and_return;
2300   }
2301 
2302   if (write_unlocked_status == NFCSTATUS_FAILED) {
2303     NXPLOG_NCIHAL_D("phNxpNciHal_close i2c write failed .Clean and Return");
2304     goto close_and_return;
2305   }
2306 
2307   if ((!bShutdown) && IS_CHIP_TYPE_L(sn100u)) {
2308     if ((uiccListenMask & 0x1) == 0x01 || (eseListenMask & 0x1) == 0x01) {
2309       NXPLOG_NCIHAL_D("phNxpNciHal_close (): Adding A passive listen");
2310       numPrms++;
2311       cmd_ce_discovery_nci[ptr++] = 0x80;
2312       cmd_ce_discovery_nci[ptr++] = 0x01;
2313       length += 2;
2314     }
2315     if ((uiccListenMask & 0x2) == 0x02 || (eseListenMask & 0x4) == 0x04) {
2316       NXPLOG_NCIHAL_D("phNxpNciHal_close (): Adding B passive listen");
2317       numPrms++;
2318       cmd_ce_discovery_nci[ptr++] = 0x81;
2319       cmd_ce_discovery_nci[ptr++] = 0x01;
2320       length += 2;
2321     }
2322     if ((uiccListenMask & 0x4) == 0x04 || (eseListenMask & 0x4) == 0x04) {
2323       NXPLOG_NCIHAL_D("phNxpNciHal_close (): Adding F passive listen");
2324       numPrms++;
2325       cmd_ce_discovery_nci[ptr++] = 0x82;
2326       cmd_ce_discovery_nci[ptr++] = 0x01;
2327       length += 2;
2328     }
2329 
2330     if (length != 0) {
2331       cmd_ce_discovery_nci[2] = length + 1;
2332       cmd_ce_discovery_nci[3] = numPrms;
2333       status = phNxpNciHal_send_ext_cmd(length + 4, cmd_ce_discovery_nci);
2334       if (status != NFCSTATUS_SUCCESS) {
2335         NXPLOG_NCIHAL_E("CMD_CE_DISC_NCI: Failed");
2336       }
2337     } else {
2338       NXPLOG_NCIHAL_E(
2339           "No changes in the discovery command, sticking to last discovery "
2340           "command sent");
2341     }
2342   } else if ((!bShutdown) && IS_CHIP_TYPE_GE(sn220u)) {
2343     if (phNxpNciHal_getULPDetFlag() == true) {
2344       phNxpNciHal_propConfULPDetMode(true);
2345     }
2346   }
2347 close_and_return:
2348   if (IS_CHIP_TYPE_L(sn220u) || bShutdown) {
2349     nxpncihal_ctrl.halStatus = HAL_STATUS_CLOSE;
2350   }
2351   if (phNxpNciHal_getULPDetFlag() == false) {
2352     do {
2353       status = phNxpNciHal_send_ext_cmd(sizeof(cmd_reset_nci), cmd_reset_nci);
2354 
2355       if (status == NFCSTATUS_SUCCESS) {
2356         break;
2357       } else {
2358         NXPLOG_NCIHAL_E("NCI_CORE_RESET: Failed, perform retry after delay");
2359         usleep(1000 * 1000);
2360         retry++;
2361         if (retry > 3) {
2362           NXPLOG_NCIHAL_E(
2363               "Maximum retries performed, shall restart HAL to recover");
2364           abort();
2365         }
2366       }
2367     } while (retry < 3);
2368 
2369     if (IS_CHIP_TYPE_GE(sn220u) && !bShutdown) {
2370       nxpncihal_ctrl.halStatus = HAL_STATUS_CLOSE;
2371       status = phNxpNciHal_send_ext_cmd(sizeof(cmd_system_set_service_status),
2372                                         cmd_system_set_service_status);
2373       if (status != NFCSTATUS_SUCCESS) {
2374         NXPLOG_NCIHAL_E("NCI SYSTEM SET SERVICE STATUS to OFF Failed");
2375       }
2376     }
2377   }
2378 
2379   sem_destroy(&nxpncihal_ctrl.syncSpiNfc);
2380 
2381   if (gParserCreated) {
2382     phNxpNciHal_deinitParser();
2383     gParserCreated = FALSE;
2384   }
2385   if (NULL != gpphTmlNfc_Context->pDevHandle) {
2386     phNxpNciHal_close_complete(NFCSTATUS_SUCCESS);
2387     /* Abort any pending read and write */
2388     status = phTmlNfc_ReadAbort();
2389     status = phTmlNfc_WriteAbort();
2390 
2391     phOsalNfc_Timer_Cleanup();
2392 
2393     status = phTmlNfc_Shutdown();
2394 
2395     if (0 != pthread_join(nxpncihal_ctrl.client_thread, (void**)NULL)) {
2396       NXPLOG_TML_E("Fail to kill client thread!");
2397     }
2398 
2399     phTmlNfc_CleanUp();
2400 
2401     phDal4Nfc_msgrelease(nxpncihal_ctrl.gDrvCfg.nClientId);
2402 
2403     memset(&nxpncihal_ctrl, 0x00, sizeof(nxpncihal_ctrl));
2404 
2405     NXPLOG_NCIHAL_D("phNxpNciHal_close - phOsalNfc_DeInit completed");
2406   }
2407 
2408   CONCURRENCY_UNLOCK();
2409 
2410   phNxpNciHal_cleanup_monitor();
2411   write_unlocked_status = NFCSTATUS_SUCCESS;
2412   phNxpNciHal_release_info();
2413   /* reset config cache */
2414   resetNxpConfig();
2415   /* Return success always */
2416   return NFCSTATUS_SUCCESS;
2417 }
2418 
2419 /******************************************************************************
2420  * Function         phNxpNciHal_close_complete
2421  *
2422  * Description      This function inform libnfc-nci about result of
2423  *                  phNxpNciHal_close.
2424  *
2425  * Returns          void.
2426  *
2427  ******************************************************************************/
phNxpNciHal_close_complete(NFCSTATUS status)2428 void phNxpNciHal_close_complete(NFCSTATUS status) {
2429   static phLibNfc_Message_t msg;
2430 
2431   if (status == NFCSTATUS_SUCCESS) {
2432     msg.eMsgType = NCI_HAL_CLOSE_CPLT_MSG;
2433   } else {
2434     msg.eMsgType = NCI_HAL_ERROR_MSG;
2435   }
2436   msg.pMsgData = NULL;
2437   msg.Size = 0;
2438   nxpncihal_ctrl.hal_open_status = false;
2439   phTmlNfc_DeferredCall(gpphTmlNfc_Context->dwCallbackThreadId, &msg);
2440 
2441   return;
2442 }
2443 
2444 /******************************************************************************
2445  * Function         phNxpNciHal_configDiscShutdown
2446  *
2447  * Description      Enable the CE and VEN config during shutdown.
2448  *
2449  * Returns          Always return NFCSTATUS_SUCCESS (0).
2450  *
2451  ******************************************************************************/
phNxpNciHal_configDiscShutdown(void)2452 int phNxpNciHal_configDiscShutdown(void) {
2453   NFCSTATUS status;
2454   /*NCI_RESET_CMD*/
2455 
2456   uint8_t cmd_disable_disc[] = {0x21, 0x06, 0x01, 0x00};
2457 
2458   uint8_t cmd_ce_disc_nci[] = {0x21, 0x03, 0x07, 0x03, 0x80,
2459                                0x01, 0x81, 0x01, 0x82, 0x01};
2460 
2461   uint8_t cmd_ven_pulld_enable_nci[] = {0x20, 0x02, 0x05, 0x01,
2462                                         0xA0, 0x07, 0x01, 0x03};
2463 
2464   /* Discover map - PROTOCOL_ISO_DEP, PROTOCOL_T3T and MIFARE Classic*/
2465   uint8_t cmd_disc_map[] = {0x21, 0x00, 0x0A, 0x03, 0x04, 0x03, 0x02,
2466                             0x03, 0x02, 0x01, 0x80, 0x01, 0x80};
2467   CONCURRENCY_LOCK();
2468 
2469   status = phNxpNciHal_send_ext_cmd(sizeof(cmd_disable_disc), cmd_disable_disc);
2470   if (status != NFCSTATUS_SUCCESS) {
2471     NXPLOG_NCIHAL_E("CMD_DISABLE_DISCOVERY: Failed");
2472   }
2473   if (IS_CHIP_TYPE_L(sn100u)) {
2474     status = phNxpNciHal_send_ext_cmd(sizeof(cmd_ven_pulld_enable_nci),
2475                                       cmd_ven_pulld_enable_nci);
2476     if (status != NFCSTATUS_SUCCESS) {
2477       NXPLOG_NCIHAL_E("CMD_VEN_PULLD_ENABLE_NCI: Failed");
2478     }
2479   }
2480 
2481   if (IS_CHIP_TYPE_GE(sn100u)) {
2482     status = phNxpNciHal_send_ext_cmd(sizeof(cmd_disc_map), cmd_disc_map);
2483     if (status != NFCSTATUS_SUCCESS) {
2484       NXPLOG_NCIHAL_E("Discovery Map command: Failed");
2485     }
2486     status = phNxpNciHal_ext_send_sram_config_to_flash();
2487     if (status != NFCSTATUS_SUCCESS) {
2488       NXPLOG_NCIHAL_E("Updation of the SRAM contents failed");
2489     }
2490   }
2491   status = phNxpNciHal_send_ext_cmd(sizeof(cmd_ce_disc_nci), cmd_ce_disc_nci);
2492   if (status != NFCSTATUS_SUCCESS) {
2493     NXPLOG_NCIHAL_E("CMD_CE_DISC_NCI: Failed");
2494   }
2495 
2496   CONCURRENCY_UNLOCK();
2497 
2498   status = phNxpNciHal_close(true);
2499   if (status != NFCSTATUS_SUCCESS) {
2500     NXPLOG_NCIHAL_E("NCI_HAL_CLOSE: Failed");
2501   }
2502 
2503   /* Return success always */
2504   return NFCSTATUS_SUCCESS;
2505 }
2506 
2507 /******************************************************************************
2508  * Function         phNxpNciHal_notify_i2c_fragmentation
2509  *
2510  * Description      This function can be used by HAL to inform
2511  *                 libnfc-nci that i2c fragmentation is enabled/disabled
2512  *
2513  * Returns          void.
2514  *
2515  ******************************************************************************/
phNxpNciHal_notify_i2c_fragmentation(void)2516 void phNxpNciHal_notify_i2c_fragmentation(void) {
2517   if (nxpncihal_ctrl.p_nfc_stack_cback != NULL) {
2518     /*inform libnfc-nci that i2c fragmentation is enabled/disabled */
2519     (*nxpncihal_ctrl.p_nfc_stack_cback)(HAL_NFC_ENABLE_I2C_FRAGMENTATION_EVT,
2520                                         HAL_NFC_STATUS_OK);
2521   }
2522 }
2523 /******************************************************************************
2524  * Function         phNxpNciHal_control_granted
2525  *
2526  * Description      Called by libnfc-nci when NFCC control is granted to HAL.
2527  *
2528  * Returns          Always returns NFCSTATUS_SUCCESS (0).
2529  *
2530  ******************************************************************************/
phNxpNciHal_control_granted(void)2531 int phNxpNciHal_control_granted(void) {
2532   /* Take the concurrency lock so no other calls from upper layer
2533    * will be allowed
2534    */
2535   CONCURRENCY_LOCK();
2536 
2537   if (NULL != nxpncihal_ctrl.p_control_granted_cback) {
2538     (*nxpncihal_ctrl.p_control_granted_cback)();
2539   }
2540   /* At the end concurrency unlock so calls from upper layer will
2541    * be allowed
2542    */
2543   CONCURRENCY_UNLOCK();
2544   return NFCSTATUS_SUCCESS;
2545 }
2546 
2547 /******************************************************************************
2548  * Function         phNxpNciHal_request_control
2549  *
2550  * Description      This function can be used by HAL to request control of
2551  *                  NFCC to libnfc-nci. When control is provided to HAL it is
2552  *                  notified through phNxpNciHal_control_granted.
2553  *
2554  * Returns          void.
2555  *
2556  ******************************************************************************/
phNxpNciHal_request_control(void)2557 void phNxpNciHal_request_control(void) {
2558   if (nxpncihal_ctrl.p_nfc_stack_cback != NULL) {
2559     /* Request Control of NCI Controller from NCI NFC Stack */
2560     (*nxpncihal_ctrl.p_nfc_stack_cback)(HAL_NFC_REQUEST_CONTROL_EVT,
2561                                         HAL_NFC_STATUS_OK);
2562   }
2563 
2564   return;
2565 }
2566 
2567 /******************************************************************************
2568  * Function         phNxpNciHal_release_control
2569  *
2570  * Description      This function can be used by HAL to release the control of
2571  *                  NFCC back to libnfc-nci.
2572  *
2573  * Returns          void.
2574  *
2575  ******************************************************************************/
phNxpNciHal_release_control(void)2576 void phNxpNciHal_release_control(void) {
2577   if (nxpncihal_ctrl.p_nfc_stack_cback != NULL) {
2578     /* Release Control of NCI Controller to NCI NFC Stack */
2579     (*nxpncihal_ctrl.p_nfc_stack_cback)(HAL_NFC_RELEASE_CONTROL_EVT,
2580                                         HAL_NFC_STATUS_OK);
2581   }
2582 
2583   return;
2584 }
2585 
2586 /******************************************************************************
2587  * Function         phNxpNciHal_power_cycle
2588  *
2589  * Description      This function is called by libnfc-nci when power cycling is
2590  *                  performed. When processing is complete it is notified to
2591  *                  libnfc-nci through phNxpNciHal_power_cycle_complete.
2592  *
2593  * Returns          Always return NFCSTATUS_SUCCESS (0).
2594  *
2595  ******************************************************************************/
phNxpNciHal_power_cycle(void)2596 int phNxpNciHal_power_cycle(void) {
2597   NXPLOG_NCIHAL_D("Power Cycle");
2598   NFCSTATUS status = NFCSTATUS_FAILED;
2599   if (nxpncihal_ctrl.halStatus != HAL_STATUS_OPEN) {
2600     NXPLOG_NCIHAL_D("Power Cycle failed due to hal status not open");
2601     return NFCSTATUS_FAILED;
2602   }
2603   nxpncihal_ctrl.power_reset_triggered = true;
2604   status = phTmlNfc_IoCtl(phTmlNfc_e_PowerReset);
2605 
2606   if (NFCSTATUS_SUCCESS == status) {
2607     NXPLOG_NCIHAL_D("PN54X Reset - SUCCESS\n");
2608   } else {
2609     NXPLOG_NCIHAL_D("PN54X Reset - FAILED\n");
2610   }
2611 
2612   phNxpNciHal_power_cycle_complete(NFCSTATUS_SUCCESS);
2613   return NFCSTATUS_SUCCESS;
2614 }
2615 
2616 /******************************************************************************
2617  * Function         phNxpNciHal_power_cycle_complete
2618  *
2619  * Description      This function is called to provide the status of
2620  *                  phNxpNciHal_power_cycle to libnfc-nci through callback.
2621  *
2622  * Returns          void.
2623  *
2624  ******************************************************************************/
phNxpNciHal_power_cycle_complete(NFCSTATUS status)2625 static void phNxpNciHal_power_cycle_complete(NFCSTATUS status) {
2626   static phLibNfc_Message_t msg;
2627 
2628   if (status == NFCSTATUS_SUCCESS) {
2629     msg.eMsgType = NCI_HAL_OPEN_CPLT_MSG;
2630   } else {
2631     msg.eMsgType = NCI_HAL_ERROR_MSG;
2632   }
2633   msg.pMsgData = NULL;
2634   msg.Size = 0;
2635 
2636   phTmlNfc_DeferredCall(gpphTmlNfc_Context->dwCallbackThreadId, &msg);
2637 
2638   return;
2639 }
2640 /******************************************************************************
2641  * Function         phNxpNciHal_check_ncicmd_write_window
2642  *
2643  * Description      This function is called to check the write synchroniztion
2644  *                  status if write already acquired then wait for corresponding
2645                     read to complete.
2646  *
2647  * Returns          return 0 on success and -1 on fail.
2648  *
2649  ******************************************************************************/
2650 
phNxpNciHal_check_ncicmd_write_window(uint16_t cmd_len,uint8_t * p_cmd)2651 int phNxpNciHal_check_ncicmd_write_window(uint16_t cmd_len, uint8_t* p_cmd) {
2652   NFCSTATUS status = NFCSTATUS_FAILED;
2653   int sem_timedout = 2, s;
2654   struct timespec ts;
2655 
2656   if (cmd_len < 1) {
2657     android_errorWriteLog(0x534e4554, "153880357");
2658     return NFCSTATUS_FAILED;
2659   }
2660 
2661   if ((p_cmd[0] & 0xF0) == 0x20) {
2662     clock_gettime(CLOCK_MONOTONIC, &ts);
2663     ts.tv_sec += sem_timedout;
2664     while ((s = sem_timedwait_monotonic_np(&nxpncihal_ctrl.syncSpiNfc, &ts)) == -1 &&
2665            errno == EINTR) {
2666       continue; /* Restart if interrupted by handler */
2667     }
2668     if (s != -1) {
2669       status = NFCSTATUS_SUCCESS;
2670     }
2671   } else {
2672     /* cmd window check not required for writing data packet */
2673     status = NFCSTATUS_SUCCESS;
2674   }
2675   return status;
2676 }
2677 
2678 /******************************************************************************
2679  * Function         phNxpNciHal_ioctl
2680  *
2681  * Description      This function is called by jni when wired mode is
2682  *                  performed.First Pn54x driver will give the access
2683  *                  permission whether wired mode is allowed or not
2684  *                  arg (0):
2685  * Returns          return 0 on success and -1 on fail, On success
2686  *                  update the acutual state of operation in arg pointer
2687  *
2688  ******************************************************************************/
phNxpNciHal_ioctl(long arg,void * p_data)2689 int phNxpNciHal_ioctl(long arg, void* p_data) {
2690   return phNxpNciHal_ioctlIf(arg, p_data);
2691 }
2692 
2693 /******************************************************************************
2694  * Function         phNxpNciHal_nfccClockCfgRead
2695  *
2696  * Description      This function is called for loading a data strcuture from
2697  *                  the config file with clock source and clock frequency values
2698  *
2699  * Returns          void.
2700  *
2701  ******************************************************************************/
phNxpNciHal_nfccClockCfgRead(void)2702 static void phNxpNciHal_nfccClockCfgRead(void) {
2703   unsigned long num = 0;
2704   int isfound = 0;
2705 
2706   nxpprofile_ctrl.bClkSrcVal = 0;
2707   nxpprofile_ctrl.bClkFreqVal = 0;
2708   nxpprofile_ctrl.bTimeout = 0;
2709 
2710   isfound = GetNxpNumValue(NAME_NXP_SYS_CLK_SRC_SEL, &num, sizeof(num));
2711   if (isfound > 0) {
2712     nxpprofile_ctrl.bClkSrcVal = num;
2713   }
2714 
2715   num = 0;
2716   isfound = 0;
2717   isfound = GetNxpNumValue(NAME_NXP_SYS_CLK_FREQ_SEL, &num, sizeof(num));
2718   if (isfound > 0) {
2719     nxpprofile_ctrl.bClkFreqVal = num;
2720   }
2721 
2722   num = 0;
2723   isfound = 0;
2724   isfound = GetNxpNumValue(NAME_NXP_SYS_CLOCK_TO_CFG, &num, sizeof(num));
2725   if (isfound > 0) {
2726     nxpprofile_ctrl.bTimeout = num;
2727   }
2728 
2729   NXPLOG_FWDNLD_D("gphNxpNciHal_fw_IoctlCtx.bClkSrcVal = 0x%x",
2730                   nxpprofile_ctrl.bClkSrcVal);
2731   NXPLOG_FWDNLD_D("gphNxpNciHal_fw_IoctlCtx.bClkFreqVal = 0x%x",
2732                   nxpprofile_ctrl.bClkFreqVal);
2733   NXPLOG_FWDNLD_D("gphNxpNciHal_fw_IoctlCtx.bClkFreqVal = 0x%x",
2734                   nxpprofile_ctrl.bTimeout);
2735 
2736   if ((nxpprofile_ctrl.bClkSrcVal < CLK_SRC_XTAL) ||
2737       (nxpprofile_ctrl.bClkSrcVal > CLK_SRC_PLL)) {
2738     NXPLOG_FWDNLD_E(
2739         "Clock source value is wrong in config file, setting it as default");
2740     nxpprofile_ctrl.bClkSrcVal = NXP_SYS_CLK_SRC_SEL;
2741   }
2742   if ((nxpprofile_ctrl.bClkFreqVal < CLK_FREQ_13MHZ) ||
2743       (nxpprofile_ctrl.bClkFreqVal > CLK_FREQ_48MHZ)) {
2744     NXPLOG_FWDNLD_E(
2745         "Clock frequency value is wrong in config file, setting it as default");
2746     nxpprofile_ctrl.bClkFreqVal = NXP_SYS_CLK_FREQ_SEL;
2747   }
2748   if ((nxpprofile_ctrl.bTimeout < CLK_TO_CFG_DEF) ||
2749       (nxpprofile_ctrl.bTimeout > CLK_TO_CFG_MAX)) {
2750     NXPLOG_FWDNLD_E(
2751         "Clock timeout value is wrong in config file, setting it as default");
2752     nxpprofile_ctrl.bTimeout = CLK_TO_CFG_DEF;
2753   }
2754 }
2755 
2756 /******************************************************************************
2757  * Function         phNxpNciHal_determineConfiguredClockSrc
2758  *
2759  * Description      This function determines and encodes clock source based on
2760  *                  clock frequency
2761  *
2762  * Returns          encoded form of clock source
2763  *
2764  *****************************************************************************/
phNxpNciHal_determineConfiguredClockSrc()2765 int phNxpNciHal_determineConfiguredClockSrc() {
2766   uint8_t param_clock_src = CLK_SRC_PLL;
2767   if (nxpprofile_ctrl.bClkSrcVal == CLK_SRC_PLL) {
2768     if (IS_CHIP_TYPE_EQ(pn553)) {
2769       param_clock_src = param_clock_src << 3;
2770     } else if (IS_CHIP_TYPE_GE(sn100u)) {
2771       param_clock_src = 0;
2772     }
2773 
2774     if (nxpprofile_ctrl.bClkFreqVal == CLK_FREQ_13MHZ) {
2775       param_clock_src |= 0x00;
2776     } else if (nxpprofile_ctrl.bClkFreqVal == CLK_FREQ_19_2MHZ) {
2777       param_clock_src |= 0x01;
2778     } else if (nxpprofile_ctrl.bClkFreqVal == CLK_FREQ_24MHZ) {
2779       param_clock_src |= 0x02;
2780     } else if (nxpprofile_ctrl.bClkFreqVal == CLK_FREQ_26MHZ) {
2781       param_clock_src |= 0x03;
2782     } else if (nxpprofile_ctrl.bClkFreqVal == CLK_FREQ_38_4MHZ) {
2783       param_clock_src |= 0x04;
2784     } else if (nxpprofile_ctrl.bClkFreqVal == CLK_FREQ_52MHZ) {
2785       param_clock_src |= 0x05;
2786     } else if (nxpprofile_ctrl.bClkFreqVal == CLK_FREQ_32MHZ) {
2787       param_clock_src |= 0x06;
2788     } else if (nxpprofile_ctrl.bClkFreqVal == CLK_FREQ_48MHZ) {
2789       param_clock_src |= 0x0A;
2790     } else {
2791       NXPLOG_NCIHAL_E("Wrong clock freq, send default PLL@19.2MHz");
2792       if (IS_CHIP_TYPE_L(sn100u))
2793         param_clock_src = 0x11;
2794       else
2795         param_clock_src = 0x01;
2796     }
2797   } else if (nxpprofile_ctrl.bClkSrcVal == CLK_SRC_XTAL) {
2798     param_clock_src = 0x08;
2799 
2800   } else {
2801     NXPLOG_NCIHAL_E("Wrong clock source. Don't apply any modification");
2802   }
2803   return param_clock_src;
2804 }
2805 
2806 /******************************************************************************
2807  * Function         phNxpNciHal_determineConfiguredClockSrc
2808  *
2809  * Description      This function determines and encodes clock source based on
2810  *                  clock frequency
2811  *
2812  * Returns          encoded form of clock source
2813  *
2814  *****************************************************************************/
phNxpNciHal_determineClockDelayRequest(uint8_t nfcc_cfg_clock_src)2815 int phNxpNciHal_determineClockDelayRequest(uint8_t nfcc_cfg_clock_src) {
2816   unsigned long num = 0;
2817   int isfound = 0;
2818   uint8_t nfcc_clock_delay_req = 0;
2819   uint8_t nfcc_clock_set_needed = false;
2820 
2821   isfound = GetNxpNumValue(NAME_NXP_CLOCK_REQ_DELAY, &num, sizeof(num));
2822   if (isfound > 0) {
2823     nxpprofile_ctrl.clkReqDelay = num;
2824   }
2825   if ((nxpprofile_ctrl.clkReqDelay < CLK_REQ_DELAY_MIN) ||
2826       (nxpprofile_ctrl.clkReqDelay > CLK_REQ_DELAY_MAX)) {
2827     NXPLOG_FWDNLD_E(
2828         "default delay to start clock value is wrong in config "
2829         "file, setting it as default");
2830     nxpprofile_ctrl.clkReqDelay = CLK_REQ_DELAY_DEF;
2831     return nfcc_clock_set_needed;
2832   }
2833   nfcc_clock_delay_req = nxpprofile_ctrl.clkReqDelay;
2834 
2835   /*Check if the clock source is XTAL as per config*/
2836   if (nfcc_cfg_clock_src == CLK_CFG_XTAL) {
2837     if (nfcc_clock_delay_req !=
2838         (phNxpNciClock.p_rx_data[CLK_REQ_DELAY_XTAL_OFFSET] &
2839          CLK_REQ_DELAY_MASK)) {
2840       nfcc_clock_set_needed = true;
2841       phNxpNciClock.p_rx_data[CLK_REQ_DELAY_XTAL_OFFSET] &=
2842           ~(CLK_REQ_DELAY_MASK);
2843       phNxpNciClock.p_rx_data[CLK_REQ_DELAY_XTAL_OFFSET] |=
2844           (nfcc_clock_delay_req & CLK_REQ_DELAY_MASK);
2845     }
2846   }
2847   /*Check if the clock source is PLL as per config*/
2848   else if (nfcc_cfg_clock_src < 6) {
2849     if (nfcc_clock_delay_req !=
2850         (phNxpNciClock.p_rx_data[CLK_REQ_DELAY_PLL_OFFSET] &
2851          CLK_REQ_DELAY_MASK)) {
2852       nfcc_clock_set_needed = true;
2853       phNxpNciClock.p_rx_data[CLK_REQ_DELAY_PLL_OFFSET] &=
2854           ~(CLK_REQ_DELAY_MASK);
2855       phNxpNciClock.p_rx_data[CLK_REQ_DELAY_PLL_OFFSET] |=
2856           (nfcc_clock_delay_req & CLK_REQ_DELAY_MASK);
2857     }
2858   }
2859   return nfcc_clock_set_needed;
2860 }
2861 
2862 /******************************************************************************
2863  * Function         phNxpNciHal_nfccClockCfgApply
2864  *
2865  * Description      This function is called after successful download
2866  *                  to check if clock settings in config file and chip
2867  *                  is same
2868  *
2869  * Returns          void.
2870  *
2871  ******************************************************************************/
phNxpNciHal_nfccClockCfgApply(void)2872 NFCSTATUS phNxpNciHal_nfccClockCfgApply(void) {
2873   NFCSTATUS status = NFCSTATUS_SUCCESS;
2874   uint8_t nfcc_cfg_clock_src, nfcc_cur_clock_src;
2875   uint8_t nfcc_clock_set_needed;
2876   uint8_t nfcc_clock_delay_req;
2877   static uint8_t* get_clock_cmd;
2878   uint8_t get_clck_cmd[] = {0x20, 0x03, 0x07, 0x03, 0xA0,
2879                             0x02, 0xA0, 0x03, 0xA0, 0x04};
2880   uint8_t get_clck_cmd_sn100[] = {0x20, 0x03, 0x03, 0x01, 0xA0, 0x11};
2881   uint8_t set_clck_cmd[] = {0x20, 0x02, 0x0B, 0x01, 0xA0, 0x11, 0x07,
2882                             0x01, 0x0A, 0x32, 0x02, 0x01, 0xF6, 0xF6};
2883   uint8_t get_clk_size = 0;
2884 
2885   if (IS_CHIP_TYPE_L(sn100u)) {
2886     get_clock_cmd = get_clck_cmd;
2887     get_clk_size = sizeof(get_clck_cmd);
2888   } else {
2889     get_clock_cmd = get_clck_cmd_sn100;
2890     get_clk_size = sizeof(get_clck_cmd_sn100);
2891   }
2892   phNxpNciHal_nfccClockCfgRead();
2893   phNxpNciClock.isClockSet = true;
2894   status = phNxpNciHal_send_ext_cmd(get_clk_size, get_clock_cmd);
2895   phNxpNciClock.isClockSet = false;
2896 
2897   if (status != NFCSTATUS_SUCCESS) {
2898     NXPLOG_NCIHAL_E("unable to retrieve get_clk_src_sel");
2899     return status;
2900   }
2901 
2902   nfcc_cfg_clock_src = phNxpNciHal_determineConfiguredClockSrc();
2903   if (IS_CHIP_TYPE_L(sn100u)) {
2904     nfcc_cur_clock_src = phNxpNciClock.p_rx_data[12];
2905   } else {
2906     nfcc_cur_clock_src = phNxpNciClock.p_rx_data[8];
2907   }
2908 
2909   if (IS_CHIP_TYPE_L(sn100u)) {
2910     nfcc_clock_set_needed =
2911         (nfcc_cfg_clock_src != nfcc_cur_clock_src ||
2912          phNxpNciClock.p_rx_data[16] == nxpprofile_ctrl.bTimeout)
2913             ? true
2914             : false;
2915   } else {
2916     nfcc_clock_delay_req =
2917         phNxpNciHal_determineClockDelayRequest(nfcc_cfg_clock_src);
2918     /**Determine clock src is as expected*/
2919     nfcc_clock_set_needed =
2920         ((nfcc_cfg_clock_src != nfcc_cur_clock_src || nfcc_clock_delay_req)
2921              ? true
2922              : false);
2923   }
2924 
2925   if (nfcc_clock_set_needed) {
2926     NXPLOG_NCIHAL_D("Setting Clock Source and Frequency");
2927     if (IS_CHIP_TYPE_L(sn100u)) {
2928       phNxpNciHal_txNfccClockSetCmd();
2929     } else {
2930       /*Read the preset value from FW*/
2931       memcpy(&set_clck_cmd[7], &phNxpNciClock.p_rx_data[8],
2932              phNxpNciClock.p_rx_data[7]);
2933       /*Update clock source and frequency as per DH configuration*/
2934       set_clck_cmd[7] = nfcc_cfg_clock_src;
2935       status = phNxpNciHal_send_ext_cmd(sizeof(set_clck_cmd), set_clck_cmd);
2936     }
2937   }
2938 
2939   return status;
2940 }
2941 
2942 /******************************************************************************
2943  * Function         phNxpNciHal_get_mw_eeprom
2944  *
2945  * Description      This function is called to retrieve data in mw eeprom area
2946  *
2947  * Returns          NFCSTATUS.
2948  *
2949  ******************************************************************************/
phNxpNciHal_get_mw_eeprom(void)2950 static NFCSTATUS phNxpNciHal_get_mw_eeprom(void) {
2951   NFCSTATUS status = NFCSTATUS_SUCCESS;
2952   uint8_t retry_cnt = 0;
2953   static uint8_t get_mw_eeprom_cmd[] = {0x20, 0x03, 0x03, 0x01, 0xA0, 0x0F};
2954 
2955 retry_send_ext:
2956   if (retry_cnt > 3) {
2957     return NFCSTATUS_FAILED;
2958   }
2959 
2960   phNxpNciMwEepromArea.isGetEepromArea = true;
2961   status =
2962       phNxpNciHal_send_ext_cmd(sizeof(get_mw_eeprom_cmd), get_mw_eeprom_cmd);
2963   if (status != NFCSTATUS_SUCCESS) {
2964     NXPLOG_NCIHAL_D("unable to get the mw eeprom data");
2965     phNxpNciMwEepromArea.isGetEepromArea = false;
2966     retry_cnt++;
2967     goto retry_send_ext;
2968   }
2969   phNxpNciMwEepromArea.isGetEepromArea = false;
2970 
2971   if (phNxpNciMwEepromArea.p_rx_data[12]) {
2972     fw_download_success = 1;
2973   }
2974   return status;
2975 }
2976 
2977 /******************************************************************************
2978  * Function         phNxpNciHal_set_mw_eeprom
2979  *
2980  * Description      This function is called to update data in mw eeprom area
2981  *
2982  * Returns          void.
2983  *
2984  ******************************************************************************/
phNxpNciHal_set_mw_eeprom(void)2985 static NFCSTATUS phNxpNciHal_set_mw_eeprom(void) {
2986   NFCSTATUS status = NFCSTATUS_SUCCESS;
2987   uint8_t retry_cnt = 0;
2988   uint8_t set_mw_eeprom_cmd[39] = {0};
2989   uint8_t cmd_header[] = {0x20, 0x02, 0x24, 0x01, 0xA0, 0x0F, 0x20};
2990 
2991   memcpy(set_mw_eeprom_cmd, cmd_header, sizeof(cmd_header));
2992   phNxpNciMwEepromArea.p_rx_data[12] = 0;
2993   memcpy(set_mw_eeprom_cmd + sizeof(cmd_header), phNxpNciMwEepromArea.p_rx_data,
2994          sizeof(phNxpNciMwEepromArea.p_rx_data));
2995 
2996 retry_send_ext:
2997   if (retry_cnt > 3) {
2998     return NFCSTATUS_FAILED;
2999   }
3000 
3001   status =
3002       phNxpNciHal_send_ext_cmd(sizeof(set_mw_eeprom_cmd), set_mw_eeprom_cmd);
3003   if (status != NFCSTATUS_SUCCESS) {
3004     NXPLOG_NCIHAL_D("unable to update the mw eeprom data");
3005     retry_cnt++;
3006     goto retry_send_ext;
3007   }
3008   return status;
3009 }
3010 
3011 /******************************************************************************
3012  * Function         phNxpNciHal_china_tianjin_rf_setting
3013  *
3014  * Description      This function is called to check RF Setting
3015  *
3016  * Returns          Status.
3017  *
3018  ******************************************************************************/
phNxpNciHal_china_tianjin_rf_setting(void)3019 NFCSTATUS phNxpNciHal_china_tianjin_rf_setting(void) {
3020   NFCSTATUS status = NFCSTATUS_SUCCESS;
3021   int isfound = 0;
3022   unsigned long config_value = 0;
3023   int rf_val = 0;
3024   int flag_send_tianjin_config = true;
3025   int flag_send_transit_config = true;
3026   int flag_send_cmabypass_config = true;
3027   int flag_send_mfc_rf_setting_config = true;
3028   uint8_t retry_cnt = 0;
3029   int enable_bit = 0;
3030 
3031   static uint8_t get_rf_cmd[] = {0x20, 0x03, 0x03, 0x01, 0xA0, 0x85};
3032   NXPLOG_NCIHAL_D("phNxpNciHal_china_tianjin_rf_setting - Enter");
3033 
3034 retry_send_ext:
3035   if (retry_cnt > 3) {
3036     return NFCSTATUS_FAILED;
3037   }
3038 
3039   phNxpNciRfSet.isGetRfSetting = true;
3040   status = phNxpNciHal_send_ext_cmd(sizeof(get_rf_cmd), get_rf_cmd);
3041   if (status != NFCSTATUS_SUCCESS) {
3042     NXPLOG_NCIHAL_E("unable to get the RF setting");
3043     phNxpNciRfSet.isGetRfSetting = false;
3044     retry_cnt++;
3045     goto retry_send_ext;
3046   }
3047   phNxpNciRfSet.isGetRfSetting = false;
3048   if (phNxpNciRfSet.p_rx_data[3] != 0x00) {
3049     NXPLOG_NCIHAL_E("GET_CONFIG_RSP is FAILED for CHINA TIANJIN");
3050     return status;
3051   }
3052 
3053   /* check if tianjin_rf_setting is required */
3054   rf_val = phNxpNciRfSet.p_rx_data[10];
3055   isfound = (GetNxpNumValue(NAME_NXP_CHINA_TIANJIN_RF_ENABLED,
3056                             (void*)&config_value, sizeof(config_value)));
3057   if (isfound > 0) {
3058     enable_bit = rf_val & 0x40;
3059     if (nfcFL.nfccFL._NFCC_MIFARE_TIANJIN) {
3060       if ((enable_bit != 0x40) && (config_value == 1)) {
3061         phNxpNciRfSet.p_rx_data[10] |= 0x40;  // Enable if it is disabled
3062       } else if ((enable_bit == 0x40) && (config_value == 0)) {
3063         phNxpNciRfSet.p_rx_data[10] &= 0xBF;  // Disable if it is Enabled
3064       } else {
3065         flag_send_tianjin_config = false;  // No need to change in RF setting
3066       }
3067     } else {
3068       enable_bit = phNxpNciRfSet.p_rx_data[11] & 0x10;
3069       if ((config_value == 1) && (enable_bit != 0x10)) {
3070         NXPLOG_NCIHAL_E("Setting Non-Mifare reader for china tianjin");
3071         phNxpNciRfSet.p_rx_data[11] |= 0x10;
3072       } else if ((config_value == 0) && (enable_bit == 0x10)) {
3073         NXPLOG_NCIHAL_E("Setting Non-Mifare reader for china tianjin");
3074         phNxpNciRfSet.p_rx_data[11] &= 0xEF;
3075       } else {
3076         flag_send_tianjin_config = false;
3077       }
3078     }
3079   } else {
3080     flag_send_tianjin_config = false;
3081   }
3082 
3083   config_value = 0;
3084   /*check MFC NACK settings*/
3085   rf_val = phNxpNciRfSet.p_rx_data[9];
3086   isfound = (GetNxpNumValue(NAME_NXP_MIFARE_NACK_TO_RATS_ENABLE,
3087                             (void*)&config_value, sizeof(config_value)));
3088   if (isfound > 0) {
3089     enable_bit = rf_val & 0x20;
3090     if ((enable_bit != 0x20) && (config_value == 1)) {
3091       phNxpNciRfSet.p_rx_data[9] |= 0x20;  // Enable if it is disabled
3092     } else if ((enable_bit == 0x20) && (config_value == 0)) {
3093       phNxpNciRfSet.p_rx_data[9] &= ~0x20;  // Disable if it is Enabled
3094     } else {
3095       flag_send_mfc_rf_setting_config =
3096           false;  // No need to change in RF setting
3097     }
3098   } else {
3099     flag_send_mfc_rf_setting_config = FALSE;  // No need to change in RF setting
3100   }
3101 
3102   config_value = 0;
3103   /*check if china block number check is required*/
3104   rf_val = phNxpNciRfSet.p_rx_data[8];
3105   isfound = (GetNxpNumValue(NAME_NXP_CHINA_BLK_NUM_CHK_ENABLE,
3106                             (void*)&config_value, sizeof(config_value)));
3107   if (isfound > 0) {
3108     enable_bit = rf_val & 0x40;
3109     if ((enable_bit != 0x40) && (config_value == 1)) {
3110       phNxpNciRfSet.p_rx_data[8] |= 0x40;  // Enable if it is disabled
3111     } else if ((enable_bit == 0x40) && (config_value == 0)) {
3112       phNxpNciRfSet.p_rx_data[8] &= ~0x40;  // Disable if it is Enabled
3113     } else {
3114       flag_send_transit_config = false;  // No need to change in RF setting
3115     }
3116   } else {
3117     flag_send_transit_config = FALSE;  // No need to change in RF setting
3118   }
3119 
3120   config_value = 0;
3121   isfound = (GetNxpNumValue(NAME_NXP_CN_TRANSIT_CMA_BYPASSMODE_ENABLE,
3122                             (void*)&config_value, sizeof(config_value)));
3123   if (isfound > 0) {
3124     if (config_value == 0 && ((phNxpNciRfSet.p_rx_data[10] & 0x80) == 0x80)) {
3125       NXPLOG_NCIHAL_D("Disable CMA_BYPASSMODE Supports EMVCo PICC Complaincy");
3126       phNxpNciRfSet.p_rx_data[10] &=
3127           ~0x80;  // set 24th bit of RF MISC SETTING to 0 for EMVCo PICC
3128                   // Complaincy support
3129     } else if (config_value == 1 &&
3130                ((phNxpNciRfSet.p_rx_data[10] & 0x80) == 0)) {
3131       NXPLOG_NCIHAL_D(
3132           "Enable CMA_BYPASSMODE bypass the ISO14443-3A state machine from "
3133           "READY to ACTIVE and backward compatibility with MIfrae Reader ");
3134       phNxpNciRfSet.p_rx_data[10] |=
3135           0x80;  // set 24th bit of RF MISC SETTING to 1 for backward
3136                  // compatibility with MIfrae Reader
3137     } else {
3138       flag_send_cmabypass_config = FALSE;  // No need to change in RF setting
3139     }
3140   } else {
3141     flag_send_cmabypass_config = FALSE;
3142   }
3143 
3144   if (flag_send_tianjin_config || flag_send_transit_config ||
3145       flag_send_cmabypass_config || flag_send_mfc_rf_setting_config) {
3146     static uint8_t set_rf_cmd[] = {0x20, 0x02, 0x08, 0x01, 0xA0, 0x85,
3147                                    0x04, 0x50, 0x08, 0x68, 0x00};
3148     memcpy(&set_rf_cmd[4], &phNxpNciRfSet.p_rx_data[5], 7);
3149     status = phNxpNciHal_send_ext_cmd(sizeof(set_rf_cmd), set_rf_cmd);
3150     if (status != NFCSTATUS_SUCCESS) {
3151       NXPLOG_NCIHAL_E("unable to set the RF setting");
3152       retry_cnt++;
3153       goto retry_send_ext;
3154     }
3155   }
3156 
3157   return status;
3158 }
3159 
3160 /******************************************************************************
3161  * Function         phNxpNciHal_CheckAndHandleFwTearDown
3162  *
3163  * Description      Check Whether chip is in FW download mode, If chip is in
3164  *                  Download mode and previous session is not complete, then
3165  *                  Do force FW update.
3166  *
3167  * Returns          Status
3168  *
3169  ******************************************************************************/
phNxpNciHal_CheckAndHandleFwTearDown()3170 void phNxpNciHal_CheckAndHandleFwTearDown() {
3171   NFCSTATUS status = NFCSTATUS_FAILED;
3172   uint8_t session_state = -1;
3173   unsigned long minimal_fw_version = DEFAULT_MINIMAL_FW_VERSION;
3174   status = phNxpNciHal_getChipInfoInFwDnldMode();
3175   if (status != NFCSTATUS_SUCCESS) {
3176     NXPLOG_NCIHAL_E("Get Chip Info Failed");
3177     usleep(150 * 1000);
3178     return;
3179   }
3180   if (!GetNxpNumValue(NAME_NXP_MINIMAL_FW_VERSION, &minimal_fw_version,
3181                       sizeof(minimal_fw_version))) {
3182     /* If config file doesn't contain the info use default */
3183     minimal_fw_version = DEFAULT_MINIMAL_FW_VERSION;
3184   }
3185   if (wFwVerRsp != minimal_fw_version) {
3186     session_state = phNxpNciHal_getSessionInfoInFwDnldMode();
3187     if (session_state == 0) {
3188       NXPLOG_NCIHAL_E("NFC not in the teared state, boot NFCC in NCI mode");
3189       return;
3190     }
3191   }
3192   phTmlNfc_IoCtl(phTmlNfc_e_EnableDownloadMode);
3193   if (wFwVerRsp == minimal_fw_version) {
3194     /* since minimal fw required dlreset
3195      * to boot in Download mode */
3196     status = phNxpNciHal_dlResetInFwDnldMode();
3197     if (status != NFCSTATUS_SUCCESS) {
3198       NXPLOG_NCIHAL_E("DL Reset failed for minimal fw");
3199     }
3200   }
3201   phTmlNfc_EnableFwDnldMode(true);
3202 
3203   /* Set the obtained device handle to download module */
3204   phDnldNfc_SetHwDevHandle();
3205   NXPLOG_NCIHAL_D("Calling Seq handler for FW Download \n");
3206   status = phNxpNciHal_fw_download_seq(nxpprofile_ctrl.bClkSrcVal,
3207                                        nxpprofile_ctrl.bClkFreqVal);
3208   if (status != NFCSTATUS_SUCCESS) {
3209     NXPLOG_NCIHAL_E("FW Download Sequence Handler Failed.");
3210   } else {
3211     property_set("nfc.fw.force_download", "0");
3212     fw_download_success = 1;
3213   }
3214 
3215   status = phNxpNciHal_dlResetInFwDnldMode();
3216   if (status != NFCSTATUS_SUCCESS) {
3217     NXPLOG_NCIHAL_E("DL Reset failed in FW DN mode");
3218   }
3219 }
3220 
3221 /******************************************************************************
3222  * Function         phNxpNciHal_getChipInfoInFwDnldMode
3223  *
3224  * Description      Helper function to get the chip info in download mode
3225  *
3226  * Returns          Status
3227  *
3228  ******************************************************************************/
phNxpNciHal_getChipInfoInFwDnldMode(bool bIsVenResetReqd)3229 NFCSTATUS phNxpNciHal_getChipInfoInFwDnldMode(bool bIsVenResetReqd) {
3230   uint8_t get_chip_info_cmd[] = {0x00, 0x04, 0xF1, 0x00,
3231                                  0x00, 0x00, 0x6E, 0xEF};
3232   NFCSTATUS status = NFCSTATUS_FAILED;
3233   int retry_cnt = 0;
3234   if (bIsVenResetReqd) {
3235     status = phTmlNfc_IoCtl(phTmlNfc_e_EnableDownloadModeWithVenRst);
3236     if (status != NFCSTATUS_SUCCESS) {
3237       NXPLOG_NCIHAL_E("Enable Download mode failed");
3238       return status;
3239     }
3240   }
3241   phTmlNfc_EnableFwDnldMode(true);
3242   do {
3243     status =
3244         phNxpNciHal_send_ext_cmd(sizeof(get_chip_info_cmd), get_chip_info_cmd);
3245     if (status != NFCSTATUS_SUCCESS) {
3246       /* break the loop if HAL write failed or response Timeout */
3247       break;
3248     } else {
3249       /* Check FW getResponse command response status byte */
3250       if (nxpncihal_ctrl.p_rx_data[0] == 0x00) {
3251         if (nxpncihal_ctrl.p_rx_data[2] != 0x00) {
3252           status = NFCSTATUS_FAILED;
3253           if (retry_cnt < MAX_RETRY_COUNT) {
3254             retry_cnt++;
3255             /*reset NFCC state to avoid any failures
3256              *such as DL_PROTOCOL_ERROR
3257              */
3258             status = phNxpNciHal_dlResetInFwDnldMode();
3259             if (status != NFCSTATUS_SUCCESS) {
3260               NXPLOG_NCIHAL_E("DL Reset failed in FW DN mode");
3261             }
3262           }
3263         }
3264       } else {
3265         status = NFCSTATUS_FAILED;
3266         break;
3267       }
3268     }
3269   } while ((status != NFCSTATUS_SUCCESS) && (retry_cnt < MAX_RETRY_COUNT));
3270 
3271   phTmlNfc_EnableFwDnldMode(false);
3272   if (phNxpNciHal_enableTmlRead() != NFCSTATUS_PENDING) {
3273     NXPLOG_NCIHAL_E("%s read status error status", __FUNCTION__);
3274   }
3275   if (status == NFCSTATUS_SUCCESS) {
3276     phNxpNciHal_configFeatureList(nxpncihal_ctrl.p_rx_data,
3277                                   nxpncihal_ctrl.rx_data_len);
3278     wFwVerRsp = pConfigFL->getFWVersionInfo(nxpncihal_ctrl.p_rx_data,
3279                                             nxpncihal_ctrl.rx_data_len);
3280     setNxpFwConfigPath();
3281   }
3282   return status;
3283 }
3284 
3285 /******************************************************************************
3286  * Function         phNxpNciHal_getSessionInfoInFwDnldMode
3287  *
3288  * Description      Helper function to get the session info in download mode
3289  *
3290  * Returns          0 means session closed
3291  *
3292  ******************************************************************************/
phNxpNciHal_getSessionInfoInFwDnldMode()3293 uint8_t phNxpNciHal_getSessionInfoInFwDnldMode() {
3294   uint8_t session_status = -1;
3295   uint8_t get_session_info_cmd[] = {0x00, 0x04, 0xF2, 0x00,
3296                                     0x00, 0x00, 0xF5, 0x33};
3297   phTmlNfc_EnableFwDnldMode(true);
3298   NFCSTATUS status = phNxpNciHal_send_ext_cmd(sizeof(get_session_info_cmd),
3299                                               get_session_info_cmd);
3300   if (status == NFCSTATUS_SUCCESS) {
3301     /* Check FW getResponse command response status byte */
3302     if (nxpncihal_ctrl.p_rx_data[2] == 0x00 &&
3303         nxpncihal_ctrl.p_rx_data[0] == 0x00) {
3304       if (nxpncihal_ctrl.p_rx_data[3] == 0x00) {
3305         session_status = 0;
3306       }
3307     } else {
3308       NXPLOG_NCIHAL_D("get session info Failed !!!");
3309       usleep(150 * 1000);
3310     }
3311   }
3312   status = phNxpNciHal_dlResetInFwDnldMode();
3313   if (status != NFCSTATUS_SUCCESS) {
3314     NXPLOG_NCIHAL_E("DL Reset failed in FW DN mode");
3315   }
3316   return session_status;
3317 }
3318 
3319 /******************************************************************************
3320  * Function         phNxpNciHal_dlResetInFwDnldMode
3321  *
3322  * Description      Helper function to change the mode from FW to NCI
3323  *
3324  * Returns          Status
3325  *
3326  ******************************************************************************/
phNxpNciHal_dlResetInFwDnldMode()3327 NFCSTATUS phNxpNciHal_dlResetInFwDnldMode() {
3328   NFCSTATUS status = NFCSTATUS_FAILED;
3329   phTmlNfc_EnableFwDnldMode(true);
3330   NXPLOG_NCIHAL_D("Sending DL Reset for NFCC soft reboot");
3331   phDnldNfc_SetHwDevHandle();
3332 
3333   if (IS_CHIP_TYPE_GE(sn100u)) {
3334     phDnldNfc_SetI2CFragmentLength(NCI_CMDRESP_MAX_BUFF_SIZE_SNXXX);
3335   } else {
3336     phDnldNfc_SetI2CFragmentLength(NCI_CMDRESP_MAX_BUFF_SIZE_PN557);
3337   }
3338 
3339   status = phNxpNciHal_fw_dnld_switch_normal_mode();
3340 
3341   phTmlNfc_EnableFwDnldMode(false);
3342   phTmlNfc_ReadAbort();
3343   phDnldNfc_ReSetHwDevHandle();
3344   if (phNxpNciHal_enableTmlRead() != NFCSTATUS_PENDING) {
3345     NXPLOG_NCIHAL_E("%s read status error status", __FUNCTION__);
3346     status = NFCSTATUS_FAILED;
3347   }
3348   return status;
3349 }
3350 
3351 /******************************************************************************
3352  * Function         phNxpNciHal_gpio_restore
3353  *
3354  * Description      This function restores the gpio values into eeprom
3355  *
3356  * Returns          void
3357  *
3358  ******************************************************************************/
phNxpNciHal_gpio_restore(phNxpNciHal_GpioInfoState state)3359 static void phNxpNciHal_gpio_restore(phNxpNciHal_GpioInfoState state) {
3360   NFCSTATUS status = NFCSTATUS_SUCCESS;
3361   uint8_t get_gpio_values_cmd[] = {0x20, 0x03, 0x03, 0x01, 0xA0, 0x00};
3362   uint8_t set_gpio_values_cmd[] = {
3363       0x20, 0x02, 0x00, 0x01, 0xA0, 0x00, 0x20, 0x00, 0x00, 0x00,
3364       0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
3365       0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
3366       0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00};
3367 
3368   if (state == GPIO_STORE) {
3369     nxpncihal_ctrl.phNxpNciGpioInfo.state = GPIO_STORE;
3370     get_gpio_values_cmd[5] = 0x08;
3371     status = phNxpNciHal_send_ext_cmd(sizeof(get_gpio_values_cmd),
3372                                       get_gpio_values_cmd);
3373     if (status != NFCSTATUS_SUCCESS) {
3374       NXPLOG_NCIHAL_E("Failed to get GPIO values!!!\n");
3375       return;
3376     }
3377 
3378     nxpncihal_ctrl.phNxpNciGpioInfo.state = GPIO_STORE_DONE;
3379     set_gpio_values_cmd[2] = 0x24;
3380     set_gpio_values_cmd[5] = 0x14;
3381     set_gpio_values_cmd[7] = nxpncihal_ctrl.phNxpNciGpioInfo.values[0];
3382     set_gpio_values_cmd[8] = nxpncihal_ctrl.phNxpNciGpioInfo.values[1];
3383     status = phNxpNciHal_send_ext_cmd(sizeof(set_gpio_values_cmd),
3384                                       set_gpio_values_cmd);
3385     if (status != NFCSTATUS_SUCCESS) {
3386       NXPLOG_NCIHAL_E("Failed to set GPIO values!!!\n");
3387       return;
3388     }
3389   } else if (state == GPIO_RESTORE) {
3390     nxpncihal_ctrl.phNxpNciGpioInfo.state = GPIO_RESTORE;
3391     get_gpio_values_cmd[5] = 0x14;
3392     status = phNxpNciHal_send_ext_cmd(sizeof(get_gpio_values_cmd),
3393                                       get_gpio_values_cmd);
3394     if (status != NFCSTATUS_SUCCESS) {
3395       NXPLOG_NCIHAL_E("Failed to get GPIO values!!!\n");
3396       return;
3397     }
3398 
3399     nxpncihal_ctrl.phNxpNciGpioInfo.state = GPIO_RESTORE_DONE;
3400     set_gpio_values_cmd[2] = 0x06;
3401     set_gpio_values_cmd[5] = 0x08;  // update TAG
3402     set_gpio_values_cmd[6] = 0x02;  // update length
3403     set_gpio_values_cmd[7] = nxpncihal_ctrl.phNxpNciGpioInfo.values[0];
3404     set_gpio_values_cmd[8] = nxpncihal_ctrl.phNxpNciGpioInfo.values[1];
3405     status = phNxpNciHal_send_ext_cmd(9, set_gpio_values_cmd);
3406     if (status != NFCSTATUS_SUCCESS) {
3407       NXPLOG_NCIHAL_E("Failed to set GPIO values!!!\n");
3408       return;
3409     }
3410   } else {
3411     NXPLOG_NCIHAL_E("GPIO Restore Invalid Option!!!\n");
3412   }
3413 }
3414 
3415 /******************************************************************************
3416  * Function         phNxpNciHal_nfcc_core_reset_init
3417  *
3418  * Description      Helper function to do nfcc core reset & core init
3419  *
3420  * Returns          Status
3421  *
3422  ******************************************************************************/
phNxpNciHal_nfcc_core_reset_init(bool keep_config)3423 NFCSTATUS phNxpNciHal_nfcc_core_reset_init(bool keep_config) {
3424   NFCSTATUS status = NFCSTATUS_FAILED;
3425   uint8_t retry_cnt = 0;
3426   uint8_t cmd_reset_nci[] = {0x20, 0x00, 0x01, 0x01};
3427 
3428   if (keep_config) {
3429     cmd_reset_nci[3] = 0x00;
3430   }
3431 retry_core_reset:
3432   status = phNxpNciHal_send_ext_cmd(sizeof(cmd_reset_nci), cmd_reset_nci);
3433   if ((status != NFCSTATUS_SUCCESS) && (retry_cnt < 3)) {
3434     NXPLOG_NCIHAL_D("Retry: NCI_CORE_RESET");
3435     retry_cnt++;
3436     goto retry_core_reset;
3437   } else if (status != NFCSTATUS_SUCCESS) {
3438     NXPLOG_NCIHAL_E("NCI_CORE_RESET failed!!!\n");
3439     return status;
3440   }
3441 
3442   retry_cnt = 0;
3443   uint8_t cmd_init_nci[] = {0x20, 0x01, 0x00};
3444   uint8_t cmd_init_nci2_0[] = {0x20, 0x01, 0x02, 0x00, 0x00};
3445 retry_core_init:
3446   if (nxpncihal_ctrl.nci_info.nci_version == NCI_VERSION_2_0) {
3447     status = phNxpNciHal_send_ext_cmd(sizeof(cmd_init_nci2_0), cmd_init_nci2_0);
3448   } else {
3449     status = phNxpNciHal_send_ext_cmd(sizeof(cmd_init_nci), cmd_init_nci);
3450   }
3451 
3452   if ((status != NFCSTATUS_SUCCESS) && (retry_cnt < 3)) {
3453     NXPLOG_NCIHAL_D("Retry: NCI_CORE_INIT\n");
3454     retry_cnt++;
3455     goto retry_core_init;
3456   } else if (status != NFCSTATUS_SUCCESS) {
3457     NXPLOG_NCIHAL_E("NCI_CORE_INIT failed!!!\n");
3458     return status;
3459   }
3460 
3461   return status;
3462 }
3463 
3464 /******************************************************************************
3465  * Function         phNxpNciHal_resetDefaultSettings
3466  *
3467  * Description      Helper function to do nfcc core reset, core init
3468  *                  (if previously firmware update was triggered) and
3469  *                  apply default NFC settings
3470  *
3471  * Returns          Status
3472  *
3473  ******************************************************************************/
phNxpNciHal_resetDefaultSettings(uint8_t fw_update_req,bool keep_config)3474 NFCSTATUS phNxpNciHal_resetDefaultSettings(uint8_t fw_update_req,
3475                                            bool keep_config) {
3476   NFCSTATUS status = NFCSTATUS_SUCCESS;
3477   if (fw_update_req) {
3478     status = phNxpNciHal_nfcc_core_reset_init(keep_config);
3479   }
3480   if (status == NFCSTATUS_SUCCESS) {
3481     unsigned long num = 0;
3482     int ret = 0;
3483     phNxpNciHal_conf_nfc_forum_mode();
3484     if (IS_CHIP_TYPE_GE(sn100u)) {
3485       ret = GetNxpNumValue(NAME_NXP_RDR_DISABLE_ENABLE_LPCD, &num, sizeof(num));
3486       if (!ret || num == 1 || num == 2) {
3487         phNxpNciHal_prop_conf_lpcd(true);
3488       } else if (ret && num == 0) {
3489         phNxpNciHal_prop_conf_lpcd(false);
3490       }
3491     }
3492   }
3493   return status;
3494 }
3495 
phNxpNciHal_check_config_parameter()3496 int phNxpNciHal_check_config_parameter() {
3497   uint8_t param_clock_src = CLK_SRC_PLL;
3498   if (nxpprofile_ctrl.bClkSrcVal == CLK_SRC_PLL) {
3499     if (IS_CHIP_TYPE_NE(pn553) && IS_CHIP_TYPE_NE(pn557)) {
3500       param_clock_src = param_clock_src << 3;
3501     }
3502     if (nxpprofile_ctrl.bClkFreqVal == CLK_FREQ_13MHZ) {
3503       param_clock_src |= 0x00;
3504     } else if (nxpprofile_ctrl.bClkFreqVal == CLK_FREQ_19_2MHZ) {
3505       param_clock_src |= 0x01;
3506     } else if (nxpprofile_ctrl.bClkFreqVal == CLK_FREQ_24MHZ) {
3507       param_clock_src |= 0x02;
3508     } else if (nxpprofile_ctrl.bClkFreqVal == CLK_FREQ_26MHZ) {
3509       param_clock_src |= 0x03;
3510     } else if (nxpprofile_ctrl.bClkFreqVal == CLK_FREQ_38_4MHZ) {
3511       param_clock_src |= 0x04;
3512     } else if (nxpprofile_ctrl.bClkFreqVal == CLK_FREQ_52MHZ) {
3513       param_clock_src |= 0x05;
3514     } else if (nxpprofile_ctrl.bClkFreqVal == CLK_FREQ_32MHZ) {
3515       param_clock_src |= 0x06;
3516     } else if (nxpprofile_ctrl.bClkFreqVal == CLK_FREQ_48MHZ) {
3517       param_clock_src |= 0x0A;
3518     } else {
3519       NXPLOG_NCIHAL_E("Wrong clock freq, send default PLL@19.2MHz");
3520       param_clock_src = 0x11;
3521     }
3522   } else if (nxpprofile_ctrl.bClkSrcVal == CLK_SRC_XTAL) {
3523     param_clock_src = 0x08;
3524 
3525   } else {
3526     NXPLOG_NCIHAL_E("Wrong clock source. Don't apply any modification");
3527   }
3528   return param_clock_src;
3529 }
3530 /******************************************************************************
3531  * Function         phNxpNciHal_enable_i2c_fragmentation
3532  *
3533  * Description      This function is called to process the response status
3534  *                  and print the status byte.
3535  *
3536  * Returns          void.
3537  *
3538  ******************************************************************************/
phNxpNciHal_enable_i2c_fragmentation()3539 void phNxpNciHal_enable_i2c_fragmentation() {
3540   NFCSTATUS status = NFCSTATUS_FAILED;
3541   static uint8_t fragmentation_enable_config_cmd[] = {0x20, 0x02, 0x05, 0x01,
3542                                                       0xA0, 0x05, 0x01, 0x10};
3543   long i2c_status = 0x00;
3544   long config_i2c_vlaue = 0xff;
3545   /*NCI_RESET_CMD*/
3546   static uint8_t cmd_reset_nci[] = {0x20, 0x00, 0x01, 0x00};
3547   /*NCI_INIT_CMD*/
3548   static uint8_t cmd_init_nci[] = {0x20, 0x01, 0x00};
3549   static uint8_t cmd_init_nci2_0[] = {0x20, 0x01, 0x02, 0x00, 0x00};
3550   static uint8_t get_i2c_fragmentation_cmd[] = {0x20, 0x03, 0x03,
3551                                                 0x01, 0xA0, 0x05};
3552   if (GetNxpNumValue(NAME_NXP_I2C_FRAGMENTATION_ENABLED, (void*)&i2c_status,
3553                      sizeof(i2c_status)) == true) {
3554     NXPLOG_FWDNLD_D("I2C status : %ld", i2c_status);
3555   } else {
3556     NXPLOG_FWDNLD_E("I2C status read not succeeded. Default value : %ld",
3557                     i2c_status);
3558   }
3559   status = phNxpNciHal_send_ext_cmd(sizeof(get_i2c_fragmentation_cmd),
3560                                     get_i2c_fragmentation_cmd);
3561   if (status != NFCSTATUS_SUCCESS) {
3562     NXPLOG_NCIHAL_E("unable to retrieve  get_i2c_fragmentation_cmd");
3563   } else {
3564     if (nxpncihal_ctrl.p_rx_data[8] == 0x10) {
3565       config_i2c_vlaue = 0x01;
3566       phNxpNciHal_notify_i2c_fragmentation();
3567       phTmlNfc_set_fragmentation_enabled(I2C_FRAGMENTATION_ENABLED);
3568     } else if (nxpncihal_ctrl.p_rx_data[8] == 0x00) {
3569       config_i2c_vlaue = 0x00;
3570     }
3571     // if the value already matches, nothing to be done
3572     if (config_i2c_vlaue != i2c_status) {
3573       if (i2c_status == 0x01) {
3574         /* NXP I2C fragmenation enabled*/
3575         status =
3576             phNxpNciHal_send_ext_cmd(sizeof(fragmentation_enable_config_cmd),
3577                                      fragmentation_enable_config_cmd);
3578         if (status != NFCSTATUS_SUCCESS) {
3579           NXPLOG_NCIHAL_E("NXP fragmentation enable failed");
3580         }
3581       } else if (i2c_status == 0x00 || config_i2c_vlaue == 0xff) {
3582         fragmentation_enable_config_cmd[7] = 0x00;
3583         /* NXP I2C fragmentation disabled*/
3584         status =
3585             phNxpNciHal_send_ext_cmd(sizeof(fragmentation_enable_config_cmd),
3586                                      fragmentation_enable_config_cmd);
3587         if (status != NFCSTATUS_SUCCESS) {
3588           NXPLOG_NCIHAL_E("NXP fragmentation disable failed");
3589         }
3590       }
3591       status = phNxpNciHal_send_ext_cmd(sizeof(cmd_reset_nci), cmd_reset_nci);
3592       if (status != NFCSTATUS_SUCCESS) {
3593         NXPLOG_NCIHAL_E("NCI_CORE_RESET: Failed");
3594       }
3595       if (nxpncihal_ctrl.nci_info.nci_version == NCI_VERSION_2_0) {
3596         status =
3597             phNxpNciHal_send_ext_cmd(sizeof(cmd_init_nci2_0), cmd_init_nci2_0);
3598       } else {
3599         status = phNxpNciHal_send_ext_cmd(sizeof(cmd_init_nci), cmd_init_nci);
3600       }
3601       if (status != NFCSTATUS_SUCCESS) {
3602         NXPLOG_NCIHAL_E("NCI_CORE_INIT : Failed");
3603       } else if (i2c_status == 0x01) {
3604         phNxpNciHal_notify_i2c_fragmentation();
3605         phTmlNfc_set_fragmentation_enabled(I2C_FRAGMENTATION_ENABLED);
3606       }
3607     }
3608   }
3609 }
3610 /******************************************************************************
3611  * Function         phNxpNciHal_do_se_session_reset
3612  *
3613  * Description      This function is called to set the session id to default
3614  *                  value.
3615  *
3616  * Returns          NFCSTATUS.
3617  *
3618  ******************************************************************************/
phNxpNciHal_do_swp_session_reset(void)3619 static NFCSTATUS phNxpNciHal_do_swp_session_reset(void) {
3620   NFCSTATUS status = NFCSTATUS_FAILED;
3621   static uint8_t reset_swp_session_identity_set[] = {
3622       0x20, 0x02, 0x17, 0x02, 0xA0, 0xEA, 0x08, 0xFF, 0xFF,
3623       0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xA0, 0x1E, 0x08,
3624       0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF};
3625   status = phNxpNciHal_send_ext_cmd(sizeof(reset_swp_session_identity_set),
3626                                     reset_swp_session_identity_set);
3627   if (status != NFCSTATUS_SUCCESS) {
3628     NXPLOG_NCIHAL_E("NXP reset_ese_session_identity_set command failed");
3629   }
3630   return status;
3631 }
3632 /******************************************************************************
3633  * Function         phNxpNciHal_do_factory_reset
3634  *
3635  * Description      This function is called during factory reset to clear/reset
3636  *                  nfc sub-system persistent data.
3637  *
3638  * Returns          void.
3639  *
3640  ******************************************************************************/
phNxpNciHal_do_factory_reset(void)3641 void phNxpNciHal_do_factory_reset(void) {
3642   NFCSTATUS status = NFCSTATUS_FAILED;
3643   if (nxpncihal_ctrl.halStatus == HAL_STATUS_CLOSE) {
3644     status = phNxpNciHal_MinOpen();
3645     if (status != NFCSTATUS_SUCCESS) {
3646       NXPLOG_NCIHAL_E("%s: NXP Nfc Open failed", __func__);
3647       return;
3648     }
3649     phNxpNciHal_deinitializeRegRfFwDnld();
3650   }
3651   status = phNxpNciHal_do_swp_session_reset();
3652   if (status != NFCSTATUS_SUCCESS) {
3653     NXPLOG_NCIHAL_E("%s failed. status = %x ", __func__, status);
3654   }
3655 }
3656 /******************************************************************************
3657  * Function         phNxpNciHal_hci_network_reset
3658  *
3659  * Description      This function resets the session id's of all the se's
3660  *                  in the HCI network and notify to HCI_NETWORK_RESET event to
3661  *                  NFC HAL Client.
3662  *
3663  * Returns          void.
3664  *
3665  ******************************************************************************/
phNxpNciHal_hci_network_reset(void)3666 static void phNxpNciHal_hci_network_reset(void) {
3667   static phLibNfc_Message_t msg;
3668   msg.pMsgData = NULL;
3669   msg.Size = 0;
3670 
3671   NFCSTATUS status = phNxpNciHal_do_swp_session_reset();
3672 
3673   if (status != NFCSTATUS_SUCCESS) {
3674     msg.eMsgType = NCI_HAL_ERROR_MSG;
3675   } else {
3676     msg.eMsgType = NCI_HAL_HCI_NETWORK_RESET_MSG;
3677   }
3678   phTmlNfc_DeferredCall(gpphTmlNfc_Context->dwCallbackThreadId, &msg);
3679 }
3680 /******************************************************************************
3681  * Function         phNxpNciHal_print_res_status
3682  *
3683  * Description      This function is called to process the response status
3684  *                  and print the status byte.
3685  *
3686  * Returns          void.
3687  *
3688  ******************************************************************************/
phNxpNciHal_print_res_status(uint8_t * p_rx_data,uint16_t * p_len)3689 static void phNxpNciHal_print_res_status(uint8_t* p_rx_data, uint16_t* p_len) {
3690   static uint8_t response_buf[][30] = {"STATUS_OK",
3691                                        "STATUS_REJECTED",
3692                                        "STATUS_RF_FRAME_CORRUPTED",
3693                                        "STATUS_FAILED",
3694                                        "STATUS_NOT_INITIALIZED",
3695                                        "STATUS_SYNTAX_ERROR",
3696                                        "STATUS_SEMANTIC_ERROR",
3697                                        "RFU",
3698                                        "RFU",
3699                                        "STATUS_INVALID_PARAM",
3700                                        "STATUS_MESSAGE_SIZE_EXCEEDED",
3701                                        "STATUS_UNDEFINED"};
3702   int status_byte;
3703   if (p_rx_data[0] == 0x40 && (p_rx_data[1] == 0x02 || p_rx_data[1] == 0x03)) {
3704     if (p_rx_data[2] && p_rx_data[3] <= 10) {
3705       status_byte = p_rx_data[CORE_RES_STATUS_BYTE];
3706       NXPLOG_NCIHAL_D("%s: response status =%s", __func__,
3707                       response_buf[status_byte]);
3708     } else {
3709       NXPLOG_NCIHAL_D("%s: response status =%s", __func__, response_buf[11]);
3710     }
3711     if (phNxpNciClock.isClockSet) {
3712       int i, len = sizeof(phNxpNciClock.p_rx_data);
3713       if (*p_len > len) {
3714         android_errorWriteLog(0x534e4554, "169257710");
3715       } else {
3716         len = *p_len;
3717       }
3718       for (i = 0; i < len; i++) {
3719         phNxpNciClock.p_rx_data[i] = p_rx_data[i];
3720       }
3721     }
3722 
3723     else if (phNxpNciRfSet.isGetRfSetting) {
3724       int i, len = sizeof(phNxpNciRfSet.p_rx_data);
3725       if (*p_len > len) {
3726         android_errorWriteLog(0x534e4554, "169258733");
3727       } else {
3728         len = *p_len;
3729       }
3730       for (i = 0; i < len; i++) {
3731         phNxpNciRfSet.p_rx_data[i] = p_rx_data[i];
3732         // NXPLOG_NCIHAL_D("%s: response status =0x%x",__func__,p_rx_data[i]);
3733       }
3734     } else if (phNxpNciMwEepromArea.isGetEepromArea) {
3735       int i, len = sizeof(phNxpNciMwEepromArea.p_rx_data) + 8;
3736       if (*p_len > len) {
3737         android_errorWriteLog(0x534e4554, "169258884");
3738       } else {
3739         len = *p_len;
3740       }
3741       for (i = 8; i < len; i++) {
3742         phNxpNciMwEepromArea.p_rx_data[i - 8] = p_rx_data[i];
3743       }
3744     } else if (nxpncihal_ctrl.phNxpNciGpioInfo.state == GPIO_STORE) {
3745       NXPLOG_NCIHAL_D("%s: Storing GPIO Values...", __func__);
3746       nxpncihal_ctrl.phNxpNciGpioInfo.values[0] = p_rx_data[9];
3747       nxpncihal_ctrl.phNxpNciGpioInfo.values[1] = p_rx_data[8];
3748     } else if (nxpncihal_ctrl.phNxpNciGpioInfo.state == GPIO_RESTORE) {
3749       NXPLOG_NCIHAL_D("%s: Restoring GPIO Values...", __func__);
3750       nxpncihal_ctrl.phNxpNciGpioInfo.values[0] = p_rx_data[9];
3751       nxpncihal_ctrl.phNxpNciGpioInfo.values[1] = p_rx_data[8];
3752     }
3753   }
3754 
3755   if (p_rx_data[2] && (config_access == true)) {
3756     if (p_rx_data[3] != NFCSTATUS_SUCCESS) {
3757       NXPLOG_NCIHAL_W("Invalid Data from config file.");
3758       config_success = false;
3759     }
3760   }
3761 }
3762 /******************************************************************************
3763  * Function         phNxpNciHal_initialize_mifare_flag
3764  *
3765  * Description      This function gets the value for Mfc flags.
3766  *
3767  * Returns          void
3768  *
3769  ******************************************************************************/
phNxpNciHal_initialize_mifare_flag()3770 static void phNxpNciHal_initialize_mifare_flag() {
3771   unsigned long num = 0;
3772   bEnableMfcReader = false;
3773   bDisableLegacyMfcExtns = true;
3774   // 1: Enable Mifare Classic protocol in RF Discovery.
3775   // 0: Remove Mifare Classic protocol in RF Discovery.
3776   if (GetNxpNumValue(NAME_MIFARE_READER_ENABLE, &num, sizeof(num))) {
3777     bEnableMfcReader = (num == 0) ? false : true;
3778   }
3779   // 1: Use legacy JNI MFC extns.
3780   // 0: Disable legacy JNI MFC extns, use hal MFC Extns instead.
3781   if (GetNxpNumValue(NAME_LEGACY_MIFARE_READER, &num, sizeof(num))) {
3782     bDisableLegacyMfcExtns = (num == 0) ? true : false;
3783   }
3784 }
3785 
3786 /*****************************************************************************
3787  * Function         phNxpNciHal_send_get_cfgs
3788  *
3789  * Description      This function is called to  send get configs
3790  *                  for all the types in get_cfg_arr.
3791  *                  Response of getConfigs(EEPROM stored) will be
3792  *                  compared with request coming from MW during discovery.
3793  *                  If same, then current setConfigs will be dropped
3794  *
3795  * Returns          Returns NFCSTATUS_SUCCESS if sending cmd is successful and
3796  *                  response is received.
3797  *
3798  *****************************************************************************/
phNxpNciHal_send_get_cfgs()3799 NFCSTATUS phNxpNciHal_send_get_cfgs() {
3800   NXPLOG_NCIHAL_D("%s Enter", __func__);
3801   NFCSTATUS status = NFCSTATUS_FAILED;
3802   uint8_t num_cfgs = sizeof(get_cfg_arr) / sizeof(uint8_t);
3803   uint8_t cfg_count = 0, retry_cnt = 0;
3804   if (mGetCfg_info != NULL) {
3805     mGetCfg_info->isGetcfg = true;
3806   }
3807   uint8_t cmd_get_cfg[] = {0x20, 0x03, 0x02, 0x01, 0x00};
3808 
3809   while (cfg_count < num_cfgs) {
3810     cmd_get_cfg[sizeof(cmd_get_cfg) - 1] = get_cfg_arr[cfg_count];
3811 
3812   retry_get_cfg:
3813     status = phNxpNciHal_send_ext_cmd(sizeof(cmd_get_cfg), cmd_get_cfg);
3814     if (status != NFCSTATUS_SUCCESS && retry_cnt < 3) {
3815       NXPLOG_NCIHAL_E("cmd_get_cfg failed");
3816       retry_cnt++;
3817       goto retry_get_cfg;
3818     }
3819     if (retry_cnt == 3) {
3820       break;
3821     }
3822     cfg_count++;
3823     retry_cnt = 0;
3824   }
3825   mGetCfg_info->isGetcfg = false;
3826   return status;
3827 }
3828 
3829 /*******************************************************************************
3830 **
3831 ** Function         phNxpNciHal_configFeatureList
3832 **
3833 ** Description      Configures the featureList based on chip type &
3834 **                  Configure fragmentation length based on chip type.
3835 **                  HW Version information number will provide chipType.
3836 **                  HW Version can be obtained from CORE_INIT_RESPONSE(NCI 1.0)
3837 **                  or CORE_RST_NTF(NCI 2.0)
3838 **
3839 ** Parameters       CORE_INIT_RESPONSE/CORE_RST_NTF, len
3840 **
3841 ** Returns          none
3842 *******************************************************************************/
phNxpNciHal_configFeatureList(uint8_t * init_rsp,uint16_t rsp_len)3843 void phNxpNciHal_configFeatureList(uint8_t* init_rsp, uint16_t rsp_len) {
3844   nxpncihal_ctrl.chipType = pConfigFL->processChipType(init_rsp, rsp_len);
3845   tNFC_chipType chipType = nxpncihal_ctrl.chipType;
3846   NXPLOG_NCIHAL_D("phNxpNciHal_configFeatureList ()chipType = %d", chipType);
3847   CONFIGURE_FEATURELIST(chipType);
3848   /* update fragment len based on the chip type.*/
3849   phTmlNfc_IoCtl(phTmlNfc_e_setFragmentSize);
3850 }
3851 
3852 /*******************************************************************************
3853 **
3854 ** Function         phNxpNciHal_UpdateFwStatus
3855 **
3856 ** Description      It shall be called to update the FW download status to the
3857 **                  libnfc-nci.
3858 **
3859 ** Parameters       fwStatus: FW update status
3860 **
3861 ** Returns          void
3862 *******************************************************************************/
phNxpNciHal_UpdateFwStatus(HalNfcFwUpdateStatus fwStatus)3863 static void phNxpNciHal_UpdateFwStatus(HalNfcFwUpdateStatus fwStatus) {
3864   static phLibNfc_Message_t msg;
3865   static uint8_t status;
3866   NXPLOG_NCIHAL_D("phNxpNciHal_UpdateFwStatus Enter");
3867 
3868   status = (uint8_t)fwStatus;
3869   msg.eMsgType = HAL_NFC_FW_UPDATE_STATUS_EVT;
3870   msg.pMsgData = &status;
3871   msg.Size = sizeof(status);
3872   phTmlNfc_DeferredCall(gpphTmlNfc_Context->dwCallbackThreadId,
3873                         (phLibNfc_Message_t*)&msg);
3874   return;
3875 }
3876 
3877 /*******************************************************************************
3878 **
3879 ** Function         phNxpNciHal_configNciParser(bool enable)
3880 **
3881 ** Description      Helper function to configure LxDebug modes
3882 **
3883 ** Parameters       none
3884 **
3885 ** Returns          void
3886 *******************************************************************************/
phNxpNciHal_configNciParser(bool enable)3887 void phNxpNciHal_configNciParser(bool enable) {
3888   NFCSTATUS status = NFCSTATUS_SUCCESS;
3889   unsigned long lx_debug_cfg = 0;
3890   uint8_t isfound = 0;
3891   static uint8_t cmd_lxdebug[] = {0x20, 0x02, 0x06, 0x01, 0xA0,
3892                                   0x1D, 0x02, 0x00, 0x00};
3893 
3894   isfound = GetNxpNumValue(NAME_NXP_CORE_PROP_SYSTEM_DEBUG, &lx_debug_cfg,
3895                            sizeof(lx_debug_cfg));
3896 
3897   if (isfound > 0 && enable == true) {
3898     if (lx_debug_cfg & LX_DEBUG_CFG_MASK_RFU) {
3899       NXPLOG_NCIHAL_E(
3900           "One or more RFU bits are enabled.\nMasking the RFU bits");
3901       lx_debug_cfg = lx_debug_cfg & ~LX_DEBUG_CFG_MASK_RFU;
3902     }
3903     if (lx_debug_cfg == LX_DEBUG_CFG_DISABLE) {
3904       NXPLOG_NCIHAL_D("Disable LxDebug");
3905     }
3906     if (lx_debug_cfg & LX_DEBUG_CFG_ENABLE_L1_EVENT) {
3907       NXPLOG_NCIHAL_D("Enable L1 RF NTF debugs");
3908     }
3909     if (lx_debug_cfg & LX_DEBUG_CFG_ENABLE_L2_EVENT) {
3910       NXPLOG_NCIHAL_D("Enable L2 RF NTF debugs (CE)");
3911     }
3912     if (lx_debug_cfg & LX_DEBUG_CFG_ENABLE_FELICA_RF) {
3913       NXPLOG_NCIHAL_D("Enable all Felica CM events");
3914     }
3915     if (lx_debug_cfg & LX_DEBUG_CFG_ENABLE_FELICA_SYSCODE) {
3916       NXPLOG_NCIHAL_D("Enable Felica System Code");
3917     }
3918     if (lx_debug_cfg & LX_DEBUG_CFG_ENABLE_L2_EVENT_READER) {
3919       NXPLOG_NCIHAL_D("Enable L2 RF NTF debugs (Reader)");
3920     }
3921     if (lx_debug_cfg & LX_DEBUG_CFG_ENABLE_MOD_DETECTED_EVENT) {
3922       NXPLOG_NCIHAL_D("Enable Modulation detected event");
3923     }
3924     if (lx_debug_cfg & LX_DEBUG_CFG_ENABLE_CMA_EVENTS) {
3925       NXPLOG_NCIHAL_D("Enable CMA events");
3926     }
3927 
3928     cmd_lxdebug[7] = (uint8_t)(lx_debug_cfg & LX_DEBUG_CFG_MASK);
3929     cmd_lxdebug[8] = (uint8_t)((lx_debug_cfg & LX_DEBUG_CFG_MASK) >> 8);
3930   }
3931   status = phNxpNciHal_send_ext_cmd(
3932       sizeof(cmd_lxdebug) / sizeof(cmd_lxdebug[0]), cmd_lxdebug);
3933   if (status != NFCSTATUS_SUCCESS) {
3934     NXPLOG_NCIHAL_E("Set lxDebug config failed");
3935   }
3936   if (enable ==
3937       false) { /*We are here to disable the LX_DEBUG_CFG and parser library*/
3938     return;
3939   }
3940   /* try initializing parser library*/
3941   NXPLOG_NCIHAL_D("Try Init Parser gParserCreated:%d", gParserCreated);
3942 
3943   if (!gParserCreated) {
3944     gParserCreated = phNxpNciHal_initParser();
3945   } else {
3946     NXPLOG_NCIHAL_D("Parser Already Initialized");
3947   }
3948 
3949   if (gParserCreated) {
3950     NXPLOG_NCIHAL_D("Parser Initialized Successfully");
3951     if (isfound) {
3952       NXPLOG_NCIHAL_D("Setting lxdebug levels in library");
3953       phNxpNciHal_parsePacket(cmd_lxdebug,
3954                               sizeof(cmd_lxdebug) / sizeof(cmd_lxdebug[0]));
3955     }
3956   } else {
3957     NXPLOG_NCIHAL_E("Parser Library Not Available");
3958   }
3959 }
3960 
3961 /*******************************************************************************
3962 **
3963 ** Function         phNxpNciHal_initializeRegRfFwDnld(void)
3964 **
3965 ** Description      Loads the module & initializes function pointers for Region
3966 **                  based RF & FW update module
3967 **
3968 ** Parameters       none
3969 **
3970 ** Returns          void
3971 *******************************************************************************/
phNxpNciHal_initializeRegRfFwDnld()3972 void phNxpNciHal_initializeRegRfFwDnld() {
3973   // Getting pointer to RF & RF Region Code Download module
3974   RfFwRegionDnld_handle =
3975       dlopen("/system/vendor/lib64/libonebinary.so", RTLD_NOW);
3976   if (RfFwRegionDnld_handle == NULL) {
3977     NXPLOG_NCIHAL_D(
3978         "Error : opening (/system/vendor/lib64/libonebinary.so) !!");
3979     return;
3980   }
3981   if ((fpVerInfoStoreInEeprom = (fpVerInfoStoreInEeprom_t)dlsym(
3982            RfFwRegionDnld_handle, "read_version_info_and_store_in_eeprom")) ==
3983       NULL) {
3984     NXPLOG_NCIHAL_D(
3985         "Error while linking (read_version_info_and_store_in_eeprom) !!");
3986     return;
3987   }
3988   if ((fpRegRfFwDndl = (fpRegRfFwDndl_t)dlsym(RfFwRegionDnld_handle,
3989                                               "RegRfFwDndl")) == NULL) {
3990     NXPLOG_NCIHAL_D("Error while linking (RegRfFwDndl) !!");
3991     return;
3992   }
3993   if ((fpPropConfCover = (fpPropConfCover_t)dlsym(RfFwRegionDnld_handle,
3994                                                   "prop_conf_cover")) == NULL) {
3995     NXPLOG_NCIHAL_D("Error while linking (prop_conf_cover) !!");
3996     return;
3997   }
3998 }
3999 
4000 /*******************************************************************************
4001 **
4002 ** Function         phNxpNciHal_deinitializeRegRfFwDnld(void)
4003 **
4004 ** Description      Resets the module handle & all the function pointers for
4005 **                  Region based RF & FW update module
4006 **
4007 ** Parameters       none
4008 **
4009 ** Returns          void
4010 *******************************************************************************/
phNxpNciHal_deinitializeRegRfFwDnld()4011 void phNxpNciHal_deinitializeRegRfFwDnld() {
4012   if (RfFwRegionDnld_handle != NULL) {
4013     NXPLOG_NCIHAL_D("closing libonebinary.so");
4014     fpVerInfoStoreInEeprom = NULL;
4015     fpRegRfFwDndl = NULL;
4016     fpPropConfCover = NULL;
4017     dlclose(RfFwRegionDnld_handle);
4018     RfFwRegionDnld_handle = NULL;
4019   }
4020 }
4021 
4022 /******************************************************************************
4023  * Function         phNxpNciHal_setVerboseLogging
4024  *
4025  * Description      This function enables the nfc_debug_enabled
4026  *
4027  * Returns          void
4028  *
4029  *****************************************************************************/
4030 
phNxpNciHal_setVerboseLogging(bool enable)4031 void phNxpNciHal_setVerboseLogging(bool enable) { nfc_debug_enabled = enable; }
4032 
4033 /******************************************************************************
4034  * Function         phNxpNciHal_getVerboseLogging
4035  *
4036  * Description      This function returns the value of nfc_debug_enabled
4037  *
4038  * Returns          void
4039  *
4040  *****************************************************************************/
4041 
phNxpNciHal_getVerboseLogging()4042 bool phNxpNciHal_getVerboseLogging() { return nfc_debug_enabled; }
4043