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

Commit 8288bc22 authored by lijilou's avatar lijilou Committed by Jilou li
Browse files

TintController: add lock to fix NPE problem.

This problem is caused by concurrent operations of the mIsActivated object by threads, such as the following situation:
1 Binder call or Background thread. In CDS service, binder all the isReduceBrightColorsActivated method and call the isActivated method.

2 Display thread. The call chain onUserChanged -> tearDown -> setActivated(null).

Test: OEM monkey test
Flag: EXEMPT bugfix
Bug: 377834826
Change-Id: Id48e7986a98ec81769e587344b19ef7e509db0e4
parent bf13e461
Loading
Loading
Loading
Loading
+29 −10
Original line number Diff line number Diff line
@@ -19,6 +19,7 @@ package com.android.server.display.color;
import android.animation.ValueAnimator;
import android.content.Context;
import android.util.Slog;
import com.android.internal.annotations.GuardedBy;

import java.io.PrintWriter;

@@ -29,47 +30,65 @@ abstract class TintController {
     */
    private static final long TRANSITION_DURATION = 3000L;

    private final Object mLock = new Object();

    @GuardedBy("mLock")
    private ValueAnimator mAnimator;
    @GuardedBy("mLock")
    private Boolean mIsActivated;

    public ValueAnimator getAnimator() {
        synchronized (mLock) {
            return mAnimator;
        }
    }

    public void setAnimator(ValueAnimator animator) {
        synchronized (mLock) {
            mAnimator = animator;
        }
    }

    /**
     * Cancel the animator if it's still running.
     */
    public void cancelAnimator() {
        synchronized (mLock) {
            if (mAnimator != null) {
                mAnimator.cancel();
            }
        }
    }

    /**
     * End the animator if it's still running, jumping to the end state.
     */
    public void endAnimator() {
        synchronized (mLock) {
            if (mAnimator != null) {
                mAnimator.end();
                mAnimator = null;
            }
        }
    }

    public void setActivated(Boolean isActivated) {
        synchronized (mLock) {
            mIsActivated = isActivated;
        }
    }

    public boolean isActivated() {
        synchronized (mLock) {
            return mIsActivated != null && mIsActivated;
        }
    }

    public boolean isActivatedStateNotSet() {
        synchronized (mLock) {
            return mIsActivated == null;
        }
    }

    public long getTransitionDurationMilliseconds() {
        return TRANSITION_DURATION;