Home | History | Annotate | Download | only in managedprovisioning
      1 /*
      2  * Copyright 2015, The Android Open Source Project
      3  *
      4  * Licensed under the Apache License, Version 2.0 (the "License");
      5  * you may not use this file except in compliance with the License.
      6  * You may obtain a copy of the License at
      7  *
      8  *      http://www.apache.org/licenses/LICENSE-2.0
      9  *
     10  * Unless required by applicable law or agreed to in writing, software
     11  * distributed under the License is distributed on an "AS IS" BASIS,
     12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
     13  * See the License for the specific language governing permissions and
     14  * limitations under the License.
     15  */
     16 
     17 package com.android.managedprovisioning;
     18 
     19 import static android.app.admin.DeviceAdminReceiver.ACTION_READY_FOR_USER_INITIALIZATION;
     20 import static android.app.admin.DevicePolicyManager.EXTRA_PROVISIONING_ADMIN_EXTRAS_BUNDLE;
     21 import static android.app.admin.DevicePolicyManager.EXTRA_PROVISIONING_DEVICE_ADMIN_PACKAGE_NAME;
     22 import static android.app.admin.DevicePolicyManager.EXTRA_PROVISIONING_DEVICE_INITIALIZER_COMPONENT_NAME;
     23 import static android.app.admin.DevicePolicyManager.EXTRA_PROVISIONING_LEAVE_ALL_SYSTEM_APPS_ENABLED;
     24 import static android.app.admin.DevicePolicyManager.EXTRA_PROVISIONING_SKIP_ENCRYPTION;
     25 import static android.Manifest.permission.BIND_DEVICE_ADMIN;
     26 
     27 import android.app.admin.DevicePolicyManager;
     28 import android.content.BroadcastReceiver;
     29 import android.content.ComponentName;
     30 import android.content.Context;
     31 import android.content.Intent;
     32 import android.content.pm.PackageManager;
     33 import android.content.pm.ResolveInfo;
     34 import android.os.PersistableBundle;
     35 import android.os.Process;
     36 import android.os.UserHandle;
     37 import android.text.TextUtils;
     38 
     39 import java.util.List;
     40 
     41 /**
     42  * On secondary user initialization, send a broadcast to the primary user to request CA certs.
     43  * Also, if this device has a Device Owner, send an intent to start managed provisioning.
     44   */
     45 public class UserInitializedReceiver extends BroadcastReceiver {
     46 
     47     private static final String MP_PACKAGE_NAME = "com.android.managedprovisioning";
     48     private static final String MP_ACTIVITY_NAME =
     49             "com.android.managedprovisioning.DeviceOwnerPreProvisioningActivity";
     50 
     51     @Override
     52     public void onReceive(Context context, Intent receivedIntent) {
     53         ProvisionLogger.logi("User is initialized");
     54         DevicePolicyManager dpm = (DevicePolicyManager)
     55                 context.getSystemService(Context.DEVICE_POLICY_SERVICE);
     56         if (!Utils.isCurrentUserOwner() && !Utils.isManagedProfile(context) &&
     57                 Utils.hasDeviceInitializer(context)) {
     58             ProvisionLogger.logi("Initializing secondary user with a device initializer. " +
     59                     "Starting managed provisioning.");
     60             requestCACerts(context);
     61             launchManagedProvisioning(context);
     62         }
     63     }
     64 
     65     private void requestCACerts(Context context) {
     66         Intent intent = new Intent(InstallCertRequestReceiver.REQUEST_CERT_ACTION);
     67         intent.addFlags(Intent.FLAG_RECEIVER_FOREGROUND);
     68         intent.putExtra(CertService.EXTRA_REQUESTING_USER, Process.myUserHandle());
     69         context.sendBroadcastAsUser(intent, UserHandle.OWNER);
     70     }
     71 
     72     /**
     73      * Construct an appropriate intent and launch managed provisioning for a secondary user.
     74      */
     75     private void launchManagedProvisioning(Context context) {
     76         DevicePolicyManager dpm = (DevicePolicyManager)
     77                 context.getSystemService(Context.DEVICE_POLICY_SERVICE);
     78 
     79         Intent startMpIntent = new Intent(context, DeviceOwnerPreProvisioningActivity.class);
     80         startMpIntent.setAction(DeviceOwnerPreProvisioningActivity.ACTION_PROVISION_SECONDARY_USER);
     81         startMpIntent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
     82         startMpIntent.putExtra(
     83                 EXTRA_PROVISIONING_DEVICE_ADMIN_PACKAGE_NAME, dpm.getDeviceOwner());
     84 
     85         ComponentName diComponentName = getDeviceInitializerComponentName(
     86                 dpm.getDeviceInitializerApp(), context);
     87         if (diComponentName != null) {
     88             startMpIntent.putExtra(
     89                     EXTRA_PROVISIONING_DEVICE_INITIALIZER_COMPONENT_NAME,
     90                     diComponentName);
     91         }
     92 
     93         // Rely on DPC to disable any system apps that need to be turned off
     94         startMpIntent.putExtra(EXTRA_PROVISIONING_LEAVE_ALL_SYSTEM_APPS_ENABLED, true);
     95 
     96         // For secondary users, if the device needs to be encrypted, it has already happened
     97         startMpIntent.putExtra(EXTRA_PROVISIONING_SKIP_ENCRYPTION, true);
     98         ProvisionLogger.logd("Sending intent to start managed provisioning");
     99         context.startActivity(startMpIntent);
    100     }
    101 
    102     /**
    103      * Find the name of the device initializer component within the given package. It must be a
    104      * broadcast receiver with ACTION_READY_FOR_USER_INITIALIZATION and the BIND_DEVICE_OWNER
    105      * permission.
    106      * @param deviceInitializerPackageName The package to check
    107      * @return The ComponentName for the DI, or null if an appropriate component couldn't be found
    108      */
    109     private ComponentName getDeviceInitializerComponentName(String deviceInitializerPackageName,
    110             Context context) {
    111 
    112         if (!TextUtils.isEmpty(deviceInitializerPackageName)) {
    113             Intent findDeviceInitIntent = new Intent(ACTION_READY_FOR_USER_INITIALIZATION);
    114             findDeviceInitIntent.setPackage(deviceInitializerPackageName);
    115 
    116             PackageManager pm = context.getPackageManager();
    117             List<ResolveInfo> results;
    118             results = pm.queryBroadcastReceivers(findDeviceInitIntent,
    119                     PackageManager.GET_DISABLED_COMPONENTS, UserHandle.USER_OWNER);
    120 
    121             for (ResolveInfo result : results) {
    122                 if (result.activityInfo.permission != null &&
    123                         result.activityInfo.permission.equals(BIND_DEVICE_ADMIN)) {
    124                     return new ComponentName(
    125                             result.activityInfo.packageName, result.activityInfo.name);
    126                 }
    127             }
    128         }
    129         return null;
    130     }
    131 }
    132