Skip to content

Commit f1b6741

Browse files
author
Craig Mautner
committed
Fix deadlock in LockPatternUtils by using local id.
Activity manager now updates window manager's current user id directly and immediately rather than waiting for a broadcast update. Window manager passes this through policy to the KeyguardViewMediator and into LockPatternUtils. LockPatternUtils no longer goes to Activity to get the current user id if it finds that its local id is non-default. Fixes bug 7193726. Change-Id: Id5613e7a9fe9e5b49e83c26b74504f587c3998c2
1 parent 5d1a870 commit f1b6741

File tree

7 files changed

+49
-24
lines changed

7 files changed

+49
-24
lines changed

core/java/android/view/WindowManagerPolicy.java

Lines changed: 9 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1111,7 +1111,15 @@ interface OnKeyguardExitResult {
11111111
* @param attrs The window's LayoutParams.
11121112
* @return Whether magnification can be applied.
11131113
*/
1114-
public boolean canMagnifyWindow(WindowManager.LayoutParams attrs);
1114+
public boolean canMagnifyWindowLw(WindowManager.LayoutParams attrs);
1115+
1116+
/**
1117+
* Called when the current user changes. Guaranteed to be called before the broadcast
1118+
* of the new user id is made to all listeners.
1119+
*
1120+
* @param newUserId The id of the incoming user.
1121+
*/
1122+
public void setCurrentUserLw(int newUserId);
11151123

11161124
/**
11171125
* Print the WindowManagerPolicy's state into the given stream.

core/java/com/android/internal/widget/LockPatternUtils.java

Lines changed: 6 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -22,14 +22,11 @@
2222

2323
import android.app.ActivityManagerNative;
2424
import android.app.admin.DevicePolicyManager;
25-
import android.content.BroadcastReceiver;
2625
import android.content.ContentResolver;
2726
import android.content.Context;
2827
import android.content.Intent;
29-
import android.content.IntentFilter;
3028
import android.content.pm.PackageManager;
3129
import android.os.Binder;
32-
import android.os.FileObserver;
3330
import android.os.IBinder;
3431
import android.os.Process;
3532
import android.os.RemoteException;
@@ -45,16 +42,10 @@
4542
import android.view.View;
4643
import android.widget.Button;
4744

48-
import java.io.File;
49-
import java.io.FileNotFoundException;
50-
import java.io.IOException;
51-
import java.io.RandomAccessFile;
5245
import java.security.MessageDigest;
5346
import java.security.NoSuchAlgorithmException;
5447
import java.security.SecureRandom;
55-
import java.util.Arrays;
5648
import java.util.List;
57-
import java.util.concurrent.atomic.AtomicBoolean;
5849

5950
/**
6051
* Utilities for the lock pattern and its settings.
@@ -134,7 +125,7 @@ public class LockPatternUtils {
134125
private final ContentResolver mContentResolver;
135126
private DevicePolicyManager mDevicePolicyManager;
136127
private ILockSettings mLockSettingsService;
137-
private int mCurrentUserId = 0;
128+
private int mCurrentUserId = UserHandle.USER_NULL;
138129

139130
public DevicePolicyManager getDevicePolicyManager() {
140131
if (mDevicePolicyManager == null) {
@@ -233,10 +224,14 @@ public void setCurrentUser(int userId) {
233224

234225
public int getCurrentUser() {
235226
if (Process.myUid() == Process.SYSTEM_UID) {
227+
if (mCurrentUserId != UserHandle.USER_NULL) {
228+
// Someone is regularly updating using setCurrentUser() use that value.
229+
return mCurrentUserId;
230+
}
236231
try {
237232
return ActivityManagerNative.getDefault().getCurrentUser().id;
238233
} catch (RemoteException re) {
239-
return mCurrentUserId;
234+
return UserHandle.USER_OWNER;
240235
}
241236
} else {
242237
throw new SecurityException("Only the system process can get the current user");

policy/src/com/android/internal/policy/impl/PhoneWindowManager.java

Lines changed: 11 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -71,7 +71,6 @@
7171
import android.util.Log;
7272
import android.util.Slog;
7373
import android.util.SparseArray;
74-
import android.util.SparseIntArray;
7574
import android.view.Display;
7675
import android.view.Gravity;
7776
import android.view.HapticFeedbackConstants;
@@ -722,6 +721,7 @@ private void cancelPendingScreenshotChordAction() {
722721
}
723722

724723
private final Runnable mPowerLongPress = new Runnable() {
724+
@Override
725725
public void run() {
726726
// The context isn't read
727727
if (mLongPressOnPowerBehavior < 0) {
@@ -4316,7 +4316,8 @@ public void setLastInputMethodWindowLw(WindowState ime, WindowState target) {
43164316
mLastInputMethodTargetWindow = target;
43174317
}
43184318

4319-
public boolean canMagnifyWindow(WindowManager.LayoutParams attrs) {
4319+
@Override
4320+
public boolean canMagnifyWindowLw(WindowManager.LayoutParams attrs) {
43204321
switch (attrs.type) {
43214322
case WindowManager.LayoutParams.TYPE_INPUT_METHOD:
43224323
case WindowManager.LayoutParams.TYPE_INPUT_METHOD_DIALOG:
@@ -4328,6 +4329,14 @@ public boolean canMagnifyWindow(WindowManager.LayoutParams attrs) {
43284329
return true;
43294330
}
43304331

4332+
@Override
4333+
public void setCurrentUserLw(int newUserId) {
4334+
if (mKeyguardMediator != null) {
4335+
mKeyguardMediator.setCurrentUser(newUserId);
4336+
}
4337+
}
4338+
4339+
@Override
43314340
public void dump(String prefix, PrintWriter pw, String[] args) {
43324341
pw.print(prefix); pw.print("mSafeMode="); pw.print(mSafeMode);
43334342
pw.print(" mSystemReady="); pw.print(mSystemReady);

policy/src/com/android/internal/policy/impl/keyguard/KeyguardViewMediator.java

Lines changed: 11 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -131,7 +131,7 @@ public class KeyguardViewMediator {
131131
private static final int KEYGUARD_LOCK_AFTER_DELAY_DEFAULT = 5000;
132132

133133
/**
134-
* How long we'll wait for the {@link KeyguardViewCallback#keyguardDoneDrawing()}
134+
* How long we'll wait for the {@link ViewMediatorCallback#keyguardDoneDrawing()}
135135
* callback before unblocking a call to {@link #setKeyguardEnabled(boolean)}
136136
* that is reenabling the keyguard.
137137
*/
@@ -297,7 +297,7 @@ public interface ViewMediatorCallback {
297297

298298
@Override
299299
public void onUserSwitched(int userId) {
300-
mLockPatternUtils.setCurrentUser(userId);
300+
// Note that the mLockPatternUtils user has already been updated from setCurrentUser.
301301
synchronized (KeyguardViewMediator.this) {
302302
resetStateLocked();
303303
}
@@ -465,6 +465,7 @@ public KeyguardViewMediator(Context context, LockPatternUtils lockPatternUtils)
465465

466466
mLockPatternUtils = lockPatternUtils != null
467467
? lockPatternUtils : new LockPatternUtils(mContext);
468+
mLockPatternUtils.setCurrentUser(UserHandle.USER_OWNER);
468469

469470
WindowManager wm = (WindowManager)context.getSystemService(Context.WINDOW_SERVICE);
470471

@@ -890,6 +891,14 @@ public boolean isSecure() {
890891
|| KeyguardUpdateMonitor.getInstance(mContext).isSimPinSecure();
891892
}
892893

894+
/**
895+
* Update the newUserId. Call while holding WindowManagerService lock.
896+
* @param newUserId The id of the incoming user.
897+
*/
898+
public void setCurrentUser(int newUserId) {
899+
mLockPatternUtils.setCurrentUser(newUserId);
900+
}
901+
893902
private final BroadcastReceiver mBroadcastReceiver = new BroadcastReceiver() {
894903
@Override
895904
public void onReceive(Context context, Intent intent) {

services/java/com/android/server/am/ActivityManagerService.java

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -13969,6 +13969,8 @@ public boolean switchUser(int userId) {
1396913969
mUserLru.remove(userIdInt);
1397013970
mUserLru.add(userIdInt);
1397113971

13972+
mWindowManager.setCurrentUser(userId);
13973+
1397213974
final UserStartedState uss = mStartedUsers.get(userId);
1397313975

1397413976
mHandler.removeMessages(REPORT_USER_SWITCH_MSG);
@@ -14007,7 +14009,7 @@ public void performReceive(Intent intent, int resultCode,
1400714009
if (!haveActivities) {
1400814010
startHomeActivityLocked(userId);
1400914011
}
14010-
14012+
1401114013
sendUserSwitchBroadcastsLocked(oldUserId, userId);
1401214014
}
1401314015
} finally {

services/java/com/android/server/wm/WindowManagerService.java

Lines changed: 7 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -292,9 +292,6 @@ public void onReceive(Context context, Intent intent) {
292292
if (DevicePolicyManager.ACTION_DEVICE_POLICY_MANAGER_STATE_CHANGED.equals(action)) {
293293
mKeyguardDisableHandler.sendEmptyMessage(
294294
KeyguardDisableHandler.KEYGUARD_POLICY_CHANGED);
295-
} else if (Intent.ACTION_USER_SWITCHED.equals(action)) {
296-
final int newUserId = intent.getIntExtra(Intent.EXTRA_USER_HANDLE, 0);
297-
mCurrentUserId = newUserId;
298295
}
299296
}
300297
};
@@ -811,8 +808,6 @@ private WindowManagerService(Context context, PowerManagerService pm,
811808
// Track changes to DevicePolicyManager state so we can enable/disable keyguard.
812809
IntentFilter filter = new IntentFilter();
813810
filter.addAction(DevicePolicyManager.ACTION_DEVICE_POLICY_MANAGER_STATE_CHANGED);
814-
// Track user switching.
815-
filter.addAction(Intent.ACTION_USER_SWITCHED);
816811
mContext.registerReceiver(mBroadcastReceiver, filter);
817812

818813
mHoldingScreenWakeLock = pmc.newWakeLock(PowerManager.SCREEN_BRIGHT_WAKE_LOCK
@@ -5396,6 +5391,13 @@ public void setInputFilter(IInputFilter filter) {
53965391
mInputManager.setInputFilter(filter);
53975392
}
53985393

5394+
public void setCurrentUser(final int newUserId) {
5395+
synchronized (mWindowMap) {
5396+
mCurrentUserId = newUserId;
5397+
mPolicy.setCurrentUserLw(newUserId);
5398+
}
5399+
}
5400+
53995401
public void enableScreenAfterBoot() {
54005402
synchronized(mWindowMap) {
54015403
if (DEBUG_BOOT) {

services/java/com/android/server/wm/WindowState.java

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -518,11 +518,11 @@ MagnificationSpec getWindowMagnificationSpecLocked() {
518518
MagnificationSpec spec = mDisplayContent.mMagnificationSpec;
519519
if (spec != null && !spec.isNop()) {
520520
if (mAttachedWindow != null) {
521-
if (!mPolicy.canMagnifyWindow(mAttachedWindow.mAttrs)) {
521+
if (!mPolicy.canMagnifyWindowLw(mAttachedWindow.mAttrs)) {
522522
return null;
523523
}
524524
}
525-
if (!mPolicy.canMagnifyWindow(mAttrs)) {
525+
if (!mPolicy.canMagnifyWindowLw(mAttrs)) {
526526
return null;
527527
}
528528
}

0 commit comments

Comments
 (0)