1 /*
2 * Copyright (C) 2013 The Android Open Source Project
3 *
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
7 *
8 * http://www.apache.org/licenses/LICENSE-2.0
9 *
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
15 */
16
17 /*
18 * Manage the listen-mode routing table.
19 */
20
21 #include <android-base/stringprintf.h>
22 #include <base/logging.h>
23 #include <nativehelper/JNIHelp.h>
24 #include <nativehelper/ScopedLocalRef.h>
25
26 #include "JavaClassConstants.h"
27 #include "RoutingManager.h"
28 #include "nfa_ce_api.h"
29 #include "nfa_ee_api.h"
30 #include "nfc_config.h"
31
32 using android::base::StringPrintf;
33
34 extern bool gActivated;
35 extern SyncEvent gDeactivatedEvent;
36 extern bool nfc_debug_enabled;
37
38 const JNINativeMethod RoutingManager::sMethods[] = {
39 {"doGetDefaultRouteDestination", "()I",
40 (void*)RoutingManager::
41 com_android_nfc_cardemulation_doGetDefaultRouteDestination},
42 {"doGetDefaultOffHostRouteDestination", "()I",
43 (void*)RoutingManager::
44 com_android_nfc_cardemulation_doGetDefaultOffHostRouteDestination},
45 {"doGetOffHostUiccDestination", "()[B",
46 (void*)RoutingManager::
47 com_android_nfc_cardemulation_doGetOffHostUiccDestination},
48 {"doGetOffHostEseDestination", "()[B",
49 (void*)RoutingManager::
50 com_android_nfc_cardemulation_doGetOffHostEseDestination},
51 {"doGetAidMatchingMode", "()I",
52 (void*)RoutingManager::com_android_nfc_cardemulation_doGetAidMatchingMode},
53 {"doGetDefaultIsoDepRouteDestination", "()I",
54 (void*)RoutingManager::
55 com_android_nfc_cardemulation_doGetDefaultIsoDepRouteDestination}};
56
57 static const int MAX_NUM_EE = 5;
58 // SCBR from host works only when App is in foreground
59 static const uint8_t SYS_CODE_PWR_STATE_HOST = 0x01;
60 static const uint16_t DEFAULT_SYS_CODE = 0xFEFE;
61
62 static const uint8_t AID_ROUTE_QUAL_PREFIX = 0x10;
63
RoutingManager()64 RoutingManager::RoutingManager()
65 : mSecureNfcEnabled(false),
66 mNativeData(NULL),
67 mAidRoutingConfigured(false) {
68 static const char fn[] = "RoutingManager::RoutingManager()";
69
70 mDefaultOffHostRoute =
71 NfcConfig::getUnsigned(NAME_DEFAULT_OFFHOST_ROUTE, 0x00);
72
73 if (NfcConfig::hasKey(NAME_OFFHOST_ROUTE_UICC)) {
74 mOffHostRouteUicc = NfcConfig::getBytes(NAME_OFFHOST_ROUTE_UICC);
75 }
76
77 if (NfcConfig::hasKey(NAME_OFFHOST_ROUTE_ESE)) {
78 mOffHostRouteEse = NfcConfig::getBytes(NAME_OFFHOST_ROUTE_ESE);
79 }
80
81 mDefaultFelicaRoute = NfcConfig::getUnsigned(NAME_DEFAULT_NFCF_ROUTE, 0x00);
82 DLOG_IF(INFO, nfc_debug_enabled) << StringPrintf(
83 "%s: Active SE for Nfc-F is 0x%02X", fn, mDefaultFelicaRoute);
84
85 mDefaultEe = NfcConfig::getUnsigned(NAME_DEFAULT_ROUTE, 0x00);
86 DLOG_IF(INFO, nfc_debug_enabled)
87 << StringPrintf("%s: default route is 0x%02X", fn, mDefaultEe);
88
89 mAidMatchingMode =
90 NfcConfig::getUnsigned(NAME_AID_MATCHING_MODE, AID_MATCHING_EXACT_ONLY);
91
92 mDefaultSysCodeRoute =
93 NfcConfig::getUnsigned(NAME_DEFAULT_SYS_CODE_ROUTE, 0xC0);
94
95 mDefaultSysCodePowerstate =
96 NfcConfig::getUnsigned(NAME_DEFAULT_SYS_CODE_PWR_STATE, 0x19);
97
98 mDefaultSysCode = DEFAULT_SYS_CODE;
99 if (NfcConfig::hasKey(NAME_DEFAULT_SYS_CODE)) {
100 std::vector<uint8_t> pSysCode = NfcConfig::getBytes(NAME_DEFAULT_SYS_CODE);
101 if (pSysCode.size() == 0x02) {
102 mDefaultSysCode = ((pSysCode[0] << 8) | ((int)pSysCode[1] << 0));
103 DLOG_IF(INFO, nfc_debug_enabled) << StringPrintf(
104 "%s: DEFAULT_SYS_CODE: 0x%02X", __func__, mDefaultSysCode);
105 }
106 }
107
108 mOffHostAidRoutingPowerState =
109 NfcConfig::getUnsigned(NAME_OFFHOST_AID_ROUTE_PWR_STATE, 0x01);
110
111 mDefaultIsoDepRoute = NfcConfig::getUnsigned(NAME_DEFAULT_ISODEP_ROUTE, 0x0);
112
113 mHostListenTechMask =
114 NfcConfig::getUnsigned(NAME_HOST_LISTEN_TECH_MASK,
115 NFA_TECHNOLOGY_MASK_A | NFA_TECHNOLOGY_MASK_F);
116
117 memset(&mEeInfo, 0, sizeof(mEeInfo));
118 mReceivedEeInfo = false;
119 mSeTechMask = 0x00;
120 mIsScbrSupported = false;
121
122 mNfcFOnDhHandle = NFA_HANDLE_INVALID;
123
124 mDeinitializing = false;
125 mEeInfoChanged = false;
126 }
127
~RoutingManager()128 RoutingManager::~RoutingManager() {}
129
initialize(nfc_jni_native_data * native)130 bool RoutingManager::initialize(nfc_jni_native_data* native) {
131 static const char fn[] = "RoutingManager::initialize()";
132 mNativeData = native;
133 mRxDataBuffer.clear();
134
135 {
136 SyncEventGuard guard(mEeRegisterEvent);
137 DLOG_IF(INFO, nfc_debug_enabled) << fn << ": try ee register";
138 tNFA_STATUS nfaStat = NFA_EeRegister(nfaEeCallback);
139 if (nfaStat != NFA_STATUS_OK) {
140 LOG(ERROR) << StringPrintf("%s: fail ee register; error=0x%X", fn,
141 nfaStat);
142 return false;
143 }
144 mEeRegisterEvent.wait();
145 }
146
147 if ((mDefaultOffHostRoute != 0) || (mDefaultFelicaRoute != 0)) {
148 // Wait for EE info if needed
149 SyncEventGuard guard(mEeInfoEvent);
150 if (!mReceivedEeInfo) {
151 LOG(INFO) << fn << "Waiting for EE info";
152 mEeInfoEvent.wait();
153 }
154 }
155 mSeTechMask = updateEeTechRouteSetting();
156
157 // Set the host-routing Tech
158 tNFA_STATUS nfaStat = NFA_CeSetIsoDepListenTech(
159 mHostListenTechMask & (NFA_TECHNOLOGY_MASK_A | NFA_TECHNOLOGY_MASK_B));
160
161 if (nfaStat != NFA_STATUS_OK)
162 LOG(ERROR) << StringPrintf("Failed to configure CE IsoDep technologies");
163
164 // Register a wild-card for AIDs routed to the host
165 nfaStat = NFA_CeRegisterAidOnDH(NULL, 0, stackCallback);
166 if (nfaStat != NFA_STATUS_OK)
167 LOG(ERROR) << fn << "Failed to register wildcard AID for DH";
168
169 updateDefaultRoute();
170 updateDefaultProtocolRoute();
171
172 return true;
173 }
174
getInstance()175 RoutingManager& RoutingManager::getInstance() {
176 static RoutingManager manager;
177 return manager;
178 }
179
enableRoutingToHost()180 void RoutingManager::enableRoutingToHost() {
181 static const char fn[] = "RoutingManager::enableRoutingToHost()";
182 tNFA_STATUS nfaStat;
183 SyncEventGuard guard(mRoutingEvent);
184
185 // Default routing for T3T protocol
186 if (!mIsScbrSupported && mDefaultEe == NFC_DH_ID) {
187 nfaStat = NFA_EeSetDefaultProtoRouting(NFC_DH_ID, NFA_PROTOCOL_MASK_T3T, 0,
188 0, 0, 0, 0);
189 if (nfaStat == NFA_STATUS_OK)
190 mRoutingEvent.wait();
191 else
192 LOG(ERROR) << fn << "Fail to set default proto routing for T3T";
193 }
194
195 // Default routing for IsoDep protocol
196 tNFA_PROTOCOL_MASK protoMask = NFA_PROTOCOL_MASK_ISO_DEP;
197 if (mDefaultIsoDepRoute == NFC_DH_ID) {
198 nfaStat = NFA_EeSetDefaultProtoRouting(
199 NFC_DH_ID, protoMask, 0, 0, mSecureNfcEnabled ? 0 : protoMask, 0, 0);
200 if (nfaStat == NFA_STATUS_OK)
201 mRoutingEvent.wait();
202 else
203 LOG(ERROR) << fn << "Fail to set default proto routing for IsoDep";
204 }
205
206 // Route Nfc-A to host if we don't have a SE
207 tNFA_TECHNOLOGY_MASK techMask = NFA_TECHNOLOGY_MASK_A;
208 if ((mHostListenTechMask & NFA_TECHNOLOGY_MASK_A) &&
209 (mSeTechMask & NFA_TECHNOLOGY_MASK_A) == 0) {
210 nfaStat = NFA_EeSetDefaultTechRouting(
211 NFC_DH_ID, techMask, 0, 0, mSecureNfcEnabled ? 0 : techMask,
212 mSecureNfcEnabled ? 0 : techMask, mSecureNfcEnabled ? 0 : techMask);
213 if (nfaStat == NFA_STATUS_OK)
214 mRoutingEvent.wait();
215 else
216 LOG(ERROR) << fn << "Fail to set default tech routing for Nfc-A";
217 }
218
219 // Route Nfc-B to host if we don't have a SE
220 techMask = NFA_TECHNOLOGY_MASK_B;
221 if ((mHostListenTechMask & NFA_TECHNOLOGY_MASK_B) &&
222 (mSeTechMask & NFA_TECHNOLOGY_MASK_B) == 0) {
223 nfaStat = NFA_EeSetDefaultTechRouting(
224 NFC_DH_ID, techMask, 0, 0, mSecureNfcEnabled ? 0 : techMask,
225 mSecureNfcEnabled ? 0 : techMask, mSecureNfcEnabled ? 0 : techMask);
226 if (nfaStat == NFA_STATUS_OK)
227 mRoutingEvent.wait();
228 else
229 LOG(ERROR) << fn << "Fail to set default tech routing for Nfc-B";
230 }
231
232 // Route Nfc-F to host if we don't have a SE
233 techMask = NFA_TECHNOLOGY_MASK_F;
234 if ((mHostListenTechMask & NFA_TECHNOLOGY_MASK_F) &&
235 (mSeTechMask & NFA_TECHNOLOGY_MASK_F) == 0) {
236 nfaStat = NFA_EeSetDefaultTechRouting(
237 NFC_DH_ID, techMask, 0, 0, mSecureNfcEnabled ? 0 : techMask,
238 mSecureNfcEnabled ? 0 : techMask, mSecureNfcEnabled ? 0 : techMask);
239 if (nfaStat == NFA_STATUS_OK)
240 mRoutingEvent.wait();
241 else
242 LOG(ERROR) << fn << "Fail to set default tech routing for Nfc-F";
243 }
244 }
245
disableRoutingToHost()246 void RoutingManager::disableRoutingToHost() {
247 static const char fn[] = "RoutingManager::disableRoutingToHost()";
248 tNFA_STATUS nfaStat;
249 SyncEventGuard guard(mRoutingEvent);
250
251 // Clear default routing for IsoDep protocol
252 if (mDefaultIsoDepRoute == NFC_DH_ID) {
253 nfaStat =
254 NFA_EeClearDefaultProtoRouting(NFC_DH_ID, NFA_PROTOCOL_MASK_ISO_DEP);
255 if (nfaStat == NFA_STATUS_OK)
256 mRoutingEvent.wait();
257 else
258 LOG(ERROR) << fn << "Fail to clear default proto routing for IsoDep";
259 }
260
261 // Clear default routing for Nfc-A technology if we don't have a SE
262 if ((mHostListenTechMask & NFA_TECHNOLOGY_MASK_A) &&
263 (mSeTechMask & NFA_TECHNOLOGY_MASK_A) == 0) {
264 nfaStat = NFA_EeClearDefaultTechRouting(NFC_DH_ID, NFA_TECHNOLOGY_MASK_A);
265 if (nfaStat == NFA_STATUS_OK)
266 mRoutingEvent.wait();
267 else
268 LOG(ERROR) << fn << "Fail to clear default tech routing for Nfc-A";
269 }
270
271 // Clear default routing for Nfc-B technology if we don't have a SE
272 if ((mHostListenTechMask & NFA_TECHNOLOGY_MASK_B) &&
273 (mSeTechMask & NFA_TECHNOLOGY_MASK_B) == 0) {
274 nfaStat = NFA_EeClearDefaultTechRouting(NFC_DH_ID, NFA_TECHNOLOGY_MASK_B);
275 if (nfaStat == NFA_STATUS_OK)
276 mRoutingEvent.wait();
277 else
278 LOG(ERROR) << fn << "Fail to clear default tech routing for Nfc-B";
279 }
280
281 // Clear default routing for Nfc-F technology if we don't have a SE
282 if ((mHostListenTechMask & NFA_TECHNOLOGY_MASK_F) &&
283 (mSeTechMask & NFA_TECHNOLOGY_MASK_F) == 0) {
284 nfaStat = NFA_EeClearDefaultTechRouting(NFC_DH_ID, NFA_TECHNOLOGY_MASK_F);
285 if (nfaStat == NFA_STATUS_OK)
286 mRoutingEvent.wait();
287 else
288 LOG(ERROR) << fn << "Fail to clear default tech routing for Nfc-F";
289 }
290
291 // Clear default routing for T3T protocol
292 if (!mIsScbrSupported && mDefaultEe == NFC_DH_ID) {
293 nfaStat = NFA_EeClearDefaultProtoRouting(NFC_DH_ID, NFA_PROTOCOL_MASK_T3T);
294 if (nfaStat == NFA_STATUS_OK)
295 mRoutingEvent.wait();
296 else
297 LOG(ERROR) << fn << "Fail to clear default proto routing for T3T";
298 }
299 }
300
addAidRouting(const uint8_t * aid,uint8_t aidLen,int route,int aidInfo,int power)301 bool RoutingManager::addAidRouting(const uint8_t* aid, uint8_t aidLen,
302 int route, int aidInfo, int power) {
303 static const char fn[] = "RoutingManager::addAidRouting";
304 DLOG_IF(INFO, nfc_debug_enabled) << fn << ": enter";
305 uint8_t powerState = 0x01;
306 if (!mSecureNfcEnabled) {
307 if (power == 0x00) {
308 powerState = (route != 0x00) ? mOffHostAidRoutingPowerState : 0x11;
309 } else {
310 powerState =
311 (route != 0x00) ? mOffHostAidRoutingPowerState & power : power;
312 }
313 }
314 SyncEventGuard guard(mRoutingEvent);
315 mAidRoutingConfigured = false;
316 tNFA_STATUS nfaStat =
317 NFA_EeAddAidRouting(route, aidLen, (uint8_t*)aid, powerState, aidInfo);
318 if (nfaStat == NFA_STATUS_OK) {
319 mRoutingEvent.wait();
320 }
321 if (mAidRoutingConfigured) {
322 DLOG_IF(INFO, nfc_debug_enabled) << fn << ": routed AID";
323 return true;
324 } else {
325 LOG(ERROR) << fn << ": failed to route AID";
326 return false;
327 }
328 }
329
removeAidRouting(const uint8_t * aid,uint8_t aidLen)330 bool RoutingManager::removeAidRouting(const uint8_t* aid, uint8_t aidLen) {
331 static const char fn[] = "RoutingManager::removeAidRouting";
332 DLOG_IF(INFO, nfc_debug_enabled) << fn << ": enter";
333 SyncEventGuard guard(mRoutingEvent);
334 mAidRoutingConfigured = false;
335 tNFA_STATUS nfaStat = NFA_EeRemoveAidRouting(aidLen, (uint8_t*)aid);
336 if (nfaStat == NFA_STATUS_OK) {
337 mRoutingEvent.wait();
338 }
339 if (mAidRoutingConfigured) {
340 DLOG_IF(INFO, nfc_debug_enabled) << fn << ": removed AID";
341 return true;
342 } else {
343 LOG(WARNING) << fn << ": failed to remove AID";
344 return false;
345 }
346 }
347
commitRouting()348 bool RoutingManager::commitRouting() {
349 static const char fn[] = "RoutingManager::commitRouting";
350 tNFA_STATUS nfaStat = 0;
351 DLOG_IF(INFO, nfc_debug_enabled) << fn;
352 if(mEeInfoChanged) {
353 mSeTechMask = updateEeTechRouteSetting();
354 mEeInfoChanged = false;
355 }
356 {
357 SyncEventGuard guard(mEeUpdateEvent);
358 nfaStat = NFA_EeUpdateNow();
359 if (nfaStat == NFA_STATUS_OK) {
360 mEeUpdateEvent.wait(); // wait for NFA_EE_UPDATED_EVT
361 }
362 }
363 return (nfaStat == NFA_STATUS_OK);
364 }
365
onNfccShutdown()366 void RoutingManager::onNfccShutdown() {
367 static const char fn[] = "RoutingManager:onNfccShutdown";
368 if (mDefaultOffHostRoute == 0x00 && mDefaultFelicaRoute == 0x00) return;
369
370 tNFA_STATUS nfaStat = NFA_STATUS_FAILED;
371 uint8_t actualNumEe = MAX_NUM_EE;
372 tNFA_EE_INFO eeInfo[MAX_NUM_EE];
373 mDeinitializing = true;
374
375 memset(&eeInfo, 0, sizeof(eeInfo));
376 if ((nfaStat = NFA_EeGetInfo(&actualNumEe, eeInfo)) != NFA_STATUS_OK) {
377 LOG(ERROR) << StringPrintf("%s: fail get info; error=0x%X", fn, nfaStat);
378 return;
379 }
380 if (actualNumEe != 0) {
381 for (uint8_t xx = 0; xx < actualNumEe; xx++) {
382 bool bIsOffHostEEPresent =
383 (NFC_GetNCIVersion() < NCI_VERSION_2_0)
384 ? (eeInfo[xx].num_interface != 0)
385 : (eeInfo[xx].ee_interface[0] !=
386 NCI_NFCEE_INTERFACE_HCI_ACCESS) &&
387 (eeInfo[xx].ee_status == NFA_EE_STATUS_ACTIVE);
388 if (bIsOffHostEEPresent) {
389 DLOG_IF(INFO, nfc_debug_enabled) << StringPrintf(
390 "%s: Handle: 0x%04x Change Status Active to Inactive", fn,
391 eeInfo[xx].ee_handle);
392 SyncEventGuard guard(mEeSetModeEvent);
393 if ((nfaStat = NFA_EeModeSet(eeInfo[xx].ee_handle,
394 NFA_EE_MD_DEACTIVATE)) == NFA_STATUS_OK) {
395 mEeSetModeEvent.wait(); // wait for NFA_EE_MODE_SET_EVT
396 } else {
397 LOG(ERROR) << fn << "Failed to set EE inactive";
398 }
399 }
400 }
401 } else {
402 DLOG_IF(INFO, nfc_debug_enabled) << fn << ": No active EEs found";
403 }
404 }
405
notifyActivated(uint8_t technology)406 void RoutingManager::notifyActivated(uint8_t technology) {
407 JNIEnv* e = NULL;
408 ScopedAttach attach(mNativeData->vm, &e);
409 if (e == NULL) {
410 LOG(ERROR) << "jni env is null";
411 return;
412 }
413
414 e->CallVoidMethod(mNativeData->manager,
415 android::gCachedNfcManagerNotifyHostEmuActivated,
416 (int)technology);
417 if (e->ExceptionCheck()) {
418 e->ExceptionClear();
419 LOG(ERROR) << "fail notify";
420 }
421 }
422
notifyDeactivated(uint8_t technology)423 void RoutingManager::notifyDeactivated(uint8_t technology) {
424 mRxDataBuffer.clear();
425 JNIEnv* e = NULL;
426 ScopedAttach attach(mNativeData->vm, &e);
427 if (e == NULL) {
428 LOG(ERROR) << "jni env is null";
429 return;
430 }
431
432 e->CallVoidMethod(mNativeData->manager,
433 android::gCachedNfcManagerNotifyHostEmuDeactivated,
434 (int)technology);
435 if (e->ExceptionCheck()) {
436 e->ExceptionClear();
437 LOG(ERROR) << StringPrintf("fail notify");
438 }
439 }
440
handleData(uint8_t technology,const uint8_t * data,uint32_t dataLen,tNFA_STATUS status)441 void RoutingManager::handleData(uint8_t technology, const uint8_t* data,
442 uint32_t dataLen, tNFA_STATUS status) {
443 if (status == NFC_STATUS_CONTINUE) {
444 if (dataLen > 0) {
445 mRxDataBuffer.insert(mRxDataBuffer.end(), &data[0],
446 &data[dataLen]); // append data; more to come
447 }
448 return; // expect another NFA_CE_DATA_EVT to come
449 } else if (status == NFA_STATUS_OK) {
450 if (dataLen > 0) {
451 mRxDataBuffer.insert(mRxDataBuffer.end(), &data[0],
452 &data[dataLen]); // append data
453 }
454 // entire data packet has been received; no more NFA_CE_DATA_EVT
455 } else if (status == NFA_STATUS_FAILED) {
456 LOG(ERROR) << "RoutingManager::handleData: read data fail";
457 goto TheEnd;
458 }
459
460 {
461 JNIEnv* e = NULL;
462 ScopedAttach attach(mNativeData->vm, &e);
463 if (e == NULL) {
464 LOG(ERROR) << "jni env is null";
465 goto TheEnd;
466 }
467
468 ScopedLocalRef<jobject> dataJavaArray(
469 e, e->NewByteArray(mRxDataBuffer.size()));
470 if (dataJavaArray.get() == NULL) {
471 LOG(ERROR) << "fail allocate array";
472 goto TheEnd;
473 }
474
475 e->SetByteArrayRegion((jbyteArray)dataJavaArray.get(), 0,
476 mRxDataBuffer.size(), (jbyte*)(&mRxDataBuffer[0]));
477 if (e->ExceptionCheck()) {
478 e->ExceptionClear();
479 LOG(ERROR) << "fail fill array";
480 goto TheEnd;
481 }
482
483 e->CallVoidMethod(mNativeData->manager,
484 android::gCachedNfcManagerNotifyHostEmuData,
485 (int)technology, dataJavaArray.get());
486 if (e->ExceptionCheck()) {
487 e->ExceptionClear();
488 LOG(ERROR) << "fail notify";
489 }
490 }
491 TheEnd:
492 mRxDataBuffer.clear();
493 }
494
notifyEeUpdated()495 void RoutingManager::notifyEeUpdated() {
496 JNIEnv* e = NULL;
497 ScopedAttach attach(mNativeData->vm, &e);
498 if (e == NULL) {
499 LOG(ERROR) << "jni env is null";
500 return;
501 }
502
503 e->CallVoidMethod(mNativeData->manager,
504 android::gCachedNfcManagerNotifyEeUpdated);
505 if (e->ExceptionCheck()) {
506 e->ExceptionClear();
507 LOG(ERROR) << "fail notify";
508 }
509 }
510
stackCallback(uint8_t event,tNFA_CONN_EVT_DATA * eventData)511 void RoutingManager::stackCallback(uint8_t event,
512 tNFA_CONN_EVT_DATA* eventData) {
513 static const char fn[] = "RoutingManager::stackCallback";
514 DLOG_IF(INFO, nfc_debug_enabled) << StringPrintf("%s: event=0x%X", fn, event);
515 RoutingManager& routingManager = RoutingManager::getInstance();
516
517 switch (event) {
518 case NFA_CE_REGISTERED_EVT: {
519 tNFA_CE_REGISTERED& ce_registered = eventData->ce_registered;
520 DLOG_IF(INFO, nfc_debug_enabled)
521 << StringPrintf("%s: NFA_CE_REGISTERED_EVT; status=0x%X; h=0x%X", fn,
522 ce_registered.status, ce_registered.handle);
523 } break;
524
525 case NFA_CE_DEREGISTERED_EVT: {
526 tNFA_CE_DEREGISTERED& ce_deregistered = eventData->ce_deregistered;
527 DLOG_IF(INFO, nfc_debug_enabled) << StringPrintf(
528 "%s: NFA_CE_DEREGISTERED_EVT; h=0x%X", fn, ce_deregistered.handle);
529 } break;
530
531 case NFA_CE_ACTIVATED_EVT: {
532 routingManager.notifyActivated(NFA_TECHNOLOGY_MASK_A);
533 } break;
534
535 case NFA_DEACTIVATED_EVT:
536 case NFA_CE_DEACTIVATED_EVT: {
537 DLOG_IF(INFO, nfc_debug_enabled) << StringPrintf(
538 "%s: NFA_DEACTIVATED_EVT, NFA_CE_DEACTIVATED_EVT", fn);
539 routingManager.notifyDeactivated(NFA_TECHNOLOGY_MASK_A);
540 SyncEventGuard g(gDeactivatedEvent);
541 gActivated = false; // guard this variable from multi-threaded access
542 gDeactivatedEvent.notifyOne();
543 } break;
544
545 case NFA_CE_DATA_EVT: {
546 tNFA_CE_DATA& ce_data = eventData->ce_data;
547 DLOG_IF(INFO, nfc_debug_enabled)
548 << StringPrintf("%s: NFA_CE_DATA_EVT; stat=0x%X; h=0x%X; data len=%u",
549 fn, ce_data.status, ce_data.handle, ce_data.len);
550 getInstance().handleData(NFA_TECHNOLOGY_MASK_A, ce_data.p_data,
551 ce_data.len, ce_data.status);
552 } break;
553 }
554 }
555
updateRoutingTable()556 void RoutingManager::updateRoutingTable() {
557 updateEeTechRouteSetting();
558 updateDefaultProtocolRoute();
559 updateDefaultRoute();
560 }
561
updateDefaultProtocolRoute()562 void RoutingManager::updateDefaultProtocolRoute() {
563 static const char fn[] = "RoutingManager::updateDefaultProtocolRoute";
564
565 // Default Routing for ISO-DEP
566 tNFA_PROTOCOL_MASK protoMask = NFA_PROTOCOL_MASK_ISO_DEP;
567 tNFA_STATUS nfaStat;
568 if (mDefaultIsoDepRoute != NFC_DH_ID) {
569 nfaStat = NFA_EeClearDefaultProtoRouting(mDefaultIsoDepRoute, protoMask);
570 nfaStat = NFA_EeSetDefaultProtoRouting(
571 mDefaultIsoDepRoute, protoMask, mSecureNfcEnabled ? 0 : protoMask, 0,
572 mSecureNfcEnabled ? 0 : protoMask, mSecureNfcEnabled ? 0 : protoMask,
573 mSecureNfcEnabled ? 0 : protoMask);
574 } else {
575 nfaStat = NFA_EeClearDefaultProtoRouting(NFC_DH_ID, protoMask);
576 nfaStat = NFA_EeSetDefaultProtoRouting(
577 NFC_DH_ID, protoMask, 0, 0, mSecureNfcEnabled ? 0 : protoMask, 0, 0);
578 }
579 if (nfaStat == NFA_STATUS_OK)
580 DLOG_IF(INFO, nfc_debug_enabled)
581 << fn << ": Succeed to register default ISO-DEP route";
582 else
583 LOG(ERROR) << fn << ": failed to register default ISO-DEP route";
584
585 // Default routing for T3T protocol
586 if (!mIsScbrSupported) {
587 SyncEventGuard guard(mRoutingEvent);
588 tNFA_PROTOCOL_MASK protoMask = NFA_PROTOCOL_MASK_T3T;
589 if (mDefaultEe == NFC_DH_ID) {
590 nfaStat =
591 NFA_EeSetDefaultProtoRouting(NFC_DH_ID, protoMask, 0, 0, 0, 0, 0);
592 } else {
593 nfaStat = NFA_EeClearDefaultProtoRouting(mDefaultEe, protoMask);
594 nfaStat = NFA_EeSetDefaultProtoRouting(
595 mDefaultEe, protoMask, 0, 0, mSecureNfcEnabled ? 0 : protoMask,
596 mSecureNfcEnabled ? 0 : protoMask, mSecureNfcEnabled ? 0 : protoMask);
597 }
598 if (nfaStat == NFA_STATUS_OK)
599 mRoutingEvent.wait();
600 else
601 LOG(ERROR) << fn << "Fail to set default proto routing for T3T";
602 }
603 }
604
updateDefaultRoute()605 void RoutingManager::updateDefaultRoute() {
606 static const char fn[] = "RoutingManager::updateDefaultRoute";
607 if (NFC_GetNCIVersion() != NCI_VERSION_2_0) return;
608
609 // Register System Code for routing
610 SyncEventGuard guard(mRoutingEvent);
611 tNFA_STATUS nfaStat = NFA_EeAddSystemCodeRouting(
612 mDefaultSysCode, mDefaultSysCodeRoute,
613 mSecureNfcEnabled ? 0x01 : mDefaultSysCodePowerstate);
614 if (nfaStat == NFA_STATUS_NOT_SUPPORTED) {
615 mIsScbrSupported = false;
616 LOG(ERROR) << fn << ": SCBR not supported";
617 } else if (nfaStat == NFA_STATUS_OK) {
618 mIsScbrSupported = true;
619 mRoutingEvent.wait();
620 DLOG_IF(INFO, nfc_debug_enabled)
621 << fn << ": Succeed to register system code";
622 } else {
623 LOG(ERROR) << fn << ": Fail to register system code";
624 }
625
626 // Register zero lengthy Aid for default Aid Routing
627 if (mDefaultEe != mDefaultIsoDepRoute) {
628 uint8_t powerState = 0x01;
629 if (!mSecureNfcEnabled)
630 powerState = (mDefaultEe != 0x00) ? mOffHostAidRoutingPowerState : 0x11;
631 nfaStat = NFA_EeAddAidRouting(mDefaultEe, 0, NULL, powerState,
632 AID_ROUTE_QUAL_PREFIX);
633 if (nfaStat == NFA_STATUS_OK)
634 DLOG_IF(INFO, nfc_debug_enabled)
635 << fn << ": Succeed to register zero length AID";
636 else
637 LOG(ERROR) << fn << ": failed to register zero length AID";
638 }
639 }
640
updateEeTechRouteSetting()641 tNFA_TECHNOLOGY_MASK RoutingManager::updateEeTechRouteSetting() {
642 static const char fn[] = "RoutingManager::updateEeTechRouteSetting";
643 tNFA_TECHNOLOGY_MASK allSeTechMask = 0x00;
644
645 if (mDefaultOffHostRoute == 0 && mDefaultFelicaRoute == 0)
646 return allSeTechMask;
647
648 DLOG_IF(INFO, nfc_debug_enabled)
649 << fn << ": Number of EE is " << (int)mEeInfo.num_ee;
650
651 tNFA_STATUS nfaStat;
652 for (uint8_t i = 0; i < mEeInfo.num_ee; i++) {
653 tNFA_HANDLE eeHandle = mEeInfo.ee_disc_info[i].ee_handle;
654 tNFA_TECHNOLOGY_MASK seTechMask = 0;
655
656 DLOG_IF(INFO, nfc_debug_enabled) << StringPrintf(
657 "%s EE[%u] Handle: 0x%04x techA: 0x%02x techB: "
658 "0x%02x techF: 0x%02x techBprime: 0x%02x",
659 fn, i, eeHandle, mEeInfo.ee_disc_info[i].la_protocol,
660 mEeInfo.ee_disc_info[i].lb_protocol,
661 mEeInfo.ee_disc_info[i].lf_protocol,
662 mEeInfo.ee_disc_info[i].lbp_protocol);
663
664 if ((mDefaultOffHostRoute != 0) &&
665 (eeHandle == (mDefaultOffHostRoute | NFA_HANDLE_GROUP_EE))) {
666 if (mEeInfo.ee_disc_info[i].la_protocol != 0)
667 seTechMask |= NFA_TECHNOLOGY_MASK_A;
668 if (mEeInfo.ee_disc_info[i].lb_protocol != 0)
669 seTechMask |= NFA_TECHNOLOGY_MASK_B;
670 }
671 if ((mDefaultFelicaRoute != 0) &&
672 (eeHandle == (mDefaultFelicaRoute | NFA_HANDLE_GROUP_EE))) {
673 if (mEeInfo.ee_disc_info[i].lf_protocol != 0)
674 seTechMask |= NFA_TECHNOLOGY_MASK_F;
675 }
676
677 DLOG_IF(INFO, nfc_debug_enabled)
678 << StringPrintf("%s: seTechMask[%u]=0x%02x", fn, i, seTechMask);
679 if (seTechMask != 0x00) {
680 DLOG_IF(INFO, nfc_debug_enabled) << StringPrintf(
681 "Configuring tech mask 0x%02x on EE 0x%04x", seTechMask, eeHandle);
682
683 nfaStat = NFA_CeConfigureUiccListenTech(eeHandle, seTechMask);
684 if (nfaStat != NFA_STATUS_OK)
685 LOG(ERROR) << fn << "Failed to configure UICC listen technologies.";
686
687 // clear previous before setting new power state
688 nfaStat = NFA_EeClearDefaultTechRouting(eeHandle, seTechMask);
689 if (nfaStat != NFA_STATUS_OK)
690 LOG(ERROR) << fn << "Failed to clear EE technology routing.";
691
692 nfaStat = NFA_EeSetDefaultTechRouting(
693 eeHandle, seTechMask, mSecureNfcEnabled ? 0 : seTechMask, 0,
694 mSecureNfcEnabled ? 0 : seTechMask,
695 mSecureNfcEnabled ? 0 : seTechMask,
696 mSecureNfcEnabled ? 0 : seTechMask);
697 if (nfaStat != NFA_STATUS_OK)
698 LOG(ERROR) << fn << "Failed to configure UICC technology routing.";
699
700 allSeTechMask |= seTechMask;
701 }
702 }
703
704 // Clear DH technology route on NFC-A
705 if ((mHostListenTechMask & NFA_TECHNOLOGY_MASK_A) &&
706 (allSeTechMask & NFA_TECHNOLOGY_MASK_A) != 0) {
707 nfaStat = NFA_EeClearDefaultTechRouting(NFC_DH_ID, NFA_TECHNOLOGY_MASK_A);
708 if (nfaStat != NFA_STATUS_OK)
709 LOG(ERROR) << "Failed to clear DH technology routing on NFC-A.";
710 }
711
712 // Clear DH technology route on NFC-B
713 if ((mHostListenTechMask & NFA_TECHNOLOGY_MASK_B) &&
714 (allSeTechMask & NFA_TECHNOLOGY_MASK_B) != 0) {
715 nfaStat = NFA_EeClearDefaultTechRouting(NFC_DH_ID, NFA_TECHNOLOGY_MASK_B);
716 if (nfaStat != NFA_STATUS_OK)
717 LOG(ERROR) << "Failed to clear DH technology routing on NFC-B.";
718 }
719
720 // Clear DH technology route on NFC-F
721 if ((mHostListenTechMask & NFA_TECHNOLOGY_MASK_F) &&
722 (allSeTechMask & NFA_TECHNOLOGY_MASK_F) != 0) {
723 nfaStat = NFA_EeClearDefaultTechRouting(NFC_DH_ID, NFA_TECHNOLOGY_MASK_F);
724 if (nfaStat != NFA_STATUS_OK)
725 LOG(ERROR) << "Failed to clear DH technology routing on NFC-F.";
726 }
727 return allSeTechMask;
728 }
729
730 /*******************************************************************************
731 **
732 ** Function: nfaEeCallback
733 **
734 ** Description: Receive execution environment-related events from stack.
735 ** event: Event code.
736 ** eventData: Event data.
737 **
738 ** Returns: None
739 **
740 *******************************************************************************/
nfaEeCallback(tNFA_EE_EVT event,tNFA_EE_CBACK_DATA * eventData)741 void RoutingManager::nfaEeCallback(tNFA_EE_EVT event,
742 tNFA_EE_CBACK_DATA* eventData) {
743 static const char fn[] = "RoutingManager::nfaEeCallback";
744
745 RoutingManager& routingManager = RoutingManager::getInstance();
746 if (!eventData) {
747 LOG(ERROR) << "eventData is null";
748 return;
749 }
750 routingManager.mCbEventData = *eventData;
751 switch (event) {
752 case NFA_EE_REGISTER_EVT: {
753 SyncEventGuard guard(routingManager.mEeRegisterEvent);
754 DLOG_IF(INFO, nfc_debug_enabled) << StringPrintf(
755 "%s: NFA_EE_REGISTER_EVT; status=%u", fn, eventData->ee_register);
756 routingManager.mEeRegisterEvent.notifyOne();
757 } break;
758
759 case NFA_EE_DEREGISTER_EVT: {
760 DLOG_IF(INFO, nfc_debug_enabled) << StringPrintf(
761 "%s: NFA_EE_DEREGISTER_EVT; status=0x%X", fn, eventData->status);
762 routingManager.mReceivedEeInfo = false;
763 routingManager.mDeinitializing = false;
764 } break;
765
766 case NFA_EE_MODE_SET_EVT: {
767 SyncEventGuard guard(routingManager.mEeSetModeEvent);
768 DLOG_IF(INFO, nfc_debug_enabled) << StringPrintf(
769 "%s: NFA_EE_MODE_SET_EVT; status: 0x%04X handle: 0x%04X ", fn,
770 eventData->mode_set.status, eventData->mode_set.ee_handle);
771 routingManager.mEeSetModeEvent.notifyOne();
772 } break;
773
774 case NFA_EE_SET_TECH_CFG_EVT: {
775 DLOG_IF(INFO, nfc_debug_enabled) << StringPrintf(
776 "%s: NFA_EE_SET_TECH_CFG_EVT; status=0x%X", fn, eventData->status);
777 SyncEventGuard guard(routingManager.mRoutingEvent);
778 routingManager.mRoutingEvent.notifyOne();
779 } break;
780
781 case NFA_EE_CLEAR_TECH_CFG_EVT: {
782 DLOG_IF(INFO, nfc_debug_enabled) << StringPrintf(
783 "%s: NFA_EE_CLEAR_TECH_CFG_EVT; status=0x%X", fn, eventData->status);
784 SyncEventGuard guard(routingManager.mRoutingEvent);
785 routingManager.mRoutingEvent.notifyOne();
786 } break;
787
788 case NFA_EE_SET_PROTO_CFG_EVT: {
789 DLOG_IF(INFO, nfc_debug_enabled) << StringPrintf(
790 "%s: NFA_EE_SET_PROTO_CFG_EVT; status=0x%X", fn, eventData->status);
791 SyncEventGuard guard(routingManager.mRoutingEvent);
792 routingManager.mRoutingEvent.notifyOne();
793 } break;
794
795 case NFA_EE_CLEAR_PROTO_CFG_EVT: {
796 DLOG_IF(INFO, nfc_debug_enabled) << StringPrintf(
797 "%s: NFA_EE_CLEAR_PROTO_CFG_EVT; status=0x%X", fn, eventData->status);
798 SyncEventGuard guard(routingManager.mRoutingEvent);
799 routingManager.mRoutingEvent.notifyOne();
800 } break;
801
802 case NFA_EE_ACTION_EVT: {
803 tNFA_EE_ACTION& action = eventData->action;
804 if (action.trigger == NFC_EE_TRIG_SELECT)
805 DLOG_IF(INFO, nfc_debug_enabled) << StringPrintf(
806 "%s: NFA_EE_ACTION_EVT; h=0x%X; trigger=select (0x%X)", fn,
807 action.ee_handle, action.trigger);
808 else if (action.trigger == NFC_EE_TRIG_APP_INIT) {
809 tNFC_APP_INIT& app_init = action.param.app_init;
810 DLOG_IF(INFO, nfc_debug_enabled) << StringPrintf(
811 "%s: NFA_EE_ACTION_EVT; h=0x%X; trigger=app-init "
812 "(0x%X); aid len=%u; data len=%u",
813 fn, action.ee_handle, action.trigger, app_init.len_aid,
814 app_init.len_data);
815 } else if (action.trigger == NFC_EE_TRIG_RF_PROTOCOL)
816 DLOG_IF(INFO, nfc_debug_enabled) << StringPrintf(
817 "%s: NFA_EE_ACTION_EVT; h=0x%X; trigger=rf protocol (0x%X)", fn,
818 action.ee_handle, action.trigger);
819 else if (action.trigger == NFC_EE_TRIG_RF_TECHNOLOGY)
820 DLOG_IF(INFO, nfc_debug_enabled) << StringPrintf(
821 "%s: NFA_EE_ACTION_EVT; h=0x%X; trigger=rf tech (0x%X)", fn,
822 action.ee_handle, action.trigger);
823 else
824 DLOG_IF(INFO, nfc_debug_enabled) << StringPrintf(
825 "%s: NFA_EE_ACTION_EVT; h=0x%X; unknown trigger (0x%X)", fn,
826 action.ee_handle, action.trigger);
827 } break;
828
829 case NFA_EE_DISCOVER_REQ_EVT: {
830 DLOG_IF(INFO, nfc_debug_enabled) << StringPrintf(
831 "%s: NFA_EE_DISCOVER_REQ_EVT; status=0x%X; num ee=%u", __func__,
832 eventData->discover_req.status, eventData->discover_req.num_ee);
833 SyncEventGuard guard(routingManager.mEeInfoEvent);
834 memcpy(&routingManager.mEeInfo, &eventData->discover_req,
835 sizeof(routingManager.mEeInfo));
836 if (routingManager.mReceivedEeInfo && !routingManager.mDeinitializing) {
837 routingManager.mEeInfoChanged = true;
838 routingManager.notifyEeUpdated();
839 }
840 routingManager.mReceivedEeInfo = true;
841 routingManager.mEeInfoEvent.notifyOne();
842 } break;
843
844 case NFA_EE_NO_CB_ERR_EVT:
845 DLOG_IF(INFO, nfc_debug_enabled) << StringPrintf(
846 "%s: NFA_EE_NO_CB_ERR_EVT status=%u", fn, eventData->status);
847 break;
848
849 case NFA_EE_ADD_AID_EVT: {
850 DLOG_IF(INFO, nfc_debug_enabled) << StringPrintf(
851 "%s: NFA_EE_ADD_AID_EVT status=%u", fn, eventData->status);
852 SyncEventGuard guard(routingManager.mRoutingEvent);
853 routingManager.mAidRoutingConfigured =
854 (eventData->status == NFA_STATUS_OK);
855 routingManager.mRoutingEvent.notifyOne();
856 } break;
857
858 case NFA_EE_ADD_SYSCODE_EVT: {
859 SyncEventGuard guard(routingManager.mRoutingEvent);
860 routingManager.mRoutingEvent.notifyOne();
861 DLOG_IF(INFO, nfc_debug_enabled) << StringPrintf(
862 "%s: NFA_EE_ADD_SYSCODE_EVT status=%u", fn, eventData->status);
863 } break;
864
865 case NFA_EE_REMOVE_SYSCODE_EVT: {
866 SyncEventGuard guard(routingManager.mRoutingEvent);
867 routingManager.mRoutingEvent.notifyOne();
868 DLOG_IF(INFO, nfc_debug_enabled) << StringPrintf(
869 "%s: NFA_EE_REMOVE_SYSCODE_EVT status=%u", fn, eventData->status);
870 } break;
871
872 case NFA_EE_REMOVE_AID_EVT: {
873 DLOG_IF(INFO, nfc_debug_enabled) << StringPrintf(
874 "%s: NFA_EE_REMOVE_AID_EVT status=%u", fn, eventData->status);
875 SyncEventGuard guard(routingManager.mRoutingEvent);
876 routingManager.mAidRoutingConfigured =
877 (eventData->status == NFA_STATUS_OK);
878 routingManager.mRoutingEvent.notifyOne();
879 } break;
880
881 case NFA_EE_NEW_EE_EVT: {
882 DLOG_IF(INFO, nfc_debug_enabled) << StringPrintf(
883 "%s: NFA_EE_NEW_EE_EVT h=0x%X; status=%u", fn,
884 eventData->new_ee.ee_handle, eventData->new_ee.ee_status);
885 } break;
886
887 case NFA_EE_UPDATED_EVT: {
888 DLOG_IF(INFO, nfc_debug_enabled)
889 << StringPrintf("%s: NFA_EE_UPDATED_EVT", fn);
890 SyncEventGuard guard(routingManager.mEeUpdateEvent);
891 routingManager.mEeUpdateEvent.notifyOne();
892 } break;
893
894 case NFA_EE_PWR_AND_LINK_CTRL_EVT: {
895 DLOG_IF(INFO, nfc_debug_enabled)
896 << StringPrintf("%s: NFA_EE_PWR_AND_LINK_CTRL_EVT", fn);
897 SyncEventGuard guard(routingManager.mEePwrAndLinkCtrlEvent);
898 routingManager.mEePwrAndLinkCtrlEvent.notifyOne();
899 } break;
900
901 default:
902 DLOG_IF(INFO, nfc_debug_enabled)
903 << StringPrintf("%s: unknown event=%u ????", fn, event);
904 break;
905 }
906 }
907
registerT3tIdentifier(uint8_t * t3tId,uint8_t t3tIdLen)908 int RoutingManager::registerT3tIdentifier(uint8_t* t3tId, uint8_t t3tIdLen) {
909 static const char fn[] = "RoutingManager::registerT3tIdentifier";
910
911 DLOG_IF(INFO, nfc_debug_enabled)
912 << fn << ": Start to register NFC-F system on DH";
913
914 if (t3tIdLen != (2 + NCI_RF_F_UID_LEN + NCI_T3T_PMM_LEN)) {
915 LOG(ERROR) << fn << ": Invalid length of T3T Identifier";
916 return NFA_HANDLE_INVALID;
917 }
918
919 mNfcFOnDhHandle = NFA_HANDLE_INVALID;
920
921 uint16_t systemCode;
922 uint8_t nfcid2[NCI_RF_F_UID_LEN];
923 uint8_t t3tPmm[NCI_T3T_PMM_LEN];
924
925 systemCode = (((int)t3tId[0] << 8) | ((int)t3tId[1] << 0));
926 memcpy(nfcid2, t3tId + 2, NCI_RF_F_UID_LEN);
927 memcpy(t3tPmm, t3tId + 10, NCI_T3T_PMM_LEN);
928 {
929 SyncEventGuard guard(mRoutingEvent);
930 tNFA_STATUS nfaStat = NFA_CeRegisterFelicaSystemCodeOnDH(
931 systemCode, nfcid2, t3tPmm, nfcFCeCallback);
932 if (nfaStat == NFA_STATUS_OK) {
933 mRoutingEvent.wait();
934 } else {
935 LOG(ERROR) << fn << ": Fail to register NFC-F system on DH";
936 return NFA_HANDLE_INVALID;
937 }
938 }
939 DLOG_IF(INFO, nfc_debug_enabled)
940 << fn << ": Succeed to register NFC-F system on DH";
941
942 // Register System Code for routing
943 if (mIsScbrSupported) {
944 SyncEventGuard guard(mRoutingEvent);
945 tNFA_STATUS nfaStat = NFA_EeAddSystemCodeRouting(systemCode, NCI_DH_ID,
946 SYS_CODE_PWR_STATE_HOST);
947 if (nfaStat == NFA_STATUS_OK) {
948 mRoutingEvent.wait();
949 }
950 if ((nfaStat != NFA_STATUS_OK) || (mCbEventData.status != NFA_STATUS_OK)) {
951 LOG(ERROR) << StringPrintf("%s: Fail to register system code on DH", fn);
952 return NFA_HANDLE_INVALID;
953 }
954 DLOG_IF(INFO, nfc_debug_enabled)
955 << StringPrintf("%s: Succeed to register system code on DH", fn);
956 // add handle and system code pair to the map
957 mMapScbrHandle.emplace(mNfcFOnDhHandle, systemCode);
958 } else {
959 LOG(ERROR) << StringPrintf("%s: SCBR Not supported", fn);
960 }
961
962 return mNfcFOnDhHandle;
963 }
964
deregisterT3tIdentifier(int handle)965 void RoutingManager::deregisterT3tIdentifier(int handle) {
966 static const char fn[] = "RoutingManager::deregisterT3tIdentifier";
967
968 DLOG_IF(INFO, nfc_debug_enabled)
969 << StringPrintf("%s: Start to deregister NFC-F system on DH", fn);
970 {
971 SyncEventGuard guard(mRoutingEvent);
972 tNFA_STATUS nfaStat = NFA_CeDeregisterFelicaSystemCodeOnDH(handle);
973 if (nfaStat == NFA_STATUS_OK) {
974 mRoutingEvent.wait();
975 DLOG_IF(INFO, nfc_debug_enabled) << StringPrintf(
976 "%s: Succeeded in deregistering NFC-F system on DH", fn);
977 } else {
978 LOG(ERROR) << StringPrintf("%s: Fail to deregister NFC-F system on DH",
979 fn);
980 }
981 }
982 if (mIsScbrSupported) {
983 map<int, uint16_t>::iterator it = mMapScbrHandle.find(handle);
984 // find system code for given handle
985 if (it != mMapScbrHandle.end()) {
986 uint16_t systemCode = it->second;
987 mMapScbrHandle.erase(handle);
988 if (systemCode != 0) {
989 SyncEventGuard guard(mRoutingEvent);
990 tNFA_STATUS nfaStat = NFA_EeRemoveSystemCodeRouting(systemCode);
991 if (nfaStat == NFA_STATUS_OK) {
992 mRoutingEvent.wait();
993 DLOG_IF(INFO, nfc_debug_enabled) << StringPrintf(
994 "%s: Succeeded in deregistering system Code on DH", fn);
995 } else {
996 LOG(ERROR) << StringPrintf("%s: Fail to deregister system Code on DH",
997 fn);
998 }
999 }
1000 }
1001 }
1002 }
1003
nfcFCeCallback(uint8_t event,tNFA_CONN_EVT_DATA * eventData)1004 void RoutingManager::nfcFCeCallback(uint8_t event,
1005 tNFA_CONN_EVT_DATA* eventData) {
1006 static const char fn[] = "RoutingManager::nfcFCeCallback";
1007 RoutingManager& routingManager = RoutingManager::getInstance();
1008
1009 DLOG_IF(INFO, nfc_debug_enabled) << StringPrintf("%s: 0x%x", __func__, event);
1010
1011 switch (event) {
1012 case NFA_CE_REGISTERED_EVT: {
1013 DLOG_IF(INFO, nfc_debug_enabled)
1014 << StringPrintf("%s: registerd event notified", fn);
1015 routingManager.mNfcFOnDhHandle = eventData->ce_registered.handle;
1016 SyncEventGuard guard(routingManager.mRoutingEvent);
1017 routingManager.mRoutingEvent.notifyOne();
1018 } break;
1019 case NFA_CE_DEREGISTERED_EVT: {
1020 DLOG_IF(INFO, nfc_debug_enabled)
1021 << StringPrintf("%s: deregisterd event notified", fn);
1022 SyncEventGuard guard(routingManager.mRoutingEvent);
1023 routingManager.mRoutingEvent.notifyOne();
1024 } break;
1025 case NFA_CE_ACTIVATED_EVT: {
1026 DLOG_IF(INFO, nfc_debug_enabled)
1027 << StringPrintf("%s: activated event notified", fn);
1028 routingManager.notifyActivated(NFA_TECHNOLOGY_MASK_F);
1029 } break;
1030 case NFA_CE_DEACTIVATED_EVT: {
1031 DLOG_IF(INFO, nfc_debug_enabled)
1032 << StringPrintf("%s: deactivated event notified", fn);
1033 routingManager.notifyDeactivated(NFA_TECHNOLOGY_MASK_F);
1034 } break;
1035 case NFA_CE_DATA_EVT: {
1036 DLOG_IF(INFO, nfc_debug_enabled)
1037 << StringPrintf("%s: data event notified", fn);
1038 tNFA_CE_DATA& ce_data = eventData->ce_data;
1039 routingManager.handleData(NFA_TECHNOLOGY_MASK_F, ce_data.p_data,
1040 ce_data.len, ce_data.status);
1041 } break;
1042 default: {
1043 DLOG_IF(INFO, nfc_debug_enabled)
1044 << StringPrintf("%s: unknown event=%u ????", fn, event);
1045 } break;
1046 }
1047 }
1048
setNfcSecure(bool enable)1049 bool RoutingManager::setNfcSecure(bool enable) {
1050 mSecureNfcEnabled = enable;
1051 DLOG_IF(INFO, true) << "setNfcSecure NfcService " << enable;
1052 return true;
1053 }
1054
1055 /*******************************************************************************
1056 **
1057 ** Function: eeSetPwrAndLinkCtrl
1058 **
1059 ** Description: Programs the NCI command NFCEE_POWER_AND_LINK_CTRL_CMD
1060 **
1061 ** Returns: None
1062 **
1063 *******************************************************************************/
eeSetPwrAndLinkCtrl(uint8_t config)1064 void RoutingManager::eeSetPwrAndLinkCtrl(uint8_t config) {
1065 static const char fn[] = "RoutingManager::eeSetPwrAndLinkCtrl";
1066 tNFA_STATUS status = NFA_STATUS_OK;
1067
1068 if (mOffHostRouteEse.size() > 0) {
1069 DLOG_IF(INFO, nfc_debug_enabled)
1070 << StringPrintf("%s - nfceeId: 0x%02X, config: 0x%02X", fn,
1071 mOffHostRouteEse[0], config);
1072
1073 SyncEventGuard guard(mEePwrAndLinkCtrlEvent);
1074 status =
1075 NFA_EePowerAndLinkCtrl(
1076 ((uint8_t)mOffHostRouteEse[0] | NFA_HANDLE_GROUP_EE), config);
1077 if (status != NFA_STATUS_OK) {
1078 LOG(ERROR) << StringPrintf("%s: fail NFA_EePowerAndLinkCtrl; error=0x%X",
1079 __FUNCTION__, status);
1080 return;
1081 } else {
1082 mEePwrAndLinkCtrlEvent.wait();
1083 }
1084 } else {
1085 LOG(ERROR) << StringPrintf("%s: No ESE specified", __FUNCTION__);
1086 }
1087 }
1088
deinitialize()1089 void RoutingManager::deinitialize() {
1090 onNfccShutdown();
1091 NFA_EeDeregister(nfaEeCallback);
1092 }
1093
registerJniFunctions(JNIEnv * e)1094 int RoutingManager::registerJniFunctions(JNIEnv* e) {
1095 static const char fn[] = "RoutingManager::registerJniFunctions";
1096 DLOG_IF(INFO, nfc_debug_enabled) << StringPrintf("%s", fn);
1097 return jniRegisterNativeMethods(
1098 e, "com/android/nfc/cardemulation/AidRoutingManager", sMethods,
1099 NELEM(sMethods));
1100 }
1101
com_android_nfc_cardemulation_doGetDefaultRouteDestination(JNIEnv *)1102 int RoutingManager::com_android_nfc_cardemulation_doGetDefaultRouteDestination(
1103 JNIEnv*) {
1104 return getInstance().mDefaultEe;
1105 }
1106
1107 int RoutingManager::
com_android_nfc_cardemulation_doGetDefaultOffHostRouteDestination(JNIEnv *)1108 com_android_nfc_cardemulation_doGetDefaultOffHostRouteDestination(JNIEnv*) {
1109 return getInstance().mDefaultOffHostRoute;
1110 }
1111
1112 jbyteArray
com_android_nfc_cardemulation_doGetOffHostUiccDestination(JNIEnv * e)1113 RoutingManager::com_android_nfc_cardemulation_doGetOffHostUiccDestination(
1114 JNIEnv* e) {
1115 std::vector<uint8_t> uicc = getInstance().mOffHostRouteUicc;
1116 if (uicc.size() == 0) {
1117 return NULL;
1118 }
1119 CHECK(e);
1120 jbyteArray uiccJavaArray = e->NewByteArray(uicc.size());
1121 CHECK(uiccJavaArray);
1122 e->SetByteArrayRegion(uiccJavaArray, 0, uicc.size(), (jbyte*)&uicc[0]);
1123 return uiccJavaArray;
1124 }
1125
1126 jbyteArray
com_android_nfc_cardemulation_doGetOffHostEseDestination(JNIEnv * e)1127 RoutingManager::com_android_nfc_cardemulation_doGetOffHostEseDestination(
1128 JNIEnv* e) {
1129 std::vector<uint8_t> ese = getInstance().mOffHostRouteEse;
1130 if (ese.size() == 0) {
1131 return NULL;
1132 }
1133 CHECK(e);
1134 jbyteArray eseJavaArray = e->NewByteArray(ese.size());
1135 CHECK(eseJavaArray);
1136 e->SetByteArrayRegion(eseJavaArray, 0, ese.size(), (jbyte*)&ese[0]);
1137 return eseJavaArray;
1138 }
1139
com_android_nfc_cardemulation_doGetAidMatchingMode(JNIEnv *)1140 int RoutingManager::com_android_nfc_cardemulation_doGetAidMatchingMode(
1141 JNIEnv*) {
1142 return getInstance().mAidMatchingMode;
1143 }
1144
1145 int RoutingManager::
com_android_nfc_cardemulation_doGetDefaultIsoDepRouteDestination(JNIEnv *)1146 com_android_nfc_cardemulation_doGetDefaultIsoDepRouteDestination(JNIEnv*) {
1147 return getInstance().mDefaultIsoDepRoute;
1148 }
1149