BackupRestoreConfirmation.java revision 4a627c71ff53a4fca1f961f4b1dcc0461df18a06
14a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate/*
24a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate * Copyright (C) 2011 The Android Open Source Project
34a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate *
44a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate * Licensed under the Apache License, Version 2.0 (the "License");
54a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate * you may not use this file except in compliance with the License.
64a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate * You may obtain a copy of the License at
74a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate *
84a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate *      http://www.apache.org/licenses/LICENSE-2.0
94a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate *
104a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate * Unless required by applicable law or agreed to in writing, software
114a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate * distributed under the License is distributed on an "AS IS" BASIS,
124a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
134a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate * See the License for the specific language governing permissions and
144a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate * limitations under the License.
154a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate */
164a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate
174a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tatepackage com.android.backupconfirm;
184a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate
194a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tateimport android.app.Activity;
204a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tateimport android.app.backup.FullBackup;
214a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tateimport android.app.backup.IBackupManager;
224a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tateimport android.app.backup.IFullBackupRestoreObserver;
234a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tateimport android.content.Context;
244a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tateimport android.content.Intent;
254a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tateimport android.os.Bundle;
264a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tateimport android.os.Handler;
274a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tateimport android.os.Looper;
284a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tateimport android.os.Message;
294a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tateimport android.os.RemoteException;
304a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tateimport android.os.ServiceManager;
314a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tateimport android.util.Slog;
324a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tateimport android.view.View;
334a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tateimport android.widget.Button;
344a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tateimport android.widget.TextView;
354a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tateimport android.widget.Toast;
364a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate
374a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate/**
384a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate * Confirm with the user that a requested full backup/restore operation is legitimate.
394a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate * Any attempt to perform a full backup/restore will launch this UI and wait for a
404a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate * designated timeout interval (nominally 30 seconds) for the user to confirm.  If the
414a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate * user fails to respond within the timeout period, or explicitly refuses the operation
424a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate * within the UI presented here, no data will be transferred off the device.
434a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate *
444a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate * Note that the fully scoped name of this class is baked into the backup manager service.
454a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate *
464a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate * @hide
474a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate */
484a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tatepublic class BackupRestoreConfirmation extends Activity {
494a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate    static final String TAG = "BackupRestoreConfirmation";
504a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate    static final boolean DEBUG = true;
514a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate
524a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate    static final int MSG_START_BACKUP = 1;
534a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate    static final int MSG_BACKUP_PACKAGE = 2;
544a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate    static final int MSG_END_BACKUP = 3;
554a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate    static final int MSG_START_RESTORE = 11;
564a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate    static final int MSG_RESTORE_PACKAGE = 12;
574a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate    static final int MSG_END_RESTORE = 13;
584a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate    static final int MSG_TIMEOUT = 100;
594a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate
604a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate    Handler mHandler;
614a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate    IBackupManager mBackupManager;
624a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate    FullObserver mObserver;
634a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate    int mToken;
644a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate
654a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate    TextView mStatusView;
664a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate    Button mAllowButton;
674a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate    Button mDenyButton;
684a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate
694a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate    // Handler for dealing with observer callbacks on the main thread
704a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate    class ObserverHandler extends Handler {
714a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate        Context mContext;
724a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate        ObserverHandler(Context context) {
734a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate            mContext = context;
744a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate        }
754a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate
764a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate        @Override
774a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate        public void handleMessage(Message msg) {
784a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate            switch (msg.what) {
794a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate                case MSG_START_BACKUP: {
804a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate                    Toast.makeText(mContext, "!!! Backup starting !!!", Toast.LENGTH_LONG);
814a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate                }
824a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate                break;
834a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate
844a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate                case MSG_BACKUP_PACKAGE: {
854a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate                    String name = (String) msg.obj;
864a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate                    mStatusView.setText(name);
874a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate                }
884a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate                break;
894a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate
904a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate                case MSG_END_BACKUP: {
914a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate                    Toast.makeText(mContext, "!!! Backup ended !!!", Toast.LENGTH_SHORT);
924a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate                }
934a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate                break;
944a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate
954a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate                case MSG_START_RESTORE: {
964a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate                    Toast.makeText(mContext, "!!! Restore starting !!!", Toast.LENGTH_LONG);
974a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate                }
984a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate                break;
994a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate
1004a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate                case MSG_RESTORE_PACKAGE: {
1014a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate                }
1024a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate                break;
1034a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate
1044a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate                case MSG_END_RESTORE: {
1054a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate                    Toast.makeText(mContext, "!!! Restore ended !!!", Toast.LENGTH_SHORT);
1064a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate                }
1074a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate                break;
1084a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate
1094a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate                case MSG_TIMEOUT: {
1104a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate                }
1114a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate                break;
1124a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate            }
1134a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate        }
1144a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate    }
1154a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate
1164a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate    @Override
1174a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate    public void onCreate(Bundle icicle) {
1184a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate        super.onCreate(icicle);
1194a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate
1204a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate        final Intent intent = getIntent();
1214a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate        final String action = intent.getAction();
1224a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate
1234a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate        int layoutId;
1244a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate        if (action.equals(FullBackup.FULL_BACKUP_INTENT_ACTION)) {
1254a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate            layoutId = R.layout.confirm_backup;
1264a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate        } else if (action.equals(FullBackup.FULL_RESTORE_INTENT_ACTION)) {
1274a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate            layoutId = R.layout.confirm_restore;
1284a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate        } else {
1294a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate            Slog.w(TAG, "Backup/restore confirmation activity launched with invalid action!");
1304a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate            finish();
1314a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate            return;
1324a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate        }
1334a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate
1344a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate        mToken = intent.getIntExtra(FullBackup.CONF_TOKEN_INTENT_EXTRA, -1);
1354a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate        if (mToken < 0) {
1364a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate            Slog.e(TAG, "Backup/restore confirmation requested but no token passed!");
1374a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate            finish();
1384a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate            return;
1394a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate        }
1404a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate
1414a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate        mBackupManager = IBackupManager.Stub.asInterface(ServiceManager.getService(Context.BACKUP_SERVICE));
1424a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate
1434a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate        mHandler = new ObserverHandler(getApplicationContext());
1444a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate        mObserver = new FullObserver();
1454a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate
1464a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate        setContentView(layoutId);
1474a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate
1484a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate        // Same resource IDs for each layout variant (backup / restore)
1494a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate        mStatusView = (TextView) findViewById(R.id.package_name);
1504a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate        mAllowButton = (Button) findViewById(R.id.button_allow);
1514a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate        mDenyButton = (Button) findViewById(R.id.button_deny);
1524a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate
1534a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate        mAllowButton.setOnClickListener(new View.OnClickListener() {
1544a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate            @Override
1554a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate            public void onClick(View v) {
1564a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate                try {
1574a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate                    mBackupManager.acknowledgeFullBackupOrRestore(mToken, true, mObserver);
1584a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate                } catch (RemoteException e) {
1594a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate                    // TODO: bail gracefully if we can't contact the backup manager
1604a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate                }
1614a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate                mAllowButton.setEnabled(false);
1624a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate                mDenyButton.setEnabled(false);
1634a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate            }
1644a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate        });
1654a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate
1664a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate        mDenyButton.setOnClickListener(new View.OnClickListener() {
1674a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate            @Override
1684a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate            public void onClick(View v) {
1694a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate                try {
1704a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate                    mBackupManager.acknowledgeFullBackupOrRestore(mToken, false, mObserver);
1714a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate                } catch (RemoteException e) {
1724a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate                    // TODO: bail gracefully if we can't contact the backup manager
1734a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate                }
1744a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate                mAllowButton.setEnabled(false);
1754a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate                mDenyButton.setEnabled(false);
1764a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate            }
1774a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate        });
1784a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate    }
1794a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate
1804a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate    @Override
1814a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate    public void onStop() {
1824a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate        super.onStop();
1834a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate
1844a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate        // We explicitly equate departure from the UI with refusal.  This includes the
1854a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate        // implicit configuration-changed stop/restart cycle.
1864a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate        try {
1874a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate            mBackupManager.acknowledgeFullBackupOrRestore(mToken, false, null);
1884a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate        } catch (RemoteException e) {
1894a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate            // if this fails we'll still time out with no acknowledgment
1904a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate        }
1914a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate        finish();
1924a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate    }
1934a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate
1944a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate    /**
1954a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate     * The observer binder for showing backup/restore progress.  This binder just bounces
1964a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate     * the notifications onto the main thread.
1974a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate     */
1984a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate    class FullObserver extends IFullBackupRestoreObserver.Stub {
1994a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate        //
2004a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate        // IFullBackupRestoreObserver implementation
2014a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate        //
2024a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate        @Override
2034a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate        public void onStartBackup() throws RemoteException {
2044a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate            mHandler.sendEmptyMessage(MSG_START_BACKUP);
2054a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate        }
2064a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate
2074a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate        @Override
2084a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate        public void onBackupPackage(String name) throws RemoteException {
2094a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate            mHandler.sendMessage(mHandler.obtainMessage(MSG_BACKUP_PACKAGE, name));
2104a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate        }
2114a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate
2124a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate        @Override
2134a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate        public void onEndBackup() throws RemoteException {
2144a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate            mHandler.sendEmptyMessage(MSG_END_BACKUP);
2154a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate        }
2164a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate
2174a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate        @Override
2184a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate        public void onStartRestore() throws RemoteException {
2194a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate            mHandler.sendEmptyMessage(MSG_START_RESTORE);
2204a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate        }
2214a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate
2224a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate        @Override
2234a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate        public void onRestorePackage(String name) throws RemoteException {
2244a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate            mHandler.sendMessage(mHandler.obtainMessage(MSG_RESTORE_PACKAGE, name));
2254a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate        }
2264a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate
2274a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate        @Override
2284a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate        public void onEndRestore() throws RemoteException {
2294a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate            mHandler.sendEmptyMessage(MSG_END_RESTORE);
2304a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate        }
2314a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate
2324a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate        @Override
2334a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate        public void onTimeout() throws RemoteException {
2344a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate            mHandler.sendEmptyMessage(MSG_TIMEOUT);
2354a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate        }
2364a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate    }
2374a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate}
238