1 /******************************************************************************
2  *
3  *  Copyright 2022-2024 NXP
4  *
5  *  Licensed under the Apache License, Version 2.0 (the "License");
6  *  you may not use this file except in compliance with the License.
7  *  You may obtain a copy of the License at
8  *
9  *  http://www.apache.org/licenses/LICENSE-2.0
10  *
11  *  Unless required by applicable law or agreed to in writing, software
12  *  distributed under the License is distributed on an "AS IS" BASIS,
13  *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14  *  See the License for the specific language governing permissions and
15  *  limitations under the License.
16  *
17  ******************************************************************************/
18 
19 #include <stdint.h>
20 
21 #include <string>
22 
23 #include "phNxpConfig.h"
24 #ifndef NXP_FEATURES_H
25 #define NXP_FEATURES_H
26 
27 #define STRMAX_2 100
28 
29 /*FW ROM CODE VERSION*/
30 #define FW_MOBILE_ROM_VERSION_PN551 0x10
31 #define FW_MOBILE_ROM_VERSION_PN553 0x11
32 #define FW_MOBILE_ROM_VERSION_PN557 0x12
33 #define FW_MOBILE_ROM_VERSION_SN100U 0x01
34 #define FW_MOBILE_ROM_VERSION_SN220U 0x01
35 #define FW_MOBILE_ROM_VERSION_SN300U 0x02
36 
37 /*FW Major VERSION Code*/
38 #define FW_MOBILE_MAJOR_NUMBER_PN553 0x01
39 #define FW_MOBILE_MAJOR_NUMBER_PN551 0x05
40 #define FW_MOBILE_MAJOR_NUMBER_PN48AD 0x01
41 #define FW_MOBILE_MAJOR_NUMBER_PN81A 0x02
42 #define FW_MOBILE_MAJOR_NUMBER_PN557 0x01
43 #define FW_MOBILE_MAJOR_NUMBER_PN557_V2 0x21
44 #define FW_MOBILE_MAJOR_NUMBER_SN100U 0x010
45 #define FW_MOBILE_MAJOR_NUMBER_SN220U 0x01
46 #define FW_MOBILE_MAJOR_NUMBER_SN300U 0x20
47 
48 #define NCI_CMD_RSP_SUCCESS_SW1 0x60
49 #define NCI_CMD_RSP_SUCCESS_SW2 0x00
50 #define FW_DL_RSP_FIRST_BYTE 0x00
51 
52 /* Supported EE */
53 #define EE_T4T_SUPPORTED 1
54 #define EE_UICC1_SUPPORTED 1
55 #define EE_UICC2_SUPPORTED 1
56 #define EE_UICC3_SUPPORTED 1
57 #define EE_ESE_SUPPORTED 1
58 #define EE_EUICC1_SUPPORTED 1
59 #define EE_EUICC2_SUPPORTED 1
60 
61 #define JCOP_VER_3_3 3
62 #define JCOP_VER_4_0 4
63 #ifndef FW_LIB_ROOT_DIR
64 #if (defined(__arm64__) || defined(__aarch64__) || defined(_M_ARM64))
65 #define FW_LIB_ROOT_DIR "/vendor/lib64/"
66 #else
67 #define FW_LIB_ROOT_DIR "/vendor/lib/"
68 #endif
69 #endif
70 #ifndef FW_BIN_ROOT_DIR
71 #define FW_BIN_ROOT_DIR "/vendor/firmware/"
72 #endif
73 #ifndef FW_LIB_EXTENSION
74 #define FW_LIB_EXTENSION ".so"
75 #endif
76 #ifndef FW_BIN_EXTENSION
77 #define FW_BIN_EXTENSION ".bin"
78 #endif
79 using namespace std;
80 typedef enum {
81   NFCC_DWNLD_WITH_VEN_RESET,
82   NFCC_DWNLD_WITH_NCI_CMD
83 } tNFCC_DnldType;
84 
85 typedef enum {
86   HW_PN553_A0 = 0x40,
87   HW_PN553_B0 = 0x41,
88   HW_PN80T_A0 = 0x50,
89   HW_PN80T_B0 = 0x51,  // PN553 B0 + P73
90   HW_PN551 = 0x98,
91   HW_PN67T_A0 = 0xA8,
92   HW_PN67T_B0 = 0x08,
93   HW_PN548C2_A0 = 0x28,
94   HW_PN548C2_B0 = 0x48,
95   HW_PN66T_A0 = 0x18,
96   HW_PN66T_B0 = 0x58,
97   HW_SN100U_A0 = 0xA0,
98   HW_SN100U_A2 = 0xA2,
99   HW_PN560_V1 = 0xCA,
100   HW_PN560_V2 = 0xCB,
101   HW_SN300U = 0xD3
102 } tNFC_HWVersion;
103 
104 typedef enum {
105   DEFAULT_CHIP_TYPE = 0x00,
106   pn547C2 = 0x01,
107   pn65T,
108   pn548C2,
109   pn66T,
110   pn551,
111   pn67T,
112   pn553,
113   pn80T,
114   pn557,
115   pn81T,
116   sn100u,
117   sn220u,
118   pn560,
119   sn300u
120 } tNFC_chipType;
121 
122 typedef struct {
123   /*Flags common to all chip types*/
124   uint8_t _NFCC_I2C_READ_WRITE_IMPROVEMENT : 1;
125   uint8_t _NFCC_MIFARE_TIANJIN : 1;
126   uint8_t _NFCC_SPI_FW_DOWNLOAD_SYNC : 1;
127   uint8_t _NFCEE_REMOVED_NTF_RECOVERY : 1;
128   uint8_t _NFCC_FORCE_FW_DOWNLOAD : 1;
129   uint8_t _NFCC_DWNLD_MODE : 1;
130   uint8_t _NFCC_4K_FW_SUPPORT : 1;
131 } tNfc_nfccFeatureList;
132 
133 typedef struct {
134   uint8_t id;
135   uint8_t len;
136   uint8_t val;
137 } tNfc_capability;
138 
139 typedef struct {
140   tNfc_capability OBSERVE_MODE;
141   tNfc_capability POLLING_FRAME_NOTIFICATION;
142   tNfc_capability POWER_SAVING;
143   tNfc_capability AUTOTRANSACT_PLF;
144 } tNfc_nfccCapabililty;
145 
146 typedef struct {
147   uint8_t nfcNxpEse : 1;
148   tNFC_chipType chipType;
149   std::string _FW_LIB_PATH;
150   std::string _FW_BIN_PATH;
151   uint16_t _PHDNLDNFC_USERDATA_EEPROM_OFFSET;
152   uint16_t _PHDNLDNFC_USERDATA_EEPROM_LEN;
153   uint8_t _FW_MOBILE_MAJOR_NUMBER;
154   tNfc_nfccFeatureList nfccFL;
155   tNfc_nfccCapabililty nfccCap;
156 } tNfc_featureList;
157 
158 extern tNfc_featureList nfcFL;
159 #define GET_FW_ROM_VERSION_NCI_RESP(msg, msg_len) (msg[msg_len - 3])
160 #define GET_FW_MAJOR_VERSION_NCI_RESP(msg, msg_len) (msg[msg_len - 2])
161 #define GET_HW_VERSION_NCI_RESP(msg, msg_len) (msg[msg_len - 4])
162 #define IS_CHIP_TYPE_GE(cType) (nfcFL.chipType >= cType)
163 #define IS_CHIP_TYPE_EQ(cType) (nfcFL.chipType == cType)
164 #define IS_CHIP_TYPE_LE(cType) (nfcFL.chipType <= cType)
165 #define IS_CHIP_TYPE_L(cType) (nfcFL.chipType < cType)
166 #define IS_CHIP_TYPE_NE(cType) (nfcFL.chipType != cType)
167 #define IS_4K_SUPPORT (nfcFL.nfccFL._NFCC_4K_FW_SUPPORT == true)
168 
169 #define CONFIGURE_4K_SUPPORT(value) \
170   { nfcFL.nfccFL._NFCC_4K_FW_SUPPORT = value; }
171 
172 #define CONFIGURE_FEATURELIST(chipType)               \
173   {                                                   \
174     nfcFL.chipType = chipType;                        \
175     switch (chipType) {                               \
176       case pn81T:                                     \
177         nfcFL.chipType = pn557;                       \
178         nfcFL.nfcNxpEse = true;                       \
179         CONFIGURE_FEATURELIST_NFCC_WITH_ESE(chipType) \
180         break;                                        \
181       case pn80T:                                     \
182         nfcFL.chipType = pn553;                       \
183         nfcFL.nfcNxpEse = true;                       \
184         CONFIGURE_FEATURELIST_NFCC_WITH_ESE(chipType) \
185         break;                                        \
186       case pn67T:                                     \
187         nfcFL.chipType = pn551;                       \
188         nfcFL.nfcNxpEse = true;                       \
189         CONFIGURE_FEATURELIST_NFCC_WITH_ESE(chipType) \
190         break;                                        \
191       case pn66T:                                     \
192         nfcFL.chipType = pn548C2;                     \
193         nfcFL.nfcNxpEse = true;                       \
194         CONFIGURE_FEATURELIST_NFCC_WITH_ESE(chipType) \
195         break;                                        \
196       case pn65T:                                     \
197         nfcFL.chipType = pn547C2;                     \
198         nfcFL.nfcNxpEse = true;                       \
199         CONFIGURE_FEATURELIST_NFCC_WITH_ESE(chipType) \
200         break;                                        \
201       case sn100u:                                    \
202         nfcFL.chipType = sn100u;                      \
203         nfcFL.nfcNxpEse = true;                       \
204         CONFIGURE_FEATURELIST_NFCC_WITH_ESE(chipType) \
205         break;                                        \
206       case sn220u:                                    \
207         nfcFL.chipType = sn220u;                      \
208         nfcFL.nfcNxpEse = true;                       \
209         CONFIGURE_FEATURELIST_NFCC_WITH_ESE(chipType) \
210         break;                                        \
211       case sn300u:                                    \
212         nfcFL.chipType = sn300u;                      \
213         nfcFL.nfcNxpEse = true;                       \
214         CONFIGURE_FEATURELIST_NFCC_WITH_ESE(chipType) \
215         break;                                        \
216       default:                                        \
217         nfcFL.nfcNxpEse = false;                      \
218         CONFIGURE_FEATURELIST_NFCC(chipType)          \
219     }                                                 \
220   }
221 
222 #define CONFIGURE_FEATURELIST_NFCC_WITH_ESE(chipType)   \
223   {                                                     \
224     switch (chipType) {                                 \
225       case pn81T:                                       \
226         CONFIGURE_FEATURELIST_NFCC(pn557)               \
227         nfcFL.nfccFL._NFCC_SPI_FW_DOWNLOAD_SYNC = true; \
228         break;                                          \
229       case sn100u:                                      \
230         CONFIGURE_FEATURELIST_NFCC(sn100u)              \
231         nfcFL.nfccFL._NFCC_SPI_FW_DOWNLOAD_SYNC = true; \
232         break;                                          \
233       case sn220u:                                      \
234         CONFIGURE_FEATURELIST_NFCC(sn220u)              \
235         nfcFL.nfccFL._NFCC_SPI_FW_DOWNLOAD_SYNC = true; \
236         break;                                          \
237       case sn300u:                                      \
238         CONFIGURE_FEATURELIST_NFCC(sn300u)              \
239         nfcFL.nfccFL._NFCC_SPI_FW_DOWNLOAD_SYNC = true; \
240         break;                                          \
241       default:                                          \
242         break;                                          \
243     }                                                   \
244   }
245 
246 #define CONFIGURE_FEATURELIST_NFCC(chipType)                           \
247   {                                                                    \
248     nfcFL._PHDNLDNFC_USERDATA_EEPROM_OFFSET = 0x023CU;                 \
249     nfcFL._PHDNLDNFC_USERDATA_EEPROM_LEN = 0x0C80U;                    \
250     nfcFL._FW_MOBILE_MAJOR_NUMBER = FW_MOBILE_MAJOR_NUMBER_PN48AD;     \
251     nfcFL.nfccFL._NFCC_DWNLD_MODE = NFCC_DWNLD_WITH_VEN_RESET;         \
252     nfcFL.nfccFL._NFCC_4K_FW_SUPPORT = false;                          \
253     UPDATE_NFCC_CAPABILITY()                                           \
254     switch (chipType) {                                                \
255       case pn557:                                                      \
256         nfcFL.nfccFL._NFCC_I2C_READ_WRITE_IMPROVEMENT = true;          \
257         STRCPY_FW("libpn557_fw")                                       \
258         STRCPY_FW_BIN("pn557")                                         \
259         break;                                                         \
260       case sn100u:                                                     \
261         nfcFL.nfccFL._NFCC_DWNLD_MODE = NFCC_DWNLD_WITH_NCI_CMD;       \
262         nfcFL.nfccFL._NFCC_I2C_READ_WRITE_IMPROVEMENT = true;          \
263         nfcFL.nfccFL._NFCC_MIFARE_TIANJIN = false;                     \
264         nfcFL.nfccFL._NFCC_FORCE_FW_DOWNLOAD = true;                   \
265         nfcFL._FW_MOBILE_MAJOR_NUMBER = FW_MOBILE_MAJOR_NUMBER_SN100U; \
266         STRCPY_FW("libsn100u_fw")                                      \
267         STRCPY_FW_BIN("sn100u")                                        \
268         break;                                                         \
269       case sn220u:                                                     \
270         nfcFL.nfccFL._NFCC_DWNLD_MODE = NFCC_DWNLD_WITH_NCI_CMD;       \
271         nfcFL.nfccFL._NFCC_I2C_READ_WRITE_IMPROVEMENT = true;          \
272         nfcFL.nfccFL._NFCC_MIFARE_TIANJIN = false;                     \
273         nfcFL.nfccFL._NFCC_FORCE_FW_DOWNLOAD = true;                   \
274         nfcFL._FW_MOBILE_MAJOR_NUMBER = FW_MOBILE_MAJOR_NUMBER_SN220U; \
275         STRCPY_FW("libsn220u_fw")                                      \
276         STRCPY_FW_BIN("sn220u")                                        \
277         break;                                                         \
278       case pn560:                                                      \
279         nfcFL.nfccFL._NFCC_DWNLD_MODE = NFCC_DWNLD_WITH_NCI_CMD;       \
280         nfcFL.nfccFL._NFCC_I2C_READ_WRITE_IMPROVEMENT = true;          \
281         nfcFL.nfccFL._NFCC_MIFARE_TIANJIN = false;                     \
282         nfcFL.nfccFL._NFCC_FORCE_FW_DOWNLOAD = true;                   \
283         nfcFL._FW_MOBILE_MAJOR_NUMBER = FW_MOBILE_MAJOR_NUMBER_SN220U; \
284         STRCPY_FW("libpn560_fw")                                       \
285         STRCPY_FW_BIN("pn560")                                         \
286         break;                                                         \
287       case sn300u:                                                     \
288         nfcFL.nfccFL._NFCC_DWNLD_MODE = NFCC_DWNLD_WITH_NCI_CMD;       \
289         nfcFL.nfccFL._NFCC_I2C_READ_WRITE_IMPROVEMENT = true;          \
290         nfcFL.nfccFL._NFCC_MIFARE_TIANJIN = false;                     \
291         nfcFL.nfccFL._NFCC_FORCE_FW_DOWNLOAD = true;                   \
292         nfcFL._FW_MOBILE_MAJOR_NUMBER = FW_MOBILE_MAJOR_NUMBER_SN300U; \
293         STRCPY_FW("libsn300u_fw")                                      \
294         STRCPY_FW_BIN("sn300u")                                        \
295         break;                                                         \
296       default:                                                         \
297         nfcFL.nfccFL._NFCC_FORCE_FW_DOWNLOAD = true;                   \
298         break;                                                         \
299     }                                                                  \
300   }
301 
302 #define STRCPY_FW_BIN(str)                       \
303   {                                              \
304     nfcFL._FW_BIN_PATH.clear();                  \
305     nfcFL._FW_BIN_PATH.append(FW_BIN_ROOT_DIR);  \
306     nfcFL._FW_BIN_PATH.append(str);              \
307     nfcFL._FW_BIN_PATH.append(FW_BIN_EXTENSION); \
308   }
309 #define STRCPY_FW(str1)                          \
310   {                                              \
311     nfcFL._FW_LIB_PATH.clear();                  \
312     nfcFL._FW_LIB_PATH.append(FW_LIB_ROOT_DIR);  \
313     nfcFL._FW_LIB_PATH.append(str1);             \
314     nfcFL._FW_LIB_PATH.append(FW_LIB_EXTENSION); \
315   }
316 
317 #define CAP_OBSERVE_MODE_ID 0x00
318 #define CAP_POLL_FRAME_NTF_ID 0x01
319 #define CAP_POWER_SAVING_MODE_ID 0x02
320 #define CAP_AUTOTRANSACT_PLF_ID 0x03
321 
322 #define UPDATE_NFCC_CAPABILITY()                                             \
323   {                                                                          \
324     nfcFL.nfccCap.OBSERVE_MODE.id = CAP_OBSERVE_MODE_ID;                     \
325     nfcFL.nfccCap.OBSERVE_MODE.len = 0x01;                                   \
326     nfcFL.nfccCap.OBSERVE_MODE.val = 0x00;                                   \
327     nfcFL.nfccCap.POLLING_FRAME_NOTIFICATION.id = CAP_POLL_FRAME_NTF_ID;     \
328     nfcFL.nfccCap.POLLING_FRAME_NOTIFICATION.len = 0x01;                     \
329     nfcFL.nfccCap.POLLING_FRAME_NOTIFICATION.val = 0x00;                     \
330     nfcFL.nfccCap.POWER_SAVING.id = CAP_POWER_SAVING_MODE_ID;                \
331     nfcFL.nfccCap.POWER_SAVING.len = 0x01;                                   \
332     nfcFL.nfccCap.POWER_SAVING.val = 0x00;                                   \
333     nfcFL.nfccCap.AUTOTRANSACT_PLF.id = CAP_AUTOTRANSACT_PLF_ID;             \
334     nfcFL.nfccCap.AUTOTRANSACT_PLF.len = 0x01;                               \
335     nfcFL.nfccCap.AUTOTRANSACT_PLF.val = 0x00;                               \
336     uint8_t extended_field_mode = 0x00;                                      \
337     if (IS_CHIP_TYPE_GE(sn100u) &&                                           \
338         GetNxpNumValue(NAME_NXP_EXTENDED_FIELD_DETECT_MODE,                  \
339                        &extended_field_mode, sizeof(extended_field_mode))) { \
340       if (extended_field_mode == 0x03) {                                     \
341         nfcFL.nfccCap.OBSERVE_MODE.val = 0x01;                               \
342       }                                                                      \
343     }                                                                        \
344     unsigned long num = 0;                                                   \
345     if ((GetNxpNumValue(NAME_NXP_DEFAULT_ULPDET_MODE, &num, sizeof(num)))) { \
346       if ((uint8_t)num > 0) {                                                \
347         nfcFL.nfccCap.POWER_SAVING.val = 0x01;                               \
348       }                                                                      \
349     }                                                                        \
350   }
351 #endif
352