Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 6e6af0d3 authored by Christopher Tate's avatar Christopher Tate Committed by Android (Google) Code Review
Browse files

Merge "Add payload-size preflight stage to full transport backup"

parents 7760820e 11ae768c
Loading
Loading
Loading
Loading
+1 −0
Original line number Diff line number Diff line
@@ -5910,6 +5910,7 @@ package android.app.backup {
    ctor public BackupTransport();
    method public int abortFullRestore();
    method public void cancelFullBackup();
    method public int checkFullBackupSize(long);
    method public int clearBackupData(android.content.pm.PackageInfo);
    method public android.content.Intent configurationIntent();
    method public java.lang.String currentDestinationString();
+5 −0
Original line number Diff line number Diff line
@@ -99,6 +99,11 @@ oneway interface IBackupAgent {
     */
    void doFullBackup(in ParcelFileDescriptor data, int token, IBackupManager callbackBinder);

    /**
     * Estimate how much data a full backup will deliver
     */
    void doMeasureFullBackup(int token, IBackupManager callbackBinder);

    /**
     * Restore a single "file" to the application.  The file was typically obtained from
     * a full-backup dataset.  The agent reads 'size' bytes of file content
+42 −13
Original line number Diff line number Diff line
@@ -424,10 +424,12 @@ public abstract class BackupAgent extends ContextWrapper {
        }

        // And now that we know where it lives, semantically, back it up appropriately
        Log.i(TAG, "backupFile() of " + filePath + " => domain=" + domain
        // In the measurement case, backupToTar() updates the size in output and returns
        // without transmitting any file data.
        if (DEBUG) Log.i(TAG, "backupFile() of " + filePath + " => domain=" + domain
                + " rootpath=" + rootpath);
        FullBackup.backupToTar(getPackageName(), domain, null, rootpath, filePath,
                output.getData());
        
        FullBackup.backupToTar(getPackageName(), domain, null, rootpath, filePath, output);
    }

    /**
@@ -477,9 +479,8 @@ public abstract class BackupAgent extends ContextWrapper {
                    continue;
                }

                // Finally, back this file up before proceeding
                FullBackup.backupToTar(packageName, domain, null, rootPath, filePath,
                        output.getData());
                // Finally, back this file up (or measure it) before proceeding
                FullBackup.backupToTar(packageName, domain, null, rootPath, filePath, output);
            }
        }
    }
@@ -640,7 +641,7 @@ public abstract class BackupAgent extends ContextWrapper {

                Binder.restoreCallingIdentity(ident);
                try {
                    callbackBinder.opComplete(token);
                    callbackBinder.opComplete(token, 0);
                } catch (RemoteException e) {
                    // we'll time out anyway, so we're safe
                }
@@ -670,7 +671,7 @@ public abstract class BackupAgent extends ContextWrapper {

                Binder.restoreCallingIdentity(ident);
                try {
                    callbackBinder.opComplete(token);
                    callbackBinder.opComplete(token, 0);
                } catch (RemoteException e) {
                    // we'll time out anyway, so we're safe
                }
@@ -692,10 +693,10 @@ public abstract class BackupAgent extends ContextWrapper {
            try {
                BackupAgent.this.onFullBackup(new FullBackupDataOutput(data));
            } catch (IOException ex) {
                Log.d(TAG, "onBackup (" + BackupAgent.this.getClass().getName() + ") threw", ex);
                Log.d(TAG, "onFullBackup (" + BackupAgent.this.getClass().getName() + ") threw", ex);
                throw new RuntimeException(ex);
            } catch (RuntimeException ex) {
                Log.d(TAG, "onBackup (" + BackupAgent.this.getClass().getName() + ") threw", ex);
                Log.d(TAG, "onFullBackup (" + BackupAgent.this.getClass().getName() + ") threw", ex);
                throw ex;
            } finally {
                // ... and then again after, as in the doBackup() case
@@ -713,13 +714,37 @@ public abstract class BackupAgent extends ContextWrapper {

                Binder.restoreCallingIdentity(ident);
                try {
                    callbackBinder.opComplete(token);
                    callbackBinder.opComplete(token, 0);
                } catch (RemoteException e) {
                    // we'll time out anyway, so we're safe
                }
            }
        }

        public void doMeasureFullBackup(int token, IBackupManager callbackBinder) {
            // Ensure that we're running with the app's normal permission level
            final long ident = Binder.clearCallingIdentity();
            FullBackupDataOutput measureOutput = new FullBackupDataOutput();

            waitForSharedPrefs();
            try {
                BackupAgent.this.onFullBackup(measureOutput);
            } catch (IOException ex) {
                Log.d(TAG, "onFullBackup[M] (" + BackupAgent.this.getClass().getName() + ") threw", ex);
                throw new RuntimeException(ex);
            } catch (RuntimeException ex) {
                Log.d(TAG, "onFullBackup[M] (" + BackupAgent.this.getClass().getName() + ") threw", ex);
                throw ex;
            } finally {
                Binder.restoreCallingIdentity(ident);
                try {
                    callbackBinder.opComplete(token, measureOutput.getSize());
                } catch (RemoteException e) {
                    // timeout, so we're safe
                }
            }
        }

        @Override
        public void doRestoreFile(ParcelFileDescriptor data, long size,
                int type, String domain, String path, long mode, long mtime,
@@ -728,6 +753,7 @@ public abstract class BackupAgent extends ContextWrapper {
            try {
                BackupAgent.this.onRestoreFile(data, size, type, domain, path, mode, mtime);
            } catch (IOException e) {
                Log.d(TAG, "onRestoreFile (" + BackupAgent.this.getClass().getName() + ") threw", e);
                throw new RuntimeException(e);
            } finally {
                // Ensure that any side-effect SharedPreferences writes have landed
@@ -735,7 +761,7 @@ public abstract class BackupAgent extends ContextWrapper {

                Binder.restoreCallingIdentity(ident);
                try {
                    callbackBinder.opComplete(token);
                    callbackBinder.opComplete(token, 0);
                } catch (RemoteException e) {
                    // we'll time out anyway, so we're safe
                }
@@ -747,13 +773,16 @@ public abstract class BackupAgent extends ContextWrapper {
            long ident = Binder.clearCallingIdentity();
            try {
                BackupAgent.this.onRestoreFinished();
            } catch (Exception e) {
                Log.d(TAG, "onRestoreFinished (" + BackupAgent.this.getClass().getName() + ") threw", e);
                throw e;
            } finally {
                // Ensure that any side-effect SharedPreferences writes have landed
                waitForSharedPrefs();

                Binder.restoreCallingIdentity(ident);
                try {
                    callbackBinder.opComplete(token);
                    callbackBinder.opComplete(token, 0);
                } catch (RemoteException e) {
                    // we'll time out anyway, so we're safe
                }
+25 −0
Original line number Diff line number Diff line
@@ -392,6 +392,26 @@ public class BackupTransport {
        return BackupTransport.TRANSPORT_PACKAGE_REJECTED;
    }

    /**
     * Called after {@link #performFullBackup} to make sure that the transport is willing to
     * handle a full-data backup operation of the specified size on the current package.
     * If the transport returns anything other than TRANSPORT_OK, the package's backup
     * operation will be skipped (and {@link #finishBackup() invoked} with no data for that
     * package being passed to {@link #sendBackupData}.
     *
     * Added in MNC (API 23).
     *
     * @param size The estimated size of the full-data payload for this app.  This includes
     *         manifest and archive format overhead, but is not guaranteed to be precise.
     * @return TRANSPORT_OK if the platform is to proceed with the full-data backup,
     *         TRANSPORT_PACKAGE_REJECTED if the proposed payload size is too large for
     *         the transport to handle, or TRANSPORT_ERROR to indicate a fatal error
     *         condition that means the platform cannot perform a backup at this time.
     */
    public int checkFullBackupSize(long size) {
        return BackupTransport.TRANSPORT_OK;
    }

    /**
     * Tells the transport to read {@code numBytes} bytes of data from the socket file
     * descriptor provided in the {@link #performFullBackup(PackageInfo, ParcelFileDescriptor)}
@@ -587,6 +607,11 @@ public class BackupTransport {
            return BackupTransport.this.performFullBackup(targetPackage, socket);
        }

        @Override
        public int checkFullBackupSize(long size) {
            return BackupTransport.this.checkFullBackupSize(size);
        }

        @Override
        public int sendBackupData(int numBytes) throws RemoteException {
            return BackupTransport.this.sendBackupData(numBytes);
+1 −1
Original line number Diff line number Diff line
@@ -58,7 +58,7 @@ public class FullBackup {
     * @hide
     */
    static public native int backupToTar(String packageName, String domain,
            String linkdomain, String rootpath, String path, BackupDataOutput output);
            String linkdomain, String rootpath, String path, FullBackupDataOutput output);

    /**
     * Copy data from a socket to the given File location on permanent storage.  The
Loading