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

Commit b64c10bc authored by TreeHugger Robot's avatar TreeHugger Robot Committed by Android (Google) Code Review
Browse files

Merge "AudioPolicy: add synchronous unregister method"

parents ef266140 cada3722
Loading
Loading
Loading
Loading
+1 −0
Original line number Diff line number Diff line
@@ -3487,6 +3487,7 @@ package android.media {
    method public void setAudioServerStateCallback(@NonNull java.util.concurrent.Executor, @NonNull android.media.AudioManager.AudioServerStateCallback);
    method @RequiresPermission(android.Manifest.permission.MODIFY_AUDIO_ROUTING) public void setFocusRequestResult(@NonNull android.media.AudioFocusInfo, int, @NonNull android.media.audiopolicy.AudioPolicy);
    method @RequiresPermission(android.Manifest.permission.MODIFY_AUDIO_ROUTING) public void setVolumeIndexForAttributes(@NonNull android.media.AudioAttributes, int, int);
    method @RequiresPermission(android.Manifest.permission.MODIFY_AUDIO_ROUTING) public void unregisterAudioPolicy(@NonNull android.media.audiopolicy.AudioPolicy);
    method @RequiresPermission(android.Manifest.permission.MODIFY_AUDIO_ROUTING) public void unregisterAudioPolicyAsync(@NonNull android.media.audiopolicy.AudioPolicy);
    method public void unregisterVolumeGroupCallback(@NonNull android.media.AudioManager.VolumeGroupCallback);
    field public static final int AUDIOFOCUS_FLAG_DELAY_OK = 1; // 0x1
+22 −0
Original line number Diff line number Diff line
@@ -3308,6 +3308,7 @@ public class AudioManager {

    /**
     * @hide
     * Unregisters an {@link AudioPolicy} asynchronously.
     * @param policy the non-null {@link AudioPolicy} to unregister.
     */
    @SystemApi
@@ -3329,6 +3330,27 @@ public class AudioManager {
        }
    }

    /**
     * @hide
     * Unregisters an {@link AudioPolicy} synchronously.
     * This method also invalidates all {@link AudioRecord} and {@link AudioTrack} objects
     * associated with mixes of this policy.
     * @param policy the non-null {@link AudioPolicy} to unregister.
     */
    @SystemApi
    @RequiresPermission(android.Manifest.permission.MODIFY_AUDIO_ROUTING)
    public void unregisterAudioPolicy(@NonNull AudioPolicy policy) {
        Preconditions.checkNotNull(policy, "Illegal null AudioPolicy argument");
        final IAudioService service = getService();
        try {
            policy.invalidateCaptorsAndInjectors();
            service.unregisterAudioPolicy(policy.cb());
            policy.setRegistration(null);
        } catch (RemoteException e) {
            throw e.rethrowFromSystemServer();
        }
    }

    //====================================================================
    // Notification of playback activity & playback configuration
    /**
+2 −0
Original line number Diff line number Diff line
@@ -199,6 +199,8 @@ interface IAudioService {

    oneway void unregisterAudioPolicyAsync(in IAudioPolicyCallback pcb);

    void unregisterAudioPolicy(in IAudioPolicyCallback pcb);

    int addMixForPolicy(in AudioPolicyConfig policyConfig, in IAudioPolicyCallback pcb);

    int removeMixForPolicy(in AudioPolicyConfig policyConfig, in IAudioPolicyCallback pcb);
+60 −0
Original line number Diff line number Diff line
@@ -43,8 +43,11 @@ import android.os.ServiceManager;
import android.util.Log;
import android.util.Slog;

import com.android.internal.annotations.GuardedBy;

import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
import java.lang.ref.WeakReference;
import java.util.ArrayList;
import java.util.List;

@@ -73,6 +76,19 @@ public class AudioPolicy {
    private AudioPolicyStatusListener mStatusListener;
    private boolean mIsFocusPolicy;

    /**
     * The list of AudioTrack instances created to inject audio into the associated mixes
     * Lazy initialization in {@link #createAudioTrackSource(AudioMix)}
     */
    @GuardedBy("mLock")
    @Nullable private ArrayList<WeakReference<AudioTrack>> mInjectors;
    /**
     * The list AudioRecord instances created to capture audio from the associated mixes
     * Lazy initialization in {@link #createAudioRecordSink(AudioMix)}
     */
    @GuardedBy("mLock")
    @Nullable private ArrayList<WeakReference<AudioRecord>> mCaptors;

    /**
     * The behavior of a policy with regards to audio focus where it relies on the application
     * to do the ducking, the is the legacy and default behavior.
@@ -606,6 +622,12 @@ public class AudioPolicy {
                        AudioFormat.CHANNEL_IN_STEREO, mix.getFormat().getEncoding()),
                AudioManager.AUDIO_SESSION_ID_GENERATE
                );
        synchronized (mLock) {
            if (mCaptors == null) {
                mCaptors = new ArrayList<>(1);
            }
            mCaptors.add(new WeakReference<AudioRecord>(ar));
        }
        return ar;
    }

@@ -638,9 +660,47 @@ public class AudioPolicy {
                AudioTrack.MODE_STREAM,
                AudioManager.AUDIO_SESSION_ID_GENERATE
                );
        synchronized (mLock) {
            if (mInjectors == null) {
                mInjectors = new ArrayList<>(1);
            }
            mInjectors.add(new WeakReference<AudioTrack>(at));
        }
        return at;
    }

    /**
     * @hide
     */
    public void invalidateCaptorsAndInjectors() {
        if (!policyReadyToUse()) {
            return;
        }
        synchronized (mLock) {
            if (mInjectors != null) {
                for (final WeakReference<AudioTrack> weakTrack : mInjectors) {
                    final AudioTrack track = weakTrack.get();
                    if (track == null) {
                        break;
                    }
                    // TODO: add synchronous versions
                    track.stop();
                    track.flush();
                }
            }
            if (mCaptors != null) {
                for (final WeakReference<AudioRecord> weakRecord : mCaptors) {
                    final AudioRecord record = weakRecord.get();
                    if (record == null) {
                        break;
                    }
                    // TODO: if needed: implement an invalidate method
                    record.stop();
                }
            }
        }
    }

    public int getStatus() {
        return mStatus;
    }
+22 −1
Original line number Diff line number Diff line
@@ -6387,7 +6387,28 @@ public class AudioService extends IAudioService.Stub
        return mProjectionService;
    }

    public void unregisterAudioPolicyAsync(IAudioPolicyCallback pcb) {
    /**
     * See {@link AudioManager#unregisterAudioPolicyAsync(AudioPolicy)}
     * Declared oneway
     * @param pcb nullable because on service interface
     */
    public void unregisterAudioPolicyAsync(@Nullable IAudioPolicyCallback pcb) {
        unregisterAudioPolicy(pcb);
    }

    /**
     * See {@link AudioManager#unregisterAudioPolicy(AudioPolicy)}
     * @param pcb nullable because on service interface
     */
    public void unregisterAudioPolicy(@Nullable IAudioPolicyCallback pcb) {
        if (pcb == null) {
            return;
        }
        unregisterAudioPolicyInt(pcb);
    }


    private void unregisterAudioPolicyInt(@NonNull IAudioPolicyCallback pcb) {
        mDynPolicyLogger.log((new AudioEventLogger.StringEvent("unregisterAudioPolicyAsync for "
                + pcb.asBinder()).printLog(TAG)));
        synchronized (mAudioPolicies) {