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.commands.bu; 184a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate 194a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tateimport android.app.backup.IBackupManager; 204a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tateimport android.os.ParcelFileDescriptor; 214a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tateimport android.os.RemoteException; 224a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tateimport android.os.ServiceManager; 23a312c03fd830c489ffc81fad0812826b093b73eeJeff Sharkeyimport android.system.OsConstants; 244a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tateimport android.util.Log; 254a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate 2646cc43c6fa7623820d4ae9149496cf96bb15f8a3Christopher Tateimport java.io.IOException; 274a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tateimport java.util.ArrayList; 284a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate 294a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tatepublic final class Backup { 3014a2935809e73a9d824888dc837f2f017100fd26Christopher Tate static final String TAG = "bu"; 314a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate 3214a2935809e73a9d824888dc837f2f017100fd26Christopher Tate static String[] mArgs; 3314a2935809e73a9d824888dc837f2f017100fd26Christopher Tate int mNextArg; 3414a2935809e73a9d824888dc837f2f017100fd26Christopher Tate IBackupManager mBackupManager; 354a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate 364a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate public static void main(String[] args) { 3775a99709accef8cf221fd436d646727e7c8dd1f1Christopher Tate Log.d(TAG, "Beginning: " + args[0]); 384a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate mArgs = args; 394a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate try { 404a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate new Backup().run(); 414a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate } catch (Exception e) { 4275a99709accef8cf221fd436d646727e7c8dd1f1Christopher Tate Log.e(TAG, "Error running backup/restore", e); 434a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate } 444a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate Log.d(TAG, "Finished."); 454a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate } 464a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate 474a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate public void run() { 4814a2935809e73a9d824888dc837f2f017100fd26Christopher Tate mBackupManager = IBackupManager.Stub.asInterface(ServiceManager.getService("backup")); 4914a2935809e73a9d824888dc837f2f017100fd26Christopher Tate if (mBackupManager == null) { 5075a99709accef8cf221fd436d646727e7c8dd1f1Christopher Tate Log.e(TAG, "Can't obtain Backup Manager binder"); 514a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate return; 524a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate } 534a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate 5414a2935809e73a9d824888dc837f2f017100fd26Christopher Tate String arg = nextArg(); 5514a2935809e73a9d824888dc837f2f017100fd26Christopher Tate if (arg.equals("backup")) { 56a312c03fd830c489ffc81fad0812826b093b73eeJeff Sharkey doFullBackup(OsConstants.STDOUT_FILENO); 5714a2935809e73a9d824888dc837f2f017100fd26Christopher Tate } else if (arg.equals("restore")) { 58a312c03fd830c489ffc81fad0812826b093b73eeJeff Sharkey doFullRestore(OsConstants.STDIN_FILENO); 5914a2935809e73a9d824888dc837f2f017100fd26Christopher Tate } else { 6075a99709accef8cf221fd436d646727e7c8dd1f1Christopher Tate Log.e(TAG, "Invalid operation '" + arg + "'"); 6114a2935809e73a9d824888dc837f2f017100fd26Christopher Tate } 6214a2935809e73a9d824888dc837f2f017100fd26Christopher Tate } 6314a2935809e73a9d824888dc837f2f017100fd26Christopher Tate 64e26e96bcc19b1cdac690d21b3986f09a502739e6Christopher Tate private void doFullBackup(int socketFd) { 654a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate ArrayList<String> packages = new ArrayList<String>(); 664a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate boolean saveApks = false; 6746cc43c6fa7623820d4ae9149496cf96bb15f8a3Christopher Tate boolean saveObbs = false; 684a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate boolean saveShared = false; 694a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate boolean doEverything = false; 70adfe8b86e9178a553b6db9722340fa4ff5201cf1Christopher Tate boolean doWidgets = false; 71240c7d2d1fb2944ee6a6f1dee41c7bbd766f8f0dChristopher Tate boolean allIncludesSystem = true; 729ff53a7100b1a40f5d2df3eb19a2f3f2fff39a46Christopher Tate boolean doCompress = true; 734a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate 744a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate String arg; 754a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate while ((arg = nextArg()) != null) { 764a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate if (arg.startsWith("-")) { 774a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate if ("-apk".equals(arg)) { 784a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate saveApks = true; 794a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate } else if ("-noapk".equals(arg)) { 804a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate saveApks = false; 8146cc43c6fa7623820d4ae9149496cf96bb15f8a3Christopher Tate } else if ("-obb".equals(arg)) { 8246cc43c6fa7623820d4ae9149496cf96bb15f8a3Christopher Tate saveObbs = true; 8346cc43c6fa7623820d4ae9149496cf96bb15f8a3Christopher Tate } else if ("-noobb".equals(arg)) { 8446cc43c6fa7623820d4ae9149496cf96bb15f8a3Christopher Tate saveObbs = false; 854a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate } else if ("-shared".equals(arg)) { 864a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate saveShared = true; 874a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate } else if ("-noshared".equals(arg)) { 884a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate saveShared = false; 89240c7d2d1fb2944ee6a6f1dee41c7bbd766f8f0dChristopher Tate } else if ("-system".equals(arg)) { 90240c7d2d1fb2944ee6a6f1dee41c7bbd766f8f0dChristopher Tate allIncludesSystem = true; 91240c7d2d1fb2944ee6a6f1dee41c7bbd766f8f0dChristopher Tate } else if ("-nosystem".equals(arg)) { 92240c7d2d1fb2944ee6a6f1dee41c7bbd766f8f0dChristopher Tate allIncludesSystem = false; 93adfe8b86e9178a553b6db9722340fa4ff5201cf1Christopher Tate } else if ("-widgets".equals(arg)) { 94adfe8b86e9178a553b6db9722340fa4ff5201cf1Christopher Tate doWidgets = true; 95adfe8b86e9178a553b6db9722340fa4ff5201cf1Christopher Tate } else if ("-nowidgets".equals(arg)) { 96adfe8b86e9178a553b6db9722340fa4ff5201cf1Christopher Tate doWidgets = false; 974a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate } else if ("-all".equals(arg)) { 984a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate doEverything = true; 999ff53a7100b1a40f5d2df3eb19a2f3f2fff39a46Christopher Tate } else if ("-compress".equals(arg)) { 1009ff53a7100b1a40f5d2df3eb19a2f3f2fff39a46Christopher Tate doCompress = true; 1019ff53a7100b1a40f5d2df3eb19a2f3f2fff39a46Christopher Tate } else if ("-nocompress".equals(arg)) { 1029ff53a7100b1a40f5d2df3eb19a2f3f2fff39a46Christopher Tate doCompress = false; 1034a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate } else { 10414a2935809e73a9d824888dc837f2f017100fd26Christopher Tate Log.w(TAG, "Unknown backup flag " + arg); 10514a2935809e73a9d824888dc837f2f017100fd26Christopher Tate continue; 1064a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate } 1074a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate } else { 1084a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate // Not a flag; treat as a package name 1094a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate packages.add(arg); 1104a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate } 1114a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate } 1124a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate 1134a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate if (doEverything && packages.size() > 0) { 11414a2935809e73a9d824888dc837f2f017100fd26Christopher Tate Log.w(TAG, "-all passed for backup along with specific package names"); 1154a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate } 1164a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate 11714a2935809e73a9d824888dc837f2f017100fd26Christopher Tate if (!doEverything && !saveShared && packages.size() == 0) { 11814a2935809e73a9d824888dc837f2f017100fd26Christopher Tate Log.e(TAG, "no backup packages supplied and neither -shared nor -all given"); 1194a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate return; 1204a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate } 1214a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate 12246cc43c6fa7623820d4ae9149496cf96bb15f8a3Christopher Tate ParcelFileDescriptor fd = null; 1234a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate try { 12446cc43c6fa7623820d4ae9149496cf96bb15f8a3Christopher Tate fd = ParcelFileDescriptor.adoptFd(socketFd); 1254a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate String[] packArray = new String[packages.size()]; 126adfe8b86e9178a553b6db9722340fa4ff5201cf1Christopher Tate mBackupManager.fullBackup(fd, saveApks, saveObbs, saveShared, doWidgets, 1279ff53a7100b1a40f5d2df3eb19a2f3f2fff39a46Christopher Tate doEverything, allIncludesSystem, doCompress, packages.toArray(packArray)); 1284a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate } catch (RemoteException e) { 12975a99709accef8cf221fd436d646727e7c8dd1f1Christopher Tate Log.e(TAG, "Unable to invoke backup manager for backup"); 13046cc43c6fa7623820d4ae9149496cf96bb15f8a3Christopher Tate } finally { 13146cc43c6fa7623820d4ae9149496cf96bb15f8a3Christopher Tate if (fd != null) { 13246cc43c6fa7623820d4ae9149496cf96bb15f8a3Christopher Tate try { 13346cc43c6fa7623820d4ae9149496cf96bb15f8a3Christopher Tate fd.close(); 13446cc43c6fa7623820d4ae9149496cf96bb15f8a3Christopher Tate } catch (IOException e) {} 13546cc43c6fa7623820d4ae9149496cf96bb15f8a3Christopher Tate } 1364a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate } 1374a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate } 1384a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate 139e26e96bcc19b1cdac690d21b3986f09a502739e6Christopher Tate private void doFullRestore(int socketFd) { 14075a99709accef8cf221fd436d646727e7c8dd1f1Christopher Tate // No arguments to restore 14146cc43c6fa7623820d4ae9149496cf96bb15f8a3Christopher Tate ParcelFileDescriptor fd = null; 14275a99709accef8cf221fd436d646727e7c8dd1f1Christopher Tate try { 14346cc43c6fa7623820d4ae9149496cf96bb15f8a3Christopher Tate fd = ParcelFileDescriptor.adoptFd(socketFd); 14475a99709accef8cf221fd436d646727e7c8dd1f1Christopher Tate mBackupManager.fullRestore(fd); 14575a99709accef8cf221fd436d646727e7c8dd1f1Christopher Tate } catch (RemoteException e) { 14675a99709accef8cf221fd436d646727e7c8dd1f1Christopher Tate Log.e(TAG, "Unable to invoke backup manager for restore"); 14746cc43c6fa7623820d4ae9149496cf96bb15f8a3Christopher Tate } finally { 14846cc43c6fa7623820d4ae9149496cf96bb15f8a3Christopher Tate if (fd != null) { 14946cc43c6fa7623820d4ae9149496cf96bb15f8a3Christopher Tate try { 15046cc43c6fa7623820d4ae9149496cf96bb15f8a3Christopher Tate fd.close(); 15146cc43c6fa7623820d4ae9149496cf96bb15f8a3Christopher Tate } catch (IOException e) {} 15246cc43c6fa7623820d4ae9149496cf96bb15f8a3Christopher Tate } 15375a99709accef8cf221fd436d646727e7c8dd1f1Christopher Tate } 15414a2935809e73a9d824888dc837f2f017100fd26Christopher Tate } 15514a2935809e73a9d824888dc837f2f017100fd26Christopher Tate 1564a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate private String nextArg() { 1574a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate if (mNextArg >= mArgs.length) { 1584a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate return null; 1594a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate } 1604a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate String arg = mArgs[mNextArg]; 1614a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate mNextArg++; 1624a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate return arg; 1634a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate } 1644a627c71ff53a4fca1f961f4b1dcc0461df18a06Christopher Tate}