1 /* 2 * Copyright 2016, 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.model; 18 19 import static android.app.admin.DevicePolicyManager.EXTRA_PROVISIONING_ACCOUNT_TO_MIGRATE; 20 import static android.app.admin.DevicePolicyManager.EXTRA_PROVISIONING_ADMIN_EXTRAS_BUNDLE; 21 import static android.app.admin.DevicePolicyManager.EXTRA_PROVISIONING_DEVICE_ADMIN_COMPONENT_NAME; 22 import static android.app.admin.DevicePolicyManager.EXTRA_PROVISIONING_DEVICE_ADMIN_PACKAGE_ICON_URI; 23 import static android.app.admin.DevicePolicyManager.EXTRA_PROVISIONING_DEVICE_ADMIN_PACKAGE_LABEL; 24 import static android.app.admin.DevicePolicyManager.EXTRA_PROVISIONING_DEVICE_ADMIN_PACKAGE_NAME; 25 import static android.app.admin.DevicePolicyManager.EXTRA_PROVISIONING_DISCLAIMERS; 26 import static android.app.admin.DevicePolicyManager.EXTRA_PROVISIONING_KEEP_ACCOUNT_ON_MIGRATION; 27 import static android.app.admin.DevicePolicyManager.EXTRA_PROVISIONING_LEAVE_ALL_SYSTEM_APPS_ENABLED; 28 import static android.app.admin.DevicePolicyManager.EXTRA_PROVISIONING_LOCALE; 29 import static android.app.admin.DevicePolicyManager.EXTRA_PROVISIONING_LOCAL_TIME; 30 import static android.app.admin.DevicePolicyManager.EXTRA_PROVISIONING_MAIN_COLOR; 31 import static android.app.admin.DevicePolicyManager.EXTRA_PROVISIONING_ORGANIZATION_NAME; 32 import static android.app.admin.DevicePolicyManager.EXTRA_PROVISIONING_SKIP_ENCRYPTION; 33 import static android.app.admin.DevicePolicyManager.EXTRA_PROVISIONING_SKIP_USER_CONSENT; 34 import static android.app.admin.DevicePolicyManager.EXTRA_PROVISIONING_SKIP_EDUCATION_SCREENS; 35 import static android.app.admin.DevicePolicyManager.EXTRA_PROVISIONING_SKIP_USER_SETUP; 36 import static android.app.admin.DevicePolicyManager.EXTRA_PROVISIONING_SUPPORT_URL; 37 import static android.app.admin.DevicePolicyManager.EXTRA_PROVISIONING_TIME_ZONE; 38 import static android.app.admin.DevicePolicyManager.EXTRA_PROVISIONING_USE_MOBILE_DATA; 39 40 import static com.android.internal.util.Preconditions.checkArgument; 41 import static com.android.internal.util.Preconditions.checkNotNull; 42 import static com.android.managedprovisioning.common.ManagedProvisioningSharedPreferences.DEFAULT_PROVISIONING_ID; 43 import static com.android.managedprovisioning.common.StoreUtils.accountToPersistableBundle; 44 import static com.android.managedprovisioning.common.StoreUtils.getIntegerAttrFromPersistableBundle; 45 import static com.android.managedprovisioning.common.StoreUtils.getObjectAttrFromPersistableBundle; 46 import static com.android.managedprovisioning.common.StoreUtils.getStringAttrFromPersistableBundle; 47 import static com.android.managedprovisioning.common.StoreUtils.putIntegerIfNotNull; 48 import static com.android.managedprovisioning.common.StoreUtils.putPersistableBundlableIfNotNull; 49 50 import android.accounts.Account; 51 import android.annotation.IntDef; 52 import android.content.ComponentName; 53 import android.content.Context; 54 import android.os.Parcel; 55 import android.os.Parcelable; 56 import android.os.PersistableBundle; 57 import android.util.AtomicFile; 58 import android.util.Xml; 59 60 import androidx.annotation.Nullable; 61 62 import com.android.internal.util.FastXmlSerializer; 63 import com.android.managedprovisioning.common.IllegalProvisioningArgumentException; 64 import com.android.managedprovisioning.common.PersistableBundlable; 65 import com.android.managedprovisioning.common.ProvisionLogger; 66 import com.android.managedprovisioning.common.StoreUtils; 67 import com.android.managedprovisioning.common.Utils; 68 69 import org.xmlpull.v1.XmlPullParser; 70 import org.xmlpull.v1.XmlPullParserException; 71 import org.xmlpull.v1.XmlSerializer; 72 73 import java.io.File; 74 import java.io.FileInputStream; 75 import java.io.FileOutputStream; 76 import java.io.IOException; 77 import java.lang.annotation.Retention; 78 import java.lang.annotation.RetentionPolicy; 79 import java.nio.charset.StandardCharsets; 80 import java.util.Locale; 81 82 /** 83 * Provisioning parameters for Device Owner and Profile Owner provisioning. 84 */ 85 public final class ProvisioningParams extends PersistableBundlable { 86 public static final long DEFAULT_LOCAL_TIME = -1; 87 public static final Integer DEFAULT_MAIN_COLOR = null; 88 public static final boolean DEFAULT_STARTED_BY_TRUSTED_SOURCE = false; 89 public static final boolean DEFAULT_IS_NFC = false; 90 public static final boolean DEFAULT_IS_QR_PROVISIONING = false; 91 public static final boolean DEFAULT_LEAVE_ALL_SYSTEM_APPS_ENABLED = false; 92 public static final boolean DEFAULT_EXTRA_PROVISIONING_SKIP_ENCRYPTION = false; 93 public static final boolean DEFAULT_EXTRA_PROVISIONING_SKIP_USER_CONSENT = false; 94 public static final boolean DEFAULT_EXTRA_PROVISIONING_SKIP_EDUCATION_SCREENS = false; 95 public static final boolean DEFAULT_EXTRA_PROVISIONING_KEEP_ACCOUNT_MIGRATED = false; 96 public static final boolean DEFAULT_SKIP_USER_SETUP = true; 97 public static final boolean DEFAULT_EXTRA_PROVISIONING_USE_MOBILE_DATA = false; 98 // Intent extra used internally for passing data between activities and service. 99 public static final String EXTRA_PROVISIONING_PARAMS = "provisioningParams"; 100 101 // Possible provisioning modes for organization owned provisioning. 102 public static final int PROVISIONING_MODE_UNDECIDED = 0; 103 public static final int PROVISIONING_MODE_FULLY_MANAGED_DEVICE = 1; 104 public static final int PROVISIONING_MODE_MANAGED_PROFILE = 2; 105 public static final int PROVISIONING_MODE_MANAGED_PROFILE_ON_FULLY_NAMAGED_DEVICE = 3; 106 public static final int PROVISIONING_MODE_FULLY_MANAGED_DEVICE_LEGACY = 4; 107 108 // Provisioning mode for financed device provisioning 109 public static final int PROVISIONING_MODE_FINANCED_DEVICE = 5; 110 111 @IntDef(prefix = { "PROVISIONING_MODE_" }, value = { 112 PROVISIONING_MODE_UNDECIDED, 113 PROVISIONING_MODE_FULLY_MANAGED_DEVICE, 114 PROVISIONING_MODE_MANAGED_PROFILE, 115 PROVISIONING_MODE_MANAGED_PROFILE_ON_FULLY_NAMAGED_DEVICE, 116 PROVISIONING_MODE_FULLY_MANAGED_DEVICE_LEGACY, 117 PROVISIONING_MODE_FINANCED_DEVICE 118 }) 119 @Retention(RetentionPolicy.SOURCE) 120 public @interface ProvisioningMode {} 121 122 private static final String TAG_PROVISIONING_ID = "provisioning-id"; 123 private static final String TAG_PROVISIONING_PARAMS = "provisioning-params"; 124 private static final String TAG_WIFI_INFO = "wifi-info"; 125 private static final String TAG_PACKAGE_DOWNLOAD_INFO = "download-info"; 126 private static final String TAG_STARTED_BY_TRUSTED_SOURCE = "started-by-trusted-source"; 127 private static final String TAG_IS_NFC = "started-is-nfc"; 128 private static final String TAG_IS_QR_PROVISIONING = "is-qr-provisioning"; 129 private static final String TAG_PROVISIONING_ACTION = "provisioning-action"; 130 private static final String TAG_IS_ORGANIZATION_OWNED_PROVISIONING = 131 "is-organization-owned-provisioning"; 132 private static final String TAG_IS_TRANSITIONING_FROM_REGULAR_TO_CHILD = 133 "is-transitioning-from-regular-to-child"; 134 private static final String TAG_PROVISIONING_MODE = "provisioning-mode"; 135 136 public static final Parcelable.Creator<ProvisioningParams> CREATOR 137 = new Parcelable.Creator<ProvisioningParams>() { 138 @Override 139 public ProvisioningParams createFromParcel(Parcel in) { 140 return new ProvisioningParams(in); 141 } 142 143 @Override 144 public ProvisioningParams[] newArray(int size) { 145 return new ProvisioningParams[size]; 146 } 147 }; 148 149 public final long provisioningId; 150 151 @Nullable 152 public final String timeZone; 153 154 public final long localTime; 155 156 @Nullable 157 public final Locale locale; 158 159 /** WiFi configuration. */ 160 @Nullable 161 public final WifiInfo wifiInfo; 162 163 public final boolean useMobileData; 164 165 /** 166 * Package name of the device admin package. 167 * 168 * <p>At least one one of deviceAdminPackageName and deviceAdminComponentName should be 169 * non-null. 170 * <p> 171 * In most cases, it is preferable to access the admin package name using 172 * {@link #inferDeviceAdminPackageName}. 173 */ 174 @Deprecated 175 @Nullable 176 public final String deviceAdminPackageName; 177 178 /** 179 * {@link ComponentName} of the device admin package. 180 * 181 * <p>At least one one of deviceAdminPackageName and deviceAdminComponentName should be 182 * non-null. 183 * <p> 184 * In most cases, it is preferable to access the admin component name using 185 * {@link #inferDeviceAdminComponentName(Utils, Context, int)} . 186 */ 187 @Nullable 188 public final ComponentName deviceAdminComponentName; 189 190 public final String deviceAdminLabel; 191 public final String organizationName; 192 public final String supportUrl; 193 public final String deviceAdminIconFilePath; 194 195 /** {@link Account} that should be migrated to the managed profile. */ 196 @Nullable 197 public final Account accountToMigrate; 198 199 /** True if the account will not be removed from the calling user after it is migrated. */ 200 public final boolean keepAccountMigrated; 201 202 /** Provisioning action comes along with the provisioning data. */ 203 public final String provisioningAction; 204 205 /** 206 * The main color theme used in managed profile only. 207 * 208 * <p>{@code null} means the default value. 209 */ 210 @Nullable 211 public final Integer mainColor; 212 213 /** The download information of device admin package. */ 214 @Nullable 215 public final PackageDownloadInfo deviceAdminDownloadInfo; 216 217 /** List of disclaimers */ 218 @Nullable 219 public final DisclaimersParam disclaimersParam; 220 221 /** 222 * Custom key-value pairs from enterprise mobility management which are passed to device admin 223 * package after provisioning. 224 * 225 * <p>Note that {@link ProvisioningParams} is not immutable because this field is mutable. 226 */ 227 @Nullable 228 public final PersistableBundle adminExtrasBundle; 229 230 /** 231 * True iff provisioning flow was started by a trusted app. This includes Nfc bump and QR code. 232 */ 233 public final boolean startedByTrustedSource; 234 235 public final boolean isNfc; 236 237 public final boolean isQrProvisioning; 238 239 /** True if all system apps should be enabled after provisioning. */ 240 public final boolean leaveAllSystemAppsEnabled; 241 242 /** True if device encryption should be skipped. */ 243 public final boolean skipEncryption; 244 245 /** True if user setup can be skipped. */ 246 public final boolean skipUserSetup; 247 248 public final boolean skipEducationScreens; 249 250 /** True if user consent page in pre-provisioning can be skipped. */ 251 public final boolean skipUserConsent; 252 253 /** True if the provisioning is done on a device owned by the organization. */ 254 public final boolean isOrganizationOwnedProvisioning; 255 256 /** True if the device is transitioning from regular to child user. */ 257 public final boolean isTransitioningFromRegularToChild; 258 259 /** 260 * The provisioning mode for organization owned provisioning. This is only used for 261 * admin integrated flow. 262 */ 263 public final @ProvisioningMode int provisioningMode; 264 inferStaticDeviceAdminPackageName(ComponentName deviceAdminComponentName, String deviceAdminPackageName)265 public static String inferStaticDeviceAdminPackageName(ComponentName deviceAdminComponentName, 266 String deviceAdminPackageName) { 267 if (deviceAdminComponentName != null) { 268 return deviceAdminComponentName.getPackageName(); 269 } 270 return deviceAdminPackageName; 271 } 272 inferDeviceAdminPackageName()273 public String inferDeviceAdminPackageName() { 274 return inferStaticDeviceAdminPackageName(deviceAdminComponentName, deviceAdminPackageName); 275 } 276 277 /** 278 * Due to legacy reason, DPC is allowed to provide either package name or the component name. 279 * If component name is not {@code null}, we will return it right away. Otherwise, we will 280 * infer the component name. 281 * <p> 282 * In most cases, it is preferable to access the admin component name using this method. 283 * But if the purpose is to verify the device admin component name, you should use 284 * {@link Utils#findDeviceAdmin(String, ComponentName, Context, int)} instead. 285 */ inferDeviceAdminComponentName(Utils utils, Context context, int userId)286 public ComponentName inferDeviceAdminComponentName(Utils utils, Context context, int userId) 287 throws IllegalProvisioningArgumentException { 288 if (deviceAdminComponentName != null) { 289 return deviceAdminComponentName; 290 } 291 return utils.findDeviceAdmin( 292 deviceAdminPackageName, deviceAdminComponentName, context, userId); 293 } 294 ProvisioningParams(Builder builder)295 private ProvisioningParams(Builder builder) { 296 provisioningId = builder.mProvisioningId; 297 timeZone = builder.mTimeZone; 298 localTime = builder.mLocalTime; 299 locale = builder.mLocale; 300 301 wifiInfo = builder.mWifiInfo; 302 useMobileData = builder.mUseMobileData; 303 304 deviceAdminComponentName = builder.mDeviceAdminComponentName; 305 deviceAdminPackageName = builder.mDeviceAdminPackageName; 306 deviceAdminLabel = builder.mDeviceAdminLabel; 307 organizationName = builder.mOrganizationName; 308 supportUrl = builder.mSupportUrl; 309 deviceAdminIconFilePath = builder.mDeviceAdminIconFilePath; 310 311 deviceAdminDownloadInfo = builder.mDeviceAdminDownloadInfo; 312 disclaimersParam = builder.mDisclaimersParam; 313 314 adminExtrasBundle = builder.mAdminExtrasBundle; 315 316 startedByTrustedSource = builder.mStartedByTrustedSource; 317 isNfc = builder.mIsNfc; 318 isQrProvisioning = builder.mIsQrProvisioning; 319 leaveAllSystemAppsEnabled = builder.mLeaveAllSystemAppsEnabled; 320 skipEncryption = builder.mSkipEncryption; 321 accountToMigrate = builder.mAccountToMigrate; 322 provisioningAction = checkNotNull(builder.mProvisioningAction); 323 mainColor = builder.mMainColor; 324 skipUserConsent = builder.mSkipUserConsent; 325 skipUserSetup = builder.mSkipUserSetup; 326 skipEducationScreens = builder.mSkipEducationScreens; 327 keepAccountMigrated = builder.mKeepAccountMigrated; 328 329 isOrganizationOwnedProvisioning = builder.mIsOrganizationOwnedProvisioning; 330 isTransitioningFromRegularToChild = builder.mIsTransitioningFromRegularToChild; 331 provisioningMode = builder.mProvisioningMode; 332 333 validateFields(); 334 } 335 ProvisioningParams(Parcel in)336 private ProvisioningParams(Parcel in) { 337 this(createBuilderFromPersistableBundle( 338 PersistableBundlable.getPersistableBundleFromParcel(in))); 339 } 340 validateFields()341 private void validateFields() { 342 checkArgument(deviceAdminPackageName != null || deviceAdminComponentName != null); 343 } 344 345 @Override toPersistableBundle()346 public PersistableBundle toPersistableBundle() { 347 final PersistableBundle bundle = new PersistableBundle(); 348 349 bundle.putLong(TAG_PROVISIONING_ID, provisioningId); 350 bundle.putString(EXTRA_PROVISIONING_TIME_ZONE, timeZone); 351 bundle.putLong(EXTRA_PROVISIONING_LOCAL_TIME, localTime); 352 bundle.putString(EXTRA_PROVISIONING_LOCALE, StoreUtils.localeToString(locale)); 353 putPersistableBundlableIfNotNull(bundle, TAG_WIFI_INFO, wifiInfo); 354 bundle.putBoolean(EXTRA_PROVISIONING_USE_MOBILE_DATA, useMobileData); 355 bundle.putString(EXTRA_PROVISIONING_DEVICE_ADMIN_PACKAGE_NAME, deviceAdminPackageName); 356 bundle.putString(EXTRA_PROVISIONING_DEVICE_ADMIN_COMPONENT_NAME, 357 StoreUtils.componentNameToString(deviceAdminComponentName)); 358 bundle.putString(EXTRA_PROVISIONING_DEVICE_ADMIN_PACKAGE_LABEL, deviceAdminLabel); 359 bundle.putString(EXTRA_PROVISIONING_ORGANIZATION_NAME, organizationName); 360 bundle.putString(EXTRA_PROVISIONING_SUPPORT_URL, supportUrl); 361 bundle.putString(EXTRA_PROVISIONING_DEVICE_ADMIN_PACKAGE_ICON_URI, deviceAdminIconFilePath); 362 bundle.putPersistableBundle(EXTRA_PROVISIONING_ACCOUNT_TO_MIGRATE, accountToMigrate == null 363 ? null : accountToPersistableBundle(accountToMigrate)); 364 bundle.putString(TAG_PROVISIONING_ACTION, provisioningAction); 365 putIntegerIfNotNull(bundle, EXTRA_PROVISIONING_MAIN_COLOR, mainColor); 366 putPersistableBundlableIfNotNull(bundle, TAG_PACKAGE_DOWNLOAD_INFO, 367 deviceAdminDownloadInfo); 368 putPersistableBundlableIfNotNull(bundle, EXTRA_PROVISIONING_DISCLAIMERS, 369 disclaimersParam); 370 bundle.putPersistableBundle(EXTRA_PROVISIONING_ADMIN_EXTRAS_BUNDLE, adminExtrasBundle); 371 bundle.putBoolean(TAG_STARTED_BY_TRUSTED_SOURCE, startedByTrustedSource); 372 bundle.putBoolean(TAG_IS_NFC, isNfc); 373 bundle.putBoolean(TAG_IS_QR_PROVISIONING, isQrProvisioning); 374 bundle.putBoolean(EXTRA_PROVISIONING_LEAVE_ALL_SYSTEM_APPS_ENABLED, 375 leaveAllSystemAppsEnabled); 376 bundle.putBoolean(EXTRA_PROVISIONING_SKIP_ENCRYPTION, skipEncryption); 377 bundle.putBoolean(EXTRA_PROVISIONING_SKIP_USER_SETUP, skipUserSetup); 378 bundle.putBoolean(EXTRA_PROVISIONING_SKIP_USER_CONSENT, skipUserConsent); 379 bundle.putBoolean(EXTRA_PROVISIONING_SKIP_EDUCATION_SCREENS, skipEducationScreens); 380 bundle.putBoolean(EXTRA_PROVISIONING_KEEP_ACCOUNT_ON_MIGRATION, keepAccountMigrated); 381 bundle.putBoolean(TAG_IS_ORGANIZATION_OWNED_PROVISIONING, isOrganizationOwnedProvisioning); 382 bundle.putBoolean(TAG_IS_TRANSITIONING_FROM_REGULAR_TO_CHILD, 383 isTransitioningFromRegularToChild); 384 bundle.putInt(TAG_PROVISIONING_MODE, provisioningMode); 385 return bundle; 386 } 387 fromPersistableBundle(PersistableBundle bundle)388 /* package */ static ProvisioningParams fromPersistableBundle(PersistableBundle bundle) { 389 return createBuilderFromPersistableBundle(bundle).build(); 390 } 391 createBuilderFromPersistableBundle(PersistableBundle bundle)392 private static Builder createBuilderFromPersistableBundle(PersistableBundle bundle) { 393 Builder builder = new Builder(); 394 builder.setProvisioningId(bundle.getLong(TAG_PROVISIONING_ID, DEFAULT_PROVISIONING_ID)); 395 builder.setTimeZone(bundle.getString(EXTRA_PROVISIONING_TIME_ZONE)); 396 builder.setLocalTime(bundle.getLong(EXTRA_PROVISIONING_LOCAL_TIME)); 397 builder.setLocale(getStringAttrFromPersistableBundle(bundle, 398 EXTRA_PROVISIONING_LOCALE, StoreUtils::stringToLocale)); 399 builder.setUseMobileData(bundle.getBoolean(EXTRA_PROVISIONING_USE_MOBILE_DATA)); 400 builder.setWifiInfo(getObjectAttrFromPersistableBundle(bundle, 401 TAG_WIFI_INFO, WifiInfo::fromPersistableBundle)); 402 builder.setDeviceAdminPackageName(bundle.getString( 403 EXTRA_PROVISIONING_DEVICE_ADMIN_PACKAGE_NAME)); 404 builder.setDeviceAdminComponentName(getStringAttrFromPersistableBundle(bundle, 405 EXTRA_PROVISIONING_DEVICE_ADMIN_COMPONENT_NAME, StoreUtils::stringToComponentName)); 406 builder.setDeviceAdminLabel(bundle.getString( 407 EXTRA_PROVISIONING_DEVICE_ADMIN_PACKAGE_LABEL)); 408 builder.setOrganizationName(bundle.getString(EXTRA_PROVISIONING_ORGANIZATION_NAME)); 409 builder.setSupportUrl(bundle.getString(EXTRA_PROVISIONING_SUPPORT_URL)); 410 builder.setDeviceAdminIconFilePath(bundle.getString( 411 EXTRA_PROVISIONING_DEVICE_ADMIN_PACKAGE_ICON_URI)); 412 builder.setAccountToMigrate(getObjectAttrFromPersistableBundle(bundle, 413 EXTRA_PROVISIONING_ACCOUNT_TO_MIGRATE, StoreUtils::persistableBundleToAccount)); 414 builder.setProvisioningAction(bundle.getString(TAG_PROVISIONING_ACTION)); 415 builder.setMainColor(getIntegerAttrFromPersistableBundle(bundle, 416 EXTRA_PROVISIONING_MAIN_COLOR)); 417 builder.setDeviceAdminDownloadInfo(getObjectAttrFromPersistableBundle(bundle, 418 TAG_PACKAGE_DOWNLOAD_INFO, PackageDownloadInfo::fromPersistableBundle)); 419 builder.setDisclaimersParam(getObjectAttrFromPersistableBundle(bundle, 420 EXTRA_PROVISIONING_DISCLAIMERS, DisclaimersParam::fromPersistableBundle)); 421 builder.setAdminExtrasBundle(bundle.getPersistableBundle( 422 EXTRA_PROVISIONING_ADMIN_EXTRAS_BUNDLE)); 423 builder.setStartedByTrustedSource(bundle.getBoolean(TAG_STARTED_BY_TRUSTED_SOURCE)); 424 builder.setIsNfc(bundle.getBoolean(TAG_IS_NFC)); 425 builder.setIsQrProvisioning(bundle.getBoolean(TAG_IS_QR_PROVISIONING)); 426 builder.setSkipEncryption(bundle.getBoolean(EXTRA_PROVISIONING_SKIP_ENCRYPTION)); 427 builder.setLeaveAllSystemAppsEnabled(bundle.getBoolean( 428 EXTRA_PROVISIONING_LEAVE_ALL_SYSTEM_APPS_ENABLED)); 429 builder.setSkipUserSetup(bundle.getBoolean(EXTRA_PROVISIONING_SKIP_USER_SETUP)); 430 builder.setSkipUserConsent(bundle.getBoolean(EXTRA_PROVISIONING_SKIP_USER_CONSENT)); 431 builder.setSkipEducationScreens(bundle.getBoolean(EXTRA_PROVISIONING_SKIP_EDUCATION_SCREENS)); 432 builder.setKeepAccountMigrated(bundle.getBoolean( 433 EXTRA_PROVISIONING_KEEP_ACCOUNT_ON_MIGRATION)); 434 builder.setIsOrganizationOwnedProvisioning(bundle.getBoolean( 435 TAG_IS_ORGANIZATION_OWNED_PROVISIONING)); 436 builder.setIsTransitioningFromRegularToChild(bundle.getBoolean( 437 TAG_IS_TRANSITIONING_FROM_REGULAR_TO_CHILD)); 438 builder.setProvisioningMode(bundle.getInt(TAG_PROVISIONING_MODE)); 439 return builder; 440 } 441 toBuilder()442 public Builder toBuilder() { 443 return createBuilderFromPersistableBundle(toPersistableBundle()); 444 } 445 446 @Override toString()447 public String toString() { 448 return "ProvisioningParams values: " + toPersistableBundle().toString(); 449 } 450 451 /** 452 * Saves the ProvisioningParams to the specified file. 453 */ save(File file)454 public void save(File file) { 455 ProvisionLogger.logd("Saving ProvisioningParams to " + file); 456 AtomicFile atomicFile = null; 457 FileOutputStream stream = null; 458 try { 459 atomicFile = new AtomicFile(file); 460 stream = atomicFile.startWrite(); 461 XmlSerializer serializer = new FastXmlSerializer(); 462 serializer.setOutput(stream, StandardCharsets.UTF_8.name()); 463 serializer.startDocument(null, true); 464 serializer.startTag(null, TAG_PROVISIONING_PARAMS); 465 toPersistableBundle().saveToXml(serializer); 466 serializer.endTag(null, TAG_PROVISIONING_PARAMS); 467 serializer.endDocument(); 468 atomicFile.finishWrite(stream); 469 } catch (IOException | XmlPullParserException e) { 470 ProvisionLogger.loge("Caught exception while trying to save Provisioning Params to " 471 + " file " + file, e); 472 file.delete(); 473 if (atomicFile != null) { 474 atomicFile.failWrite(stream); 475 } 476 } 477 } 478 cleanUp()479 public void cleanUp() { 480 if (disclaimersParam != null) { 481 disclaimersParam.cleanUp(); 482 } 483 if (deviceAdminIconFilePath != null) { 484 new File(deviceAdminIconFilePath).delete(); 485 } 486 } 487 488 /** 489 * Loads the ProvisioningParams From the specified file. 490 */ load(File file)491 public static ProvisioningParams load(File file) { 492 if (!file.exists()) { 493 return null; 494 } 495 ProvisionLogger.logd("Loading ProvisioningParams from " + file); 496 try (FileInputStream stream = new FileInputStream(file)) { 497 XmlPullParser parser = Xml.newPullParser(); 498 parser.setInput(stream, null); 499 return load(parser); 500 } catch (IOException | XmlPullParserException e) { 501 ProvisionLogger.loge("Caught exception while trying to load the provisioning params" 502 + " from file " + file, e); 503 return null; 504 } 505 } 506 load(XmlPullParser parser)507 private static ProvisioningParams load(XmlPullParser parser) throws XmlPullParserException, 508 IOException { 509 int type; 510 int outerDepth = parser.getDepth(); 511 while ((type = parser.next()) != XmlPullParser.END_DOCUMENT 512 && (type != XmlPullParser.END_TAG || parser.getDepth() > outerDepth)) { 513 if (type == XmlPullParser.END_TAG || type == XmlPullParser.TEXT) { 514 continue; 515 } 516 String tag = parser.getName(); 517 switch (tag) { 518 case TAG_PROVISIONING_PARAMS: 519 return createBuilderFromPersistableBundle( 520 PersistableBundle.restoreFromXml(parser)).build(); 521 } 522 } 523 return new Builder().build(); 524 } 525 526 public final static class Builder { 527 private long mProvisioningId; 528 private String mTimeZone; 529 private long mLocalTime = DEFAULT_LOCAL_TIME; 530 private Locale mLocale; 531 private WifiInfo mWifiInfo; 532 private String mDeviceAdminPackageName; 533 private ComponentName mDeviceAdminComponentName; 534 private String mDeviceAdminLabel; 535 private String mOrganizationName; 536 private String mSupportUrl; 537 private String mDeviceAdminIconFilePath; 538 private Account mAccountToMigrate; 539 private String mProvisioningAction; 540 private Integer mMainColor = DEFAULT_MAIN_COLOR; 541 private PackageDownloadInfo mDeviceAdminDownloadInfo; 542 private DisclaimersParam mDisclaimersParam; 543 private PersistableBundle mAdminExtrasBundle; 544 private boolean mStartedByTrustedSource = DEFAULT_STARTED_BY_TRUSTED_SOURCE; 545 private boolean mIsNfc = DEFAULT_IS_NFC; 546 private boolean mIsQrProvisioning = DEFAULT_IS_QR_PROVISIONING; 547 private boolean mLeaveAllSystemAppsEnabled = DEFAULT_LEAVE_ALL_SYSTEM_APPS_ENABLED; 548 private boolean mSkipEncryption = DEFAULT_EXTRA_PROVISIONING_SKIP_ENCRYPTION; 549 private boolean mSkipUserConsent = DEFAULT_EXTRA_PROVISIONING_SKIP_USER_CONSENT; 550 private boolean mSkipEducationScreens = DEFAULT_EXTRA_PROVISIONING_SKIP_EDUCATION_SCREENS; 551 private boolean mSkipUserSetup = DEFAULT_SKIP_USER_SETUP; 552 private boolean mKeepAccountMigrated = DEFAULT_EXTRA_PROVISIONING_KEEP_ACCOUNT_MIGRATED; 553 private boolean mUseMobileData = DEFAULT_EXTRA_PROVISIONING_USE_MOBILE_DATA; 554 private boolean mIsOrganizationOwnedProvisioning = false; 555 private boolean mIsTransitioningFromRegularToChild = false; 556 private @ProvisioningMode int mProvisioningMode = PROVISIONING_MODE_UNDECIDED; 557 setProvisioningId(long provisioningId)558 public Builder setProvisioningId(long provisioningId) { 559 mProvisioningId = provisioningId; 560 return this; 561 } 562 setTimeZone(String timeZone)563 public Builder setTimeZone(String timeZone) { 564 mTimeZone = timeZone; 565 return this; 566 } 567 setLocalTime(long localTime)568 public Builder setLocalTime(long localTime) { 569 mLocalTime = localTime; 570 return this; 571 } 572 setLocale(Locale locale)573 public Builder setLocale(Locale locale) { 574 mLocale = locale; 575 return this; 576 } 577 setWifiInfo(WifiInfo wifiInfo)578 public Builder setWifiInfo(WifiInfo wifiInfo) { 579 mWifiInfo = wifiInfo; 580 return this; 581 } 582 583 @Deprecated setDeviceAdminPackageName(String deviceAdminPackageName)584 public Builder setDeviceAdminPackageName(String deviceAdminPackageName) { 585 mDeviceAdminPackageName = deviceAdminPackageName; 586 return this; 587 } 588 setDeviceAdminComponentName(ComponentName deviceAdminComponentName)589 public Builder setDeviceAdminComponentName(ComponentName deviceAdminComponentName) { 590 mDeviceAdminComponentName = deviceAdminComponentName; 591 return this; 592 } 593 setDeviceAdminLabel(String deviceAdminLabel)594 public Builder setDeviceAdminLabel(String deviceAdminLabel) { 595 mDeviceAdminLabel = deviceAdminLabel; 596 return this; 597 } 598 setOrganizationName(String organizationName)599 public Builder setOrganizationName(String organizationName) { 600 mOrganizationName = organizationName; 601 return this; 602 } 603 setSupportUrl(String supportUrl)604 public Builder setSupportUrl(String supportUrl) { 605 mSupportUrl = supportUrl; 606 return this; 607 } 608 setDeviceAdminIconFilePath(String deviceAdminIconFilePath)609 public Builder setDeviceAdminIconFilePath(String deviceAdminIconFilePath) { 610 mDeviceAdminIconFilePath = deviceAdminIconFilePath; 611 return this; 612 } 613 setAccountToMigrate(Account accountToMigrate)614 public Builder setAccountToMigrate(Account accountToMigrate) { 615 mAccountToMigrate = accountToMigrate; 616 return this; 617 } 618 setProvisioningAction(String provisioningAction)619 public Builder setProvisioningAction(String provisioningAction) { 620 mProvisioningAction = provisioningAction; 621 return this; 622 } 623 setMainColor(Integer mainColor)624 public Builder setMainColor(Integer mainColor) { 625 mMainColor = mainColor; 626 return this; 627 } 628 setDeviceAdminDownloadInfo(PackageDownloadInfo deviceAdminDownloadInfo)629 public Builder setDeviceAdminDownloadInfo(PackageDownloadInfo deviceAdminDownloadInfo) { 630 mDeviceAdminDownloadInfo = deviceAdminDownloadInfo; 631 return this; 632 } 633 setDisclaimersParam(DisclaimersParam disclaimersParam)634 public Builder setDisclaimersParam(DisclaimersParam disclaimersParam) { 635 mDisclaimersParam = disclaimersParam; 636 return this; 637 } 638 setAdminExtrasBundle(PersistableBundle adminExtrasBundle)639 public Builder setAdminExtrasBundle(PersistableBundle adminExtrasBundle) { 640 mAdminExtrasBundle = adminExtrasBundle; 641 return this; 642 } 643 setStartedByTrustedSource(boolean startedByTrustedSource)644 public Builder setStartedByTrustedSource(boolean startedByTrustedSource) { 645 mStartedByTrustedSource = startedByTrustedSource; 646 return this; 647 } 648 setIsNfc(boolean isNfc)649 public Builder setIsNfc(boolean isNfc) { 650 mIsNfc = isNfc; 651 return this; 652 } 653 setIsQrProvisioning(boolean qrProvisioning)654 public Builder setIsQrProvisioning(boolean qrProvisioning) { 655 mIsQrProvisioning = qrProvisioning; 656 return this; 657 } 658 setLeaveAllSystemAppsEnabled(boolean leaveAllSystemAppsEnabled)659 public Builder setLeaveAllSystemAppsEnabled(boolean leaveAllSystemAppsEnabled) { 660 mLeaveAllSystemAppsEnabled = leaveAllSystemAppsEnabled; 661 return this; 662 } 663 setSkipEncryption(boolean skipEncryption)664 public Builder setSkipEncryption(boolean skipEncryption) { 665 mSkipEncryption = skipEncryption; 666 return this; 667 } 668 setSkipUserConsent(boolean skipUserConsent)669 public Builder setSkipUserConsent(boolean skipUserConsent) { 670 mSkipUserConsent = skipUserConsent; 671 return this; 672 } 673 setSkipEducationScreens(boolean skipEducationScreens)674 public Builder setSkipEducationScreens(boolean skipEducationScreens) { 675 mSkipEducationScreens = skipEducationScreens; 676 return this; 677 } 678 setSkipUserSetup(boolean skipUserSetup)679 public Builder setSkipUserSetup(boolean skipUserSetup) { 680 mSkipUserSetup = skipUserSetup; 681 return this; 682 } 683 setKeepAccountMigrated(boolean keepAccountMigrated)684 public Builder setKeepAccountMigrated(boolean keepAccountMigrated) { 685 mKeepAccountMigrated = keepAccountMigrated; 686 return this; 687 } 688 setUseMobileData(boolean useMobileData)689 public Builder setUseMobileData(boolean useMobileData) { 690 mUseMobileData = useMobileData; 691 return this; 692 } 693 setIsOrganizationOwnedProvisioning(boolean isOrganizationOwnedProvisioning)694 public Builder setIsOrganizationOwnedProvisioning(boolean isOrganizationOwnedProvisioning) { 695 mIsOrganizationOwnedProvisioning = isOrganizationOwnedProvisioning; 696 return this; 697 } 698 setIsTransitioningFromRegularToChild( boolean isTransitioningFromRegularToChild)699 public Builder setIsTransitioningFromRegularToChild( 700 boolean isTransitioningFromRegularToChild) { 701 mIsTransitioningFromRegularToChild = isTransitioningFromRegularToChild; 702 return this; 703 } 704 setProvisioningMode(@rovisioningMode int provisioningMode)705 public Builder setProvisioningMode(@ProvisioningMode int provisioningMode) { 706 mProvisioningMode = provisioningMode; 707 return this; 708 } 709 710 /** 711 * Builds the {@link ProvisioningParams} object. Note that {@link 712 * #setProvisioningAction(String)} and {@link #setDeviceAdminComponentName(ComponentName)} 713 * methods must be called with a non-null parameter before this is called. 714 */ build()715 public ProvisioningParams build() { 716 return new ProvisioningParams(this); 717 } 718 builder()719 public static Builder builder() { 720 return new Builder(); 721 } 722 } 723 } 724