xref: /aosp_15_r20/frameworks/av/services/audioflinger/fastpath/FastMixer.h (revision ec779b8e0859a360c3d303172224686826e6e0e1)
1*ec779b8eSAndroid Build Coastguard Worker /*
2*ec779b8eSAndroid Build Coastguard Worker  * Copyright (C) 2012 The Android Open Source Project
3*ec779b8eSAndroid Build Coastguard Worker  *
4*ec779b8eSAndroid Build Coastguard Worker  * Licensed under the Apache License, Version 2.0 (the "License");
5*ec779b8eSAndroid Build Coastguard Worker  * you may not use this file except in compliance with the License.
6*ec779b8eSAndroid Build Coastguard Worker  * You may obtain a copy of the License at
7*ec779b8eSAndroid Build Coastguard Worker  *
8*ec779b8eSAndroid Build Coastguard Worker  *      http://www.apache.org/licenses/LICENSE-2.0
9*ec779b8eSAndroid Build Coastguard Worker  *
10*ec779b8eSAndroid Build Coastguard Worker  * Unless required by applicable law or agreed to in writing, software
11*ec779b8eSAndroid Build Coastguard Worker  * distributed under the License is distributed on an "AS IS" BASIS,
12*ec779b8eSAndroid Build Coastguard Worker  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13*ec779b8eSAndroid Build Coastguard Worker  * See the License for the specific language governing permissions and
14*ec779b8eSAndroid Build Coastguard Worker  * limitations under the License.
15*ec779b8eSAndroid Build Coastguard Worker  */
16*ec779b8eSAndroid Build Coastguard Worker 
17*ec779b8eSAndroid Build Coastguard Worker #pragma once
18*ec779b8eSAndroid Build Coastguard Worker 
19*ec779b8eSAndroid Build Coastguard Worker #include <atomic>
20*ec779b8eSAndroid Build Coastguard Worker #include <audio_utils/Balance.h>
21*ec779b8eSAndroid Build Coastguard Worker #include "FastThread.h"
22*ec779b8eSAndroid Build Coastguard Worker #include "StateQueue.h"
23*ec779b8eSAndroid Build Coastguard Worker #include "FastMixerState.h"
24*ec779b8eSAndroid Build Coastguard Worker #include "FastMixerDumpState.h"
25*ec779b8eSAndroid Build Coastguard Worker #include <afutils/NBAIO_Tee.h>
26*ec779b8eSAndroid Build Coastguard Worker 
27*ec779b8eSAndroid Build Coastguard Worker namespace android {
28*ec779b8eSAndroid Build Coastguard Worker 
29*ec779b8eSAndroid Build Coastguard Worker class AudioMixer;
30*ec779b8eSAndroid Build Coastguard Worker 
31*ec779b8eSAndroid Build Coastguard Worker using FastMixerStateQueue = StateQueue<FastMixerState>;
32*ec779b8eSAndroid Build Coastguard Worker 
33*ec779b8eSAndroid Build Coastguard Worker class FastMixer : public FastThread {
34*ec779b8eSAndroid Build Coastguard Worker 
35*ec779b8eSAndroid Build Coastguard Worker public:
36*ec779b8eSAndroid Build Coastguard Worker     /** FastMixer constructor takes as param the parent MixerThread's io handle (id)
37*ec779b8eSAndroid Build Coastguard Worker         for purposes of identification. */
38*ec779b8eSAndroid Build Coastguard Worker     explicit FastMixer(audio_io_handle_t threadIoHandle);
39*ec779b8eSAndroid Build Coastguard Worker 
40*ec779b8eSAndroid Build Coastguard Worker             FastMixerStateQueue* sq();
41*ec779b8eSAndroid Build Coastguard Worker 
setMasterMono(bool mono)42*ec779b8eSAndroid Build Coastguard Worker     virtual void setMasterMono(bool mono) { mMasterMono.store(mono); /* memory_order_seq_cst */ }
setMasterBalance(float balance)43*ec779b8eSAndroid Build Coastguard Worker     virtual void setMasterBalance(float balance) { mMasterBalance.store(balance); }
getMasterBalance()44*ec779b8eSAndroid Build Coastguard Worker     virtual float getMasterBalance() const { return mMasterBalance.load(); }
setBoottimeOffset(int64_t boottimeOffset)45*ec779b8eSAndroid Build Coastguard Worker     virtual void setBoottimeOffset(int64_t boottimeOffset) {
46*ec779b8eSAndroid Build Coastguard Worker         mBoottimeOffset.store(boottimeOffset); /* memory_order_seq_cst */
47*ec779b8eSAndroid Build Coastguard Worker     }
48*ec779b8eSAndroid Build Coastguard Worker private:
49*ec779b8eSAndroid Build Coastguard Worker             FastMixerStateQueue mSQ;
50*ec779b8eSAndroid Build Coastguard Worker 
51*ec779b8eSAndroid Build Coastguard Worker     // callouts
52*ec779b8eSAndroid Build Coastguard Worker     const FastThreadState *poll() override;
53*ec779b8eSAndroid Build Coastguard Worker     void setNBLogWriter(NBLog::Writer *logWriter) override;
54*ec779b8eSAndroid Build Coastguard Worker     void onIdle() override;
55*ec779b8eSAndroid Build Coastguard Worker     void onExit() override;
56*ec779b8eSAndroid Build Coastguard Worker     bool isSubClassCommand(FastThreadState::Command command) override;
57*ec779b8eSAndroid Build Coastguard Worker     void onStateChange() override;
58*ec779b8eSAndroid Build Coastguard Worker     void onWork() override;
59*ec779b8eSAndroid Build Coastguard Worker 
60*ec779b8eSAndroid Build Coastguard Worker     enum Reason {
61*ec779b8eSAndroid Build Coastguard Worker         REASON_REMOVE,
62*ec779b8eSAndroid Build Coastguard Worker         REASON_ADD,
63*ec779b8eSAndroid Build Coastguard Worker         REASON_MODIFY,
64*ec779b8eSAndroid Build Coastguard Worker     };
65*ec779b8eSAndroid Build Coastguard Worker     // called when a fast track of index has been removed, added, or modified
66*ec779b8eSAndroid Build Coastguard Worker     void updateMixerTrack(int index, Reason reason);
67*ec779b8eSAndroid Build Coastguard Worker 
68*ec779b8eSAndroid Build Coastguard Worker     // FIXME these former local variables need comments
69*ec779b8eSAndroid Build Coastguard Worker     static const FastMixerState sInitial;
70*ec779b8eSAndroid Build Coastguard Worker 
71*ec779b8eSAndroid Build Coastguard Worker     FastMixerState  mPreIdle;   // copy of state before we went into idle
72*ec779b8eSAndroid Build Coastguard Worker     int             mGenerations[FastMixerState::kMaxFastTracks]{};
73*ec779b8eSAndroid Build Coastguard Worker                                 // last observed mFastTracks[i].mGeneration
74*ec779b8eSAndroid Build Coastguard Worker     NBAIO_Sink*     mOutputSink = nullptr;
75*ec779b8eSAndroid Build Coastguard Worker     int             mOutputSinkGen = 0;
76*ec779b8eSAndroid Build Coastguard Worker     AudioMixer*     mMixer = nullptr;
77*ec779b8eSAndroid Build Coastguard Worker 
78*ec779b8eSAndroid Build Coastguard Worker     // mSinkBuffer audio format is stored in format.mFormat.
79*ec779b8eSAndroid Build Coastguard Worker     void*           mSinkBuffer = nullptr; // used for mixer output format translation
80*ec779b8eSAndroid Build Coastguard Worker                                         // if sink format is different than mixer output.
81*ec779b8eSAndroid Build Coastguard Worker     size_t          mSinkBufferSize = 0;
82*ec779b8eSAndroid Build Coastguard Worker     uint32_t        mSinkChannelCount = FCC_2;
83*ec779b8eSAndroid Build Coastguard Worker     audio_channel_mask_t mSinkChannelMask;        // set in ctor
84*ec779b8eSAndroid Build Coastguard Worker     void*           mMixerBuffer = nullptr;       // mixer output buffer.
85*ec779b8eSAndroid Build Coastguard Worker     size_t          mMixerBufferSize = 0;
86*ec779b8eSAndroid Build Coastguard Worker     static constexpr audio_format_t mMixerBufferFormat = AUDIO_FORMAT_PCM_FLOAT;
87*ec779b8eSAndroid Build Coastguard Worker 
88*ec779b8eSAndroid Build Coastguard Worker     // audio channel count, excludes haptic channels.  Set in onStateChange().
89*ec779b8eSAndroid Build Coastguard Worker     uint32_t        mAudioChannelCount = 0;
90*ec779b8eSAndroid Build Coastguard Worker 
91*ec779b8eSAndroid Build Coastguard Worker     enum {UNDEFINED, MIXED, ZEROED} mMixerBufferState = UNDEFINED;
92*ec779b8eSAndroid Build Coastguard Worker     NBAIO_Format    mFormat{Format_Invalid};
93*ec779b8eSAndroid Build Coastguard Worker     unsigned        mSampleRate = 0;
94*ec779b8eSAndroid Build Coastguard Worker     int             mFastTracksGen = 0;
95*ec779b8eSAndroid Build Coastguard Worker     FastMixerDumpState mDummyFastMixerDumpState;
96*ec779b8eSAndroid Build Coastguard Worker     int64_t         mTotalNativeFramesWritten = 0;  // copied to dumpState->mFramesWritten
97*ec779b8eSAndroid Build Coastguard Worker 
98*ec779b8eSAndroid Build Coastguard Worker     // next 2 fields are valid only when timestampStatus == NO_ERROR
99*ec779b8eSAndroid Build Coastguard Worker     ExtendedTimestamp mTimestamp;
100*ec779b8eSAndroid Build Coastguard Worker     int64_t         mNativeFramesWrittenButNotPresented = 0;
101*ec779b8eSAndroid Build Coastguard Worker 
102*ec779b8eSAndroid Build Coastguard Worker     audio_utils::Balance mBalance;
103*ec779b8eSAndroid Build Coastguard Worker 
104*ec779b8eSAndroid Build Coastguard Worker     // accessed without lock between multiple threads.
105*ec779b8eSAndroid Build Coastguard Worker     std::atomic_bool mMasterMono{};
106*ec779b8eSAndroid Build Coastguard Worker     std::atomic<float> mMasterBalance{};
107*ec779b8eSAndroid Build Coastguard Worker     std::atomic_int_fast64_t mBoottimeOffset{};
108*ec779b8eSAndroid Build Coastguard Worker 
109*ec779b8eSAndroid Build Coastguard Worker     // parent thread id for debugging purposes
110*ec779b8eSAndroid Build Coastguard Worker     [[maybe_unused]] const audio_io_handle_t mThreadIoHandle;
111*ec779b8eSAndroid Build Coastguard Worker #ifdef TEE_SINK
112*ec779b8eSAndroid Build Coastguard Worker     NBAIO_Tee       mTee;
113*ec779b8eSAndroid Build Coastguard Worker #endif
114*ec779b8eSAndroid Build Coastguard Worker };  // class FastMixer
115*ec779b8eSAndroid Build Coastguard Worker 
116*ec779b8eSAndroid Build Coastguard Worker }   // namespace android
117