blob: d9f7b49cab081644a3579ed7257e7beee7854350 [file] [log] [blame]
The Android Open Source Project7c1b96a2008-10-21 07:00:00 -07001/* //device/include/server/AudioFlinger/AudioFlinger.h
2**
3** Copyright 2007, 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_FLINGER_H
19#define ANDROID_AUDIO_FLINGER_H
20
21#include <stdint.h>
22#include <sys/types.h>
23
24#include <media/IAudioFlinger.h>
25#include <media/IAudioTrack.h>
26#include <media/IAudioRecord.h>
27#include <media/AudioTrack.h>
28
29#include <utils/Atomic.h>
30#include <utils/Errors.h>
31#include <utils/threads.h>
32#include <utils/MemoryDealer.h>
33#include <utils/KeyedVector.h>
34#include <utils/SortedVector.h>
35
36#include <hardware/AudioHardwareInterface.h>
37
38#include "AudioBufferProvider.h"
39
40namespace android {
41
42class audio_track_cblk_t;
43class AudioMixer;
44class AudioBuffer;
45
The Android Open Source Projecte09fd9e2008-12-17 18:05:43 -080046
The Android Open Source Project7c1b96a2008-10-21 07:00:00 -070047// ----------------------------------------------------------------------------
48
49#define LIKELY( exp ) (__builtin_expect( (exp) != 0, true ))
50#define UNLIKELY( exp ) (__builtin_expect( (exp) != 0, false ))
51
The Android Open Source Projecte09fd9e2008-12-17 18:05:43 -080052
The Android Open Source Project7c1b96a2008-10-21 07:00:00 -070053// ----------------------------------------------------------------------------
54
The Android Open Source Projecte09fd9e2008-12-17 18:05:43 -080055static const nsecs_t kStandbyTimeInNsecs = seconds(3);
56
The Android Open Source Project7c1b96a2008-10-21 07:00:00 -070057class AudioFlinger : public BnAudioFlinger, protected Thread
58{
59public:
60 static void instantiate();
61
62 virtual status_t dump(int fd, const Vector<String16>& args);
63
64 // Thread virtuals
65 virtual bool threadLoop();
66 virtual status_t readyToRun();
67 virtual void onFirstRef();
68
69 // IAudioFlinger interface
70 virtual sp<IAudioTrack> createTrack(
71 pid_t pid,
72 int streamType,
73 uint32_t sampleRate,
74 int format,
75 int channelCount,
The Android Open Source Projecte09fd9e2008-12-17 18:05:43 -080076 int frameCount,
77 uint32_t flags,
78 const sp<IMemory>& sharedBuffer,
79 status_t *status);
The Android Open Source Project7c1b96a2008-10-21 07:00:00 -070080
81 virtual uint32_t sampleRate() const;
82 virtual int channelCount() const;
83 virtual int format() const;
84 virtual size_t frameCount() const;
The Android Open Source Projecte09fd9e2008-12-17 18:05:43 -080085 virtual size_t latency() const;
The Android Open Source Project7c1b96a2008-10-21 07:00:00 -070086
87 virtual status_t setMasterVolume(float value);
88 virtual status_t setMasterMute(bool muted);
89
90 virtual float masterVolume() const;
91 virtual bool masterMute() const;
92
93 virtual status_t setStreamVolume(int stream, float value);
94 virtual status_t setStreamMute(int stream, bool muted);
95
96 virtual float streamVolume(int stream) const;
97 virtual bool streamMute(int stream) const;
98
99 virtual status_t setRouting(int mode, uint32_t routes, uint32_t mask);
100 virtual uint32_t getRouting(int mode) const;
101
102 virtual status_t setMode(int mode);
103 virtual int getMode() const;
104
105 virtual status_t setMicMute(bool state);
106 virtual bool getMicMute() const;
107
108 virtual bool isMusicActive() const;
109
110 virtual status_t setParameter(const char* key, const char* value);
111
112 enum hardware_call_state {
113 AUDIO_HW_IDLE = 0,
114 AUDIO_HW_INIT,
115 AUDIO_HW_OUTPUT_OPEN,
116 AUDIO_HW_OUTPUT_CLOSE,
117 AUDIO_HW_INPUT_OPEN,
118 AUDIO_HW_INPUT_CLOSE,
119 AUDIO_HW_STANDBY,
120 AUDIO_HW_SET_MASTER_VOLUME,
121 AUDIO_HW_GET_ROUTING,
122 AUDIO_HW_SET_ROUTING,
123 AUDIO_HW_GET_MODE,
124 AUDIO_HW_SET_MODE,
125 AUDIO_HW_GET_MIC_MUTE,
126 AUDIO_HW_SET_MIC_MUTE,
127 AUDIO_SET_VOICE_VOLUME,
128 AUDIO_SET_PARAMETER,
129 };
130
131 // record interface
132 virtual sp<IAudioRecord> openRecord(
133 pid_t pid,
134 int streamType,
135 uint32_t sampleRate,
136 int format,
137 int channelCount,
The Android Open Source Projecte09fd9e2008-12-17 18:05:43 -0800138 int frameCount,
139 uint32_t flags,
140 status_t *status);
The Android Open Source Project7c1b96a2008-10-21 07:00:00 -0700141
142 virtual status_t onTransact(
143 uint32_t code,
144 const Parcel& data,
145 Parcel* reply,
146 uint32_t flags);
147
148private:
149 AudioFlinger();
150 virtual ~AudioFlinger();
151
The Android Open Source Projecte09fd9e2008-12-17 18:05:43 -0800152 void setOutput(AudioStreamOut* output);
153 size_t getOutputFrameCount(AudioStreamOut* output);
154
The Android Open Source Project7c1b96a2008-10-21 07:00:00 -0700155 // Internal dump utilites.
156 status_t dumpPermissionDenial(int fd, const Vector<String16>& args);
157 status_t dumpClients(int fd, const Vector<String16>& args);
158 status_t dumpTracks(int fd, const Vector<String16>& args);
159 status_t dumpInternals(int fd, const Vector<String16>& args);
The Android Open Source Projecte09fd9e2008-12-17 18:05:43 -0800160
The Android Open Source Project7c1b96a2008-10-21 07:00:00 -0700161 // --- Client ---
162 class Client : public RefBase {
163 public:
164 Client(const sp<AudioFlinger>& audioFlinger, pid_t pid);
165 virtual ~Client();
166 const sp<MemoryDealer>& heap() const;
167 pid_t pid() const { return mPid; }
168 private:
169 Client(const Client&);
170 Client& operator = (const Client&);
171 sp<AudioFlinger> mAudioFlinger;
172 sp<MemoryDealer> mMemoryDealer;
173 pid_t mPid;
174 };
175
176
177 // --- Track ---
178 class TrackHandle;
179 class RecordHandle;
180 class AudioRecordThread;
181
182 // base for record and playback
183 class TrackBase : public AudioBufferProvider, public RefBase {
184
185 public:
186 enum track_state {
187 IDLE,
188 TERMINATED,
189 STOPPED,
190 RESUMING,
191 ACTIVE,
192 PAUSING,
193 PAUSED
194 };
195
196 enum track_flags {
The Android Open Source Projecte09fd9e2008-12-17 18:05:43 -0800197 STEPSERVER_FAILED = 0x01 // StepServer could not acquire cblk->lock mutex
The Android Open Source Project7c1b96a2008-10-21 07:00:00 -0700198 };
The Android Open Source Projecte09fd9e2008-12-17 18:05:43 -0800199
The Android Open Source Project7c1b96a2008-10-21 07:00:00 -0700200 TrackBase( const sp<AudioFlinger>& audioFlinger,
201 const sp<Client>& client,
202 int streamType,
203 uint32_t sampleRate,
204 int format,
205 int channelCount,
The Android Open Source Projecte09fd9e2008-12-17 18:05:43 -0800206 int frameCount,
207 const sp<IMemory>& sharedBuffer);
The Android Open Source Project7c1b96a2008-10-21 07:00:00 -0700208 ~TrackBase();
209
210 virtual status_t start() = 0;
211 virtual void stop() = 0;
212 sp<IMemory> getCblk() const;
213
214 protected:
215 friend class AudioFlinger;
216 friend class RecordHandle;
The Android Open Source Projecte09fd9e2008-12-17 18:05:43 -0800217 friend class AudioRecordThread;
The Android Open Source Project7c1b96a2008-10-21 07:00:00 -0700218
219 TrackBase(const TrackBase&);
220 TrackBase& operator = (const TrackBase&);
221
222 virtual status_t getNextBuffer(AudioBufferProvider::Buffer* buffer) = 0;
223 virtual void releaseBuffer(AudioBufferProvider::Buffer* buffer);
224
225 audio_track_cblk_t* cblk() const {
226 return mCblk;
227 }
228
229 int type() const {
230 return mStreamType;
231 }
232
233 int format() const {
234 return mFormat;
235 }
236
The Android Open Source Projecte09fd9e2008-12-17 18:05:43 -0800237 int channelCount() const ;
The Android Open Source Project7c1b96a2008-10-21 07:00:00 -0700238
239 int sampleRate() const;
240
The Android Open Source Projecte09fd9e2008-12-17 18:05:43 -0800241 void* getBuffer(uint32_t offset, uint32_t frames) const;
The Android Open Source Project7c1b96a2008-10-21 07:00:00 -0700242
243 int name() const {
244 return mName;
245 }
246
247 bool isStopped() const {
248 return mState == STOPPED;
249 }
250
251 bool isTerminated() const {
252 return mState == TERMINATED;
253 }
254
255 bool step();
256 void reset();
257
258 sp<AudioFlinger> mAudioFlinger;
259 sp<Client> mClient;
260 sp<IMemory> mCblkMemory;
261 audio_track_cblk_t* mCblk;
262 int mStreamType;
The Android Open Source Projecte09fd9e2008-12-17 18:05:43 -0800263 void* mBuffer;
264 void* mBufferEnd;
265 uint32_t mFrameCount;
The Android Open Source Project7c1b96a2008-10-21 07:00:00 -0700266 int mName;
267 // we don't really need a lock for these
268 int mState;
269 int mClientTid;
The Android Open Source Projecte09fd9e2008-12-17 18:05:43 -0800270 uint8_t mFormat;
271 uint8_t mFlags;
The Android Open Source Project7c1b96a2008-10-21 07:00:00 -0700272 };
273
274 // playback track
275 class Track : public TrackBase {
276 public:
277 Track( const sp<AudioFlinger>& audioFlinger,
278 const sp<Client>& client,
279 int streamType,
280 uint32_t sampleRate,
281 int format,
282 int channelCount,
The Android Open Source Projecte09fd9e2008-12-17 18:05:43 -0800283 int frameCount,
284 const sp<IMemory>& sharedBuffer);
The Android Open Source Project7c1b96a2008-10-21 07:00:00 -0700285 ~Track();
286
287 void dump(char* buffer, size_t size);
288 virtual status_t start();
289 virtual void stop();
290 void pause();
291
292 void flush();
293 void destroy();
294 void mute(bool);
295 void setVolume(float left, float right);
296
297 private:
298 friend class AudioFlinger;
299 friend class TrackHandle;
300
301 Track(const Track&);
302 Track& operator = (const Track&);
303
304 virtual status_t getNextBuffer(AudioBufferProvider::Buffer* buffer);
305
306 bool isMuted() const {
307 return mMute;
308 }
309
310 bool isPausing() const {
311 return mState == PAUSING;
312 }
313
314 bool isPaused() const {
315 return mState == PAUSED;
316 }
317
The Android Open Source Projecte09fd9e2008-12-17 18:05:43 -0800318 bool isReady() const;
The Android Open Source Project7c1b96a2008-10-21 07:00:00 -0700319
320 void setPaused() { mState = PAUSED; }
321 void reset();
322
323 // we don't really need a lock for these
324 float mVolume[2];
325 volatile bool mMute;
326 // FILLED state is used for suppressing volume ramp at begin of playing
327 enum {FS_FILLING, FS_FILLED, FS_ACTIVE};
328 mutable uint8_t mFillingUpStatus;
329 int8_t mRetryCount;
The Android Open Source Projecte09fd9e2008-12-17 18:05:43 -0800330 sp<IMemory> mSharedBuffer;
331 bool mResetDone;
The Android Open Source Project7c1b96a2008-10-21 07:00:00 -0700332 }; // end of Track
333
334 friend class AudioBuffer;
335
336 class TrackHandle : public android::BnAudioTrack {
337 public:
338 TrackHandle(const sp<Track>& track);
339 virtual ~TrackHandle();
340 virtual status_t start();
341 virtual void stop();
342 virtual void flush();
343 virtual void mute(bool);
344 virtual void pause();
345 virtual void setVolume(float left, float right);
346 virtual sp<IMemory> getCblk() const;
347 virtual status_t onTransact(
348 uint32_t code, const Parcel& data, Parcel* reply, uint32_t flags);
349 private:
350 sp<Track> mTrack;
351 };
352
353 struct stream_type_t {
354 stream_type_t()
355 : volume(1.0f),
356 mute(false)
357 {
358 }
359 float volume;
360 bool mute;
361 };
362
363 friend class Client;
364 friend class Track;
365
366
367 void removeClient(pid_t pid);
368
369 status_t addTrack(const sp<Track>& track);
370 void removeTrack(wp<Track> track, int name);
371 void remove_track_l(wp<Track> track, int name);
372 void destroyTrack(const sp<Track>& track);
373
The Android Open Source Projecte09fd9e2008-12-17 18:05:43 -0800374 AudioMixer* audioMixer() {
375 return mAudioMixer;
The Android Open Source Project7c1b96a2008-10-21 07:00:00 -0700376 }
377
378 // record track
379 class RecordTrack : public TrackBase {
380 public:
381 RecordTrack( const sp<AudioFlinger>& audioFlinger,
382 const sp<Client>& client,
383 int streamType,
384 uint32_t sampleRate,
385 int format,
386 int channelCount,
The Android Open Source Projecte09fd9e2008-12-17 18:05:43 -0800387 int frameCount);
The Android Open Source Project7c1b96a2008-10-21 07:00:00 -0700388 ~RecordTrack();
389
390 virtual status_t start();
391 virtual void stop();
392
393 bool overflow() { bool tmp = mOverflow; mOverflow = false; return tmp; }
394 bool setOverflow() { bool tmp = mOverflow; mOverflow = true; return tmp; }
395
396 private:
397 friend class AudioFlinger;
398 friend class RecordHandle;
399 friend class AudioRecordThread;
400
401 RecordTrack(const Track&);
402 RecordTrack& operator = (const Track&);
403
404 virtual status_t getNextBuffer(AudioBufferProvider::Buffer* buffer);
405
406 bool mOverflow;
407 };
408
409 class RecordHandle : public android::BnAudioRecord {
410 public:
411 RecordHandle(const sp<RecordTrack>& recordTrack);
412 virtual ~RecordHandle();
413 virtual status_t start();
414 virtual void stop();
415 virtual sp<IMemory> getCblk() const;
416 virtual status_t onTransact(
417 uint32_t code, const Parcel& data, Parcel* reply, uint32_t flags);
418 private:
419 sp<RecordTrack> mRecordTrack;
420 };
421
422 // record thread
423 class AudioRecordThread : public Thread
424 {
425 public:
The Android Open Source Projecte09fd9e2008-12-17 18:05:43 -0800426 AudioRecordThread(AudioHardwareInterface* audioHardware);
The Android Open Source Project7c1b96a2008-10-21 07:00:00 -0700427 virtual ~AudioRecordThread();
428 virtual bool threadLoop();
429 virtual status_t readyToRun() { return NO_ERROR; }
430 virtual void onFirstRef() {}
431
The Android Open Source Projecte09fd9e2008-12-17 18:05:43 -0800432 status_t start(RecordTrack* recordTrack);
433 void stop(RecordTrack* recordTrack);
The Android Open Source Project7c1b96a2008-10-21 07:00:00 -0700434 void exit();
The Android Open Source Project7c1b96a2008-10-21 07:00:00 -0700435
436 private:
437 AudioRecordThread();
The Android Open Source Projecte09fd9e2008-12-17 18:05:43 -0800438 AudioHardwareInterface *mAudioHardware;
439 sp<RecordTrack> mRecordTrack;
The Android Open Source Project7c1b96a2008-10-21 07:00:00 -0700440 Mutex mLock;
441 Condition mWaitWorkCV;
The Android Open Source Project7c1b96a2008-10-21 07:00:00 -0700442 volatile bool mActive;
The Android Open Source Projecte09fd9e2008-12-17 18:05:43 -0800443 status_t mStartStatus;
The Android Open Source Project7c1b96a2008-10-21 07:00:00 -0700444 };
445
446 friend class AudioRecordThread;
447
The Android Open Source Projecte09fd9e2008-12-17 18:05:43 -0800448 status_t startRecord(RecordTrack* recordTrack);
449 void stopRecord(RecordTrack* recordTrack);
The Android Open Source Project7c1b96a2008-10-21 07:00:00 -0700450
451 mutable Mutex mHardwareLock;
452 mutable Mutex mLock;
The Android Open Source Projecte09fd9e2008-12-17 18:05:43 -0800453 mutable Mutex mOutputLock;
The Android Open Source Project7c1b96a2008-10-21 07:00:00 -0700454 mutable Condition mWaitWorkCV;
455 DefaultKeyedVector< pid_t, wp<Client> > mClients;
456 SortedVector< wp<Track> > mActiveTracks;
457 SortedVector< sp<Track> > mTracks;
458 float mMasterVolume;
459 uint32_t mMasterRouting;
460 bool mMasterMute;
461 stream_type_t mStreamTypes[AudioTrack::NUM_STREAM_TYPES];
462
The Android Open Source Projecte09fd9e2008-12-17 18:05:43 -0800463 AudioMixer* mHardwareAudioMixer;
464 AudioMixer* mA2dpAudioMixer;
The Android Open Source Project7c1b96a2008-10-21 07:00:00 -0700465 AudioMixer* mAudioMixer;
466 AudioHardwareInterface* mAudioHardware;
The Android Open Source Projecte09fd9e2008-12-17 18:05:43 -0800467 AudioHardwareInterface* mA2dpAudioInterface;
468 AudioStreamOut* mHardwareOutput;
469 AudioStreamOut* mA2dpOutput;
The Android Open Source Project7c1b96a2008-10-21 07:00:00 -0700470 AudioStreamOut* mOutput;
471 sp<AudioRecordThread> mAudioRecordThread;
472 uint32_t mSampleRate;
473 size_t mFrameCount;
474 int mChannelCount;
475 int mFormat;
The Android Open Source Project7c1b96a2008-10-21 07:00:00 -0700476 int16_t* mMixBuffer;
477 mutable int mHardwareStatus;
478 nsecs_t mLastWriteTime;
479 int mNumWrites;
480 int mNumDelayedWrites;
481 bool mStandby;
482 bool mInWrite;
483};
484
485// ----------------------------------------------------------------------------
486
487}; // namespace android
488
489#endif // ANDROID_AUDIO_FLINGER_H