Merge "Deprecate the old rebootAndApply API"
diff --git a/core/api/system-current.txt b/core/api/system-current.txt
index cbd65d1..ad43ad6 100644
--- a/core/api/system-current.txt
+++ b/core/api/system-current.txt
@@ -7354,7 +7354,7 @@
     method @RequiresPermission(anyOf={android.Manifest.permission.RECOVERY, android.Manifest.permission.REBOOT}) public static void prepareForUnattendedUpdate(@NonNull android.content.Context, @NonNull String, @Nullable android.content.IntentSender) throws java.io.IOException;
     method @RequiresPermission(android.Manifest.permission.RECOVERY) public static void processPackage(android.content.Context, java.io.File, android.os.RecoverySystem.ProgressListener, android.os.Handler) throws java.io.IOException;
     method @RequiresPermission(android.Manifest.permission.RECOVERY) public static void processPackage(android.content.Context, java.io.File, android.os.RecoverySystem.ProgressListener) throws java.io.IOException;
-    method @RequiresPermission(anyOf={android.Manifest.permission.RECOVERY, android.Manifest.permission.REBOOT}) public static void rebootAndApply(@NonNull android.content.Context, @NonNull String, @NonNull String) throws java.io.IOException;
+    method @Deprecated @RequiresPermission(android.Manifest.permission.RECOVERY) public static void rebootAndApply(@NonNull android.content.Context, @NonNull String, @NonNull String) throws java.io.IOException;
     method @RequiresPermission(anyOf={android.Manifest.permission.RECOVERY, android.Manifest.permission.REBOOT}) public static void rebootAndApply(@NonNull android.content.Context, @NonNull String, boolean) throws java.io.IOException;
     method @RequiresPermission(allOf={android.Manifest.permission.RECOVERY, android.Manifest.permission.REBOOT}) public static void rebootWipeAb(android.content.Context, java.io.File, String) throws java.io.IOException;
     method @RequiresPermission(android.Manifest.permission.RECOVERY) public static void scheduleUpdateOnBoot(android.content.Context, java.io.File) throws java.io.IOException;
diff --git a/core/java/android/os/IRecoverySystem.aidl b/core/java/android/os/IRecoverySystem.aidl
index 5f8b932..2052883 100644
--- a/core/java/android/os/IRecoverySystem.aidl
+++ b/core/java/android/os/IRecoverySystem.aidl
@@ -30,5 +30,6 @@
     boolean requestLskf(in String packageName, in IntentSender sender);
     boolean clearLskf(in String packageName);
     boolean isLskfCaptured(in String packageName);
+    boolean rebootWithLskfAssumeSlotSwitch(in String packageName, in String reason);
     boolean rebootWithLskf(in String packageName, in String reason, in boolean slotSwitch);
 }
diff --git a/core/java/android/os/RecoverySystem.java b/core/java/android/os/RecoverySystem.java
index 189e62b..6713de8 100644
--- a/core/java/android/os/RecoverySystem.java
+++ b/core/java/android/os/RecoverySystem.java
@@ -687,8 +687,8 @@
     }
 
     /**
-     * Request that the device reboot and apply the update that has been prepared. Callers are
-     * recommended to use {@link #rebootAndApply(Context, String, boolean)} instead.
+     * Request that the device reboot and apply the update that has been prepared. This API is
+     * deprecated, and is expected to be used by OTA only on devices running Android 11.
      *
      * @param context the Context to use.
      * @param updateToken this parameter is deprecated and won't be used. See details in
@@ -699,18 +699,18 @@
      *               unattended reboot or if the {@code updateToken} did not match the previously
      *               given token
      * @hide
+     * @deprecated Use {@link #rebootAndApply(Context, String, boolean)} instead
      */
     @SystemApi
-    @RequiresPermission(anyOf = {android.Manifest.permission.RECOVERY,
-            android.Manifest.permission.REBOOT})
+    @RequiresPermission(android.Manifest.permission.RECOVERY)
     public static void rebootAndApply(@NonNull Context context, @NonNull String updateToken,
             @NonNull String reason) throws IOException {
         if (updateToken == null) {
             throw new NullPointerException("updateToken == null");
         }
         RecoverySystem rs = (RecoverySystem) context.getSystemService(Context.RECOVERY_SERVICE);
-        // OTA is the sole user before S, and a slot switch is required for ota update.
-        if (!rs.rebootWithLskf(context.getPackageName(), reason, true)) {
+        // OTA is the sole user, who expects a slot switch.
+        if (!rs.rebootWithLskfAssumeSlotSwitch(context.getPackageName(), reason)) {
             throw new IOException("system not prepared to apply update");
         }
     }
@@ -738,7 +738,7 @@
      *
      * @param context the Context to use.
      * @param reason the reboot reason to give to the {@link PowerManager}
-     * @param slotSwitch true if the caller intends to switch the slot on an A/B device.
+     * @param slotSwitch true if the caller expects the slot to be switched on A/B devices.
      * @throws IOException if the reboot couldn't proceed because the device wasn't ready for an
      *               unattended reboot.
      * @hide
@@ -1387,6 +1387,21 @@
         }
     }
 
+
+    /**
+     * Calls the recovery system service to reboot and apply update. This is the legacy API and
+     * expects a slot switch for A/B devices.
+     *
+     */
+    private boolean rebootWithLskfAssumeSlotSwitch(String packageName, String reason)
+            throws IOException {
+        try {
+            return mService.rebootWithLskfAssumeSlotSwitch(packageName, reason);
+        } catch (RemoteException e) {
+            throw new IOException("could not reboot for update");
+        }
+    }
+
     /**
      * Internally, recovery treats each line of the command file as a separate
      * argv, so we only need to protect against newlines and nulls.
diff --git a/services/core/java/com/android/server/recoverysystem/RecoverySystemService.java b/services/core/java/com/android/server/recoverysystem/RecoverySystemService.java
index 91f613f..5c01e43 100644
--- a/services/core/java/com/android/server/recoverysystem/RecoverySystemService.java
+++ b/services/core/java/com/android/server/recoverysystem/RecoverySystemService.java
@@ -476,9 +476,7 @@
         return needClear ? ROR_REQUESTED_NEED_CLEAR : ROR_REQUESTED_SKIP_CLEAR;
     }
 
-    @Override // Binder call
-    public boolean rebootWithLskf(String packageName, String reason, boolean slotSwitch) {
-        enforcePermissionForResumeOnReboot();
+    private boolean rebootWithLskfImpl(String packageName, String reason, boolean slotSwitch) {
         if (packageName == null) {
             Slog.w(TAG, "Missing packageName when rebooting with lskf.");
             return false;
@@ -499,6 +497,18 @@
         return true;
     }
 
+    @Override // Binder call for the legacy rebootWithLskf
+    public boolean rebootWithLskfAssumeSlotSwitch(String packageName, String reason) {
+        mContext.enforceCallingOrSelfPermission(android.Manifest.permission.RECOVERY, null);
+        return rebootWithLskfImpl(packageName, reason, true);
+    }
+
+    @Override // Binder call
+    public boolean rebootWithLskf(String packageName, String reason, boolean slotSwitch) {
+        enforcePermissionForResumeOnReboot();
+        return rebootWithLskfImpl(packageName, reason, slotSwitch);
+    }
+
     @Override // Binder call
     public boolean isLskfCaptured(String packageName) {
         enforcePermissionForResumeOnReboot();