Improve protection against malicious admins.
- 2 second timeout until we give up on displaying a message, keeping us within the 5 second activity launch block time. - Restart the activity launch block when we show the dialog. - Use app ops to prevent the app of the currently displayed admin from putting windows on top while the settings screen is running. Change-Id: I631e8896ec7539c2de3ff36f183e67e36bcc37ca
This commit is contained in:
@@ -16,6 +16,7 @@
|
|||||||
|
|
||||||
package com.android.settings;
|
package com.android.settings;
|
||||||
|
|
||||||
|
import android.app.AppOpsManager;
|
||||||
import org.xmlpull.v1.XmlPullParserException;
|
import org.xmlpull.v1.XmlPullParserException;
|
||||||
|
|
||||||
import android.app.Activity;
|
import android.app.Activity;
|
||||||
@@ -51,7 +52,6 @@ import android.widget.TextView;
|
|||||||
|
|
||||||
import java.io.IOException;
|
import java.io.IOException;
|
||||||
import java.util.ArrayList;
|
import java.util.ArrayList;
|
||||||
import java.util.HashSet;
|
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
|
|
||||||
public class DeviceAdminAdd extends Activity {
|
public class DeviceAdminAdd extends Activity {
|
||||||
@@ -66,6 +66,7 @@ public class DeviceAdminAdd extends Activity {
|
|||||||
Handler mHandler;
|
Handler mHandler;
|
||||||
|
|
||||||
DevicePolicyManager mDPM;
|
DevicePolicyManager mDPM;
|
||||||
|
AppOpsManager mAppOps;
|
||||||
DeviceAdminInfo mDeviceAdmin;
|
DeviceAdminInfo mDeviceAdmin;
|
||||||
CharSequence mAddMsgText;
|
CharSequence mAddMsgText;
|
||||||
|
|
||||||
@@ -85,6 +86,9 @@ public class DeviceAdminAdd extends Activity {
|
|||||||
|
|
||||||
boolean mAdding;
|
boolean mAdding;
|
||||||
boolean mRefreshing;
|
boolean mRefreshing;
|
||||||
|
boolean mWaitingForRemoveMsg;
|
||||||
|
int mCurSysAppOpMode;
|
||||||
|
int mCurToastAppOpMode;
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
protected void onCreate(Bundle icicle) {
|
protected void onCreate(Bundle icicle) {
|
||||||
@@ -93,6 +97,7 @@ public class DeviceAdminAdd extends Activity {
|
|||||||
mHandler = new Handler(getMainLooper());
|
mHandler = new Handler(getMainLooper());
|
||||||
|
|
||||||
mDPM = (DevicePolicyManager)getSystemService(Context.DEVICE_POLICY_SERVICE);
|
mDPM = (DevicePolicyManager)getSystemService(Context.DEVICE_POLICY_SERVICE);
|
||||||
|
mAppOps = (AppOpsManager)getSystemService(Context.APP_OPS_SERVICE);
|
||||||
|
|
||||||
if ((getIntent().getFlags()&Intent.FLAG_ACTIVITY_NEW_TASK) != 0) {
|
if ((getIntent().getFlags()&Intent.FLAG_ACTIVITY_NEW_TASK) != 0) {
|
||||||
Log.w(TAG, "Cannot start ADD_DEVICE_ADMIN as a new task");
|
Log.w(TAG, "Cannot start ADD_DEVICE_ADMIN as a new task");
|
||||||
@@ -235,13 +240,14 @@ public class DeviceAdminAdd extends Activity {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
finish();
|
finish();
|
||||||
} else {
|
} else if (!mWaitingForRemoveMsg) {
|
||||||
try {
|
try {
|
||||||
// Don't allow the admin to put a dialog up in front
|
// Don't allow the admin to put a dialog up in front
|
||||||
// of us while we interact with the user.
|
// of us while we interact with the user.
|
||||||
ActivityManagerNative.getDefault().stopAppSwitches();
|
ActivityManagerNative.getDefault().stopAppSwitches();
|
||||||
} catch (RemoteException e) {
|
} catch (RemoteException e) {
|
||||||
}
|
}
|
||||||
|
mWaitingForRemoveMsg = true;
|
||||||
mDPM.getRemoveWarning(mDeviceAdmin.getComponent(),
|
mDPM.getRemoveWarning(mDeviceAdmin.getComponent(),
|
||||||
new RemoteCallback(mHandler) {
|
new RemoteCallback(mHandler) {
|
||||||
@Override
|
@Override
|
||||||
@@ -250,6 +256,25 @@ public class DeviceAdminAdd extends Activity {
|
|||||||
? bundle.getCharSequence(
|
? bundle.getCharSequence(
|
||||||
DeviceAdminReceiver.EXTRA_DISABLE_WARNING)
|
DeviceAdminReceiver.EXTRA_DISABLE_WARNING)
|
||||||
: null;
|
: null;
|
||||||
|
continueRemoveAction(msg);
|
||||||
|
}
|
||||||
|
});
|
||||||
|
// Don't want to wait too long.
|
||||||
|
getWindow().getDecorView().getHandler().postDelayed(new Runnable() {
|
||||||
|
@Override public void run() {
|
||||||
|
continueRemoveAction(null);
|
||||||
|
}
|
||||||
|
}, 2*1000);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
void continueRemoveAction(CharSequence msg) {
|
||||||
|
if (!mWaitingForRemoveMsg) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
mWaitingForRemoveMsg = false;
|
||||||
if (msg == null) {
|
if (msg == null) {
|
||||||
try {
|
try {
|
||||||
ActivityManagerNative.getDefault().resumeAppSwitches();
|
ActivityManagerNative.getDefault().resumeAppSwitches();
|
||||||
@@ -258,22 +283,43 @@ public class DeviceAdminAdd extends Activity {
|
|||||||
mDPM.removeActiveAdmin(mDeviceAdmin.getComponent());
|
mDPM.removeActiveAdmin(mDeviceAdmin.getComponent());
|
||||||
finish();
|
finish();
|
||||||
} else {
|
} else {
|
||||||
|
try {
|
||||||
|
// Continue preventing anything from coming in front.
|
||||||
|
ActivityManagerNative.getDefault().stopAppSwitches();
|
||||||
|
} catch (RemoteException e) {
|
||||||
|
}
|
||||||
Bundle args = new Bundle();
|
Bundle args = new Bundle();
|
||||||
args.putCharSequence(
|
args.putCharSequence(
|
||||||
DeviceAdminReceiver.EXTRA_DISABLE_WARNING, msg);
|
DeviceAdminReceiver.EXTRA_DISABLE_WARNING, msg);
|
||||||
showDialog(DIALOG_WARNING, args);
|
showDialog(DIALOG_WARNING, args);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
});
|
|
||||||
}
|
|
||||||
}
|
|
||||||
});
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
protected void onResume() {
|
protected void onResume() {
|
||||||
super.onResume();
|
super.onResume();
|
||||||
updateInterface();
|
updateInterface();
|
||||||
|
// As long as we are running, don't let this admin overlay stuff on top of the screen.
|
||||||
|
final int uid = mDeviceAdmin.getActivityInfo().applicationInfo.uid;
|
||||||
|
final String pkg = mDeviceAdmin.getActivityInfo().applicationInfo.packageName;
|
||||||
|
mCurSysAppOpMode = mAppOps.checkOp(AppOpsManager.OP_SYSTEM_ALERT_WINDOW, uid, pkg);
|
||||||
|
mCurToastAppOpMode = mAppOps.checkOp(AppOpsManager.OP_TOAST_WINDOW, uid, pkg);
|
||||||
|
mAppOps.setMode(AppOpsManager.OP_SYSTEM_ALERT_WINDOW, uid, pkg, AppOpsManager.MODE_IGNORED);
|
||||||
|
mAppOps.setMode(AppOpsManager.OP_TOAST_WINDOW, uid, pkg, AppOpsManager.MODE_IGNORED);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
protected void onPause() {
|
||||||
|
super.onPause();
|
||||||
|
// As long as we are running, don't let this admin overlay stuff on top of the screen.
|
||||||
|
final int uid = mDeviceAdmin.getActivityInfo().applicationInfo.uid;
|
||||||
|
final String pkg = mDeviceAdmin.getActivityInfo().applicationInfo.packageName;
|
||||||
|
mAppOps.setMode(AppOpsManager.OP_SYSTEM_ALERT_WINDOW, uid, pkg, mCurSysAppOpMode);
|
||||||
|
mAppOps.setMode(AppOpsManager.OP_TOAST_WINDOW, uid, pkg, mCurToastAppOpMode);
|
||||||
|
try {
|
||||||
|
ActivityManagerNative.getDefault().resumeAppSwitches();
|
||||||
|
} catch (RemoteException e) {
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
@@ -287,6 +333,10 @@ public class DeviceAdminAdd extends Activity {
|
|||||||
builder.setPositiveButton(R.string.dlg_ok,
|
builder.setPositiveButton(R.string.dlg_ok,
|
||||||
new DialogInterface.OnClickListener() {
|
new DialogInterface.OnClickListener() {
|
||||||
public void onClick(DialogInterface dialog, int which) {
|
public void onClick(DialogInterface dialog, int which) {
|
||||||
|
try {
|
||||||
|
ActivityManagerNative.getDefault().resumeAppSwitches();
|
||||||
|
} catch (RemoteException e) {
|
||||||
|
}
|
||||||
mDPM.removeActiveAdmin(mDeviceAdmin.getComponent());
|
mDPM.removeActiveAdmin(mDeviceAdmin.getComponent());
|
||||||
finish();
|
finish();
|
||||||
}
|
}
|
||||||
|
Reference in New Issue
Block a user