• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  *  Copyright 2010-2022 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 /*
18  * Download Component
19  * Download Interface routines implementation
20  */
21 
22 #include <dlfcn.h>
23 #include <phDnldNfc_Internal.h>
24 #include <phNxpConfig.h>
25 #include <phNxpLog.h>
26 #include <phTmlNfc.h>
27 #include <string>
28 
29 #if (NXP_NFC_RECOVERY == TRUE)
30 #include <phDnldNfc_UpdateSeq.h>
31 #endif
32 
33 static void* pFwHandle; /* Global firmware handle*/
34 uint16_t wMwVer = 0;    /* Middleware version no */
35 uint16_t wFwVer = 0;    /* Firmware version no */
36 uint8_t gRecFWDwnld;    /* flag set to true to indicate recovery FW download */
37 phTmlNfc_i2cfragmentation_t fragmentation_enabled = I2C_FRAGMENATATION_DISABLED;
38 static pphDnldNfc_DlContext_t gpphDnldContext = NULL; /* Download contex */
39 #undef EEPROM_Read_Mem_IMP
40 
41 /*******************************************************************************
42 **
43 ** Function         phDnldNfc_Reset
44 **
45 ** Description      Performs a soft reset of the download module
46 **
47 ** Parameters       pNotify  - notify caller after getting response
48 **                  pContext - caller context
49 **
50 ** Returns          NFC status:
51 **                  NFCSTATUS_SUCCESS - reset request to NFCC is successful
52 **                  NFCSTATUS_FAILED - reset request failed due to internal
53 **                                     error
54 **                  NFCSTATUS_NOT_ALLOWED - command not allowed
55 **                  Other command specific errors
56 **
57 *******************************************************************************/
phDnldNfc_Reset(pphDnldNfc_RspCb_t pNotify,void * pContext)58 NFCSTATUS phDnldNfc_Reset(pphDnldNfc_RspCb_t pNotify, void* pContext) {
59   NFCSTATUS wStatus = NFCSTATUS_SUCCESS;
60 
61   if ((NULL == pNotify) || (NULL == pContext)) {
62     NXPLOG_FWDNLD_E("Invalid Input Parameters!!");
63     wStatus = PHNFCSTVAL(CID_NFC_DNLD, NFCSTATUS_INVALID_PARAMETER);
64   } else {
65     if (phDnldNfc_TransitionIdle != gpphDnldContext->tDnldInProgress) {
66       NXPLOG_FWDNLD_E("Dnld Cmd Request in Progress..Cannot Continue!!");
67       wStatus = PHNFCSTVAL(CID_NFC_DNLD, NFCSTATUS_BUSY);
68     } else {
69       (gpphDnldContext->FrameInp.Type) = phDnldNfc_FTNone;
70       (gpphDnldContext->tCmdId) = PH_DL_CMD_RESET;
71       (gpphDnldContext->tRspBuffInfo.pBuff) = NULL;
72       (gpphDnldContext->tRspBuffInfo.wLen) = 0;
73       (gpphDnldContext->tUserData.pBuff) = NULL;
74       (gpphDnldContext->tUserData.wLen) = 0;
75       (gpphDnldContext->UserCb) = pNotify;
76       (gpphDnldContext->UserCtxt) = pContext;
77 
78       wStatus = phDnldNfc_CmdHandler(gpphDnldContext, phDnldNfc_EventReset);
79 
80       if (NFCSTATUS_PENDING == wStatus) {
81         NXPLOG_FWDNLD_D("Reset Request submitted successfully");
82       } else {
83         NXPLOG_FWDNLD_E("Reset Request Failed!!");
84       }
85     }
86   }
87 
88   return wStatus;
89 }
90 
91 /*******************************************************************************
92 **
93 ** Function         phDnldNfc_GetVersion
94 **
95 ** Description      Retrieves Hardware version, ROM Code version, Protected Data
96 **                  version, Trim data version, User data version, and Firmware
97 **                  version information
98 **
99 ** Parameters       pVersionInfo - response buffer which gets updated with
100 **                                 complete version info from NFCC
101 **                  pNotify - notify caller after getting response
102 **                  pContext - caller context
103 **
104 ** Returns          NFC status:
105 **                  NFCSTATUS_SUCCESS - GetVersion request to NFCC is successful
106 **                  NFCSTATUS_FAILED - GetVersion request failed due to internal
107 **                                     error
108 **                  NFCSTATUS_NOT_ALLOWED - command not allowed
109 **                  Other command specific errors
110 **
111 *******************************************************************************/
phDnldNfc_GetVersion(pphDnldNfc_Buff_t pVersionInfo,pphDnldNfc_RspCb_t pNotify,void * pContext)112 NFCSTATUS phDnldNfc_GetVersion(pphDnldNfc_Buff_t pVersionInfo,
113                                pphDnldNfc_RspCb_t pNotify, void* pContext) {
114   NFCSTATUS wStatus = NFCSTATUS_SUCCESS;
115 
116   if ((NULL == pVersionInfo) || (NULL == pNotify) || (NULL == pContext)) {
117     NXPLOG_FWDNLD_E("Invalid Input Parameters!!");
118     wStatus = PHNFCSTVAL(CID_NFC_DNLD, NFCSTATUS_INVALID_PARAMETER);
119   } else {
120     if (phDnldNfc_TransitionIdle != gpphDnldContext->tDnldInProgress) {
121       NXPLOG_FWDNLD_E("Dnld Cmd Request in Progress..Cannot Continue!!");
122       wStatus = PHNFCSTVAL(CID_NFC_DNLD, NFCSTATUS_BUSY);
123     } else {
124       if ((NULL != pVersionInfo->pBuff) && (0 != pVersionInfo->wLen)) {
125         (gpphDnldContext->tRspBuffInfo.pBuff) = pVersionInfo->pBuff;
126         (gpphDnldContext->tRspBuffInfo.wLen) = pVersionInfo->wLen;
127         (gpphDnldContext->FrameInp.Type) = phDnldNfc_FTNone;
128         (gpphDnldContext->tCmdId) = PH_DL_CMD_GETVERSION;
129         (gpphDnldContext->tUserData.pBuff) = NULL;
130         (gpphDnldContext->tUserData.wLen) = 0;
131         (gpphDnldContext->UserCb) = pNotify;
132         (gpphDnldContext->UserCtxt) = pContext;
133 
134         wStatus = phDnldNfc_CmdHandler(gpphDnldContext, phDnldNfc_EventGetVer);
135 
136         if (NFCSTATUS_PENDING == wStatus) {
137           NXPLOG_FWDNLD_D("GetVersion Request submitted successfully");
138         } else {
139           NXPLOG_FWDNLD_E("GetVersion Request Failed!!");
140         }
141       } else {
142         NXPLOG_FWDNLD_E("Invalid Buff Parameters!!");
143         wStatus = PHNFCSTVAL(CID_NFC_DNLD, NFCSTATUS_INVALID_PARAMETER);
144       }
145     }
146   }
147 
148   return wStatus;
149 }
150 
151 /*******************************************************************************
152 **
153 ** Function         phDnldNfc_GetSessionState
154 **
155 ** Description      Retrieves the current session state of NFCC
156 **
157 ** Parameters       pSession - response buffer which gets updated with complete
158 **                             version info from NFCC
159 **                  pNotify - notify caller after getting response
160 **                  pContext - caller context
161 **
162 ** Returns          NFC status:
163 **                  NFCSTATUS_SUCCESS - GetSessionState request to NFCC is
164 **                                      successful
165 **                  NFCSTATUS_FAILED - GetSessionState request failed due to
166 **                                     internal error
167 **                  NFCSTATUS_NOT_ALLOWED - command not allowed
168 **                  Other command specific errors
169 **
170 *******************************************************************************/
phDnldNfc_GetSessionState(pphDnldNfc_Buff_t pSession,pphDnldNfc_RspCb_t pNotify,void * pContext)171 NFCSTATUS phDnldNfc_GetSessionState(pphDnldNfc_Buff_t pSession,
172                                     pphDnldNfc_RspCb_t pNotify,
173                                     void* pContext) {
174   NFCSTATUS wStatus = NFCSTATUS_SUCCESS;
175 
176   if ((NULL == pSession) || (NULL == pNotify) || (NULL == pContext)) {
177     NXPLOG_FWDNLD_E("Invalid Input Parameters!!");
178     wStatus = PHNFCSTVAL(CID_NFC_DNLD, NFCSTATUS_INVALID_PARAMETER);
179   } else {
180     if (phDnldNfc_TransitionIdle != gpphDnldContext->tDnldInProgress) {
181       NXPLOG_FWDNLD_E("Dnld Cmd Request in Progress..Cannot Continue!!");
182       wStatus = PHNFCSTVAL(CID_NFC_DNLD, NFCSTATUS_BUSY);
183     } else {
184       if ((NULL != pSession->pBuff) && (0 != pSession->wLen)) {
185         (gpphDnldContext->tRspBuffInfo.pBuff) = pSession->pBuff;
186         (gpphDnldContext->tRspBuffInfo.wLen) = pSession->wLen;
187         (gpphDnldContext->FrameInp.Type) = phDnldNfc_FTNone;
188         (gpphDnldContext->tCmdId) = PH_DL_CMD_GETSESSIONSTATE;
189         (gpphDnldContext->tUserData.pBuff) = NULL;
190         (gpphDnldContext->tUserData.wLen) = 0;
191         (gpphDnldContext->UserCb) = pNotify;
192         (gpphDnldContext->UserCtxt) = pContext;
193 
194         wStatus =
195             phDnldNfc_CmdHandler(gpphDnldContext, phDnldNfc_EventGetSesnSt);
196 
197         if (NFCSTATUS_PENDING == wStatus) {
198           NXPLOG_FWDNLD_D("GetSessionState Request submitted successfully");
199         } else {
200           NXPLOG_FWDNLD_E("GetSessionState Request Failed!!");
201         }
202       } else {
203         NXPLOG_FWDNLD_E("Invalid Buff Parameters!!");
204         wStatus = PHNFCSTVAL(CID_NFC_DNLD, NFCSTATUS_INVALID_PARAMETER);
205       }
206     }
207   }
208 
209   return wStatus;
210 }
211 
212 /*******************************************************************************
213 **
214 ** Function         phDnldNfc_CheckIntegrity
215 **
216 ** Description      Inspects the integrity of EEPROM and FLASH contents of the
217 **                  NFCC, provides CRC for each section
218 **                  NOTE: The user data section CRC is valid only after fresh
219 **                        download
220 **
221 ** Parameters       bChipVer - current ChipVersion for including additional
222 **                             parameters in request payload
223 **                  pCRCData - response buffer which gets updated with
224 **                             respective section CRC status and CRC bytes from
225 **                             NFCC
226 **                  pNotify - notify caller after getting response
227 **                  pContext - caller context
228 **
229 ** Returns          NFC status:
230 **                  NFCSTATUS_SUCCESS - CheckIntegrity request is successful
231 **                  NFCSTATUS_FAILED - CheckIntegrity request failed due to
232 **                                     internal error
233 **                  NFCSTATUS_NOT_ALLOWED - command not allowed
234 **                  Other command specific errors
235 **
236 *******************************************************************************/
phDnldNfc_CheckIntegrity(uint8_t bChipVer,pphDnldNfc_Buff_t pCRCData,pphDnldNfc_RspCb_t pNotify,void * pContext)237 NFCSTATUS phDnldNfc_CheckIntegrity(uint8_t bChipVer, pphDnldNfc_Buff_t pCRCData,
238                                    pphDnldNfc_RspCb_t pNotify, void* pContext) {
239   NFCSTATUS wStatus = NFCSTATUS_SUCCESS;
240 
241   if ((NULL == pNotify) || (NULL == pContext)) {
242     NXPLOG_FWDNLD_E("Invalid Input Parameters!!");
243     wStatus = PHNFCSTVAL(CID_NFC_DNLD, NFCSTATUS_INVALID_PARAMETER);
244   } else {
245     if (phDnldNfc_TransitionIdle != gpphDnldContext->tDnldInProgress) {
246       NXPLOG_FWDNLD_E("Dnld Cmd Request in Progress..Cannot Continue!!");
247       wStatus = PHNFCSTVAL(CID_NFC_DNLD, NFCSTATUS_BUSY);
248     } else {
249       if ((PHDNLDNFC_HWVER_MRA2_1 == bChipVer) ||
250           (PHDNLDNFC_HWVER_MRA2_2 == bChipVer) ||
251           (IS_CHIP_TYPE_EQ(pn551) &&
252            ((PHDNLDNFC_HWVER_PN551_MRA1_0 == bChipVer))) ||
253           ((IS_CHIP_TYPE_EQ(pn553) || IS_CHIP_TYPE_EQ(pn557)) &&
254            ((PHDNLDNFC_HWVER_PN553_MRA1_0 == bChipVer) ||
255             (PHDNLDNFC_HWVER_PN553_MRA1_0_UPDATED & bChipVer) ||
256             ((PHDNLDNFC_HWVER_PN557_MRA1_0 == bChipVer)))) ||
257           (IS_CHIP_TYPE_EQ(sn100u) &&
258            (PHDNLDNFC_HWVER_VENUS_MRA1_0 & bChipVer)) ||
259           ((IS_CHIP_TYPE_EQ(sn220u) || IS_CHIP_TYPE_EQ(pn560)) &&
260            (PHDNLDNFC_HWVER_VULCAN_MRA1_0 & bChipVer))) {
261         (gpphDnldContext->FrameInp.Type) = phDnldNfc_ChkIntg;
262       } else {
263         (gpphDnldContext->FrameInp.Type) = phDnldNfc_FTNone;
264       }
265 
266       if ((NULL != pCRCData->pBuff) && (0 != pCRCData->wLen)) {
267         (gpphDnldContext->tRspBuffInfo.pBuff) = pCRCData->pBuff;
268         (gpphDnldContext->tRspBuffInfo.wLen) = pCRCData->wLen;
269         (gpphDnldContext->tCmdId) = PH_DL_CMD_CHECKINTEGRITY;
270         (gpphDnldContext->tUserData.pBuff) = NULL;
271         (gpphDnldContext->tUserData.wLen) = 0;
272         (gpphDnldContext->UserCb) = pNotify;
273         (gpphDnldContext->UserCtxt) = pContext;
274 
275         wStatus =
276             phDnldNfc_CmdHandler(gpphDnldContext, phDnldNfc_EventIntegChk);
277 
278         if (NFCSTATUS_PENDING == wStatus) {
279           NXPLOG_FWDNLD_D("CheckIntegrity Request submitted successfully");
280         } else {
281           NXPLOG_FWDNLD_E("CheckIntegrity Request Failed!!");
282         }
283       } else {
284         NXPLOG_FWDNLD_E("Invalid Buff Parameters!!");
285         wStatus = PHNFCSTVAL(CID_NFC_DNLD, NFCSTATUS_INVALID_PARAMETER);
286       }
287     }
288   }
289 
290   return wStatus;
291 }
292 /*******************************************************************************
293 **
294 ** Function         phDnldNfc_ReadLog
295 **
296 ** Description      Retrieves log data from EEPROM
297 **
298 ** Parameters       pData - response buffer which gets updated with data from
299 **                          EEPROM
300 **                  pNotify - notify caller after getting response
301 **                  pContext - caller context
302 **
303 ** Returns          NFC status:
304 **                  NFCSTATUS_SUCCESS - Read request to NFCC is successful
305 **                  NFCSTATUS_FAILED - Read request failed due to internal error
306 **                  NFCSTATUS_NOT_ALLOWED - command not allowed
307 **                  Other command specific errors
308 **
309 *******************************************************************************/
phDnldNfc_ReadLog(pphDnldNfc_Buff_t pData,pphDnldNfc_RspCb_t pNotify,void * pContext)310 NFCSTATUS phDnldNfc_ReadLog(pphDnldNfc_Buff_t pData, pphDnldNfc_RspCb_t pNotify,
311                             void* pContext) {
312   NFCSTATUS wStatus = NFCSTATUS_SUCCESS;
313 
314   if ((NULL == pNotify) || (NULL == pData) || (NULL == pContext)) {
315     NXPLOG_FWDNLD_E("Invalid Input Parameters!!");
316     wStatus = PHNFCSTVAL(CID_NFC_DNLD, NFCSTATUS_INVALID_PARAMETER);
317   } else {
318     if (phDnldNfc_TransitionIdle != gpphDnldContext->tDnldInProgress) {
319       NXPLOG_FWDNLD_E("Dnld Cmd Request in Progress..Cannot Continue!!");
320       wStatus = PHNFCSTVAL(CID_NFC_DNLD, NFCSTATUS_BUSY);
321     } else {
322       if ((NULL != pData->pBuff) && (0 != pData->wLen)) {
323         (gpphDnldContext->tCmdId) = PH_DL_CMD_READ;
324         (gpphDnldContext->FrameInp.Type) = phDnldNfc_FTRead;
325         (gpphDnldContext->FrameInp.dwAddr) = PHDNLDNFC_EEPROM_LOG_START_ADDR;
326         (gpphDnldContext->tRspBuffInfo.pBuff) = pData->pBuff;
327         (gpphDnldContext->tRspBuffInfo.wLen) = pData->wLen;
328         (gpphDnldContext->tUserData.pBuff) = NULL;
329         (gpphDnldContext->tUserData.wLen) = 0;
330         (gpphDnldContext->UserCb) = pNotify;
331         (gpphDnldContext->UserCtxt) = pContext;
332 
333         memset(&(gpphDnldContext->tRWInfo), 0,
334                sizeof(gpphDnldContext->tRWInfo));
335 
336         wStatus = phDnldNfc_CmdHandler(gpphDnldContext, phDnldNfc_EventRead);
337 
338         if (NFCSTATUS_PENDING == wStatus) {
339           NXPLOG_FWDNLD_D("Read Request submitted successfully");
340         } else {
341           NXPLOG_FWDNLD_E("Read Request Failed!!");
342         }
343       } else {
344         NXPLOG_FWDNLD_E("Invalid Buff Parameters!!");
345         wStatus = PHNFCSTVAL(CID_NFC_DNLD, NFCSTATUS_INVALID_PARAMETER);
346       }
347     }
348   }
349 
350   return wStatus;
351 }
352 
353 /*******************************************************************************
354 **
355 ** Function         phDnldNfc_Write
356 **
357 ** Description      Writes requested  data of length len to desired EEPROM/FLASH
358 **                  address
359 **
360 ** Parameters       bRecoverSeq - flag to indicate whether recover sequence data
361 **                                needs to be written or not
362 **                  pData - data buffer to write into EEPROM/FLASH by user
363 **                  pNotify - notify caller after getting response
364 **                  pContext - caller context
365 **
366 ** Returns          NFC status:
367 **                  NFCSTATUS_SUCCESS - Write request to NFCC is successful
368 **                  NFCSTATUS_FAILED - Write request failed due to internal
369 **                                     error
370 **                  NFCSTATUS_NOT_ALLOWED - command not allowed
371 **                  Other command specific errors
372 **
373 *******************************************************************************/
phDnldNfc_Write(bool_t bRecoverSeq,pphDnldNfc_Buff_t pData,pphDnldNfc_RspCb_t pNotify,void * pContext)374 NFCSTATUS phDnldNfc_Write(bool_t bRecoverSeq, pphDnldNfc_Buff_t pData,
375                           pphDnldNfc_RspCb_t pNotify, void* pContext) {
376   NFCSTATUS wStatus = NFCSTATUS_SUCCESS;
377   uint8_t* pImgPtr = NULL;
378   uint32_t wLen = 0;
379   phDnldNfc_Buff_t tImgBuff;
380 
381   if ((NULL == pNotify) || (NULL == pContext)) {
382     NXPLOG_FWDNLD_E("Invalid Input Parameters!!");
383     wStatus = PHNFCSTVAL(CID_NFC_DNLD, NFCSTATUS_INVALID_PARAMETER);
384   } else {
385     if (phDnldNfc_TransitionIdle != gpphDnldContext->tDnldInProgress) {
386       NXPLOG_FWDNLD_E("Dnld Cmd Request in Progress..Cannot Continue!!");
387       wStatus = PHNFCSTVAL(CID_NFC_DNLD, NFCSTATUS_BUSY);
388     } else {
389       if (NULL != pData) {
390         pImgPtr = pData->pBuff;
391         wLen = pData->wLen;
392       } else {
393         if (bRecoverSeq == false) {
394           pImgPtr = (uint8_t*)gpphDnldContext->nxp_nfc_fw;
395           wLen = gpphDnldContext->nxp_nfc_fw_len;
396 
397         } else {
398           if (IS_CHIP_TYPE_GE(sn100u)) {
399             if (PH_DL_STATUS_PLL_ERROR == (gpphDnldContext->tLastStatus)) {
400               wStatus = phDnldNfc_LoadRecInfo();
401             } else if (PH_DL_STATUS_SIGNATURE_ERROR ==
402                        (gpphDnldContext->tLastStatus)) {
403               wStatus = phDnldNfc_LoadPKInfo();
404             } else {
405             }
406           }
407 
408           if (NFCSTATUS_SUCCESS == wStatus) {
409             pImgPtr = (uint8_t*)gpphDnldContext->nxp_nfc_fwp;
410             wLen = gpphDnldContext->nxp_nfc_fwp_len;
411           } else {
412             NXPLOG_FWDNLD_E("Platform Recovery Image extraction Failed!!");
413             pImgPtr = NULL;
414             wLen = 0;
415           }
416         }
417       }
418 
419       if ((NULL != pImgPtr) && (0 != wLen)) {
420         tImgBuff.pBuff = pImgPtr;
421         tImgBuff.wLen = wLen;
422 
423         (gpphDnldContext->tCmdId) = PH_DL_CMD_WRITE;
424         (gpphDnldContext->FrameInp.Type) = phDnldNfc_FTWrite;
425         (gpphDnldContext->tRspBuffInfo.pBuff) = NULL;
426         (gpphDnldContext->tRspBuffInfo.wLen) = 0;
427         (gpphDnldContext->tUserData.pBuff) = pImgPtr;
428         (gpphDnldContext->tUserData.wLen) = wLen;
429         (gpphDnldContext->bResendLastFrame) = false;
430 
431         memset(&(gpphDnldContext->tRWInfo), 0,
432                sizeof(gpphDnldContext->tRWInfo));
433         (gpphDnldContext->tRWInfo.bFirstWrReq) = true;
434         (gpphDnldContext->UserCb) = pNotify;
435         (gpphDnldContext->UserCtxt) = pContext;
436 
437         wStatus = phDnldNfc_CmdHandler(gpphDnldContext, phDnldNfc_EventWrite);
438 
439         if (NFCSTATUS_PENDING == wStatus) {
440           NXPLOG_FWDNLD_D("Write Request submitted successfully");
441         } else {
442           NXPLOG_FWDNLD_E("Write Request Failed!!");
443         }
444       } else {
445         NXPLOG_FWDNLD_E("Download Image Primitives extraction failed!!");
446         wStatus = NFCSTATUS_FAILED;
447       }
448     }
449   }
450 
451   return wStatus;
452 }
453 
454 /*******************************************************************************
455 **
456 ** Function         phDnldNfc_Log
457 **
458 ** Description      Provides a full page free write to EEPROM
459 **
460 ** Parameters       pData - data buffer to write into EEPROM/FLASH by user
461 **                  pNotify - notify caller after getting response
462 **                  pContext - caller context
463 **
464 ** Returns          NFC status:
465 **                  NFCSTATUS_SUCCESS - Write request to NFCC is successful
466 **                  NFCSTATUS_FAILED - Write request failed due to internal
467 **                                     error
468 **                  NFCSTATUS_NOT_ALLOWED - command not allowed
469 **                  Other command specific error
470 **
471 *******************************************************************************/
phDnldNfc_Log(pphDnldNfc_Buff_t pData,pphDnldNfc_RspCb_t pNotify,void * pContext)472 NFCSTATUS phDnldNfc_Log(pphDnldNfc_Buff_t pData, pphDnldNfc_RspCb_t pNotify,
473                         void* pContext) {
474   NFCSTATUS wStatus = NFCSTATUS_SUCCESS;
475 
476   if ((NULL == pNotify) || (NULL == pData) || (NULL == pContext)) {
477     NXPLOG_FWDNLD_E("Invalid Input Parameters!!");
478     wStatus = PHNFCSTVAL(CID_NFC_DNLD, NFCSTATUS_INVALID_PARAMETER);
479   } else {
480     if (phDnldNfc_TransitionIdle != gpphDnldContext->tDnldInProgress) {
481       NXPLOG_FWDNLD_E("Dnld Cmd Request in Progress..Cannot Continue!!");
482       wStatus = PHNFCSTVAL(CID_NFC_DNLD, NFCSTATUS_BUSY);
483     } else {
484       if ((NULL != (pData->pBuff)) &&
485           ((0 != (pData->wLen) && (PHDNLDNFC_MAX_LOG_SIZE >= (pData->wLen))))) {
486         (gpphDnldContext->tCmdId) = PH_DL_CMD_LOG;
487         (gpphDnldContext->FrameInp.Type) = phDnldNfc_FTLog;
488         (gpphDnldContext->tRspBuffInfo.pBuff) = NULL;
489         (gpphDnldContext->tRspBuffInfo.wLen) = 0;
490         (gpphDnldContext->tUserData.pBuff) = (pData->pBuff);
491         (gpphDnldContext->tUserData.wLen) = (pData->wLen);
492 
493         memset(&(gpphDnldContext->tRWInfo), 0,
494                sizeof(gpphDnldContext->tRWInfo));
495         (gpphDnldContext->UserCb) = pNotify;
496         (gpphDnldContext->UserCtxt) = pContext;
497 
498         wStatus = phDnldNfc_CmdHandler(gpphDnldContext, phDnldNfc_EventLog);
499 
500         if (NFCSTATUS_PENDING == wStatus) {
501           NXPLOG_FWDNLD_D("Log Request submitted successfully");
502         } else {
503           NXPLOG_FWDNLD_E("Log Request Failed!!");
504         }
505       } else {
506         NXPLOG_FWDNLD_E("Invalid Input Parameters for Log!!");
507         wStatus = PHNFCSTVAL(CID_NFC_DNLD, NFCSTATUS_INVALID_PARAMETER);
508       }
509     }
510   }
511 
512   return wStatus;
513 }
514 
515 /*******************************************************************************
516 **
517 ** Function         phDnldNfc_Force
518 **
519 ** Description      Used as an emergency recovery procedure for NFCC due to
520 **                  corrupt settings of system platform specific parameters by
521 **                  the host
522 **
523 ** Parameters       pInputs - input buffer which contains  clk src & clk freq
524 **                            settings for desired platform
525 **                  pNotify - notify caller after getting response
526 **                  pContext - caller context
527 **
528 ** Returns          NFC status:
529 **                  NFCSTATUS_SUCCESS - Emergency Recovery request is successful
530 **                  NFCSTATUS_FAILED - Emergency Recovery failed due to internal
531 **                                     error
532 **                  NFCSTATUS_NOT_ALLOWED - command not allowed
533 **                  Other command specific errors
534 **
535 *******************************************************************************/
phDnldNfc_Force(pphDnldNfc_Buff_t pInputs,pphDnldNfc_RspCb_t pNotify,void * pContext)536 NFCSTATUS phDnldNfc_Force(pphDnldNfc_Buff_t pInputs, pphDnldNfc_RspCb_t pNotify,
537                           void* pContext) {
538   NFCSTATUS wStatus = NFCSTATUS_SUCCESS;
539   uint8_t bClkSrc = 0x00, bClkFreq = 0x00;
540   uint8_t bPldVal[3] = {
541       0x11, 0x00, 0x00}; /* default values to be used if input not provided */
542 
543   if ((NULL == pNotify) || (NULL == pContext)) {
544     NXPLOG_FWDNLD_E("Invalid Input Parameters!!");
545     wStatus = PHNFCSTVAL(CID_NFC_DNLD, NFCSTATUS_INVALID_PARAMETER);
546   } else {
547     if (phDnldNfc_TransitionIdle != gpphDnldContext->tDnldInProgress) {
548       NXPLOG_FWDNLD_E("Dnld Cmd Request in Progress..Cannot Continue!!");
549       wStatus = PHNFCSTVAL(CID_NFC_DNLD, NFCSTATUS_BUSY);
550     } else {
551       (gpphDnldContext->tCmdId) = PH_DL_CMD_FORCE;
552       (gpphDnldContext->FrameInp.Type) = phDnldNfc_FTForce;
553       (gpphDnldContext->tRspBuffInfo.pBuff) = NULL;
554       (gpphDnldContext->tRspBuffInfo.wLen) = 0;
555 
556       if ((0 != (pInputs->wLen)) || (NULL != (pInputs->pBuff))) {
557         if (CLK_SRC_XTAL == (pInputs->pBuff[0])) {
558           bClkSrc = phDnldNfc_ClkSrcXtal;
559         } else if (CLK_SRC_PLL == (pInputs->pBuff[0])) {
560           bClkSrc = phDnldNfc_ClkSrcPLL;
561           if (CLK_FREQ_13MHZ == (pInputs->pBuff[1])) {
562             bClkFreq = phDnldNfc_ClkFreq_13Mhz;
563           } else if (CLK_FREQ_19_2MHZ == (pInputs->pBuff[1])) {
564             bClkFreq = phDnldNfc_ClkFreq_19_2Mhz;
565           } else if (CLK_FREQ_24MHZ == (pInputs->pBuff[1])) {
566             bClkFreq = phDnldNfc_ClkFreq_24Mhz;
567           } else if (CLK_FREQ_26MHZ == (pInputs->pBuff[1])) {
568             bClkFreq = phDnldNfc_ClkFreq_26Mhz;
569           } else if (CLK_FREQ_38_4MHZ == (pInputs->pBuff[1])) {
570             bClkFreq = phDnldNfc_ClkFreq_38_4Mhz;
571           } else if (CLK_FREQ_52MHZ == (pInputs->pBuff[1])) {
572             bClkFreq = phDnldNfc_ClkFreq_52Mhz;
573           } else if (CLK_FREQ_32MHZ == (pInputs->pBuff[1])) {
574             bClkFreq = phDnldNfc_ClkFreq_32Mhz;
575           } else if (CLK_FREQ_48MHZ == (pInputs->pBuff[1])) {
576             bClkFreq = phDnldNfc_ClkFreq_48Mhz;
577           } else {
578             NXPLOG_FWDNLD_E(
579                 "Invalid Clk Frequency !! Using default value of 19.2Mhz..");
580             bClkFreq = phDnldNfc_ClkFreq_19_2Mhz;
581           }
582 
583         } else if (CLK_SRC_PADDIRECT == (pInputs->pBuff[0])) {
584           bClkSrc = phDnldNfc_ClkSrcPad;
585         } else {
586           NXPLOG_FWDNLD_E("Invalid Clk src !! Using default value of PLL..");
587           bClkSrc = phDnldNfc_ClkSrcPLL;
588         }
589 
590         bPldVal[0] = 0U;
591         bPldVal[0] = ((bClkSrc << 3U) | bClkFreq);
592       } else {
593         NXPLOG_FWDNLD_E("Clk src inputs not provided!! Using default values..");
594       }
595 
596       (gpphDnldContext->tUserData.pBuff) = bPldVal;
597       (gpphDnldContext->tUserData.wLen) = sizeof(bPldVal);
598 
599       memset(&(gpphDnldContext->tRWInfo), 0, sizeof(gpphDnldContext->tRWInfo));
600       (gpphDnldContext->UserCb) = pNotify;
601       (gpphDnldContext->UserCtxt) = pContext;
602 
603       wStatus = phDnldNfc_CmdHandler(gpphDnldContext, phDnldNfc_EventForce);
604 
605       if (NFCSTATUS_PENDING == wStatus) {
606         NXPLOG_FWDNLD_D("Force Command Request submitted successfully");
607       } else {
608         NXPLOG_FWDNLD_E("Force Command Request Failed!!");
609       }
610     }
611   }
612 
613   return wStatus;
614 }
615 
616 /*******************************************************************************
617 **
618 ** Function         phDnldNfc_SetHwDevHandle
619 **
620 ** Description      Stores the HwDev handle to download context. The handle is
621 **                  required for subsequent operations
622 **
623 ** Parameters       None
624 **
625 ** Returns          None                -
626 **
627 *******************************************************************************/
phDnldNfc_SetHwDevHandle(void)628 void phDnldNfc_SetHwDevHandle(void) {
629   pphDnldNfc_DlContext_t psDnldContext = NULL;
630 
631   if (NULL == gpphDnldContext) {
632     NXPLOG_FWDNLD_D("Allocating Mem for Dnld Context..");
633     /* Create the memory for Download Mgmt Context */
634     psDnldContext =
635         (pphDnldNfc_DlContext_t)malloc(sizeof(phDnldNfc_DlContext_t));
636 
637     if (psDnldContext != NULL) {
638       (void)memset((void*)psDnldContext, 0, sizeof(phDnldNfc_DlContext_t));
639       gpphDnldContext = psDnldContext;
640     } else {
641       NXPLOG_FWDNLD_E("Error Allocating Mem for Dnld Context..");
642     }
643   } else {
644     (void)memset((void*)gpphDnldContext, 0, sizeof(phDnldNfc_DlContext_t));
645   }
646   return;
647 }
648 
649 /*******************************************************************************
650 **
651 ** Function         phDnldNfc_ReSetHwDevHandle
652 **
653 ** Description      Frees the HwDev handle to download context.
654 **
655 ** Parameters       None
656 **
657 ** Returns          None                -
658 **
659 *******************************************************************************/
phDnldNfc_ReSetHwDevHandle(void)660 void phDnldNfc_ReSetHwDevHandle(void) {
661   if (gpphDnldContext != NULL) {
662     NXPLOG_FWDNLD_D("Freeing Mem for Dnld Context..");
663     free(gpphDnldContext);
664     gpphDnldContext = NULL;
665   }
666 }
667 
668 /*******************************************************************************
669 **
670 ** Function         phDnldNfc_RawReq
671 **
672 ** Description      Sends raw frame request to NFCC.
673 **                  It is currently used for sending an NCI RESET cmd after
674 **                  doing a production key update
675 **
676 ** Parameters       pFrameData - input buffer, contains raw frame packet to be
677 **                               sent to NFCC
678 **                  pRspData - response buffer received from NFCC
679 **                  pNotify - notify caller after getting response
680 **                  pContext - caller context
681 **
682 ** Returns          NFC status:
683 **                  NFCSTATUS_SUCCESS - GetSessionState request to NFCC is
684 **                                      successful
685 **                  NFCSTATUS_FAILED - GetSessionState request failed due to
686 **                                     internal error
687 **                  NFCSTATUS_NOT_ALLOWED - command not allowed
688 **                  Other command specific errors
689 **
690 *******************************************************************************/
phDnldNfc_RawReq(pphDnldNfc_Buff_t pFrameData,pphDnldNfc_Buff_t pRspData,pphDnldNfc_RspCb_t pNotify,void * pContext)691 NFCSTATUS phDnldNfc_RawReq(pphDnldNfc_Buff_t pFrameData,
692                            pphDnldNfc_Buff_t pRspData,
693                            pphDnldNfc_RspCb_t pNotify, void* pContext) {
694   NFCSTATUS wStatus = NFCSTATUS_SUCCESS;
695 
696   if ((NULL == pFrameData) || (NULL == pNotify) || (NULL == pRspData) ||
697       (NULL == pContext)) {
698     NXPLOG_FWDNLD_E("Invalid Input Parameters!!");
699     wStatus = PHNFCSTVAL(CID_NFC_DNLD, NFCSTATUS_INVALID_PARAMETER);
700   } else {
701     if (phDnldNfc_TransitionIdle != gpphDnldContext->tDnldInProgress) {
702       NXPLOG_FWDNLD_E("Raw Cmd Request in Progress..Cannot Continue!!");
703       wStatus = PHNFCSTVAL(CID_NFC_DNLD, NFCSTATUS_BUSY);
704     } else {
705       if (((NULL != pFrameData->pBuff) && (0 != pFrameData->wLen)) &&
706           ((NULL != pRspData->pBuff) && (0 != pRspData->wLen))) {
707         (gpphDnldContext->tRspBuffInfo.pBuff) = pRspData->pBuff;
708         (gpphDnldContext->tRspBuffInfo.wLen) = pRspData->wLen;
709         (gpphDnldContext->FrameInp.Type) = phDnldNfc_FTRaw;
710         (gpphDnldContext->tCmdId) = PH_DL_CMD_NONE;
711         (gpphDnldContext->tUserData.pBuff) = pFrameData->pBuff;
712         (gpphDnldContext->tUserData.wLen) = pFrameData->wLen;
713         (gpphDnldContext->UserCb) = pNotify;
714         (gpphDnldContext->UserCtxt) = pContext;
715 
716         wStatus = phDnldNfc_CmdHandler(gpphDnldContext, phDnldNfc_EventRaw);
717 
718         if (NFCSTATUS_PENDING == wStatus) {
719           NXPLOG_FWDNLD_D("RawFrame Request submitted successfully");
720         } else {
721           NXPLOG_FWDNLD_E("RawFrame Request Failed!!");
722         }
723       } else {
724         NXPLOG_FWDNLD_E("Invalid Buff Parameters!!");
725         wStatus = PHNFCSTVAL(CID_NFC_DNLD, NFCSTATUS_INVALID_PARAMETER);
726       }
727     }
728   }
729 
730   return wStatus;
731 }
732 
733 /*******************************************************************************
734 **
735 ** Function         phDnldNfc_InitImgInfo
736 **
737 ** Description      Extracts image information and stores it in respective
738 **                  variables, to be used internally for write operation
739 **
740 ** Parameters       bMinimalFw - flag indicates for minimal FW Image
741 **
742 ** Returns          NFC status
743 **
744 *******************************************************************************/
phDnldNfc_InitImgInfo(bool bMinimalFw)745 NFCSTATUS phDnldNfc_InitImgInfo(bool bMinimalFw) {
746   NFCSTATUS wStatus = NFCSTATUS_SUCCESS;
747   uint8_t* pImageInfo = NULL;
748   uint32_t ImageInfoLen = 0;
749   unsigned long fwType = FW_FORMAT_SO;
750 
751   /* if memory is not allocated then allocate memory for download context
752    * structure */
753   phDnldNfc_SetHwDevHandle();
754 
755   gpphDnldContext->FwFormat = FW_FORMAT_UNKNOWN;
756   phDnldNfc_SetDlRspTimeout((uint16_t)PHDNLDNFC_RSP_TIMEOUT);
757   if (bMinimalFw) {
758     fwType = FW_FORMAT_ARRAY;
759   } else if (GetNxpNumValue(NAME_NXP_FW_TYPE, &fwType, sizeof(fwType)) ==
760              true) {
761     /*Read Firmware file name from config file*/
762     NXPLOG_FWDNLD_D("firmware type from conf file: %lu", fwType);
763   } else {
764     NXPLOG_FWDNLD_W("firmware type not found. Taking default value: %lu",
765                     fwType);
766   }
767 
768   if (fwType == FW_FORMAT_ARRAY) {
769     gpphDnldContext->FwFormat = FW_FORMAT_ARRAY;
770 #if (NXP_NFC_RECOVERY == TRUE)
771     pImageInfo = (uint8_t*)gphDnldNfc_DlSequence;
772     ImageInfoLen = gphDnldNfc_DlSeqSz;
773 #endif
774     wStatus = NFCSTATUS_SUCCESS;
775   } else if (fwType == FW_FORMAT_BIN) {
776     gpphDnldContext->FwFormat = FW_FORMAT_BIN;
777     wStatus = phDnldNfc_LoadBinFW(&pImageInfo, &ImageInfoLen);
778   } else if (fwType == FW_FORMAT_SO) {
779     gpphDnldContext->FwFormat = FW_FORMAT_SO;
780 #ifdef NXP_DUMMY_FW_DNLD
781     if (gRecFWDwnld == true) {
782       wStatus =
783           phDnldNfc_LoadRecoveryFW(Fw_Lib_Path, &pImageInfo, &ImageInfoLen);
784     } else {
785       wStatus = phDnldNfc_LoadFW(Fw_Lib_Path, &pImageInfo, &ImageInfoLen);
786     }
787 #else
788     wStatus = phDnldNfc_LoadFW(Fw_Lib_Path, &pImageInfo, &ImageInfoLen);
789 #endif
790   } else {
791     NXPLOG_FWDNLD_E("firmware file format mismatch!!!\n");
792     return NFCSTATUS_FAILED;
793   }
794 
795   NXPLOG_FWDNLD_D("FW Image Length - ImageInfoLen %d", ImageInfoLen);
796   NXPLOG_FWDNLD_D("FW Image Info Pointer - pImageInfo %p", pImageInfo);
797 
798   if ((pImageInfo == NULL) || (ImageInfoLen == 0)) {
799     NXPLOG_FWDNLD_E(
800         "Image extraction Failed - invalid imginfo or imginfolen!!");
801     wStatus = NFCSTATUS_FAILED;
802   }
803 
804   if (wStatus != NFCSTATUS_SUCCESS) {
805     NXPLOG_FWDNLD_E("Error loading FW file !!\n");
806   }
807 
808   /* get the MW version */
809   if (NFCSTATUS_SUCCESS == wStatus) {
810     // NXPLOG_FWDNLD_D("MW Major Version Num - %x",NXP_MW_VERSION_MAJ);
811     // NXPLOG_FWDNLD_D("MW Minor Version Num - %x",NXP_MW_VERSION_MIN);
812     wMwVer = (((uint16_t)(NXP_MW_VERSION_MAJ) << 8U) | (NXP_MW_VERSION_MIN));
813   }
814 
815   if (NFCSTATUS_SUCCESS == wStatus) {
816     gpphDnldContext->nxp_nfc_fw = (uint8_t*)pImageInfo;
817     gpphDnldContext->nxp_nfc_fw_len = ImageInfoLen;
818     if ((NULL != gpphDnldContext->nxp_nfc_fw) &&
819         (0 != gpphDnldContext->nxp_nfc_fw_len)) {
820       uint16_t offsetFwMajorNum, offsetFwMinorNum;
821       if (IS_CHIP_TYPE_EQ(sn220u) || IS_CHIP_TYPE_EQ(pn560)) {
822         offsetFwMajorNum = ((uint16_t)(gpphDnldContext->nxp_nfc_fw[795]) << 8U);
823         offsetFwMinorNum = ((uint16_t)(gpphDnldContext->nxp_nfc_fw[794]));
824       } else {
825         offsetFwMajorNum = ((uint16_t)(gpphDnldContext->nxp_nfc_fw[5]) << 8U);
826         offsetFwMinorNum = ((uint16_t)(gpphDnldContext->nxp_nfc_fw[4]));
827       }
828       NXPLOG_FWDNLD_D("FW Major Version Num - %x", offsetFwMajorNum);
829       NXPLOG_FWDNLD_D("FW Minor Version Num - %x", offsetFwMinorNum);
830       /* get the FW version */
831       wFwVer = (offsetFwMajorNum | offsetFwMinorNum);
832 
833       NXPLOG_FWDNLD_D("FW Image Length - %d", ImageInfoLen);
834       NXPLOG_FWDNLD_D("FW Image Info Pointer - %p", pImageInfo);
835       wStatus = NFCSTATUS_SUCCESS;
836     } else {
837       NXPLOG_FWDNLD_E("Image details extraction Failed!!");
838       wStatus = NFCSTATUS_FAILED;
839     }
840   }
841 
842   /* gpphDnldContext reset by phDnldNfc_SetHwDevHandle()
843      so reassign the Fragment Length based on chip version */
844   if (NFCSTATUS_SUCCESS == wStatus) {
845     if (IS_CHIP_TYPE_GE(sn100u)) {
846       phDnldNfc_SetI2CFragmentLength(PHDNLDNFC_CMDRESP_MAX_BUFF_SIZE_SNXXX);
847     } else {
848       phDnldNfc_SetI2CFragmentLength(PHDNLDNFC_CMDRESP_MAX_BUFF_SIZE_PN557);
849     }
850   }
851 
852   return wStatus;
853 }
854 
855 /*******************************************************************************
856 **
857 ** Function         phDnldNfc_LoadRecInfo
858 **
859 ** Description      Extracts recovery sequence image information and stores it
860 **                  in respective variables, to be used internally for write
861 **                  operation
862 **
863 ** Parameters       None
864 **
865 ** Returns          NFC status
866 **
867 *******************************************************************************/
phDnldNfc_LoadRecInfo(void)868 NFCSTATUS phDnldNfc_LoadRecInfo(void) {
869   NFCSTATUS wStatus = NFCSTATUS_SUCCESS;
870   uint8_t* pImageInfo = NULL;
871   uint32_t ImageInfoLen = 0;
872 
873   /* if memory is not allocated then allocate memory for donwload context
874    * structure */
875   phDnldNfc_SetHwDevHandle();
876 #ifdef NXP_DUMMY_FW_DNLD
877   if (gRecFWDwnld == true)
878     wStatus =
879         phDnldNfc_LoadRecoveryFW(PLATFORM_LIB_PATH, &pImageInfo, &ImageInfoLen);
880   else
881 #endif
882     wStatus = phDnldNfc_LoadFW(PLATFORM_LIB_PATH, &pImageInfo, &ImageInfoLen);
883   if ((pImageInfo == NULL) || (ImageInfoLen == 0)) {
884     NXPLOG_FWDNLD_E(
885         "Image extraction Failed - invalid imginfo or imginfolen!!");
886     wStatus = NFCSTATUS_FAILED;
887   }
888 
889   /* load the PLL recovery image library */
890   if (wStatus != NFCSTATUS_SUCCESS) {
891     NXPLOG_FWDNLD_E("Error loading FW file... !!\n");
892   }
893 
894   if (NFCSTATUS_SUCCESS == wStatus) {
895     /* fetch the PLL recovery image pointer and the image length */
896     gpphDnldContext->nxp_nfc_fwp = (uint8_t*)pImageInfo;
897     gpphDnldContext->nxp_nfc_fwp_len = ImageInfoLen;
898 
899     /* gpphDnldContext reset by phDnldNfc_SetHwDevHandle()
900     so reassign the Fragment Length 554 (0x22A) for chip sn1xx*/
901     phDnldNfc_SetI2CFragmentLength(PHDNLDNFC_CMDRESP_MAX_BUFF_SIZE_SNXXX);
902 
903     if ((NULL != gpphDnldContext->nxp_nfc_fwp) &&
904         (0 != gpphDnldContext->nxp_nfc_fwp_len)) {
905       NXPLOG_FWDNLD_D("Recovery Image Length - %d", ImageInfoLen);
906       NXPLOG_FWDNLD_D("Recovery Image Info Pointer - %p", pImageInfo);
907       wStatus = NFCSTATUS_SUCCESS;
908     } else {
909       NXPLOG_FWDNLD_E("Recovery Image details extraction Failed!!");
910       wStatus = NFCSTATUS_FAILED;
911     }
912   }
913 
914   return wStatus;
915 }
916 
917 /*******************************************************************************
918 **
919 ** Function         phDnldNfc_LoadPKInfo
920 **
921 ** Description      Extracts production sequence image information and stores it
922 **                  in respective variables, to be used internally for write
923 **                  operation
924 **
925 ** Parameters       None
926 **
927 ** Returns          NFC status
928 **
929 *******************************************************************************/
phDnldNfc_LoadPKInfo(void)930 NFCSTATUS phDnldNfc_LoadPKInfo(void) {
931   NFCSTATUS wStatus = NFCSTATUS_SUCCESS;
932   uint8_t* pImageInfo = NULL;
933   uint32_t ImageInfoLen = 0;
934 
935   /* if memory is not allocated then allocate memory for donwload context
936    * structure */
937   phDnldNfc_SetHwDevHandle();
938 
939 /* load the PKU image library */
940 #ifdef NXP_DUMMY_FW_DNLD
941   if (gRecFWDwnld == true)
942     wStatus =
943         phDnldNfc_LoadRecoveryFW(PKU_LIB_PATH, &pImageInfo, &ImageInfoLen);
944   else
945 #endif
946     wStatus = phDnldNfc_LoadFW(PKU_LIB_PATH, &pImageInfo, &ImageInfoLen);
947   if ((pImageInfo == NULL) || (ImageInfoLen == 0)) {
948     NXPLOG_FWDNLD_E(
949         "Image extraction Failed - invalid imginfo or imginfolen!!");
950     wStatus = NFCSTATUS_FAILED;
951   }
952 
953   if (wStatus != NFCSTATUS_SUCCESS) {
954     NXPLOG_FWDNLD_E("Error loading FW File pku !!\n");
955   }
956 
957   if (NFCSTATUS_SUCCESS == wStatus) {
958     /* fetch the PKU image pointer and the image length */
959     gpphDnldContext->nxp_nfc_fwp = (uint8_t*)pImageInfo;
960     gpphDnldContext->nxp_nfc_fwp_len = ImageInfoLen;
961 
962     /* gpphDnldContext reset by phDnldNfc_SetHwDevHandle()
963     so reassign the Fragment Length 554 (0x22A) for chip sn1xx*/
964     phDnldNfc_SetI2CFragmentLength(PHDNLDNFC_CMDRESP_MAX_BUFF_SIZE_SNXXX);
965 
966     if ((NULL != gpphDnldContext->nxp_nfc_fwp) &&
967         (0 != gpphDnldContext->nxp_nfc_fwp_len)) {
968       NXPLOG_FWDNLD_D("PKU Image Length - %d", ImageInfoLen);
969       NXPLOG_FWDNLD_D("PKU Image Info Pointer - %p", pImageInfo);
970       wStatus = NFCSTATUS_SUCCESS;
971     } else {
972       NXPLOG_FWDNLD_E("PKU Image details extraction Failed!!");
973       wStatus = NFCSTATUS_FAILED;
974     }
975   }
976 
977   return wStatus;
978 }
979 
980 /*******************************************************************************
981 **
982 ** Function         phDnldNfc_CloseFwLibHandle
983 **
984 ** Description      Closes previously opened fw library handle as part of
985 **                  dynamic loader processing
986 **
987 ** Parameters       None
988 **
989 ** Returns          None
990 **
991 *******************************************************************************/
phDnldNfc_CloseFwLibHandle(void)992 void phDnldNfc_CloseFwLibHandle(void) {
993   NFCSTATUS wStatus = NFCSTATUS_FAILED;
994   if (gpphDnldContext->FwFormat == FW_FORMAT_SO) {
995     wStatus = phDnldNfc_UnloadFW();
996     if (wStatus != NFCSTATUS_SUCCESS) {
997       NXPLOG_FWDNLD_E("free library FAILED !!\n");
998     } else {
999       NXPLOG_FWDNLD_E("free library SUCCESS !!\n");
1000     }
1001   } else if (gpphDnldContext->FwFormat == FW_FORMAT_BIN) {
1002     if (pFwHandle != NULL) {
1003       free(pFwHandle);
1004       pFwHandle = NULL;
1005     }
1006   }
1007   return;
1008 }
1009 
1010 /*******************************************************************************
1011 **
1012 ** Function         phDnldNfc_LoadFW
1013 **
1014 ** Description      Load the firmware version form firmware lib
1015 **
1016 ** Parameters       pathName    - Firmware image path
1017 **                  pImgInfo    - Firmware image handle
1018 **                  pImgInfoLen - Firmware image length
1019 **
1020 ** Returns          NFC status
1021 **
1022 *******************************************************************************/
phDnldNfc_LoadFW(const char * pathName,uint8_t ** pImgInfo,uint32_t * pImgInfoLen)1023 NFCSTATUS phDnldNfc_LoadFW(const char* pathName, uint8_t** pImgInfo,
1024                            uint32_t* pImgInfoLen) {
1025   void* pImageInfo = NULL;
1026   void* pImageInfoLen = NULL;
1027 
1028   /* check for path name */
1029   if (pathName == NULL) pathName = nfcFL._FW_LIB_PATH.c_str();
1030 
1031   /* check if the handle is not NULL then free the library */
1032   if (pFwHandle != NULL) {
1033     phDnldNfc_CloseFwLibHandle();
1034     pFwHandle = NULL;
1035   }
1036 
1037   /* load the DLL file */
1038   pFwHandle = dlopen(pathName, RTLD_LAZY);
1039   NXPLOG_FWDNLD_D("@@@%s", pathName);
1040 
1041   /* if library load failed then handle will be NULL */
1042   if (pFwHandle == NULL) {
1043     NXPLOG_FWDNLD_E(
1044         "NULL handler : unable to load the library file, specify correct path");
1045     return NFCSTATUS_FAILED;
1046   }
1047 
1048   dlerror(); /* Clear any existing error */
1049 
1050   /* load the address of download image pointer and image size */
1051   pImageInfo = (void*)dlsym(pFwHandle, "gphDnldNfc_DlSeq");
1052 
1053   if (dlerror() || (NULL == pImageInfo)) {
1054     NXPLOG_FWDNLD_E("Problem loading symbol : gphDnldNfc_DlSeq");
1055     return NFCSTATUS_FAILED;
1056   }
1057   (*pImgInfo) = (*(uint8_t**)pImageInfo);
1058 
1059   pImageInfoLen = (void*)dlsym(pFwHandle, "gphDnldNfc_DlSeqSz");
1060   if (dlerror() || (NULL == pImageInfoLen)) {
1061     NXPLOG_FWDNLD_E("Problem loading symbol : gphDnldNfc_DlSeqSz");
1062     return NFCSTATUS_FAILED;
1063   }
1064 
1065   if (IS_CHIP_TYPE_GE(sn100u)) {
1066     (*pImgInfoLen) = (uint32_t)(*((uint32_t*)pImageInfoLen));
1067     NXPLOG_FWDNLD_D("FW image loded for chipType sn100u (%x)", nfcFL.chipType)
1068   } else {
1069     (*pImgInfoLen) = (uint16_t)(*((uint16_t*)pImageInfoLen));
1070     NXPLOG_FWDNLD_D("FW image loded for chipType pn557 (%x)", nfcFL.chipType)
1071   }
1072 
1073   return NFCSTATUS_SUCCESS;
1074 }
1075 
1076 /*******************************************************************************
1077 **
1078 ** Function         phDnldNfc_LoadBinFW
1079 **
1080 ** Description      Load the firmware version form firmware lib
1081 **
1082 ** Parameters       pImgInfo    - Firmware image handle
1083 **                  pImgInfoLen - Firmware image length
1084 **
1085 ** Returns          NFC status
1086 **
1087 *******************************************************************************/
phDnldNfc_LoadBinFW(uint8_t ** pImgInfo,uint32_t * pImgInfoLen)1088 NFCSTATUS phDnldNfc_LoadBinFW(uint8_t** pImgInfo, uint32_t* pImgInfoLen) {
1089   FILE* pFile = NULL;
1090   long fileSize = 0;
1091   long bytesRead = 0;
1092   long ftellFileSize = 0;
1093 
1094   /* check for path name */
1095   if (nfcFL._FW_BIN_PATH.c_str() == NULL) {
1096     NXPLOG_FWDNLD_E("Invalid FW file path!!!\n");
1097     return NFCSTATUS_FAILED;
1098   }
1099 
1100   /* check if the handle is not NULL then free the memory*/
1101   if (pFwHandle != NULL) {
1102     phDnldNfc_CloseFwLibHandle();
1103     pFwHandle = NULL;
1104   }
1105 
1106   /* Open the FW binary image file to be read */
1107   pFile = fopen(nfcFL._FW_BIN_PATH.c_str(), "r");
1108   if (NULL == pFile) {
1109     NXPLOG_FWDNLD_E("Failed to load FW binary image file!!!\n");
1110     return NFCSTATUS_FAILED;
1111   }
1112 
1113   /* Seek to the end of the file */
1114   fseek(pFile, 0, SEEK_END);
1115 
1116   /* get the actual length of the file */
1117   ftellFileSize = ftell(pFile);
1118 
1119   if (ftellFileSize > 0) {
1120     fileSize = ftellFileSize;
1121   } else {
1122     fileSize = 0;
1123   }
1124 
1125   /* Seek to the start of the file, to move file handle back to start of file*/
1126   fseek(pFile, 0, SEEK_SET);
1127 
1128   /* allocate the memory to read the FW binary image */
1129   pFwHandle = (void*)malloc(sizeof(uint8_t) * fileSize);
1130 
1131   /* check for valid memory allocation */
1132   if (NULL == pFwHandle) {
1133     NXPLOG_FWDNLD_E("Failed to allocate memory to load FW image !!!\n");
1134     fclose(pFile);
1135     return NFCSTATUS_FAILED;
1136   }
1137 
1138   /* Read the actual contents of the FW binary image */
1139   bytesRead =
1140       (uint32_t)fread(pFwHandle, sizeof(uint8_t), (size_t)fileSize, pFile);
1141   if (bytesRead != fileSize) {
1142     NXPLOG_FWDNLD_E("Unable to read the specified size from file !!!\n");
1143     fclose(pFile);
1144     free(pFwHandle);
1145     pFwHandle = NULL;
1146     return NFCSTATUS_FAILED;
1147   }
1148 
1149   /* Update the image info pointer to the caller */
1150   *pImgInfo = (uint8_t*)pFwHandle;
1151   *pImgInfoLen = (uint32_t)(bytesRead & 0xFFFFFFFF);
1152 
1153   /* close the FW binary image file */
1154   fclose(pFile);
1155   return NFCSTATUS_SUCCESS;
1156 }
1157 
1158 /*******************************************************************************
1159 **
1160 ** Function         phDnldNfc_LoadRecoveryFW
1161 **
1162 ** Description      Load the recovery firmware version form firmware lib for
1163 **                  recovery. This will change the FW version of the NFCC
1164 **                  firmware and enable flashing of firmware of same version.
1165 **
1166 ** Parameters       pathName    - Firmware image path
1167 **                  pImgInfo    - Firmware image handle
1168 **                  pImgInfoLen - Firmware image length
1169 **
1170 ** Returns          NFCSTATUS
1171 **
1172 *******************************************************************************/
phDnldNfc_LoadRecoveryFW(const char * pathName,uint8_t ** pImgInfo,uint32_t * pImgInfoLen)1173 NFCSTATUS phDnldNfc_LoadRecoveryFW(const char* pathName, uint8_t** pImgInfo,
1174                                    uint32_t* pImgInfoLen) {
1175   void* pImageInfo = NULL;
1176   void* pImageInfoLen = NULL;
1177 
1178   /* check for path name */
1179   if (pathName == NULL) pathName = nfcFL._FW_LIB_PATH.c_str();
1180 
1181   /* check if the handle is not NULL then free the library */
1182   if (pFwHandle != NULL) {
1183     phDnldNfc_CloseFwLibHandle();
1184     pFwHandle = NULL;
1185   }
1186   /* load the DLL file */
1187   pFwHandle = dlopen(pathName, RTLD_LAZY);
1188   NXPLOG_FWDNLD_D("phDnldNfc_LoadRecoveryFW %s ", pathName);
1189 
1190   /* if library load failed then handle will be NULL */
1191   if (pFwHandle == NULL) {
1192     NXPLOG_FWDNLD_E(
1193         "NULL handler : unable to load the library file, specify correct path");
1194     return NFCSTATUS_FAILED;
1195   }
1196 
1197   dlerror(); /* Clear any existing error */
1198 
1199   /* load the address of download image pointer and image size */
1200   pImageInfo = (void*)dlsym(pFwHandle, "gphDnldNfc_DummyDlSeq");
1201 
1202   if (dlerror() || (NULL == pImageInfo)) {
1203     NXPLOG_FWDNLD_E("Problem loading symbol : gphDnldNfc_DummyDlSeq");
1204     return NFCSTATUS_FAILED;
1205   }
1206 
1207   (*pImgInfo) = (*(uint8_t**)pImageInfo);
1208   pImageInfoLen = (void*)dlsym(pFwHandle, "gphDnldNfc_DlSeqDummyFwSz");
1209   if (dlerror() || (NULL == pImageInfoLen)) {
1210     NXPLOG_FWDNLD_E("Problem loading symbol : gphDnldNfc_DlSeqDummyFwSz");
1211     return NFCSTATUS_FAILED;
1212   }
1213 
1214   (*pImgInfoLen) = (uint32_t)(*((uint32_t*)pImageInfoLen));
1215 
1216   return NFCSTATUS_SUCCESS;
1217 }
1218 
1219 /*******************************************************************************
1220 **
1221 ** Function         phDnldNfc_UnloadFW
1222 **
1223 ** Description      Deinit the firmware handle
1224 **
1225 ** Parameters       None
1226 **
1227 ** Returns          NFC status
1228 **
1229 *******************************************************************************/
phDnldNfc_UnloadFW(void)1230 NFCSTATUS phDnldNfc_UnloadFW(void) {
1231   NFCSTATUS wStatus = NFCSTATUS_SUCCESS;
1232   int32_t status;
1233 
1234   /* check if the handle is not NULL then free the library */
1235   if (pFwHandle != NULL) {
1236     status = dlclose(pFwHandle);
1237     pFwHandle = NULL;
1238 
1239     dlerror(); /* Clear any existing error */
1240     if (status != 0) {
1241       wStatus = NFCSTATUS_FAILED;
1242       NXPLOG_FWDNLD_E("Free library file failed");
1243     }
1244   }
1245 
1246   return wStatus;
1247 }
1248 
1249 /*******************************************************************************
1250 **
1251 ** Function         phDnldNfc_SetDlRspTimeout
1252 **
1253 ** Description      This function sets the timeout value dnld cmd response
1254 **
1255 ** Parameters       timeout : timeout value for dnld response
1256 **
1257 ** Returns          None
1258 **
1259 *******************************************************************************/
phDnldNfc_SetDlRspTimeout(uint16_t timeout)1260 void phDnldNfc_SetDlRspTimeout(uint16_t timeout) {
1261   gpphDnldContext->TimerInfo.rspTimeout = timeout;
1262   NXPLOG_FWDNLD_E("phDnldNfc_SetDlRspTimeout timeout value =%x", timeout);
1263 }
1264 
1265 /*******************************************************************************
1266 **
1267 ** Function         phDnldNfc_SetI2CFragmentLength
1268 **
1269 ** Description      sets the fragment length
1270 **
1271 ** Parameters       Fragment Length
1272 **
1273 ** Returns          None                -
1274 **
1275 *******************************************************************************/
phDnldNfc_SetI2CFragmentLength(uint16_t len)1276 void phDnldNfc_SetI2CFragmentLength(uint16_t len) {
1277   if (NULL != gpphDnldContext) {
1278     gpphDnldContext->nxp_i2c_fragment_len = len;
1279     NXPLOG_FWDNLD_D("fragment len set %x",
1280                     gpphDnldContext->nxp_i2c_fragment_len);
1281   } else {
1282     NXPLOG_FWDNLD_E("Error setting the fragment length");
1283   }
1284   return;
1285 }
1286 
1287 #ifdef EEPROM_Read_Mem_IMP
1288 static pphDnldNfc_RspCb_t UserCb; /* Upper layer call back function */
1289 static void* UserCtxt;            /* Pointer to upper layer context */
1290 /* Function prototype declaration */
1291 static void phDnldNfc_ReadComplete(void* pContext, NFCSTATUS status,
1292                                    void* pInfo);
1293 
1294 /*******************************************************************************
1295 **
1296 ** Function         phDnldNfc_ReadMem
1297 **
1298 ** Description      Dumps the contents of EEPROM. The handle is required for
1299 **                  subsequent operations
1300 **
1301 ** Parameters       pHwRef - pointer to the hardware device
1302 **                  pNotify - notify caller after getting response
1303 **                  pContext - caller context
1304 **
1305 ** Returns          NFC status:
1306 **                  NFCSTATUS_SUCCESS - request to NFCC is successful
1307 **                  NFCSTATUS_FAILED - request failed due to internal error
1308 **                  NFCSTATUS_NOT_ALLOWED - command not allowed
1309 **                  Other command specific errors
1310 **
1311 *******************************************************************************/
phDnldNfc_ReadMem(void * pHwRef,pphDnldNfc_RspCb_t pNotify,void * pContext)1312 NFCSTATUS phDnldNfc_ReadMem(void* pHwRef, pphDnldNfc_RspCb_t pNotify,
1313                             void* pContext) {
1314   NFCSTATUS wStatus = NFCSTATUS_SUCCESS;
1315   uint32_t wAddr = 0x2011C0; /* eeprom platform specific area start address */
1316   uint32_t wRdAddr = 0;
1317   uint8_t* pAddr;
1318   static uint8_t bRdData[3519]; /* buffer to hold the read data */
1319   static phDnldNfc_Buff_t Data;
1320 
1321   if ((NULL == pNotify) || (NULL == pContext)) {
1322     NXPLOG_FWDNLD_E("Invalid Input Parameters!!");
1323     wStatus = PHNFCSTVAL(CID_NFC_DNLD, NFCSTATUS_INVALID_PARAMETER);
1324   } else {
1325     /* Call Tml Ioctl to enable download mode */
1326     wStatus = phTmlNfc_IoCtl(phTmlNfc_e_EnableDownloadMode);
1327 
1328     if (NFCSTATUS_SUCCESS == wStatus) {
1329       /* Set the obtained device handle to download module */
1330       phDnldNfc_SetHwDevHandle();
1331       /* gpphDnldContext reset by phDnldNfc_SetHwDevHandle()
1332       so reassign the Fragment Length 554 (0x22A) for chip sn1xx*/
1333       phDnldNfc_SetI2CFragmentLength(PHDNLDNFC_CMDRESP_MAX_BUFF_SIZE_SNXXX);
1334     } else {
1335       wStatus = NFCSTATUS_FAILED;
1336     }
1337 
1338     if (NFCSTATUS_SUCCESS == wStatus) {
1339       pAddr = (uint8_t*)&wAddr;
1340 
1341       wRdAddr = (pAddr[3]);
1342       wRdAddr <<= 8;
1343       wRdAddr |= (pAddr[2]);
1344       wRdAddr <<= 8;
1345       wRdAddr |= (pAddr[1]);
1346       wRdAddr <<= 8;
1347       wRdAddr |= (pAddr[0]);
1348 
1349       Data.pBuff = bRdData;
1350       Data.wLen = sizeof(bRdData);
1351       UserCb = pNotify;
1352       UserCtxt = pContext;
1353 
1354       wStatus = phDnldNfc_Read(&Data, wRdAddr,
1355                                (pphDnldNfc_RspCb_t)phDnldNfc_ReadComplete,
1356                                gpphDnldContext);
1357     } else {
1358       Data.pBuff = NULL;
1359       Data.wLen = 0;
1360       wStatus = NFCSTATUS_FAILED;
1361     }
1362 
1363     if (NFCSTATUS_PENDING == wStatus) {
1364       NXPLOG_FWDNLD_D("Read Request submitted successfully..");
1365     } else {
1366       NXPLOG_FWDNLD_E("Read Request submission failed!!");
1367     }
1368   }
1369 
1370   return wStatus;
1371 }
1372 
1373 /*******************************************************************************
1374 **
1375 ** Function         phDnldNfc_ReadComplete
1376 **
1377 ** Description      Read complete
1378 **
1379 ** Parameters       pContext - caller layer context
1380 **                  status   - status of the transaction
1381 **                  pInfo    - transaction info
1382 **
1383 ** Returns          None
1384 **
1385 *******************************************************************************/
phDnldNfc_ReadComplete(void * pContext,NFCSTATUS status,void * pInfo)1386 static void phDnldNfc_ReadComplete(void* pContext, NFCSTATUS status,
1387                                    void* pInfo) {
1388   NFCSTATUS wStatus = NFCSTATUS_SUCCESS;
1389   UNUSED_PROP(pContext);
1390 
1391   /* Call Tml Ioctl to enable/restore normal mode */
1392   wStatus = phTmlNfc_IoCtl(phTmlNfc_e_EnableNormalMode);
1393 
1394   if (NFCSTATUS_SUCCESS == wStatus) {
1395     NXPLOG_FWDNLD_D("Read Done!!");
1396   }
1397 
1398   UserCb(&UserCtxt, status, pInfo);
1399 
1400   return;
1401 }
1402 
1403 /*******************************************************************************
1404 **
1405 ** Function         phDnldNfc_Read
1406 **
1407 ** Description      Retrieves requested data of specified length from desired
1408 **                  EEPROM address
1409 **
1410 ** Parameters       pData - response buffer which gets updated with data from
1411 **                          EEPROM
1412 **                  dwRdAddr - EEPROM address for data read
1413 **                  pNotify - notify caller after getting response
1414 **                  pContext - caller context
1415 **
1416 ** Returns          NFC status:
1417 **                  NFCSTATUS_SUCCESS - Read request to NFCC is successful
1418 **                  NFCSTATUS_FAILED - Read request failed due to internal error
1419 **                  NFCSTATUS_NOT_ALLOWED - command not allowed
1420 **                  Other command specific errors
1421 **
1422 *******************************************************************************/
phDnldNfc_Read(pphDnldNfc_Buff_t pData,uint32_t dwRdAddr,pphDnldNfc_RspCb_t pNotify,void * pContext)1423 NFCSTATUS phDnldNfc_Read(pphDnldNfc_Buff_t pData, uint32_t dwRdAddr,
1424                          pphDnldNfc_RspCb_t pNotify, void* pContext) {
1425   NFCSTATUS wStatus = NFCSTATUS_SUCCESS;
1426 
1427   if ((NULL == pNotify) || (NULL == pData) || (NULL == pContext)) {
1428     NXPLOG_FWDNLD_E("Invalid Input Parameters!!");
1429     wStatus = PHNFCSTVAL(CID_NFC_DNLD, NFCSTATUS_INVALID_PARAMETER);
1430   } else {
1431     if (phDnldNfc_TransitionIdle != gpphDnldContext->tDnldInProgress) {
1432       NXPLOG_FWDNLD_E("Dnld Cmd Request in Progress..Cannot Continue!!");
1433       wStatus = PHNFCSTVAL(CID_NFC_DNLD, NFCSTATUS_BUSY);
1434     } else {
1435       if ((NULL != pData->pBuff) && (0 != pData->wLen)) {
1436         (gpphDnldContext->tCmdId) = PH_DL_CMD_READ;
1437         (gpphDnldContext->FrameInp.Type) = phDnldNfc_FTRead;
1438         (gpphDnldContext->FrameInp.dwAddr) = dwRdAddr;
1439         (gpphDnldContext->tRspBuffInfo.pBuff) = pData->pBuff;
1440         (gpphDnldContext->tRspBuffInfo.wLen) = pData->wLen;
1441         (gpphDnldContext->tUserData.pBuff) = NULL;
1442         (gpphDnldContext->tUserData.wLen) = 0;
1443         (gpphDnldContext->UserCb) = pNotify;
1444         (gpphDnldContext->UserCtxt) = pContext;
1445 
1446         memset(&(gpphDnldContext->tRWInfo), 0,
1447                sizeof(gpphDnldContext->tRWInfo));
1448 
1449         wStatus = phDnldNfc_CmdHandler(gpphDnldContext, phDnldNfc_EventRead);
1450 
1451         if (NFCSTATUS_PENDING == wStatus) {
1452           NXPLOG_FWDNLD_D("Read Request submitted successfully");
1453         } else {
1454           NXPLOG_FWDNLD_E("Read Request Failed!!");
1455         }
1456       } else {
1457         NXPLOG_FWDNLD_E("Invalid Buff Parameters!!");
1458         wStatus = PHNFCSTVAL(CID_NFC_DNLD, NFCSTATUS_INVALID_PARAMETER);
1459       }
1460     }
1461   }
1462 
1463   return wStatus;
1464 }
1465 #endif
1466