1 /*
2  * Copyright (C) 2008 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 package com.android.keyguard;
18 
19 import static android.content.Intent.ACTION_USER_UNLOCKED;
20 import static android.os.BatteryManager.BATTERY_HEALTH_UNKNOWN;
21 import static android.os.BatteryManager.BATTERY_STATUS_FULL;
22 import static android.os.BatteryManager.BATTERY_STATUS_UNKNOWN;
23 import static android.os.BatteryManager.EXTRA_HEALTH;
24 import static android.os.BatteryManager.EXTRA_LEVEL;
25 import static android.os.BatteryManager.EXTRA_MAX_CHARGING_CURRENT;
26 import static android.os.BatteryManager.EXTRA_MAX_CHARGING_VOLTAGE;
27 import static android.os.BatteryManager.EXTRA_PLUGGED;
28 import static android.os.BatteryManager.EXTRA_STATUS;
29 
30 import android.app.ActivityManager;
31 import android.app.AlarmManager;
32 import android.app.PendingIntent;
33 import android.app.UserSwitchObserver;
34 import android.app.admin.DevicePolicyManager;
35 import android.app.trust.TrustManager;
36 import android.content.BroadcastReceiver;
37 import android.content.ComponentName;
38 import android.content.Context;
39 import android.content.Intent;
40 import android.content.IntentFilter;
41 import android.content.pm.PackageManager;
42 import android.content.pm.ResolveInfo;
43 import android.database.ContentObserver;
44 import android.graphics.Bitmap;
45 import android.hardware.fingerprint.FingerprintManager;
46 import android.hardware.fingerprint.FingerprintManager.AuthenticationCallback;
47 import android.hardware.fingerprint.FingerprintManager.AuthenticationResult;
48 import android.media.AudioManager;
49 import android.os.BatteryManager;
50 import android.os.CancellationSignal;
51 import android.os.Handler;
52 import android.os.IRemoteCallback;
53 import android.os.Message;
54 import android.os.RemoteException;
55 import android.os.SystemClock;
56 import android.os.Trace;
57 import android.os.UserHandle;
58 import android.os.UserManager;
59 import android.provider.Settings;
60 import android.telephony.ServiceState;
61 import android.telephony.SubscriptionInfo;
62 import android.telephony.SubscriptionManager;
63 import android.telephony.SubscriptionManager.OnSubscriptionsChangedListener;
64 import android.telephony.TelephonyManager;
65 import android.util.ArraySet;
66 import android.util.Log;
67 import android.util.SparseBooleanArray;
68 import android.util.SparseIntArray;
69 
70 import com.google.android.collect.Lists;
71 
72 import com.android.internal.telephony.IccCardConstants;
73 import com.android.internal.telephony.IccCardConstants.State;
74 import com.android.internal.telephony.PhoneConstants;
75 import com.android.internal.telephony.TelephonyIntents;
76 import com.android.internal.widget.LockPatternUtils;
77 
78 import java.io.FileDescriptor;
79 import java.io.PrintWriter;
80 import java.lang.ref.WeakReference;
81 import java.util.ArrayList;
82 import java.util.HashMap;
83 import java.util.List;
84 import java.util.Map.Entry;
85 
86 /**
87  * Watches for updates that may be interesting to the keyguard, and provides
88  * the up to date information as well as a registration for callbacks that care
89  * to be updated.
90  *
91  * Note: under time crunch, this has been extended to include some stuff that
92  * doesn't really belong here.  see {@link #handleBatteryUpdate} where it shutdowns
93  * the device, and {@link #getFailedUnlockAttempts()}, {@link #reportFailedAttempt()}
94  * and {@link #clearFailedUnlockAttempts()}.  Maybe we should rename this 'KeyguardContext'...
95  */
96 public class KeyguardUpdateMonitor implements TrustManager.TrustListener {
97 
98     private static final String TAG = "KeyguardUpdateMonitor";
99     private static final boolean DEBUG = KeyguardConstants.DEBUG;
100     private static final boolean DEBUG_SIM_STATES = KeyguardConstants.DEBUG_SIM_STATES;
101     private static final int LOW_BATTERY_THRESHOLD = 20;
102 
103     private static final String ACTION_FACE_UNLOCK_STARTED
104             = "com.android.facelock.FACE_UNLOCK_STARTED";
105     private static final String ACTION_FACE_UNLOCK_STOPPED
106             = "com.android.facelock.FACE_UNLOCK_STOPPED";
107 
108     // Callback messages
109     private static final int MSG_TIME_UPDATE = 301;
110     private static final int MSG_BATTERY_UPDATE = 302;
111     private static final int MSG_SIM_STATE_CHANGE = 304;
112     private static final int MSG_RINGER_MODE_CHANGED = 305;
113     private static final int MSG_PHONE_STATE_CHANGED = 306;
114     private static final int MSG_DEVICE_PROVISIONED = 308;
115     private static final int MSG_DPM_STATE_CHANGED = 309;
116     private static final int MSG_USER_SWITCHING = 310;
117     private static final int MSG_KEYGUARD_RESET = 312;
118     private static final int MSG_BOOT_COMPLETED = 313;
119     private static final int MSG_USER_SWITCH_COMPLETE = 314;
120     private static final int MSG_USER_INFO_CHANGED = 317;
121     private static final int MSG_REPORT_EMERGENCY_CALL_ACTION = 318;
122     private static final int MSG_STARTED_WAKING_UP = 319;
123     private static final int MSG_FINISHED_GOING_TO_SLEEP = 320;
124     private static final int MSG_STARTED_GOING_TO_SLEEP = 321;
125     private static final int MSG_KEYGUARD_BOUNCER_CHANGED = 322;
126     private static final int MSG_FACE_UNLOCK_STATE_CHANGED = 327;
127     private static final int MSG_SIM_SUBSCRIPTION_INFO_CHANGED = 328;
128     private static final int MSG_AIRPLANE_MODE_CHANGED = 329;
129     private static final int MSG_SERVICE_STATE_CHANGE = 330;
130     private static final int MSG_SCREEN_TURNED_ON = 331;
131     private static final int MSG_SCREEN_TURNED_OFF = 332;
132     private static final int MSG_DREAMING_STATE_CHANGED = 333;
133     private static final int MSG_USER_UNLOCKED = 334;
134 
135     /** Fingerprint state: Not listening to fingerprint. */
136     private static final int FINGERPRINT_STATE_STOPPED = 0;
137 
138     /** Fingerprint state: Listening. */
139     private static final int FINGERPRINT_STATE_RUNNING = 1;
140 
141     /**
142      * Fingerprint state: Cancelling and waiting for the confirmation from FingerprintService to
143      * send us the confirmation that cancellation has happened.
144      */
145     private static final int FINGERPRINT_STATE_CANCELLING = 2;
146 
147     /**
148      * Fingerprint state: During cancelling we got another request to start listening, so when we
149      * receive the cancellation done signal, we should start listening again.
150      */
151     private static final int FINGERPRINT_STATE_CANCELLING_RESTARTING = 3;
152 
153     private static final int DEFAULT_CHARGING_VOLTAGE_MICRO_VOLT = 5000000;
154 
155     private static final ComponentName FALLBACK_HOME_COMPONENT = new ComponentName(
156             "com.android.settings", "com.android.settings.FallbackHome");
157 
158     private static KeyguardUpdateMonitor sInstance;
159 
160     private final Context mContext;
161     HashMap<Integer, SimData> mSimDatas = new HashMap<Integer, SimData>();
162     HashMap<Integer, ServiceState> mServiceStates = new HashMap<Integer, ServiceState>();
163 
164     private int mRingMode;
165     private int mPhoneState;
166     private boolean mKeyguardIsVisible;
167     private boolean mKeyguardGoingAway;
168     private boolean mGoingToSleep;
169     private boolean mBouncer;
170     private boolean mBootCompleted;
171     private boolean mNeedsSlowUnlockTransition;
172     private boolean mHasLockscreenWallpaper;
173 
174     // Device provisioning state
175     private boolean mDeviceProvisioned;
176 
177     // Battery status
178     private BatteryStatus mBatteryStatus;
179 
180     // Password attempts
181     private SparseIntArray mFailedAttempts = new SparseIntArray();
182 
183     private final StrongAuthTracker mStrongAuthTracker;
184 
185     private final ArrayList<WeakReference<KeyguardUpdateMonitorCallback>>
186             mCallbacks = Lists.newArrayList();
187     private ContentObserver mDeviceProvisionedObserver;
188 
189     private boolean mSwitchingUser;
190 
191     private boolean mDeviceInteractive;
192     private boolean mScreenOn;
193     private SubscriptionManager mSubscriptionManager;
194     private List<SubscriptionInfo> mSubscriptionInfo;
195     private TrustManager mTrustManager;
196     private UserManager mUserManager;
197     private int mFingerprintRunningState = FINGERPRINT_STATE_STOPPED;
198     private LockPatternUtils mLockPatternUtils;
199 
200     // If FP daemon dies, keyguard should retry after a short delay
201     private int mHardwareUnavailableRetryCount = 0;
202     private static final int HW_UNAVAILABLE_TIMEOUT = 3000; // ms
203     private static final int HW_UNAVAILABLE_RETRY_MAX = 3;
204 
205     private final Handler mHandler = new Handler() {
206         @Override
207         public void handleMessage(Message msg) {
208             switch (msg.what) {
209                 case MSG_TIME_UPDATE:
210                     handleTimeUpdate();
211                     break;
212                 case MSG_BATTERY_UPDATE:
213                     handleBatteryUpdate((BatteryStatus) msg.obj);
214                     break;
215                 case MSG_SIM_STATE_CHANGE:
216                     handleSimStateChange(msg.arg1, msg.arg2, (State) msg.obj);
217                     break;
218                 case MSG_RINGER_MODE_CHANGED:
219                     handleRingerModeChange(msg.arg1);
220                     break;
221                 case MSG_PHONE_STATE_CHANGED:
222                     handlePhoneStateChanged((String) msg.obj);
223                     break;
224                 case MSG_DEVICE_PROVISIONED:
225                     handleDeviceProvisioned();
226                     break;
227                 case MSG_DPM_STATE_CHANGED:
228                     handleDevicePolicyManagerStateChanged();
229                     break;
230                 case MSG_USER_SWITCHING:
231                     handleUserSwitching(msg.arg1, (IRemoteCallback) msg.obj);
232                     break;
233                 case MSG_USER_SWITCH_COMPLETE:
234                     handleUserSwitchComplete(msg.arg1);
235                     break;
236                 case MSG_KEYGUARD_RESET:
237                     handleKeyguardReset();
238                     break;
239                 case MSG_KEYGUARD_BOUNCER_CHANGED:
240                     handleKeyguardBouncerChanged(msg.arg1);
241                     break;
242                 case MSG_BOOT_COMPLETED:
243                     handleBootCompleted();
244                     break;
245                 case MSG_USER_INFO_CHANGED:
246                     handleUserInfoChanged(msg.arg1);
247                     break;
248                 case MSG_REPORT_EMERGENCY_CALL_ACTION:
249                     handleReportEmergencyCallAction();
250                     break;
251                 case MSG_STARTED_GOING_TO_SLEEP:
252                     handleStartedGoingToSleep(msg.arg1);
253                     break;
254                 case MSG_FINISHED_GOING_TO_SLEEP:
255                     handleFinishedGoingToSleep(msg.arg1);
256                     break;
257                 case MSG_STARTED_WAKING_UP:
258                     Trace.beginSection("KeyguardUpdateMonitor#handler MSG_STARTED_WAKING_UP");
259                     handleStartedWakingUp();
260                     Trace.endSection();
261                     break;
262                 case MSG_FACE_UNLOCK_STATE_CHANGED:
263                     Trace.beginSection("KeyguardUpdateMonitor#handler MSG_FACE_UNLOCK_STATE_CHANGED");
264                     handleFaceUnlockStateChanged(msg.arg1 != 0, msg.arg2);
265                     Trace.endSection();
266                     break;
267                 case MSG_SIM_SUBSCRIPTION_INFO_CHANGED:
268                     handleSimSubscriptionInfoChanged();
269                     break;
270                 case MSG_AIRPLANE_MODE_CHANGED:
271                     handleAirplaneModeChanged();
272                     break;
273                 case MSG_SERVICE_STATE_CHANGE:
274                     handleServiceStateChange(msg.arg1, (ServiceState) msg.obj);
275                     break;
276                 case MSG_SCREEN_TURNED_ON:
277                     handleScreenTurnedOn();
278                     break;
279                 case MSG_SCREEN_TURNED_OFF:
280                     Trace.beginSection("KeyguardUpdateMonitor#handler MSG_SCREEN_TURNED_ON");
281                     handleScreenTurnedOff();
282                     Trace.endSection();
283                     break;
284                 case MSG_DREAMING_STATE_CHANGED:
285                     handleDreamingStateChanged(msg.arg1);
286                     break;
287                 case MSG_USER_UNLOCKED:
288                     handleUserUnlocked();
289                     break;
290             }
291         }
292     };
293 
294     private OnSubscriptionsChangedListener mSubscriptionListener =
295             new OnSubscriptionsChangedListener() {
296         @Override
297         public void onSubscriptionsChanged() {
298             mHandler.sendEmptyMessage(MSG_SIM_SUBSCRIPTION_INFO_CHANGED);
299         }
300     };
301 
302     private SparseBooleanArray mUserHasTrust = new SparseBooleanArray();
303     private SparseBooleanArray mUserTrustIsManaged = new SparseBooleanArray();
304     private SparseBooleanArray mUserFingerprintAuthenticated = new SparseBooleanArray();
305     private SparseBooleanArray mUserFaceUnlockRunning = new SparseBooleanArray();
306 
307     private static int sCurrentUser;
308 
setCurrentUser(int currentUser)309     public synchronized static void setCurrentUser(int currentUser) {
310         sCurrentUser = currentUser;
311     }
312 
getCurrentUser()313     public synchronized static int getCurrentUser() {
314         return sCurrentUser;
315     }
316 
317     @Override
onTrustChanged(boolean enabled, int userId, int flags)318     public void onTrustChanged(boolean enabled, int userId, int flags) {
319         mUserHasTrust.put(userId, enabled);
320         for (int i = 0; i < mCallbacks.size(); i++) {
321             KeyguardUpdateMonitorCallback cb = mCallbacks.get(i).get();
322             if (cb != null) {
323                 cb.onTrustChanged(userId);
324                 if (enabled && flags != 0) {
325                     cb.onTrustGrantedWithFlags(flags, userId);
326                 }
327             }
328         }
329     }
330 
handleSimSubscriptionInfoChanged()331     protected void handleSimSubscriptionInfoChanged() {
332         if (DEBUG_SIM_STATES) {
333             Log.v(TAG, "onSubscriptionInfoChanged()");
334             List<SubscriptionInfo> sil = mSubscriptionManager.getActiveSubscriptionInfoList();
335             if (sil != null) {
336                 for (SubscriptionInfo subInfo : sil) {
337                     Log.v(TAG, "SubInfo:" + subInfo);
338                 }
339             } else {
340                 Log.v(TAG, "onSubscriptionInfoChanged: list is null");
341             }
342         }
343         List<SubscriptionInfo> subscriptionInfos = getSubscriptionInfo(true /* forceReload */);
344 
345         // Hack level over 9000: Because the subscription id is not yet valid when we see the
346         // first update in handleSimStateChange, we need to force refresh all all SIM states
347         // so the subscription id for them is consistent.
348         ArrayList<SubscriptionInfo> changedSubscriptions = new ArrayList<>();
349         for (int i = 0; i < subscriptionInfos.size(); i++) {
350             SubscriptionInfo info = subscriptionInfos.get(i);
351             boolean changed = refreshSimState(info.getSubscriptionId(), info.getSimSlotIndex());
352             if (changed) {
353                 changedSubscriptions.add(info);
354             }
355         }
356         for (int i = 0; i < changedSubscriptions.size(); i++) {
357             SimData data = mSimDatas.get(changedSubscriptions.get(i).getSubscriptionId());
358             for (int j = 0; j < mCallbacks.size(); j++) {
359                 KeyguardUpdateMonitorCallback cb = mCallbacks.get(j).get();
360                 if (cb != null) {
361                     cb.onSimStateChanged(data.subId, data.slotId, data.simState);
362                 }
363             }
364         }
365         for (int j = 0; j < mCallbacks.size(); j++) {
366             KeyguardUpdateMonitorCallback cb = mCallbacks.get(j).get();
367             if (cb != null) {
368                 cb.onRefreshCarrierInfo();
369             }
370         }
371     }
372 
handleAirplaneModeChanged()373     private void handleAirplaneModeChanged() {
374         for (int j = 0; j < mCallbacks.size(); j++) {
375             KeyguardUpdateMonitorCallback cb = mCallbacks.get(j).get();
376             if (cb != null) {
377                 cb.onRefreshCarrierInfo();
378             }
379         }
380     }
381 
382     /** @return List of SubscriptionInfo records, maybe empty but never null */
getSubscriptionInfo(boolean forceReload)383     public List<SubscriptionInfo> getSubscriptionInfo(boolean forceReload) {
384         List<SubscriptionInfo> sil = mSubscriptionInfo;
385         if (sil == null || forceReload) {
386             sil = mSubscriptionManager.getActiveSubscriptionInfoList();
387         }
388         if (sil == null) {
389             // getActiveSubscriptionInfoList was null callers expect an empty list.
390             mSubscriptionInfo = new ArrayList<SubscriptionInfo>();
391         } else {
392             mSubscriptionInfo = sil;
393         }
394         return mSubscriptionInfo;
395     }
396 
397     @Override
onTrustManagedChanged(boolean managed, int userId)398     public void onTrustManagedChanged(boolean managed, int userId) {
399         mUserTrustIsManaged.put(userId, managed);
400 
401         for (int i = 0; i < mCallbacks.size(); i++) {
402             KeyguardUpdateMonitorCallback cb = mCallbacks.get(i).get();
403             if (cb != null) {
404                 cb.onTrustManagedChanged(userId);
405             }
406         }
407     }
408 
409     /**
410      * Updates KeyguardUpdateMonitor's internal state to know if keyguard is goingAway
411      * @param goingAway
412      */
setKeyguardGoingAway(boolean goingAway)413     public void setKeyguardGoingAway(boolean goingAway) {
414         mKeyguardGoingAway = goingAway;
415     }
416 
onFingerprintAuthenticated(int userId)417     private void onFingerprintAuthenticated(int userId) {
418         Trace.beginSection("KeyGuardUpdateMonitor#onFingerPrintAuthenticated");
419         mUserFingerprintAuthenticated.put(userId, true);
420         // Don't send cancel if authentication succeeds
421         mFingerprintCancelSignal = null;
422         for (int i = 0; i < mCallbacks.size(); i++) {
423             KeyguardUpdateMonitorCallback cb = mCallbacks.get(i).get();
424             if (cb != null) {
425                 cb.onFingerprintAuthenticated(userId);
426             }
427         }
428         Trace.endSection();
429     }
430 
handleFingerprintAuthFailed()431     private void handleFingerprintAuthFailed() {
432         for (int i = 0; i < mCallbacks.size(); i++) {
433             KeyguardUpdateMonitorCallback cb = mCallbacks.get(i).get();
434             if (cb != null) {
435                 cb.onFingerprintAuthFailed();
436             }
437         }
438         handleFingerprintHelp(-1, mContext.getString(R.string.fingerprint_not_recognized));
439     }
440 
handleFingerprintAcquired(int acquireInfo)441     private void handleFingerprintAcquired(int acquireInfo) {
442         if (acquireInfo != FingerprintManager.FINGERPRINT_ACQUIRED_GOOD) {
443             return;
444         }
445         for (int i = 0; i < mCallbacks.size(); i++) {
446             KeyguardUpdateMonitorCallback cb = mCallbacks.get(i).get();
447             if (cb != null) {
448                 cb.onFingerprintAcquired();
449             }
450         }
451     }
452 
handleFingerprintAuthenticated(int authUserId)453     private void handleFingerprintAuthenticated(int authUserId) {
454         Trace.beginSection("KeyGuardUpdateMonitor#handlerFingerPrintAuthenticated");
455         try {
456             final int userId;
457             try {
458                 userId = ActivityManager.getService().getCurrentUser().id;
459             } catch (RemoteException e) {
460                 Log.e(TAG, "Failed to get current user id: ", e);
461                 return;
462             }
463             if (userId != authUserId) {
464                 Log.d(TAG, "Fingerprint authenticated for wrong user: " + authUserId);
465                 return;
466             }
467             if (isFingerprintDisabled(userId)) {
468                 Log.d(TAG, "Fingerprint disabled by DPM for userId: " + userId);
469                 return;
470             }
471             onFingerprintAuthenticated(userId);
472         } finally {
473             setFingerprintRunningState(FINGERPRINT_STATE_STOPPED);
474         }
475         Trace.endSection();
476     }
477 
handleFingerprintHelp(int msgId, String helpString)478     private void handleFingerprintHelp(int msgId, String helpString) {
479         for (int i = 0; i < mCallbacks.size(); i++) {
480             KeyguardUpdateMonitorCallback cb = mCallbacks.get(i).get();
481             if (cb != null) {
482                 cb.onFingerprintHelp(msgId, helpString);
483             }
484         }
485     }
486 
487     private Runnable mRetryFingerprintAuthentication = new Runnable() {
488         @Override
489         public void run() {
490             Log.w(TAG, "Retrying fingerprint after HW unavailable, attempt " +
491                     mHardwareUnavailableRetryCount);
492             updateFingerprintListeningState();
493         }
494     };
495 
handleFingerprintError(int msgId, String errString)496     private void handleFingerprintError(int msgId, String errString) {
497         if (msgId == FingerprintManager.FINGERPRINT_ERROR_CANCELED
498                 && mFingerprintRunningState == FINGERPRINT_STATE_CANCELLING_RESTARTING) {
499             setFingerprintRunningState(FINGERPRINT_STATE_STOPPED);
500             startListeningForFingerprint();
501         } else {
502             setFingerprintRunningState(FINGERPRINT_STATE_STOPPED);
503         }
504 
505         if (msgId == FingerprintManager.FINGERPRINT_ERROR_HW_UNAVAILABLE) {
506             if (mHardwareUnavailableRetryCount < HW_UNAVAILABLE_RETRY_MAX) {
507                 mHardwareUnavailableRetryCount++;
508                 mHandler.removeCallbacks(mRetryFingerprintAuthentication);
509                 mHandler.postDelayed(mRetryFingerprintAuthentication, HW_UNAVAILABLE_TIMEOUT);
510             }
511         }
512 
513         if (msgId == FingerprintManager.FINGERPRINT_ERROR_LOCKOUT_PERMANENT) {
514             mLockPatternUtils.requireStrongAuth(
515                     LockPatternUtils.StrongAuthTracker.STRONG_AUTH_REQUIRED_AFTER_LOCKOUT,
516                     getCurrentUser());
517         }
518 
519         for (int i = 0; i < mCallbacks.size(); i++) {
520             KeyguardUpdateMonitorCallback cb = mCallbacks.get(i).get();
521             if (cb != null) {
522                 cb.onFingerprintError(msgId, errString);
523             }
524         }
525     }
526 
handleFingerprintLockoutReset()527     private void handleFingerprintLockoutReset() {
528         updateFingerprintListeningState();
529     }
530 
setFingerprintRunningState(int fingerprintRunningState)531     private void setFingerprintRunningState(int fingerprintRunningState) {
532         boolean wasRunning = mFingerprintRunningState == FINGERPRINT_STATE_RUNNING;
533         boolean isRunning = fingerprintRunningState == FINGERPRINT_STATE_RUNNING;
534         mFingerprintRunningState = fingerprintRunningState;
535 
536         // Clients of KeyguardUpdateMonitor don't care about the internal state about the
537         // asynchronousness of the cancel cycle. So only notify them if the actualy running state
538         // has changed.
539         if (wasRunning != isRunning) {
540             notifyFingerprintRunningStateChanged();
541         }
542     }
543 
notifyFingerprintRunningStateChanged()544     private void notifyFingerprintRunningStateChanged() {
545         for (int i = 0; i < mCallbacks.size(); i++) {
546             KeyguardUpdateMonitorCallback cb = mCallbacks.get(i).get();
547             if (cb != null) {
548                 cb.onFingerprintRunningStateChanged(isFingerprintDetectionRunning());
549             }
550         }
551     }
handleFaceUnlockStateChanged(boolean running, int userId)552     private void handleFaceUnlockStateChanged(boolean running, int userId) {
553         mUserFaceUnlockRunning.put(userId, running);
554         for (int i = 0; i < mCallbacks.size(); i++) {
555             KeyguardUpdateMonitorCallback cb = mCallbacks.get(i).get();
556             if (cb != null) {
557                 cb.onFaceUnlockStateChanged(running, userId);
558             }
559         }
560     }
561 
isFaceUnlockRunning(int userId)562     public boolean isFaceUnlockRunning(int userId) {
563         return mUserFaceUnlockRunning.get(userId);
564     }
565 
isFingerprintDetectionRunning()566     public boolean isFingerprintDetectionRunning() {
567         return mFingerprintRunningState == FINGERPRINT_STATE_RUNNING;
568     }
569 
isTrustDisabled(int userId)570     private boolean isTrustDisabled(int userId) {
571         // Don't allow trust agent if device is secured with a SIM PIN. This is here
572         // mainly because there's no other way to prompt the user to enter their SIM PIN
573         // once they get past the keyguard screen.
574         final boolean disabledBySimPin = isSimPinSecure();
575         return disabledBySimPin;
576     }
577 
isFingerprintDisabled(int userId)578     private boolean isFingerprintDisabled(int userId) {
579         final DevicePolicyManager dpm =
580                 (DevicePolicyManager) mContext.getSystemService(Context.DEVICE_POLICY_SERVICE);
581         return dpm != null && (dpm.getKeyguardDisabledFeatures(null, userId)
582                     & DevicePolicyManager.KEYGUARD_DISABLE_FINGERPRINT) != 0
583                 || isSimPinSecure();
584     }
585 
getUserCanSkipBouncer(int userId)586     public boolean getUserCanSkipBouncer(int userId) {
587         return getUserHasTrust(userId) || (mUserFingerprintAuthenticated.get(userId)
588                 && isUnlockingWithFingerprintAllowed());
589     }
590 
getUserHasTrust(int userId)591     public boolean getUserHasTrust(int userId) {
592         return !isTrustDisabled(userId) && mUserHasTrust.get(userId);
593     }
594 
getUserTrustIsManaged(int userId)595     public boolean getUserTrustIsManaged(int userId) {
596         return mUserTrustIsManaged.get(userId) && !isTrustDisabled(userId);
597     }
598 
isUnlockingWithFingerprintAllowed()599     public boolean isUnlockingWithFingerprintAllowed() {
600         return mStrongAuthTracker.isUnlockingWithFingerprintAllowed();
601     }
602 
needsSlowUnlockTransition()603     public boolean needsSlowUnlockTransition() {
604         return mNeedsSlowUnlockTransition;
605     }
606 
getStrongAuthTracker()607     public StrongAuthTracker getStrongAuthTracker() {
608         return mStrongAuthTracker;
609     }
610 
reportSuccessfulStrongAuthUnlockAttempt()611     public void reportSuccessfulStrongAuthUnlockAttempt() {
612         if (mFpm != null) {
613             byte[] token = null; /* TODO: pass real auth token once fp HAL supports it */
614             mFpm.resetTimeout(token);
615         }
616     }
617 
notifyStrongAuthStateChanged(int userId)618     private void notifyStrongAuthStateChanged(int userId) {
619         for (int i = 0; i < mCallbacks.size(); i++) {
620             KeyguardUpdateMonitorCallback cb = mCallbacks.get(i).get();
621             if (cb != null) {
622                 cb.onStrongAuthStateChanged(userId);
623             }
624         }
625     }
626 
isScreenOn()627     public boolean isScreenOn() {
628         return mScreenOn;
629     }
630 
631     static class DisplayClientState {
632         public int clientGeneration;
633         public boolean clearing;
634         public PendingIntent intent;
635         public int playbackState;
636         public long playbackEventTime;
637     }
638 
639     private DisplayClientState mDisplayClientState = new DisplayClientState();
640 
641     private final BroadcastReceiver mBroadcastReceiver = new BroadcastReceiver() {
642 
643         @Override
644         public void onReceive(Context context, Intent intent) {
645             final String action = intent.getAction();
646             if (DEBUG) Log.d(TAG, "received broadcast " + action);
647 
648             if (Intent.ACTION_TIME_TICK.equals(action)
649                     || Intent.ACTION_TIME_CHANGED.equals(action)
650                     || Intent.ACTION_TIMEZONE_CHANGED.equals(action)) {
651                 mHandler.sendEmptyMessage(MSG_TIME_UPDATE);
652             } else if (Intent.ACTION_BATTERY_CHANGED.equals(action)) {
653                 final int status = intent.getIntExtra(EXTRA_STATUS, BATTERY_STATUS_UNKNOWN);
654                 final int plugged = intent.getIntExtra(EXTRA_PLUGGED, 0);
655                 final int level = intent.getIntExtra(EXTRA_LEVEL, 0);
656                 final int health = intent.getIntExtra(EXTRA_HEALTH, BATTERY_HEALTH_UNKNOWN);
657 
658                 final int maxChargingMicroAmp = intent.getIntExtra(EXTRA_MAX_CHARGING_CURRENT, -1);
659                 int maxChargingMicroVolt = intent.getIntExtra(EXTRA_MAX_CHARGING_VOLTAGE, -1);
660                 final int maxChargingMicroWatt;
661 
662                 if (maxChargingMicroVolt <= 0) {
663                     maxChargingMicroVolt = DEFAULT_CHARGING_VOLTAGE_MICRO_VOLT;
664                 }
665                 if (maxChargingMicroAmp > 0) {
666                     // Calculating muW = muA * muV / (10^6 mu^2 / mu); splitting up the divisor
667                     // to maintain precision equally on both factors.
668                     maxChargingMicroWatt = (maxChargingMicroAmp / 1000)
669                             * (maxChargingMicroVolt / 1000);
670                 } else {
671                     maxChargingMicroWatt = -1;
672                 }
673                 final Message msg = mHandler.obtainMessage(
674                         MSG_BATTERY_UPDATE, new BatteryStatus(status, level, plugged, health,
675                                 maxChargingMicroWatt));
676                 mHandler.sendMessage(msg);
677             } else if (TelephonyIntents.ACTION_SIM_STATE_CHANGED.equals(action)) {
678                 SimData args = SimData.fromIntent(intent);
679                 if (DEBUG_SIM_STATES) {
680                     Log.v(TAG, "action " + action
681                         + " state: " + intent.getStringExtra(IccCardConstants.INTENT_KEY_ICC_STATE)
682                         + " slotId: " + args.slotId + " subid: " + args.subId);
683                 }
684                 mHandler.obtainMessage(MSG_SIM_STATE_CHANGE, args.subId, args.slotId, args.simState)
685                         .sendToTarget();
686             } else if (AudioManager.RINGER_MODE_CHANGED_ACTION.equals(action)) {
687                 mHandler.sendMessage(mHandler.obtainMessage(MSG_RINGER_MODE_CHANGED,
688                         intent.getIntExtra(AudioManager.EXTRA_RINGER_MODE, -1), 0));
689             } else if (TelephonyManager.ACTION_PHONE_STATE_CHANGED.equals(action)) {
690                 String state = intent.getStringExtra(TelephonyManager.EXTRA_STATE);
691                 mHandler.sendMessage(mHandler.obtainMessage(MSG_PHONE_STATE_CHANGED, state));
692             } else if (Intent.ACTION_AIRPLANE_MODE_CHANGED.equals(action)) {
693                 mHandler.sendEmptyMessage(MSG_AIRPLANE_MODE_CHANGED);
694             } else if (Intent.ACTION_BOOT_COMPLETED.equals(action)) {
695                 dispatchBootCompleted();
696             } else if (TelephonyIntents.ACTION_SERVICE_STATE_CHANGED.equals(action)) {
697                 ServiceState serviceState = ServiceState.newFromBundle(intent.getExtras());
698                 int subId = intent.getIntExtra(PhoneConstants.SUBSCRIPTION_KEY,
699                         SubscriptionManager.INVALID_SUBSCRIPTION_ID);
700                 if (DEBUG) {
701                     Log.v(TAG, "action " + action + " serviceState=" + serviceState + " subId="
702                             + subId);
703                 }
704                 mHandler.sendMessage(
705                         mHandler.obtainMessage(MSG_SERVICE_STATE_CHANGE, subId, 0, serviceState));
706             }
707         }
708     };
709 
710     private final BroadcastReceiver mBroadcastAllReceiver = new BroadcastReceiver() {
711 
712         @Override
713         public void onReceive(Context context, Intent intent) {
714             final String action = intent.getAction();
715             if (AlarmManager.ACTION_NEXT_ALARM_CLOCK_CHANGED.equals(action)) {
716                 mHandler.sendEmptyMessage(MSG_TIME_UPDATE);
717             } else if (Intent.ACTION_USER_INFO_CHANGED.equals(action)) {
718                 mHandler.sendMessage(mHandler.obtainMessage(MSG_USER_INFO_CHANGED,
719                         intent.getIntExtra(Intent.EXTRA_USER_HANDLE, getSendingUserId()), 0));
720             } else if (ACTION_FACE_UNLOCK_STARTED.equals(action)) {
721                 Trace.beginSection("KeyguardUpdateMonitor.mBroadcastAllReceiver#onReceive ACTION_FACE_UNLOCK_STARTED");
722                 mHandler.sendMessage(mHandler.obtainMessage(MSG_FACE_UNLOCK_STATE_CHANGED, 1,
723                         getSendingUserId()));
724                 Trace.endSection();
725             } else if (ACTION_FACE_UNLOCK_STOPPED.equals(action)) {
726                 mHandler.sendMessage(mHandler.obtainMessage(MSG_FACE_UNLOCK_STATE_CHANGED, 0,
727                         getSendingUserId()));
728             } else if (DevicePolicyManager.ACTION_DEVICE_POLICY_MANAGER_STATE_CHANGED
729                     .equals(action)) {
730                 mHandler.sendEmptyMessage(MSG_DPM_STATE_CHANGED);
731             } else if (ACTION_USER_UNLOCKED.equals(action)) {
732                 mHandler.sendEmptyMessage(MSG_USER_UNLOCKED);
733             }
734         }
735     };
736 
737     private final FingerprintManager.LockoutResetCallback mLockoutResetCallback
738             = new FingerprintManager.LockoutResetCallback() {
739         @Override
740         public void onLockoutReset() {
741             handleFingerprintLockoutReset();
742         }
743     };
744 
745     private FingerprintManager.AuthenticationCallback mAuthenticationCallback
746             = new AuthenticationCallback() {
747 
748         @Override
749         public void onAuthenticationFailed() {
750             handleFingerprintAuthFailed();
751         };
752 
753         @Override
754         public void onAuthenticationSucceeded(AuthenticationResult result) {
755             Trace.beginSection("KeyguardUpdateMonitor#onAuthenticationSucceeded");
756             handleFingerprintAuthenticated(result.getUserId());
757             Trace.endSection();
758         }
759 
760         @Override
761         public void onAuthenticationHelp(int helpMsgId, CharSequence helpString) {
762             handleFingerprintHelp(helpMsgId, helpString.toString());
763         }
764 
765         @Override
766         public void onAuthenticationError(int errMsgId, CharSequence errString) {
767             handleFingerprintError(errMsgId, errString.toString());
768         }
769 
770         @Override
771         public void onAuthenticationAcquired(int acquireInfo) {
772             handleFingerprintAcquired(acquireInfo);
773         }
774     };
775     private CancellationSignal mFingerprintCancelSignal;
776     private FingerprintManager mFpm;
777 
778     /**
779      * When we receive a
780      * {@link com.android.internal.telephony.TelephonyIntents#ACTION_SIM_STATE_CHANGED} broadcast,
781      * and then pass a result via our handler to {@link KeyguardUpdateMonitor#handleSimStateChange},
782      * we need a single object to pass to the handler.  This class helps decode
783      * the intent and provide a {@link SimCard.State} result.
784      */
785     private static class SimData {
786         public State simState;
787         public int slotId;
788         public int subId;
789 
SimData(State state, int slot, int id)790         SimData(State state, int slot, int id) {
791             simState = state;
792             slotId = slot;
793             subId = id;
794         }
795 
fromIntent(Intent intent)796         static SimData fromIntent(Intent intent) {
797             State state;
798             if (!TelephonyIntents.ACTION_SIM_STATE_CHANGED.equals(intent.getAction())) {
799                 throw new IllegalArgumentException("only handles intent ACTION_SIM_STATE_CHANGED");
800             }
801             String stateExtra = intent.getStringExtra(IccCardConstants.INTENT_KEY_ICC_STATE);
802             int slotId = intent.getIntExtra(PhoneConstants.SLOT_KEY, 0);
803             int subId = intent.getIntExtra(PhoneConstants.SUBSCRIPTION_KEY,
804                     SubscriptionManager.INVALID_SUBSCRIPTION_ID);
805             if (IccCardConstants.INTENT_VALUE_ICC_ABSENT.equals(stateExtra)) {
806                 final String absentReason = intent
807                     .getStringExtra(IccCardConstants.INTENT_KEY_LOCKED_REASON);
808 
809                 if (IccCardConstants.INTENT_VALUE_ABSENT_ON_PERM_DISABLED.equals(
810                         absentReason)) {
811                     state = IccCardConstants.State.PERM_DISABLED;
812                 } else {
813                     state = IccCardConstants.State.ABSENT;
814                 }
815             } else if (IccCardConstants.INTENT_VALUE_ICC_READY.equals(stateExtra)) {
816                 state = IccCardConstants.State.READY;
817             } else if (IccCardConstants.INTENT_VALUE_ICC_LOCKED.equals(stateExtra)) {
818                 final String lockedReason = intent
819                         .getStringExtra(IccCardConstants.INTENT_KEY_LOCKED_REASON);
820                 if (IccCardConstants.INTENT_VALUE_LOCKED_ON_PIN.equals(lockedReason)) {
821                     state = IccCardConstants.State.PIN_REQUIRED;
822                 } else if (IccCardConstants.INTENT_VALUE_LOCKED_ON_PUK.equals(lockedReason)) {
823                     state = IccCardConstants.State.PUK_REQUIRED;
824                 } else {
825                     state = IccCardConstants.State.UNKNOWN;
826                 }
827             } else if (IccCardConstants.INTENT_VALUE_LOCKED_NETWORK.equals(stateExtra)) {
828                 state = IccCardConstants.State.NETWORK_LOCKED;
829             } else if (IccCardConstants.INTENT_VALUE_ICC_LOADED.equals(stateExtra)
830                         || IccCardConstants.INTENT_VALUE_ICC_IMSI.equals(stateExtra)) {
831                 // This is required because telephony doesn't return to "READY" after
832                 // these state transitions. See bug 7197471.
833                 state = IccCardConstants.State.READY;
834             } else {
835                 state = IccCardConstants.State.UNKNOWN;
836             }
837             return new SimData(state, slotId, subId);
838         }
839 
840         @Override
toString()841         public String toString() {
842             return "SimData{state=" + simState + ",slotId=" + slotId + ",subId=" + subId + "}";
843         }
844     }
845 
846     public static class BatteryStatus {
847         public static final int CHARGING_UNKNOWN = -1;
848         public static final int CHARGING_SLOWLY = 0;
849         public static final int CHARGING_REGULAR = 1;
850         public static final int CHARGING_FAST = 2;
851 
852         public final int status;
853         public final int level;
854         public final int plugged;
855         public final int health;
856         public final int maxChargingWattage;
BatteryStatus(int status, int level, int plugged, int health, int maxChargingWattage)857         public BatteryStatus(int status, int level, int plugged, int health,
858                 int maxChargingWattage) {
859             this.status = status;
860             this.level = level;
861             this.plugged = plugged;
862             this.health = health;
863             this.maxChargingWattage = maxChargingWattage;
864         }
865 
866         /**
867          * Determine whether the device is plugged in (USB, power, or wireless).
868          * @return true if the device is plugged in.
869          */
isPluggedIn()870         public boolean isPluggedIn() {
871             return plugged == BatteryManager.BATTERY_PLUGGED_AC
872                     || plugged == BatteryManager.BATTERY_PLUGGED_USB
873                     || plugged == BatteryManager.BATTERY_PLUGGED_WIRELESS;
874         }
875 
876         /**
877          * Whether or not the device is charged. Note that some devices never return 100% for
878          * battery level, so this allows either battery level or status to determine if the
879          * battery is charged.
880          * @return true if the device is charged
881          */
isCharged()882         public boolean isCharged() {
883             return status == BATTERY_STATUS_FULL || level >= 100;
884         }
885 
886         /**
887          * Whether battery is low and needs to be charged.
888          * @return true if battery is low
889          */
isBatteryLow()890         public boolean isBatteryLow() {
891             return level < LOW_BATTERY_THRESHOLD;
892         }
893 
getChargingSpeed(int slowThreshold, int fastThreshold)894         public final int getChargingSpeed(int slowThreshold, int fastThreshold) {
895             return maxChargingWattage <= 0 ? CHARGING_UNKNOWN :
896                     maxChargingWattage < slowThreshold ? CHARGING_SLOWLY :
897                     maxChargingWattage > fastThreshold ? CHARGING_FAST :
898                     CHARGING_REGULAR;
899         }
900     }
901 
902     public class StrongAuthTracker extends LockPatternUtils.StrongAuthTracker {
StrongAuthTracker(Context context)903         public StrongAuthTracker(Context context) {
904             super(context);
905         }
906 
isUnlockingWithFingerprintAllowed()907         public boolean isUnlockingWithFingerprintAllowed() {
908             int userId = getCurrentUser();
909             return isFingerprintAllowedForUser(userId);
910         }
911 
hasUserAuthenticatedSinceBoot()912         public boolean hasUserAuthenticatedSinceBoot() {
913             int userId = getCurrentUser();
914             return (getStrongAuthForUser(userId)
915                     & STRONG_AUTH_REQUIRED_AFTER_BOOT) == 0;
916         }
917 
918         @Override
onStrongAuthRequiredChanged(int userId)919         public void onStrongAuthRequiredChanged(int userId) {
920             notifyStrongAuthStateChanged(userId);
921         }
922     }
923 
getInstance(Context context)924     public static KeyguardUpdateMonitor getInstance(Context context) {
925         if (sInstance == null) {
926             sInstance = new KeyguardUpdateMonitor(context);
927         }
928         return sInstance;
929     }
930 
handleStartedWakingUp()931     protected void handleStartedWakingUp() {
932         Trace.beginSection("KeyguardUpdateMonitor#handleStartedWakingUp");
933         updateFingerprintListeningState();
934         final int count = mCallbacks.size();
935         for (int i = 0; i < count; i++) {
936             KeyguardUpdateMonitorCallback cb = mCallbacks.get(i).get();
937             if (cb != null) {
938                 cb.onStartedWakingUp();
939             }
940         }
941         Trace.endSection();
942     }
943 
handleStartedGoingToSleep(int arg1)944     protected void handleStartedGoingToSleep(int arg1) {
945         clearFingerprintRecognized();
946         final int count = mCallbacks.size();
947         for (int i = 0; i < count; i++) {
948             KeyguardUpdateMonitorCallback cb = mCallbacks.get(i).get();
949             if (cb != null) {
950                 cb.onStartedGoingToSleep(arg1);
951             }
952         }
953         mGoingToSleep = true;
954         updateFingerprintListeningState();
955     }
956 
handleFinishedGoingToSleep(int arg1)957     protected void handleFinishedGoingToSleep(int arg1) {
958         mGoingToSleep = false;
959         final int count = mCallbacks.size();
960         for (int i = 0; i < count; i++) {
961             KeyguardUpdateMonitorCallback cb = mCallbacks.get(i).get();
962             if (cb != null) {
963                 cb.onFinishedGoingToSleep(arg1);
964             }
965         }
966         updateFingerprintListeningState();
967     }
968 
handleScreenTurnedOn()969     private void handleScreenTurnedOn() {
970         final int count = mCallbacks.size();
971         for (int i = 0; i < count; i++) {
972             KeyguardUpdateMonitorCallback cb = mCallbacks.get(i).get();
973             if (cb != null) {
974                 cb.onScreenTurnedOn();
975             }
976         }
977     }
978 
handleScreenTurnedOff()979     private void handleScreenTurnedOff() {
980         mHardwareUnavailableRetryCount = 0;
981         final int count = mCallbacks.size();
982         for (int i = 0; i < count; i++) {
983             KeyguardUpdateMonitorCallback cb = mCallbacks.get(i).get();
984             if (cb != null) {
985                 cb.onScreenTurnedOff();
986             }
987         }
988     }
989 
handleDreamingStateChanged(int dreamStart)990     private void handleDreamingStateChanged(int dreamStart) {
991         final int count = mCallbacks.size();
992         boolean showingDream = dreamStart == 1;
993         for (int i = 0; i < count; i++) {
994             KeyguardUpdateMonitorCallback cb = mCallbacks.get(i).get();
995             if (cb != null) {
996                 cb.onDreamingStateChanged(showingDream);
997             }
998         }
999     }
1000 
1001     /**
1002      * IMPORTANT: Must be called from UI thread.
1003      */
dispatchSetBackground(Bitmap bmp)1004     public void dispatchSetBackground(Bitmap bmp) {
1005         if (DEBUG) Log.d(TAG, "dispatchSetBackground");
1006         final int count = mCallbacks.size();
1007         for (int i = 0; i < count; i++) {
1008             KeyguardUpdateMonitorCallback cb = mCallbacks.get(i).get();
1009             if (cb != null) {
1010                 cb.onSetBackground(bmp);
1011             }
1012         }
1013     }
1014 
handleUserInfoChanged(int userId)1015     private void handleUserInfoChanged(int userId) {
1016         for (int i = 0; i < mCallbacks.size(); i++) {
1017             KeyguardUpdateMonitorCallback cb = mCallbacks.get(i).get();
1018             if (cb != null) {
1019                 cb.onUserInfoChanged(userId);
1020             }
1021         }
1022     }
1023 
handleUserUnlocked()1024     private void handleUserUnlocked() {
1025         mNeedsSlowUnlockTransition = resolveNeedsSlowUnlockTransition();
1026         for (int i = 0; i < mCallbacks.size(); i++) {
1027             KeyguardUpdateMonitorCallback cb = mCallbacks.get(i).get();
1028             if (cb != null) {
1029                 cb.onUserUnlocked();
1030             }
1031         }
1032     }
1033 
KeyguardUpdateMonitor(Context context)1034     private KeyguardUpdateMonitor(Context context) {
1035         mContext = context;
1036         mSubscriptionManager = SubscriptionManager.from(context);
1037         mDeviceProvisioned = isDeviceProvisionedInSettingsDb();
1038         mStrongAuthTracker = new StrongAuthTracker(context);
1039 
1040         // Since device can't be un-provisioned, we only need to register a content observer
1041         // to update mDeviceProvisioned when we are...
1042         if (!mDeviceProvisioned) {
1043             watchForDeviceProvisioning();
1044         }
1045 
1046         // Take a guess at initial SIM state, battery status and PLMN until we get an update
1047         mBatteryStatus = new BatteryStatus(BATTERY_STATUS_UNKNOWN, 100, 0, 0, 0);
1048 
1049         // Watch for interesting updates
1050         final IntentFilter filter = new IntentFilter();
1051         filter.addAction(Intent.ACTION_TIME_TICK);
1052         filter.addAction(Intent.ACTION_TIME_CHANGED);
1053         filter.addAction(Intent.ACTION_BATTERY_CHANGED);
1054         filter.addAction(Intent.ACTION_TIMEZONE_CHANGED);
1055         filter.addAction(Intent.ACTION_AIRPLANE_MODE_CHANGED);
1056         filter.addAction(TelephonyIntents.ACTION_SIM_STATE_CHANGED);
1057         filter.addAction(TelephonyIntents.ACTION_SERVICE_STATE_CHANGED);
1058         filter.addAction(TelephonyManager.ACTION_PHONE_STATE_CHANGED);
1059         filter.addAction(AudioManager.RINGER_MODE_CHANGED_ACTION);
1060         context.registerReceiver(mBroadcastReceiver, filter);
1061 
1062         final IntentFilter bootCompleteFilter = new IntentFilter();
1063         bootCompleteFilter.setPriority(IntentFilter.SYSTEM_HIGH_PRIORITY);
1064         bootCompleteFilter.addAction(Intent.ACTION_BOOT_COMPLETED);
1065         context.registerReceiver(mBroadcastReceiver, bootCompleteFilter);
1066 
1067         final IntentFilter allUserFilter = new IntentFilter();
1068         allUserFilter.addAction(Intent.ACTION_USER_INFO_CHANGED);
1069         allUserFilter.addAction(AlarmManager.ACTION_NEXT_ALARM_CLOCK_CHANGED);
1070         allUserFilter.addAction(ACTION_FACE_UNLOCK_STARTED);
1071         allUserFilter.addAction(ACTION_FACE_UNLOCK_STOPPED);
1072         allUserFilter.addAction(DevicePolicyManager.ACTION_DEVICE_POLICY_MANAGER_STATE_CHANGED);
1073         allUserFilter.addAction(ACTION_USER_UNLOCKED);
1074         context.registerReceiverAsUser(mBroadcastAllReceiver, UserHandle.ALL, allUserFilter,
1075                 null, null);
1076 
1077         mSubscriptionManager.addOnSubscriptionsChangedListener(mSubscriptionListener);
1078         try {
1079             ActivityManager.getService().registerUserSwitchObserver(
1080                     new UserSwitchObserver() {
1081                         @Override
1082                         public void onUserSwitching(int newUserId, IRemoteCallback reply) {
1083                             mHandler.sendMessage(mHandler.obtainMessage(MSG_USER_SWITCHING,
1084                                     newUserId, 0, reply));
1085                         }
1086                         @Override
1087                         public void onUserSwitchComplete(int newUserId) throws RemoteException {
1088                             mHandler.sendMessage(mHandler.obtainMessage(MSG_USER_SWITCH_COMPLETE,
1089                                     newUserId, 0));
1090                         }
1091                     }, TAG);
1092         } catch (RemoteException e) {
1093             e.rethrowAsRuntimeException();
1094         }
1095 
1096         mTrustManager = (TrustManager) context.getSystemService(Context.TRUST_SERVICE);
1097         mTrustManager.registerTrustListener(this);
1098         mLockPatternUtils = new LockPatternUtils(context);
1099         mLockPatternUtils.registerStrongAuthTracker(mStrongAuthTracker);
1100 
1101         if (mContext.getPackageManager().hasSystemFeature(PackageManager.FEATURE_FINGERPRINT)) {
1102             mFpm = (FingerprintManager) context.getSystemService(Context.FINGERPRINT_SERVICE);
1103         }
1104         updateFingerprintListeningState();
1105         if (mFpm != null) {
1106             mFpm.addLockoutResetCallback(mLockoutResetCallback);
1107         }
1108 
1109         mUserManager = context.getSystemService(UserManager.class);
1110     }
1111 
updateFingerprintListeningState()1112     private void updateFingerprintListeningState() {
1113         mHandler.removeCallbacks(mRetryFingerprintAuthentication);
1114         boolean shouldListenForFingerprint = shouldListenForFingerprint();
1115         if (mFingerprintRunningState == FINGERPRINT_STATE_RUNNING && !shouldListenForFingerprint) {
1116             stopListeningForFingerprint();
1117         } else if (mFingerprintRunningState != FINGERPRINT_STATE_RUNNING
1118                 && shouldListenForFingerprint) {
1119             startListeningForFingerprint();
1120         }
1121     }
1122 
shouldListenForFingerprint()1123     private boolean shouldListenForFingerprint() {
1124         return (mKeyguardIsVisible || !mDeviceInteractive ||
1125                     (mBouncer && !mKeyguardGoingAway) || mGoingToSleep)
1126                 && !mSwitchingUser && !isFingerprintDisabled(getCurrentUser());
1127     }
1128 
startListeningForFingerprint()1129     private void startListeningForFingerprint() {
1130         if (mFingerprintRunningState == FINGERPRINT_STATE_CANCELLING) {
1131             setFingerprintRunningState(FINGERPRINT_STATE_CANCELLING_RESTARTING);
1132             return;
1133         }
1134         if (DEBUG) Log.v(TAG, "startListeningForFingerprint()");
1135         int userId = ActivityManager.getCurrentUser();
1136         if (isUnlockWithFingerprintPossible(userId)) {
1137             if (mFingerprintCancelSignal != null) {
1138                 mFingerprintCancelSignal.cancel();
1139             }
1140             mFingerprintCancelSignal = new CancellationSignal();
1141             mFpm.authenticate(null, mFingerprintCancelSignal, 0, mAuthenticationCallback, null, userId);
1142             setFingerprintRunningState(FINGERPRINT_STATE_RUNNING);
1143         }
1144     }
1145 
isUnlockWithFingerprintPossible(int userId)1146     public boolean isUnlockWithFingerprintPossible(int userId) {
1147         return mFpm != null && mFpm.isHardwareDetected() && !isFingerprintDisabled(userId)
1148                 && mFpm.getEnrolledFingerprints(userId).size() > 0;
1149     }
1150 
stopListeningForFingerprint()1151     private void stopListeningForFingerprint() {
1152         if (DEBUG) Log.v(TAG, "stopListeningForFingerprint()");
1153         if (mFingerprintRunningState == FINGERPRINT_STATE_RUNNING) {
1154             mFingerprintCancelSignal.cancel();
1155             mFingerprintCancelSignal = null;
1156             setFingerprintRunningState(FINGERPRINT_STATE_CANCELLING);
1157         }
1158         if (mFingerprintRunningState == FINGERPRINT_STATE_CANCELLING_RESTARTING) {
1159             setFingerprintRunningState(FINGERPRINT_STATE_CANCELLING);
1160         }
1161     }
1162 
isDeviceProvisionedInSettingsDb()1163     private boolean isDeviceProvisionedInSettingsDb() {
1164         return Settings.Global.getInt(mContext.getContentResolver(),
1165                 Settings.Global.DEVICE_PROVISIONED, 0) != 0;
1166     }
1167 
watchForDeviceProvisioning()1168     private void watchForDeviceProvisioning() {
1169         mDeviceProvisionedObserver = new ContentObserver(mHandler) {
1170             @Override
1171             public void onChange(boolean selfChange) {
1172                 super.onChange(selfChange);
1173                 mDeviceProvisioned = isDeviceProvisionedInSettingsDb();
1174                 if (mDeviceProvisioned) {
1175                     mHandler.sendEmptyMessage(MSG_DEVICE_PROVISIONED);
1176                 }
1177                 if (DEBUG) Log.d(TAG, "DEVICE_PROVISIONED state = " + mDeviceProvisioned);
1178             }
1179         };
1180 
1181         mContext.getContentResolver().registerContentObserver(
1182                 Settings.Global.getUriFor(Settings.Global.DEVICE_PROVISIONED),
1183                 false, mDeviceProvisionedObserver);
1184 
1185         // prevent a race condition between where we check the flag and where we register the
1186         // observer by grabbing the value once again...
1187         boolean provisioned = isDeviceProvisionedInSettingsDb();
1188         if (provisioned != mDeviceProvisioned) {
1189             mDeviceProvisioned = provisioned;
1190             if (mDeviceProvisioned) {
1191                 mHandler.sendEmptyMessage(MSG_DEVICE_PROVISIONED);
1192             }
1193         }
1194     }
1195 
1196     /**
1197      * Update the state whether Keyguard currently has a lockscreen wallpaper.
1198      *
1199      * @param hasLockscreenWallpaper Whether Keyguard has a lockscreen wallpaper.
1200      */
setHasLockscreenWallpaper(boolean hasLockscreenWallpaper)1201     public void setHasLockscreenWallpaper(boolean hasLockscreenWallpaper) {
1202         if (hasLockscreenWallpaper != mHasLockscreenWallpaper) {
1203             mHasLockscreenWallpaper = hasLockscreenWallpaper;
1204             for (int i = mCallbacks.size() - 1; i >= 0; i--) {
1205                 KeyguardUpdateMonitorCallback cb = mCallbacks.get(i).get();
1206                 if (cb != null) {
1207                     cb.onHasLockscreenWallpaperChanged(hasLockscreenWallpaper);
1208                 }
1209             }
1210         }
1211     }
1212 
1213     /**
1214      * @return Whether Keyguard has a lockscreen wallpaper.
1215      */
hasLockscreenWallpaper()1216     public boolean hasLockscreenWallpaper() {
1217         return mHasLockscreenWallpaper;
1218     }
1219 
1220     /**
1221      * Handle {@link #MSG_DPM_STATE_CHANGED}
1222      */
handleDevicePolicyManagerStateChanged()1223     protected void handleDevicePolicyManagerStateChanged() {
1224         updateFingerprintListeningState();
1225         for (int i = mCallbacks.size() - 1; i >= 0; i--) {
1226             KeyguardUpdateMonitorCallback cb = mCallbacks.get(i).get();
1227             if (cb != null) {
1228                 cb.onDevicePolicyManagerStateChanged();
1229             }
1230         }
1231     }
1232 
1233     /**
1234      * Handle {@link #MSG_USER_SWITCHING}
1235      */
handleUserSwitching(int userId, IRemoteCallback reply)1236     protected void handleUserSwitching(int userId, IRemoteCallback reply) {
1237         for (int i = 0; i < mCallbacks.size(); i++) {
1238             KeyguardUpdateMonitorCallback cb = mCallbacks.get(i).get();
1239             if (cb != null) {
1240                 cb.onUserSwitching(userId);
1241             }
1242         }
1243         try {
1244             reply.sendResult(null);
1245         } catch (RemoteException e) {
1246         }
1247     }
1248 
1249     /**
1250      * Handle {@link #MSG_USER_SWITCH_COMPLETE}
1251      */
handleUserSwitchComplete(int userId)1252     protected void handleUserSwitchComplete(int userId) {
1253         for (int i = 0; i < mCallbacks.size(); i++) {
1254             KeyguardUpdateMonitorCallback cb = mCallbacks.get(i).get();
1255             if (cb != null) {
1256                 cb.onUserSwitchComplete(userId);
1257             }
1258         }
1259     }
1260 
1261     /**
1262      * This is exposed since {@link Intent#ACTION_BOOT_COMPLETED} is not sticky. If
1263      * keyguard crashes sometime after boot, then it will never receive this
1264      * broadcast and hence not handle the event. This method is ultimately called by
1265      * PhoneWindowManager in this case.
1266      */
dispatchBootCompleted()1267     public void dispatchBootCompleted() {
1268         mHandler.sendEmptyMessage(MSG_BOOT_COMPLETED);
1269     }
1270 
1271     /**
1272      * Handle {@link #MSG_BOOT_COMPLETED}
1273      */
handleBootCompleted()1274     protected void handleBootCompleted() {
1275         if (mBootCompleted) return;
1276         mBootCompleted = true;
1277         for (int i = 0; i < mCallbacks.size(); i++) {
1278             KeyguardUpdateMonitorCallback cb = mCallbacks.get(i).get();
1279             if (cb != null) {
1280                 cb.onBootCompleted();
1281             }
1282         }
1283     }
1284 
1285     /**
1286      * We need to store this state in the KeyguardUpdateMonitor since this class will not be
1287      * destroyed.
1288      */
hasBootCompleted()1289     public boolean hasBootCompleted() {
1290         return mBootCompleted;
1291     }
1292 
1293     /**
1294      * Handle {@link #MSG_DEVICE_PROVISIONED}
1295      */
handleDeviceProvisioned()1296     protected void handleDeviceProvisioned() {
1297         for (int i = 0; i < mCallbacks.size(); i++) {
1298             KeyguardUpdateMonitorCallback cb = mCallbacks.get(i).get();
1299             if (cb != null) {
1300                 cb.onDeviceProvisioned();
1301             }
1302         }
1303         if (mDeviceProvisionedObserver != null) {
1304             // We don't need the observer anymore...
1305             mContext.getContentResolver().unregisterContentObserver(mDeviceProvisionedObserver);
1306             mDeviceProvisionedObserver = null;
1307         }
1308     }
1309 
1310     /**
1311      * Handle {@link #MSG_PHONE_STATE_CHANGED}
1312      */
handlePhoneStateChanged(String newState)1313     protected void handlePhoneStateChanged(String newState) {
1314         if (DEBUG) Log.d(TAG, "handlePhoneStateChanged(" + newState + ")");
1315         if (TelephonyManager.EXTRA_STATE_IDLE.equals(newState)) {
1316             mPhoneState = TelephonyManager.CALL_STATE_IDLE;
1317         } else if (TelephonyManager.EXTRA_STATE_OFFHOOK.equals(newState)) {
1318             mPhoneState = TelephonyManager.CALL_STATE_OFFHOOK;
1319         } else if (TelephonyManager.EXTRA_STATE_RINGING.equals(newState)) {
1320             mPhoneState = TelephonyManager.CALL_STATE_RINGING;
1321         }
1322         for (int i = 0; i < mCallbacks.size(); i++) {
1323             KeyguardUpdateMonitorCallback cb = mCallbacks.get(i).get();
1324             if (cb != null) {
1325                 cb.onPhoneStateChanged(mPhoneState);
1326             }
1327         }
1328     }
1329 
1330     /**
1331      * Handle {@link #MSG_RINGER_MODE_CHANGED}
1332      */
handleRingerModeChange(int mode)1333     protected void handleRingerModeChange(int mode) {
1334         if (DEBUG) Log.d(TAG, "handleRingerModeChange(" + mode + ")");
1335         mRingMode = mode;
1336         for (int i = 0; i < mCallbacks.size(); i++) {
1337             KeyguardUpdateMonitorCallback cb = mCallbacks.get(i).get();
1338             if (cb != null) {
1339                 cb.onRingerModeChanged(mode);
1340             }
1341         }
1342     }
1343 
1344     /**
1345      * Handle {@link #MSG_TIME_UPDATE}
1346      */
handleTimeUpdate()1347     private void handleTimeUpdate() {
1348         if (DEBUG) Log.d(TAG, "handleTimeUpdate");
1349         for (int i = 0; i < mCallbacks.size(); i++) {
1350             KeyguardUpdateMonitorCallback cb = mCallbacks.get(i).get();
1351             if (cb != null) {
1352                 cb.onTimeChanged();
1353             }
1354         }
1355     }
1356 
1357     /**
1358      * Handle {@link #MSG_BATTERY_UPDATE}
1359      */
handleBatteryUpdate(BatteryStatus status)1360     private void handleBatteryUpdate(BatteryStatus status) {
1361         if (DEBUG) Log.d(TAG, "handleBatteryUpdate");
1362         final boolean batteryUpdateInteresting = isBatteryUpdateInteresting(mBatteryStatus, status);
1363         mBatteryStatus = status;
1364         if (batteryUpdateInteresting) {
1365             for (int i = 0; i < mCallbacks.size(); i++) {
1366                 KeyguardUpdateMonitorCallback cb = mCallbacks.get(i).get();
1367                 if (cb != null) {
1368                     cb.onRefreshBatteryInfo(status);
1369                 }
1370             }
1371         }
1372     }
1373 
1374     /**
1375      * Handle {@link #MSG_SIM_STATE_CHANGE}
1376      */
handleSimStateChange(int subId, int slotId, State state)1377     private void handleSimStateChange(int subId, int slotId, State state) {
1378 
1379         if (DEBUG_SIM_STATES) {
1380             Log.d(TAG, "handleSimStateChange(subId=" + subId + ", slotId="
1381                     + slotId + ", state=" + state +")");
1382         }
1383 
1384         if (!SubscriptionManager.isValidSubscriptionId(subId)) {
1385             Log.w(TAG, "invalid subId in handleSimStateChange()");
1386             return;
1387         }
1388 
1389         SimData data = mSimDatas.get(subId);
1390         final boolean changed;
1391         if (data == null) {
1392             data = new SimData(state, slotId, subId);
1393             mSimDatas.put(subId, data);
1394             changed = true; // no data yet; force update
1395         } else {
1396             changed = (data.simState != state || data.subId != subId || data.slotId != slotId);
1397             data.simState = state;
1398             data.subId = subId;
1399             data.slotId = slotId;
1400         }
1401         if (changed && state != State.UNKNOWN) {
1402             for (int i = 0; i < mCallbacks.size(); i++) {
1403                 KeyguardUpdateMonitorCallback cb = mCallbacks.get(i).get();
1404                 if (cb != null) {
1405                     cb.onSimStateChanged(subId, slotId, state);
1406                 }
1407             }
1408         }
1409     }
1410 
1411     /**
1412      * Handle {@link #MSG_SERVICE_STATE_CHANGE}
1413      */
handleServiceStateChange(int subId, ServiceState serviceState)1414     private void handleServiceStateChange(int subId, ServiceState serviceState) {
1415         if (DEBUG) {
1416             Log.d(TAG,
1417                     "handleServiceStateChange(subId=" + subId + ", serviceState=" + serviceState);
1418         }
1419 
1420         if (!SubscriptionManager.isValidSubscriptionId(subId)) {
1421             Log.w(TAG, "invalid subId in handleServiceStateChange()");
1422             return;
1423         }
1424 
1425         mServiceStates.put(subId, serviceState);
1426 
1427         for (int j = 0; j < mCallbacks.size(); j++) {
1428             KeyguardUpdateMonitorCallback cb = mCallbacks.get(j).get();
1429             if (cb != null) {
1430                 cb.onRefreshCarrierInfo();
1431             }
1432         }
1433     }
1434 
1435     /**
1436      * Notifies that the visibility state of Keyguard has changed.
1437      *
1438      * <p>Needs to be called from the main thread.
1439      */
onKeyguardVisibilityChanged(boolean showing)1440     public void onKeyguardVisibilityChanged(boolean showing) {
1441         if (DEBUG) Log.d(TAG, "onKeyguardVisibilityChanged(" + showing + ")");
1442         mKeyguardIsVisible = showing;
1443         for (int i = 0; i < mCallbacks.size(); i++) {
1444             KeyguardUpdateMonitorCallback cb = mCallbacks.get(i).get();
1445             if (cb != null) {
1446                 cb.onKeyguardVisibilityChangedRaw(showing);
1447             }
1448         }
1449         updateFingerprintListeningState();
1450     }
1451 
1452     /**
1453      * Handle {@link #MSG_KEYGUARD_RESET}
1454      */
handleKeyguardReset()1455     private void handleKeyguardReset() {
1456         if (DEBUG) Log.d(TAG, "handleKeyguardReset");
1457         updateFingerprintListeningState();
1458         mNeedsSlowUnlockTransition = resolveNeedsSlowUnlockTransition();
1459     }
1460 
resolveNeedsSlowUnlockTransition()1461     private boolean resolveNeedsSlowUnlockTransition() {
1462         if (mUserManager.isUserUnlocked(getCurrentUser())) {
1463             return false;
1464         }
1465         Intent homeIntent = new Intent(Intent.ACTION_MAIN)
1466                 .addCategory(Intent.CATEGORY_HOME);
1467         ResolveInfo resolveInfo = mContext.getPackageManager().resolveActivity(homeIntent,
1468                 0 /* flags */);
1469         return FALLBACK_HOME_COMPONENT.equals(resolveInfo.getComponentInfo().getComponentName());
1470     }
1471 
1472     /**
1473      * Handle {@link #MSG_KEYGUARD_BOUNCER_CHANGED}
1474      * @see #sendKeyguardBouncerChanged(boolean)
1475      */
handleKeyguardBouncerChanged(int bouncer)1476     private void handleKeyguardBouncerChanged(int bouncer) {
1477         if (DEBUG) Log.d(TAG, "handleKeyguardBouncerChanged(" + bouncer + ")");
1478         boolean isBouncer = (bouncer == 1);
1479         mBouncer = isBouncer;
1480         for (int i = 0; i < mCallbacks.size(); i++) {
1481             KeyguardUpdateMonitorCallback cb = mCallbacks.get(i).get();
1482             if (cb != null) {
1483                 cb.onKeyguardBouncerChanged(isBouncer);
1484             }
1485         }
1486         updateFingerprintListeningState();
1487     }
1488 
1489     /**
1490      * Handle {@link #MSG_REPORT_EMERGENCY_CALL_ACTION}
1491      */
handleReportEmergencyCallAction()1492     private void handleReportEmergencyCallAction() {
1493         for (int i = 0; i < mCallbacks.size(); i++) {
1494             KeyguardUpdateMonitorCallback cb = mCallbacks.get(i).get();
1495             if (cb != null) {
1496                 cb.onEmergencyCallAction();
1497             }
1498         }
1499     }
1500 
isBatteryUpdateInteresting(BatteryStatus old, BatteryStatus current)1501     private static boolean isBatteryUpdateInteresting(BatteryStatus old, BatteryStatus current) {
1502         final boolean nowPluggedIn = current.isPluggedIn();
1503         final boolean wasPluggedIn = old.isPluggedIn();
1504         final boolean stateChangedWhilePluggedIn =
1505             wasPluggedIn == true && nowPluggedIn == true
1506             && (old.status != current.status);
1507 
1508         // change in plug state is always interesting
1509         if (wasPluggedIn != nowPluggedIn || stateChangedWhilePluggedIn) {
1510             return true;
1511         }
1512 
1513         // change in battery level while plugged in
1514         if (nowPluggedIn && old.level != current.level) {
1515             return true;
1516         }
1517 
1518         // change where battery needs charging
1519         if (!nowPluggedIn && current.isBatteryLow() && current.level != old.level) {
1520             return true;
1521         }
1522 
1523         // change in charging current while plugged in
1524         if (nowPluggedIn && current.maxChargingWattage != old.maxChargingWattage) {
1525             return true;
1526         }
1527 
1528         return false;
1529     }
1530 
1531     /**
1532      * Remove the given observer's callback.
1533      *
1534      * @param callback The callback to remove
1535      */
removeCallback(KeyguardUpdateMonitorCallback callback)1536     public void removeCallback(KeyguardUpdateMonitorCallback callback) {
1537         if (DEBUG) Log.v(TAG, "*** unregister callback for " + callback);
1538         for (int i = mCallbacks.size() - 1; i >= 0; i--) {
1539             if (mCallbacks.get(i).get() == callback) {
1540                 mCallbacks.remove(i);
1541             }
1542         }
1543     }
1544 
1545     /**
1546      * Register to receive notifications about general keyguard information
1547      * (see {@link InfoCallback}.
1548      * @param callback The callback to register
1549      */
registerCallback(KeyguardUpdateMonitorCallback callback)1550     public void registerCallback(KeyguardUpdateMonitorCallback callback) {
1551         if (DEBUG) Log.v(TAG, "*** register callback for " + callback);
1552         // Prevent adding duplicate callbacks
1553         for (int i = 0; i < mCallbacks.size(); i++) {
1554             if (mCallbacks.get(i).get() == callback) {
1555                 if (DEBUG) Log.e(TAG, "Object tried to add another callback",
1556                         new Exception("Called by"));
1557                 return;
1558             }
1559         }
1560         mCallbacks.add(new WeakReference<KeyguardUpdateMonitorCallback>(callback));
1561         removeCallback(null); // remove unused references
1562         sendUpdates(callback);
1563     }
1564 
isSwitchingUser()1565     public boolean isSwitchingUser() {
1566         return mSwitchingUser;
1567     }
1568 
setSwitchingUser(boolean switching)1569     public void setSwitchingUser(boolean switching) {
1570         mSwitchingUser = switching;
1571         updateFingerprintListeningState();
1572     }
1573 
sendUpdates(KeyguardUpdateMonitorCallback callback)1574     private void sendUpdates(KeyguardUpdateMonitorCallback callback) {
1575         // Notify listener of the current state
1576         callback.onRefreshBatteryInfo(mBatteryStatus);
1577         callback.onTimeChanged();
1578         callback.onRingerModeChanged(mRingMode);
1579         callback.onPhoneStateChanged(mPhoneState);
1580         callback.onRefreshCarrierInfo();
1581         callback.onClockVisibilityChanged();
1582         for (Entry<Integer, SimData> data : mSimDatas.entrySet()) {
1583             final SimData state = data.getValue();
1584             callback.onSimStateChanged(state.subId, state.slotId, state.simState);
1585         }
1586     }
1587 
sendKeyguardReset()1588     public void sendKeyguardReset() {
1589         mHandler.obtainMessage(MSG_KEYGUARD_RESET).sendToTarget();
1590     }
1591 
1592     /**
1593      * @see #handleKeyguardBouncerChanged(int)
1594      */
sendKeyguardBouncerChanged(boolean showingBouncer)1595     public void sendKeyguardBouncerChanged(boolean showingBouncer) {
1596         if (DEBUG) Log.d(TAG, "sendKeyguardBouncerChanged(" + showingBouncer + ")");
1597         Message message = mHandler.obtainMessage(MSG_KEYGUARD_BOUNCER_CHANGED);
1598         message.arg1 = showingBouncer ? 1 : 0;
1599         message.sendToTarget();
1600     }
1601 
1602     /**
1603      * Report that the user successfully entered the SIM PIN or PUK/SIM PIN so we
1604      * have the information earlier than waiting for the intent
1605      * broadcast from the telephony code.
1606      *
1607      * NOTE: Because handleSimStateChange() invokes callbacks immediately without going
1608      * through mHandler, this *must* be called from the UI thread.
1609      */
reportSimUnlocked(int subId)1610     public void reportSimUnlocked(int subId) {
1611         if (DEBUG_SIM_STATES) Log.v(TAG, "reportSimUnlocked(subId=" + subId + ")");
1612         int slotId = SubscriptionManager.getSlotIndex(subId);
1613         handleSimStateChange(subId, slotId, State.READY);
1614     }
1615 
1616     /**
1617      * Report that the emergency call button has been pressed and the emergency dialer is
1618      * about to be displayed.
1619      *
1620      * @param bypassHandler runs immediately.
1621      *
1622      * NOTE: Must be called from UI thread if bypassHandler == true.
1623      */
reportEmergencyCallAction(boolean bypassHandler)1624     public void reportEmergencyCallAction(boolean bypassHandler) {
1625         if (!bypassHandler) {
1626             mHandler.obtainMessage(MSG_REPORT_EMERGENCY_CALL_ACTION).sendToTarget();
1627         } else {
1628             handleReportEmergencyCallAction();
1629         }
1630     }
1631 
1632     /**
1633      * @return Whether the device is provisioned (whether they have gone through
1634      *   the setup wizard)
1635      */
isDeviceProvisioned()1636     public boolean isDeviceProvisioned() {
1637         return mDeviceProvisioned;
1638     }
1639 
clearFailedUnlockAttempts()1640     public void clearFailedUnlockAttempts() {
1641         mFailedAttempts.delete(sCurrentUser);
1642     }
1643 
getFailedUnlockAttempts(int userId)1644     public int getFailedUnlockAttempts(int userId) {
1645         return mFailedAttempts.get(userId, 0);
1646     }
1647 
reportFailedStrongAuthUnlockAttempt(int userId)1648     public void reportFailedStrongAuthUnlockAttempt(int userId) {
1649         mFailedAttempts.put(userId, getFailedUnlockAttempts(userId) + 1);
1650     }
1651 
clearFingerprintRecognized()1652     public void clearFingerprintRecognized() {
1653         mUserFingerprintAuthenticated.clear();
1654     }
1655 
isSimPinVoiceSecure()1656     public boolean isSimPinVoiceSecure() {
1657         // TODO: only count SIMs that handle voice
1658         return isSimPinSecure();
1659     }
1660 
isSimPinSecure()1661     public boolean isSimPinSecure() {
1662         // True if any SIM is pin secure
1663         for (SubscriptionInfo info : getSubscriptionInfo(false /* forceReload */)) {
1664             if (isSimPinSecure(getSimState(info.getSubscriptionId()))) return true;
1665         }
1666         return false;
1667     }
1668 
getSimState(int subId)1669     public State getSimState(int subId) {
1670         if (mSimDatas.containsKey(subId)) {
1671             return mSimDatas.get(subId).simState;
1672         } else {
1673             return State.UNKNOWN;
1674         }
1675     }
1676 
1677     /**
1678      * @return true if and only if the state has changed for the specified {@code slotId}
1679      */
refreshSimState(int subId, int slotId)1680     private boolean refreshSimState(int subId, int slotId) {
1681 
1682         // This is awful. It exists because there are two APIs for getting the SIM status
1683         // that don't return the complete set of values and have different types. In Keyguard we
1684         // need IccCardConstants, but TelephonyManager would only give us
1685         // TelephonyManager.SIM_STATE*, so we retrieve it manually.
1686         final TelephonyManager tele = TelephonyManager.from(mContext);
1687         int simState =  tele.getSimState(slotId);
1688         State state;
1689         try {
1690             state = State.intToState(simState);
1691         } catch(IllegalArgumentException ex) {
1692             Log.w(TAG, "Unknown sim state: " + simState);
1693             state = State.UNKNOWN;
1694         }
1695         SimData data = mSimDatas.get(subId);
1696         final boolean changed;
1697         if (data == null) {
1698             data = new SimData(state, slotId, subId);
1699             mSimDatas.put(subId, data);
1700             changed = true; // no data yet; force update
1701         } else {
1702             changed = data.simState != state;
1703             data.simState = state;
1704         }
1705         return changed;
1706     }
1707 
isSimPinSecure(IccCardConstants.State state)1708     public static boolean isSimPinSecure(IccCardConstants.State state) {
1709         final IccCardConstants.State simState = state;
1710         return (simState == IccCardConstants.State.PIN_REQUIRED
1711                 || simState == IccCardConstants.State.PUK_REQUIRED
1712                 || simState == IccCardConstants.State.PERM_DISABLED);
1713     }
1714 
getCachedDisplayClientState()1715     public DisplayClientState getCachedDisplayClientState() {
1716         return mDisplayClientState;
1717     }
1718 
1719     // TODO: use these callbacks elsewhere in place of the existing notifyScreen*()
1720     // (KeyguardViewMediator, KeyguardHostView)
dispatchStartedWakingUp()1721     public void dispatchStartedWakingUp() {
1722         synchronized (this) {
1723             mDeviceInteractive = true;
1724         }
1725         mHandler.sendEmptyMessage(MSG_STARTED_WAKING_UP);
1726     }
1727 
dispatchStartedGoingToSleep(int why)1728     public void dispatchStartedGoingToSleep(int why) {
1729         mHandler.sendMessage(mHandler.obtainMessage(MSG_STARTED_GOING_TO_SLEEP, why, 0));
1730     }
1731 
dispatchFinishedGoingToSleep(int why)1732     public void dispatchFinishedGoingToSleep(int why) {
1733         synchronized(this) {
1734             mDeviceInteractive = false;
1735         }
1736         mHandler.sendMessage(mHandler.obtainMessage(MSG_FINISHED_GOING_TO_SLEEP, why, 0));
1737     }
1738 
dispatchScreenTurnedOn()1739     public void dispatchScreenTurnedOn() {
1740         synchronized (this) {
1741             mScreenOn = true;
1742         }
1743         mHandler.sendEmptyMessage(MSG_SCREEN_TURNED_ON);
1744     }
1745 
dispatchScreenTurnedOff()1746     public void dispatchScreenTurnedOff() {
1747         synchronized(this) {
1748             mScreenOn = false;
1749         }
1750         mHandler.sendEmptyMessage(MSG_SCREEN_TURNED_OFF);
1751     }
1752 
dispatchDreamingStarted()1753     public void dispatchDreamingStarted() {
1754         mHandler.sendMessage(mHandler.obtainMessage(MSG_DREAMING_STATE_CHANGED, 1, 0));
1755     }
1756 
dispatchDreamingStopped()1757     public void dispatchDreamingStopped() {
1758         mHandler.sendMessage(mHandler.obtainMessage(MSG_DREAMING_STATE_CHANGED, 0, 0));
1759     }
1760 
isDeviceInteractive()1761     public boolean isDeviceInteractive() {
1762         return mDeviceInteractive;
1763     }
1764 
isGoingToSleep()1765     public boolean isGoingToSleep() {
1766         return mGoingToSleep;
1767     }
1768 
1769     /**
1770      * Find the next SubscriptionId for a SIM in the given state, favoring lower slot numbers first.
1771      * @param state
1772      * @return subid or {@link SubscriptionManager#INVALID_SUBSCRIPTION_ID} if none found
1773      */
getNextSubIdForState(State state)1774     public int getNextSubIdForState(State state) {
1775         List<SubscriptionInfo> list = getSubscriptionInfo(false /* forceReload */);
1776         int resultId = SubscriptionManager.INVALID_SUBSCRIPTION_ID;
1777         int bestSlotId = Integer.MAX_VALUE; // Favor lowest slot first
1778         for (int i = 0; i < list.size(); i++) {
1779             final SubscriptionInfo info = list.get(i);
1780             final int id = info.getSubscriptionId();
1781             int slotId = SubscriptionManager.getSlotIndex(id);
1782             if (state == getSimState(id) && bestSlotId > slotId ) {
1783                 resultId = id;
1784                 bestSlotId = slotId;
1785             }
1786         }
1787         return resultId;
1788     }
1789 
getSubscriptionInfoForSubId(int subId)1790     public SubscriptionInfo getSubscriptionInfoForSubId(int subId) {
1791         List<SubscriptionInfo> list = getSubscriptionInfo(false /* forceReload */);
1792         for (int i = 0; i < list.size(); i++) {
1793             SubscriptionInfo info = list.get(i);
1794             if (subId == info.getSubscriptionId()) return info;
1795         }
1796         return null; // not found
1797     }
1798 
dump(FileDescriptor fd, PrintWriter pw, String[] args)1799     public void dump(FileDescriptor fd, PrintWriter pw, String[] args) {
1800         pw.println("KeyguardUpdateMonitor state:");
1801         pw.println("  SIM States:");
1802         for (SimData data : mSimDatas.values()) {
1803             pw.println("    " + data.toString());
1804         }
1805         pw.println("  Subs:");
1806         if (mSubscriptionInfo != null) {
1807             for (int i = 0; i < mSubscriptionInfo.size(); i++) {
1808                 pw.println("    " + mSubscriptionInfo.get(i));
1809             }
1810         }
1811         pw.println("  Service states:");
1812         for (int subId : mServiceStates.keySet()) {
1813             pw.println("    " + subId + "=" + mServiceStates.get(subId));
1814         }
1815         if (mFpm != null && mFpm.isHardwareDetected()) {
1816             final int userId = ActivityManager.getCurrentUser();
1817             final int strongAuthFlags = mStrongAuthTracker.getStrongAuthForUser(userId);
1818             pw.println("  Fingerprint state (user=" + userId + ")");
1819             pw.println("    allowed=" + isUnlockingWithFingerprintAllowed());
1820             pw.println("    auth'd=" + mUserFingerprintAuthenticated.get(userId));
1821             pw.println("    authSinceBoot="
1822                     + getStrongAuthTracker().hasUserAuthenticatedSinceBoot());
1823             pw.println("    disabled(DPM)=" + isFingerprintDisabled(userId));
1824             pw.println("    possible=" + isUnlockWithFingerprintPossible(userId));
1825             pw.println("    strongAuthFlags=" + Integer.toHexString(strongAuthFlags));
1826             pw.println("    trustManaged=" + getUserTrustIsManaged(userId));
1827         }
1828     }
1829 }
1830