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

Commit 9f06cf82 authored by Neil Fuller's avatar Neil Fuller Committed by Android (Google) Code Review
Browse files

Merge "Follow best practice for listener notification"

parents a36c5fe4 8e65afd5
Loading
Loading
Loading
Loading
+11 −1
Original line number Diff line number Diff line
@@ -35,7 +35,9 @@ import java.lang.annotation.Target;
import java.time.DateTimeException;
import java.time.Duration;
import java.time.Instant;
import java.util.ArrayList;
import java.util.HashSet;
import java.util.List;
import java.util.Map;
import java.util.Objects;
import java.util.Optional;
@@ -211,7 +213,11 @@ public final class ServerFlags {
    }

    private void handlePropertiesChanged(@NonNull DeviceConfig.Properties properties) {
        // Copy the listeners to notify under the "mListeners" lock but don't hold the lock while
        // delivering the notifications to avoid deadlocks.
        List<StateChangeListener> listenersToNotify;
        synchronized (mListeners) {
            listenersToNotify = new ArrayList<>(mListeners.size());
            for (Map.Entry<StateChangeListener, HashSet<String>> listenerEntry
                    : mListeners.entrySet()) {
                // It's unclear which set of the following two Sets is going to be larger in the
@@ -225,10 +231,14 @@ public final class ServerFlags {
                HashSet<String> monitoredKeys = listenerEntry.getValue();
                Iterable<String> modifiedKeys = properties.getKeyset();
                if (containsAny(monitoredKeys, modifiedKeys)) {
                    listenerEntry.getKey().onChange();
                    listenersToNotify.add(listenerEntry.getKey());
                }
            }
        }

        for (StateChangeListener listener : listenersToNotify) {
            listener.onChange();
        }
    }

    private static boolean containsAny(
+8 −2
Original line number Diff line number Diff line
@@ -166,8 +166,14 @@ final class ServiceConfigAccessorImpl implements ServiceConfigAccessor {
        }
    }

    private synchronized void handleConfigurationInternalChangeOnMainThread() {
        for (StateChangeListener changeListener : mConfigurationInternalListeners) {
    private void handleConfigurationInternalChangeOnMainThread() {
        // Copy the listeners holding the "this" lock but don't hold the lock while delivering the
        // notifications to avoid deadlocks.
        List<StateChangeListener> configurationInternalListeners;
        synchronized (this) {
            configurationInternalListeners = new ArrayList<>(this.mConfigurationInternalListeners);
        }
        for (StateChangeListener changeListener : configurationInternalListeners) {
            changeListener.onChange();
        }
    }
+2 −0
Original line number Diff line number Diff line
@@ -266,6 +266,8 @@ public final class TimeDetectorService extends ITimeDetectorService.Stub
            for (int listenerIndex = 0; listenerIndex < listenerCount; listenerIndex++) {
                ITimeDetectorListener listener = mListeners.valueAt(listenerIndex);
                try {
                    // No need to surrender the mListeners lock while doing this:
                    // ITimeDetectorListener is declared "oneway".
                    listener.onChange();
                } catch (RemoteException e) {
                    Slog.w(TAG, "Unable to notify listener=" + listener, e);
+8 −2
Original line number Diff line number Diff line
@@ -77,12 +77,18 @@ class DeviceActivityMonitorImpl implements DeviceActivityMonitor {
        mListeners.add(listener);
    }

    private synchronized void notifyFlightComplete() {
    private void notifyFlightComplete() {
        if (DBG) {
            Slog.d(LOG_TAG, "notifyFlightComplete");
        }

        for (Listener listener : mListeners) {
        // Copy the listeners holding the "this" lock but don't hold the lock while delivering the
        // notifications to avoid deadlocks.
        List<Listener> listeners;
        synchronized (this) {
            listeners = new ArrayList<>(mListeners);
        }
        for (Listener listener : listeners) {
            listener.onFlightComplete();
        }
    }
+8 −2
Original line number Diff line number Diff line
@@ -205,8 +205,14 @@ public final class ServiceConfigAccessorImpl implements ServiceConfigAccessor {
        }
    }

    private synchronized void handleConfigurationInternalChangeOnMainThread() {
        for (StateChangeListener changeListener : mConfigurationInternalListeners) {
    private void handleConfigurationInternalChangeOnMainThread() {
        // Copy the listeners holding the "this" lock but don't hold the lock while delivering the
        // notifications to avoid deadlocks.
        List<StateChangeListener> configurationInternalListeners;
        synchronized (this) {
            configurationInternalListeners = new ArrayList<>(this.mConfigurationInternalListeners);
        }
        for (StateChangeListener changeListener : configurationInternalListeners) {
            changeListener.onChange();
        }
    }
Loading