1 /*
2  * Copyright (C) 2014 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 package com.android.nfc.cardemulation;
17 
18 import android.annotation.TargetApi;
19 import android.annotation.FlaggedApi;
20 import android.app.ActivityManager;
21 import android.app.role.RoleManager;
22 import android.content.ComponentName;
23 import android.content.Context;
24 import android.content.pm.ApplicationInfo;
25 import android.content.pm.PackageManager;
26 import android.content.pm.PackageManager.NameNotFoundException;
27 import android.nfc.Constants;
28 import android.nfc.INfcCardEmulation;
29 import android.nfc.INfcFCardEmulation;
30 import android.nfc.NfcAdapter;
31 import android.nfc.cardemulation.AidGroup;
32 import android.nfc.cardemulation.ApduServiceInfo;
33 import android.nfc.cardemulation.CardEmulation;
34 import android.nfc.cardemulation.NfcFServiceInfo;
35 import android.nfc.cardemulation.PollingFrame;
36 import android.os.Binder;
37 import android.os.Bundle;
38 import android.os.Looper;
39 import android.os.PowerManager;
40 import android.os.Process;
41 import android.os.RemoteException;
42 import android.os.SystemClock;
43 import android.os.UserHandle;
44 import android.os.UserManager;
45 import android.provider.Settings;
46 import android.sysprop.NfcProperties;
47 import android.util.Log;
48 import android.util.proto.ProtoOutputStream;
49 
50 import com.android.internal.annotations.VisibleForTesting;
51 import com.android.nfc.ForegroundUtils;
52 import com.android.nfc.NfcInjector;
53 import com.android.nfc.NfcPermissions;
54 import com.android.nfc.NfcService;
55 
56 import java.io.FileDescriptor;
57 import java.io.PrintWriter;
58 import java.util.Arrays;
59 import java.util.List;
60 import java.util.Objects;
61 
62 import com.android.nfc.R;
63 import android.permission.flags.Flags;
64 
65 /**
66  * CardEmulationManager is the central entity
67  * responsible for delegating to individual components
68  * implementing card emulation:
69  * - RegisteredServicesCache keeping track of HCE and SE services on the device
70  * - RegisteredNfcFServicesCache keeping track of HCE-F services on the device
71  * - RegisteredAidCache keeping track of AIDs registered by those services and manages
72  *   the routing table in the NFCC.
73  * - RegisteredT3tIdentifiersCache keeping track of T3T Identifier registered by
74  *   those services and manages the routing table in the NFCC.
75  * - HostEmulationManager handles incoming APDUs for the host and forwards to HCE
76  *   services as necessary.
77  * - HostNfcFEmulationManager handles incoming NFC-F packets for the host and
78  *   forwards to HCE-F services as necessary.
79  */
80 public class CardEmulationManager implements RegisteredServicesCache.Callback,
81         RegisteredNfcFServicesCache.Callback, PreferredServices.Callback,
82         EnabledNfcFServices.Callback, WalletRoleObserver.Callback {
83     static final String TAG = "CardEmulationManager";
84     static final boolean DBG = NfcProperties.debug_enabled().orElse(true);
85 
86     static final int NFC_HCE_APDU = 0x01;
87     static final int NFC_HCE_NFCF = 0x04;
88     /** Minimum AID length as per ISO7816 */
89     static final int MINIMUM_AID_LENGTH = 5;
90     /** Length of Select APDU header including length byte */
91     static final int SELECT_APDU_HDR_LENGTH = 5;
92     /** Length of the NDEF Tag application AID */
93     static final int NDEF_AID_LENGTH = 7;
94     /** AID of the NDEF Tag application Mapping Version 1.0 */
95     static final byte[] NDEF_AID_V1 =
96             new byte[] {(byte) 0xd2, 0x76, 0x00, 0x00, (byte) 0x85, 0x01, 0x00};
97     /** AID of the NDEF Tag application Mapping Version 2.0 */
98     static final byte[] NDEF_AID_V2 =
99             new byte[] {(byte) 0xd2, 0x76, 0x00, 0x00, (byte) 0x85, 0x01, 0x01};
100     /** Select APDU header */
101     static final byte[] SELECT_AID_HDR = new byte[] {0x00, (byte) 0xa4, 0x04, 0x00};
102 
103     final RegisteredAidCache mAidCache;
104     final RegisteredT3tIdentifiersCache mT3tIdentifiersCache;
105     final RegisteredServicesCache mServiceCache;
106     final RegisteredNfcFServicesCache mNfcFServicesCache;
107     final HostEmulationManager mHostEmulationManager;
108     final HostNfcFEmulationManager mHostNfcFEmulationManager;
109     final PreferredServices mPreferredServices;
110 
111     final WalletRoleObserver mWalletRoleObserver;
112     final EnabledNfcFServices mEnabledNfcFServices;
113     final Context mContext;
114     final CardEmulationInterface mCardEmulationInterface;
115     final NfcFCardEmulationInterface mNfcFCardEmulationInterface;
116     final PowerManager mPowerManager;
117     boolean mNotSkipAid;
118 
119     final ForegroundUtils mForegroundUtils;
120     private int mForegroundUid;
121 
122     RoutingOptionManager mRoutingOptionManager;
123     final byte[] mOffHostRouteUicc;
124     final byte[] mOffHostRouteEse;
125 
126     // TODO: Move this object instantiation and dependencies to NfcInjector.
CardEmulationManager(Context context, NfcInjector nfcInjector)127     public CardEmulationManager(Context context, NfcInjector nfcInjector) {
128         mContext = context;
129         mCardEmulationInterface = new CardEmulationInterface();
130         mNfcFCardEmulationInterface = new NfcFCardEmulationInterface();
131         mForegroundUtils = ForegroundUtils.getInstance(
132             context.getSystemService(ActivityManager.class));
133         mWalletRoleObserver = new WalletRoleObserver(context,
134                 context.getSystemService(RoleManager.class), this, nfcInjector);
135         mAidCache = new RegisteredAidCache(context, mWalletRoleObserver);
136         mT3tIdentifiersCache = new RegisteredT3tIdentifiersCache(context);
137         mHostEmulationManager =
138                 new HostEmulationManager(context, Looper.getMainLooper(), mAidCache);
139         mHostNfcFEmulationManager = new HostNfcFEmulationManager(context, mT3tIdentifiersCache);
140         mServiceCache = new RegisteredServicesCache(context, this);
141         mNfcFServicesCache = new RegisteredNfcFServicesCache(context, this);
142         mPreferredServices = new PreferredServices(context, mServiceCache, mAidCache,
143                 mWalletRoleObserver, this);
144         mEnabledNfcFServices = new EnabledNfcFServices(
145                 context, mNfcFServicesCache, mT3tIdentifiersCache, this);
146         mPowerManager = context.getSystemService(PowerManager.class);
147         mRoutingOptionManager = RoutingOptionManager.getInstance();
148         mOffHostRouteEse = mRoutingOptionManager.getOffHostRouteEse();
149         mOffHostRouteUicc = mRoutingOptionManager.getOffHostRouteUicc();
150         initialize();
151     }
152 
153     @VisibleForTesting
CardEmulationManager(Context context, ForegroundUtils foregroundUtils, WalletRoleObserver walletRoleObserver, RegisteredAidCache registeredAidCache, RegisteredT3tIdentifiersCache registeredT3tIdentifiersCache, HostEmulationManager hostEmulationManager, HostNfcFEmulationManager hostNfcFEmulationManager, RegisteredServicesCache registeredServicesCache, RegisteredNfcFServicesCache registeredNfcFServicesCache, PreferredServices preferredServices, EnabledNfcFServices enabledNfcFServices, RoutingOptionManager routingOptionManager, PowerManager powerManager)154     CardEmulationManager(Context context,
155             ForegroundUtils foregroundUtils,
156             WalletRoleObserver walletRoleObserver,
157             RegisteredAidCache registeredAidCache,
158             RegisteredT3tIdentifiersCache registeredT3tIdentifiersCache,
159             HostEmulationManager hostEmulationManager,
160             HostNfcFEmulationManager hostNfcFEmulationManager,
161             RegisteredServicesCache registeredServicesCache,
162             RegisteredNfcFServicesCache registeredNfcFServicesCache,
163             PreferredServices preferredServices,
164             EnabledNfcFServices enabledNfcFServices,
165             RoutingOptionManager routingOptionManager,
166             PowerManager powerManager) {
167         mContext = context;
168         mCardEmulationInterface = new CardEmulationInterface();
169         mNfcFCardEmulationInterface = new NfcFCardEmulationInterface();
170         mForegroundUtils = foregroundUtils;
171         mWalletRoleObserver = walletRoleObserver;
172         mAidCache = registeredAidCache;
173         mT3tIdentifiersCache = registeredT3tIdentifiersCache;
174         mHostEmulationManager = hostEmulationManager;
175         mHostNfcFEmulationManager = hostNfcFEmulationManager;
176         mServiceCache = registeredServicesCache;
177         mNfcFServicesCache = registeredNfcFServicesCache;
178         mPreferredServices = preferredServices;
179         mEnabledNfcFServices = enabledNfcFServices;
180         mPowerManager = powerManager;
181         mRoutingOptionManager = routingOptionManager;
182         mOffHostRouteEse = mRoutingOptionManager.getOffHostRouteEse();
183         mOffHostRouteUicc = mRoutingOptionManager.getOffHostRouteUicc();
184         initialize();
185     }
186 
initialize()187     private void initialize() {
188         mServiceCache.initialize();
189         mNfcFServicesCache.initialize();
190         mForegroundUid = Process.INVALID_UID;
191         if (mWalletRoleObserver.isWalletRoleFeatureEnabled()) {
192             int currentUser = ActivityManager.getCurrentUser();
193             onWalletRoleHolderChanged(
194                     mWalletRoleObserver.getDefaultWalletRoleHolder(currentUser), currentUser);
195         }
196     }
197 
getNfcCardEmulationInterface()198     public INfcCardEmulation getNfcCardEmulationInterface() {
199         return mCardEmulationInterface;
200     }
201 
getNfcFCardEmulationInterface()202     public INfcFCardEmulation getNfcFCardEmulationInterface() {
203         return mNfcFCardEmulationInterface;
204     }
205 
206     @FlaggedApi(android.nfc.Flags.FLAG_NFC_READ_POLLING_LOOP)
onPollingLoopDetected(List<PollingFrame> pollingFrames)207     public void onPollingLoopDetected(List<PollingFrame> pollingFrames) {
208         mHostEmulationManager.onPollingLoopDetected(pollingFrames);
209     }
210 
onFieldChangeDetected(boolean fieldOn)211     public void onFieldChangeDetected(boolean fieldOn) {
212         mHostEmulationManager.onFieldChangeDetected(fieldOn);
213     }
214 
onHostCardEmulationActivated(int technology)215     public void onHostCardEmulationActivated(int technology) {
216         if (mPowerManager != null) {
217             // Use USER_ACTIVITY_FLAG_INDIRECT to applying power hints without resets
218             // the screen timeout
219             mPowerManager.userActivity(SystemClock.uptimeMillis(),
220                     PowerManager.USER_ACTIVITY_EVENT_TOUCH,
221                     PowerManager.USER_ACTIVITY_FLAG_INDIRECT);
222         }
223         if (technology == NFC_HCE_APDU) {
224             mHostEmulationManager.onHostEmulationActivated();
225             mPreferredServices.onHostEmulationActivated();
226             mNotSkipAid = false;
227         } else if (technology == NFC_HCE_NFCF) {
228             mHostNfcFEmulationManager.onHostEmulationActivated();
229             mNfcFServicesCache.onHostEmulationActivated();
230             mEnabledNfcFServices.onHostEmulationActivated();
231         }
232     }
233 
onHostCardEmulationData(int technology, byte[] data)234     public void onHostCardEmulationData(int technology, byte[] data) {
235         if (technology == NFC_HCE_APDU) {
236             mHostEmulationManager.onHostEmulationData(data);
237         } else if (technology == NFC_HCE_NFCF) {
238             mHostNfcFEmulationManager.onHostEmulationData(data);
239         }
240         // Don't trigger userActivity if it's selecting NDEF AID
241         if (mPowerManager != null && !(technology == NFC_HCE_APDU && isSkipAid(data))) {
242             // Caution!! USER_ACTIVITY_EVENT_TOUCH resets the screen timeout
243             mPowerManager.userActivity(SystemClock.uptimeMillis(),
244                     PowerManager.USER_ACTIVITY_EVENT_TOUCH, 0);
245         }
246     }
247 
onHostCardEmulationDeactivated(int technology)248     public void onHostCardEmulationDeactivated(int technology) {
249         if (technology == NFC_HCE_APDU) {
250             mHostEmulationManager.onHostEmulationDeactivated();
251             mPreferredServices.onHostEmulationDeactivated();
252         } else if (technology == NFC_HCE_NFCF) {
253             mHostNfcFEmulationManager.onHostEmulationDeactivated();
254             mNfcFServicesCache.onHostEmulationDeactivated();
255             mEnabledNfcFServices.onHostEmulationDeactivated();
256         }
257     }
258 
onOffHostAidSelected()259     public void onOffHostAidSelected() {
260         mHostEmulationManager.onOffHostAidSelected();
261     }
262 
onUserSwitched(int userId)263     public void onUserSwitched(int userId) {
264         mWalletRoleObserver.onUserSwitched(userId);
265         // for HCE
266         mServiceCache.onUserSwitched();
267         mPreferredServices.onUserSwitched(userId);
268         // for HCE-F
269         mHostNfcFEmulationManager.onUserSwitched();
270         mT3tIdentifiersCache.onUserSwitched();
271         mEnabledNfcFServices.onUserSwitched(userId);
272         mNfcFServicesCache.onUserSwitched();
273     }
274 
onManagedProfileChanged()275     public void onManagedProfileChanged() {
276         // for HCE
277         mServiceCache.onManagedProfileChanged();
278         // for HCE-F
279         mNfcFServicesCache.onManagedProfileChanged();
280     }
281 
onNfcEnabled()282     public void onNfcEnabled() {
283         // for HCE
284         mAidCache.onNfcEnabled();
285         // for HCE-F
286         mT3tIdentifiersCache.onNfcEnabled();
287     }
288 
onNfcDisabled()289     public void onNfcDisabled() {
290         // for HCE
291         mAidCache.onNfcDisabled();
292         // for HCE-F
293         mHostNfcFEmulationManager.onNfcDisabled();
294         mNfcFServicesCache.onNfcDisabled();
295         mT3tIdentifiersCache.onNfcDisabled();
296         mEnabledNfcFServices.onNfcDisabled();
297     }
298 
onSecureNfcToggled()299     public void onSecureNfcToggled() {
300         mAidCache.onSecureNfcToggled();
301         mT3tIdentifiersCache.onSecureNfcToggled();
302     }
303 
dump(FileDescriptor fd, PrintWriter pw, String[] args)304     public void dump(FileDescriptor fd, PrintWriter pw, String[] args) {
305         mServiceCache.dump(fd, pw, args);
306         mNfcFServicesCache.dump(fd, pw ,args);
307         mPreferredServices.dump(fd, pw, args);
308         mEnabledNfcFServices.dump(fd, pw, args);
309         mAidCache.dump(fd, pw, args);
310         mT3tIdentifiersCache.dump(fd, pw, args);
311         mHostEmulationManager.dump(fd, pw, args);
312         mHostNfcFEmulationManager.dump(fd, pw, args);
313     }
314 
315     /**
316      * Dump debugging information as a CardEmulationManagerProto
317      *
318      * Note:
319      * See proto definition in frameworks/base/core/proto/android/nfc/card_emulation.proto
320      * When writing a nested message, must call {@link ProtoOutputStream#start(long)} before and
321      * {@link ProtoOutputStream#end(long)} after.
322      * Never reuse a proto field number. When removing a field, mark it as reserved.
323      */
dumpDebug(ProtoOutputStream proto)324     public void dumpDebug(ProtoOutputStream proto) {
325         long token = proto.start(CardEmulationManagerProto.REGISTERED_SERVICES_CACHE);
326         mServiceCache.dumpDebug(proto);
327         proto.end(token);
328 
329         token = proto.start(CardEmulationManagerProto.REGISTERED_NFC_F_SERVICES_CACHE);
330         mNfcFServicesCache.dumpDebug(proto);
331         proto.end(token);
332 
333         token = proto.start(CardEmulationManagerProto.PREFERRED_SERVICES);
334         mPreferredServices.dumpDebug(proto);
335         proto.end(token);
336 
337         token = proto.start(CardEmulationManagerProto.ENABLED_NFC_F_SERVICES);
338         mEnabledNfcFServices.dumpDebug(proto);
339         proto.end(token);
340 
341         token = proto.start(CardEmulationManagerProto.AID_CACHE);
342         mAidCache.dumpDebug(proto);
343         proto.end(token);
344 
345         token = proto.start(CardEmulationManagerProto.T3T_IDENTIFIERS_CACHE);
346         mT3tIdentifiersCache.dumpDebug(proto);
347         proto.end(token);
348 
349         token = proto.start(CardEmulationManagerProto.HOST_EMULATION_MANAGER);
350         mHostEmulationManager.dumpDebug(proto);
351         proto.end(token);
352 
353         token = proto.start(CardEmulationManagerProto.HOST_NFC_F_EMULATION_MANAGER);
354         mHostNfcFEmulationManager.dumpDebug(proto);
355         proto.end(token);
356     }
357 
358     @Override
onServicesUpdated(int userId, List<ApduServiceInfo> services, boolean validateInstalled)359     public void onServicesUpdated(int userId, List<ApduServiceInfo> services,
360             boolean validateInstalled) {
361         if (!mWalletRoleObserver.isWalletRoleFeatureEnabled()) {
362             // Verify defaults are still the same
363             verifyDefaults(userId, services, validateInstalled);
364         }
365         // Update the AID cache
366         mAidCache.onServicesUpdated(userId, services);
367         // Update the preferred services list
368         mPreferredServices.onServicesUpdated();
369         if (android.nfc.Flags.nfcReadPollingLoop()) {
370             mHostEmulationManager.updatePollingLoopFilters(userId, services);
371         }
372         NfcService.getInstance().onPreferredPaymentChanged(NfcAdapter.PREFERRED_PAYMENT_UPDATED);
373     }
374 
375     @Override
onNfcFServicesUpdated(int userId, List<NfcFServiceInfo> services)376     public void onNfcFServicesUpdated(int userId, List<NfcFServiceInfo> services) {
377         // Update the T3T identifier cache
378         mT3tIdentifiersCache.onServicesUpdated(userId, services);
379         // Update the enabled services list
380         mEnabledNfcFServices.onServicesUpdated();
381     }
382 
verifyDefaults(int userId, List<ApduServiceInfo> services, boolean validateInstalled)383     void verifyDefaults(int userId, List<ApduServiceInfo> services, boolean validateInstalled) {
384         UserManager um = mContext.createContextAsUser(
385                 UserHandle.of(userId), /*flags=*/0).getSystemService(UserManager.class);
386         List<UserHandle> luh = um.getEnabledProfiles();
387 
388         ComponentName defaultPaymentService = null;
389         int numDefaultPaymentServices = 0;
390         int userIdDefaultPaymentService = userId;
391 
392         for (UserHandle uh : luh) {
393             ComponentName paymentService = getDefaultServiceForCategory(uh.getIdentifier(),
394                     CardEmulation.CATEGORY_PAYMENT,
395                     validateInstalled && (uh.getIdentifier() == userId));
396             if (DBG) Log.d(TAG, "default: " + paymentService + " for user:" + uh);
397             if (paymentService != null) {
398                 numDefaultPaymentServices++;
399                 defaultPaymentService = paymentService;
400                 userIdDefaultPaymentService = uh.getIdentifier();
401             }
402         }
403         if (numDefaultPaymentServices > 1) {
404             Log.e(TAG, "Current default is not aligned across multiple users");
405             // leave default unset
406             for (UserHandle uh : luh) {
407                 setDefaultServiceForCategoryChecked(uh.getIdentifier(), null,
408                         CardEmulation.CATEGORY_PAYMENT);
409             }
410         } else {
411             if (DBG) {
412                 Log.d(TAG, "Current default: " + defaultPaymentService + " for user:"
413                         + userIdDefaultPaymentService);
414             }
415         }
416         if (defaultPaymentService == null) {
417             // A payment service may have been removed, leaving only one;
418             // in that case, automatically set that app as default.
419             int numPaymentServices = 0;
420             ComponentName lastFoundPaymentService = null;
421             PackageManager pm;
422             try {
423                 pm = mContext.createPackageContextAsUser("android", /*flags=*/0,
424                     UserHandle.of(userId)).getPackageManager();
425             } catch (NameNotFoundException e) {
426                 Log.e(TAG, "Could not create user package context");
427                 return;
428             }
429 
430             for (ApduServiceInfo service : services) {
431                 if (service.hasCategory(CardEmulation.CATEGORY_PAYMENT)
432                             && wasServicePreInstalled(pm, service.getComponent())) {
433                     numPaymentServices++;
434                     lastFoundPaymentService = service.getComponent();
435                 }
436             }
437             if (numPaymentServices > 1) {
438                 // More than one service left, leave default unset
439                 if (DBG) Log.d(TAG, "No default set, more than one service left.");
440                 setDefaultServiceForCategoryChecked(userId, null, CardEmulation.CATEGORY_PAYMENT);
441             } else if (numPaymentServices == 1) {
442                 // Make single found payment service the default
443                 if (DBG) Log.d(TAG, "No default set, making single service default.");
444                 setDefaultServiceForCategoryChecked(userId, lastFoundPaymentService,
445                         CardEmulation.CATEGORY_PAYMENT);
446             } else {
447                 // No payment services left, leave default at null
448                 if (DBG) Log.d(TAG, "No default set, last payment service removed.");
449                 setDefaultServiceForCategoryChecked(userId, null, CardEmulation.CATEGORY_PAYMENT);
450             }
451         }
452     }
453 
wasServicePreInstalled(PackageManager packageManager, ComponentName service)454     boolean wasServicePreInstalled(PackageManager packageManager, ComponentName service) {
455         try {
456             ApplicationInfo ai = packageManager
457                     .getApplicationInfo(service.getPackageName(), /*flags=*/0);
458             if ((ApplicationInfo.FLAG_SYSTEM & ai.flags) != 0) {
459                 if (DBG) Log.d(TAG, "Service was pre-installed on the device");
460                 return true;
461             }
462         } catch (NameNotFoundException e) {
463             Log.e(TAG, "Service is not currently installed on the device.");
464             return false;
465         }
466         if (DBG) Log.d(TAG, "Service was not pre-installed on the device");
467         return false;
468     }
469 
getDefaultServiceForCategory(int userId, String category, boolean validateInstalled)470     ComponentName getDefaultServiceForCategory(int userId, String category,
471              boolean validateInstalled) {
472         if (!CardEmulation.CATEGORY_PAYMENT.equals(category)) {
473             Log.e(TAG, "Not allowing defaults for category " + category);
474             return null;
475         }
476         // Load current payment default from settings
477         String name = Settings.Secure.getString(
478                 mContext.createContextAsUser(UserHandle.of(userId), 0).getContentResolver(),
479                 Constants.SETTINGS_SECURE_NFC_PAYMENT_DEFAULT_COMPONENT);
480         if (name != null) {
481             ComponentName service = ComponentName.unflattenFromString(name);
482             if (!validateInstalled || service == null) {
483                 return service;
484             } else {
485                 return mServiceCache.hasService(userId, service) ? service : null;
486             }
487         } else {
488             return null;
489         }
490     }
491 
setDefaultServiceForCategoryChecked(int userId, ComponentName service, String category)492     boolean setDefaultServiceForCategoryChecked(int userId, ComponentName service,
493             String category) {
494         if (!CardEmulation.CATEGORY_PAYMENT.equals(category)) {
495             Log.e(TAG, "Not allowing defaults for category " + category);
496             return false;
497         }
498         // TODO Not really nice to be writing to Settings.Secure here...
499         // ideally we overlay our local changes over whatever is in
500         // Settings.Secure
501         if (service == null || mServiceCache.hasService(userId, service)) {
502             Settings.Secure.putString(mContext
503                     .createContextAsUser(UserHandle.of(userId), 0).getContentResolver(),
504                     Constants.SETTINGS_SECURE_NFC_PAYMENT_DEFAULT_COMPONENT,
505                     service != null ? service.flattenToString() : null);
506         } else {
507             Log.e(TAG, "Could not find default service to make default: " + service);
508         }
509         return true;
510     }
511 
isServiceRegistered(int userId, ComponentName service)512     boolean isServiceRegistered(int userId, ComponentName service) {
513         boolean serviceFound = mServiceCache.hasService(userId, service);
514         if (!serviceFound) {
515             // If we don't know about this service yet, it may have just been enabled
516             // using PackageManager.setComponentEnabledSetting(). The PackageManager
517             // broadcasts are delayed by 10 seconds in that scenario, which causes
518             // calls to our APIs referencing that service to fail.
519             // Hence, update the cache in case we don't know about the service.
520             if (DBG) Log.d(TAG, "Didn't find passed in service, invalidating cache.");
521             mServiceCache.invalidateCache(userId, true);
522         }
523         return mServiceCache.hasService(userId, service);
524     }
525 
isNfcFServiceInstalled(int userId, ComponentName service)526     boolean isNfcFServiceInstalled(int userId, ComponentName service) {
527         boolean serviceFound = mNfcFServicesCache.hasService(userId, service);
528         if (!serviceFound) {
529             // If we don't know about this service yet, it may have just been enabled
530             // using PackageManager.setComponentEnabledSetting(). The PackageManager
531             // broadcasts are delayed by 10 seconds in that scenario, which causes
532             // calls to our APIs referencing that service to fail.
533             // Hence, update the cache in case we don't know about the service.
534             if (DBG) Log.d(TAG, "Didn't find passed in service, invalidating cache.");
535             mNfcFServicesCache.invalidateCache(userId);
536         }
537         return mNfcFServicesCache.hasService(userId, service);
538     }
539 
540     /**
541      * Returns true if it's not selecting NDEF AIDs
542      * It's used to skip userActivity if it only selects NDEF AIDs
543      */
isSkipAid(byte[] data)544     boolean isSkipAid(byte[] data) {
545         if (mNotSkipAid || data == null
546                 || data.length < SELECT_APDU_HDR_LENGTH + MINIMUM_AID_LENGTH
547                 || !Arrays.equals(SELECT_AID_HDR, 0, SELECT_AID_HDR.length,
548                         data, 0, SELECT_AID_HDR.length)) {
549             return false;
550         }
551         int aidLength = Byte.toUnsignedInt(data[SELECT_APDU_HDR_LENGTH - 1]);
552         if (data.length >= SELECT_APDU_HDR_LENGTH + NDEF_AID_LENGTH
553                 && aidLength == NDEF_AID_LENGTH) {
554             if (Arrays.equals(data, SELECT_APDU_HDR_LENGTH,
555                         SELECT_APDU_HDR_LENGTH + NDEF_AID_LENGTH,
556                         NDEF_AID_V1, 0, NDEF_AID_LENGTH)) {
557                 if (DBG) Log.d(TAG, "Skip for NDEF_V1");
558                 return true;
559             } else if (Arrays.equals(data, SELECT_APDU_HDR_LENGTH,
560                         SELECT_APDU_HDR_LENGTH + NDEF_AID_LENGTH,
561                         NDEF_AID_V2, 0, NDEF_AID_LENGTH)) {
562                 if (DBG) Log.d(TAG, "Skip for NDEF_V2");
563                 return true;
564             }
565         }
566         // The data payload is not selecting the skip AID.
567         mNotSkipAid = true;
568         return false;
569     }
570 
571     /**
572      * Returns whether a service in this package is preferred,
573      * either because it's the default payment app or it's running
574      * in the foreground.
575      */
packageHasPreferredService(String packageName)576     public boolean packageHasPreferredService(String packageName) {
577         return mPreferredServices.packageHasPreferredService(packageName);
578     }
579 
580     /**
581      * This class implements the application-facing APIs and are called
582      * from binder. All calls must be permission-checked.
583      */
584     final class CardEmulationInterface extends INfcCardEmulation.Stub {
585         @Override
isDefaultServiceForCategory(int userId, ComponentName service, String category)586         public boolean isDefaultServiceForCategory(int userId, ComponentName service,
587                 String category) {
588             NfcPermissions.enforceUserPermissions(mContext);
589             NfcPermissions.validateUserId(userId);
590             if (!isServiceRegistered(userId, service)) {
591                 return false;
592             }
593             if (mWalletRoleObserver.isWalletRoleFeatureEnabled()) {
594                 return service.getPackageName()
595                         .equals(mWalletRoleObserver.getDefaultWalletRoleHolder(userId));
596             }
597             ComponentName defaultService =
598                     getDefaultServiceForCategory(userId, category, true);
599             return (defaultService != null && defaultService.equals(service));
600         }
601 
602         @Override
isDefaultServiceForAid(int userId, ComponentName service, String aid)603         public boolean isDefaultServiceForAid(int userId,
604                 ComponentName service, String aid) throws RemoteException {
605             NfcPermissions.validateUserId(userId);
606             NfcPermissions.enforceUserPermissions(mContext);
607             if (!isServiceRegistered(userId, service)) {
608                 return false;
609             }
610             return mAidCache.isDefaultServiceForAid(userId, service, aid);
611         }
612 
613         @Override
setDefaultServiceForCategory(int userId, ComponentName service, String category)614         public boolean setDefaultServiceForCategory(int userId,
615                 ComponentName service, String category) throws RemoteException {
616             NfcPermissions.validateUserId(userId);
617             NfcPermissions.enforceAdminPermissions(mContext);
618             if (!isServiceRegistered(userId, service)) {
619                 return false;
620             }
621             return setDefaultServiceForCategoryChecked(userId, service, category);
622         }
623 
624         @Override
setDefaultForNextTap(int userId, ComponentName service)625         public boolean setDefaultForNextTap(int userId, ComponentName service)
626                 throws RemoteException {
627             NfcPermissions.validateProfileId(mContext, userId);
628             NfcPermissions.enforceAdminPermissions(mContext);
629             if (service != null && !isServiceRegistered(userId, service)) {
630                 return false;
631             }
632             return mPreferredServices.setDefaultForNextTap(userId, service);
633         }
634 
635         @Override
setShouldDefaultToObserveModeForService(int userId, ComponentName service, boolean enable)636         public boolean setShouldDefaultToObserveModeForService(int userId,
637                 ComponentName service, boolean enable) {
638             NfcPermissions.validateUserId(userId);
639             NfcPermissions.enforceUserPermissions(mContext);
640             if (!isServiceRegistered(userId, service)) {
641                 return false;
642             }
643             Log.d(TAG, "Set should default to observe mode for service (" + service + ") to "
644                     + enable);
645             boolean currentStatus = mServiceCache.doesServiceShouldDefaultToObserveMode(userId,
646                     service);
647 
648             if (currentStatus != enable) {
649                 if (!mServiceCache.setShouldDefaultToObserveModeForService(userId,
650                         Binder.getCallingUid(), service, enable)) {
651                     return false;
652                 }
653                 updateForShouldDefaultToObserveMode(userId);
654             }
655             return true;
656         }
657 
658         @Override
registerAidGroupForService(int userId, ComponentName service, AidGroup aidGroup)659         public boolean registerAidGroupForService(int userId,
660                 ComponentName service, AidGroup aidGroup) throws RemoteException {
661             NfcPermissions.validateUserId(userId);
662             NfcPermissions.enforceUserPermissions(mContext);
663             if (!isServiceRegistered(userId, service)) {
664                 Log.e(TAG, "service ("+ service + ") isn't registered for user " + userId);
665                 return false;
666             }
667             if (!mServiceCache.registerAidGroupForService(userId, Binder.getCallingUid(), service,
668                     aidGroup)) {
669                 return false;
670             }
671             NfcService.getInstance().onPreferredPaymentChanged(
672                     NfcAdapter.PREFERRED_PAYMENT_UPDATED);
673             return true;
674         }
675 
676         @Override
677         @FlaggedApi(android.nfc.Flags.FLAG_NFC_READ_POLLING_LOOP)
registerPollingLoopFilterForService(int userId, ComponentName service, String pollingLoopFilter, boolean autoTransact)678         public boolean registerPollingLoopFilterForService(int userId, ComponentName service,
679                 String pollingLoopFilter, boolean autoTransact) throws RemoteException {
680             NfcPermissions.validateUserId(userId);
681             NfcPermissions.enforceUserPermissions(mContext);
682             if (!isServiceRegistered(userId, service)) {
683                 Log.e(TAG, "service ("+ service + ") isn't registered for user " + userId);
684                 return false;
685             }
686             return mServiceCache.registerPollingLoopFilterForService(userId, Binder.getCallingUid(),
687                     service, pollingLoopFilter, autoTransact);
688         }
689 
690         @Override
691         @FlaggedApi(android.nfc.Flags.FLAG_NFC_READ_POLLING_LOOP)
removePollingLoopFilterForService(int userId, ComponentName service, String pollingLoopFilter)692         public boolean removePollingLoopFilterForService(int userId, ComponentName service,
693                 String pollingLoopFilter) throws RemoteException {
694             NfcPermissions.validateUserId(userId);
695             NfcPermissions.enforceUserPermissions(mContext);
696             if (!isServiceRegistered(userId, service)) {
697                 Log.e(TAG, "service ("+ service + ") isn't registered for user " + userId);
698                 return false;
699             }
700             return mServiceCache.removePollingLoopFilterForService(userId, Binder.getCallingUid(),
701                     service, pollingLoopFilter);
702         }
703 
704         @Override
705         @FlaggedApi(android.nfc.Flags.FLAG_NFC_READ_POLLING_LOOP)
registerPollingLoopPatternFilterForService(int userId, ComponentName service, String pollingLoopPatternFilter, boolean autoTransact)706         public boolean registerPollingLoopPatternFilterForService(int userId, ComponentName service,
707                 String pollingLoopPatternFilter, boolean autoTransact) throws RemoteException {
708             NfcPermissions.validateUserId(userId);
709             NfcPermissions.enforceUserPermissions(mContext);
710             if (!isServiceRegistered(userId, service)) {
711                 Log.e(TAG, "service ("+ service + ") isn't registed for user " + userId);
712                 return false;
713             }
714             return mServiceCache.registerPollingLoopPatternFilterForService(userId,
715                     Binder.getCallingUid(), service, pollingLoopPatternFilter, autoTransact);
716         }
717 
718         @Override
719         @FlaggedApi(android.nfc.Flags.FLAG_NFC_READ_POLLING_LOOP)
removePollingLoopPatternFilterForService(int userId, ComponentName service, String pollingLoopPatternFilter)720         public boolean removePollingLoopPatternFilterForService(int userId, ComponentName service,
721                 String pollingLoopPatternFilter) throws RemoteException {
722             NfcPermissions.validateUserId(userId);
723             NfcPermissions.enforceUserPermissions(mContext);
724             if (!isServiceRegistered(userId, service)) {
725                 Log.e(TAG, "service ("+ service + ") isn't registed for user " + userId);
726                 return false;
727             }
728             return mServiceCache.removePollingLoopPatternFilterForService(userId,
729                     Binder.getCallingUid(), service, pollingLoopPatternFilter);
730         }
731 
732         @Override
setOffHostForService(int userId, ComponentName service, String offHostSE)733         public boolean setOffHostForService(int userId, ComponentName service, String offHostSE) {
734             NfcPermissions.validateUserId(userId);
735             NfcPermissions.enforceUserPermissions(mContext);
736             if (!isServiceRegistered(userId, service)) {
737                 return false;
738             }
739             if (!mServiceCache.setOffHostSecureElement(userId, Binder.getCallingUid(), service,
740                     offHostSE)) {
741                 return false;
742             }
743             NfcService.getInstance().onPreferredPaymentChanged(
744                     NfcAdapter.PREFERRED_PAYMENT_UPDATED);
745             return true;
746         }
747 
748         @Override
unsetOffHostForService(int userId, ComponentName service)749         public boolean unsetOffHostForService(int userId, ComponentName service) {
750             NfcPermissions.validateUserId(userId);
751             NfcPermissions.enforceUserPermissions(mContext);
752             if (!isServiceRegistered(userId, service)) {
753                 return false;
754             }
755             if (!mServiceCache.resetOffHostSecureElement(userId, Binder.getCallingUid(), service)) {
756                 return false;
757             }
758             NfcService.getInstance().onPreferredPaymentChanged(
759                     NfcAdapter.PREFERRED_PAYMENT_UPDATED);
760             return true;
761         }
762 
763         @Override
getAidGroupForService(int userId, ComponentName service, String category)764         public AidGroup getAidGroupForService(int userId,
765                 ComponentName service, String category) throws RemoteException {
766             NfcPermissions.validateUserId(userId);
767             NfcPermissions.enforceUserPermissions(mContext);
768             if (!isServiceRegistered(userId, service)) {
769                 return null;
770             }
771             return mServiceCache.getAidGroupForService(userId, Binder.getCallingUid(), service,
772                     category);
773         }
774 
775         @Override
removeAidGroupForService(int userId, ComponentName service, String category)776         public boolean removeAidGroupForService(int userId,
777                 ComponentName service, String category) throws RemoteException {
778             NfcPermissions.validateUserId(userId);
779             NfcPermissions.enforceUserPermissions(mContext);
780             if (!isServiceRegistered(userId, service)) {
781                 return false;
782             }
783             if (!mServiceCache.removeAidGroupForService(userId, Binder.getCallingUid(), service,
784                     category)) {
785                 return false;
786             }
787             NfcService.getInstance().onPreferredPaymentChanged(
788                     NfcAdapter.PREFERRED_PAYMENT_UPDATED);
789             return true;
790         }
791 
792         @Override
getServices(int userId, String category)793         public List<ApduServiceInfo> getServices(int userId, String category)
794                 throws RemoteException {
795             NfcPermissions.validateProfileId(mContext, userId);
796             NfcPermissions.enforceAdminPermissions(mContext);
797             return mServiceCache.getServicesForCategory(userId, category);
798         }
799 
800         @Override
setPreferredService(ComponentName service)801         public boolean setPreferredService(ComponentName service)
802                 throws RemoteException {
803             NfcPermissions.enforceUserPermissions(mContext);
804             if (!isServiceRegistered( UserHandle.getUserHandleForUid(
805                     Binder.getCallingUid()).getIdentifier(), service)) {
806                 Log.e(TAG, "setPreferredService: unknown component.");
807                 return false;
808             }
809             return mPreferredServices.registerPreferredForegroundService(service,
810                     Binder.getCallingUid());
811         }
812 
813         @Override
unsetPreferredService()814         public boolean unsetPreferredService() throws RemoteException {
815             NfcPermissions.enforceUserPermissions(mContext);
816             return mPreferredServices.unregisteredPreferredForegroundService(
817                     Binder.getCallingUid());
818         }
819 
820         @Override
supportsAidPrefixRegistration()821         public boolean supportsAidPrefixRegistration() throws RemoteException {
822             return mAidCache.supportsAidPrefixRegistration();
823         }
824 
825         @Override
getPreferredPaymentService(int userId)826         public ApduServiceInfo getPreferredPaymentService(int userId) throws RemoteException {
827             NfcPermissions.validateUserId(userId);
828             NfcPermissions.enforceUserPermissions(mContext);
829             NfcPermissions.enforcePreferredPaymentInfoPermissions(mContext);
830             return mServiceCache.getService(userId, mAidCache.getPreferredService().second);
831         }
832 
833         @Override
setServiceEnabledForCategoryOther(int userId, ComponentName app, boolean status)834         public boolean setServiceEnabledForCategoryOther(int userId,
835                 ComponentName app, boolean status) throws RemoteException {
836             if (!mContext.getResources().getBoolean(R.bool.enable_service_for_category_other))
837               return false;
838             NfcPermissions.enforceUserPermissions(mContext);
839 
840             return mServiceCache.registerOtherForService(userId, app, status);
841         }
842 
843         @Override
isDefaultPaymentRegistered()844         public boolean isDefaultPaymentRegistered() throws RemoteException {
845             if (mWalletRoleObserver.isWalletRoleFeatureEnabled()) {
846                 int callingUserId = Binder.getCallingUserHandle().getIdentifier();
847                 return mWalletRoleObserver
848                         .getDefaultWalletRoleHolder(callingUserId) != null;
849             }
850             String defaultComponent = Settings.Secure.getString(mContext.getContentResolver(),
851                     Constants.SETTINGS_SECURE_NFC_PAYMENT_DEFAULT_COMPONENT);
852             return defaultComponent != null ? true : false;
853         }
854 
855         @Override
overrideRoutingTable(int userHandle, String protocol, String technology)856         public boolean overrideRoutingTable(int userHandle, String protocol, String technology) {
857             Log.d(TAG, "overrideRoutingTable. userHandle " + userHandle + ", protocol " + protocol +
858                     ", technology " + technology);
859 
860             int callingUid = Binder.getCallingUid();
861             if (!mForegroundUtils
862                     .registerUidToBackgroundCallback(mForegroundCallback, callingUid)) {
863                 Log.e(TAG, "overrideRoutingTable: Caller is not in foreground.");
864                 return false;
865             }
866             mForegroundUid = callingUid;
867 
868             int protocolRoute = getRouteForSecureElement(protocol);
869             int technologyRoute = getRouteForSecureElement(technology);
870             if (DBG) Log.d(TAG, "protocolRoute " + protocolRoute +
871                 ", technologyRoute " + technologyRoute);
872 
873 //            mRoutingOptionManager.overrideDefaultRoute(protocolRoute);
874             mRoutingOptionManager.overrideDefaultIsoDepRoute(protocolRoute);
875             mRoutingOptionManager.overrideDefaultOffHostRoute(technologyRoute);
876             mAidCache.onRoutingOverridedOrRecovered();
877 //            NfcService.getInstance().commitRouting();
878 
879             return true;
880         }
881 
882         @Override
recoverRoutingTable(int userHandle)883         public boolean recoverRoutingTable(int userHandle) {
884             Log.d(TAG, "recoverRoutingTable. userHandle " + userHandle);
885 
886             if (!mForegroundUtils.isInForeground(Binder.getCallingUid())) {
887                 if (DBG) Log.d(TAG, "recoverRoutingTable : not in foreground.");
888                 return false;
889             }
890             mForegroundUid = Process.INVALID_UID;
891 
892             mRoutingOptionManager.recoverOverridedRoutingTable();
893             mAidCache.onRoutingOverridedOrRecovered();
894 //            NfcService.getInstance().commitRouting();
895 
896             return true;
897         }
898     }
899 
900     final ForegroundUtils.Callback mForegroundCallback = new ForegroundCallbackImpl();
901 
902     class ForegroundCallbackImpl implements ForegroundUtils.Callback {
903         @Override
onUidToBackground(int uid)904         public void onUidToBackground(int uid) {
905             synchronized (CardEmulationManager.this) {
906                 if (mForegroundUid == uid) {
907                     if (DBG) Log.d(TAG, "Uid " + uid + " switch to background.");
908                     mForegroundUid = Process.INVALID_UID;
909                     mRoutingOptionManager.recoverOverridedRoutingTable();
910                 }
911             }
912         }
913     }
914 
getRouteForSecureElement(String se)915     private int getRouteForSecureElement(String se) {
916         String route = se;
917         if (route == null) {
918             return -1;
919         }
920 
921         if (route.equals("DH")) {
922             return 0;
923         }
924 
925         if (route.length() == 3) {
926             route = route + '1';
927         }
928 
929         try {
930             if (route.startsWith("eSE") && mOffHostRouteEse != null) {
931                 int index = Integer.parseInt(route.substring(3));
932                 if (mOffHostRouteEse.length >= index && index > 0) {
933                     return mOffHostRouteEse[index - 1] & 0xFF;
934                 }
935             } else if (route.startsWith("SIM") && mOffHostRouteUicc != null) {
936                 int index = Integer.parseInt(route.substring(3));
937                 if (mOffHostRouteUicc.length >= index && index > 0) {
938                     return mOffHostRouteUicc[index - 1] & 0xFF;
939                 }
940             }
941             if (mOffHostRouteEse == null && mOffHostRouteUicc == null)
942                 return -1;
943         } catch (NumberFormatException ignored) { }
944 
945         return 0;
946     }
947 
948     /**
949      * This class implements the application-facing APIs and are called
950      * from binder. All calls must be permission-checked.
951      */
952     final class NfcFCardEmulationInterface extends INfcFCardEmulation.Stub {
953         @Override
getSystemCodeForService(int userId, ComponentName service)954         public String getSystemCodeForService(int userId, ComponentName service)
955                 throws RemoteException {
956             NfcPermissions.validateUserId(userId);
957             NfcPermissions.enforceUserPermissions(mContext);
958             if (!isNfcFServiceInstalled(userId, service)) {
959                 return null;
960             }
961             return mNfcFServicesCache.getSystemCodeForService(
962                     userId, Binder.getCallingUid(), service);
963         }
964 
965         @Override
registerSystemCodeForService(int userId, ComponentName service, String systemCode)966         public boolean registerSystemCodeForService(int userId, ComponentName service,
967                 String systemCode)
968                 throws RemoteException {
969             NfcPermissions.validateUserId(userId);
970             NfcPermissions.enforceUserPermissions(mContext);
971             if (!isNfcFServiceInstalled(userId, service)) {
972                 return false;
973             }
974             return mNfcFServicesCache.registerSystemCodeForService(
975                     userId, Binder.getCallingUid(), service, systemCode);
976         }
977 
978         @Override
removeSystemCodeForService(int userId, ComponentName service)979         public boolean removeSystemCodeForService(int userId, ComponentName service)
980                 throws RemoteException {
981             NfcPermissions.validateUserId(userId);
982             NfcPermissions.enforceUserPermissions(mContext);
983             if (!isNfcFServiceInstalled(userId, service)) {
984                 return false;
985             }
986             return mNfcFServicesCache.removeSystemCodeForService(
987                     userId, Binder.getCallingUid(), service);
988         }
989 
990         @Override
getNfcid2ForService(int userId, ComponentName service)991         public String getNfcid2ForService(int userId, ComponentName service)
992                 throws RemoteException {
993             NfcPermissions.validateUserId(userId);
994             NfcPermissions.enforceUserPermissions(mContext);
995             if (!isNfcFServiceInstalled(userId, service)) {
996                 return null;
997             }
998             return mNfcFServicesCache.getNfcid2ForService(
999                     userId, Binder.getCallingUid(), service);
1000         }
1001 
1002         @Override
setNfcid2ForService(int userId, ComponentName service, String nfcid2)1003         public boolean setNfcid2ForService(int userId,
1004                 ComponentName service, String nfcid2) throws RemoteException {
1005             NfcPermissions.validateUserId(userId);
1006             NfcPermissions.enforceUserPermissions(mContext);
1007             if (!isNfcFServiceInstalled(userId, service)) {
1008                 return false;
1009             }
1010             return mNfcFServicesCache.setNfcid2ForService(
1011                     userId, Binder.getCallingUid(), service, nfcid2);
1012         }
1013 
1014         @Override
enableNfcFForegroundService(ComponentName service)1015         public boolean enableNfcFForegroundService(ComponentName service)
1016                 throws RemoteException {
1017             NfcPermissions.enforceUserPermissions(mContext);
1018             if (isNfcFServiceInstalled(UserHandle.getUserHandleForUid(
1019                     Binder.getCallingUid()).getIdentifier(), service)) {
1020                 return mEnabledNfcFServices.registerEnabledForegroundService(service,
1021                         Binder.getCallingUid());
1022             }
1023             return false;
1024         }
1025 
1026         @Override
disableNfcFForegroundService()1027         public boolean disableNfcFForegroundService() throws RemoteException {
1028             NfcPermissions.enforceUserPermissions(mContext);
1029             return mEnabledNfcFServices.unregisteredEnabledForegroundService(
1030                     Binder.getCallingUid());
1031         }
1032 
1033         @Override
getNfcFServices(int userId)1034         public List<NfcFServiceInfo> getNfcFServices(int userId)
1035                 throws RemoteException {
1036             NfcPermissions.validateProfileId(mContext, userId);
1037             NfcPermissions.enforceUserPermissions(mContext);
1038             return mNfcFServicesCache.getServices(userId);
1039         }
1040 
1041         @Override
getMaxNumOfRegisterableSystemCodes()1042         public int getMaxNumOfRegisterableSystemCodes()
1043                 throws RemoteException {
1044             NfcPermissions.enforceUserPermissions(mContext);
1045             return NfcService.getInstance().getLfT3tMax();
1046         }
1047     }
1048 
1049     @Override
onPreferredPaymentServiceChanged(int userId, ComponentName service)1050     public void onPreferredPaymentServiceChanged(int userId, ComponentName service) {
1051         Log.i(TAG, "onPreferredPaymentServiceChanged");
1052         ComponentName oldPreferredService = mAidCache.getPreferredService().second;
1053         mAidCache.onPreferredPaymentServiceChanged(userId, service);
1054         mHostEmulationManager.onPreferredPaymentServiceChanged(userId, service);
1055         ComponentName newPreferredService = mAidCache.getPreferredService().second;
1056 
1057         NfcService.getInstance().onPreferredPaymentChanged(
1058                     NfcAdapter.PREFERRED_PAYMENT_CHANGED);
1059         if (!Objects.equals(oldPreferredService, newPreferredService)) {
1060             updateForShouldDefaultToObserveMode(userId);
1061         }
1062     }
1063 
1064     @Override
onPreferredForegroundServiceChanged(int userId, ComponentName service)1065     public void onPreferredForegroundServiceChanged(int userId, ComponentName service) {
1066         Log.i(TAG, "onPreferredForegroundServiceChanged");
1067         ComponentName oldPreferredService = mAidCache.getPreferredService().second;
1068         mAidCache.onPreferredForegroundServiceChanged(userId, service);
1069         mHostEmulationManager.onPreferredForegroundServiceChanged(userId, service);
1070         ComponentName newPreferredService = mAidCache.getPreferredService().second;
1071 
1072         NfcService.getInstance().onPreferredPaymentChanged(
1073                 NfcAdapter.PREFERRED_PAYMENT_CHANGED);
1074         if (!Objects.equals(oldPreferredService, newPreferredService)) {
1075             updateForShouldDefaultToObserveMode(userId);
1076         }
1077     }
1078 
updateForShouldDefaultToObserveMode(int userId)1079     public void updateForShouldDefaultToObserveMode(int userId) {
1080         long token = Binder.clearCallingIdentity();
1081         try {
1082             if (!android.nfc.Flags.nfcObserveMode()) {
1083                 Log.d(TAG, "observe mode isn't enabled");
1084                 return;
1085             }
1086 
1087             NfcAdapter adapter = NfcAdapter.getDefaultAdapter(mContext);
1088             if (adapter == null) {
1089                 Log.e(TAG, "adapter is null, returning");
1090                 return;
1091             }
1092             ComponentName preferredService = mAidCache.getPreferredService().second;
1093             boolean enableObserveMode = mServiceCache.doesServiceShouldDefaultToObserveMode(userId,
1094                     preferredService);
1095             mHostEmulationManager.updateForShouldDefaultToObserveMode(enableObserveMode);
1096         } finally {
1097             Binder.restoreCallingIdentity(token);
1098         }
1099     }
1100 
onObserveModeStateChange(boolean enabled)1101     public void onObserveModeStateChange(boolean enabled) {
1102         mHostEmulationManager.onObserveModeStateChange(enabled);
1103     }
1104 
1105     @Override
onWalletRoleHolderChanged(String holder, int userId)1106     public void onWalletRoleHolderChanged(String holder, int userId) {
1107         mPreferredServices.onWalletRoleHolderChanged(holder, userId);
1108         mAidCache.onWalletRoleHolderChanged(holder, userId);
1109     }
1110 
1111     @Override
onEnabledForegroundNfcFServiceChanged(int userId, ComponentName service)1112     public void onEnabledForegroundNfcFServiceChanged(int userId, ComponentName service) {
1113         mT3tIdentifiersCache.onEnabledForegroundNfcFServiceChanged(userId, service);
1114         mHostNfcFEmulationManager.onEnabledForegroundNfcFServiceChanged(userId, service);
1115     }
1116 
getRegisteredAidCategory(String aid)1117     public String getRegisteredAidCategory(String aid) {
1118         RegisteredAidCache.AidResolveInfo resolvedInfo = mAidCache.resolveAid(aid);
1119         if (resolvedInfo != null) {
1120             return resolvedInfo.getCategory();
1121         }
1122         return "";
1123     }
1124 
isRequiresScreenOnServiceExist()1125     public boolean isRequiresScreenOnServiceExist() {
1126         return mAidCache.isRequiresScreenOnServiceExist();
1127     }
1128 
isPreferredServicePackageNameForUser(String packageName, int userId)1129     public boolean isPreferredServicePackageNameForUser(String packageName, int userId) {
1130         return mAidCache.isPreferredServicePackageNameForUser(packageName, userId);
1131     }
1132 
isHostCardEmulationActivated()1133     public boolean isHostCardEmulationActivated() {
1134         return mHostEmulationManager.isHostCardEmulationActivated();
1135     }
1136 }
1137