DevicePolicyManagerService.java revision 22745f4c9ad0e5abc58fe9ff93e9952a601cc6c9
1/*
2 * Copyright (C) 2010 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
17package com.android.server.devicepolicy;
18
19import static android.Manifest.permission.MANAGE_CA_CERTIFICATES;
20
21import com.android.internal.R;
22import com.android.internal.app.IAppOpsService;
23import com.android.internal.os.storage.ExternalStorageFormatter;
24import com.android.internal.util.FastXmlSerializer;
25import com.android.internal.util.JournaledFile;
26import com.android.internal.util.XmlUtils;
27import com.android.internal.widget.LockPatternUtils;
28import com.android.org.conscrypt.TrustedCertificateStore;
29import com.android.server.SystemService;
30
31import android.app.Activity;
32import android.app.ActivityManagerNative;
33import android.app.AlarmManager;
34import android.app.AppGlobals;
35import android.app.Notification;
36import android.app.NotificationManager;
37import android.app.PendingIntent;
38import android.app.admin.DeviceAdminInfo;
39import android.app.admin.DeviceAdminReceiver;
40import android.app.admin.DevicePolicyManager;
41import android.app.admin.IDevicePolicyManager;
42import android.content.BroadcastReceiver;
43import android.content.ComponentName;
44import android.content.ContentResolver;
45import android.content.Context;
46import android.content.Intent;
47import android.content.IntentFilter;
48import android.content.pm.ActivityInfo;
49import android.content.pm.ApplicationInfo;
50import android.content.pm.IPackageManager;
51import android.content.pm.PackageManager;
52import android.content.pm.ResolveInfo;
53import android.content.pm.UserInfo;
54import android.net.ProxyInfo;
55import android.os.Binder;
56import android.os.Bundle;
57import android.os.Environment;
58import android.os.Handler;
59import android.os.IBinder;
60import android.os.IPowerManager;
61import android.os.PowerManager;
62import android.os.Process;
63import android.os.RecoverySystem;
64import android.os.RemoteCallback;
65import android.os.RemoteException;
66import android.os.ServiceManager;
67import android.os.SystemClock;
68import android.os.SystemProperties;
69import android.os.UserHandle;
70import android.os.UserManager;
71import android.provider.Settings;
72import android.security.Credentials;
73import android.security.IKeyChainService;
74import android.security.KeyChain;
75import android.security.KeyChain.KeyChainConnection;
76import android.util.Log;
77import android.util.PrintWriterPrinter;
78import android.util.Printer;
79import android.util.Slog;
80import android.util.SparseArray;
81import android.util.Xml;
82import android.view.IWindowManager;
83
84import org.xmlpull.v1.XmlPullParser;
85import org.xmlpull.v1.XmlPullParserException;
86import org.xmlpull.v1.XmlSerializer;
87
88import java.io.ByteArrayInputStream;
89import java.io.File;
90import java.io.FileDescriptor;
91import java.io.FileInputStream;
92import java.io.FileNotFoundException;
93import java.io.FileOutputStream;
94import java.io.IOException;
95import java.io.PrintWriter;
96import java.security.cert.CertificateException;
97import java.security.cert.CertificateFactory;
98import java.security.cert.X509Certificate;
99import java.text.DateFormat;
100import java.util.ArrayList;
101import java.util.Arrays;
102import java.util.Collections;
103import java.util.Date;
104import java.util.HashMap;
105import java.util.HashSet;
106import java.util.List;
107import java.util.Set;
108
109/**
110 * Implementation of the device policy APIs.
111 */
112public class DevicePolicyManagerService extends IDevicePolicyManager.Stub {
113
114    private static final String LOG_TAG = "DevicePolicyManagerService";
115
116    private static final String DEVICE_POLICIES_XML = "device_policies.xml";
117
118    private static final String LOCK_TASK_COMPONENTS_XML = "lock-task-component";
119
120    private static final int REQUEST_EXPIRE_PASSWORD = 5571;
121
122    private static final long MS_PER_DAY = 86400 * 1000;
123
124    private static final long EXPIRATION_GRACE_PERIOD_MS = 5 * MS_PER_DAY; // 5 days, in ms
125
126    protected static final String ACTION_EXPIRED_PASSWORD_NOTIFICATION
127            = "com.android.server.ACTION_EXPIRED_PASSWORD_NOTIFICATION";
128
129    private static final int MONITORING_CERT_NOTIFICATION_ID = R.string.ssl_ca_cert_warning;
130
131    private static final boolean DBG = false;
132
133    private static final String ATTR_PERMISSION_PROVIDER = "permission-provider";
134
135    final Context mContext;
136    final UserManager mUserManager;
137    final PowerManager.WakeLock mWakeLock;
138
139    IPowerManager mIPowerManager;
140    IWindowManager mIWindowManager;
141    NotificationManager mNotificationManager;
142
143    // Stores and loads state on device and profile owners.
144    private DeviceOwner mDeviceOwner;
145
146    /**
147     * Whether or not device admin feature is supported. If it isn't return defaults for all
148     * public methods.
149     */
150    private boolean mHasFeature;
151
152    public static final class Lifecycle extends SystemService {
153        private DevicePolicyManagerService mService;
154
155        public Lifecycle(Context context) {
156            super(context);
157            mService = new DevicePolicyManagerService(context);
158        }
159
160        @Override
161        public void onStart() {
162            publishBinderService(Context.DEVICE_POLICY_SERVICE, mService);
163        }
164
165        @Override
166        public void onBootPhase(int phase) {
167            if (phase == PHASE_LOCK_SETTINGS_READY) {
168                mService.systemReady();
169            }
170        }
171    }
172    public static class DevicePolicyData {
173        int mActivePasswordQuality = DevicePolicyManager.PASSWORD_QUALITY_UNSPECIFIED;
174        int mActivePasswordLength = 0;
175        int mActivePasswordUpperCase = 0;
176        int mActivePasswordLowerCase = 0;
177        int mActivePasswordLetters = 0;
178        int mActivePasswordNumeric = 0;
179        int mActivePasswordSymbols = 0;
180        int mActivePasswordNonLetter = 0;
181        int mFailedPasswordAttempts = 0;
182
183        int mUserHandle;
184        int mPasswordOwner = -1;
185        long mLastMaximumTimeToLock = -1;
186
187        final HashMap<ComponentName, ActiveAdmin> mAdminMap
188                = new HashMap<ComponentName, ActiveAdmin>();
189        final ArrayList<ActiveAdmin> mAdminList
190                = new ArrayList<ActiveAdmin>();
191
192        // This is the list of component allowed to start lock task mode.
193        final List<ComponentName> mLockTaskComponents = new ArrayList<ComponentName>();
194
195        ComponentName mRestrictionsProvider;
196
197        public DevicePolicyData(int userHandle) {
198            mUserHandle = userHandle;
199        }
200    }
201
202    final SparseArray<DevicePolicyData> mUserData = new SparseArray<DevicePolicyData>();
203
204    Handler mHandler = new Handler();
205
206    BroadcastReceiver mReceiver = new BroadcastReceiver() {
207        @Override
208        public void onReceive(Context context, Intent intent) {
209            final String action = intent.getAction();
210            final int userHandle = intent.getIntExtra(Intent.EXTRA_USER_HANDLE,
211                    getSendingUserId());
212            if (Intent.ACTION_BOOT_COMPLETED.equals(action)
213                    || ACTION_EXPIRED_PASSWORD_NOTIFICATION.equals(action)) {
214                if (DBG) Slog.v(LOG_TAG, "Sending password expiration notifications for action "
215                        + action + " for user " + userHandle);
216                mHandler.post(new Runnable() {
217                    public void run() {
218                        handlePasswordExpirationNotification(userHandle);
219                    }
220                });
221            }
222            if (Intent.ACTION_BOOT_COMPLETED.equals(action)
223                    || KeyChain.ACTION_STORAGE_CHANGED.equals(action)) {
224                manageMonitoringCertificateNotification(intent);
225            }
226            if (Intent.ACTION_USER_REMOVED.equals(action)) {
227                removeUserData(userHandle);
228            } else if (Intent.ACTION_USER_STARTED.equals(action)
229                    || Intent.ACTION_PACKAGE_CHANGED.equals(action)
230                    || Intent.ACTION_PACKAGE_REMOVED.equals(action)
231                    || Intent.ACTION_EXTERNAL_APPLICATIONS_UNAVAILABLE.equals(action)) {
232
233                if (Intent.ACTION_USER_STARTED.equals(action)) {
234                    // Reset the policy data
235                    synchronized (DevicePolicyManagerService.this) {
236                        mUserData.remove(userHandle);
237                    }
238                }
239
240                handlePackagesChanged(userHandle);
241            }
242        }
243    };
244
245    private IAppOpsService mAppOpsService;
246
247    static class ActiveAdmin {
248        private static final String TAG_DISABLE_KEYGUARD_FEATURES = "disable-keyguard-features";
249        private static final String TAG_DISABLE_CAMERA = "disable-camera";
250        private static final String TAG_DISABLE_ACCOUNT_MANAGEMENT = "disable-account-management";
251        private static final String TAG_ACCOUNT_TYPE = "account-type";
252        private static final String TAG_ENCRYPTION_REQUESTED = "encryption-requested";
253        private static final String TAG_PASSWORD_EXPIRATION_DATE = "password-expiration-date";
254        private static final String TAG_PASSWORD_EXPIRATION_TIMEOUT = "password-expiration-timeout";
255        private static final String TAG_GLOBAL_PROXY_EXCLUSION_LIST = "global-proxy-exclusion-list";
256        private static final String TAG_GLOBAL_PROXY_SPEC = "global-proxy-spec";
257        private static final String TAG_SPECIFIES_GLOBAL_PROXY = "specifies-global-proxy";
258        private static final String TAG_MAX_FAILED_PASSWORD_WIPE = "max-failed-password-wipe";
259        private static final String TAG_MAX_TIME_TO_UNLOCK = "max-time-to-unlock";
260        private static final String TAG_MIN_PASSWORD_NONLETTER = "min-password-nonletter";
261        private static final String TAG_MIN_PASSWORD_SYMBOLS = "min-password-symbols";
262        private static final String TAG_MIN_PASSWORD_NUMERIC = "min-password-numeric";
263        private static final String TAG_MIN_PASSWORD_LETTERS = "min-password-letters";
264        private static final String TAG_MIN_PASSWORD_LOWERCASE = "min-password-lowercase";
265        private static final String TAG_MIN_PASSWORD_UPPERCASE = "min-password-uppercase";
266        private static final String TAG_PASSWORD_HISTORY_LENGTH = "password-history-length";
267        private static final String TAG_MIN_PASSWORD_LENGTH = "min-password-length";
268        private static final String ATTR_VALUE = "value";
269        private static final String TAG_PASSWORD_QUALITY = "password-quality";
270        private static final String TAG_POLICIES = "policies";
271
272        final DeviceAdminInfo info;
273
274        int passwordQuality = DevicePolicyManager.PASSWORD_QUALITY_UNSPECIFIED;
275
276        static final int DEF_MINIMUM_PASSWORD_LENGTH = 0;
277        int minimumPasswordLength = DEF_MINIMUM_PASSWORD_LENGTH;
278
279        static final int DEF_PASSWORD_HISTORY_LENGTH = 0;
280        int passwordHistoryLength = DEF_PASSWORD_HISTORY_LENGTH;
281
282        static final int DEF_MINIMUM_PASSWORD_UPPER_CASE = 0;
283        int minimumPasswordUpperCase = DEF_MINIMUM_PASSWORD_UPPER_CASE;
284
285        static final int DEF_MINIMUM_PASSWORD_LOWER_CASE = 0;
286        int minimumPasswordLowerCase = DEF_MINIMUM_PASSWORD_LOWER_CASE;
287
288        static final int DEF_MINIMUM_PASSWORD_LETTERS = 1;
289        int minimumPasswordLetters = DEF_MINIMUM_PASSWORD_LETTERS;
290
291        static final int DEF_MINIMUM_PASSWORD_NUMERIC = 1;
292        int minimumPasswordNumeric = DEF_MINIMUM_PASSWORD_NUMERIC;
293
294        static final int DEF_MINIMUM_PASSWORD_SYMBOLS = 1;
295        int minimumPasswordSymbols = DEF_MINIMUM_PASSWORD_SYMBOLS;
296
297        static final int DEF_MINIMUM_PASSWORD_NON_LETTER = 0;
298        int minimumPasswordNonLetter = DEF_MINIMUM_PASSWORD_NON_LETTER;
299
300        static final long DEF_MAXIMUM_TIME_TO_UNLOCK = 0;
301        long maximumTimeToUnlock = DEF_MAXIMUM_TIME_TO_UNLOCK;
302
303        static final int DEF_MAXIMUM_FAILED_PASSWORDS_FOR_WIPE = 0;
304        int maximumFailedPasswordsForWipe = DEF_MAXIMUM_FAILED_PASSWORDS_FOR_WIPE;
305
306        static final long DEF_PASSWORD_EXPIRATION_TIMEOUT = 0;
307        long passwordExpirationTimeout = DEF_PASSWORD_EXPIRATION_TIMEOUT;
308
309        static final long DEF_PASSWORD_EXPIRATION_DATE = 0;
310        long passwordExpirationDate = DEF_PASSWORD_EXPIRATION_DATE;
311
312        static final int DEF_KEYGUARD_FEATURES_DISABLED = 0; // none
313        int disabledKeyguardFeatures = DEF_KEYGUARD_FEATURES_DISABLED;
314
315        boolean encryptionRequested = false;
316        boolean disableCamera = false;
317        Set<String> accountTypesWithManagementDisabled = new HashSet<String>();
318
319        // TODO: review implementation decisions with frameworks team
320        boolean specifiesGlobalProxy = false;
321        String globalProxySpec = null;
322        String globalProxyExclusionList = null;
323
324        ActiveAdmin(DeviceAdminInfo _info) {
325            info = _info;
326        }
327
328        int getUid() { return info.getActivityInfo().applicationInfo.uid; }
329
330        public UserHandle getUserHandle() {
331            return new UserHandle(UserHandle.getUserId(info.getActivityInfo().applicationInfo.uid));
332        }
333
334        void writeToXml(XmlSerializer out)
335                throws IllegalArgumentException, IllegalStateException, IOException {
336            out.startTag(null, TAG_POLICIES);
337            info.writePoliciesToXml(out);
338            out.endTag(null, TAG_POLICIES);
339            if (passwordQuality != DevicePolicyManager.PASSWORD_QUALITY_UNSPECIFIED) {
340                out.startTag(null, TAG_PASSWORD_QUALITY);
341                out.attribute(null, ATTR_VALUE, Integer.toString(passwordQuality));
342                out.endTag(null, TAG_PASSWORD_QUALITY);
343                if (minimumPasswordLength != DEF_MINIMUM_PASSWORD_LENGTH) {
344                    out.startTag(null, TAG_MIN_PASSWORD_LENGTH);
345                    out.attribute(null, ATTR_VALUE, Integer.toString(minimumPasswordLength));
346                    out.endTag(null, TAG_MIN_PASSWORD_LENGTH);
347                }
348                if(passwordHistoryLength != DEF_PASSWORD_HISTORY_LENGTH) {
349                    out.startTag(null, TAG_PASSWORD_HISTORY_LENGTH);
350                    out.attribute(null, ATTR_VALUE, Integer.toString(passwordHistoryLength));
351                    out.endTag(null, TAG_PASSWORD_HISTORY_LENGTH);
352                }
353                if (minimumPasswordUpperCase != DEF_MINIMUM_PASSWORD_UPPER_CASE) {
354                    out.startTag(null, TAG_MIN_PASSWORD_UPPERCASE);
355                    out.attribute(null, ATTR_VALUE, Integer.toString(minimumPasswordUpperCase));
356                    out.endTag(null, TAG_MIN_PASSWORD_UPPERCASE);
357                }
358                if (minimumPasswordLowerCase != DEF_MINIMUM_PASSWORD_LOWER_CASE) {
359                    out.startTag(null, TAG_MIN_PASSWORD_LOWERCASE);
360                    out.attribute(null, ATTR_VALUE, Integer.toString(minimumPasswordLowerCase));
361                    out.endTag(null, TAG_MIN_PASSWORD_LOWERCASE);
362                }
363                if (minimumPasswordLetters != DEF_MINIMUM_PASSWORD_LETTERS) {
364                    out.startTag(null, TAG_MIN_PASSWORD_LETTERS);
365                    out.attribute(null, ATTR_VALUE, Integer.toString(minimumPasswordLetters));
366                    out.endTag(null, TAG_MIN_PASSWORD_LETTERS);
367                }
368                if (minimumPasswordNumeric != DEF_MINIMUM_PASSWORD_NUMERIC) {
369                    out.startTag(null, TAG_MIN_PASSWORD_NUMERIC);
370                    out.attribute(null, ATTR_VALUE, Integer.toString(minimumPasswordNumeric));
371                    out.endTag(null, TAG_MIN_PASSWORD_NUMERIC);
372                }
373                if (minimumPasswordSymbols != DEF_MINIMUM_PASSWORD_SYMBOLS) {
374                    out.startTag(null, TAG_MIN_PASSWORD_SYMBOLS);
375                    out.attribute(null, ATTR_VALUE, Integer.toString(minimumPasswordSymbols));
376                    out.endTag(null, TAG_MIN_PASSWORD_SYMBOLS);
377                }
378                if (minimumPasswordNonLetter > DEF_MINIMUM_PASSWORD_NON_LETTER) {
379                    out.startTag(null, TAG_MIN_PASSWORD_NONLETTER);
380                    out.attribute(null, ATTR_VALUE, Integer.toString(minimumPasswordNonLetter));
381                    out.endTag(null, TAG_MIN_PASSWORD_NONLETTER);
382                }
383            }
384            if (maximumTimeToUnlock != DEF_MAXIMUM_TIME_TO_UNLOCK) {
385                out.startTag(null, TAG_MAX_TIME_TO_UNLOCK);
386                out.attribute(null, ATTR_VALUE, Long.toString(maximumTimeToUnlock));
387                out.endTag(null, TAG_MAX_TIME_TO_UNLOCK);
388            }
389            if (maximumFailedPasswordsForWipe != DEF_MAXIMUM_FAILED_PASSWORDS_FOR_WIPE) {
390                out.startTag(null, TAG_MAX_FAILED_PASSWORD_WIPE);
391                out.attribute(null, ATTR_VALUE, Integer.toString(maximumFailedPasswordsForWipe));
392                out.endTag(null, TAG_MAX_FAILED_PASSWORD_WIPE);
393            }
394            if (specifiesGlobalProxy) {
395                out.startTag(null, TAG_SPECIFIES_GLOBAL_PROXY);
396                out.attribute(null, ATTR_VALUE, Boolean.toString(specifiesGlobalProxy));
397                out.endTag(null, TAG_SPECIFIES_GLOBAL_PROXY);
398                if (globalProxySpec != null) {
399                    out.startTag(null, TAG_GLOBAL_PROXY_SPEC);
400                    out.attribute(null, ATTR_VALUE, globalProxySpec);
401                    out.endTag(null, TAG_GLOBAL_PROXY_SPEC);
402                }
403                if (globalProxyExclusionList != null) {
404                    out.startTag(null, TAG_GLOBAL_PROXY_EXCLUSION_LIST);
405                    out.attribute(null, ATTR_VALUE, globalProxyExclusionList);
406                    out.endTag(null, TAG_GLOBAL_PROXY_EXCLUSION_LIST);
407                }
408            }
409            if (passwordExpirationTimeout != DEF_PASSWORD_EXPIRATION_TIMEOUT) {
410                out.startTag(null, TAG_PASSWORD_EXPIRATION_TIMEOUT);
411                out.attribute(null, ATTR_VALUE, Long.toString(passwordExpirationTimeout));
412                out.endTag(null, TAG_PASSWORD_EXPIRATION_TIMEOUT);
413            }
414            if (passwordExpirationDate != DEF_PASSWORD_EXPIRATION_DATE) {
415                out.startTag(null, TAG_PASSWORD_EXPIRATION_DATE);
416                out.attribute(null, ATTR_VALUE, Long.toString(passwordExpirationDate));
417                out.endTag(null, TAG_PASSWORD_EXPIRATION_DATE);
418            }
419            if (encryptionRequested) {
420                out.startTag(null, TAG_ENCRYPTION_REQUESTED);
421                out.attribute(null, ATTR_VALUE, Boolean.toString(encryptionRequested));
422                out.endTag(null, TAG_ENCRYPTION_REQUESTED);
423            }
424            if (disableCamera) {
425                out.startTag(null, TAG_DISABLE_CAMERA);
426                out.attribute(null, ATTR_VALUE, Boolean.toString(disableCamera));
427                out.endTag(null, TAG_DISABLE_CAMERA);
428            }
429            if (disabledKeyguardFeatures != DEF_KEYGUARD_FEATURES_DISABLED) {
430                out.startTag(null, TAG_DISABLE_KEYGUARD_FEATURES);
431                out.attribute(null, ATTR_VALUE, Integer.toString(disabledKeyguardFeatures));
432                out.endTag(null, TAG_DISABLE_KEYGUARD_FEATURES);
433            }
434            if (!accountTypesWithManagementDisabled.isEmpty()) {
435                out.startTag(null, TAG_DISABLE_ACCOUNT_MANAGEMENT);
436                for (String ac : accountTypesWithManagementDisabled) {
437                    out.startTag(null, TAG_ACCOUNT_TYPE);
438                    out.attribute(null, ATTR_VALUE, ac);
439                    out.endTag(null, TAG_ACCOUNT_TYPE);
440                }
441                out.endTag(null,  TAG_DISABLE_ACCOUNT_MANAGEMENT);
442            }
443        }
444
445        void readFromXml(XmlPullParser parser)
446                throws XmlPullParserException, IOException {
447            int outerDepth = parser.getDepth();
448            int type;
449            while ((type=parser.next()) != XmlPullParser.END_DOCUMENT
450                   && (type != XmlPullParser.END_TAG || parser.getDepth() > outerDepth)) {
451                if (type == XmlPullParser.END_TAG || type == XmlPullParser.TEXT) {
452                    continue;
453                }
454                String tag = parser.getName();
455                if (TAG_POLICIES.equals(tag)) {
456                    info.readPoliciesFromXml(parser);
457                } else if (TAG_PASSWORD_QUALITY.equals(tag)) {
458                    passwordQuality = Integer.parseInt(
459                            parser.getAttributeValue(null, ATTR_VALUE));
460                } else if (TAG_MIN_PASSWORD_LENGTH.equals(tag)) {
461                    minimumPasswordLength = Integer.parseInt(
462                            parser.getAttributeValue(null, ATTR_VALUE));
463                } else if (TAG_PASSWORD_HISTORY_LENGTH.equals(tag)) {
464                    passwordHistoryLength = Integer.parseInt(
465                            parser.getAttributeValue(null, ATTR_VALUE));
466                } else if (TAG_MIN_PASSWORD_UPPERCASE.equals(tag)) {
467                    minimumPasswordUpperCase = Integer.parseInt(
468                            parser.getAttributeValue(null, ATTR_VALUE));
469                } else if (TAG_MIN_PASSWORD_LOWERCASE.equals(tag)) {
470                    minimumPasswordLowerCase = Integer.parseInt(
471                            parser.getAttributeValue(null, ATTR_VALUE));
472                } else if (TAG_MIN_PASSWORD_LETTERS.equals(tag)) {
473                    minimumPasswordLetters = Integer.parseInt(
474                            parser.getAttributeValue(null, ATTR_VALUE));
475                } else if (TAG_MIN_PASSWORD_NUMERIC.equals(tag)) {
476                    minimumPasswordNumeric = Integer.parseInt(
477                            parser.getAttributeValue(null, ATTR_VALUE));
478                } else if (TAG_MIN_PASSWORD_SYMBOLS.equals(tag)) {
479                    minimumPasswordSymbols = Integer.parseInt(
480                            parser.getAttributeValue(null, ATTR_VALUE));
481                } else if (TAG_MIN_PASSWORD_NONLETTER.equals(tag)) {
482                    minimumPasswordNonLetter = Integer.parseInt(
483                            parser.getAttributeValue(null, ATTR_VALUE));
484                } else if (TAG_MAX_TIME_TO_UNLOCK.equals(tag)) {
485                    maximumTimeToUnlock = Long.parseLong(
486                            parser.getAttributeValue(null, ATTR_VALUE));
487                } else if (TAG_MAX_FAILED_PASSWORD_WIPE.equals(tag)) {
488                    maximumFailedPasswordsForWipe = Integer.parseInt(
489                            parser.getAttributeValue(null, ATTR_VALUE));
490                } else if (TAG_SPECIFIES_GLOBAL_PROXY.equals(tag)) {
491                    specifiesGlobalProxy = Boolean.parseBoolean(
492                            parser.getAttributeValue(null, ATTR_VALUE));
493                } else if (TAG_GLOBAL_PROXY_SPEC.equals(tag)) {
494                    globalProxySpec =
495                        parser.getAttributeValue(null, ATTR_VALUE);
496                } else if (TAG_GLOBAL_PROXY_EXCLUSION_LIST.equals(tag)) {
497                    globalProxyExclusionList =
498                        parser.getAttributeValue(null, ATTR_VALUE);
499                } else if (TAG_PASSWORD_EXPIRATION_TIMEOUT.equals(tag)) {
500                    passwordExpirationTimeout = Long.parseLong(
501                            parser.getAttributeValue(null, ATTR_VALUE));
502                } else if (TAG_PASSWORD_EXPIRATION_DATE.equals(tag)) {
503                    passwordExpirationDate = Long.parseLong(
504                            parser.getAttributeValue(null, ATTR_VALUE));
505                } else if (TAG_ENCRYPTION_REQUESTED.equals(tag)) {
506                    encryptionRequested = Boolean.parseBoolean(
507                            parser.getAttributeValue(null, ATTR_VALUE));
508                } else if (TAG_DISABLE_CAMERA.equals(tag)) {
509                    disableCamera = Boolean.parseBoolean(
510                            parser.getAttributeValue(null, ATTR_VALUE));
511                } else if (TAG_DISABLE_KEYGUARD_FEATURES.equals(tag)) {
512                    disabledKeyguardFeatures = Integer.parseInt(
513                            parser.getAttributeValue(null, ATTR_VALUE));
514                } else if (TAG_DISABLE_ACCOUNT_MANAGEMENT.equals(tag)) {
515                    int outerDepthDAM = parser.getDepth();
516                    int typeDAM;
517                    while ((typeDAM=parser.next()) != XmlPullParser.END_DOCUMENT
518                            && (typeDAM != XmlPullParser.END_TAG
519                                    || parser.getDepth() > outerDepthDAM)) {
520                        if (typeDAM == XmlPullParser.END_TAG || typeDAM == XmlPullParser.TEXT) {
521                            continue;
522                        }
523                        String tagDAM = parser.getName();
524                        if (TAG_ACCOUNT_TYPE.equals(tagDAM)) {
525                            accountTypesWithManagementDisabled.add(
526                                    parser.getAttributeValue(null, ATTR_VALUE));
527                        } else {
528                            Slog.w(LOG_TAG, "Unknown tag under " + tag +  ": " + tagDAM);
529                        }
530                    }
531                } else {
532                    Slog.w(LOG_TAG, "Unknown admin tag: " + tag);
533                }
534                XmlUtils.skipCurrentTag(parser);
535            }
536        }
537
538        void dump(String prefix, PrintWriter pw) {
539            pw.print(prefix); pw.print("uid="); pw.println(getUid());
540            pw.print(prefix); pw.println("policies:");
541            ArrayList<DeviceAdminInfo.PolicyInfo> pols = info.getUsedPolicies();
542            if (pols != null) {
543                for (int i=0; i<pols.size(); i++) {
544                    pw.print(prefix); pw.print("  "); pw.println(pols.get(i).tag);
545                }
546            }
547            pw.print(prefix); pw.print("passwordQuality=0x");
548                    pw.println(Integer.toHexString(passwordQuality));
549            pw.print(prefix); pw.print("minimumPasswordLength=");
550                    pw.println(minimumPasswordLength);
551            pw.print(prefix); pw.print("passwordHistoryLength=");
552                    pw.println(passwordHistoryLength);
553            pw.print(prefix); pw.print("minimumPasswordUpperCase=");
554                    pw.println(minimumPasswordUpperCase);
555            pw.print(prefix); pw.print("minimumPasswordLowerCase=");
556                    pw.println(minimumPasswordLowerCase);
557            pw.print(prefix); pw.print("minimumPasswordLetters=");
558                    pw.println(minimumPasswordLetters);
559            pw.print(prefix); pw.print("minimumPasswordNumeric=");
560                    pw.println(minimumPasswordNumeric);
561            pw.print(prefix); pw.print("minimumPasswordSymbols=");
562                    pw.println(minimumPasswordSymbols);
563            pw.print(prefix); pw.print("minimumPasswordNonLetter=");
564                    pw.println(minimumPasswordNonLetter);
565            pw.print(prefix); pw.print("maximumTimeToUnlock=");
566                    pw.println(maximumTimeToUnlock);
567            pw.print(prefix); pw.print("maximumFailedPasswordsForWipe=");
568                    pw.println(maximumFailedPasswordsForWipe);
569            pw.print(prefix); pw.print("specifiesGlobalProxy=");
570                    pw.println(specifiesGlobalProxy);
571            pw.print(prefix); pw.print("passwordExpirationTimeout=");
572                    pw.println(passwordExpirationTimeout);
573            pw.print(prefix); pw.print("passwordExpirationDate=");
574                    pw.println(passwordExpirationDate);
575            if (globalProxySpec != null) {
576                pw.print(prefix); pw.print("globalProxySpec=");
577                        pw.println(globalProxySpec);
578            }
579            if (globalProxyExclusionList != null) {
580                pw.print(prefix); pw.print("globalProxyEclusionList=");
581                        pw.println(globalProxyExclusionList);
582            }
583            pw.print(prefix); pw.print("encryptionRequested=");
584                    pw.println(encryptionRequested);
585            pw.print(prefix); pw.print("disableCamera=");
586                    pw.println(disableCamera);
587            pw.print(prefix); pw.print("disabledKeyguardFeatures=");
588                    pw.println(disabledKeyguardFeatures);
589        }
590    }
591
592    private void handlePackagesChanged(int userHandle) {
593        boolean removed = false;
594        if (DBG) Slog.d(LOG_TAG, "Handling package changes for user " + userHandle);
595        DevicePolicyData policy = getUserData(userHandle);
596        IPackageManager pm = AppGlobals.getPackageManager();
597        for (int i = policy.mAdminList.size() - 1; i >= 0; i--) {
598            ActiveAdmin aa = policy.mAdminList.get(i);
599            try {
600                if (pm.getPackageInfo(aa.info.getPackageName(), 0, userHandle) == null
601                        || pm.getReceiverInfo(aa.info.getComponent(), 0, userHandle) == null) {
602                    removed = true;
603                    policy.mAdminList.remove(i);
604                    policy.mAdminMap.remove(aa.info.getComponent());
605                }
606            } catch (RemoteException re) {
607                // Shouldn't happen
608            }
609        }
610        if (removed) {
611            validatePasswordOwnerLocked(policy);
612            syncDeviceCapabilitiesLocked(policy);
613            saveSettingsLocked(policy.mUserHandle);
614        }
615    }
616
617    /**
618     * Instantiates the service.
619     */
620    public DevicePolicyManagerService(Context context) {
621        mContext = context;
622        mUserManager = UserManager.get(mContext);
623        mHasFeature = context.getPackageManager().hasSystemFeature(
624                PackageManager.FEATURE_DEVICE_ADMIN);
625        mWakeLock = ((PowerManager)context.getSystemService(Context.POWER_SERVICE))
626                .newWakeLock(PowerManager.PARTIAL_WAKE_LOCK, "DPM");
627        if (!mHasFeature) {
628            // Skip the rest of the initialization
629            return;
630        }
631        IntentFilter filter = new IntentFilter();
632        filter.addAction(Intent.ACTION_BOOT_COMPLETED);
633        filter.addAction(ACTION_EXPIRED_PASSWORD_NOTIFICATION);
634        filter.addAction(Intent.ACTION_USER_REMOVED);
635        filter.addAction(Intent.ACTION_USER_STARTED);
636        filter.addAction(KeyChain.ACTION_STORAGE_CHANGED);
637        filter.setPriority(IntentFilter.SYSTEM_HIGH_PRIORITY);
638        context.registerReceiverAsUser(mReceiver, UserHandle.ALL, filter, null, mHandler);
639        filter = new IntentFilter();
640        filter.addAction(Intent.ACTION_PACKAGE_CHANGED);
641        filter.addAction(Intent.ACTION_PACKAGE_REMOVED);
642        filter.addAction(Intent.ACTION_EXTERNAL_APPLICATIONS_UNAVAILABLE);
643        filter.addAction(Intent.ACTION_PACKAGE_ADDED);
644        filter.addDataScheme("package");
645        context.registerReceiverAsUser(mReceiver, UserHandle.ALL, filter, null, mHandler);
646    }
647
648    /**
649     * Creates and loads the policy data from xml.
650     * @param userHandle the user for whom to load the policy data
651     * @return
652     */
653    DevicePolicyData getUserData(int userHandle) {
654        synchronized (this) {
655            DevicePolicyData policy = mUserData.get(userHandle);
656            if (policy == null) {
657                policy = new DevicePolicyData(userHandle);
658                mUserData.append(userHandle, policy);
659                loadSettingsLocked(policy, userHandle);
660            }
661            return policy;
662        }
663    }
664
665    void removeUserData(int userHandle) {
666        synchronized (this) {
667            if (userHandle == UserHandle.USER_OWNER) {
668                Slog.w(LOG_TAG, "Tried to remove device policy file for user 0! Ignoring.");
669                return;
670            }
671            if (mDeviceOwner != null) {
672                mDeviceOwner.removeProfileOwner(userHandle);
673                mDeviceOwner.writeOwnerFile();
674            }
675
676            DevicePolicyData policy = mUserData.get(userHandle);
677            if (policy != null) {
678                mUserData.remove(userHandle);
679            }
680            File policyFile = new File(Environment.getUserSystemDirectory(userHandle),
681                    DEVICE_POLICIES_XML);
682            policyFile.delete();
683            Slog.i(LOG_TAG, "Removed device policy file " + policyFile.getAbsolutePath());
684        }
685    }
686
687    void loadDeviceOwner() {
688        synchronized (this) {
689            mDeviceOwner = DeviceOwner.load();
690        }
691    }
692
693    /**
694     * Set an alarm for an upcoming event - expiration warning, expiration, or post-expiration
695     * reminders.  Clears alarm if no expirations are configured.
696     */
697    protected void setExpirationAlarmCheckLocked(Context context, DevicePolicyData policy) {
698        final long expiration = getPasswordExpirationLocked(null, policy.mUserHandle);
699        final long now = System.currentTimeMillis();
700        final long timeToExpire = expiration - now;
701        final long alarmTime;
702        if (expiration == 0) {
703            // No expirations are currently configured:  Cancel alarm.
704            alarmTime = 0;
705        } else if (timeToExpire <= 0) {
706            // The password has already expired:  Repeat every 24 hours.
707            alarmTime = now + MS_PER_DAY;
708        } else {
709            // Selecting the next alarm time:  Roll forward to the next 24 hour multiple before
710            // the expiration time.
711            long alarmInterval = timeToExpire % MS_PER_DAY;
712            if (alarmInterval == 0) {
713                alarmInterval = MS_PER_DAY;
714            }
715            alarmTime = now + alarmInterval;
716        }
717
718        long token = Binder.clearCallingIdentity();
719        try {
720            AlarmManager am = (AlarmManager) context.getSystemService(Context.ALARM_SERVICE);
721            PendingIntent pi = PendingIntent.getBroadcastAsUser(context, REQUEST_EXPIRE_PASSWORD,
722                    new Intent(ACTION_EXPIRED_PASSWORD_NOTIFICATION),
723                    PendingIntent.FLAG_ONE_SHOT | PendingIntent.FLAG_UPDATE_CURRENT,
724                    new UserHandle(policy.mUserHandle));
725            am.cancel(pi);
726            if (alarmTime != 0) {
727                am.set(AlarmManager.RTC, alarmTime, pi);
728            }
729        } finally {
730            Binder.restoreCallingIdentity(token);
731        }
732    }
733
734    private IPowerManager getIPowerManager() {
735        if (mIPowerManager == null) {
736            IBinder b = ServiceManager.getService(Context.POWER_SERVICE);
737            mIPowerManager = IPowerManager.Stub.asInterface(b);
738        }
739        return mIPowerManager;
740    }
741
742    private IWindowManager getWindowManager() {
743        if (mIWindowManager == null) {
744            IBinder b = ServiceManager.getService(Context.WINDOW_SERVICE);
745            mIWindowManager = IWindowManager.Stub.asInterface(b);
746        }
747        return mIWindowManager;
748    }
749
750    private NotificationManager getNotificationManager() {
751        if (mNotificationManager == null) {
752            mNotificationManager =
753                    (NotificationManager) mContext.getSystemService(Context.NOTIFICATION_SERVICE);
754        }
755        return mNotificationManager;
756    }
757
758    ActiveAdmin getActiveAdminUncheckedLocked(ComponentName who, int userHandle) {
759        ActiveAdmin admin = getUserData(userHandle).mAdminMap.get(who);
760        if (admin != null
761                && who.getPackageName().equals(admin.info.getActivityInfo().packageName)
762                && who.getClassName().equals(admin.info.getActivityInfo().name)) {
763            return admin;
764        }
765        return null;
766    }
767
768    ActiveAdmin getActiveAdminForCallerLocked(ComponentName who, int reqPolicy)
769            throws SecurityException {
770        final int callingUid = Binder.getCallingUid();
771        final int userHandle = UserHandle.getUserId(callingUid);
772        final DevicePolicyData policy = getUserData(userHandle);
773
774        List<ActiveAdmin> candidates = new ArrayList<ActiveAdmin>();
775
776        // Build a list of admins for this uid matching the given ComponentName
777        if (who != null) {
778            ActiveAdmin admin = policy.mAdminMap.get(who);
779            if (admin == null) {
780                throw new SecurityException("No active admin " + who);
781            }
782            if (admin.getUid() != callingUid) {
783                throw new SecurityException("Admin " + who + " is not owned by uid "
784                        + Binder.getCallingUid());
785            }
786            candidates.add(admin);
787        } else {
788            for (ActiveAdmin admin : policy.mAdminList) {
789                if (admin.getUid() == callingUid) {
790                    candidates.add(admin);
791                }
792            }
793        }
794
795        // Try to find an admin which can use reqPolicy
796        for (ActiveAdmin admin : candidates) {
797            boolean ownsDevice = isDeviceOwner(admin.info.getPackageName());
798            boolean ownsProfile = (getProfileOwner(userHandle) != null
799                    && getProfileOwner(userHandle).equals(admin.info.getPackageName()));
800
801            if (reqPolicy == DeviceAdminInfo.USES_POLICY_DEVICE_OWNER) {
802                if (ownsDevice) {
803                    return admin;
804                }
805            } else if (reqPolicy == DeviceAdminInfo.USES_POLICY_PROFILE_OWNER) {
806                if (ownsDevice || ownsProfile) {
807                    return admin;
808                }
809            } else {
810                if (admin.info.usesPolicy(reqPolicy)) {
811                    return admin;
812                }
813            }
814        }
815
816        if (who != null) {
817            throw new SecurityException("Admin " + candidates.get(0).info.getComponent()
818                    + " did not specify uses-policy for: "
819                    + candidates.get(0).info.getTagForPolicy(reqPolicy));
820        } else {
821            throw new SecurityException("No active admin owned by uid "
822                    + Binder.getCallingUid() + " for policy:" + reqPolicy);
823        }
824    }
825
826    void sendAdminCommandLocked(ActiveAdmin admin, String action) {
827        sendAdminCommandLocked(admin, action, null);
828    }
829
830    /**
831     * Send an update to one specific admin, get notified when that admin returns a result.
832     */
833    void sendAdminCommandLocked(ActiveAdmin admin, String action, BroadcastReceiver result) {
834        Intent intent = new Intent(action);
835        intent.setComponent(admin.info.getComponent());
836        if (action.equals(DeviceAdminReceiver.ACTION_PASSWORD_EXPIRING)) {
837            intent.putExtra("expiration", admin.passwordExpirationDate);
838        }
839        if (result != null) {
840            mContext.sendOrderedBroadcastAsUser(intent, admin.getUserHandle(),
841                    null, result, mHandler, Activity.RESULT_OK, null, null);
842        } else {
843            mContext.sendBroadcastAsUser(intent, UserHandle.OWNER);
844        }
845    }
846
847    /**
848     * Send an update to all admins of a user that enforce a specified policy.
849     */
850    void sendAdminCommandLocked(String action, int reqPolicy, int userHandle) {
851        final DevicePolicyData policy = getUserData(userHandle);
852        final int count = policy.mAdminList.size();
853        if (count > 0) {
854            for (int i = 0; i < count; i++) {
855                final ActiveAdmin admin = policy.mAdminList.get(i);
856                if (admin.info.usesPolicy(reqPolicy)) {
857                    sendAdminCommandLocked(admin, action);
858                }
859            }
860        }
861    }
862
863    /**
864     * Send an update intent to all admins of a user and its profiles. Only send to admins that
865     * enforce a specified policy.
866     */
867    private void sendAdminCommandToSelfAndProfilesLocked(String action, int reqPolicy,
868            int userHandle) {
869        List<UserInfo> profiles = mUserManager.getProfiles(userHandle);
870        for (UserInfo ui : profiles) {
871            int id = ui.getUserHandle().getIdentifier();
872            sendAdminCommandLocked(action, reqPolicy, id);
873        }
874    }
875
876    void removeActiveAdminLocked(final ComponentName adminReceiver, int userHandle) {
877        final ActiveAdmin admin = getActiveAdminUncheckedLocked(adminReceiver, userHandle);
878        if (admin != null) {
879            sendAdminCommandLocked(admin,
880                    DeviceAdminReceiver.ACTION_DEVICE_ADMIN_DISABLED,
881                    new BroadcastReceiver() {
882                        @Override
883                        public void onReceive(Context context, Intent intent) {
884                            synchronized (DevicePolicyManagerService.this) {
885                                int userHandle = admin.getUserHandle().getIdentifier();
886                                DevicePolicyData policy = getUserData(userHandle);
887                                boolean doProxyCleanup = admin.info.usesPolicy(
888                                        DeviceAdminInfo.USES_POLICY_SETS_GLOBAL_PROXY);
889                                policy.mAdminList.remove(admin);
890                                policy.mAdminMap.remove(adminReceiver);
891                                validatePasswordOwnerLocked(policy);
892                                syncDeviceCapabilitiesLocked(policy);
893                                if (doProxyCleanup) {
894                                    resetGlobalProxyLocked(getUserData(userHandle));
895                                }
896                                saveSettingsLocked(userHandle);
897                                updateMaximumTimeToLockLocked(policy);
898                            }
899                        }
900            });
901        }
902    }
903
904    public DeviceAdminInfo findAdmin(ComponentName adminName, int userHandle) {
905        if (!mHasFeature) {
906            return null;
907        }
908        enforceCrossUserPermission(userHandle);
909        Intent resolveIntent = new Intent();
910        resolveIntent.setComponent(adminName);
911        List<ResolveInfo> infos = mContext.getPackageManager().queryBroadcastReceivers(
912                resolveIntent,
913                PackageManager.GET_META_DATA | PackageManager.GET_DISABLED_UNTIL_USED_COMPONENTS,
914                userHandle);
915        if (infos == null || infos.size() <= 0) {
916            throw new IllegalArgumentException("Unknown admin: " + adminName);
917        }
918
919        try {
920            return new DeviceAdminInfo(mContext, infos.get(0));
921        } catch (XmlPullParserException e) {
922            Slog.w(LOG_TAG, "Bad device admin requested for user=" + userHandle + ": " + adminName,
923                    e);
924            return null;
925        } catch (IOException e) {
926            Slog.w(LOG_TAG, "Bad device admin requested for user=" + userHandle + ": " + adminName,
927                    e);
928            return null;
929        }
930    }
931
932    private static JournaledFile makeJournaledFile(int userHandle) {
933        final String base = userHandle == 0
934                ? "/data/system/" + DEVICE_POLICIES_XML
935                : new File(Environment.getUserSystemDirectory(userHandle), DEVICE_POLICIES_XML)
936                        .getAbsolutePath();
937        return new JournaledFile(new File(base), new File(base + ".tmp"));
938    }
939
940    private void saveSettingsLocked(int userHandle) {
941        DevicePolicyData policy = getUserData(userHandle);
942        JournaledFile journal = makeJournaledFile(userHandle);
943        FileOutputStream stream = null;
944        try {
945            stream = new FileOutputStream(journal.chooseForWrite(), false);
946            XmlSerializer out = new FastXmlSerializer();
947            out.setOutput(stream, "utf-8");
948            out.startDocument(null, true);
949
950            out.startTag(null, "policies");
951            if (policy.mRestrictionsProvider != null) {
952                out.attribute(null, ATTR_PERMISSION_PROVIDER,
953                        policy.mRestrictionsProvider.flattenToString());
954            }
955
956            final int N = policy.mAdminList.size();
957            for (int i=0; i<N; i++) {
958                ActiveAdmin ap = policy.mAdminList.get(i);
959                if (ap != null) {
960                    out.startTag(null, "admin");
961                    out.attribute(null, "name", ap.info.getComponent().flattenToString());
962                    ap.writeToXml(out);
963                    out.endTag(null, "admin");
964                }
965            }
966
967            if (policy.mPasswordOwner >= 0) {
968                out.startTag(null, "password-owner");
969                out.attribute(null, "value", Integer.toString(policy.mPasswordOwner));
970                out.endTag(null, "password-owner");
971            }
972
973            if (policy.mFailedPasswordAttempts != 0) {
974                out.startTag(null, "failed-password-attempts");
975                out.attribute(null, "value", Integer.toString(policy.mFailedPasswordAttempts));
976                out.endTag(null, "failed-password-attempts");
977            }
978
979            if (policy.mActivePasswordQuality != 0 || policy.mActivePasswordLength != 0
980                    || policy.mActivePasswordUpperCase != 0 || policy.mActivePasswordLowerCase != 0
981                    || policy.mActivePasswordLetters != 0 || policy.mActivePasswordNumeric != 0
982                    || policy.mActivePasswordSymbols != 0 || policy.mActivePasswordNonLetter != 0) {
983                out.startTag(null, "active-password");
984                out.attribute(null, "quality", Integer.toString(policy.mActivePasswordQuality));
985                out.attribute(null, "length", Integer.toString(policy.mActivePasswordLength));
986                out.attribute(null, "uppercase", Integer.toString(policy.mActivePasswordUpperCase));
987                out.attribute(null, "lowercase", Integer.toString(policy.mActivePasswordLowerCase));
988                out.attribute(null, "letters", Integer.toString(policy.mActivePasswordLetters));
989                out.attribute(null, "numeric", Integer
990                        .toString(policy.mActivePasswordNumeric));
991                out.attribute(null, "symbols", Integer.toString(policy.mActivePasswordSymbols));
992                out.attribute(null, "nonletter", Integer.toString(policy.mActivePasswordNonLetter));
993                out.endTag(null, "active-password");
994            }
995
996            for (int i=0; i<policy.mLockTaskComponents.size(); i++) {
997                ComponentName component = policy.mLockTaskComponents.get(i);
998                out.startTag(null, LOCK_TASK_COMPONENTS_XML);
999                out.attribute(null, "name", component.flattenToString());
1000                out.endTag(null, LOCK_TASK_COMPONENTS_XML);
1001            }
1002
1003            out.endTag(null, "policies");
1004
1005            out.endDocument();
1006            stream.close();
1007            journal.commit();
1008            sendChangedNotification(userHandle);
1009        } catch (IOException e) {
1010            try {
1011                if (stream != null) {
1012                    stream.close();
1013                }
1014            } catch (IOException ex) {
1015                // Ignore
1016            }
1017            journal.rollback();
1018        }
1019    }
1020
1021    private void sendChangedNotification(int userHandle) {
1022        Intent intent = new Intent(DevicePolicyManager.ACTION_DEVICE_POLICY_MANAGER_STATE_CHANGED);
1023        intent.setFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY);
1024        long ident = Binder.clearCallingIdentity();
1025        try {
1026            mContext.sendBroadcastAsUser(intent, new UserHandle(userHandle));
1027        } finally {
1028            Binder.restoreCallingIdentity(ident);
1029        }
1030    }
1031
1032    private void loadSettingsLocked(DevicePolicyData policy, int userHandle) {
1033        JournaledFile journal = makeJournaledFile(userHandle);
1034        FileInputStream stream = null;
1035        File file = journal.chooseForRead();
1036        try {
1037            stream = new FileInputStream(file);
1038            XmlPullParser parser = Xml.newPullParser();
1039            parser.setInput(stream, null);
1040
1041            int type;
1042            while ((type=parser.next()) != XmlPullParser.END_DOCUMENT
1043                    && type != XmlPullParser.START_TAG) {
1044            }
1045            String tag = parser.getName();
1046            if (!"policies".equals(tag)) {
1047                throw new XmlPullParserException(
1048                        "Settings do not start with policies tag: found " + tag);
1049            }
1050
1051            // Extract the permission provider component name if available
1052            String permissionProvider = parser.getAttributeValue(null, ATTR_PERMISSION_PROVIDER);
1053            if (permissionProvider != null) {
1054                policy.mRestrictionsProvider = ComponentName.unflattenFromString(permissionProvider);
1055            }
1056
1057            type = parser.next();
1058            int outerDepth = parser.getDepth();
1059            policy.mLockTaskComponents.clear();
1060            while ((type=parser.next()) != XmlPullParser.END_DOCUMENT
1061                   && (type != XmlPullParser.END_TAG || parser.getDepth() > outerDepth)) {
1062                if (type == XmlPullParser.END_TAG || type == XmlPullParser.TEXT) {
1063                    continue;
1064                }
1065                tag = parser.getName();
1066                if ("admin".equals(tag)) {
1067                    String name = parser.getAttributeValue(null, "name");
1068                    try {
1069                        DeviceAdminInfo dai = findAdmin(
1070                                ComponentName.unflattenFromString(name), userHandle);
1071                        if (DBG && (UserHandle.getUserId(dai.getActivityInfo().applicationInfo.uid)
1072                                != userHandle)) {
1073                            Slog.w(LOG_TAG, "findAdmin returned an incorrect uid "
1074                                    + dai.getActivityInfo().applicationInfo.uid + " for user "
1075                                    + userHandle);
1076                        }
1077                        if (dai != null) {
1078                            ActiveAdmin ap = new ActiveAdmin(dai);
1079                            ap.readFromXml(parser);
1080                            policy.mAdminMap.put(ap.info.getComponent(), ap);
1081                            policy.mAdminList.add(ap);
1082                        }
1083                    } catch (RuntimeException e) {
1084                        Slog.w(LOG_TAG, "Failed loading admin " + name, e);
1085                    }
1086                } else if ("failed-password-attempts".equals(tag)) {
1087                    policy.mFailedPasswordAttempts = Integer.parseInt(
1088                            parser.getAttributeValue(null, "value"));
1089                    XmlUtils.skipCurrentTag(parser);
1090                } else if ("password-owner".equals(tag)) {
1091                    policy.mPasswordOwner = Integer.parseInt(
1092                            parser.getAttributeValue(null, "value"));
1093                    XmlUtils.skipCurrentTag(parser);
1094                } else if ("active-password".equals(tag)) {
1095                    policy.mActivePasswordQuality = Integer.parseInt(
1096                            parser.getAttributeValue(null, "quality"));
1097                    policy.mActivePasswordLength = Integer.parseInt(
1098                            parser.getAttributeValue(null, "length"));
1099                    policy.mActivePasswordUpperCase = Integer.parseInt(
1100                            parser.getAttributeValue(null, "uppercase"));
1101                    policy.mActivePasswordLowerCase = Integer.parseInt(
1102                            parser.getAttributeValue(null, "lowercase"));
1103                    policy.mActivePasswordLetters = Integer.parseInt(
1104                            parser.getAttributeValue(null, "letters"));
1105                    policy.mActivePasswordNumeric = Integer.parseInt(
1106                            parser.getAttributeValue(null, "numeric"));
1107                    policy.mActivePasswordSymbols = Integer.parseInt(
1108                            parser.getAttributeValue(null, "symbols"));
1109                    policy.mActivePasswordNonLetter = Integer.parseInt(
1110                            parser.getAttributeValue(null, "nonletter"));
1111                    XmlUtils.skipCurrentTag(parser);
1112                } else if (LOCK_TASK_COMPONENTS_XML.equals(tag)) {
1113                    policy.mLockTaskComponents.add
1114                        (ComponentName.unflattenFromString
1115                         (parser.getAttributeValue(null, "name")));
1116                    XmlUtils.skipCurrentTag(parser);
1117                } else {
1118                    Slog.w(LOG_TAG, "Unknown tag: " + tag);
1119                    XmlUtils.skipCurrentTag(parser);
1120                }
1121            }
1122        } catch (NullPointerException e) {
1123            Slog.w(LOG_TAG, "failed parsing " + file + " " + e);
1124        } catch (NumberFormatException e) {
1125            Slog.w(LOG_TAG, "failed parsing " + file + " " + e);
1126        } catch (XmlPullParserException e) {
1127            Slog.w(LOG_TAG, "failed parsing " + file + " " + e);
1128        } catch (FileNotFoundException e) {
1129            // Don't be noisy, this is normal if we haven't defined any policies.
1130        } catch (IOException e) {
1131            Slog.w(LOG_TAG, "failed parsing " + file + " " + e);
1132        } catch (IndexOutOfBoundsException e) {
1133            Slog.w(LOG_TAG, "failed parsing " + file + " " + e);
1134        }
1135        try {
1136            if (stream != null) {
1137                stream.close();
1138            }
1139        } catch (IOException e) {
1140            // Ignore
1141        }
1142
1143        // Validate that what we stored for the password quality matches
1144        // sufficiently what is currently set.  Note that this is only
1145        // a sanity check in case the two get out of sync; this should
1146        // never normally happen.
1147        LockPatternUtils utils = new LockPatternUtils(mContext);
1148        if (utils.getActivePasswordQuality() < policy.mActivePasswordQuality) {
1149            Slog.w(LOG_TAG, "Active password quality 0x"
1150                    + Integer.toHexString(policy.mActivePasswordQuality)
1151                    + " does not match actual quality 0x"
1152                    + Integer.toHexString(utils.getActivePasswordQuality()));
1153            policy.mActivePasswordQuality = DevicePolicyManager.PASSWORD_QUALITY_UNSPECIFIED;
1154            policy.mActivePasswordLength = 0;
1155            policy.mActivePasswordUpperCase = 0;
1156            policy.mActivePasswordLowerCase = 0;
1157            policy.mActivePasswordLetters = 0;
1158            policy.mActivePasswordNumeric = 0;
1159            policy.mActivePasswordSymbols = 0;
1160            policy.mActivePasswordNonLetter = 0;
1161        }
1162
1163        validatePasswordOwnerLocked(policy);
1164        syncDeviceCapabilitiesLocked(policy);
1165        updateMaximumTimeToLockLocked(policy);
1166    }
1167
1168    static void validateQualityConstant(int quality) {
1169        switch (quality) {
1170            case DevicePolicyManager.PASSWORD_QUALITY_UNSPECIFIED:
1171            case DevicePolicyManager.PASSWORD_QUALITY_BIOMETRIC_WEAK:
1172            case DevicePolicyManager.PASSWORD_QUALITY_SOMETHING:
1173            case DevicePolicyManager.PASSWORD_QUALITY_NUMERIC:
1174            case DevicePolicyManager.PASSWORD_QUALITY_ALPHABETIC:
1175            case DevicePolicyManager.PASSWORD_QUALITY_ALPHANUMERIC:
1176            case DevicePolicyManager.PASSWORD_QUALITY_COMPLEX:
1177                return;
1178        }
1179        throw new IllegalArgumentException("Invalid quality constant: 0x"
1180                + Integer.toHexString(quality));
1181    }
1182
1183    void validatePasswordOwnerLocked(DevicePolicyData policy) {
1184        if (policy.mPasswordOwner >= 0) {
1185            boolean haveOwner = false;
1186            for (int i = policy.mAdminList.size() - 1; i >= 0; i--) {
1187                if (policy.mAdminList.get(i).getUid() == policy.mPasswordOwner) {
1188                    haveOwner = true;
1189                    break;
1190                }
1191            }
1192            if (!haveOwner) {
1193                Slog.w(LOG_TAG, "Previous password owner " + policy.mPasswordOwner
1194                        + " no longer active; disabling");
1195                policy.mPasswordOwner = -1;
1196            }
1197        }
1198    }
1199
1200    /**
1201     * Pushes down policy information to the system for any policies related to general device
1202     * capabilities that need to be enforced by lower level services (e.g. Camera services).
1203     */
1204    void syncDeviceCapabilitiesLocked(DevicePolicyData policy) {
1205        // Ensure the status of the camera is synced down to the system. Interested native services
1206        // should monitor this value and act accordingly.
1207        boolean systemState = SystemProperties.getBoolean(SYSTEM_PROP_DISABLE_CAMERA, false);
1208        boolean cameraDisabled = getCameraDisabled(null, policy.mUserHandle);
1209        if (cameraDisabled != systemState) {
1210            long token = Binder.clearCallingIdentity();
1211            try {
1212                String value = cameraDisabled ? "1" : "0";
1213                if (DBG) Slog.v(LOG_TAG, "Change in camera state ["
1214                        + SYSTEM_PROP_DISABLE_CAMERA + "] = " + value);
1215                SystemProperties.set(SYSTEM_PROP_DISABLE_CAMERA, value);
1216            } finally {
1217                Binder.restoreCallingIdentity(token);
1218            }
1219        }
1220    }
1221
1222    public void systemReady() {
1223        if (!mHasFeature) {
1224            return;
1225        }
1226        synchronized (this) {
1227            loadSettingsLocked(getUserData(UserHandle.USER_OWNER), UserHandle.USER_OWNER);
1228            loadDeviceOwner();
1229        }
1230        cleanUpOldUsers();
1231        mAppOpsService = IAppOpsService.Stub.asInterface(
1232                ServiceManager.getService(Context.APP_OPS_SERVICE));
1233        if (mDeviceOwner != null) {
1234            if (mDeviceOwner.hasDeviceOwner()) {
1235                try {
1236                    mAppOpsService.setDeviceOwner(mDeviceOwner.getDeviceOwnerPackageName());
1237                } catch (RemoteException e) {
1238                    Log.w(LOG_TAG, "Unable to notify AppOpsService of DeviceOwner", e);
1239                }
1240            }
1241            for (Integer i : mDeviceOwner.getProfileOwnerKeys()) {
1242                try {
1243                    mAppOpsService.setProfileOwner(mDeviceOwner.getProfileOwnerPackageName(i), i);
1244                } catch (RemoteException e) {
1245                    Log.w(LOG_TAG, "Unable to notify AppOpsService of ProfileOwner", e);
1246                }
1247            }
1248        }
1249    }
1250
1251    private void cleanUpOldUsers() {
1252        // This is needed in case the broadcast {@link Intent.ACTION_USER_REMOVED} was not handled
1253        // before reboot
1254        Set<Integer> usersWithProfileOwners;
1255        Set<Integer> usersWithData;
1256        synchronized(this) {
1257            usersWithProfileOwners = mDeviceOwner != null
1258                    ? mDeviceOwner.getProfileOwnerKeys() : new HashSet<Integer>();
1259            usersWithData = new HashSet<Integer>();
1260            for (int i = 0; i < mUserData.size(); i++) {
1261                usersWithData.add(mUserData.keyAt(i));
1262            }
1263        }
1264        List<UserInfo> allUsers = mUserManager.getUsers();
1265
1266        Set<Integer> deletedUsers = new HashSet<Integer>();
1267        deletedUsers.addAll(usersWithProfileOwners);
1268        deletedUsers.addAll(usersWithData);
1269        for (UserInfo userInfo : allUsers) {
1270            deletedUsers.remove(userInfo.id);
1271        }
1272        for (Integer userId : deletedUsers) {
1273            removeUserData(userId);
1274        }
1275    }
1276
1277    private void handlePasswordExpirationNotification(int userHandle) {
1278        synchronized (this) {
1279            final long now = System.currentTimeMillis();
1280
1281            List<UserInfo> profiles = mUserManager.getProfiles(userHandle);
1282            for (UserInfo ui : profiles) {
1283                int profileUserHandle = ui.getUserHandle().getIdentifier();
1284                final DevicePolicyData policy = getUserData(profileUserHandle);
1285                final int count = policy.mAdminList.size();
1286                if (count > 0) {
1287                    for (int i = 0; i < count; i++) {
1288                        final ActiveAdmin admin = policy.mAdminList.get(i);
1289                        if (admin.info.usesPolicy(DeviceAdminInfo.USES_POLICY_EXPIRE_PASSWORD)
1290                                && admin.passwordExpirationTimeout > 0L
1291                                && now >= admin.passwordExpirationDate - EXPIRATION_GRACE_PERIOD_MS
1292                                && admin.passwordExpirationDate > 0L) {
1293                            sendAdminCommandLocked(admin,
1294                                    DeviceAdminReceiver.ACTION_PASSWORD_EXPIRING);
1295                        }
1296                    }
1297                }
1298            }
1299            setExpirationAlarmCheckLocked(mContext, getUserData(userHandle));
1300        }
1301    }
1302
1303    private void manageMonitoringCertificateNotification(Intent intent) {
1304        final NotificationManager notificationManager = getNotificationManager();
1305
1306        final boolean hasCert = DevicePolicyManager.hasAnyCaCertsInstalled();
1307        if (! hasCert) {
1308            if (intent.getAction().equals(KeyChain.ACTION_STORAGE_CHANGED)) {
1309                for (UserInfo user : mUserManager.getUsers()) {
1310                    notificationManager.cancelAsUser(
1311                            null, MONITORING_CERT_NOTIFICATION_ID, user.getUserHandle());
1312                }
1313            }
1314            return;
1315        }
1316        final boolean isManaged = getDeviceOwner() != null;
1317        int smallIconId;
1318        String contentText;
1319        if (isManaged) {
1320            contentText = mContext.getString(R.string.ssl_ca_cert_noti_managed,
1321                    getDeviceOwnerName());
1322            smallIconId = R.drawable.stat_sys_certificate_info;
1323        } else {
1324            contentText = mContext.getString(R.string.ssl_ca_cert_noti_by_unknown);
1325            smallIconId = android.R.drawable.stat_sys_warning;
1326        }
1327
1328        Intent dialogIntent = new Intent(Settings.ACTION_MONITORING_CERT_INFO);
1329        dialogIntent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK | Intent.FLAG_ACTIVITY_CLEAR_TASK);
1330        dialogIntent.setPackage("com.android.settings");
1331        // Notification will be sent individually to all users. The activity should start as
1332        // whichever user is current when it starts.
1333        PendingIntent notifyIntent = PendingIntent.getActivityAsUser(mContext, 0, dialogIntent,
1334                PendingIntent.FLAG_UPDATE_CURRENT, null, UserHandle.CURRENT);
1335
1336        Notification noti = new Notification.Builder(mContext)
1337            .setSmallIcon(smallIconId)
1338            .setContentTitle(mContext.getString(R.string.ssl_ca_cert_warning))
1339            .setContentText(contentText)
1340            .setContentIntent(notifyIntent)
1341            .setPriority(Notification.PRIORITY_HIGH)
1342            .setShowWhen(false)
1343            .build();
1344
1345        // If this is a boot intent, this will fire for each user. But if this is a storage changed
1346        // intent, it will fire once, so we need to notify all users.
1347        if (intent.getAction().equals(KeyChain.ACTION_STORAGE_CHANGED)) {
1348            for (UserInfo user : mUserManager.getUsers()) {
1349                notificationManager.notifyAsUser(
1350                        null, MONITORING_CERT_NOTIFICATION_ID, noti, user.getUserHandle());
1351            }
1352        } else {
1353            notificationManager.notifyAsUser(
1354                    null, MONITORING_CERT_NOTIFICATION_ID, noti, UserHandle.CURRENT);
1355        }
1356    }
1357
1358    /**
1359     * @param adminReceiver The admin to add
1360     * @param refreshing true = update an active admin, no error
1361     */
1362    public void setActiveAdmin(ComponentName adminReceiver, boolean refreshing, int userHandle) {
1363        if (!mHasFeature) {
1364            return;
1365        }
1366        mContext.enforceCallingOrSelfPermission(
1367                android.Manifest.permission.MANAGE_DEVICE_ADMINS, null);
1368        enforceCrossUserPermission(userHandle);
1369
1370        DevicePolicyData policy = getUserData(userHandle);
1371        DeviceAdminInfo info = findAdmin(adminReceiver, userHandle);
1372        if (info == null) {
1373            throw new IllegalArgumentException("Bad admin: " + adminReceiver);
1374        }
1375        synchronized (this) {
1376            long ident = Binder.clearCallingIdentity();
1377            try {
1378                if (!refreshing
1379                        && getActiveAdminUncheckedLocked(adminReceiver, userHandle) != null) {
1380                    throw new IllegalArgumentException("Admin is already added");
1381                }
1382                ActiveAdmin newAdmin = new ActiveAdmin(info);
1383                policy.mAdminMap.put(adminReceiver, newAdmin);
1384                int replaceIndex = -1;
1385                if (refreshing) {
1386                    final int N = policy.mAdminList.size();
1387                    for (int i=0; i < N; i++) {
1388                        ActiveAdmin oldAdmin = policy.mAdminList.get(i);
1389                        if (oldAdmin.info.getComponent().equals(adminReceiver)) {
1390                            replaceIndex = i;
1391                            break;
1392                        }
1393                    }
1394                }
1395                if (replaceIndex == -1) {
1396                    policy.mAdminList.add(newAdmin);
1397                    enableIfNecessary(info.getPackageName(), userHandle);
1398                } else {
1399                    policy.mAdminList.set(replaceIndex, newAdmin);
1400                }
1401                saveSettingsLocked(userHandle);
1402                sendAdminCommandLocked(newAdmin, DeviceAdminReceiver.ACTION_DEVICE_ADMIN_ENABLED);
1403            } finally {
1404                Binder.restoreCallingIdentity(ident);
1405            }
1406        }
1407    }
1408
1409    public boolean isAdminActive(ComponentName adminReceiver, int userHandle) {
1410        if (!mHasFeature) {
1411            return false;
1412        }
1413        enforceCrossUserPermission(userHandle);
1414        synchronized (this) {
1415            return getActiveAdminUncheckedLocked(adminReceiver, userHandle) != null;
1416        }
1417    }
1418
1419    public boolean hasGrantedPolicy(ComponentName adminReceiver, int policyId, int userHandle) {
1420        if (!mHasFeature) {
1421            return false;
1422        }
1423        enforceCrossUserPermission(userHandle);
1424        synchronized (this) {
1425            ActiveAdmin administrator = getActiveAdminUncheckedLocked(adminReceiver, userHandle);
1426            if (administrator == null) {
1427                throw new SecurityException("No active admin " + adminReceiver);
1428            }
1429            return administrator.info.usesPolicy(policyId);
1430        }
1431    }
1432
1433    @SuppressWarnings("unchecked")
1434    public List<ComponentName> getActiveAdmins(int userHandle) {
1435        if (!mHasFeature) {
1436            return Collections.EMPTY_LIST;
1437        }
1438
1439        enforceCrossUserPermission(userHandle);
1440        synchronized (this) {
1441            DevicePolicyData policy = getUserData(userHandle);
1442            final int N = policy.mAdminList.size();
1443            if (N <= 0) {
1444                return null;
1445            }
1446            ArrayList<ComponentName> res = new ArrayList<ComponentName>(N);
1447            for (int i=0; i<N; i++) {
1448                res.add(policy.mAdminList.get(i).info.getComponent());
1449            }
1450            return res;
1451        }
1452    }
1453
1454    public boolean packageHasActiveAdmins(String packageName, int userHandle) {
1455        if (!mHasFeature) {
1456            return false;
1457        }
1458        enforceCrossUserPermission(userHandle);
1459        synchronized (this) {
1460            DevicePolicyData policy = getUserData(userHandle);
1461            final int N = policy.mAdminList.size();
1462            for (int i=0; i<N; i++) {
1463                if (policy.mAdminList.get(i).info.getPackageName().equals(packageName)) {
1464                    return true;
1465                }
1466            }
1467            return false;
1468        }
1469    }
1470
1471    public void removeActiveAdmin(ComponentName adminReceiver, int userHandle) {
1472        if (!mHasFeature) {
1473            return;
1474        }
1475        enforceCrossUserPermission(userHandle);
1476        synchronized (this) {
1477            ActiveAdmin admin = getActiveAdminUncheckedLocked(adminReceiver, userHandle);
1478            if (admin == null) {
1479                return;
1480            }
1481            if (admin.getUid() != Binder.getCallingUid()) {
1482                // If trying to remove device owner, refuse when the caller is not the owner.
1483                if (isDeviceOwner(adminReceiver.getPackageName())) {
1484                    return;
1485                }
1486                mContext.enforceCallingOrSelfPermission(
1487                        android.Manifest.permission.MANAGE_DEVICE_ADMINS, null);
1488            }
1489            long ident = Binder.clearCallingIdentity();
1490            try {
1491                removeActiveAdminLocked(adminReceiver, userHandle);
1492            } finally {
1493                Binder.restoreCallingIdentity(ident);
1494            }
1495        }
1496    }
1497
1498    public void setPasswordQuality(ComponentName who, int quality, int userHandle) {
1499        if (!mHasFeature) {
1500            return;
1501        }
1502        validateQualityConstant(quality);
1503        enforceCrossUserPermission(userHandle);
1504
1505        synchronized (this) {
1506            if (who == null) {
1507                throw new NullPointerException("ComponentName is null");
1508            }
1509            ActiveAdmin ap = getActiveAdminForCallerLocked(who,
1510                    DeviceAdminInfo.USES_POLICY_LIMIT_PASSWORD);
1511            if (ap.passwordQuality != quality) {
1512                ap.passwordQuality = quality;
1513                saveSettingsLocked(userHandle);
1514            }
1515        }
1516    }
1517
1518    public int getPasswordQuality(ComponentName who, int userHandle) {
1519        if (!mHasFeature) {
1520            return DevicePolicyManager.PASSWORD_QUALITY_UNSPECIFIED;
1521        }
1522        enforceCrossUserPermission(userHandle);
1523        synchronized (this) {
1524            int mode = DevicePolicyManager.PASSWORD_QUALITY_UNSPECIFIED;
1525
1526            if (who != null) {
1527                ActiveAdmin admin = getActiveAdminUncheckedLocked(who, userHandle);
1528                return admin != null ? admin.passwordQuality : mode;
1529            }
1530
1531            // Return strictest policy for this user and profiles that are visible from this user.
1532            List<UserInfo> profiles = mUserManager.getProfiles(userHandle);
1533            for (UserInfo userInfo : profiles) {
1534                DevicePolicyData policy = getUserData(userInfo.getUserHandle().getIdentifier());
1535                final int N = policy.mAdminList.size();
1536                for (int i=0; i<N; i++) {
1537                    ActiveAdmin admin = policy.mAdminList.get(i);
1538                    if (mode < admin.passwordQuality) {
1539                        mode = admin.passwordQuality;
1540                    }
1541                }
1542            }
1543            return mode;
1544        }
1545    }
1546
1547    public void setPasswordMinimumLength(ComponentName who, int length, int userHandle) {
1548        if (!mHasFeature) {
1549            return;
1550        }
1551        enforceCrossUserPermission(userHandle);
1552        synchronized (this) {
1553            if (who == null) {
1554                throw new NullPointerException("ComponentName is null");
1555            }
1556            ActiveAdmin ap = getActiveAdminForCallerLocked(who,
1557                    DeviceAdminInfo.USES_POLICY_LIMIT_PASSWORD);
1558            if (ap.minimumPasswordLength != length) {
1559                ap.minimumPasswordLength = length;
1560                saveSettingsLocked(userHandle);
1561            }
1562        }
1563    }
1564
1565    public int getPasswordMinimumLength(ComponentName who, int userHandle) {
1566        if (!mHasFeature) {
1567            return 0;
1568        }
1569        enforceCrossUserPermission(userHandle);
1570        synchronized (this) {
1571            int length = 0;
1572
1573            if (who != null) {
1574                ActiveAdmin admin = getActiveAdminUncheckedLocked(who, userHandle);
1575                return admin != null ? admin.minimumPasswordLength : length;
1576            }
1577
1578            // Return strictest policy for this user and profiles that are visible from this user.
1579            List<UserInfo> profiles = mUserManager.getProfiles(userHandle);
1580            for (UserInfo userInfo : profiles) {
1581                DevicePolicyData policy = getUserData(userInfo.getUserHandle().getIdentifier());
1582                final int N = policy.mAdminList.size();
1583                for (int i=0; i<N; i++) {
1584                    ActiveAdmin admin = policy.mAdminList.get(i);
1585                    if (length < admin.minimumPasswordLength) {
1586                        length = admin.minimumPasswordLength;
1587                    }
1588                }
1589            }
1590            return length;
1591        }
1592    }
1593
1594    public void setPasswordHistoryLength(ComponentName who, int length, int userHandle) {
1595        if (!mHasFeature) {
1596            return;
1597        }
1598        enforceCrossUserPermission(userHandle);
1599        synchronized (this) {
1600            if (who == null) {
1601                throw new NullPointerException("ComponentName is null");
1602            }
1603            ActiveAdmin ap = getActiveAdminForCallerLocked(who,
1604                    DeviceAdminInfo.USES_POLICY_LIMIT_PASSWORD);
1605            if (ap.passwordHistoryLength != length) {
1606                ap.passwordHistoryLength = length;
1607                saveSettingsLocked(userHandle);
1608            }
1609        }
1610    }
1611
1612    public int getPasswordHistoryLength(ComponentName who, int userHandle) {
1613        if (!mHasFeature) {
1614            return 0;
1615        }
1616        enforceCrossUserPermission(userHandle);
1617        synchronized (this) {
1618            int length = 0;
1619
1620            if (who != null) {
1621                ActiveAdmin admin = getActiveAdminUncheckedLocked(who, userHandle);
1622                return admin != null ? admin.passwordHistoryLength : length;
1623            }
1624
1625            // Return strictest policy for this user and profiles that are visible from this user.
1626            List<UserInfo> profiles = mUserManager.getProfiles(userHandle);
1627            for (UserInfo userInfo : profiles) {
1628                DevicePolicyData policy = getUserData(userInfo.getUserHandle().getIdentifier());
1629                final int N = policy.mAdminList.size();
1630                for (int i = 0; i < N; i++) {
1631                    ActiveAdmin admin = policy.mAdminList.get(i);
1632                    if (length < admin.passwordHistoryLength) {
1633                        length = admin.passwordHistoryLength;
1634                    }
1635                }
1636            }
1637            return length;
1638        }
1639    }
1640
1641    public void setPasswordExpirationTimeout(ComponentName who, long timeout, int userHandle) {
1642        if (!mHasFeature) {
1643            return;
1644        }
1645        enforceCrossUserPermission(userHandle);
1646        synchronized (this) {
1647            if (who == null) {
1648                throw new NullPointerException("ComponentName is null");
1649            }
1650            if (timeout < 0) {
1651                throw new IllegalArgumentException("Timeout must be >= 0 ms");
1652            }
1653            ActiveAdmin ap = getActiveAdminForCallerLocked(who,
1654                    DeviceAdminInfo.USES_POLICY_EXPIRE_PASSWORD);
1655            // Calling this API automatically bumps the expiration date
1656            final long expiration = timeout > 0L ? (timeout + System.currentTimeMillis()) : 0L;
1657            ap.passwordExpirationDate = expiration;
1658            ap.passwordExpirationTimeout = timeout;
1659            if (timeout > 0L) {
1660                Slog.w(LOG_TAG, "setPasswordExpiration(): password will expire on "
1661                        + DateFormat.getDateTimeInstance(DateFormat.DEFAULT, DateFormat.DEFAULT)
1662                        .format(new Date(expiration)));
1663            }
1664            saveSettingsLocked(userHandle);
1665            // in case this is the first one
1666            setExpirationAlarmCheckLocked(mContext, getUserData(userHandle));
1667        }
1668    }
1669
1670    /**
1671     * Return a single admin's expiration cycle time, or the min of all cycle times.
1672     * Returns 0 if not configured.
1673     */
1674    public long getPasswordExpirationTimeout(ComponentName who, int userHandle) {
1675        if (!mHasFeature) {
1676            return 0L;
1677        }
1678        enforceCrossUserPermission(userHandle);
1679        synchronized (this) {
1680            long timeout = 0L;
1681
1682            if (who != null) {
1683                ActiveAdmin admin = getActiveAdminUncheckedLocked(who, userHandle);
1684                return admin != null ? admin.passwordExpirationTimeout : timeout;
1685            }
1686
1687            List<UserInfo> profiles = mUserManager.getProfiles(userHandle);
1688            for (UserInfo userInfo : profiles) {
1689                DevicePolicyData policy = getUserData(userInfo.getUserHandle().getIdentifier());
1690                final int N = policy.mAdminList.size();
1691                for (int i = 0; i < N; i++) {
1692                    ActiveAdmin admin = policy.mAdminList.get(i);
1693                    if (timeout == 0L || (admin.passwordExpirationTimeout != 0L
1694                            && timeout > admin.passwordExpirationTimeout)) {
1695                        timeout = admin.passwordExpirationTimeout;
1696                    }
1697                }
1698            }
1699            return timeout;
1700        }
1701    }
1702
1703    /**
1704     * Return a single admin's expiration date/time, or the min (soonest) for all admins.
1705     * Returns 0 if not configured.
1706     */
1707    private long getPasswordExpirationLocked(ComponentName who, int userHandle) {
1708        long timeout = 0L;
1709
1710        if (who != null) {
1711            ActiveAdmin admin = getActiveAdminUncheckedLocked(who, userHandle);
1712            return admin != null ? admin.passwordExpirationDate : timeout;
1713        }
1714
1715        List<UserInfo> profiles = mUserManager.getProfiles(userHandle);
1716        for (UserInfo userInfo : profiles) {
1717            DevicePolicyData policy = getUserData(userInfo.getUserHandle().getIdentifier());
1718            final int N = policy.mAdminList.size();
1719            for (int i = 0; i < N; i++) {
1720                ActiveAdmin admin = policy.mAdminList.get(i);
1721                if (timeout == 0L || (admin.passwordExpirationDate != 0
1722                        && timeout > admin.passwordExpirationDate)) {
1723                    timeout = admin.passwordExpirationDate;
1724                }
1725            }
1726        }
1727        return timeout;
1728    }
1729
1730    public long getPasswordExpiration(ComponentName who, int userHandle) {
1731        if (!mHasFeature) {
1732            return 0L;
1733        }
1734        enforceCrossUserPermission(userHandle);
1735        synchronized (this) {
1736            return getPasswordExpirationLocked(who, userHandle);
1737        }
1738    }
1739
1740    public void setPasswordMinimumUpperCase(ComponentName who, int length, int userHandle) {
1741        if (!mHasFeature) {
1742            return;
1743        }
1744        enforceCrossUserPermission(userHandle);
1745        synchronized (this) {
1746            if (who == null) {
1747                throw new NullPointerException("ComponentName is null");
1748            }
1749            ActiveAdmin ap = getActiveAdminForCallerLocked(who,
1750                    DeviceAdminInfo.USES_POLICY_LIMIT_PASSWORD);
1751            if (ap.minimumPasswordUpperCase != length) {
1752                ap.minimumPasswordUpperCase = length;
1753                saveSettingsLocked(userHandle);
1754            }
1755        }
1756    }
1757
1758    public int getPasswordMinimumUpperCase(ComponentName who, int userHandle) {
1759        if (!mHasFeature) {
1760            return 0;
1761        }
1762        enforceCrossUserPermission(userHandle);
1763        synchronized (this) {
1764            int length = 0;
1765
1766            if (who != null) {
1767                ActiveAdmin admin = getActiveAdminUncheckedLocked(who, userHandle);
1768                return admin != null ? admin.minimumPasswordUpperCase : length;
1769            }
1770
1771            // Return strictest policy for this user and profiles that are visible from this user.
1772            List<UserInfo> profiles = mUserManager.getProfiles(userHandle);
1773            for (UserInfo userInfo : profiles) {
1774                DevicePolicyData policy = getUserData(userInfo.getUserHandle().getIdentifier());
1775                final int N = policy.mAdminList.size();
1776                for (int i=0; i<N; i++) {
1777                    ActiveAdmin admin = policy.mAdminList.get(i);
1778                    if (length < admin.minimumPasswordUpperCase) {
1779                        length = admin.minimumPasswordUpperCase;
1780                    }
1781                }
1782            }
1783            return length;
1784        }
1785    }
1786
1787    public void setPasswordMinimumLowerCase(ComponentName who, int length, int userHandle) {
1788        enforceCrossUserPermission(userHandle);
1789        synchronized (this) {
1790            if (who == null) {
1791                throw new NullPointerException("ComponentName is null");
1792            }
1793            ActiveAdmin ap = getActiveAdminForCallerLocked(who,
1794                    DeviceAdminInfo.USES_POLICY_LIMIT_PASSWORD);
1795            if (ap.minimumPasswordLowerCase != length) {
1796                ap.minimumPasswordLowerCase = length;
1797                saveSettingsLocked(userHandle);
1798            }
1799        }
1800    }
1801
1802    public int getPasswordMinimumLowerCase(ComponentName who, int userHandle) {
1803        if (!mHasFeature) {
1804            return 0;
1805        }
1806        enforceCrossUserPermission(userHandle);
1807        synchronized (this) {
1808            int length = 0;
1809
1810            if (who != null) {
1811                ActiveAdmin admin = getActiveAdminUncheckedLocked(who, userHandle);
1812                return admin != null ? admin.minimumPasswordLowerCase : length;
1813            }
1814
1815            // Return strictest policy for this user and profiles that are visible from this user.
1816            List<UserInfo> profiles = mUserManager.getProfiles(userHandle);
1817            for (UserInfo userInfo : profiles) {
1818                DevicePolicyData policy = getUserData(userInfo.getUserHandle().getIdentifier());
1819                final int N = policy.mAdminList.size();
1820                for (int i=0; i<N; i++) {
1821                    ActiveAdmin admin = policy.mAdminList.get(i);
1822                    if (length < admin.minimumPasswordLowerCase) {
1823                        length = admin.minimumPasswordLowerCase;
1824                    }
1825                }
1826            }
1827            return length;
1828        }
1829    }
1830
1831    public void setPasswordMinimumLetters(ComponentName who, int length, int userHandle) {
1832        if (!mHasFeature) {
1833            return;
1834        }
1835        enforceCrossUserPermission(userHandle);
1836        synchronized (this) {
1837            if (who == null) {
1838                throw new NullPointerException("ComponentName is null");
1839            }
1840            ActiveAdmin ap = getActiveAdminForCallerLocked(who,
1841                    DeviceAdminInfo.USES_POLICY_LIMIT_PASSWORD);
1842            if (ap.minimumPasswordLetters != length) {
1843                ap.minimumPasswordLetters = length;
1844                saveSettingsLocked(userHandle);
1845            }
1846        }
1847    }
1848
1849    public int getPasswordMinimumLetters(ComponentName who, int userHandle) {
1850        if (!mHasFeature) {
1851            return 0;
1852        }
1853        enforceCrossUserPermission(userHandle);
1854        synchronized (this) {
1855            int length = 0;
1856
1857            if (who != null) {
1858                ActiveAdmin admin = getActiveAdminUncheckedLocked(who, userHandle);
1859                return admin != null ? admin.minimumPasswordLetters : length;
1860            }
1861
1862            // Return strictest policy for this user and profiles that are visible from this user.
1863            List<UserInfo> profiles = mUserManager.getProfiles(userHandle);
1864            for (UserInfo userInfo : profiles) {
1865                DevicePolicyData policy = getUserData(userInfo.getUserHandle().getIdentifier());
1866                final int N = policy.mAdminList.size();
1867                for (int i=0; i<N; i++) {
1868                    ActiveAdmin admin = policy.mAdminList.get(i);
1869                    if (length < admin.minimumPasswordLetters) {
1870                        length = admin.minimumPasswordLetters;
1871                    }
1872                }
1873            }
1874            return length;
1875        }
1876    }
1877
1878    public void setPasswordMinimumNumeric(ComponentName who, int length, int userHandle) {
1879        if (!mHasFeature) {
1880            return;
1881        }
1882        enforceCrossUserPermission(userHandle);
1883        synchronized (this) {
1884            if (who == null) {
1885                throw new NullPointerException("ComponentName is null");
1886            }
1887            ActiveAdmin ap = getActiveAdminForCallerLocked(who,
1888                    DeviceAdminInfo.USES_POLICY_LIMIT_PASSWORD);
1889            if (ap.minimumPasswordNumeric != length) {
1890                ap.minimumPasswordNumeric = length;
1891                saveSettingsLocked(userHandle);
1892            }
1893        }
1894    }
1895
1896    public int getPasswordMinimumNumeric(ComponentName who, int userHandle) {
1897        if (!mHasFeature) {
1898            return 0;
1899        }
1900        enforceCrossUserPermission(userHandle);
1901        synchronized (this) {
1902            int length = 0;
1903
1904            if (who != null) {
1905                ActiveAdmin admin = getActiveAdminUncheckedLocked(who, userHandle);
1906                return admin != null ? admin.minimumPasswordNumeric : length;
1907            }
1908
1909            // Return strictest policy for this user and profiles that are visible from this user.
1910            List<UserInfo> profiles = mUserManager.getProfiles(userHandle);
1911            for (UserInfo userInfo : profiles) {
1912                DevicePolicyData policy = getUserData(userInfo.getUserHandle().getIdentifier());
1913                final int N = policy.mAdminList.size();
1914                for (int i = 0; i < N; i++) {
1915                    ActiveAdmin admin = policy.mAdminList.get(i);
1916                    if (length < admin.minimumPasswordNumeric) {
1917                        length = admin.minimumPasswordNumeric;
1918                    }
1919                }
1920            }
1921            return length;
1922        }
1923    }
1924
1925    public void setPasswordMinimumSymbols(ComponentName who, int length, int userHandle) {
1926        if (!mHasFeature) {
1927            return;
1928        }
1929        enforceCrossUserPermission(userHandle);
1930        synchronized (this) {
1931            if (who == null) {
1932                throw new NullPointerException("ComponentName is null");
1933            }
1934            ActiveAdmin ap = getActiveAdminForCallerLocked(who,
1935                    DeviceAdminInfo.USES_POLICY_LIMIT_PASSWORD);
1936            if (ap.minimumPasswordSymbols != length) {
1937                ap.minimumPasswordSymbols = length;
1938                saveSettingsLocked(userHandle);
1939            }
1940        }
1941    }
1942
1943    public int getPasswordMinimumSymbols(ComponentName who, int userHandle) {
1944        if (!mHasFeature) {
1945            return 0;
1946        }
1947        enforceCrossUserPermission(userHandle);
1948        synchronized (this) {
1949            int length = 0;
1950
1951            if (who != null) {
1952                ActiveAdmin admin = getActiveAdminUncheckedLocked(who, userHandle);
1953                return admin != null ? admin.minimumPasswordSymbols : length;
1954            }
1955
1956            // Return strictest policy for this user and profiles that are visible from this user.
1957            List<UserInfo> profiles = mUserManager.getProfiles(userHandle);
1958            for (UserInfo userInfo : profiles) {
1959                DevicePolicyData policy = getUserData(userInfo.getUserHandle().getIdentifier());
1960                final int N = policy.mAdminList.size();
1961                for (int i=0; i<N; i++) {
1962                    ActiveAdmin admin = policy.mAdminList.get(i);
1963                    if (length < admin.minimumPasswordSymbols) {
1964                        length = admin.minimumPasswordSymbols;
1965                    }
1966                }
1967            }
1968            return length;
1969        }
1970    }
1971
1972    public void setPasswordMinimumNonLetter(ComponentName who, int length, int userHandle) {
1973        if (!mHasFeature) {
1974            return;
1975        }
1976        enforceCrossUserPermission(userHandle);
1977        synchronized (this) {
1978            if (who == null) {
1979                throw new NullPointerException("ComponentName is null");
1980            }
1981            ActiveAdmin ap = getActiveAdminForCallerLocked(who,
1982                    DeviceAdminInfo.USES_POLICY_LIMIT_PASSWORD);
1983            if (ap.minimumPasswordNonLetter != length) {
1984                ap.minimumPasswordNonLetter = length;
1985                saveSettingsLocked(userHandle);
1986            }
1987        }
1988    }
1989
1990    public int getPasswordMinimumNonLetter(ComponentName who, int userHandle) {
1991        if (!mHasFeature) {
1992            return 0;
1993        }
1994        enforceCrossUserPermission(userHandle);
1995        synchronized (this) {
1996            int length = 0;
1997
1998            if (who != null) {
1999                ActiveAdmin admin = getActiveAdminUncheckedLocked(who, userHandle);
2000                return admin != null ? admin.minimumPasswordNonLetter : length;
2001            }
2002
2003            // Return strictest policy for this user and profiles that are visible from this user.
2004            List<UserInfo> profiles = mUserManager.getProfiles(userHandle);
2005            for (UserInfo userInfo : profiles) {
2006                DevicePolicyData policy = getUserData(userInfo.getUserHandle().getIdentifier());
2007                final int N = policy.mAdminList.size();
2008                for (int i=0; i<N; i++) {
2009                    ActiveAdmin admin = policy.mAdminList.get(i);
2010                    if (length < admin.minimumPasswordNonLetter) {
2011                        length = admin.minimumPasswordNonLetter;
2012                    }
2013                }
2014            }
2015            return length;
2016        }
2017    }
2018
2019    public boolean isActivePasswordSufficient(int userHandle) {
2020        if (!mHasFeature) {
2021            return true;
2022        }
2023        enforceCrossUserPermission(userHandle);
2024
2025        synchronized (this) {
2026
2027            // The active password is stored in the user that runs the launcher
2028            // If the user this is called from is part of a profile group, that is the parent
2029            // of the group.
2030            UserInfo parent = getProfileParent(userHandle);
2031            int id = parent == null ? userHandle : parent.id;
2032            DevicePolicyData policy = getUserData(id);
2033
2034            // This API can only be called by an active device admin,
2035            // so try to retrieve it to check that the caller is one.
2036            getActiveAdminForCallerLocked(null,
2037                    DeviceAdminInfo.USES_POLICY_LIMIT_PASSWORD);
2038            if (policy.mActivePasswordQuality < getPasswordQuality(null, userHandle)
2039                    || policy.mActivePasswordLength < getPasswordMinimumLength(null, userHandle)) {
2040                return false;
2041            }
2042            if (policy.mActivePasswordQuality != DevicePolicyManager.PASSWORD_QUALITY_COMPLEX) {
2043                return true;
2044            }
2045            return policy.mActivePasswordUpperCase >= getPasswordMinimumUpperCase(null, userHandle)
2046                && policy.mActivePasswordLowerCase >= getPasswordMinimumLowerCase(null, userHandle)
2047                && policy.mActivePasswordLetters >= getPasswordMinimumLetters(null, userHandle)
2048                && policy.mActivePasswordNumeric >= getPasswordMinimumNumeric(null, userHandle)
2049                && policy.mActivePasswordSymbols >= getPasswordMinimumSymbols(null, userHandle)
2050                && policy.mActivePasswordNonLetter >= getPasswordMinimumNonLetter(null, userHandle);
2051        }
2052    }
2053
2054    public int getCurrentFailedPasswordAttempts(int userHandle) {
2055        synchronized (this) {
2056            // This API can only be called by an active device admin,
2057            // so try to retrieve it to check that the caller is one.
2058            getActiveAdminForCallerLocked(null,
2059                    DeviceAdminInfo.USES_POLICY_WATCH_LOGIN);
2060
2061            // The active password is stored in the parent.
2062            DevicePolicyData policy = getUserData(getProfileParent(userHandle).id);
2063
2064            return policy.mFailedPasswordAttempts;
2065        }
2066    }
2067
2068    public void setMaximumFailedPasswordsForWipe(ComponentName who, int num, int userHandle) {
2069        if (!mHasFeature) {
2070            return;
2071        }
2072        enforceCrossUserPermission(userHandle);
2073        synchronized (this) {
2074            if (who == null) {
2075                throw new NullPointerException("ComponentName is null");
2076            }
2077            // This API can only be called by an active device admin,
2078            // so try to retrieve it to check that the caller is one.
2079            getActiveAdminForCallerLocked(who,
2080                    DeviceAdminInfo.USES_POLICY_WIPE_DATA);
2081            ActiveAdmin ap = getActiveAdminForCallerLocked(who,
2082                    DeviceAdminInfo.USES_POLICY_WATCH_LOGIN);
2083            if (ap.maximumFailedPasswordsForWipe != num) {
2084                ap.maximumFailedPasswordsForWipe = num;
2085                saveSettingsLocked(userHandle);
2086            }
2087        }
2088    }
2089
2090    public int getMaximumFailedPasswordsForWipe(ComponentName who, int userHandle) {
2091        if (!mHasFeature) {
2092            return 0;
2093        }
2094        enforceCrossUserPermission(userHandle);
2095        synchronized (this) {
2096            int count = 0;
2097
2098            if (who != null) {
2099                ActiveAdmin admin = getActiveAdminUncheckedLocked(who, userHandle);
2100                return admin != null ? admin.maximumFailedPasswordsForWipe : count;
2101            }
2102
2103            // Return strictest policy for this user and profiles that are visible from this user.
2104            List<UserInfo> profiles = mUserManager.getProfiles(userHandle);
2105            for (UserInfo userInfo : profiles) {
2106                DevicePolicyData policy = getUserData(userInfo.getUserHandle().getIdentifier());
2107                final int N = policy.mAdminList.size();
2108                for (int i=0; i<N; i++) {
2109                    ActiveAdmin admin = policy.mAdminList.get(i);
2110                    if (count == 0) {
2111                        count = admin.maximumFailedPasswordsForWipe;
2112                    } else if (admin.maximumFailedPasswordsForWipe != 0
2113                            && count > admin.maximumFailedPasswordsForWipe) {
2114                        count = admin.maximumFailedPasswordsForWipe;
2115                    }
2116                }
2117            }
2118            return count;
2119        }
2120    }
2121
2122    public boolean resetPassword(String password, int flags, int userHandle) {
2123        if (!mHasFeature) {
2124            return false;
2125        }
2126        enforceCrossUserPermission(userHandle);
2127        enforceNotManagedProfile(userHandle, "reset the password");
2128
2129        int quality;
2130        synchronized (this) {
2131            // This api can only be called by an active device admin,
2132            // so try to retrieve it to check that the caller is one.
2133            getActiveAdminForCallerLocked(null,
2134                    DeviceAdminInfo.USES_POLICY_RESET_PASSWORD);
2135            quality = getPasswordQuality(null, userHandle);
2136            if (quality != DevicePolicyManager.PASSWORD_QUALITY_UNSPECIFIED) {
2137                int realQuality = LockPatternUtils.computePasswordQuality(password);
2138                if (realQuality < quality
2139                        && quality != DevicePolicyManager.PASSWORD_QUALITY_COMPLEX) {
2140                    Slog.w(LOG_TAG, "resetPassword: password quality 0x"
2141                            + Integer.toHexString(realQuality)
2142                            + " does not meet required quality 0x"
2143                            + Integer.toHexString(quality));
2144                    return false;
2145                }
2146                quality = Math.max(realQuality, quality);
2147            }
2148            int length = getPasswordMinimumLength(null, userHandle);
2149            if (password.length() < length) {
2150                Slog.w(LOG_TAG, "resetPassword: password length " + password.length()
2151                        + " does not meet required length " + length);
2152                return false;
2153            }
2154            if (quality == DevicePolicyManager.PASSWORD_QUALITY_COMPLEX) {
2155                int letters = 0;
2156                int uppercase = 0;
2157                int lowercase = 0;
2158                int numbers = 0;
2159                int symbols = 0;
2160                int nonletter = 0;
2161                for (int i = 0; i < password.length(); i++) {
2162                    char c = password.charAt(i);
2163                    if (c >= 'A' && c <= 'Z') {
2164                        letters++;
2165                        uppercase++;
2166                    } else if (c >= 'a' && c <= 'z') {
2167                        letters++;
2168                        lowercase++;
2169                    } else if (c >= '0' && c <= '9') {
2170                        numbers++;
2171                        nonletter++;
2172                    } else {
2173                        symbols++;
2174                        nonletter++;
2175                    }
2176                }
2177                int neededLetters = getPasswordMinimumLetters(null, userHandle);
2178                if(letters < neededLetters) {
2179                    Slog.w(LOG_TAG, "resetPassword: number of letters " + letters
2180                            + " does not meet required number of letters " + neededLetters);
2181                    return false;
2182                }
2183                int neededNumbers = getPasswordMinimumNumeric(null, userHandle);
2184                if (numbers < neededNumbers) {
2185                    Slog.w(LOG_TAG, "resetPassword: number of numerical digits " + numbers
2186                            + " does not meet required number of numerical digits "
2187                            + neededNumbers);
2188                    return false;
2189                }
2190                int neededLowerCase = getPasswordMinimumLowerCase(null, userHandle);
2191                if (lowercase < neededLowerCase) {
2192                    Slog.w(LOG_TAG, "resetPassword: number of lowercase letters " + lowercase
2193                            + " does not meet required number of lowercase letters "
2194                            + neededLowerCase);
2195                    return false;
2196                }
2197                int neededUpperCase = getPasswordMinimumUpperCase(null, userHandle);
2198                if (uppercase < neededUpperCase) {
2199                    Slog.w(LOG_TAG, "resetPassword: number of uppercase letters " + uppercase
2200                            + " does not meet required number of uppercase letters "
2201                            + neededUpperCase);
2202                    return false;
2203                }
2204                int neededSymbols = getPasswordMinimumSymbols(null, userHandle);
2205                if (symbols < neededSymbols) {
2206                    Slog.w(LOG_TAG, "resetPassword: number of special symbols " + symbols
2207                            + " does not meet required number of special symbols " + neededSymbols);
2208                    return false;
2209                }
2210                int neededNonLetter = getPasswordMinimumNonLetter(null, userHandle);
2211                if (nonletter < neededNonLetter) {
2212                    Slog.w(LOG_TAG, "resetPassword: number of non-letter characters " + nonletter
2213                            + " does not meet required number of non-letter characters "
2214                            + neededNonLetter);
2215                    return false;
2216                }
2217            }
2218        }
2219
2220        int callingUid = Binder.getCallingUid();
2221        DevicePolicyData policy = getUserData(userHandle);
2222        if (policy.mPasswordOwner >= 0 && policy.mPasswordOwner != callingUid) {
2223            Slog.w(LOG_TAG, "resetPassword: already set by another uid and not entered by user");
2224            return false;
2225        }
2226
2227        // Don't do this with the lock held, because it is going to call
2228        // back in to the service.
2229        long ident = Binder.clearCallingIdentity();
2230        try {
2231            LockPatternUtils utils = new LockPatternUtils(mContext);
2232            utils.saveLockPassword(password, quality, false, userHandle);
2233            synchronized (this) {
2234                int newOwner = (flags&DevicePolicyManager.RESET_PASSWORD_REQUIRE_ENTRY)
2235                        != 0 ? callingUid : -1;
2236                if (policy.mPasswordOwner != newOwner) {
2237                    policy.mPasswordOwner = newOwner;
2238                    saveSettingsLocked(userHandle);
2239                }
2240            }
2241        } finally {
2242            Binder.restoreCallingIdentity(ident);
2243        }
2244
2245        return true;
2246    }
2247
2248    public void setMaximumTimeToLock(ComponentName who, long timeMs, int userHandle) {
2249        if (!mHasFeature) {
2250            return;
2251        }
2252        enforceCrossUserPermission(userHandle);
2253        synchronized (this) {
2254            if (who == null) {
2255                throw new NullPointerException("ComponentName is null");
2256            }
2257            ActiveAdmin ap = getActiveAdminForCallerLocked(who,
2258                    DeviceAdminInfo.USES_POLICY_FORCE_LOCK);
2259            if (ap.maximumTimeToUnlock != timeMs) {
2260                ap.maximumTimeToUnlock = timeMs;
2261                saveSettingsLocked(userHandle);
2262                updateMaximumTimeToLockLocked(getUserData(userHandle));
2263            }
2264        }
2265    }
2266
2267    void updateMaximumTimeToLockLocked(DevicePolicyData policy) {
2268        long timeMs = getMaximumTimeToLock(null, policy.mUserHandle);
2269        if (policy.mLastMaximumTimeToLock == timeMs) {
2270            return;
2271        }
2272
2273        long ident = Binder.clearCallingIdentity();
2274        try {
2275            if (timeMs <= 0) {
2276                timeMs = Integer.MAX_VALUE;
2277            } else {
2278                // Make sure KEEP_SCREEN_ON is disabled, since that
2279                // would allow bypassing of the maximum time to lock.
2280                Settings.Global.putInt(mContext.getContentResolver(),
2281                        Settings.Global.STAY_ON_WHILE_PLUGGED_IN, 0);
2282            }
2283
2284            policy.mLastMaximumTimeToLock = timeMs;
2285
2286            try {
2287                getIPowerManager().setMaximumScreenOffTimeoutFromDeviceAdmin((int)timeMs);
2288            } catch (RemoteException e) {
2289                Slog.w(LOG_TAG, "Failure talking with power manager", e);
2290            }
2291        } finally {
2292            Binder.restoreCallingIdentity(ident);
2293        }
2294    }
2295
2296    public long getMaximumTimeToLock(ComponentName who, int userHandle) {
2297        if (!mHasFeature) {
2298            return 0;
2299        }
2300        enforceCrossUserPermission(userHandle);
2301        synchronized (this) {
2302            long time = 0;
2303
2304            if (who != null) {
2305                ActiveAdmin admin = getActiveAdminUncheckedLocked(who, userHandle);
2306                return admin != null ? admin.maximumTimeToUnlock : time;
2307            }
2308
2309            // Return strictest policy for this user and profiles that are visible from this user.
2310            List<UserInfo> profiles = mUserManager.getProfiles(userHandle);
2311            for (UserInfo userInfo : profiles) {
2312                DevicePolicyData policy = getUserData(userInfo.getUserHandle().getIdentifier());
2313                final int N = policy.mAdminList.size();
2314                for (int i=0; i<N; i++) {
2315                    ActiveAdmin admin = policy.mAdminList.get(i);
2316                    if (time == 0) {
2317                        time = admin.maximumTimeToUnlock;
2318                    } else if (admin.maximumTimeToUnlock != 0
2319                            && time > admin.maximumTimeToUnlock) {
2320                        time = admin.maximumTimeToUnlock;
2321                    }
2322                }
2323            }
2324            return time;
2325        }
2326    }
2327
2328    public void lockNow() {
2329        if (!mHasFeature) {
2330            return;
2331        }
2332        synchronized (this) {
2333            // This API can only be called by an active device admin,
2334            // so try to retrieve it to check that the caller is one.
2335            getActiveAdminForCallerLocked(null,
2336                    DeviceAdminInfo.USES_POLICY_FORCE_LOCK);
2337            lockNowUnchecked();
2338        }
2339    }
2340
2341    private void lockNowUnchecked() {
2342        long ident = Binder.clearCallingIdentity();
2343        try {
2344            // Power off the display
2345            getIPowerManager().goToSleep(SystemClock.uptimeMillis(),
2346                    PowerManager.GO_TO_SLEEP_REASON_DEVICE_ADMIN, 0);
2347            // Ensure the device is locked
2348            getWindowManager().lockNow(null);
2349        } catch (RemoteException e) {
2350        } finally {
2351            Binder.restoreCallingIdentity(ident);
2352        }
2353    }
2354
2355    private boolean isExtStorageEncrypted() {
2356        String state = SystemProperties.get("vold.decrypt");
2357        return !"".equals(state);
2358    }
2359
2360    public boolean installCaCert(byte[] certBuffer) throws RemoteException {
2361        mContext.enforceCallingOrSelfPermission(MANAGE_CA_CERTIFICATES, null);
2362        KeyChainConnection keyChainConnection = null;
2363        byte[] pemCert;
2364        try {
2365            X509Certificate cert = parseCert(certBuffer);
2366            pemCert =  Credentials.convertToPem(cert);
2367        } catch (CertificateException ce) {
2368            Log.e(LOG_TAG, "Problem converting cert", ce);
2369            return false;
2370        } catch (IOException ioe) {
2371            Log.e(LOG_TAG, "Problem reading cert", ioe);
2372            return false;
2373        }
2374        try {
2375            keyChainConnection = KeyChain.bind(mContext);
2376            try {
2377                keyChainConnection.getService().installCaCertificate(pemCert);
2378                return true;
2379            } finally {
2380                if (keyChainConnection != null) {
2381                    keyChainConnection.close();
2382                    keyChainConnection = null;
2383                }
2384            }
2385        } catch (InterruptedException e1) {
2386            Log.w(LOG_TAG, "installCaCertsToKeyChain(): ", e1);
2387            Thread.currentThread().interrupt();
2388        }
2389        return false;
2390    }
2391
2392    private static X509Certificate parseCert(byte[] certBuffer)
2393            throws CertificateException, IOException {
2394        CertificateFactory certFactory = CertificateFactory.getInstance("X.509");
2395        return (X509Certificate) certFactory.generateCertificate(new ByteArrayInputStream(
2396                certBuffer));
2397    }
2398
2399    public void uninstallCaCert(final byte[] certBuffer) {
2400        mContext.enforceCallingOrSelfPermission(MANAGE_CA_CERTIFICATES, null);
2401        TrustedCertificateStore certStore = new TrustedCertificateStore();
2402        String alias = null;
2403        try {
2404            X509Certificate cert = parseCert(certBuffer);
2405            alias = certStore.getCertificateAlias(cert);
2406        } catch (CertificateException ce) {
2407            Log.e(LOG_TAG, "Problem creating X509Certificate", ce);
2408            return;
2409        } catch (IOException ioe) {
2410            Log.e(LOG_TAG, "Problem reading certificate", ioe);
2411            return;
2412        }
2413        try {
2414            KeyChainConnection keyChainConnection = KeyChain.bind(mContext);
2415            IKeyChainService service = keyChainConnection.getService();
2416            try {
2417                service.deleteCaCertificate(alias);
2418            } catch (RemoteException e) {
2419                Log.e(LOG_TAG, "from CaCertUninstaller: ", e);
2420            } finally {
2421                keyChainConnection.close();
2422                keyChainConnection = null;
2423            }
2424        } catch (InterruptedException ie) {
2425            Log.w(LOG_TAG, "CaCertUninstaller: ", ie);
2426            Thread.currentThread().interrupt();
2427        }
2428    }
2429
2430    void wipeDataLocked(int flags) {
2431        // If the SD card is encrypted and non-removable, we have to force a wipe.
2432        boolean forceExtWipe = !Environment.isExternalStorageRemovable() && isExtStorageEncrypted();
2433        boolean wipeExtRequested = (flags&DevicePolicyManager.WIPE_EXTERNAL_STORAGE) != 0;
2434
2435        // Note: we can only do the wipe via ExternalStorageFormatter if the volume is not emulated.
2436        if ((forceExtWipe || wipeExtRequested) && !Environment.isExternalStorageEmulated()) {
2437            Intent intent = new Intent(ExternalStorageFormatter.FORMAT_AND_FACTORY_RESET);
2438            intent.putExtra(ExternalStorageFormatter.EXTRA_ALWAYS_RESET, true);
2439            intent.setComponent(ExternalStorageFormatter.COMPONENT_NAME);
2440            mWakeLock.acquire(10000);
2441            mContext.startService(intent);
2442        } else {
2443            try {
2444                RecoverySystem.rebootWipeUserData(mContext);
2445            } catch (IOException e) {
2446                Slog.w(LOG_TAG, "Failed requesting data wipe", e);
2447            }
2448        }
2449    }
2450
2451    public void wipeData(int flags, final int userHandle) {
2452        if (!mHasFeature) {
2453            return;
2454        }
2455        enforceCrossUserPermission(userHandle);
2456        if ((flags & DevicePolicyManager.WIPE_EXTERNAL_STORAGE) != 0) {
2457            enforceNotManagedProfile(userHandle, "wipe external storage");
2458        }
2459        synchronized (this) {
2460            // This API can only be called by an active device admin,
2461            // so try to retrieve it to check that the caller is one.
2462            getActiveAdminForCallerLocked(null,
2463                    DeviceAdminInfo.USES_POLICY_WIPE_DATA);
2464            long ident = Binder.clearCallingIdentity();
2465            try {
2466                wipeDeviceOrUserLocked(flags, userHandle);
2467            } finally {
2468                Binder.restoreCallingIdentity(ident);
2469            }
2470        }
2471    }
2472
2473    private void wipeDeviceOrUserLocked(int flags, final int userHandle) {
2474        if (userHandle == UserHandle.USER_OWNER) {
2475            wipeDataLocked(flags);
2476        } else {
2477            lockNowUnchecked();
2478            mHandler.post(new Runnable() {
2479                public void run() {
2480                    try {
2481                        ActivityManagerNative.getDefault().switchUser(UserHandle.USER_OWNER);
2482                        (mUserManager)
2483                                .removeUser(userHandle);
2484                    } catch (RemoteException re) {
2485                        // Shouldn't happen
2486                    }
2487                }
2488            });
2489        }
2490    }
2491
2492    public void getRemoveWarning(ComponentName comp, final RemoteCallback result, int userHandle) {
2493        if (!mHasFeature) {
2494            return;
2495        }
2496        enforceCrossUserPermission(userHandle);
2497        mContext.enforceCallingOrSelfPermission(
2498                android.Manifest.permission.BIND_DEVICE_ADMIN, null);
2499
2500        synchronized (this) {
2501            ActiveAdmin admin = getActiveAdminUncheckedLocked(comp, userHandle);
2502            if (admin == null) {
2503                try {
2504                    result.sendResult(null);
2505                } catch (RemoteException e) {
2506                }
2507                return;
2508            }
2509            Intent intent = new Intent(DeviceAdminReceiver.ACTION_DEVICE_ADMIN_DISABLE_REQUESTED);
2510            intent.setComponent(admin.info.getComponent());
2511            mContext.sendOrderedBroadcastAsUser(intent, new UserHandle(userHandle),
2512                    null, new BroadcastReceiver() {
2513                @Override
2514                public void onReceive(Context context, Intent intent) {
2515                    try {
2516                        result.sendResult(getResultExtras(false));
2517                    } catch (RemoteException e) {
2518                    }
2519                }
2520            }, null, Activity.RESULT_OK, null, null);
2521        }
2522    }
2523
2524    public void setActivePasswordState(int quality, int length, int letters, int uppercase,
2525            int lowercase, int numbers, int symbols, int nonletter, int userHandle) {
2526        if (!mHasFeature) {
2527            return;
2528        }
2529        enforceCrossUserPermission(userHandle);
2530        enforceNotManagedProfile(userHandle, "set the active password");
2531
2532        mContext.enforceCallingOrSelfPermission(
2533                android.Manifest.permission.BIND_DEVICE_ADMIN, null);
2534        DevicePolicyData p = getUserData(userHandle);
2535
2536        validateQualityConstant(quality);
2537
2538        synchronized (this) {
2539            if (p.mActivePasswordQuality != quality || p.mActivePasswordLength != length
2540                    || p.mFailedPasswordAttempts != 0 || p.mActivePasswordLetters != letters
2541                    || p.mActivePasswordUpperCase != uppercase
2542                    || p.mActivePasswordLowerCase != lowercase
2543                    || p.mActivePasswordNumeric != numbers
2544                    || p.mActivePasswordSymbols != symbols
2545                    || p.mActivePasswordNonLetter != nonletter) {
2546                long ident = Binder.clearCallingIdentity();
2547                try {
2548                    p.mActivePasswordQuality = quality;
2549                    p.mActivePasswordLength = length;
2550                    p.mActivePasswordLetters = letters;
2551                    p.mActivePasswordLowerCase = lowercase;
2552                    p.mActivePasswordUpperCase = uppercase;
2553                    p.mActivePasswordNumeric = numbers;
2554                    p.mActivePasswordSymbols = symbols;
2555                    p.mActivePasswordNonLetter = nonletter;
2556                    p.mFailedPasswordAttempts = 0;
2557                    saveSettingsLocked(userHandle);
2558                    updatePasswordExpirationsLocked(userHandle);
2559                    setExpirationAlarmCheckLocked(mContext, p);
2560                    sendAdminCommandToSelfAndProfilesLocked(
2561                            DeviceAdminReceiver.ACTION_PASSWORD_CHANGED,
2562                            DeviceAdminInfo.USES_POLICY_LIMIT_PASSWORD, userHandle);
2563                } finally {
2564                    Binder.restoreCallingIdentity(ident);
2565                }
2566            }
2567        }
2568    }
2569
2570    /**
2571     * Called any time the device password is updated. Resets all password expiration clocks.
2572     */
2573    private void updatePasswordExpirationsLocked(int userHandle) {
2574            List<UserInfo> profiles = mUserManager.getProfiles(userHandle);
2575            for (UserInfo userInfo : profiles) {
2576                int profileId = userInfo.getUserHandle().getIdentifier();
2577                DevicePolicyData policy = getUserData(profileId);
2578                final int N = policy.mAdminList.size();
2579                if (N > 0) {
2580                    for (int i=0; i<N; i++) {
2581                        ActiveAdmin admin = policy.mAdminList.get(i);
2582                        if (admin.info.usesPolicy(DeviceAdminInfo.USES_POLICY_EXPIRE_PASSWORD)) {
2583                            long timeout = admin.passwordExpirationTimeout;
2584                            long expiration = timeout > 0L ? (timeout + System.currentTimeMillis()) : 0L;
2585                            admin.passwordExpirationDate = expiration;
2586                        }
2587                    }
2588                }
2589                saveSettingsLocked(profileId);
2590            }
2591    }
2592
2593    public void reportFailedPasswordAttempt(int userHandle) {
2594        enforceCrossUserPermission(userHandle);
2595        enforceNotManagedProfile(userHandle, "report failed password attempt");
2596        mContext.enforceCallingOrSelfPermission(
2597                android.Manifest.permission.BIND_DEVICE_ADMIN, null);
2598
2599        synchronized (this) {
2600            DevicePolicyData policy = getUserData(userHandle);
2601            long ident = Binder.clearCallingIdentity();
2602            try {
2603                policy.mFailedPasswordAttempts++;
2604                saveSettingsLocked(userHandle);
2605                if (mHasFeature) {
2606                    int max = getMaximumFailedPasswordsForWipe(null, userHandle);
2607                    if (max > 0 && policy.mFailedPasswordAttempts >= max) {
2608                        wipeDeviceOrUserLocked(0, userHandle);
2609                    }
2610                    sendAdminCommandToSelfAndProfilesLocked(
2611                            DeviceAdminReceiver.ACTION_PASSWORD_FAILED,
2612                            DeviceAdminInfo.USES_POLICY_WATCH_LOGIN, userHandle);
2613                }
2614            } finally {
2615                Binder.restoreCallingIdentity(ident);
2616            }
2617        }
2618    }
2619
2620    public void reportSuccessfulPasswordAttempt(int userHandle) {
2621        enforceCrossUserPermission(userHandle);
2622        mContext.enforceCallingOrSelfPermission(
2623                android.Manifest.permission.BIND_DEVICE_ADMIN, null);
2624
2625        synchronized (this) {
2626            DevicePolicyData policy = getUserData(userHandle);
2627            if (policy.mFailedPasswordAttempts != 0 || policy.mPasswordOwner >= 0) {
2628                long ident = Binder.clearCallingIdentity();
2629                try {
2630                    policy.mFailedPasswordAttempts = 0;
2631                    policy.mPasswordOwner = -1;
2632                    saveSettingsLocked(userHandle);
2633                    if (mHasFeature) {
2634                        sendAdminCommandToSelfAndProfilesLocked(
2635                                DeviceAdminReceiver.ACTION_PASSWORD_SUCCEEDED,
2636                                DeviceAdminInfo.USES_POLICY_WATCH_LOGIN, userHandle);
2637                    }
2638                } finally {
2639                    Binder.restoreCallingIdentity(ident);
2640                }
2641            }
2642        }
2643    }
2644
2645    public ComponentName setGlobalProxy(ComponentName who, String proxySpec,
2646            String exclusionList, int userHandle) {
2647        if (!mHasFeature) {
2648            return null;
2649        }
2650        enforceCrossUserPermission(userHandle);
2651        synchronized(this) {
2652            if (who == null) {
2653                throw new NullPointerException("ComponentName is null");
2654            }
2655
2656            // Only check if owner has set global proxy. We don't allow other users to set it.
2657            DevicePolicyData policy = getUserData(UserHandle.USER_OWNER);
2658            ActiveAdmin admin = getActiveAdminForCallerLocked(who,
2659                    DeviceAdminInfo.USES_POLICY_SETS_GLOBAL_PROXY);
2660
2661            // Scan through active admins and find if anyone has already
2662            // set the global proxy.
2663            Set<ComponentName> compSet = policy.mAdminMap.keySet();
2664            for (ComponentName component : compSet) {
2665                ActiveAdmin ap = policy.mAdminMap.get(component);
2666                if ((ap.specifiesGlobalProxy) && (!component.equals(who))) {
2667                    // Another admin already sets the global proxy
2668                    // Return it to the caller.
2669                    return component;
2670                }
2671            }
2672
2673            // If the user is not the owner, don't set the global proxy. Fail silently.
2674            if (UserHandle.getCallingUserId() != UserHandle.USER_OWNER) {
2675                Slog.w(LOG_TAG, "Only the owner is allowed to set the global proxy. User "
2676                        + userHandle + " is not permitted.");
2677                return null;
2678            }
2679            if (proxySpec == null) {
2680                admin.specifiesGlobalProxy = false;
2681                admin.globalProxySpec = null;
2682                admin.globalProxyExclusionList = null;
2683            } else {
2684
2685                admin.specifiesGlobalProxy = true;
2686                admin.globalProxySpec = proxySpec;
2687                admin.globalProxyExclusionList = exclusionList;
2688            }
2689
2690            // Reset the global proxy accordingly
2691            // Do this using system permissions, as apps cannot write to secure settings
2692            long origId = Binder.clearCallingIdentity();
2693            try {
2694                resetGlobalProxyLocked(policy);
2695            } finally {
2696                Binder.restoreCallingIdentity(origId);
2697            }
2698            return null;
2699        }
2700    }
2701
2702    public ComponentName getGlobalProxyAdmin(int userHandle) {
2703        if (!mHasFeature) {
2704            return null;
2705        }
2706        enforceCrossUserPermission(userHandle);
2707        synchronized(this) {
2708            DevicePolicyData policy = getUserData(UserHandle.USER_OWNER);
2709            // Scan through active admins and find if anyone has already
2710            // set the global proxy.
2711            final int N = policy.mAdminList.size();
2712            for (int i = 0; i < N; i++) {
2713                ActiveAdmin ap = policy.mAdminList.get(i);
2714                if (ap.specifiesGlobalProxy) {
2715                    // Device admin sets the global proxy
2716                    // Return it to the caller.
2717                    return ap.info.getComponent();
2718                }
2719            }
2720        }
2721        // No device admin sets the global proxy.
2722        return null;
2723    }
2724
2725    private void resetGlobalProxyLocked(DevicePolicyData policy) {
2726        final int N = policy.mAdminList.size();
2727        for (int i = 0; i < N; i++) {
2728            ActiveAdmin ap = policy.mAdminList.get(i);
2729            if (ap.specifiesGlobalProxy) {
2730                saveGlobalProxyLocked(ap.globalProxySpec, ap.globalProxyExclusionList);
2731                return;
2732            }
2733        }
2734        // No device admins defining global proxies - reset global proxy settings to none
2735        saveGlobalProxyLocked(null, null);
2736    }
2737
2738    private void saveGlobalProxyLocked(String proxySpec, String exclusionList) {
2739        if (exclusionList == null) {
2740            exclusionList = "";
2741        }
2742        if (proxySpec == null) {
2743            proxySpec = "";
2744        }
2745        // Remove white spaces
2746        proxySpec = proxySpec.trim();
2747        String data[] = proxySpec.split(":");
2748        int proxyPort = 8080;
2749        if (data.length > 1) {
2750            try {
2751                proxyPort = Integer.parseInt(data[1]);
2752            } catch (NumberFormatException e) {}
2753        }
2754        exclusionList = exclusionList.trim();
2755        ContentResolver res = mContext.getContentResolver();
2756
2757        ProxyInfo proxyProperties = new ProxyInfo(data[0], proxyPort, exclusionList);
2758        if (!proxyProperties.isValid()) {
2759            Slog.e(LOG_TAG, "Invalid proxy properties, ignoring: " + proxyProperties.toString());
2760            return;
2761        }
2762        Settings.Global.putString(res, Settings.Global.GLOBAL_HTTP_PROXY_HOST, data[0]);
2763        Settings.Global.putInt(res, Settings.Global.GLOBAL_HTTP_PROXY_PORT, proxyPort);
2764        Settings.Global.putString(res, Settings.Global.GLOBAL_HTTP_PROXY_EXCLUSION_LIST,
2765                exclusionList);
2766    }
2767
2768    /**
2769     * Set the storage encryption request for a single admin.  Returns the new total request
2770     * status (for all admins).
2771     */
2772    public int setStorageEncryption(ComponentName who, boolean encrypt, int userHandle) {
2773        if (!mHasFeature) {
2774            return DevicePolicyManager.ENCRYPTION_STATUS_UNSUPPORTED;
2775        }
2776        enforceCrossUserPermission(userHandle);
2777        synchronized (this) {
2778            // Check for permissions
2779            if (who == null) {
2780                throw new NullPointerException("ComponentName is null");
2781            }
2782            // Only owner can set storage encryption
2783            if (userHandle != UserHandle.USER_OWNER
2784                    || UserHandle.getCallingUserId() != UserHandle.USER_OWNER) {
2785                Slog.w(LOG_TAG, "Only owner is allowed to set storage encryption. User "
2786                        + UserHandle.getCallingUserId() + " is not permitted.");
2787                return 0;
2788            }
2789
2790            ActiveAdmin ap = getActiveAdminForCallerLocked(who,
2791                    DeviceAdminInfo.USES_ENCRYPTED_STORAGE);
2792
2793            // Quick exit:  If the filesystem does not support encryption, we can exit early.
2794            if (!isEncryptionSupported()) {
2795                return DevicePolicyManager.ENCRYPTION_STATUS_UNSUPPORTED;
2796            }
2797
2798            // (1) Record the value for the admin so it's sticky
2799            if (ap.encryptionRequested != encrypt) {
2800                ap.encryptionRequested = encrypt;
2801                saveSettingsLocked(userHandle);
2802            }
2803
2804            DevicePolicyData policy = getUserData(UserHandle.USER_OWNER);
2805            // (2) Compute "max" for all admins
2806            boolean newRequested = false;
2807            final int N = policy.mAdminList.size();
2808            for (int i = 0; i < N; i++) {
2809                newRequested |= policy.mAdminList.get(i).encryptionRequested;
2810            }
2811
2812            // Notify OS of new request
2813            setEncryptionRequested(newRequested);
2814
2815            // Return the new global request status
2816            return newRequested
2817                    ? DevicePolicyManager.ENCRYPTION_STATUS_ACTIVE
2818                    : DevicePolicyManager.ENCRYPTION_STATUS_INACTIVE;
2819        }
2820    }
2821
2822    /**
2823     * Get the current storage encryption request status for a given admin, or aggregate of all
2824     * active admins.
2825     */
2826    public boolean getStorageEncryption(ComponentName who, int userHandle) {
2827        if (!mHasFeature) {
2828            return false;
2829        }
2830        enforceCrossUserPermission(userHandle);
2831        synchronized (this) {
2832            // Check for permissions if a particular caller is specified
2833            if (who != null) {
2834                // When checking for a single caller, status is based on caller's request
2835                ActiveAdmin ap = getActiveAdminUncheckedLocked(who, userHandle);
2836                return ap != null ? ap.encryptionRequested : false;
2837            }
2838
2839            // If no particular caller is specified, return the aggregate set of requests.
2840            // This is short circuited by returning true on the first hit.
2841            DevicePolicyData policy = getUserData(userHandle);
2842            final int N = policy.mAdminList.size();
2843            for (int i = 0; i < N; i++) {
2844                if (policy.mAdminList.get(i).encryptionRequested) {
2845                    return true;
2846                }
2847            }
2848            return false;
2849        }
2850    }
2851
2852    /**
2853     * Get the current encryption status of the device.
2854     */
2855    public int getStorageEncryptionStatus(int userHandle) {
2856        if (!mHasFeature) {
2857            // Ok to return current status.
2858        }
2859        enforceCrossUserPermission(userHandle);
2860        return getEncryptionStatus();
2861    }
2862
2863    /**
2864     * Hook to low-levels:  This should report if the filesystem supports encrypted storage.
2865     */
2866    private boolean isEncryptionSupported() {
2867        // Note, this can be implemented as
2868        //   return getEncryptionStatus() != DevicePolicyManager.ENCRYPTION_STATUS_UNSUPPORTED;
2869        // But is provided as a separate internal method if there's a faster way to do a
2870        // simple check for supported-or-not.
2871        return getEncryptionStatus() != DevicePolicyManager.ENCRYPTION_STATUS_UNSUPPORTED;
2872    }
2873
2874    /**
2875     * Hook to low-levels:  Reporting the current status of encryption.
2876     * @return A value such as {@link DevicePolicyManager#ENCRYPTION_STATUS_UNSUPPORTED} or
2877     * {@link DevicePolicyManager#ENCRYPTION_STATUS_INACTIVE} or
2878     * {@link DevicePolicyManager#ENCRYPTION_STATUS_ACTIVE}.
2879     */
2880    private int getEncryptionStatus() {
2881        String status = SystemProperties.get("ro.crypto.state", "unsupported");
2882        if ("encrypted".equalsIgnoreCase(status)) {
2883            return DevicePolicyManager.ENCRYPTION_STATUS_ACTIVE;
2884        } else if ("unencrypted".equalsIgnoreCase(status)) {
2885            return DevicePolicyManager.ENCRYPTION_STATUS_INACTIVE;
2886        } else {
2887            return DevicePolicyManager.ENCRYPTION_STATUS_UNSUPPORTED;
2888        }
2889    }
2890
2891    /**
2892     * Hook to low-levels:  If needed, record the new admin setting for encryption.
2893     */
2894    private void setEncryptionRequested(boolean encrypt) {
2895    }
2896
2897    /**
2898     * The system property used to share the state of the camera. The native camera service
2899     * is expected to read this property and act accordingly.
2900     */
2901    public static final String SYSTEM_PROP_DISABLE_CAMERA = "sys.secpolicy.camera.disabled";
2902
2903    /**
2904     * Disables all device cameras according to the specified admin.
2905     */
2906    public void setCameraDisabled(ComponentName who, boolean disabled, int userHandle) {
2907        if (!mHasFeature) {
2908            return;
2909        }
2910        enforceCrossUserPermission(userHandle);
2911        enforceNotManagedProfile(userHandle, "enable/disable cameras");
2912        synchronized (this) {
2913            if (who == null) {
2914                throw new NullPointerException("ComponentName is null");
2915            }
2916            ActiveAdmin ap = getActiveAdminForCallerLocked(who,
2917                    DeviceAdminInfo.USES_POLICY_DISABLE_CAMERA);
2918            if (ap.disableCamera != disabled) {
2919                ap.disableCamera = disabled;
2920                saveSettingsLocked(userHandle);
2921            }
2922            syncDeviceCapabilitiesLocked(getUserData(userHandle));
2923        }
2924    }
2925
2926    /**
2927     * Gets whether or not all device cameras are disabled for a given admin, or disabled for any
2928     * active admins.
2929     */
2930    public boolean getCameraDisabled(ComponentName who, int userHandle) {
2931        if (!mHasFeature) {
2932            return false;
2933        }
2934        synchronized (this) {
2935            if (who != null) {
2936                ActiveAdmin admin = getActiveAdminUncheckedLocked(who, userHandle);
2937                return (admin != null) ? admin.disableCamera : false;
2938            }
2939
2940            DevicePolicyData policy = getUserData(userHandle);
2941            // Determine whether or not the device camera is disabled for any active admins.
2942            final int N = policy.mAdminList.size();
2943            for (int i = 0; i < N; i++) {
2944                ActiveAdmin admin = policy.mAdminList.get(i);
2945                if (admin.disableCamera) {
2946                    return true;
2947                }
2948            }
2949            return false;
2950        }
2951    }
2952
2953    /**
2954     * Selectively disable keyguard features.
2955     */
2956    public void setKeyguardDisabledFeatures(ComponentName who, int which, int userHandle) {
2957        if (!mHasFeature) {
2958            return;
2959        }
2960        enforceCrossUserPermission(userHandle);
2961        enforceNotManagedProfile(userHandle, "disable keyguard features");
2962        synchronized (this) {
2963            if (who == null) {
2964                throw new NullPointerException("ComponentName is null");
2965            }
2966            ActiveAdmin ap = getActiveAdminForCallerLocked(who,
2967                    DeviceAdminInfo.USES_POLICY_DISABLE_KEYGUARD_FEATURES);
2968            if (ap.disabledKeyguardFeatures != which) {
2969                ap.disabledKeyguardFeatures = which;
2970                saveSettingsLocked(userHandle);
2971            }
2972            syncDeviceCapabilitiesLocked(getUserData(userHandle));
2973        }
2974    }
2975
2976    /**
2977     * Gets the disabled state for features in keyguard for the given admin,
2978     * or the aggregate of all active admins if who is null.
2979     */
2980    public int getKeyguardDisabledFeatures(ComponentName who, int userHandle) {
2981        if (!mHasFeature) {
2982            return 0;
2983        }
2984        enforceCrossUserPermission(userHandle);
2985        synchronized (this) {
2986            if (who != null) {
2987                ActiveAdmin admin = getActiveAdminUncheckedLocked(who, userHandle);
2988                return (admin != null) ? admin.disabledKeyguardFeatures : 0;
2989            }
2990
2991            // Determine which keyguard features are disabled for any active admins.
2992            DevicePolicyData policy = getUserData(userHandle);
2993            final int N = policy.mAdminList.size();
2994            int which = 0;
2995            for (int i = 0; i < N; i++) {
2996                ActiveAdmin admin = policy.mAdminList.get(i);
2997                which |= admin.disabledKeyguardFeatures;
2998            }
2999            return which;
3000        }
3001    }
3002
3003    @Override
3004    public boolean setDeviceOwner(String packageName, String ownerName) {
3005        if (!mHasFeature) {
3006            return false;
3007        }
3008        if (packageName == null
3009                || !DeviceOwner.isInstalled(packageName, mContext.getPackageManager())) {
3010            throw new IllegalArgumentException("Invalid package name " + packageName
3011                    + " for device owner");
3012        }
3013        synchronized (this) {
3014            if (isDeviceProvisioned()) {
3015                throw new IllegalStateException(
3016                        "Trying to set device owner but device is already provisioned.");
3017            }
3018
3019            if (mDeviceOwner != null && mDeviceOwner.hasDeviceOwner()) {
3020                throw new IllegalStateException(
3021                        "Trying to set device owner but device owner is already set.");
3022            }
3023
3024            long token = Binder.clearCallingIdentity();
3025            try {
3026                mAppOpsService.setDeviceOwner(packageName);
3027            } catch (RemoteException e) {
3028                Log.w(LOG_TAG, "Unable to notify AppOpsService of DeviceOwner", e);
3029            } finally {
3030                Binder.restoreCallingIdentity(token);
3031            }
3032            if (mDeviceOwner == null) {
3033                // Device owner is not set and does not exist, set it.
3034                mDeviceOwner = DeviceOwner.createWithDeviceOwner(packageName, ownerName);
3035                mDeviceOwner.writeOwnerFile();
3036                return true;
3037            } else {
3038                // Device owner is not set but a profile owner exists, update Device owner state.
3039                mDeviceOwner.setDeviceOwner(packageName, ownerName);
3040                mDeviceOwner.writeOwnerFile();
3041                return true;
3042            }
3043        }
3044    }
3045
3046    @Override
3047    public boolean isDeviceOwner(String packageName) {
3048        if (!mHasFeature) {
3049            return false;
3050        }
3051        synchronized (this) {
3052            return mDeviceOwner != null
3053                    && mDeviceOwner.hasDeviceOwner()
3054                    && mDeviceOwner.getDeviceOwnerPackageName().equals(packageName);
3055        }
3056    }
3057
3058    @Override
3059    public String getDeviceOwner() {
3060        if (!mHasFeature) {
3061            return null;
3062        }
3063        synchronized (this) {
3064            if (mDeviceOwner != null && mDeviceOwner.hasDeviceOwner()) {
3065                return mDeviceOwner.getDeviceOwnerPackageName();
3066            }
3067        }
3068        return null;
3069    }
3070
3071    @Override
3072    public String getDeviceOwnerName() {
3073        if (!mHasFeature) {
3074            return null;
3075        }
3076        mContext.enforceCallingOrSelfPermission(android.Manifest.permission.MANAGE_USERS, null);
3077        synchronized (this) {
3078            if (mDeviceOwner != null) {
3079                return mDeviceOwner.getDeviceOwnerName();
3080            }
3081        }
3082        return null;
3083    }
3084
3085    @Override
3086    public boolean setProfileOwner(String packageName, String ownerName, int userHandle) {
3087        if (!mHasFeature) {
3088            return false;
3089        }
3090        mContext.enforceCallingOrSelfPermission(android.Manifest.permission.MANAGE_USERS, null);
3091
3092        if (mUserManager.getUserInfo(userHandle) == null) {
3093            // User doesn't exist.
3094            throw new IllegalArgumentException(
3095                    "Attempted to set profile owner for invalid userId: " + userHandle);
3096        }
3097
3098        if (packageName == null
3099                || !DeviceOwner.isInstalledForUser(packageName, userHandle)) {
3100            throw new IllegalArgumentException("Package name " + packageName
3101                    + " not installed for userId:" + userHandle);
3102        }
3103        synchronized (this) {
3104            if (isUserSetupComplete(userHandle)) {
3105                throw new IllegalStateException(
3106                        "Trying to set profile owner but user is already set-up.");
3107            }
3108            long token = Binder.clearCallingIdentity();
3109            try {
3110                mAppOpsService.setProfileOwner(packageName, userHandle);
3111            } catch (RemoteException e) {
3112                Log.w(LOG_TAG, "Unable to notify AppOpsService of ProfileOwner", e);
3113            } finally {
3114                Binder.restoreCallingIdentity(token);
3115            }
3116            if (mDeviceOwner == null) {
3117                // Device owner state does not exist, create it.
3118                mDeviceOwner = DeviceOwner.createWithProfileOwner(packageName, ownerName,
3119                        userHandle);
3120                mDeviceOwner.writeOwnerFile();
3121                return true;
3122            } else {
3123                // Device owner already exists, update it.
3124                mDeviceOwner.setProfileOwner(packageName, ownerName, userHandle);
3125                mDeviceOwner.writeOwnerFile();
3126                return true;
3127            }
3128        }
3129    }
3130
3131    @Override
3132    public void setProfileEnabled(ComponentName who) {
3133        if (!mHasFeature) {
3134            return;
3135        }
3136        synchronized (this) {
3137            // Check for permissions
3138            if (who == null) {
3139                throw new NullPointerException("ComponentName is null");
3140            }
3141            // Check if this is the profile owner who is calling
3142            getActiveAdminForCallerLocked(who, DeviceAdminInfo.USES_POLICY_PROFILE_OWNER);
3143            int userId = UserHandle.getCallingUserId();
3144            Slog.d(LOG_TAG, "Enabling the profile for: " + userId);
3145
3146            long id = Binder.clearCallingIdentity();
3147            try {
3148                mUserManager.setUserEnabled(userId);
3149                Intent intent = new Intent(Intent.ACTION_MANAGED_PROFILE_ADDED);
3150                intent.putExtra(Intent.EXTRA_USER, new UserHandle(UserHandle.getCallingUserId()));
3151                intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY |
3152                        Intent.FLAG_RECEIVER_FOREGROUND);
3153                mContext.sendBroadcastAsUser(intent, UserHandle.OWNER);
3154            } finally {
3155                restoreCallingIdentity(id);
3156            }
3157        }
3158    }
3159
3160    @Override
3161    public String getProfileOwner(int userHandle) {
3162        if (!mHasFeature) {
3163            return null;
3164        }
3165
3166        synchronized (this) {
3167            if (mDeviceOwner != null) {
3168                return mDeviceOwner.getProfileOwnerPackageName(userHandle);
3169            }
3170        }
3171        return null;
3172    }
3173
3174    @Override
3175    public String getProfileOwnerName(int userHandle) {
3176        if (!mHasFeature) {
3177            return null;
3178        }
3179        mContext.enforceCallingOrSelfPermission(android.Manifest.permission.MANAGE_USERS, null);
3180
3181        synchronized (this) {
3182            if (mDeviceOwner != null) {
3183                return mDeviceOwner.getProfileOwnerName(userHandle);
3184            }
3185        }
3186        return null;
3187    }
3188
3189    private boolean isDeviceProvisioned() {
3190        return Settings.Global.getInt(mContext.getContentResolver(),
3191                Settings.Global.DEVICE_PROVISIONED, 0) > 0;
3192    }
3193
3194    private boolean isUserSetupComplete(int userId) {
3195        return Settings.Secure.getIntForUser(mContext.getContentResolver(),
3196                Settings.Secure.USER_SETUP_COMPLETE, 0, userId) > 0;
3197    }
3198
3199    private void enforceCrossUserPermission(int userHandle) {
3200        if (userHandle < 0) {
3201            throw new IllegalArgumentException("Invalid userId " + userHandle);
3202        }
3203        final int callingUid = Binder.getCallingUid();
3204        if (userHandle == UserHandle.getUserId(callingUid)) return;
3205        if (callingUid != Process.SYSTEM_UID && callingUid != 0) {
3206            mContext.enforceCallingOrSelfPermission(
3207                    android.Manifest.permission.INTERACT_ACROSS_USERS_FULL, "Must be system or have"
3208                    + " INTERACT_ACROSS_USERS_FULL permission");
3209        }
3210    }
3211
3212    private void enforceNotManagedProfile(int userHandle, String message) {
3213        if(isManagedProfile(userHandle)) {
3214            throw new SecurityException("You can not " + message + " for a managed profile. ");
3215        }
3216    }
3217
3218    private UserInfo getProfileParent(int userHandle) {
3219        long ident = Binder.clearCallingIdentity();
3220        try {
3221            return mUserManager.getProfileParent(userHandle);
3222        } finally {
3223            Binder.restoreCallingIdentity(ident);
3224        }
3225    }
3226
3227    private boolean isManagedProfile(int userHandle) {
3228        long ident = Binder.clearCallingIdentity();
3229        try {
3230            return mUserManager.getUserInfo(userHandle).isManagedProfile();
3231        } finally {
3232            Binder.restoreCallingIdentity(ident);
3233        }
3234    }
3235
3236    private void enableIfNecessary(String packageName, int userId) {
3237        try {
3238            IPackageManager ipm = AppGlobals.getPackageManager();
3239            ApplicationInfo ai = ipm.getApplicationInfo(packageName,
3240                    PackageManager.GET_DISABLED_UNTIL_USED_COMPONENTS,
3241                    userId);
3242            if (ai.enabledSetting
3243                    == PackageManager.COMPONENT_ENABLED_STATE_DISABLED_UNTIL_USED) {
3244                ipm.setApplicationEnabledSetting(packageName,
3245                        PackageManager.COMPONENT_ENABLED_STATE_DEFAULT,
3246                        PackageManager.DONT_KILL_APP, userId, "DevicePolicyManager");
3247            }
3248        } catch (RemoteException e) {
3249        }
3250    }
3251
3252    @Override
3253    protected void dump(FileDescriptor fd, PrintWriter pw, String[] args) {
3254        if (mContext.checkCallingOrSelfPermission(android.Manifest.permission.DUMP)
3255                != PackageManager.PERMISSION_GRANTED) {
3256
3257            pw.println("Permission Denial: can't dump DevicePolicyManagerService from from pid="
3258                    + Binder.getCallingPid()
3259                    + ", uid=" + Binder.getCallingUid());
3260            return;
3261        }
3262
3263        final Printer p = new PrintWriterPrinter(pw);
3264
3265        synchronized (this) {
3266            p.println("Current Device Policy Manager state:");
3267
3268            int userCount = mUserData.size();
3269            for (int u = 0; u < userCount; u++) {
3270                DevicePolicyData policy = getUserData(mUserData.keyAt(u));
3271                p.println("  Enabled Device Admins (User " + policy.mUserHandle + "):");
3272                final int N = policy.mAdminList.size();
3273                for (int i=0; i<N; i++) {
3274                    ActiveAdmin ap = policy.mAdminList.get(i);
3275                    if (ap != null) {
3276                        pw.print("  "); pw.print(ap.info.getComponent().flattenToShortString());
3277                                pw.println(":");
3278                        ap.dump("    ", pw);
3279                    }
3280                }
3281
3282                pw.println(" ");
3283                pw.print("  mPasswordOwner="); pw.println(policy.mPasswordOwner);
3284            }
3285        }
3286    }
3287
3288    @Override
3289    public void addPersistentPreferredActivity(ComponentName who, IntentFilter filter,
3290            ComponentName activity) {
3291        synchronized (this) {
3292            if (who == null) {
3293                throw new NullPointerException("ComponentName is null");
3294            }
3295            getActiveAdminForCallerLocked(who, DeviceAdminInfo.USES_POLICY_PROFILE_OWNER);
3296
3297            IPackageManager pm = AppGlobals.getPackageManager();
3298            long id = Binder.clearCallingIdentity();
3299            try {
3300                pm.addPersistentPreferredActivity(filter, activity, UserHandle.getCallingUserId());
3301            } catch (RemoteException re) {
3302                // Shouldn't happen
3303            } finally {
3304                restoreCallingIdentity(id);
3305            }
3306        }
3307    }
3308
3309    @Override
3310    public void clearPackagePersistentPreferredActivities(ComponentName who, String packageName) {
3311        synchronized (this) {
3312            if (who == null) {
3313                throw new NullPointerException("ComponentName is null");
3314            }
3315            getActiveAdminForCallerLocked(who, DeviceAdminInfo.USES_POLICY_PROFILE_OWNER);
3316
3317            IPackageManager pm = AppGlobals.getPackageManager();
3318            long id = Binder.clearCallingIdentity();
3319            try {
3320                pm.clearPackagePersistentPreferredActivities(packageName, UserHandle.getCallingUserId());
3321            } catch (RemoteException re) {
3322                // Shouldn't happen
3323            } finally {
3324                restoreCallingIdentity(id);
3325            }
3326        }
3327    }
3328
3329    @Override
3330    public void setApplicationRestrictions(ComponentName who, String packageName, Bundle settings) {
3331        final UserHandle userHandle = new UserHandle(UserHandle.getCallingUserId());
3332
3333        synchronized (this) {
3334            if (who == null) {
3335                throw new NullPointerException("ComponentName is null");
3336            }
3337            getActiveAdminForCallerLocked(who, DeviceAdminInfo.USES_POLICY_PROFILE_OWNER);
3338
3339            long id = Binder.clearCallingIdentity();
3340            try {
3341                mUserManager.setApplicationRestrictions(packageName, settings, userHandle);
3342            } finally {
3343                restoreCallingIdentity(id);
3344            }
3345        }
3346    }
3347
3348    @Override
3349    public void setRestrictionsProvider(ComponentName who, ComponentName permissionProvider) {
3350        synchronized (this) {
3351            if (who == null) {
3352                throw new NullPointerException("ComponentName is null");
3353            }
3354            getActiveAdminForCallerLocked(who, DeviceAdminInfo.USES_POLICY_PROFILE_OWNER);
3355
3356            int userHandle = UserHandle.getCallingUserId();
3357            DevicePolicyData userData = getUserData(userHandle);
3358            userData.mRestrictionsProvider = permissionProvider;
3359            saveSettingsLocked(userHandle);
3360        }
3361    }
3362
3363    @Override
3364    public ComponentName getRestrictionsProvider(int userHandle) {
3365        synchronized (this) {
3366            if (Binder.getCallingUid() != Process.SYSTEM_UID) {
3367                throw new SecurityException("Only the system can query the permission provider");
3368            }
3369            DevicePolicyData userData = getUserData(userHandle);
3370            return userData != null ? userData.mRestrictionsProvider : null;
3371        }
3372    }
3373
3374    public void addCrossProfileIntentFilter(ComponentName who, IntentFilter filter, int flags) {
3375        int callingUserId = UserHandle.getCallingUserId();
3376        synchronized (this) {
3377            if (who == null) {
3378                throw new NullPointerException("ComponentName is null");
3379            }
3380            getActiveAdminForCallerLocked(who, DeviceAdminInfo.USES_POLICY_PROFILE_OWNER);
3381
3382            IPackageManager pm = AppGlobals.getPackageManager();
3383            long id = Binder.clearCallingIdentity();
3384            try {
3385                if ((flags & DevicePolicyManager.FLAG_PARENT_CAN_ACCESS_MANAGED) != 0) {
3386                    pm.addCrossProfileIntentFilter(filter, true /*removable*/, callingUserId,
3387                            UserHandle.USER_OWNER);
3388                }
3389                if ((flags & DevicePolicyManager.FLAG_MANAGED_CAN_ACCESS_PARENT) != 0) {
3390                    pm.addCrossProfileIntentFilter(filter, true /*removable*/, UserHandle.USER_OWNER,
3391                            callingUserId);
3392                }
3393            } catch (RemoteException re) {
3394                // Shouldn't happen
3395            } finally {
3396                restoreCallingIdentity(id);
3397            }
3398        }
3399    }
3400
3401    public void clearCrossProfileIntentFilters(ComponentName who) {
3402        int callingUserId = UserHandle.getCallingUserId();
3403        synchronized (this) {
3404            if (who == null) {
3405                throw new NullPointerException("ComponentName is null");
3406            }
3407            getActiveAdminForCallerLocked(who, DeviceAdminInfo.USES_POLICY_PROFILE_OWNER);
3408            IPackageManager pm = AppGlobals.getPackageManager();
3409            long id = Binder.clearCallingIdentity();
3410            try {
3411                pm.clearCrossProfileIntentFilters(callingUserId);
3412                pm.clearCrossProfileIntentFilters(UserHandle.USER_OWNER);
3413            } catch (RemoteException re) {
3414                // Shouldn't happen
3415            } finally {
3416                restoreCallingIdentity(id);
3417            }
3418        }
3419    }
3420
3421    @Override
3422    public UserHandle createUser(ComponentName who, String name) {
3423        synchronized (this) {
3424            if (who == null) {
3425                throw new NullPointerException("ComponentName is null");
3426            }
3427            getActiveAdminForCallerLocked(who, DeviceAdminInfo.USES_POLICY_DEVICE_OWNER);
3428
3429            long id = Binder.clearCallingIdentity();
3430            try {
3431                UserInfo userInfo = mUserManager.createUser(name, 0 /* flags */);
3432                if (userInfo != null) {
3433                    return userInfo.getUserHandle();
3434                }
3435                return null;
3436            } finally {
3437                restoreCallingIdentity(id);
3438            }
3439        }
3440    }
3441
3442    @Override
3443    public boolean removeUser(ComponentName who, UserHandle userHandle) {
3444        synchronized (this) {
3445            if (who == null) {
3446                throw new NullPointerException("ComponentName is null");
3447            }
3448            getActiveAdminForCallerLocked(who, DeviceAdminInfo.USES_POLICY_DEVICE_OWNER);
3449
3450            long id = Binder.clearCallingIdentity();
3451            try {
3452                return mUserManager.removeUser(userHandle.getIdentifier());
3453            } finally {
3454                restoreCallingIdentity(id);
3455            }
3456        }
3457    }
3458
3459    @Override
3460    public Bundle getApplicationRestrictions(ComponentName who, String packageName) {
3461        final UserHandle userHandle = new UserHandle(UserHandle.getCallingUserId());
3462
3463        synchronized (this) {
3464            if (who == null) {
3465                throw new NullPointerException("ComponentName is null");
3466            }
3467            getActiveAdminForCallerLocked(who, DeviceAdminInfo.USES_POLICY_PROFILE_OWNER);
3468
3469            long id = Binder.clearCallingIdentity();
3470            try {
3471                return mUserManager.getApplicationRestrictions(packageName, userHandle);
3472            } finally {
3473                restoreCallingIdentity(id);
3474            }
3475        }
3476    }
3477
3478    @Override
3479    public void setUserRestriction(ComponentName who, String key, boolean enabled) {
3480        final UserHandle userHandle = new UserHandle(UserHandle.getCallingUserId());
3481
3482        synchronized (this) {
3483            if (who == null) {
3484                throw new NullPointerException("ComponentName is null");
3485            }
3486            getActiveAdminForCallerLocked(who, DeviceAdminInfo.USES_POLICY_PROFILE_OWNER);
3487
3488            long id = Binder.clearCallingIdentity();
3489            try {
3490                mUserManager.setUserRestriction(key, enabled, userHandle);
3491            } finally {
3492                restoreCallingIdentity(id);
3493            }
3494        }
3495    }
3496
3497    @Override
3498    public boolean setApplicationBlocked(ComponentName who, String packageName,
3499            boolean blocked) {
3500        int callingUserId = UserHandle.getCallingUserId();
3501        synchronized (this) {
3502            if (who == null) {
3503                throw new NullPointerException("ComponentName is null");
3504            }
3505            getActiveAdminForCallerLocked(who, DeviceAdminInfo.USES_POLICY_PROFILE_OWNER);
3506
3507            long id = Binder.clearCallingIdentity();
3508            try {
3509                IPackageManager pm = AppGlobals.getPackageManager();
3510                return pm.setApplicationBlockedSettingAsUser(packageName, blocked, callingUserId);
3511            } catch (RemoteException re) {
3512                // shouldn't happen
3513                Slog.e(LOG_TAG, "Failed to setApplicationBlockedSetting", re);
3514            } finally {
3515                restoreCallingIdentity(id);
3516            }
3517            return false;
3518        }
3519    }
3520
3521    @Override
3522    public int setApplicationsBlocked(ComponentName who, Intent intent, boolean blocked) {
3523        int callingUserId = UserHandle.getCallingUserId();
3524        synchronized (this) {
3525            if (who == null) {
3526                throw new NullPointerException("ComponentName is null");
3527            }
3528            getActiveAdminForCallerLocked(who, DeviceAdminInfo.USES_POLICY_PROFILE_OWNER);
3529
3530            long id = Binder.clearCallingIdentity();
3531            try {
3532                IPackageManager pm = AppGlobals.getPackageManager();
3533                List<ResolveInfo> activitiesToEnable = pm.queryIntentActivities(intent,
3534                        intent.resolveTypeIfNeeded(mContext.getContentResolver()),
3535                        PackageManager.GET_DISABLED_COMPONENTS
3536                                | PackageManager.GET_UNINSTALLED_PACKAGES,
3537                        callingUserId);
3538
3539                if (DBG) Slog.d(LOG_TAG, "Enabling activities: " + activitiesToEnable);
3540                int numberOfAppsUnblocked = 0;
3541                if (activitiesToEnable != null) {
3542                    for (ResolveInfo info : activitiesToEnable) {
3543                        if (info.activityInfo != null) {
3544                            numberOfAppsUnblocked++;
3545                            pm.setApplicationBlockedSettingAsUser(info.activityInfo.packageName,
3546                                    blocked, callingUserId);
3547                        }
3548                    }
3549                }
3550                return numberOfAppsUnblocked;
3551            } catch (RemoteException re) {
3552                // shouldn't happen
3553                Slog.e(LOG_TAG, "Failed to setApplicationsBlockedSettingsWithIntent", re);
3554            } finally {
3555                restoreCallingIdentity(id);
3556            }
3557            return 0;
3558        }
3559    }
3560
3561    @Override
3562    public boolean isApplicationBlocked(ComponentName who, String packageName) {
3563        int callingUserId = UserHandle.getCallingUserId();
3564        synchronized (this) {
3565            if (who == null) {
3566                throw new NullPointerException("ComponentName is null");
3567            }
3568            getActiveAdminForCallerLocked(who, DeviceAdminInfo.USES_POLICY_PROFILE_OWNER);
3569
3570            long id = Binder.clearCallingIdentity();
3571            try {
3572                IPackageManager pm = AppGlobals.getPackageManager();
3573                return pm.getApplicationBlockedSettingAsUser(packageName, callingUserId);
3574            } catch (RemoteException re) {
3575                // shouldn't happen
3576                Slog.e(LOG_TAG, "Failed to getApplicationBlockedSettingAsUser", re);
3577            } finally {
3578                restoreCallingIdentity(id);
3579            }
3580            return false;
3581        }
3582    }
3583
3584    @Override
3585    public void setAccountManagementDisabled(ComponentName who, String accountType,
3586            boolean disabled) {
3587        if (!mHasFeature) {
3588            return;
3589        }
3590        synchronized (this) {
3591            if (who == null) {
3592                throw new NullPointerException("ComponentName is null");
3593            }
3594            ActiveAdmin ap = getActiveAdminForCallerLocked(who,
3595                    DeviceAdminInfo.USES_POLICY_PROFILE_OWNER);
3596            if (disabled) {
3597                ap.accountTypesWithManagementDisabled.add(accountType);
3598            } else {
3599                ap.accountTypesWithManagementDisabled.remove(accountType);
3600            }
3601            saveSettingsLocked(UserHandle.getCallingUserId());
3602        }
3603    }
3604
3605    @Override
3606    public String[] getAccountTypesWithManagementDisabled() {
3607        if (!mHasFeature) {
3608            return null;
3609        }
3610        synchronized (this) {
3611            DevicePolicyData policy = getUserData(UserHandle.getCallingUserId());
3612            final int N = policy.mAdminList.size();
3613            HashSet<String> resultSet = new HashSet<String>();
3614            for (int i = 0; i < N; i++) {
3615                ActiveAdmin admin = policy.mAdminList.get(i);
3616                resultSet.addAll(admin.accountTypesWithManagementDisabled);
3617            }
3618            return resultSet.toArray(new String[resultSet.size()]);
3619        }
3620    }
3621
3622    /**
3623     * Sets which componets may enter lock task mode.
3624     *
3625     * This function can only be called by the device owner or the profile owner.
3626     * @param components The list of components allowed to enter lock task mode.
3627     */
3628    public void setLockTaskComponents(ComponentName[] components) throws SecurityException {
3629        // Get the package names of the caller.
3630        int uid = Binder.getCallingUid();
3631        String[] packageNames = mContext.getPackageManager().getPackagesForUid(uid);
3632
3633        // Check whether any of the package name is the device owner or the profile owner.
3634        for (int i=0; i<packageNames.length; i++) {
3635            String packageName = packageNames[i];
3636            int userHandle = UserHandle.getUserId(uid);
3637            String profileOwnerPackage = getProfileOwner(userHandle);
3638            if (isDeviceOwner(packageName) ||
3639                (profileOwnerPackage != null && profileOwnerPackage.equals(packageName))) {
3640
3641                // If a package name is the device owner or the profile owner,
3642                // we update the component list.
3643                DevicePolicyData policy = getUserData(userHandle);
3644                policy.mLockTaskComponents.clear();
3645                if (components != null) {
3646                    for (int j=0; j<components.length; j++) {
3647                        ComponentName component = components[j];
3648                        policy.mLockTaskComponents.add(component);
3649                    }
3650                }
3651
3652                // Store the settings persistently.
3653                saveSettingsLocked(userHandle);
3654                return;
3655            }
3656        }
3657        throw new SecurityException();
3658    }
3659
3660    /**
3661     * This function returns the list of components allowed to start the task lock mode.
3662     */
3663    public ComponentName[] getLockTaskComponents() {
3664        int userHandle = UserHandle.USER_OWNER;
3665        DevicePolicyData policy = getUserData(userHandle);
3666        ComponentName[] tempArray = policy.mLockTaskComponents.toArray(new ComponentName[0]);
3667        return tempArray;
3668    }
3669
3670    /**
3671     * This function lets the caller know whether the given component is allowed to start the
3672     * lock task mode.
3673     * @param component The component to check
3674     */
3675    public boolean isLockTaskPermitted(ComponentName component) {
3676        // Get current user's devicepolicy
3677        int uid = Binder.getCallingUid();
3678        int userHandle = UserHandle.getUserId(uid);
3679        DevicePolicyData policy = getUserData(userHandle);
3680        for (int i=0; i<policy.mLockTaskComponents.size(); i++) {
3681            ComponentName lockTaskComponent = policy.mLockTaskComponents.get(i);
3682
3683            // If the given component equals one of the component stored our device-owner-set
3684            // list, we allow this component to start the lock task mode.
3685            if (lockTaskComponent.getPackageName().equals(component.getPackageName())) {
3686                return true;
3687            }
3688        }
3689        return false;
3690    }
3691
3692    @Override
3693    public void setGlobalSetting(ComponentName who, String setting, String value) {
3694        final ContentResolver contentResolver = mContext.getContentResolver();
3695
3696        synchronized (this) {
3697            if (who == null) {
3698                throw new NullPointerException("ComponentName is null");
3699            }
3700            getActiveAdminForCallerLocked(who, DeviceAdminInfo.USES_POLICY_DEVICE_OWNER);
3701
3702            long id = Binder.clearCallingIdentity();
3703            try {
3704                Settings.Global.putString(contentResolver, setting, value);
3705            } finally {
3706                restoreCallingIdentity(id);
3707            }
3708        }
3709    }
3710
3711    @Override
3712    public void setSecureSetting(ComponentName who, String setting, String value) {
3713        int callingUserId = UserHandle.getCallingUserId();
3714        final ContentResolver contentResolver = mContext.getContentResolver();
3715
3716        synchronized (this) {
3717            if (who == null) {
3718                throw new NullPointerException("ComponentName is null");
3719            }
3720            getActiveAdminForCallerLocked(who, DeviceAdminInfo.USES_POLICY_PROFILE_OWNER);
3721
3722            long id = Binder.clearCallingIdentity();
3723            try {
3724                Settings.Secure.putStringForUser(contentResolver, setting, value, callingUserId);
3725            } finally {
3726                restoreCallingIdentity(id);
3727            }
3728        }
3729    }
3730}
3731