Loading services/backup/java/com/android/server/backup/RefactoredBackupManagerService.java +27 −4 Original line number Original line Diff line number Diff line Loading @@ -48,7 +48,6 @@ import android.app.backup.IBackupObserver; import android.app.backup.IFullBackupRestoreObserver; import android.app.backup.IFullBackupRestoreObserver; import android.app.backup.IRestoreSession; import android.app.backup.IRestoreSession; import android.app.backup.ISelectBackupTransportCallback; import android.app.backup.ISelectBackupTransportCallback; import android.app.backup.SelectBackupTransportCallback; import android.content.ActivityNotFoundException; import android.content.ActivityNotFoundException; import android.content.BroadcastReceiver; import android.content.BroadcastReceiver; import android.content.ComponentName; import android.content.ComponentName; Loading Loading @@ -103,6 +102,7 @@ import com.android.server.backup.fullbackup.PerformFullTransportBackupTask; import com.android.server.backup.internal.BackupHandler; import com.android.server.backup.internal.BackupHandler; import com.android.server.backup.internal.BackupRequest; import com.android.server.backup.internal.BackupRequest; import com.android.server.backup.internal.ClearDataObserver; import com.android.server.backup.internal.ClearDataObserver; import com.android.server.backup.internal.OnTaskFinishedListener; import com.android.server.backup.internal.Operation; import com.android.server.backup.internal.Operation; import com.android.server.backup.internal.PerformInitializeTask; import com.android.server.backup.internal.PerformInitializeTask; import com.android.server.backup.internal.ProvisionedObserver; import com.android.server.backup.internal.ProvisionedObserver; Loading @@ -117,6 +117,7 @@ import com.android.server.backup.params.ClearRetryParams; import com.android.server.backup.params.RestoreParams; import com.android.server.backup.params.RestoreParams; import com.android.server.backup.restore.ActiveRestoreSession; import com.android.server.backup.restore.ActiveRestoreSession; import com.android.server.backup.restore.PerformUnifiedRestoreTask; import com.android.server.backup.restore.PerformUnifiedRestoreTask; import com.android.server.backup.transport.TransportClient; import com.android.server.backup.utils.AppBackupUtils; import com.android.server.backup.utils.AppBackupUtils; import com.android.server.backup.utils.BackupManagerMonitorUtils; import com.android.server.backup.utils.BackupManagerMonitorUtils; import com.android.server.backup.utils.BackupObserverUtils; import com.android.server.backup.utils.BackupObserverUtils; Loading Loading @@ -1585,8 +1586,27 @@ public class RefactoredBackupManagerService implements BackupManagerServiceInter return BackupManager.ERROR_BACKUP_NOT_ALLOWED; return BackupManager.ERROR_BACKUP_NOT_ALLOWED; } } // We're using pieces of the new binding on-demand infra-structure and the old always-bound // infra-structure below this comment. The TransportManager.getCurrentTransportClient() line // is using the new one and TransportManager.getCurrentTransportBinder() is using the old. // This is weird but there is a reason. // This is the natural place to put TransportManager.getCurrentTransportClient() because of // the null handling below that should be the same for TransportClient. // TransportClient.connect() would return a IBackupTransport for us (instead of using the // old infra), but it may block and we don't want this in this thread. // The only usage of transport in this method is for transport.transportDirName(). When the // push-from-transport part of binding on-demand is in place we will replace the calls for // IBackupTransport.transportDirName() with calls for // TransportManager.transportDirName(transportName) or similar. So we'll leave the old piece // here until we implement that. // TODO(brufino): Remove always-bound code mTransportManager.getCurrentTransportBinder() TransportClient transportClient = mTransportManager.getCurrentTransportClient("BMS.requestBackup()"); IBackupTransport transport = mTransportManager.getCurrentTransportBinder(); IBackupTransport transport = mTransportManager.getCurrentTransportBinder(); if (transport == null) { if (transportClient == null || transport == null) { if (transportClient != null) { mTransportManager.disposeOfTransportClient(transportClient, "BMS.requestBackup()"); } BackupObserverUtils.sendBackupFinished(observer, BackupManager.ERROR_TRANSPORT_ABORTED); BackupObserverUtils.sendBackupFinished(observer, BackupManager.ERROR_TRANSPORT_ABORTED); monitor = BackupManagerMonitorUtils.monitorEvent(monitor, monitor = BackupManagerMonitorUtils.monitorEvent(monitor, BackupManagerMonitor.LOG_EVENT_ID_TRANSPORT_IS_NULL, BackupManagerMonitor.LOG_EVENT_ID_TRANSPORT_IS_NULL, Loading @@ -1594,6 +1614,9 @@ public class RefactoredBackupManagerService implements BackupManagerServiceInter return BackupManager.ERROR_TRANSPORT_ABORTED; return BackupManager.ERROR_TRANSPORT_ABORTED; } } OnTaskFinishedListener listener = caller -> mTransportManager.disposeOfTransportClient(transportClient, caller); ArrayList<String> fullBackupList = new ArrayList<>(); ArrayList<String> fullBackupList = new ArrayList<>(); ArrayList<String> kvBackupList = new ArrayList<>(); ArrayList<String> kvBackupList = new ArrayList<>(); for (String packageName : packages) { for (String packageName : packages) { Loading Loading @@ -1640,8 +1663,8 @@ public class RefactoredBackupManagerService implements BackupManagerServiceInter boolean nonIncrementalBackup = (flags & BackupManager.FLAG_NON_INCREMENTAL_BACKUP) != 0; boolean nonIncrementalBackup = (flags & BackupManager.FLAG_NON_INCREMENTAL_BACKUP) != 0; Message msg = mBackupHandler.obtainMessage(MSG_REQUEST_BACKUP); Message msg = mBackupHandler.obtainMessage(MSG_REQUEST_BACKUP); msg.obj = new BackupParams(transport, dirName, kvBackupList, fullBackupList, observer, msg.obj = new BackupParams(transportClient, dirName, kvBackupList, fullBackupList, observer, monitor, true, nonIncrementalBackup); monitor, listener, true, nonIncrementalBackup); mBackupHandler.sendMessage(msg); mBackupHandler.sendMessage(msg); return BackupManager.SUCCESS; return BackupManager.SUCCESS; } } Loading services/backup/java/com/android/server/backup/TransportManager.java +75 −5 Original line number Original line Diff line number Diff line Loading @@ -16,8 +16,9 @@ package com.android.server.backup; package com.android.server.backup; import android.annotation.Nullable; import android.app.backup.BackupManager; import android.app.backup.BackupManager; import android.app.backup.SelectBackupTransportCallback; import android.app.backup.BackupTransport; import android.content.ComponentName; import android.content.ComponentName; import android.content.Context; import android.content.Context; import android.content.Intent; import android.content.Intent; Loading @@ -44,9 +45,11 @@ import com.android.internal.annotations.GuardedBy; import com.android.internal.annotations.VisibleForTesting; import com.android.internal.annotations.VisibleForTesting; import com.android.internal.backup.IBackupTransport; import com.android.internal.backup.IBackupTransport; import com.android.server.EventLogTags; import com.android.server.EventLogTags; import com.android.server.backup.transport.TransportClient; import com.android.server.backup.transport.TransportClientManager; import com.android.server.backup.transport.TransportConnectionListener; import java.util.ArrayList; import java.util.ArrayList; import java.util.Collections; import java.util.Iterator; import java.util.Iterator; import java.util.List; import java.util.List; import java.util.Map; import java.util.Map; Loading @@ -60,8 +63,7 @@ public class TransportManager { private static final String TAG = "BackupTransportManager"; private static final String TAG = "BackupTransportManager"; @VisibleForTesting @VisibleForTesting /* package */ static final String SERVICE_ACTION_TRANSPORT_HOST = public static final String SERVICE_ACTION_TRANSPORT_HOST = "android.backup.TRANSPORT_HOST"; "android.backup.TRANSPORT_HOST"; private static final long REBINDING_TIMEOUT_UNPROVISIONED_MS = 30 * 1000; // 30 sec private static final long REBINDING_TIMEOUT_UNPROVISIONED_MS = 30 * 1000; // 30 sec private static final long REBINDING_TIMEOUT_PROVISIONED_MS = 5 * 60 * 1000; // 5 mins private static final long REBINDING_TIMEOUT_PROVISIONED_MS = 5 * 60 * 1000; // 5 mins Loading @@ -72,6 +74,7 @@ public class TransportManager { private final PackageManager mPackageManager; private final PackageManager mPackageManager; private final Set<ComponentName> mTransportWhitelist; private final Set<ComponentName> mTransportWhitelist; private final Handler mHandler; private final Handler mHandler; private final TransportClientManager mTransportClientManager; /** /** * This listener is called after we bind to any transport. If it returns true, this is a valid * This listener is called after we bind to any transport. If it returns true, this is a valid Loading @@ -95,6 +98,10 @@ public class TransportManager { @GuardedBy("mTransportLock") @GuardedBy("mTransportLock") private final Map<String, ComponentName> mBoundTransports = new ArrayMap<>(); private final Map<String, ComponentName> mBoundTransports = new ArrayMap<>(); /** Names of transports we've bound to at least once */ @GuardedBy("mTransportLock") private final Map<String, ComponentName> mTransportsByName = new ArrayMap<>(); /** /** * Callback interface for {@link #ensureTransportReady(ComponentName, TransportReadyCallback)}. * Callback interface for {@link #ensureTransportReady(ComponentName, TransportReadyCallback)}. */ */ Loading Loading @@ -123,6 +130,7 @@ public class TransportManager { mCurrentTransportName = defaultTransport; mCurrentTransportName = defaultTransport; mTransportBoundListener = listener; mTransportBoundListener = listener; mHandler = new RebindOnTimeoutHandler(looper); mHandler = new RebindOnTimeoutHandler(looper); mTransportClientManager = new TransportClientManager(context); } } void onPackageAdded(String packageName) { void onPackageAdded(String packageName) { Loading Loading @@ -204,6 +212,67 @@ public class TransportManager { return null; return null; } } /** * Returns the transport name associated with {@param transportClient} or {@code null} if not * found. */ @Nullable public String getTransportName(TransportClient transportClient) { ComponentName transportComponent = transportClient.getTransportComponent(); synchronized (mTransportLock) { for (Map.Entry<String, ComponentName> transportEntry : mTransportsByName.entrySet()) { if (transportEntry.getValue().equals(transportComponent)) { return transportEntry.getKey(); } } return null; } } /** * Returns a {@link TransportClient} for {@param transportName} or {@code null} if not found. * * @param transportName The name of the transport as returned by {@link BackupTransport#name()}. * @param caller A {@link String} identifying the caller for logging/debugging purposes. Check * {@link TransportClient#connectAsync(TransportConnectionListener, String)} for more * details. * @return A {@link TransportClient} or null if not found. */ @Nullable public TransportClient getTransportClient(String transportName, String caller) { ComponentName transportComponent = mTransportsByName.get(transportName); if (transportComponent == null) { Slog.w(TAG, "Transport " + transportName + " not registered"); return null; } return mTransportClientManager.getTransportClient(transportComponent, caller); } /** * Returns a {@link TransportClient} for the current transport or null if not found. * * @param caller A {@link String} identifying the caller for logging/debugging purposes. Check * {@link TransportClient#connectAsync(TransportConnectionListener, String)} for more * details. * @return A {@link TransportClient} or null if not found. */ @Nullable public TransportClient getCurrentTransportClient(String caller) { return getTransportClient(mCurrentTransportName, caller); } /** * Disposes of the {@link TransportClient}. * * @param transportClient The {@link TransportClient} to be disposed of. * @param caller A {@link String} identifying the caller for logging/debugging purposes. Check * {@link TransportClient#connectAsync(TransportConnectionListener, String)} for more * details. */ public void disposeOfTransportClient(TransportClient transportClient, String caller) { mTransportClientManager.disposeOfTransportClient(transportClient, caller); } String[] getBoundTransportNames() { String[] getBoundTransportNames() { synchronized (mTransportLock) { synchronized (mTransportLock) { return mBoundTransports.keySet().toArray(new String[mBoundTransports.size()]); return mBoundTransports.keySet().toArray(new String[mBoundTransports.size()]); Loading Loading @@ -374,6 +443,7 @@ public class TransportManager { String componentShortString = component.flattenToShortString().intern(); String componentShortString = component.flattenToShortString().intern(); if (success) { if (success) { Slog.d(TAG, "Bound to transport: " + componentShortString); Slog.d(TAG, "Bound to transport: " + componentShortString); mTransportsByName.put(mTransportName, component); mBoundTransports.put(mTransportName, component); mBoundTransports.put(mTransportName, component); for (TransportReadyCallback listener : mListeners) { for (TransportReadyCallback listener : mListeners) { listener.onSuccess(mTransportName); listener.onSuccess(mTransportName); Loading Loading @@ -528,7 +598,7 @@ public class TransportManager { // These only exists to make it testable with Robolectric, which is not updated to API level 24 // These only exists to make it testable with Robolectric, which is not updated to API level 24 // yet. // yet. // TODO: Get rid of this once Robolectric is updated. // TODO: Get rid of this once Robolectric is updated. private static UserHandle createSystemUserHandle() { public static UserHandle createSystemUserHandle() { return new UserHandle(UserHandle.USER_SYSTEM); return new UserHandle(UserHandle.USER_SYSTEM); } } } } services/backup/java/com/android/server/backup/internal/BackupHandler.java +24 −9 Original line number Original line Diff line number Diff line Loading @@ -38,6 +38,8 @@ import com.android.server.EventLogTags; import com.android.server.backup.BackupRestoreTask; import com.android.server.backup.BackupRestoreTask; import com.android.server.backup.DataChangedJournal; import com.android.server.backup.DataChangedJournal; import com.android.server.backup.RefactoredBackupManagerService; import com.android.server.backup.RefactoredBackupManagerService; import com.android.server.backup.transport.TransportClient; import com.android.server.backup.TransportManager; import com.android.server.backup.fullbackup.PerformAdbBackupTask; import com.android.server.backup.fullbackup.PerformAdbBackupTask; import com.android.server.backup.fullbackup.PerformFullTransportBackupTask; import com.android.server.backup.fullbackup.PerformFullTransportBackupTask; import com.android.server.backup.params.AdbBackupParams; import com.android.server.backup.params.AdbBackupParams; Loading @@ -51,10 +53,8 @@ import com.android.server.backup.params.RestoreParams; import com.android.server.backup.restore.PerformAdbRestoreTask; import com.android.server.backup.restore.PerformAdbRestoreTask; import com.android.server.backup.restore.PerformUnifiedRestoreTask; import com.android.server.backup.restore.PerformUnifiedRestoreTask; import java.io.File; import java.util.ArrayList; import java.util.ArrayList; import java.util.Collections; import java.util.Collections; import java.util.HashSet; /** /** * Asynchronous backup/restore handler thread. * Asynchronous backup/restore handler thread. Loading @@ -81,7 +81,7 @@ public class BackupHandler extends Handler { public static final int MSG_BACKUP_RESTORE_STEP = 20; public static final int MSG_BACKUP_RESTORE_STEP = 20; public static final int MSG_OP_COMPLETE = 21; public static final int MSG_OP_COMPLETE = 21; private RefactoredBackupManagerService backupManagerService; private final RefactoredBackupManagerService backupManagerService; public BackupHandler( public BackupHandler( RefactoredBackupManagerService backupManagerService, Looper looper) { RefactoredBackupManagerService backupManagerService, Looper looper) { Loading @@ -91,13 +91,23 @@ public class BackupHandler extends Handler { public void handleMessage(Message msg) { public void handleMessage(Message msg) { TransportManager transportManager = backupManagerService.getTransportManager(); switch (msg.what) { switch (msg.what) { case MSG_RUN_BACKUP: { case MSG_RUN_BACKUP: { backupManagerService.setLastBackupPass(System.currentTimeMillis()); backupManagerService.setLastBackupPass(System.currentTimeMillis()); String callerLogString = "BH/MSG_RUN_BACKUP"; TransportClient transportClient = transportManager.getCurrentTransportClient(callerLogString); IBackupTransport transport = IBackupTransport transport = backupManagerService.getTransportManager().getCurrentTransportBinder(); transportClient != null ? transportClient.connect(callerLogString) : null; if (transport == null) { if (transport == null) { if (transportClient != null) { transportManager .disposeOfTransportClient(transportClient, callerLogString); } Slog.v(TAG, "Backup requested but no transport available"); Slog.v(TAG, "Backup requested but no transport available"); synchronized (backupManagerService.getQueueLock()) { synchronized (backupManagerService.getQueueLock()) { backupManagerService.setBackupRunning(false); backupManagerService.setBackupRunning(false); Loading Loading @@ -138,9 +148,13 @@ public class BackupHandler extends Handler { // Spin up a backup state sequence and set it running // Spin up a backup state sequence and set it running try { try { String dirName = transport.transportDirName(); String dirName = transport.transportDirName(); OnTaskFinishedListener listener = caller -> transportManager .disposeOfTransportClient(transportClient, caller); PerformBackupTask pbt = new PerformBackupTask( PerformBackupTask pbt = new PerformBackupTask( backupManagerService, transport, dirName, queue, backupManagerService, transportClient, dirName, queue, oldJournal, null, null, Collections.<String>emptyList(), false, oldJournal, null, null, listener, Collections.emptyList(), false, false /* nonIncremental */); false /* nonIncremental */); Message pbtMessage = obtainMessage(MSG_BACKUP_RESTORE_STEP, pbt); Message pbtMessage = obtainMessage(MSG_BACKUP_RESTORE_STEP, pbt); sendMessage(pbtMessage); sendMessage(pbtMessage); Loading @@ -157,6 +171,7 @@ public class BackupHandler extends Handler { } } if (!staged) { if (!staged) { transportManager.disposeOfTransportClient(transportClient, callerLogString); // if we didn't actually hand off the wakelock, rewind until next time // if we didn't actually hand off the wakelock, rewind until next time synchronized (backupManagerService.getQueueLock()) { synchronized (backupManagerService.getQueueLock()) { backupManagerService.setBackupRunning(false); backupManagerService.setBackupRunning(false); Loading Loading @@ -382,9 +397,9 @@ public class BackupHandler extends Handler { PerformBackupTask pbt = new PerformBackupTask( PerformBackupTask pbt = new PerformBackupTask( backupManagerService, backupManagerService, params.transport, params.dirName, params.transportClient, params.dirName, kvQueue, null, params.observer, params.monitor, params.fullPackages, true, kvQueue, null, params.observer, params.monitor, params.listener, params.nonIncrementalBackup); params.fullPackages, true, params.nonIncrementalBackup); Message pbtMessage = obtainMessage(MSG_BACKUP_RESTORE_STEP, pbt); Message pbtMessage = obtainMessage(MSG_BACKUP_RESTORE_STEP, pbt); sendMessage(pbtMessage); sendMessage(pbtMessage); break; break; Loading services/backup/java/com/android/server/backup/internal/OnTaskFinishedListener.java 0 → 100644 +34 −0 Original line number Original line Diff line number Diff line /* * Copyright (C) 2017 The Android Open Source Project * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License */ package com.android.server.backup.internal; import com.android.server.backup.transport.TransportClient; import com.android.server.backup.transport.TransportConnectionListener; /** Listener to be called when a task finishes, successfully or not. */ public interface OnTaskFinishedListener { OnTaskFinishedListener NOP = caller -> {}; /** * Called when a task finishes, successfully or not. * * @param caller A {@link String} identifying the caller for logging/debugging purposes. Check * {@link TransportClient#connectAsync(TransportConnectionListener, String)} for more * details. */ void onFinished(String caller); } services/backup/java/com/android/server/backup/internal/PerformBackupTask.java +39 −21 File changed.Preview size limit exceeded, changes collapsed. Show changes Loading
services/backup/java/com/android/server/backup/RefactoredBackupManagerService.java +27 −4 Original line number Original line Diff line number Diff line Loading @@ -48,7 +48,6 @@ import android.app.backup.IBackupObserver; import android.app.backup.IFullBackupRestoreObserver; import android.app.backup.IFullBackupRestoreObserver; import android.app.backup.IRestoreSession; import android.app.backup.IRestoreSession; import android.app.backup.ISelectBackupTransportCallback; import android.app.backup.ISelectBackupTransportCallback; import android.app.backup.SelectBackupTransportCallback; import android.content.ActivityNotFoundException; import android.content.ActivityNotFoundException; import android.content.BroadcastReceiver; import android.content.BroadcastReceiver; import android.content.ComponentName; import android.content.ComponentName; Loading Loading @@ -103,6 +102,7 @@ import com.android.server.backup.fullbackup.PerformFullTransportBackupTask; import com.android.server.backup.internal.BackupHandler; import com.android.server.backup.internal.BackupHandler; import com.android.server.backup.internal.BackupRequest; import com.android.server.backup.internal.BackupRequest; import com.android.server.backup.internal.ClearDataObserver; import com.android.server.backup.internal.ClearDataObserver; import com.android.server.backup.internal.OnTaskFinishedListener; import com.android.server.backup.internal.Operation; import com.android.server.backup.internal.Operation; import com.android.server.backup.internal.PerformInitializeTask; import com.android.server.backup.internal.PerformInitializeTask; import com.android.server.backup.internal.ProvisionedObserver; import com.android.server.backup.internal.ProvisionedObserver; Loading @@ -117,6 +117,7 @@ import com.android.server.backup.params.ClearRetryParams; import com.android.server.backup.params.RestoreParams; import com.android.server.backup.params.RestoreParams; import com.android.server.backup.restore.ActiveRestoreSession; import com.android.server.backup.restore.ActiveRestoreSession; import com.android.server.backup.restore.PerformUnifiedRestoreTask; import com.android.server.backup.restore.PerformUnifiedRestoreTask; import com.android.server.backup.transport.TransportClient; import com.android.server.backup.utils.AppBackupUtils; import com.android.server.backup.utils.AppBackupUtils; import com.android.server.backup.utils.BackupManagerMonitorUtils; import com.android.server.backup.utils.BackupManagerMonitorUtils; import com.android.server.backup.utils.BackupObserverUtils; import com.android.server.backup.utils.BackupObserverUtils; Loading Loading @@ -1585,8 +1586,27 @@ public class RefactoredBackupManagerService implements BackupManagerServiceInter return BackupManager.ERROR_BACKUP_NOT_ALLOWED; return BackupManager.ERROR_BACKUP_NOT_ALLOWED; } } // We're using pieces of the new binding on-demand infra-structure and the old always-bound // infra-structure below this comment. The TransportManager.getCurrentTransportClient() line // is using the new one and TransportManager.getCurrentTransportBinder() is using the old. // This is weird but there is a reason. // This is the natural place to put TransportManager.getCurrentTransportClient() because of // the null handling below that should be the same for TransportClient. // TransportClient.connect() would return a IBackupTransport for us (instead of using the // old infra), but it may block and we don't want this in this thread. // The only usage of transport in this method is for transport.transportDirName(). When the // push-from-transport part of binding on-demand is in place we will replace the calls for // IBackupTransport.transportDirName() with calls for // TransportManager.transportDirName(transportName) or similar. So we'll leave the old piece // here until we implement that. // TODO(brufino): Remove always-bound code mTransportManager.getCurrentTransportBinder() TransportClient transportClient = mTransportManager.getCurrentTransportClient("BMS.requestBackup()"); IBackupTransport transport = mTransportManager.getCurrentTransportBinder(); IBackupTransport transport = mTransportManager.getCurrentTransportBinder(); if (transport == null) { if (transportClient == null || transport == null) { if (transportClient != null) { mTransportManager.disposeOfTransportClient(transportClient, "BMS.requestBackup()"); } BackupObserverUtils.sendBackupFinished(observer, BackupManager.ERROR_TRANSPORT_ABORTED); BackupObserverUtils.sendBackupFinished(observer, BackupManager.ERROR_TRANSPORT_ABORTED); monitor = BackupManagerMonitorUtils.monitorEvent(monitor, monitor = BackupManagerMonitorUtils.monitorEvent(monitor, BackupManagerMonitor.LOG_EVENT_ID_TRANSPORT_IS_NULL, BackupManagerMonitor.LOG_EVENT_ID_TRANSPORT_IS_NULL, Loading @@ -1594,6 +1614,9 @@ public class RefactoredBackupManagerService implements BackupManagerServiceInter return BackupManager.ERROR_TRANSPORT_ABORTED; return BackupManager.ERROR_TRANSPORT_ABORTED; } } OnTaskFinishedListener listener = caller -> mTransportManager.disposeOfTransportClient(transportClient, caller); ArrayList<String> fullBackupList = new ArrayList<>(); ArrayList<String> fullBackupList = new ArrayList<>(); ArrayList<String> kvBackupList = new ArrayList<>(); ArrayList<String> kvBackupList = new ArrayList<>(); for (String packageName : packages) { for (String packageName : packages) { Loading Loading @@ -1640,8 +1663,8 @@ public class RefactoredBackupManagerService implements BackupManagerServiceInter boolean nonIncrementalBackup = (flags & BackupManager.FLAG_NON_INCREMENTAL_BACKUP) != 0; boolean nonIncrementalBackup = (flags & BackupManager.FLAG_NON_INCREMENTAL_BACKUP) != 0; Message msg = mBackupHandler.obtainMessage(MSG_REQUEST_BACKUP); Message msg = mBackupHandler.obtainMessage(MSG_REQUEST_BACKUP); msg.obj = new BackupParams(transport, dirName, kvBackupList, fullBackupList, observer, msg.obj = new BackupParams(transportClient, dirName, kvBackupList, fullBackupList, observer, monitor, true, nonIncrementalBackup); monitor, listener, true, nonIncrementalBackup); mBackupHandler.sendMessage(msg); mBackupHandler.sendMessage(msg); return BackupManager.SUCCESS; return BackupManager.SUCCESS; } } Loading
services/backup/java/com/android/server/backup/TransportManager.java +75 −5 Original line number Original line Diff line number Diff line Loading @@ -16,8 +16,9 @@ package com.android.server.backup; package com.android.server.backup; import android.annotation.Nullable; import android.app.backup.BackupManager; import android.app.backup.BackupManager; import android.app.backup.SelectBackupTransportCallback; import android.app.backup.BackupTransport; import android.content.ComponentName; import android.content.ComponentName; import android.content.Context; import android.content.Context; import android.content.Intent; import android.content.Intent; Loading @@ -44,9 +45,11 @@ import com.android.internal.annotations.GuardedBy; import com.android.internal.annotations.VisibleForTesting; import com.android.internal.annotations.VisibleForTesting; import com.android.internal.backup.IBackupTransport; import com.android.internal.backup.IBackupTransport; import com.android.server.EventLogTags; import com.android.server.EventLogTags; import com.android.server.backup.transport.TransportClient; import com.android.server.backup.transport.TransportClientManager; import com.android.server.backup.transport.TransportConnectionListener; import java.util.ArrayList; import java.util.ArrayList; import java.util.Collections; import java.util.Iterator; import java.util.Iterator; import java.util.List; import java.util.List; import java.util.Map; import java.util.Map; Loading @@ -60,8 +63,7 @@ public class TransportManager { private static final String TAG = "BackupTransportManager"; private static final String TAG = "BackupTransportManager"; @VisibleForTesting @VisibleForTesting /* package */ static final String SERVICE_ACTION_TRANSPORT_HOST = public static final String SERVICE_ACTION_TRANSPORT_HOST = "android.backup.TRANSPORT_HOST"; "android.backup.TRANSPORT_HOST"; private static final long REBINDING_TIMEOUT_UNPROVISIONED_MS = 30 * 1000; // 30 sec private static final long REBINDING_TIMEOUT_UNPROVISIONED_MS = 30 * 1000; // 30 sec private static final long REBINDING_TIMEOUT_PROVISIONED_MS = 5 * 60 * 1000; // 5 mins private static final long REBINDING_TIMEOUT_PROVISIONED_MS = 5 * 60 * 1000; // 5 mins Loading @@ -72,6 +74,7 @@ public class TransportManager { private final PackageManager mPackageManager; private final PackageManager mPackageManager; private final Set<ComponentName> mTransportWhitelist; private final Set<ComponentName> mTransportWhitelist; private final Handler mHandler; private final Handler mHandler; private final TransportClientManager mTransportClientManager; /** /** * This listener is called after we bind to any transport. If it returns true, this is a valid * This listener is called after we bind to any transport. If it returns true, this is a valid Loading @@ -95,6 +98,10 @@ public class TransportManager { @GuardedBy("mTransportLock") @GuardedBy("mTransportLock") private final Map<String, ComponentName> mBoundTransports = new ArrayMap<>(); private final Map<String, ComponentName> mBoundTransports = new ArrayMap<>(); /** Names of transports we've bound to at least once */ @GuardedBy("mTransportLock") private final Map<String, ComponentName> mTransportsByName = new ArrayMap<>(); /** /** * Callback interface for {@link #ensureTransportReady(ComponentName, TransportReadyCallback)}. * Callback interface for {@link #ensureTransportReady(ComponentName, TransportReadyCallback)}. */ */ Loading Loading @@ -123,6 +130,7 @@ public class TransportManager { mCurrentTransportName = defaultTransport; mCurrentTransportName = defaultTransport; mTransportBoundListener = listener; mTransportBoundListener = listener; mHandler = new RebindOnTimeoutHandler(looper); mHandler = new RebindOnTimeoutHandler(looper); mTransportClientManager = new TransportClientManager(context); } } void onPackageAdded(String packageName) { void onPackageAdded(String packageName) { Loading Loading @@ -204,6 +212,67 @@ public class TransportManager { return null; return null; } } /** * Returns the transport name associated with {@param transportClient} or {@code null} if not * found. */ @Nullable public String getTransportName(TransportClient transportClient) { ComponentName transportComponent = transportClient.getTransportComponent(); synchronized (mTransportLock) { for (Map.Entry<String, ComponentName> transportEntry : mTransportsByName.entrySet()) { if (transportEntry.getValue().equals(transportComponent)) { return transportEntry.getKey(); } } return null; } } /** * Returns a {@link TransportClient} for {@param transportName} or {@code null} if not found. * * @param transportName The name of the transport as returned by {@link BackupTransport#name()}. * @param caller A {@link String} identifying the caller for logging/debugging purposes. Check * {@link TransportClient#connectAsync(TransportConnectionListener, String)} for more * details. * @return A {@link TransportClient} or null if not found. */ @Nullable public TransportClient getTransportClient(String transportName, String caller) { ComponentName transportComponent = mTransportsByName.get(transportName); if (transportComponent == null) { Slog.w(TAG, "Transport " + transportName + " not registered"); return null; } return mTransportClientManager.getTransportClient(transportComponent, caller); } /** * Returns a {@link TransportClient} for the current transport or null if not found. * * @param caller A {@link String} identifying the caller for logging/debugging purposes. Check * {@link TransportClient#connectAsync(TransportConnectionListener, String)} for more * details. * @return A {@link TransportClient} or null if not found. */ @Nullable public TransportClient getCurrentTransportClient(String caller) { return getTransportClient(mCurrentTransportName, caller); } /** * Disposes of the {@link TransportClient}. * * @param transportClient The {@link TransportClient} to be disposed of. * @param caller A {@link String} identifying the caller for logging/debugging purposes. Check * {@link TransportClient#connectAsync(TransportConnectionListener, String)} for more * details. */ public void disposeOfTransportClient(TransportClient transportClient, String caller) { mTransportClientManager.disposeOfTransportClient(transportClient, caller); } String[] getBoundTransportNames() { String[] getBoundTransportNames() { synchronized (mTransportLock) { synchronized (mTransportLock) { return mBoundTransports.keySet().toArray(new String[mBoundTransports.size()]); return mBoundTransports.keySet().toArray(new String[mBoundTransports.size()]); Loading Loading @@ -374,6 +443,7 @@ public class TransportManager { String componentShortString = component.flattenToShortString().intern(); String componentShortString = component.flattenToShortString().intern(); if (success) { if (success) { Slog.d(TAG, "Bound to transport: " + componentShortString); Slog.d(TAG, "Bound to transport: " + componentShortString); mTransportsByName.put(mTransportName, component); mBoundTransports.put(mTransportName, component); mBoundTransports.put(mTransportName, component); for (TransportReadyCallback listener : mListeners) { for (TransportReadyCallback listener : mListeners) { listener.onSuccess(mTransportName); listener.onSuccess(mTransportName); Loading Loading @@ -528,7 +598,7 @@ public class TransportManager { // These only exists to make it testable with Robolectric, which is not updated to API level 24 // These only exists to make it testable with Robolectric, which is not updated to API level 24 // yet. // yet. // TODO: Get rid of this once Robolectric is updated. // TODO: Get rid of this once Robolectric is updated. private static UserHandle createSystemUserHandle() { public static UserHandle createSystemUserHandle() { return new UserHandle(UserHandle.USER_SYSTEM); return new UserHandle(UserHandle.USER_SYSTEM); } } } }
services/backup/java/com/android/server/backup/internal/BackupHandler.java +24 −9 Original line number Original line Diff line number Diff line Loading @@ -38,6 +38,8 @@ import com.android.server.EventLogTags; import com.android.server.backup.BackupRestoreTask; import com.android.server.backup.BackupRestoreTask; import com.android.server.backup.DataChangedJournal; import com.android.server.backup.DataChangedJournal; import com.android.server.backup.RefactoredBackupManagerService; import com.android.server.backup.RefactoredBackupManagerService; import com.android.server.backup.transport.TransportClient; import com.android.server.backup.TransportManager; import com.android.server.backup.fullbackup.PerformAdbBackupTask; import com.android.server.backup.fullbackup.PerformAdbBackupTask; import com.android.server.backup.fullbackup.PerformFullTransportBackupTask; import com.android.server.backup.fullbackup.PerformFullTransportBackupTask; import com.android.server.backup.params.AdbBackupParams; import com.android.server.backup.params.AdbBackupParams; Loading @@ -51,10 +53,8 @@ import com.android.server.backup.params.RestoreParams; import com.android.server.backup.restore.PerformAdbRestoreTask; import com.android.server.backup.restore.PerformAdbRestoreTask; import com.android.server.backup.restore.PerformUnifiedRestoreTask; import com.android.server.backup.restore.PerformUnifiedRestoreTask; import java.io.File; import java.util.ArrayList; import java.util.ArrayList; import java.util.Collections; import java.util.Collections; import java.util.HashSet; /** /** * Asynchronous backup/restore handler thread. * Asynchronous backup/restore handler thread. Loading @@ -81,7 +81,7 @@ public class BackupHandler extends Handler { public static final int MSG_BACKUP_RESTORE_STEP = 20; public static final int MSG_BACKUP_RESTORE_STEP = 20; public static final int MSG_OP_COMPLETE = 21; public static final int MSG_OP_COMPLETE = 21; private RefactoredBackupManagerService backupManagerService; private final RefactoredBackupManagerService backupManagerService; public BackupHandler( public BackupHandler( RefactoredBackupManagerService backupManagerService, Looper looper) { RefactoredBackupManagerService backupManagerService, Looper looper) { Loading @@ -91,13 +91,23 @@ public class BackupHandler extends Handler { public void handleMessage(Message msg) { public void handleMessage(Message msg) { TransportManager transportManager = backupManagerService.getTransportManager(); switch (msg.what) { switch (msg.what) { case MSG_RUN_BACKUP: { case MSG_RUN_BACKUP: { backupManagerService.setLastBackupPass(System.currentTimeMillis()); backupManagerService.setLastBackupPass(System.currentTimeMillis()); String callerLogString = "BH/MSG_RUN_BACKUP"; TransportClient transportClient = transportManager.getCurrentTransportClient(callerLogString); IBackupTransport transport = IBackupTransport transport = backupManagerService.getTransportManager().getCurrentTransportBinder(); transportClient != null ? transportClient.connect(callerLogString) : null; if (transport == null) { if (transport == null) { if (transportClient != null) { transportManager .disposeOfTransportClient(transportClient, callerLogString); } Slog.v(TAG, "Backup requested but no transport available"); Slog.v(TAG, "Backup requested but no transport available"); synchronized (backupManagerService.getQueueLock()) { synchronized (backupManagerService.getQueueLock()) { backupManagerService.setBackupRunning(false); backupManagerService.setBackupRunning(false); Loading Loading @@ -138,9 +148,13 @@ public class BackupHandler extends Handler { // Spin up a backup state sequence and set it running // Spin up a backup state sequence and set it running try { try { String dirName = transport.transportDirName(); String dirName = transport.transportDirName(); OnTaskFinishedListener listener = caller -> transportManager .disposeOfTransportClient(transportClient, caller); PerformBackupTask pbt = new PerformBackupTask( PerformBackupTask pbt = new PerformBackupTask( backupManagerService, transport, dirName, queue, backupManagerService, transportClient, dirName, queue, oldJournal, null, null, Collections.<String>emptyList(), false, oldJournal, null, null, listener, Collections.emptyList(), false, false /* nonIncremental */); false /* nonIncremental */); Message pbtMessage = obtainMessage(MSG_BACKUP_RESTORE_STEP, pbt); Message pbtMessage = obtainMessage(MSG_BACKUP_RESTORE_STEP, pbt); sendMessage(pbtMessage); sendMessage(pbtMessage); Loading @@ -157,6 +171,7 @@ public class BackupHandler extends Handler { } } if (!staged) { if (!staged) { transportManager.disposeOfTransportClient(transportClient, callerLogString); // if we didn't actually hand off the wakelock, rewind until next time // if we didn't actually hand off the wakelock, rewind until next time synchronized (backupManagerService.getQueueLock()) { synchronized (backupManagerService.getQueueLock()) { backupManagerService.setBackupRunning(false); backupManagerService.setBackupRunning(false); Loading Loading @@ -382,9 +397,9 @@ public class BackupHandler extends Handler { PerformBackupTask pbt = new PerformBackupTask( PerformBackupTask pbt = new PerformBackupTask( backupManagerService, backupManagerService, params.transport, params.dirName, params.transportClient, params.dirName, kvQueue, null, params.observer, params.monitor, params.fullPackages, true, kvQueue, null, params.observer, params.monitor, params.listener, params.nonIncrementalBackup); params.fullPackages, true, params.nonIncrementalBackup); Message pbtMessage = obtainMessage(MSG_BACKUP_RESTORE_STEP, pbt); Message pbtMessage = obtainMessage(MSG_BACKUP_RESTORE_STEP, pbt); sendMessage(pbtMessage); sendMessage(pbtMessage); break; break; Loading
services/backup/java/com/android/server/backup/internal/OnTaskFinishedListener.java 0 → 100644 +34 −0 Original line number Original line Diff line number Diff line /* * Copyright (C) 2017 The Android Open Source Project * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License */ package com.android.server.backup.internal; import com.android.server.backup.transport.TransportClient; import com.android.server.backup.transport.TransportConnectionListener; /** Listener to be called when a task finishes, successfully or not. */ public interface OnTaskFinishedListener { OnTaskFinishedListener NOP = caller -> {}; /** * Called when a task finishes, successfully or not. * * @param caller A {@link String} identifying the caller for logging/debugging purposes. Check * {@link TransportClient#connectAsync(TransportConnectionListener, String)} for more * details. */ void onFinished(String caller); }
services/backup/java/com/android/server/backup/internal/PerformBackupTask.java +39 −21 File changed.Preview size limit exceeded, changes collapsed. Show changes