1 /****************************************************************************** 2 * 3 * Copyright (C) 2012 Broadcom Corporation 4 * 5 * Licensed under the Apache License, Version 2.0 (the "License"); 6 * you may not use this file except in compliance with the License. 7 * You may obtain a copy of the License at: 8 * 9 * http://www.apache.org/licenses/LICENSE-2.0 10 * 11 * Unless required by applicable law or agreed to in writing, software 12 * distributed under the License is distributed on an "AS IS" BASIS, 13 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 14 * See the License for the specific language governing permissions and 15 * limitations under the License. 16 * 17 ******************************************************************************/ 18 19 /****************************************************************************** 20 * 21 * HAL Adaptation Interface (HAI). This interface regulates the interaction 22 * between standard Android HAL and Broadcom-specific HAL. It adapts 23 * Broadcom-specific features to the Android framework. 24 * 25 ******************************************************************************/ 26 #define LOG_TAG "NfcNciHal" 27 #include "HalAdaptation.h" 28 #include <cutils/properties.h> 29 #include <errno.h> 30 #include <pthread.h> 31 #include "SyncEvent.h" 32 #include "_OverrideLog.h" 33 #include "android_logmsg.h" 34 #include "buildcfg.h" 35 #include "config.h" 36 #include "nfc_hal_int.h" 37 #include "nfc_hal_post_reset.h" 38 extern void delete_hal_non_volatile_store(bool forceDelete); 39 extern void verify_hal_non_volatile_store(); 40 extern void resetConfig(); 41 extern "C" { 42 #include "userial.h" 43 } 44 45 extern void configureCrystalFrequency(); 46 47 /////////////////////////////////////// 48 // private declaration, definition 49 50 static nfc_stack_callback_t* gAndroidHalCallback = NULL; 51 static nfc_stack_data_callback_t* gAndroidHalDataCallback = NULL; 52 static SyncEvent gOpenCompletedEvent; 53 static SyncEvent gPostInitCompletedEvent; 54 static SyncEvent gCloseCompletedEvent; 55 56 uint32_t ScrProtocolTraceFlag = SCR_PROTO_TRACE_ALL; // 0x017F00; 57 58 static void BroadcomHalCallback(uint8_t event, tHAL_NFC_STATUS status); 59 static void BroadcomHalDataCallback(uint16_t data_len, uint8_t* p_data); 60 61 static bool isColdBoot = true; 62 63 extern tNFC_HAL_CFG* p_nfc_hal_cfg; 64 extern const uint8_t nfca_version_string[]; 65 extern const uint8_t nfa_version_string[]; 66 67 tNFC_HAL_DM_PRE_SET_MEM nfc_hal_pre_set_mem_20795a1[] = { 68 {0x0016403c, 0x00000008}, 69 {0x0016403c, 0x00000000}, 70 {0x0014008c, 0x00000001}, 71 {0, 0}}; 72 73 extern tNFC_HAL_DM_PRE_SET_MEM* p_nfc_hal_dm_pre_set_mem; 74 75 /////////////////////////////////////// 76 77 int HaiInitializeLibrary(const bcm2079x_dev_t* device) { 78 ALOGD("%s: enter", __func__); 79 ALOGE("%s: ver=%s nfa=%s", __func__, nfca_version_string, nfa_version_string); 80 int retval = EACCES; 81 unsigned long freq = 0; 82 unsigned long num = 0; 83 char temp[120]; 84 int8_t prop_value; 85 uint8_t logLevel = 0; 86 87 logLevel = InitializeGlobalAppLogLevel(); 88 89 if (GetNumValue(NAME_GLOBAL_RESET, &num, sizeof(num))) { 90 if (num == 1) { 91 // Send commands to disable boc 92 p_nfc_hal_dm_pre_set_mem = nfc_hal_pre_set_mem_20795a1; 93 } 94 } 95 96 configureCrystalFrequency(); 97 verify_hal_non_volatile_store(); 98 if (GetNumValue(NAME_PRESERVE_STORAGE, (char*)&num, sizeof(num)) && 99 (num == 1)) 100 ALOGD("%s: preserve HAL NV store", __func__); 101 else { 102 delete_hal_non_volatile_store(false); 103 } 104 105 if (GetNumValue(NAME_USE_RAW_NCI_TRACE, &num, sizeof(num))) { 106 if (num == 1) { 107 // display protocol traces in raw format 108 ProtoDispAdapterUseRawOutput(TRUE); 109 } 110 } 111 112 // Initialize protocol logging level 113 InitializeProtocolLogLevel(); 114 115 tUSERIAL_OPEN_CFG cfg; 116 struct tUART_CONFIG uart; 117 118 if (GetStrValue(NAME_UART_PARITY, temp, sizeof(temp))) { 119 if (strcmp(temp, "even") == 0) 120 uart.m_iParity = USERIAL_PARITY_EVEN; 121 else if (strcmp(temp, "odd") == 0) 122 uart.m_iParity = USERIAL_PARITY_ODD; 123 else if (strcmp(temp, "none") == 0) 124 uart.m_iParity = USERIAL_PARITY_NONE; 125 } else 126 uart.m_iParity = USERIAL_PARITY_NONE; 127 128 if (GetStrValue(NAME_UART_STOPBITS, temp, sizeof(temp))) { 129 if (strcmp(temp, "1") == 0) 130 uart.m_iStopbits = USERIAL_STOPBITS_1; 131 else if (strcmp(temp, "2") == 0) 132 uart.m_iStopbits = USERIAL_STOPBITS_2; 133 else if (strcmp(temp, "1.5") == 0) 134 uart.m_iStopbits = USERIAL_STOPBITS_1_5; 135 } else if (GetNumValue(NAME_UART_STOPBITS, &num, sizeof(num))) { 136 if (num == 1) 137 uart.m_iStopbits = USERIAL_STOPBITS_1; 138 else if (num == 2) 139 uart.m_iStopbits = USERIAL_STOPBITS_2; 140 } else 141 uart.m_iStopbits = USERIAL_STOPBITS_1; 142 143 if (GetNumValue(NAME_UART_DATABITS, &num, sizeof(num))) { 144 if (5 <= num && num <= 8) uart.m_iDatabits = (1 << (num + 1)); 145 } else 146 uart.m_iDatabits = USERIAL_DATABITS_8; 147 148 if (GetNumValue(NAME_UART_BAUD, &num, sizeof(num))) { 149 if (num == 300) 150 uart.m_iBaudrate = USERIAL_BAUD_300; 151 else if (num == 600) 152 uart.m_iBaudrate = USERIAL_BAUD_600; 153 else if (num == 1200) 154 uart.m_iBaudrate = USERIAL_BAUD_1200; 155 else if (num == 2400) 156 uart.m_iBaudrate = USERIAL_BAUD_2400; 157 else if (num == 9600) 158 uart.m_iBaudrate = USERIAL_BAUD_9600; 159 else if (num == 19200) 160 uart.m_iBaudrate = USERIAL_BAUD_19200; 161 else if (num == 57600) 162 uart.m_iBaudrate = USERIAL_BAUD_57600; 163 else if (num == 115200) 164 uart.m_iBaudrate = USERIAL_BAUD_115200; 165 else if (num == 230400) 166 uart.m_iBaudrate = USERIAL_BAUD_230400; 167 else if (num == 460800) 168 uart.m_iBaudrate = USERIAL_BAUD_460800; 169 else if (num == 921600) 170 uart.m_iBaudrate = USERIAL_BAUD_921600; 171 } else if (GetStrValue(NAME_UART_BAUD, temp, sizeof(temp))) { 172 if (strcmp(temp, "auto") == 0) uart.m_iBaudrate = USERIAL_BAUD_AUTO; 173 } else 174 uart.m_iBaudrate = USERIAL_BAUD_115200; 175 176 memset(&cfg, 0, sizeof(tUSERIAL_OPEN_CFG)); 177 cfg.fmt = uart.m_iDatabits | uart.m_iParity | uart.m_iStopbits; 178 cfg.baud = uart.m_iBaudrate; 179 180 ALOGD("%s: uart config=0x%04x, %d\n", __func__, cfg.fmt, cfg.baud); 181 USERIAL_Init(&cfg); 182 183 if (GetNumValue(NAME_NFCC_ENABLE_TIMEOUT, &num, sizeof(num))) { 184 p_nfc_hal_cfg->nfc_hal_nfcc_enable_timeout = num; 185 } 186 187 if (GetNumValue(NAME_NFA_MAX_EE_SUPPORTED, &num, sizeof(num)) && num == 0) { 188 // Since NFA_MAX_EE_SUPPORTED is explicetly set to 0, no UICC support is 189 // needed. 190 p_nfc_hal_cfg->nfc_hal_hci_uicc_support = 0; 191 } 192 193 prop_value = property_get_bool("nfc.bcm2079x.isColdboot", 0); 194 if (prop_value) { 195 isColdBoot = true; 196 property_set("nfc.bcm2079x.isColdboot", "0"); 197 } 198 // Set 'first boot' flag based on static variable that will get set to false 199 // after the stack has first initialized the EE. 200 p_nfc_hal_cfg->nfc_hal_first_boot = isColdBoot ? TRUE : FALSE; 201 202 HAL_NfcInitialize(); 203 HAL_NfcSetTraceLevel(logLevel); // Initialize HAL's logging level 204 205 retval = 0; 206 ALOGD("%s: exit %d", __func__, retval); 207 return retval; 208 } 209 210 int HaiTerminateLibrary() { 211 int retval = EACCES; 212 ALOGD("%s: enter", __func__); 213 214 HAL_NfcTerminate(); 215 gAndroidHalCallback = NULL; 216 gAndroidHalDataCallback = NULL; 217 GKI_shutdown(); 218 resetConfig(); 219 retval = 0; 220 ALOGD("%s: exit %d", __func__, retval); 221 return retval; 222 } 223 224 int HaiOpen(const bcm2079x_dev_t* device, nfc_stack_callback_t* halCallbackFunc, 225 nfc_stack_data_callback_t* halDataCallbackFunc) { 226 ALOGD("%s: enter", __func__); 227 int retval = EACCES; 228 229 gAndroidHalCallback = halCallbackFunc; 230 gAndroidHalDataCallback = halDataCallbackFunc; 231 232 SyncEventGuard guard(gOpenCompletedEvent); 233 HAL_NfcOpen(BroadcomHalCallback, BroadcomHalDataCallback); 234 gOpenCompletedEvent.wait(); 235 236 retval = 0; 237 ALOGD("%s: exit %d", __func__, retval); 238 return retval; 239 } 240 241 void BroadcomHalCallback(uint8_t event, tHAL_NFC_STATUS status) { 242 ALOGD("%s: enter; event=0x%X", __func__, event); 243 switch (event) { 244 case HAL_NFC_OPEN_CPLT_EVT: { 245 ALOGD("%s: HAL_NFC_OPEN_CPLT_EVT; status=0x%X", __func__, status); 246 SyncEventGuard guard(gOpenCompletedEvent); 247 gOpenCompletedEvent.notifyOne(); 248 break; 249 } 250 251 case HAL_NFC_POST_INIT_CPLT_EVT: { 252 ALOGD("%s: HAL_NFC_POST_INIT_CPLT_EVT", __func__); 253 SyncEventGuard guard(gPostInitCompletedEvent); 254 gPostInitCompletedEvent.notifyOne(); 255 break; 256 } 257 258 case HAL_NFC_CLOSE_CPLT_EVT: { 259 ALOGD("%s: HAL_NFC_CLOSE_CPLT_EVT", __func__); 260 SyncEventGuard guard(gCloseCompletedEvent); 261 gCloseCompletedEvent.notifyOne(); 262 break; 263 } 264 265 case HAL_NFC_ERROR_EVT: { 266 ALOGD("%s: HAL_NFC_ERROR_EVT", __func__); 267 { 268 SyncEventGuard guard(gOpenCompletedEvent); 269 gOpenCompletedEvent.notifyOne(); 270 } 271 { 272 SyncEventGuard guard(gPostInitCompletedEvent); 273 gPostInitCompletedEvent.notifyOne(); 274 } 275 { 276 SyncEventGuard guard(gCloseCompletedEvent); 277 gCloseCompletedEvent.notifyOne(); 278 } 279 break; 280 } 281 } 282 gAndroidHalCallback(event, status); 283 ALOGD("%s: exit; event=0x%X", __func__, event); 284 } 285 286 void BroadcomHalDataCallback(uint16_t data_len, uint8_t* p_data) { 287 ALOGD("%s: enter; len=%u", __func__, data_len); 288 gAndroidHalDataCallback(data_len, p_data); 289 } 290 291 int HaiClose(const bcm2079x_dev_t* device) { 292 ALOGD("%s: enter", __func__); 293 int retval = EACCES; 294 295 SyncEventGuard guard(gCloseCompletedEvent); 296 HAL_NfcClose(); 297 gCloseCompletedEvent.wait(); 298 retval = 0; 299 ALOGD("%s: exit %d", __func__, retval); 300 return retval; 301 } 302 303 int HaiCoreInitialized(const bcm2079x_dev_t* device, 304 uint8_t* coreInitResponseParams) { 305 ALOGD("%s: enter", __func__); 306 int retval = EACCES; 307 308 SyncEventGuard guard(gPostInitCompletedEvent); 309 HAL_NfcCoreInitialized(0, coreInitResponseParams); 310 gPostInitCompletedEvent.wait(); 311 retval = 0; 312 ALOGD("%s: exit %d", __func__, retval); 313 return retval; 314 } 315 316 int HaiWrite(const bcm2079x_dev_t* dev, uint16_t dataLen, const uint8_t* data) { 317 ALOGD("%s: enter; len=%u", __func__, dataLen); 318 int retval = EACCES; 319 320 HAL_NfcWrite(dataLen, const_cast<uint8_t*>(data)); 321 retval = 0; 322 ALOGD("%s: exit %d", __func__, retval); 323 return retval; 324 } 325 326 int HaiPreDiscover(const bcm2079x_dev_t* device) { 327 ALOGD("%s: enter", __func__); 328 int retval = EACCES; 329 330 // This function is a clear indication that the stack is initializing 331 // EE. So we can reset the cold-boot flag here. 332 isColdBoot = false; 333 retval = HAL_NfcPreDiscover() ? 1 : 0; 334 ALOGD("%s: exit %d", __func__, retval); 335 return retval; 336 } 337 338 int HaiControlGranted(const bcm2079x_dev_t* device) { 339 ALOGD("%s: enter", __func__); 340 int retval = EACCES; 341 342 HAL_NfcControlGranted(); 343 retval = 0; 344 ALOGD("%s: exit %d", __func__, retval); 345 return retval; 346 } 347 348 int HaiPowerCycle(const bcm2079x_dev_t* device) { 349 ALOGD("%s: enter", __func__); 350 int retval = EACCES; 351 352 HAL_NfcPowerCycle(); 353 retval = 0; 354 ALOGD("%s: exit %d", __func__, retval); 355 return retval; 356 } 357 358 int HaiGetMaxNfcee(const bcm2079x_dev_t* device, uint8_t* maxNfcee) { 359 ALOGD("%s: enter", __func__); 360 int retval = EACCES; 361 362 // This function is a clear indication that the stack is initializing 363 // EE. So we can reset the cold-boot flag here. 364 isColdBoot = false; 365 366 if (maxNfcee) { 367 *maxNfcee = HAL_NfcGetMaxNfcee(); 368 ALOGD("%s: max_ee from HAL to use %d", __func__, *maxNfcee); 369 retval = 0; 370 } 371 ALOGD("%s: exit %d", __func__, retval); 372 return retval; 373 } 374