1.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000 1.2 +++ b/dom/system/gonk/android_audio/AudioTrack.h Wed Dec 31 06:09:35 2014 +0100 1.3 @@ -0,0 +1,489 @@ 1.4 +/* 1.5 + * Copyright (C) 2007 The Android Open Source Project 1.6 + * 1.7 + * Licensed under the Apache License, Version 2.0 (the "License"); 1.8 + * you may not use this file except in compliance with the License. 1.9 + * You may obtain a copy of the License at 1.10 + * 1.11 + * http://www.apache.org/licenses/LICENSE-2.0 1.12 + * 1.13 + * Unless required by applicable law or agreed to in writing, software 1.14 + * distributed under the License is distributed on an "AS IS" BASIS, 1.15 + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 1.16 + * See the License for the specific language governing permissions and 1.17 + * limitations under the License. 1.18 + */ 1.19 + 1.20 +#ifndef ANDROID_AUDIOTRACK_H 1.21 +#define ANDROID_AUDIOTRACK_H 1.22 + 1.23 +#include <stdint.h> 1.24 +#include <sys/types.h> 1.25 + 1.26 +#include "IAudioFlinger.h" 1.27 +#include "IAudioTrack.h" 1.28 +#include "AudioSystem.h" 1.29 + 1.30 +#include <utils/RefBase.h> 1.31 +#include <utils/Errors.h> 1.32 +#include <binder/IInterface.h> 1.33 +#include <binder/IMemory.h> 1.34 +#include <utils/threads.h> 1.35 + 1.36 + 1.37 +namespace android { 1.38 + 1.39 +// ---------------------------------------------------------------------------- 1.40 + 1.41 +class audio_track_cblk_t; 1.42 + 1.43 +// ---------------------------------------------------------------------------- 1.44 + 1.45 +class AudioTrack 1.46 +{ 1.47 +public: 1.48 + enum channel_index { 1.49 + MONO = 0, 1.50 + LEFT = 0, 1.51 + RIGHT = 1 1.52 + }; 1.53 + 1.54 + /* Events used by AudioTrack callback function (audio_track_cblk_t). 1.55 + */ 1.56 + enum event_type { 1.57 + EVENT_MORE_DATA = 0, // Request to write more data to PCM buffer. 1.58 + EVENT_UNDERRUN = 1, // PCM buffer underrun occured. 1.59 + EVENT_LOOP_END = 2, // Sample loop end was reached; playback restarted from loop start if loop count was not 0. 1.60 + EVENT_MARKER = 3, // Playback head is at the specified marker position (See setMarkerPosition()). 1.61 + EVENT_NEW_POS = 4, // Playback head is at a new position (See setPositionUpdatePeriod()). 1.62 + EVENT_BUFFER_END = 5 // Playback head is at the end of the buffer. 1.63 + }; 1.64 + 1.65 + /* Create Buffer on the stack and pass it to obtainBuffer() 1.66 + * and releaseBuffer(). 1.67 + */ 1.68 + 1.69 + class Buffer 1.70 + { 1.71 + public: 1.72 + enum { 1.73 + MUTE = 0x00000001 1.74 + }; 1.75 + uint32_t flags; 1.76 + int channelCount; 1.77 + int format; 1.78 + size_t frameCount; 1.79 + size_t size; 1.80 + union { 1.81 + void* raw; 1.82 + short* i16; 1.83 + int8_t* i8; 1.84 + }; 1.85 + }; 1.86 + 1.87 + 1.88 + /* As a convenience, if a callback is supplied, a handler thread 1.89 + * is automatically created with the appropriate priority. This thread 1.90 + * invokes the callback when a new buffer becomes availlable or an underrun condition occurs. 1.91 + * Parameters: 1.92 + * 1.93 + * event: type of event notified (see enum AudioTrack::event_type). 1.94 + * user: Pointer to context for use by the callback receiver. 1.95 + * info: Pointer to optional parameter according to event type: 1.96 + * - EVENT_MORE_DATA: pointer to AudioTrack::Buffer struct. The callback must not write 1.97 + * more bytes than indicated by 'size' field and update 'size' if less bytes are 1.98 + * written. 1.99 + * - EVENT_UNDERRUN: unused. 1.100 + * - EVENT_LOOP_END: pointer to an int indicating the number of loops remaining. 1.101 + * - EVENT_MARKER: pointer to an uin32_t containing the marker position in frames. 1.102 + * - EVENT_NEW_POS: pointer to an uin32_t containing the new position in frames. 1.103 + * - EVENT_BUFFER_END: unused. 1.104 + */ 1.105 + 1.106 + typedef void (*callback_t)(int event, void* user, void *info); 1.107 + 1.108 + /* Returns the minimum frame count required for the successful creation of 1.109 + * an AudioTrack object. 1.110 + * Returned status (from utils/Errors.h) can be: 1.111 + * - NO_ERROR: successful operation 1.112 + * - NO_INIT: audio server or audio hardware not initialized 1.113 + */ 1.114 + 1.115 + static status_t getMinFrameCount(int* frameCount, 1.116 + int streamType =-1, 1.117 + uint32_t sampleRate = 0); 1.118 + 1.119 + /* Constructs an uninitialized AudioTrack. No connection with 1.120 + * AudioFlinger takes place. 1.121 + */ 1.122 + AudioTrack(); 1.123 + 1.124 + /* Creates an audio track and registers it with AudioFlinger. 1.125 + * Once created, the track needs to be started before it can be used. 1.126 + * Unspecified values are set to the audio hardware's current 1.127 + * values. 1.128 + * 1.129 + * Parameters: 1.130 + * 1.131 + * streamType: Select the type of audio stream this track is attached to 1.132 + * (e.g. AudioSystem::MUSIC). 1.133 + * sampleRate: Track sampling rate in Hz. 1.134 + * format: Audio format (e.g AudioSystem::PCM_16_BIT for signed 1.135 + * 16 bits per sample). 1.136 + * channels: Channel mask: see AudioSystem::audio_channels. 1.137 + * frameCount: Total size of track PCM buffer in frames. This defines the 1.138 + * latency of the track. 1.139 + * flags: Reserved for future use. 1.140 + * cbf: Callback function. If not null, this function is called periodically 1.141 + * to request new PCM data. 1.142 + * notificationFrames: The callback function is called each time notificationFrames PCM 1.143 + * frames have been comsumed from track input buffer. 1.144 + * user Context for use by the callback receiver. 1.145 + */ 1.146 + 1.147 + AudioTrack( int streamType, 1.148 + uint32_t sampleRate = 0, 1.149 + int format = 0, 1.150 + int channels = 0, 1.151 + int frameCount = 0, 1.152 + uint32_t flags = 0, 1.153 + callback_t cbf = 0, 1.154 + void* user = 0, 1.155 + int notificationFrames = 0, 1.156 + int sessionId = 0); 1.157 + 1.158 + /* Creates an audio track and registers it with AudioFlinger. With this constructor, 1.159 + * The PCM data to be rendered by AudioTrack is passed in a shared memory buffer 1.160 + * identified by the argument sharedBuffer. This prototype is for static buffer playback. 1.161 + * PCM data must be present into memory before the AudioTrack is started. 1.162 + * The Write() and Flush() methods are not supported in this case. 1.163 + * It is recommented to pass a callback function to be notified of playback end by an 1.164 + * EVENT_UNDERRUN event. 1.165 + */ 1.166 + 1.167 + AudioTrack( int streamType, 1.168 + uint32_t sampleRate = 0, 1.169 + int format = 0, 1.170 + int channels = 0, 1.171 + const sp<IMemory>& sharedBuffer = 0, 1.172 + uint32_t flags = 0, 1.173 + callback_t cbf = 0, 1.174 + void* user = 0, 1.175 + int notificationFrames = 0, 1.176 + int sessionId = 0); 1.177 + 1.178 + /* Terminates the AudioTrack and unregisters it from AudioFlinger. 1.179 + * Also destroys all resources assotiated with the AudioTrack. 1.180 + */ 1.181 + ~AudioTrack(); 1.182 + 1.183 + 1.184 + /* Initialize an uninitialized AudioTrack. 1.185 + * Returned status (from utils/Errors.h) can be: 1.186 + * - NO_ERROR: successful intialization 1.187 + * - INVALID_OPERATION: AudioTrack is already intitialized 1.188 + * - BAD_VALUE: invalid parameter (channels, format, sampleRate...) 1.189 + * - NO_INIT: audio server or audio hardware not initialized 1.190 + * */ 1.191 + status_t set(int streamType =-1, 1.192 + uint32_t sampleRate = 0, 1.193 + int format = 0, 1.194 + int channels = 0, 1.195 + int frameCount = 0, 1.196 + uint32_t flags = 0, 1.197 + callback_t cbf = 0, 1.198 + void* user = 0, 1.199 + int notificationFrames = 0, 1.200 + const sp<IMemory>& sharedBuffer = 0, 1.201 + bool threadCanCallJava = false, 1.202 + int sessionId = 0); 1.203 + 1.204 + 1.205 + /* Result of constructing the AudioTrack. This must be checked 1.206 + * before using any AudioTrack API (except for set()), using 1.207 + * an uninitialized AudioTrack produces undefined results. 1.208 + * See set() method above for possible return codes. 1.209 + */ 1.210 + status_t initCheck() const; 1.211 + 1.212 + /* Returns this track's latency in milliseconds. 1.213 + * This includes the latency due to AudioTrack buffer size, AudioMixer (if any) 1.214 + * and audio hardware driver. 1.215 + */ 1.216 + uint32_t latency() const; 1.217 + 1.218 + /* getters, see constructor */ 1.219 + 1.220 + int streamType() const; 1.221 + int format() const; 1.222 + int channelCount() const; 1.223 + uint32_t frameCount() const; 1.224 + int frameSize() const; 1.225 + sp<IMemory>& sharedBuffer(); 1.226 + 1.227 + 1.228 + /* After it's created the track is not active. Call start() to 1.229 + * make it active. If set, the callback will start being called. 1.230 + */ 1.231 + void start(); 1.232 + 1.233 + /* Stop a track. If set, the callback will cease being called and 1.234 + * obtainBuffer returns STOPPED. Note that obtainBuffer() still works 1.235 + * and will fill up buffers until the pool is exhausted. 1.236 + */ 1.237 + void stop(); 1.238 + bool stopped() const; 1.239 + 1.240 + /* flush a stopped track. All pending buffers are discarded. 1.241 + * This function has no effect if the track is not stoped. 1.242 + */ 1.243 + void flush(); 1.244 + 1.245 + /* Pause a track. If set, the callback will cease being called and 1.246 + * obtainBuffer returns STOPPED. Note that obtainBuffer() still works 1.247 + * and will fill up buffers until the pool is exhausted. 1.248 + */ 1.249 + void pause(); 1.250 + 1.251 + /* mute or unmutes this track. 1.252 + * While mutted, the callback, if set, is still called. 1.253 + */ 1.254 + void mute(bool); 1.255 + bool muted() const; 1.256 + 1.257 + 1.258 + /* set volume for this track, mostly used for games' sound effects 1.259 + * left and right volumes. Levels must be <= 1.0. 1.260 + */ 1.261 + status_t setVolume(float left, float right); 1.262 + void getVolume(float* left, float* right); 1.263 + 1.264 + /* set the send level for this track. An auxiliary effect should be attached 1.265 + * to the track with attachEffect(). Level must be <= 1.0. 1.266 + */ 1.267 + status_t setAuxEffectSendLevel(float level); 1.268 + void getAuxEffectSendLevel(float* level); 1.269 + 1.270 + /* set sample rate for this track, mostly used for games' sound effects 1.271 + */ 1.272 + status_t setSampleRate(int sampleRate); 1.273 + uint32_t getSampleRate(); 1.274 + 1.275 + /* Enables looping and sets the start and end points of looping. 1.276 + * 1.277 + * Parameters: 1.278 + * 1.279 + * loopStart: loop start expressed as the number of PCM frames played since AudioTrack start. 1.280 + * loopEnd: loop end expressed as the number of PCM frames played since AudioTrack start. 1.281 + * loopCount: number of loops to execute. Calling setLoop() with loopCount == 0 cancels any pending or 1.282 + * active loop. loopCount = -1 means infinite looping. 1.283 + * 1.284 + * For proper operation the following condition must be respected: 1.285 + * (loopEnd-loopStart) <= framecount() 1.286 + */ 1.287 + status_t setLoop(uint32_t loopStart, uint32_t loopEnd, int loopCount); 1.288 + status_t getLoop(uint32_t *loopStart, uint32_t *loopEnd, int *loopCount); 1.289 + 1.290 + 1.291 + /* Sets marker position. When playback reaches the number of frames specified, a callback with event 1.292 + * type EVENT_MARKER is called. Calling setMarkerPosition with marker == 0 cancels marker notification 1.293 + * callback. 1.294 + * If the AudioTrack has been opened with no callback function associated, the operation will fail. 1.295 + * 1.296 + * Parameters: 1.297 + * 1.298 + * marker: marker position expressed in frames. 1.299 + * 1.300 + * Returned status (from utils/Errors.h) can be: 1.301 + * - NO_ERROR: successful operation 1.302 + * - INVALID_OPERATION: the AudioTrack has no callback installed. 1.303 + */ 1.304 + status_t setMarkerPosition(uint32_t marker); 1.305 + status_t getMarkerPosition(uint32_t *marker); 1.306 + 1.307 + 1.308 + /* Sets position update period. Every time the number of frames specified has been played, 1.309 + * a callback with event type EVENT_NEW_POS is called. 1.310 + * Calling setPositionUpdatePeriod with updatePeriod == 0 cancels new position notification 1.311 + * callback. 1.312 + * If the AudioTrack has been opened with no callback function associated, the operation will fail. 1.313 + * 1.314 + * Parameters: 1.315 + * 1.316 + * updatePeriod: position update notification period expressed in frames. 1.317 + * 1.318 + * Returned status (from utils/Errors.h) can be: 1.319 + * - NO_ERROR: successful operation 1.320 + * - INVALID_OPERATION: the AudioTrack has no callback installed. 1.321 + */ 1.322 + status_t setPositionUpdatePeriod(uint32_t updatePeriod); 1.323 + status_t getPositionUpdatePeriod(uint32_t *updatePeriod); 1.324 + 1.325 + 1.326 + /* Sets playback head position within AudioTrack buffer. The new position is specified 1.327 + * in number of frames. 1.328 + * This method must be called with the AudioTrack in paused or stopped state. 1.329 + * Note that the actual position set is <position> modulo the AudioTrack buffer size in frames. 1.330 + * Therefore using this method makes sense only when playing a "static" audio buffer 1.331 + * as opposed to streaming. 1.332 + * The getPosition() method on the other hand returns the total number of frames played since 1.333 + * playback start. 1.334 + * 1.335 + * Parameters: 1.336 + * 1.337 + * position: New playback head position within AudioTrack buffer. 1.338 + * 1.339 + * Returned status (from utils/Errors.h) can be: 1.340 + * - NO_ERROR: successful operation 1.341 + * - INVALID_OPERATION: the AudioTrack is not stopped. 1.342 + * - BAD_VALUE: The specified position is beyond the number of frames present in AudioTrack buffer 1.343 + */ 1.344 + status_t setPosition(uint32_t position); 1.345 + status_t getPosition(uint32_t *position); 1.346 + 1.347 + /* Forces AudioTrack buffer full condition. When playing a static buffer, this method avoids 1.348 + * rewriting the buffer before restarting playback after a stop. 1.349 + * This method must be called with the AudioTrack in paused or stopped state. 1.350 + * 1.351 + * Returned status (from utils/Errors.h) can be: 1.352 + * - NO_ERROR: successful operation 1.353 + * - INVALID_OPERATION: the AudioTrack is not stopped. 1.354 + */ 1.355 + status_t reload(); 1.356 + 1.357 + /* returns a handle on the audio output used by this AudioTrack. 1.358 + * 1.359 + * Parameters: 1.360 + * none. 1.361 + * 1.362 + * Returned value: 1.363 + * handle on audio hardware output 1.364 + */ 1.365 + audio_io_handle_t getOutput(); 1.366 + 1.367 + /* returns the unique ID associated to this track. 1.368 + * 1.369 + * Parameters: 1.370 + * none. 1.371 + * 1.372 + * Returned value: 1.373 + * AudioTrack ID. 1.374 + */ 1.375 + int getSessionId(); 1.376 + 1.377 + 1.378 + /* Attach track auxiliary output to specified effect. Used effectId = 0 1.379 + * to detach track from effect. 1.380 + * 1.381 + * Parameters: 1.382 + * 1.383 + * effectId: effectId obtained from AudioEffect::id(). 1.384 + * 1.385 + * Returned status (from utils/Errors.h) can be: 1.386 + * - NO_ERROR: successful operation 1.387 + * - INVALID_OPERATION: the effect is not an auxiliary effect. 1.388 + * - BAD_VALUE: The specified effect ID is invalid 1.389 + */ 1.390 + status_t attachAuxEffect(int effectId); 1.391 + 1.392 + /* obtains a buffer of "frameCount" frames. The buffer must be 1.393 + * filled entirely. If the track is stopped, obtainBuffer() returns 1.394 + * STOPPED instead of NO_ERROR as long as there are buffers availlable, 1.395 + * at which point NO_MORE_BUFFERS is returned. 1.396 + * Buffers will be returned until the pool (buffercount()) 1.397 + * is exhausted, at which point obtainBuffer() will either block 1.398 + * or return WOULD_BLOCK depending on the value of the "blocking" 1.399 + * parameter. 1.400 + */ 1.401 + 1.402 + enum { 1.403 + NO_MORE_BUFFERS = 0x80000001, 1.404 + STOPPED = 1 1.405 + }; 1.406 + 1.407 + status_t obtainBuffer(Buffer* audioBuffer, int32_t waitCount); 1.408 + void releaseBuffer(Buffer* audioBuffer); 1.409 + 1.410 + 1.411 + /* As a convenience we provide a write() interface to the audio buffer. 1.412 + * This is implemented on top of lockBuffer/unlockBuffer. For best 1.413 + * performance 1.414 + * 1.415 + */ 1.416 + ssize_t write(const void* buffer, size_t size); 1.417 + 1.418 + /* 1.419 + * Dumps the state of an audio track. 1.420 + */ 1.421 + status_t dump(int fd, const Vector<String16>& args) const; 1.422 + 1.423 +private: 1.424 + /* copying audio tracks is not allowed */ 1.425 + AudioTrack(const AudioTrack& other); 1.426 + AudioTrack& operator = (const AudioTrack& other); 1.427 + 1.428 + /* a small internal class to handle the callback */ 1.429 + class AudioTrackThread : public Thread 1.430 + { 1.431 + public: 1.432 + AudioTrackThread(AudioTrack& receiver, bool bCanCallJava = false); 1.433 + private: 1.434 + friend class AudioTrack; 1.435 + virtual bool threadLoop(); 1.436 + virtual status_t readyToRun(); 1.437 + virtual void onFirstRef(); 1.438 + AudioTrack& mReceiver; 1.439 + Mutex mLock; 1.440 + }; 1.441 + 1.442 + bool processAudioBuffer(const sp<AudioTrackThread>& thread); 1.443 + status_t createTrack(int streamType, 1.444 + uint32_t sampleRate, 1.445 + int format, 1.446 + int channelCount, 1.447 + int frameCount, 1.448 + uint32_t flags, 1.449 + const sp<IMemory>& sharedBuffer, 1.450 + audio_io_handle_t output, 1.451 + bool enforceFrameCount); 1.452 + 1.453 + sp<IAudioTrack> mAudioTrack; 1.454 + sp<IMemory> mCblkMemory; 1.455 + sp<AudioTrackThread> mAudioTrackThread; 1.456 + 1.457 + float mVolume[2]; 1.458 + float mSendLevel; 1.459 + uint32_t mFrameCount; 1.460 + 1.461 + audio_track_cblk_t* mCblk; 1.462 + uint8_t mStreamType; 1.463 + uint8_t mFormat; 1.464 + uint8_t mChannelCount; 1.465 + uint8_t mMuted; 1.466 + uint32_t mChannels; 1.467 + status_t mStatus; 1.468 + uint32_t mLatency; 1.469 + 1.470 + volatile int32_t mActive; 1.471 + 1.472 + callback_t mCbf; 1.473 + void* mUserData; 1.474 + uint32_t mNotificationFramesReq; // requested number of frames between each notification callback 1.475 + uint32_t mNotificationFramesAct; // actual number of frames between each notification callback 1.476 + sp<IMemory> mSharedBuffer; 1.477 + int mLoopCount; 1.478 + uint32_t mRemainingFrames; 1.479 + uint32_t mMarkerPosition; 1.480 + bool mMarkerReached; 1.481 + uint32_t mNewPosition; 1.482 + uint32_t mUpdatePeriod; 1.483 + uint32_t mFlags; 1.484 + int mSessionId; 1.485 + int mAuxEffectId; 1.486 + uint32_t mPadding[8]; 1.487 +}; 1.488 + 1.489 + 1.490 +}; // namespace android 1.491 + 1.492 +#endif // ANDROID_AUDIOTRACK_H