1 /*
2 **
3 ** Copyright 2014, The Android Open Source Project
4 **
5 ** Licensed under the Apache License, Version 2.0 (the "License");
6 ** you may not use this file except in compliance with the License.
7 ** You may obtain a copy of the License at
8 **
9 **     http://www.apache.org/licenses/LICENSE-2.0
10 **
11 ** Unless required by applicable law or agreed to in writing, software
12 ** distributed under the License is distributed on an "AS IS" BASIS,
13 ** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14 ** See the License for the specific language governing permissions and
15 ** limitations under the License.
16 */
17 
18 #ifndef ANDROID_AUDIO_HARDWARE_OUTPUT_H
19 #define ANDROID_AUDIO_HARDWARE_OUTPUT_H
20 
21 #include <stdint.h>
22 #include <sys/types.h>
23 
24 #include <hardware/audio.h>
25 #include <utils/String8.h>
26 #include <utils/threads.h>
27 
28 #include "alsa_utils.h"
29 #include "AudioOutput.h"
30 
31 namespace android {
32 
33 class AudioStreamOut;
34 class AudioOutput;
35 
36 class AudioHardwareOutput {
37   public:
38                 AudioHardwareOutput();
39     virtual    ~AudioHardwareOutput();
40     status_t    initCheck();
41     status_t    setMasterVolume(float volume);
42     status_t    getMasterVolume(float* volume);
43     status_t    setMasterMute(bool mute);
44     status_t    getMasterMute(bool* mute);
45     status_t    setParameters(const char* kvpairs);
46     char*       getParameters(const char* keys);
47     status_t    dump(int fd);
48     void        updateRouting(uint32_t devMask);
getMaxDelayCompUsec()49     uint32_t    getMaxDelayCompUsec() const { return mMaxDelayCompUsec; }
getVideoDelayCompUsec()50     uint32_t    getVideoDelayCompUsec() const {
51         return mSettings.videoDelayCompUsec;
52     }
getHDMIAudioCaps()53     HDMIAudioCaps& getHDMIAudioCaps() { return mHDMIAudioCaps; }
54 
55     // Interface to allow streams to obtain and release various physical
56     // outputs.
57     status_t       obtainOutput(const AudioStreamOut& tgtStream,
58                              uint32_t devMask,
59                              sp<AudioOutput>* newOutput);
60     void           releaseOutput(const AudioStreamOut& tgtStream,
61                               const sp<AudioOutput>& releaseMe);
62 
63 
64     // create I/O streams
65     AudioStreamOut* openOutputStream(uint32_t  devices,
66                                      audio_format_t *format,
67                                      uint32_t *channels,
68                                      uint32_t *sampleRate,
69                                      audio_output_flags_t flags,
70                                      status_t *status);
71     void           closeOutputStream(AudioStreamOut* out);
72 
73     void           standbyStatusUpdate(bool isInStandby, bool isMCStream);
74 
75   private:
76     struct OutputSettings {
77         bool        allowed;
78         uint32_t    delayCompUsec;
79         bool        isFixed;
80         float       fixedLvl;
81         void        setDefaults();
82     };
83 
84     struct Settings {
85         OutputSettings hdmi;
86         uint32_t       videoDelayCompUsec;
87         float          masterVolume;
88         bool           masterMute;
89         void           setDefaults();
90     };
91 
92     void     updateTgtDevices_l();
93     bool     applyOutputSettings_l(const OutputSettings& initial,
94                                    const OutputSettings& current,
95                                    OutputSettings& updateMe,
96                                    uint32_t outDevMask);
97 
98     // Notes on locking:
99     // There are 3 locks in the AudioHardware class; mStreamLock, mOutputLock
100     // and mSettingsLock.
101     //
102     // mStreamLock is held when interacting with AudioStreamOuts, in particular
103     // during creation and destruction of streams, and during routing changes
104     // (HDMI connecting and disconnecting) which (potentially) end up effecting
105     // the target device masks of the output streams.
106     //
107     // mOutputLock is held while interacting with AudioOutputs (which represent
108     // the physical outputs of the system).  AudioStreamOuts grab this lock
109     // during calls to (obtain|release)Output which can trigger instantiation
110     // and destruction of AudioOutputs.  During this operation, the
111     // AudioStreamOut instance will be holding its own "routing" lock.  Care
112     // should be taken to never hold the output lock or setting lock while making
113     // a call into an AudioStreamOut which may obtain the routing lock.
114     // Currently, the set of publicly accessible calls in AudioStreamOut which
115     // may obtain the routing lock are...
116     // 1) ~AudioStreamOut (calls releaseAllOutputs)
117     // 2) standby (calls releaseAllOutputs)
118     // 3) setTgtDevices
119     //
120     // mSettingsLock is held while reading settings and while writing/applying
121     // settings to existing outputs.  Lock ordering is important when applying
122     // settings to outputs as the both the output and settings lock need to be
123     // held at the same time.  Whenever settings need to be applied to outputs,
124     // the output lock should always obtained first, followed by the settings
125     // lock.
126 
127     Mutex            mStreamLock;
128     AudioStreamOut  *mMainOutput;
129     AudioStreamOut  *mMCOutput;
130     bool             mHDMIConnected;
131 
132     Mutex            mOutputLock;
133     AudioOutputList  mPhysOutputs;
134 
135     Mutex            mSettingsLock;
136     Settings         mSettings;
137     uint32_t         mMaxDelayCompUsec;
138 
139     HDMIAudioCaps    mHDMIAudioCaps;
140     int              mHDMICardID;
141 
142     static const String8 kHDMIAllowedParamKey;
143     static const String8 kHDMIDelayCompParamKey;
144     static const String8 kFixedHDMIOutputParamKey;
145     static const String8 kFixedHDMIOutputLevelParamKey;
146     static const String8 kVideoDelayCompParamKey;
147     static const float   kDefaultMasterVol;
148 
149 };
150 
151 // ----------------------------------------------------------------------------
152 
153 }; // namespace android
154 
155 #endif  // ANDROID_AUDIO_HARDWARE_OUTPUT_H
156