1 /* 2 * Copyright (C) 2018 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 android.os; 18 19 import static com.android.internal.util.Preconditions.checkNotNull; 20 21 import android.annotation.RequiresPermission; 22 import android.annotation.SystemApi; 23 import android.annotation.SystemService; 24 import android.content.Context; 25 26 /** 27 * Allows querying and posting system update information. 28 * 29 * {@hide} 30 */ 31 @SystemApi 32 @SystemService(Context.SYSTEM_UPDATE_SERVICE) 33 public class SystemUpdateManager { 34 private static final String TAG = "SystemUpdateManager"; 35 36 /** The status key of the system update info, expecting an int value. */ 37 public static final String KEY_STATUS = "status"; 38 39 /** The title of the current update, expecting a String value. */ 40 public static final String KEY_TITLE = "title"; 41 42 /** Whether it is a security update, expecting a boolean value. */ 43 public static final String KEY_IS_SECURITY_UPDATE = "is_security_update"; 44 45 /** The build fingerprint after installing the current update, expecting a String value. */ 46 public static final String KEY_TARGET_BUILD_FINGERPRINT = "target_build_fingerprint"; 47 48 /** The security patch level after installing the current update, expecting a String value. */ 49 public static final String KEY_TARGET_SECURITY_PATCH_LEVEL = "target_security_patch_level"; 50 51 /** 52 * The KEY_STATUS value that indicates there's no update status info available. 53 */ 54 public static final int STATUS_UNKNOWN = 0; 55 56 /** 57 * The KEY_STATUS value that indicates there's no pending update. 58 */ 59 public static final int STATUS_IDLE = 1; 60 61 /** 62 * The KEY_STATUS value that indicates an update is available for download, but pending user 63 * approval to start. 64 */ 65 public static final int STATUS_WAITING_DOWNLOAD = 2; 66 67 /** 68 * The KEY_STATUS value that indicates an update is in progress (i.e. downloading or installing 69 * has started). 70 */ 71 public static final int STATUS_IN_PROGRESS = 3; 72 73 /** 74 * The KEY_STATUS value that indicates an update is available for install. 75 */ 76 public static final int STATUS_WAITING_INSTALL = 4; 77 78 /** 79 * The KEY_STATUS value that indicates an update will be installed after a reboot. This applies 80 * to both of A/B and non-A/B OTAs. 81 */ 82 public static final int STATUS_WAITING_REBOOT = 5; 83 84 private final ISystemUpdateManager mService; 85 86 /** @hide */ SystemUpdateManager(ISystemUpdateManager service)87 public SystemUpdateManager(ISystemUpdateManager service) { 88 mService = checkNotNull(service, "missing ISystemUpdateManager"); 89 } 90 91 /** 92 * Queries the current pending system update info. 93 * 94 * <p>Requires the {@link android.Manifest.permission#READ_SYSTEM_UPDATE_INFO} or 95 * {@link android.Manifest.permission#RECOVERY} permission. 96 * 97 * @return A {@code Bundle} that contains the pending system update information in key-value 98 * pairs. 99 * 100 * @throws SecurityException if the caller is not allowed to read the info. 101 */ 102 @RequiresPermission(anyOf = { 103 android.Manifest.permission.READ_SYSTEM_UPDATE_INFO, 104 android.Manifest.permission.RECOVERY, 105 }) retrieveSystemUpdateInfo()106 public Bundle retrieveSystemUpdateInfo() { 107 try { 108 return mService.retrieveSystemUpdateInfo(); 109 } catch (RemoteException re) { 110 throw re.rethrowFromSystemServer(); 111 } 112 } 113 114 /** 115 * Allows a system updater to publish the pending update info. 116 * 117 * <p>The reported info will not persist across reboots. Because only the reporting updater 118 * understands the criteria to determine a successful/failed update. 119 * 120 * <p>Requires the {@link android.Manifest.permission#RECOVERY} permission. 121 * 122 * @param infoBundle The {@code PersistableBundle} that contains the system update information, 123 * such as the current update status. {@link #KEY_STATUS} is required in the bundle. 124 * 125 * @throws IllegalArgumentException if @link #KEY_STATUS} does not exist. 126 * @throws SecurityException if the caller is not allowed to update the info. 127 */ 128 @RequiresPermission(android.Manifest.permission.RECOVERY) updateSystemUpdateInfo(PersistableBundle infoBundle)129 public void updateSystemUpdateInfo(PersistableBundle infoBundle) { 130 if (infoBundle == null || !infoBundle.containsKey(KEY_STATUS)) { 131 throw new IllegalArgumentException("Missing status in the bundle"); 132 } 133 try { 134 mService.updateSystemUpdateInfo(infoBundle); 135 } catch (RemoteException re) { 136 throw re.rethrowFromSystemServer(); 137 } 138 } 139 } 140