Merge "Use RemoteCallbackList to store registered callbacks" into qt-dev
am: 60f7b58a9a
Change-Id: I6eace2328a4397205e522b5525ecf8cae243c031
This commit is contained in:
@@ -28,7 +28,7 @@ import android.content.pm.PackageManager;
|
|||||||
import android.content.pm.PackageManager.NameNotFoundException;
|
import android.content.pm.PackageManager.NameNotFoundException;
|
||||||
import android.content.pm.ParceledListSlice;
|
import android.content.pm.ParceledListSlice;
|
||||||
import android.content.pm.ServiceInfo;
|
import android.content.pm.ServiceInfo;
|
||||||
import android.os.IBinder;
|
import android.os.RemoteCallbackList;
|
||||||
import android.os.RemoteException;
|
import android.os.RemoteException;
|
||||||
import android.service.appprediction.AppPredictionService;
|
import android.service.appprediction.AppPredictionService;
|
||||||
import android.util.ArrayMap;
|
import android.util.ArrayMap;
|
||||||
@@ -37,7 +37,7 @@ import android.util.Slog;
|
|||||||
import com.android.internal.annotations.GuardedBy;
|
import com.android.internal.annotations.GuardedBy;
|
||||||
import com.android.server.infra.AbstractPerUserSystemService;
|
import com.android.server.infra.AbstractPerUserSystemService;
|
||||||
|
|
||||||
import java.util.ArrayList;
|
import java.util.function.Consumer;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Per-user instance of {@link AppPredictionManagerService}.
|
* Per-user instance of {@link AppPredictionManagerService}.
|
||||||
@@ -108,16 +108,11 @@ public class AppPredictionPerUserService extends
|
|||||||
if (service != null) {
|
if (service != null) {
|
||||||
service.onCreatePredictionSession(context, sessionId);
|
service.onCreatePredictionSession(context, sessionId);
|
||||||
|
|
||||||
mSessionInfos.put(sessionId, new AppPredictionSessionInfo(sessionId, context, () -> {
|
if (!mSessionInfos.containsKey(sessionId)) {
|
||||||
synchronized (mLock) {
|
mSessionInfos.put(sessionId, new AppPredictionSessionInfo(sessionId, context,
|
||||||
AppPredictionSessionInfo sessionInfo = mSessionInfos.get(sessionId);
|
this::removeAppPredictionSessionInfo));
|
||||||
if (sessionInfo != null) {
|
|
||||||
sessionInfo.removeAllCallbacksLocked();
|
|
||||||
mSessionInfos.remove(sessionId);
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}));
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -212,8 +207,7 @@ public class AppPredictionPerUserService extends
|
|||||||
|
|
||||||
AppPredictionSessionInfo sessionInfo = mSessionInfos.get(sessionId);
|
AppPredictionSessionInfo sessionInfo = mSessionInfos.get(sessionId);
|
||||||
if (sessionInfo != null) {
|
if (sessionInfo != null) {
|
||||||
sessionInfo.removeAllCallbacksLocked();
|
sessionInfo.destroy();
|
||||||
mSessionInfos.remove(sessionId);
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -273,6 +267,15 @@ public class AppPredictionPerUserService extends
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private void removeAppPredictionSessionInfo(AppPredictionSessionId sessionId) {
|
||||||
|
if (isDebug()) {
|
||||||
|
Slog.d(TAG, "removeAppPredictionSessionInfo(): sessionId=" + sessionId);
|
||||||
|
}
|
||||||
|
synchronized (mLock) {
|
||||||
|
mSessionInfos.remove(sessionId);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
@GuardedBy("mLock")
|
@GuardedBy("mLock")
|
||||||
@Nullable
|
@Nullable
|
||||||
private RemoteAppPredictionService getRemoteServiceLocked() {
|
private RemoteAppPredictionService getRemoteServiceLocked() {
|
||||||
@@ -295,55 +298,71 @@ public class AppPredictionPerUserService extends
|
|||||||
}
|
}
|
||||||
|
|
||||||
private static final class AppPredictionSessionInfo {
|
private static final class AppPredictionSessionInfo {
|
||||||
private final AppPredictionSessionId mSessionId;
|
private static final boolean DEBUG = false; // Do not submit with true
|
||||||
private final AppPredictionContext mContext;
|
|
||||||
private final ArrayList<IPredictionCallback> mCallbacks = new ArrayList<>();
|
|
||||||
private final IBinder.DeathRecipient mBinderDeathHandler;
|
|
||||||
|
|
||||||
AppPredictionSessionInfo(AppPredictionSessionId id, AppPredictionContext context,
|
private final AppPredictionSessionId mSessionId;
|
||||||
IBinder.DeathRecipient binderDeathHandler) {
|
private final AppPredictionContext mPredictionContext;
|
||||||
|
private final Consumer<AppPredictionSessionId> mRemoveSessionInfoAction;
|
||||||
|
|
||||||
|
private final RemoteCallbackList<IPredictionCallback> mCallbacks =
|
||||||
|
new RemoteCallbackList<IPredictionCallback>() {
|
||||||
|
@Override
|
||||||
|
public void onCallbackDied(IPredictionCallback callback) {
|
||||||
|
if (DEBUG) {
|
||||||
|
Slog.d(TAG, "Binder died for session Id=" + mSessionId
|
||||||
|
+ " and callback=" + callback.asBinder());
|
||||||
|
}
|
||||||
|
if (mCallbacks.getRegisteredCallbackCount() == 0) {
|
||||||
|
destroy();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
AppPredictionSessionInfo(AppPredictionSessionId id, AppPredictionContext predictionContext,
|
||||||
|
Consumer<AppPredictionSessionId> removeSessionInfoAction) {
|
||||||
|
if (DEBUG) {
|
||||||
|
Slog.d(TAG, "Creating AppPredictionSessionInfo for session Id=" + id);
|
||||||
|
}
|
||||||
mSessionId = id;
|
mSessionId = id;
|
||||||
mContext = context;
|
mPredictionContext = predictionContext;
|
||||||
mBinderDeathHandler = binderDeathHandler;
|
mRemoveSessionInfoAction = removeSessionInfoAction;
|
||||||
}
|
}
|
||||||
|
|
||||||
void addCallbackLocked(IPredictionCallback callback) {
|
void addCallbackLocked(IPredictionCallback callback) {
|
||||||
if (mBinderDeathHandler != null) {
|
if (DEBUG) {
|
||||||
try {
|
Slog.d(TAG, "Storing callback for session Id=" + mSessionId
|
||||||
callback.asBinder().linkToDeath(mBinderDeathHandler, 0);
|
+ " and callback=" + callback.asBinder());
|
||||||
} catch (RemoteException e) {
|
|
||||||
Slog.e(TAG, "Failed to link to death: " + e);
|
|
||||||
}
|
}
|
||||||
}
|
mCallbacks.register(callback);
|
||||||
mCallbacks.add(callback);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void removeCallbackLocked(IPredictionCallback callback) {
|
void removeCallbackLocked(IPredictionCallback callback) {
|
||||||
if (mBinderDeathHandler != null) {
|
if (DEBUG) {
|
||||||
callback.asBinder().unlinkToDeath(mBinderDeathHandler, 0);
|
Slog.d(TAG, "Removing callback for session Id=" + mSessionId
|
||||||
|
+ " and callback=" + callback.asBinder());
|
||||||
}
|
}
|
||||||
mCallbacks.remove(callback);
|
mCallbacks.unregister(callback);
|
||||||
}
|
}
|
||||||
|
|
||||||
void removeAllCallbacksLocked() {
|
void destroy() {
|
||||||
if (mBinderDeathHandler != null) {
|
if (DEBUG) {
|
||||||
for (IPredictionCallback callback : mCallbacks) {
|
Slog.d(TAG, "Removing all callbacks for session Id=" + mSessionId
|
||||||
callback.asBinder().unlinkToDeath(mBinderDeathHandler, 0);
|
+ " and " + mCallbacks.getRegisteredCallbackCount() + " callbacks.");
|
||||||
}
|
}
|
||||||
}
|
mCallbacks.kill();
|
||||||
mCallbacks.clear();
|
mRemoveSessionInfoAction.accept(mSessionId);
|
||||||
}
|
}
|
||||||
|
|
||||||
void resurrectSessionLocked(AppPredictionPerUserService service) {
|
void resurrectSessionLocked(AppPredictionPerUserService service) {
|
||||||
if (service.isDebug()) {
|
int callbackCount = mCallbacks.getRegisteredCallbackCount();
|
||||||
|
if (DEBUG) {
|
||||||
Slog.d(TAG, "Resurrecting remote service (" + service.getRemoteServiceLocked()
|
Slog.d(TAG, "Resurrecting remote service (" + service.getRemoteServiceLocked()
|
||||||
+ ") for session Id=" + mSessionId + " and "
|
+ ") for session Id=" + mSessionId + " and "
|
||||||
+ mCallbacks.size() + " callbacks.");
|
+ callbackCount + " callbacks.");
|
||||||
}
|
|
||||||
service.onCreatePredictionSessionLocked(mContext, mSessionId);
|
|
||||||
for (IPredictionCallback callback : mCallbacks) {
|
|
||||||
service.registerPredictionUpdatesLocked(mSessionId, callback);
|
|
||||||
}
|
}
|
||||||
|
service.onCreatePredictionSessionLocked(mPredictionContext, mSessionId);
|
||||||
|
mCallbacks.broadcast(
|
||||||
|
callback -> service.registerPredictionUpdatesLocked(mSessionId, callback));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user