• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /* //device/extlibs/pv/android/AudioTrack.cpp
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 
19 //#define LOG_NDEBUG 0
20 #define LOG_TAG "AudioTrack"
21 
22 #include <stdint.h>
23 #include <sys/types.h>
24 #include <limits.h>
25 
26 #include <sched.h>
27 #include <sys/resource.h>
28 
29 #include <private/media/AudioTrackShared.h>
30 
31 #include <media/AudioSystem.h>
32 #include <media/AudioTrack.h>
33 
34 #include <utils/Log.h>
35 #include <binder/Parcel.h>
36 #include <binder/IPCThreadState.h>
37 #include <utils/Timers.h>
38 #include <utils/Atomic.h>
39 
40 #include <cutils/bitops.h>
41 
42 #include <system/audio.h>
43 #include <system/audio_policy.h>
44 
45 #define LIKELY( exp )       (__builtin_expect( (exp) != 0, true  ))
46 #define UNLIKELY( exp )     (__builtin_expect( (exp) != 0, false ))
47 
48 namespace android {
49 // ---------------------------------------------------------------------------
50 
51 // static
getMinFrameCount(int * frameCount,int streamType,uint32_t sampleRate)52 status_t AudioTrack::getMinFrameCount(
53         int* frameCount,
54         int streamType,
55         uint32_t sampleRate)
56 {
57     int afSampleRate;
58     if (AudioSystem::getOutputSamplingRate(&afSampleRate, streamType) != NO_ERROR) {
59         return NO_INIT;
60     }
61     int afFrameCount;
62     if (AudioSystem::getOutputFrameCount(&afFrameCount, streamType) != NO_ERROR) {
63         return NO_INIT;
64     }
65     uint32_t afLatency;
66     if (AudioSystem::getOutputLatency(&afLatency, streamType) != NO_ERROR) {
67         return NO_INIT;
68     }
69 
70     // Ensure that buffer depth covers at least audio hardware latency
71     uint32_t minBufCount = afLatency / ((1000 * afFrameCount) / afSampleRate);
72     if (minBufCount < 2) minBufCount = 2;
73 
74     *frameCount = (sampleRate == 0) ? afFrameCount * minBufCount :
75               afFrameCount * minBufCount * sampleRate / afSampleRate;
76     return NO_ERROR;
77 }
78 
79 // ---------------------------------------------------------------------------
80 
AudioTrack()81 AudioTrack::AudioTrack()
82     : mStatus(NO_INIT)
83 {
84 }
85 
AudioTrack(int streamType,uint32_t sampleRate,int format,int channelMask,int frameCount,uint32_t flags,callback_t cbf,void * user,int notificationFrames,int sessionId)86 AudioTrack::AudioTrack(
87         int streamType,
88         uint32_t sampleRate,
89         int format,
90         int channelMask,
91         int frameCount,
92         uint32_t flags,
93         callback_t cbf,
94         void* user,
95         int notificationFrames,
96         int sessionId)
97     : mStatus(NO_INIT)
98 {
99     mStatus = set(streamType, sampleRate, format, channelMask,
100             frameCount, flags, cbf, user, notificationFrames,
101             0, false, sessionId);
102 }
103 
AudioTrack(int streamType,uint32_t sampleRate,int format,int channelMask,const sp<IMemory> & sharedBuffer,uint32_t flags,callback_t cbf,void * user,int notificationFrames,int sessionId)104 AudioTrack::AudioTrack(
105         int streamType,
106         uint32_t sampleRate,
107         int format,
108         int channelMask,
109         const sp<IMemory>& sharedBuffer,
110         uint32_t flags,
111         callback_t cbf,
112         void* user,
113         int notificationFrames,
114         int sessionId)
115     : mStatus(NO_INIT)
116 {
117     mStatus = set(streamType, sampleRate, format, channelMask,
118             0, flags, cbf, user, notificationFrames,
119             sharedBuffer, false, sessionId);
120 }
121 
~AudioTrack()122 AudioTrack::~AudioTrack()
123 {
124     LOGV_IF(mSharedBuffer != 0, "Destructor sharedBuffer: %p", mSharedBuffer->pointer());
125 
126     if (mStatus == NO_ERROR) {
127         // Make sure that callback function exits in the case where
128         // it is looping on buffer full condition in obtainBuffer().
129         // Otherwise the callback thread will never exit.
130         stop();
131         if (mAudioTrackThread != 0) {
132             mAudioTrackThread->requestExitAndWait();
133             mAudioTrackThread.clear();
134         }
135         mAudioTrack.clear();
136         IPCThreadState::self()->flushCommands();
137         AudioSystem::releaseAudioSessionId(mSessionId);
138     }
139 }
140 
set(int streamType,uint32_t sampleRate,int format,int channelMask,int frameCount,uint32_t flags,callback_t cbf,void * user,int notificationFrames,const sp<IMemory> & sharedBuffer,bool threadCanCallJava,int sessionId)141 status_t AudioTrack::set(
142         int streamType,
143         uint32_t sampleRate,
144         int format,
145         int channelMask,
146         int frameCount,
147         uint32_t flags,
148         callback_t cbf,
149         void* user,
150         int notificationFrames,
151         const sp<IMemory>& sharedBuffer,
152         bool threadCanCallJava,
153         int sessionId)
154 {
155 
156     LOGV_IF(sharedBuffer != 0, "sharedBuffer: %p, size: %d", sharedBuffer->pointer(), sharedBuffer->size());
157 
158     AutoMutex lock(mLock);
159     if (mAudioTrack != 0) {
160         LOGE("Track already in use");
161         return INVALID_OPERATION;
162     }
163 
164     int afSampleRate;
165     if (AudioSystem::getOutputSamplingRate(&afSampleRate, streamType) != NO_ERROR) {
166         return NO_INIT;
167     }
168     uint32_t afLatency;
169     if (AudioSystem::getOutputLatency(&afLatency, streamType) != NO_ERROR) {
170         return NO_INIT;
171     }
172 
173     // handle default values first.
174     if (streamType == AUDIO_STREAM_DEFAULT) {
175         streamType = AUDIO_STREAM_MUSIC;
176     }
177     if (sampleRate == 0) {
178         sampleRate = afSampleRate;
179     }
180     // these below should probably come from the audioFlinger too...
181     if (format == 0) {
182         format = AUDIO_FORMAT_PCM_16_BIT;
183     }
184     if (channelMask == 0) {
185         channelMask = AUDIO_CHANNEL_OUT_STEREO;
186     }
187 
188     // validate parameters
189     if (!audio_is_valid_format(format)) {
190         LOGE("Invalid format");
191         return BAD_VALUE;
192     }
193 
194     // force direct flag if format is not linear PCM
195     if (!audio_is_linear_pcm(format)) {
196         flags |= AUDIO_POLICY_OUTPUT_FLAG_DIRECT;
197     }
198 
199     if (!audio_is_output_channel(channelMask)) {
200         LOGE("Invalid channel mask");
201         return BAD_VALUE;
202     }
203     uint32_t channelCount = popcount(channelMask);
204 
205     audio_io_handle_t output = AudioSystem::getOutput(
206                                     (audio_stream_type_t)streamType,
207                                     sampleRate,format, channelMask,
208                                     (audio_policy_output_flags_t)flags);
209 
210     if (output == 0) {
211         LOGE("Could not get audio output for stream type %d", streamType);
212         return BAD_VALUE;
213     }
214 
215     mVolume[LEFT] = 1.0f;
216     mVolume[RIGHT] = 1.0f;
217     mSendLevel = 0;
218     mFrameCount = frameCount;
219     mNotificationFramesReq = notificationFrames;
220     mSessionId = sessionId;
221     mAuxEffectId = 0;
222 
223     // create the IAudioTrack
224     status_t status = createTrack_l(streamType,
225                                   sampleRate,
226                                   (uint32_t)format,
227                                   (uint32_t)channelMask,
228                                   frameCount,
229                                   flags,
230                                   sharedBuffer,
231                                   output,
232                                   true);
233 
234     if (status != NO_ERROR) {
235         return status;
236     }
237 
238     if (cbf != 0) {
239         mAudioTrackThread = new AudioTrackThread(*this, threadCanCallJava);
240         if (mAudioTrackThread == 0) {
241           LOGE("Could not create callback thread");
242           return NO_INIT;
243         }
244     }
245 
246     mStatus = NO_ERROR;
247 
248     mStreamType = streamType;
249     mFormat = (uint32_t)format;
250     mChannelMask = (uint32_t)channelMask;
251     mChannelCount = channelCount;
252     mSharedBuffer = sharedBuffer;
253     mMuted = false;
254     mActive = 0;
255     mCbf = cbf;
256     mUserData = user;
257     mLoopCount = 0;
258     mMarkerPosition = 0;
259     mMarkerReached = false;
260     mNewPosition = 0;
261     mUpdatePeriod = 0;
262     mFlushed = false;
263     mFlags = flags;
264     AudioSystem::acquireAudioSessionId(mSessionId);
265     mRestoreStatus = NO_ERROR;
266     return NO_ERROR;
267 }
268 
initCheck() const269 status_t AudioTrack::initCheck() const
270 {
271     return mStatus;
272 }
273 
274 // -------------------------------------------------------------------------
275 
latency() const276 uint32_t AudioTrack::latency() const
277 {
278     return mLatency;
279 }
280 
streamType() const281 int AudioTrack::streamType() const
282 {
283     return mStreamType;
284 }
285 
format() const286 int AudioTrack::format() const
287 {
288     return mFormat;
289 }
290 
channelCount() const291 int AudioTrack::channelCount() const
292 {
293     return mChannelCount;
294 }
295 
frameCount() const296 uint32_t AudioTrack::frameCount() const
297 {
298     return mCblk->frameCount;
299 }
300 
frameSize() const301 int AudioTrack::frameSize() const
302 {
303     if (audio_is_linear_pcm(mFormat)) {
304         return channelCount()*audio_bytes_per_sample(mFormat);
305     } else {
306         return sizeof(uint8_t);
307     }
308 }
309 
sharedBuffer()310 sp<IMemory>& AudioTrack::sharedBuffer()
311 {
312     return mSharedBuffer;
313 }
314 
315 // -------------------------------------------------------------------------
316 
start()317 void AudioTrack::start()
318 {
319     sp<AudioTrackThread> t = mAudioTrackThread;
320     status_t status = NO_ERROR;
321 
322     LOGV("start %p", this);
323     if (t != 0) {
324         if (t->exitPending()) {
325             if (t->requestExitAndWait() == WOULD_BLOCK) {
326                 LOGE("AudioTrack::start called from thread");
327                 return;
328             }
329         }
330         t->mLock.lock();
331      }
332 
333     AutoMutex lock(mLock);
334     // acquire a strong reference on the IMemory and IAudioTrack so that they cannot be destroyed
335     // while we are accessing the cblk
336     sp <IAudioTrack> audioTrack = mAudioTrack;
337     sp <IMemory> iMem = mCblkMemory;
338     audio_track_cblk_t* cblk = mCblk;
339 
340     if (mActive == 0) {
341         mFlushed = false;
342         mActive = 1;
343         mNewPosition = cblk->server + mUpdatePeriod;
344         cblk->lock.lock();
345         cblk->bufferTimeoutMs = MAX_STARTUP_TIMEOUT_MS;
346         cblk->waitTimeMs = 0;
347         android_atomic_and(~CBLK_DISABLED_ON, &cblk->flags);
348         if (t != 0) {
349            t->run("AudioTrackThread", ANDROID_PRIORITY_AUDIO);
350         } else {
351             setpriority(PRIO_PROCESS, 0, ANDROID_PRIORITY_AUDIO);
352         }
353 
354         LOGV("start %p before lock cblk %p", this, mCblk);
355         if (!(cblk->flags & CBLK_INVALID_MSK)) {
356             cblk->lock.unlock();
357             status = mAudioTrack->start();
358             cblk->lock.lock();
359             if (status == DEAD_OBJECT) {
360                 android_atomic_or(CBLK_INVALID_ON, &cblk->flags);
361             }
362         }
363         if (cblk->flags & CBLK_INVALID_MSK) {
364             status = restoreTrack_l(cblk, true);
365         }
366         cblk->lock.unlock();
367         if (status != NO_ERROR) {
368             LOGV("start() failed");
369             mActive = 0;
370             if (t != 0) {
371                 t->requestExit();
372             } else {
373                 setpriority(PRIO_PROCESS, 0, ANDROID_PRIORITY_NORMAL);
374             }
375         }
376     }
377 
378     if (t != 0) {
379         t->mLock.unlock();
380     }
381 }
382 
stop()383 void AudioTrack::stop()
384 {
385     sp<AudioTrackThread> t = mAudioTrackThread;
386 
387     LOGV("stop %p", this);
388     if (t != 0) {
389         t->mLock.lock();
390     }
391 
392     AutoMutex lock(mLock);
393     if (mActive == 1) {
394         mActive = 0;
395         mCblk->cv.signal();
396         mAudioTrack->stop();
397         // Cancel loops (If we are in the middle of a loop, playback
398         // would not stop until loopCount reaches 0).
399         setLoop_l(0, 0, 0);
400         // the playback head position will reset to 0, so if a marker is set, we need
401         // to activate it again
402         mMarkerReached = false;
403         // Force flush if a shared buffer is used otherwise audioflinger
404         // will not stop before end of buffer is reached.
405         if (mSharedBuffer != 0) {
406             flush_l();
407         }
408         if (t != 0) {
409             t->requestExit();
410         } else {
411             setpriority(PRIO_PROCESS, 0, ANDROID_PRIORITY_NORMAL);
412         }
413     }
414 
415     if (t != 0) {
416         t->mLock.unlock();
417     }
418 }
419 
stopped() const420 bool AudioTrack::stopped() const
421 {
422     return !mActive;
423 }
424 
flush()425 void AudioTrack::flush()
426 {
427     AutoMutex lock(mLock);
428     flush_l();
429 }
430 
431 // must be called with mLock held
flush_l()432 void AudioTrack::flush_l()
433 {
434     LOGV("flush");
435 
436     // clear playback marker and periodic update counter
437     mMarkerPosition = 0;
438     mMarkerReached = false;
439     mUpdatePeriod = 0;
440 
441     if (!mActive) {
442         mFlushed = true;
443         mAudioTrack->flush();
444         // Release AudioTrack callback thread in case it was waiting for new buffers
445         // in AudioTrack::obtainBuffer()
446         mCblk->cv.signal();
447     }
448 }
449 
pause()450 void AudioTrack::pause()
451 {
452     LOGV("pause");
453     AutoMutex lock(mLock);
454     if (mActive == 1) {
455         mActive = 0;
456         mAudioTrack->pause();
457     }
458 }
459 
mute(bool e)460 void AudioTrack::mute(bool e)
461 {
462     mAudioTrack->mute(e);
463     mMuted = e;
464 }
465 
muted() const466 bool AudioTrack::muted() const
467 {
468     return mMuted;
469 }
470 
setVolume(float left,float right)471 status_t AudioTrack::setVolume(float left, float right)
472 {
473     if (left > 1.0f || right > 1.0f) {
474         return BAD_VALUE;
475     }
476 
477     AutoMutex lock(mLock);
478     mVolume[LEFT] = left;
479     mVolume[RIGHT] = right;
480 
481     // write must be atomic
482     mCblk->volumeLR = (uint32_t(uint16_t(right * 0x1000)) << 16) | uint16_t(left * 0x1000);
483 
484     return NO_ERROR;
485 }
486 
getVolume(float * left,float * right)487 void AudioTrack::getVolume(float* left, float* right)
488 {
489     if (left != NULL) {
490         *left  = mVolume[LEFT];
491     }
492     if (right != NULL) {
493         *right = mVolume[RIGHT];
494     }
495 }
496 
setAuxEffectSendLevel(float level)497 status_t AudioTrack::setAuxEffectSendLevel(float level)
498 {
499     LOGV("setAuxEffectSendLevel(%f)", level);
500     if (level > 1.0f) {
501         return BAD_VALUE;
502     }
503     AutoMutex lock(mLock);
504 
505     mSendLevel = level;
506 
507     mCblk->sendLevel = uint16_t(level * 0x1000);
508 
509     return NO_ERROR;
510 }
511 
getAuxEffectSendLevel(float * level)512 void AudioTrack::getAuxEffectSendLevel(float* level)
513 {
514     if (level != NULL) {
515         *level  = mSendLevel;
516     }
517 }
518 
setSampleRate(int rate)519 status_t AudioTrack::setSampleRate(int rate)
520 {
521     int afSamplingRate;
522 
523     if (AudioSystem::getOutputSamplingRate(&afSamplingRate, mStreamType) != NO_ERROR) {
524         return NO_INIT;
525     }
526     // Resampler implementation limits input sampling rate to 2 x output sampling rate.
527     if (rate <= 0 || rate > afSamplingRate*2 ) return BAD_VALUE;
528 
529     AutoMutex lock(mLock);
530     mCblk->sampleRate = rate;
531     return NO_ERROR;
532 }
533 
getSampleRate()534 uint32_t AudioTrack::getSampleRate()
535 {
536     AutoMutex lock(mLock);
537     return mCblk->sampleRate;
538 }
539 
setLoop(uint32_t loopStart,uint32_t loopEnd,int loopCount)540 status_t AudioTrack::setLoop(uint32_t loopStart, uint32_t loopEnd, int loopCount)
541 {
542     AutoMutex lock(mLock);
543     return setLoop_l(loopStart, loopEnd, loopCount);
544 }
545 
546 // must be called with mLock held
setLoop_l(uint32_t loopStart,uint32_t loopEnd,int loopCount)547 status_t AudioTrack::setLoop_l(uint32_t loopStart, uint32_t loopEnd, int loopCount)
548 {
549     audio_track_cblk_t* cblk = mCblk;
550 
551     Mutex::Autolock _l(cblk->lock);
552 
553     if (loopCount == 0) {
554         cblk->loopStart = UINT_MAX;
555         cblk->loopEnd = UINT_MAX;
556         cblk->loopCount = 0;
557         mLoopCount = 0;
558         return NO_ERROR;
559     }
560 
561     if (loopStart >= loopEnd ||
562         loopEnd - loopStart > cblk->frameCount ||
563         cblk->server > loopStart) {
564         LOGE("setLoop invalid value: loopStart %d, loopEnd %d, loopCount %d, framecount %d, user %d", loopStart, loopEnd, loopCount, cblk->frameCount, cblk->user);
565         return BAD_VALUE;
566     }
567 
568     if ((mSharedBuffer != 0) && (loopEnd > cblk->frameCount)) {
569         LOGE("setLoop invalid value: loop markers beyond data: loopStart %d, loopEnd %d, framecount %d",
570             loopStart, loopEnd, cblk->frameCount);
571         return BAD_VALUE;
572     }
573 
574     cblk->loopStart = loopStart;
575     cblk->loopEnd = loopEnd;
576     cblk->loopCount = loopCount;
577     mLoopCount = loopCount;
578 
579     return NO_ERROR;
580 }
581 
getLoop(uint32_t * loopStart,uint32_t * loopEnd,int * loopCount)582 status_t AudioTrack::getLoop(uint32_t *loopStart, uint32_t *loopEnd, int *loopCount)
583 {
584     AutoMutex lock(mLock);
585     if (loopStart != 0) {
586         *loopStart = mCblk->loopStart;
587     }
588     if (loopEnd != 0) {
589         *loopEnd = mCblk->loopEnd;
590     }
591     if (loopCount != 0) {
592         if (mCblk->loopCount < 0) {
593             *loopCount = -1;
594         } else {
595             *loopCount = mCblk->loopCount;
596         }
597     }
598 
599     return NO_ERROR;
600 }
601 
setMarkerPosition(uint32_t marker)602 status_t AudioTrack::setMarkerPosition(uint32_t marker)
603 {
604     if (mCbf == 0) return INVALID_OPERATION;
605 
606     mMarkerPosition = marker;
607     mMarkerReached = false;
608 
609     return NO_ERROR;
610 }
611 
getMarkerPosition(uint32_t * marker)612 status_t AudioTrack::getMarkerPosition(uint32_t *marker)
613 {
614     if (marker == 0) return BAD_VALUE;
615 
616     *marker = mMarkerPosition;
617 
618     return NO_ERROR;
619 }
620 
setPositionUpdatePeriod(uint32_t updatePeriod)621 status_t AudioTrack::setPositionUpdatePeriod(uint32_t updatePeriod)
622 {
623     if (mCbf == 0) return INVALID_OPERATION;
624 
625     uint32_t curPosition;
626     getPosition(&curPosition);
627     mNewPosition = curPosition + updatePeriod;
628     mUpdatePeriod = updatePeriod;
629 
630     return NO_ERROR;
631 }
632 
getPositionUpdatePeriod(uint32_t * updatePeriod)633 status_t AudioTrack::getPositionUpdatePeriod(uint32_t *updatePeriod)
634 {
635     if (updatePeriod == 0) return BAD_VALUE;
636 
637     *updatePeriod = mUpdatePeriod;
638 
639     return NO_ERROR;
640 }
641 
setPosition(uint32_t position)642 status_t AudioTrack::setPosition(uint32_t position)
643 {
644     AutoMutex lock(mLock);
645     Mutex::Autolock _l(mCblk->lock);
646 
647     if (!stopped()) return INVALID_OPERATION;
648 
649     if (position > mCblk->user) return BAD_VALUE;
650 
651     mCblk->server = position;
652     android_atomic_or(CBLK_FORCEREADY_ON, &mCblk->flags);
653 
654     return NO_ERROR;
655 }
656 
getPosition(uint32_t * position)657 status_t AudioTrack::getPosition(uint32_t *position)
658 {
659     if (position == 0) return BAD_VALUE;
660     AutoMutex lock(mLock);
661     *position = mFlushed ? 0 : mCblk->server;
662 
663     return NO_ERROR;
664 }
665 
reload()666 status_t AudioTrack::reload()
667 {
668     AutoMutex lock(mLock);
669 
670     if (!stopped()) return INVALID_OPERATION;
671 
672     flush_l();
673 
674     mCblk->stepUser(mCblk->frameCount);
675 
676     return NO_ERROR;
677 }
678 
getOutput()679 audio_io_handle_t AudioTrack::getOutput()
680 {
681     AutoMutex lock(mLock);
682     return getOutput_l();
683 }
684 
685 // must be called with mLock held
getOutput_l()686 audio_io_handle_t AudioTrack::getOutput_l()
687 {
688     return AudioSystem::getOutput((audio_stream_type_t)mStreamType,
689             mCblk->sampleRate, mFormat, mChannelMask, (audio_policy_output_flags_t)mFlags);
690 }
691 
getSessionId()692 int AudioTrack::getSessionId()
693 {
694     return mSessionId;
695 }
696 
attachAuxEffect(int effectId)697 status_t AudioTrack::attachAuxEffect(int effectId)
698 {
699     LOGV("attachAuxEffect(%d)", effectId);
700     status_t status = mAudioTrack->attachAuxEffect(effectId);
701     if (status == NO_ERROR) {
702         mAuxEffectId = effectId;
703     }
704     return status;
705 }
706 
707 // -------------------------------------------------------------------------
708 
709 // must be called with mLock held
createTrack_l(int streamType,uint32_t sampleRate,uint32_t format,uint32_t channelMask,int frameCount,uint32_t flags,const sp<IMemory> & sharedBuffer,audio_io_handle_t output,bool enforceFrameCount)710 status_t AudioTrack::createTrack_l(
711         int streamType,
712         uint32_t sampleRate,
713         uint32_t format,
714         uint32_t channelMask,
715         int frameCount,
716         uint32_t flags,
717         const sp<IMemory>& sharedBuffer,
718         audio_io_handle_t output,
719         bool enforceFrameCount)
720 {
721     status_t status;
722     const sp<IAudioFlinger>& audioFlinger = AudioSystem::get_audio_flinger();
723     if (audioFlinger == 0) {
724        LOGE("Could not get audioflinger");
725        return NO_INIT;
726     }
727 
728     int afSampleRate;
729     if (AudioSystem::getOutputSamplingRate(&afSampleRate, streamType) != NO_ERROR) {
730         return NO_INIT;
731     }
732     int afFrameCount;
733     if (AudioSystem::getOutputFrameCount(&afFrameCount, streamType) != NO_ERROR) {
734         return NO_INIT;
735     }
736     uint32_t afLatency;
737     if (AudioSystem::getOutputLatency(&afLatency, streamType) != NO_ERROR) {
738         return NO_INIT;
739     }
740 
741     mNotificationFramesAct = mNotificationFramesReq;
742     if (!audio_is_linear_pcm(format)) {
743         if (sharedBuffer != 0) {
744             frameCount = sharedBuffer->size();
745         }
746     } else {
747         // Ensure that buffer depth covers at least audio hardware latency
748         uint32_t minBufCount = afLatency / ((1000 * afFrameCount)/afSampleRate);
749         if (minBufCount < 2) minBufCount = 2;
750 
751         int minFrameCount = (afFrameCount*sampleRate*minBufCount)/afSampleRate;
752 
753         if (sharedBuffer == 0) {
754             if (frameCount == 0) {
755                 frameCount = minFrameCount;
756             }
757             if (mNotificationFramesAct == 0) {
758                 mNotificationFramesAct = frameCount/2;
759             }
760             // Make sure that application is notified with sufficient margin
761             // before underrun
762             if (mNotificationFramesAct > (uint32_t)frameCount/2) {
763                 mNotificationFramesAct = frameCount/2;
764             }
765             if (frameCount < minFrameCount) {
766                 if (enforceFrameCount) {
767                     LOGE("Invalid buffer size: minFrameCount %d, frameCount %d", minFrameCount, frameCount);
768                     return BAD_VALUE;
769                 } else {
770                     frameCount = minFrameCount;
771                 }
772             }
773         } else {
774             // Ensure that buffer alignment matches channelcount
775             int channelCount = popcount(channelMask);
776             if (((uint32_t)sharedBuffer->pointer() & (channelCount | 1)) != 0) {
777                 LOGE("Invalid buffer alignement: address %p, channelCount %d", sharedBuffer->pointer(), channelCount);
778                 return BAD_VALUE;
779             }
780             frameCount = sharedBuffer->size()/channelCount/sizeof(int16_t);
781         }
782     }
783 
784     sp<IAudioTrack> track = audioFlinger->createTrack(getpid(),
785                                                       streamType,
786                                                       sampleRate,
787                                                       format,
788                                                       channelMask,
789                                                       frameCount,
790                                                       ((uint16_t)flags) << 16,
791                                                       sharedBuffer,
792                                                       output,
793                                                       &mSessionId,
794                                                       &status);
795 
796     if (track == 0) {
797         LOGE("AudioFlinger could not create track, status: %d", status);
798         return status;
799     }
800     sp<IMemory> cblk = track->getCblk();
801     if (cblk == 0) {
802         LOGE("Could not get control block");
803         return NO_INIT;
804     }
805     mAudioTrack.clear();
806     mAudioTrack = track;
807     mCblkMemory.clear();
808     mCblkMemory = cblk;
809     mCblk = static_cast<audio_track_cblk_t*>(cblk->pointer());
810     android_atomic_or(CBLK_DIRECTION_OUT, &mCblk->flags);
811     if (sharedBuffer == 0) {
812         mCblk->buffers = (char*)mCblk + sizeof(audio_track_cblk_t);
813     } else {
814         mCblk->buffers = sharedBuffer->pointer();
815          // Force buffer full condition as data is already present in shared memory
816         mCblk->stepUser(mCblk->frameCount);
817     }
818 
819     mCblk->volumeLR = (uint32_t(uint16_t(mVolume[RIGHT] * 0x1000)) << 16) | uint16_t(mVolume[LEFT] * 0x1000);
820     mCblk->sendLevel = uint16_t(mSendLevel * 0x1000);
821     mAudioTrack->attachAuxEffect(mAuxEffectId);
822     mCblk->bufferTimeoutMs = MAX_STARTUP_TIMEOUT_MS;
823     mCblk->waitTimeMs = 0;
824     mRemainingFrames = mNotificationFramesAct;
825     mLatency = afLatency + (1000*mCblk->frameCount) / sampleRate;
826     return NO_ERROR;
827 }
828 
obtainBuffer(Buffer * audioBuffer,int32_t waitCount)829 status_t AudioTrack::obtainBuffer(Buffer* audioBuffer, int32_t waitCount)
830 {
831     AutoMutex lock(mLock);
832     int active;
833     status_t result = NO_ERROR;
834     audio_track_cblk_t* cblk = mCblk;
835     uint32_t framesReq = audioBuffer->frameCount;
836     uint32_t waitTimeMs = (waitCount < 0) ? cblk->bufferTimeoutMs : WAIT_PERIOD_MS;
837 
838     audioBuffer->frameCount  = 0;
839     audioBuffer->size = 0;
840 
841     uint32_t framesAvail = cblk->framesAvailable();
842 
843     cblk->lock.lock();
844     if (cblk->flags & CBLK_INVALID_MSK) {
845         goto create_new_track;
846     }
847     cblk->lock.unlock();
848 
849     if (framesAvail == 0) {
850         cblk->lock.lock();
851         goto start_loop_here;
852         while (framesAvail == 0) {
853             active = mActive;
854             if (UNLIKELY(!active)) {
855                 LOGV("Not active and NO_MORE_BUFFERS");
856                 cblk->lock.unlock();
857                 return NO_MORE_BUFFERS;
858             }
859             if (UNLIKELY(!waitCount)) {
860                 cblk->lock.unlock();
861                 return WOULD_BLOCK;
862             }
863             if (!(cblk->flags & CBLK_INVALID_MSK)) {
864                 mLock.unlock();
865                 result = cblk->cv.waitRelative(cblk->lock, milliseconds(waitTimeMs));
866                 cblk->lock.unlock();
867                 mLock.lock();
868                 if (mActive == 0) {
869                     return status_t(STOPPED);
870                 }
871                 cblk->lock.lock();
872             }
873 
874             if (cblk->flags & CBLK_INVALID_MSK) {
875                 goto create_new_track;
876             }
877             if (__builtin_expect(result!=NO_ERROR, false)) {
878                 cblk->waitTimeMs += waitTimeMs;
879                 if (cblk->waitTimeMs >= cblk->bufferTimeoutMs) {
880                     // timing out when a loop has been set and we have already written upto loop end
881                     // is a normal condition: no need to wake AudioFlinger up.
882                     if (cblk->user < cblk->loopEnd) {
883                         LOGW(   "obtainBuffer timed out (is the CPU pegged?) %p "
884                                 "user=%08x, server=%08x", this, cblk->user, cblk->server);
885                         //unlock cblk mutex before calling mAudioTrack->start() (see issue #1617140)
886                         cblk->lock.unlock();
887                         result = mAudioTrack->start();
888                         cblk->lock.lock();
889                         if (result == DEAD_OBJECT) {
890                             android_atomic_or(CBLK_INVALID_ON, &cblk->flags);
891 create_new_track:
892                             result = restoreTrack_l(cblk, false);
893                         }
894                         if (result != NO_ERROR) {
895                             LOGW("obtainBuffer create Track error %d", result);
896                             cblk->lock.unlock();
897                             return result;
898                         }
899                     }
900                     cblk->waitTimeMs = 0;
901                 }
902 
903                 if (--waitCount == 0) {
904                     cblk->lock.unlock();
905                     return TIMED_OUT;
906                 }
907             }
908             // read the server count again
909         start_loop_here:
910             framesAvail = cblk->framesAvailable_l();
911         }
912         cblk->lock.unlock();
913     }
914 
915     // restart track if it was disabled by audioflinger due to previous underrun
916     if (mActive && (cblk->flags & CBLK_DISABLED_MSK)) {
917         android_atomic_and(~CBLK_DISABLED_ON, &cblk->flags);
918         LOGW("obtainBuffer() track %p disabled, restarting", this);
919         mAudioTrack->start();
920     }
921 
922     cblk->waitTimeMs = 0;
923 
924     if (framesReq > framesAvail) {
925         framesReq = framesAvail;
926     }
927 
928     uint32_t u = cblk->user;
929     uint32_t bufferEnd = cblk->userBase + cblk->frameCount;
930 
931     if (u + framesReq > bufferEnd) {
932         framesReq = bufferEnd - u;
933     }
934 
935     audioBuffer->flags = mMuted ? Buffer::MUTE : 0;
936     audioBuffer->channelCount = mChannelCount;
937     audioBuffer->frameCount = framesReq;
938     audioBuffer->size = framesReq * cblk->frameSize;
939     if (audio_is_linear_pcm(mFormat)) {
940         audioBuffer->format = AUDIO_FORMAT_PCM_16_BIT;
941     } else {
942         audioBuffer->format = mFormat;
943     }
944     audioBuffer->raw = (int8_t *)cblk->buffer(u);
945     active = mActive;
946     return active ? status_t(NO_ERROR) : status_t(STOPPED);
947 }
948 
releaseBuffer(Buffer * audioBuffer)949 void AudioTrack::releaseBuffer(Buffer* audioBuffer)
950 {
951     AutoMutex lock(mLock);
952     mCblk->stepUser(audioBuffer->frameCount);
953 }
954 
955 // -------------------------------------------------------------------------
956 
write(const void * buffer,size_t userSize)957 ssize_t AudioTrack::write(const void* buffer, size_t userSize)
958 {
959 
960     if (mSharedBuffer != 0) return INVALID_OPERATION;
961 
962     if (ssize_t(userSize) < 0) {
963         // sanity-check. user is most-likely passing an error code.
964         LOGE("AudioTrack::write(buffer=%p, size=%u (%d)",
965                 buffer, userSize, userSize);
966         return BAD_VALUE;
967     }
968 
969     LOGV("write %p: %d bytes, mActive=%d", this, userSize, mActive);
970 
971     // acquire a strong reference on the IMemory and IAudioTrack so that they cannot be destroyed
972     // while we are accessing the cblk
973     mLock.lock();
974     sp <IAudioTrack> audioTrack = mAudioTrack;
975     sp <IMemory> iMem = mCblkMemory;
976     mLock.unlock();
977 
978     ssize_t written = 0;
979     const int8_t *src = (const int8_t *)buffer;
980     Buffer audioBuffer;
981     size_t frameSz = (size_t)frameSize();
982 
983     do {
984         audioBuffer.frameCount = userSize/frameSz;
985 
986         // Calling obtainBuffer() with a negative wait count causes
987         // an (almost) infinite wait time.
988         status_t err = obtainBuffer(&audioBuffer, -1);
989         if (err < 0) {
990             // out of buffers, return #bytes written
991             if (err == status_t(NO_MORE_BUFFERS))
992                 break;
993             return ssize_t(err);
994         }
995 
996         size_t toWrite;
997 
998         if (mFormat == AUDIO_FORMAT_PCM_8_BIT && !(mFlags & AUDIO_POLICY_OUTPUT_FLAG_DIRECT)) {
999             // Divide capacity by 2 to take expansion into account
1000             toWrite = audioBuffer.size>>1;
1001             // 8 to 16 bit conversion
1002             int count = toWrite;
1003             int16_t *dst = (int16_t *)(audioBuffer.i8);
1004             while(count--) {
1005                 *dst++ = (int16_t)(*src++^0x80) << 8;
1006             }
1007         } else {
1008             toWrite = audioBuffer.size;
1009             memcpy(audioBuffer.i8, src, toWrite);
1010             src += toWrite;
1011         }
1012         userSize -= toWrite;
1013         written += toWrite;
1014 
1015         releaseBuffer(&audioBuffer);
1016     } while (userSize >= frameSz);
1017 
1018     return written;
1019 }
1020 
1021 // -------------------------------------------------------------------------
1022 
processAudioBuffer(const sp<AudioTrackThread> & thread)1023 bool AudioTrack::processAudioBuffer(const sp<AudioTrackThread>& thread)
1024 {
1025     Buffer audioBuffer;
1026     uint32_t frames;
1027     size_t writtenSize;
1028 
1029     mLock.lock();
1030     // acquire a strong reference on the IMemory and IAudioTrack so that they cannot be destroyed
1031     // while we are accessing the cblk
1032     sp <IAudioTrack> audioTrack = mAudioTrack;
1033     sp <IMemory> iMem = mCblkMemory;
1034     audio_track_cblk_t* cblk = mCblk;
1035     mLock.unlock();
1036 
1037     // Manage underrun callback
1038     if (mActive && (cblk->framesAvailable() == cblk->frameCount)) {
1039         LOGV("Underrun user: %x, server: %x, flags %04x", cblk->user, cblk->server, cblk->flags);
1040         if (!(android_atomic_or(CBLK_UNDERRUN_ON, &cblk->flags) & CBLK_UNDERRUN_MSK)) {
1041             mCbf(EVENT_UNDERRUN, mUserData, 0);
1042             if (cblk->server == cblk->frameCount) {
1043                 mCbf(EVENT_BUFFER_END, mUserData, 0);
1044             }
1045             if (mSharedBuffer != 0) return false;
1046         }
1047     }
1048 
1049     // Manage loop end callback
1050     while (mLoopCount > cblk->loopCount) {
1051         int loopCount = -1;
1052         mLoopCount--;
1053         if (mLoopCount >= 0) loopCount = mLoopCount;
1054 
1055         mCbf(EVENT_LOOP_END, mUserData, (void *)&loopCount);
1056     }
1057 
1058     // Manage marker callback
1059     if (!mMarkerReached && (mMarkerPosition > 0)) {
1060         if (cblk->server >= mMarkerPosition) {
1061             mCbf(EVENT_MARKER, mUserData, (void *)&mMarkerPosition);
1062             mMarkerReached = true;
1063         }
1064     }
1065 
1066     // Manage new position callback
1067     if (mUpdatePeriod > 0) {
1068         while (cblk->server >= mNewPosition) {
1069             mCbf(EVENT_NEW_POS, mUserData, (void *)&mNewPosition);
1070             mNewPosition += mUpdatePeriod;
1071         }
1072     }
1073 
1074     // If Shared buffer is used, no data is requested from client.
1075     if (mSharedBuffer != 0) {
1076         frames = 0;
1077     } else {
1078         frames = mRemainingFrames;
1079     }
1080 
1081     int32_t waitCount = -1;
1082     if (mUpdatePeriod || (!mMarkerReached && mMarkerPosition) || mLoopCount) {
1083         waitCount = 1;
1084     }
1085 
1086     do {
1087 
1088         audioBuffer.frameCount = frames;
1089 
1090         // Calling obtainBuffer() with a wait count of 1
1091         // limits wait time to WAIT_PERIOD_MS. This prevents from being
1092         // stuck here not being able to handle timed events (position, markers, loops).
1093         status_t err = obtainBuffer(&audioBuffer, waitCount);
1094         if (err < NO_ERROR) {
1095             if (err != TIMED_OUT) {
1096                 LOGE_IF(err != status_t(NO_MORE_BUFFERS), "Error obtaining an audio buffer, giving up.");
1097                 return false;
1098             }
1099             break;
1100         }
1101         if (err == status_t(STOPPED)) return false;
1102 
1103         // Divide buffer size by 2 to take into account the expansion
1104         // due to 8 to 16 bit conversion: the callback must fill only half
1105         // of the destination buffer
1106         if (mFormat == AUDIO_FORMAT_PCM_8_BIT && !(mFlags & AUDIO_POLICY_OUTPUT_FLAG_DIRECT)) {
1107             audioBuffer.size >>= 1;
1108         }
1109 
1110         size_t reqSize = audioBuffer.size;
1111         mCbf(EVENT_MORE_DATA, mUserData, &audioBuffer);
1112         writtenSize = audioBuffer.size;
1113 
1114         // Sanity check on returned size
1115         if (ssize_t(writtenSize) <= 0) {
1116             // The callback is done filling buffers
1117             // Keep this thread going to handle timed events and
1118             // still try to get more data in intervals of WAIT_PERIOD_MS
1119             // but don't just loop and block the CPU, so wait
1120             usleep(WAIT_PERIOD_MS*1000);
1121             break;
1122         }
1123         if (writtenSize > reqSize) writtenSize = reqSize;
1124 
1125         if (mFormat == AUDIO_FORMAT_PCM_8_BIT && !(mFlags & AUDIO_POLICY_OUTPUT_FLAG_DIRECT)) {
1126             // 8 to 16 bit conversion
1127             const int8_t *src = audioBuffer.i8 + writtenSize-1;
1128             int count = writtenSize;
1129             int16_t *dst = audioBuffer.i16 + writtenSize-1;
1130             while(count--) {
1131                 *dst-- = (int16_t)(*src--^0x80) << 8;
1132             }
1133             writtenSize <<= 1;
1134         }
1135 
1136         audioBuffer.size = writtenSize;
1137         // NOTE: mCblk->frameSize is not equal to AudioTrack::frameSize() for
1138         // 8 bit PCM data: in this case,  mCblk->frameSize is based on a sampel size of
1139         // 16 bit.
1140         audioBuffer.frameCount = writtenSize/mCblk->frameSize;
1141 
1142         frames -= audioBuffer.frameCount;
1143 
1144         releaseBuffer(&audioBuffer);
1145     }
1146     while (frames);
1147 
1148     if (frames == 0) {
1149         mRemainingFrames = mNotificationFramesAct;
1150     } else {
1151         mRemainingFrames = frames;
1152     }
1153     return true;
1154 }
1155 
1156 // must be called with mLock and cblk.lock held. Callers must also hold strong references on
1157 // the IAudioTrack and IMemory in case they are recreated here.
1158 // If the IAudioTrack is successfully restored, the cblk pointer is updated
restoreTrack_l(audio_track_cblk_t * & cblk,bool fromStart)1159 status_t AudioTrack::restoreTrack_l(audio_track_cblk_t*& cblk, bool fromStart)
1160 {
1161     status_t result;
1162 
1163     if (!(android_atomic_or(CBLK_RESTORING_ON, &cblk->flags) & CBLK_RESTORING_MSK)) {
1164         LOGW("dead IAudioTrack, creating a new one from %s TID %d",
1165              fromStart ? "start()" : "obtainBuffer()", gettid());
1166 
1167         // signal old cblk condition so that other threads waiting for available buffers stop
1168         // waiting now
1169         cblk->cv.broadcast();
1170         cblk->lock.unlock();
1171 
1172         // refresh the audio configuration cache in this process to make sure we get new
1173         // output parameters in getOutput_l() and createTrack_l()
1174         AudioSystem::clearAudioConfigCache();
1175 
1176         // if the new IAudioTrack is created, createTrack_l() will modify the
1177         // following member variables: mAudioTrack, mCblkMemory and mCblk.
1178         // It will also delete the strong references on previous IAudioTrack and IMemory
1179         result = createTrack_l(mStreamType,
1180                                cblk->sampleRate,
1181                                mFormat,
1182                                mChannelMask,
1183                                mFrameCount,
1184                                mFlags,
1185                                mSharedBuffer,
1186                                getOutput_l(),
1187                                false);
1188 
1189         if (result == NO_ERROR) {
1190             uint32_t user = cblk->user;
1191             uint32_t server = cblk->server;
1192             // restore write index and set other indexes to reflect empty buffer status
1193             mCblk->user = user;
1194             mCblk->server = user;
1195             mCblk->userBase = user;
1196             mCblk->serverBase = user;
1197             // restore loop: this is not guaranteed to succeed if new frame count is not
1198             // compatible with loop length
1199             setLoop_l(cblk->loopStart, cblk->loopEnd, cblk->loopCount);
1200             if (!fromStart) {
1201                 mCblk->bufferTimeoutMs = MAX_RUN_TIMEOUT_MS;
1202                 // Make sure that a client relying on callback events indicating underrun or
1203                 // the actual amount of audio frames played (e.g SoundPool) receives them.
1204                 if (mSharedBuffer == 0) {
1205                     uint32_t frames = 0;
1206                     if (user > server) {
1207                         frames = ((user - server) > mCblk->frameCount) ?
1208                                 mCblk->frameCount : (user - server);
1209                         memset(mCblk->buffers, 0, frames * mCblk->frameSize);
1210                     }
1211                     // restart playback even if buffer is not completely filled.
1212                     android_atomic_or(CBLK_FORCEREADY_ON, &mCblk->flags);
1213                     // stepUser() clears CBLK_UNDERRUN_ON flag enabling underrun callbacks to
1214                     // the client
1215                     mCblk->stepUser(frames);
1216                 }
1217             }
1218             if (mActive) {
1219                 result = mAudioTrack->start();
1220                 LOGW_IF(result != NO_ERROR, "restoreTrack_l() start() failed status %d", result);
1221             }
1222             if (fromStart && result == NO_ERROR) {
1223                 mNewPosition = mCblk->server + mUpdatePeriod;
1224             }
1225         }
1226         if (result != NO_ERROR) {
1227             android_atomic_and(~CBLK_RESTORING_ON, &cblk->flags);
1228             LOGW_IF(result != NO_ERROR, "restoreTrack_l() failed status %d", result);
1229         }
1230         mRestoreStatus = result;
1231         // signal old cblk condition for other threads waiting for restore completion
1232         android_atomic_or(CBLK_RESTORED_ON, &cblk->flags);
1233         cblk->cv.broadcast();
1234     } else {
1235         if (!(cblk->flags & CBLK_RESTORED_MSK)) {
1236             LOGW("dead IAudioTrack, waiting for a new one TID %d", gettid());
1237             mLock.unlock();
1238             result = cblk->cv.waitRelative(cblk->lock, milliseconds(RESTORE_TIMEOUT_MS));
1239             if (result == NO_ERROR) {
1240                 result = mRestoreStatus;
1241             }
1242             cblk->lock.unlock();
1243             mLock.lock();
1244         } else {
1245             LOGW("dead IAudioTrack, already restored TID %d", gettid());
1246             result = mRestoreStatus;
1247             cblk->lock.unlock();
1248         }
1249     }
1250     LOGV("restoreTrack_l() status %d mActive %d cblk %p, old cblk %p flags %08x old flags %08x",
1251          result, mActive, mCblk, cblk, mCblk->flags, cblk->flags);
1252 
1253     if (result == NO_ERROR) {
1254         // from now on we switch to the newly created cblk
1255         cblk = mCblk;
1256     }
1257     cblk->lock.lock();
1258 
1259     LOGW_IF(result != NO_ERROR, "restoreTrack_l() error %d TID %d", result, gettid());
1260 
1261     return result;
1262 }
1263 
dump(int fd,const Vector<String16> & args) const1264 status_t AudioTrack::dump(int fd, const Vector<String16>& args) const
1265 {
1266 
1267     const size_t SIZE = 256;
1268     char buffer[SIZE];
1269     String8 result;
1270 
1271     result.append(" AudioTrack::dump\n");
1272     snprintf(buffer, 255, "  stream type(%d), left - right volume(%f, %f)\n", mStreamType, mVolume[0], mVolume[1]);
1273     result.append(buffer);
1274     snprintf(buffer, 255, "  format(%d), channel count(%d), frame count(%d)\n", mFormat, mChannelCount, mCblk->frameCount);
1275     result.append(buffer);
1276     snprintf(buffer, 255, "  sample rate(%d), status(%d), muted(%d)\n", (mCblk == 0) ? 0 : mCblk->sampleRate, mStatus, mMuted);
1277     result.append(buffer);
1278     snprintf(buffer, 255, "  active(%d), latency (%d)\n", mActive, mLatency);
1279     result.append(buffer);
1280     ::write(fd, result.string(), result.size());
1281     return NO_ERROR;
1282 }
1283 
1284 // =========================================================================
1285 
AudioTrackThread(AudioTrack & receiver,bool bCanCallJava)1286 AudioTrack::AudioTrackThread::AudioTrackThread(AudioTrack& receiver, bool bCanCallJava)
1287     : Thread(bCanCallJava), mReceiver(receiver)
1288 {
1289 }
1290 
threadLoop()1291 bool AudioTrack::AudioTrackThread::threadLoop()
1292 {
1293     return mReceiver.processAudioBuffer(this);
1294 }
1295 
readyToRun()1296 status_t AudioTrack::AudioTrackThread::readyToRun()
1297 {
1298     return NO_ERROR;
1299 }
1300 
onFirstRef()1301 void AudioTrack::AudioTrackThread::onFirstRef()
1302 {
1303 }
1304 
1305 // =========================================================================
1306 
1307 
audio_track_cblk_t()1308 audio_track_cblk_t::audio_track_cblk_t()
1309     : lock(Mutex::SHARED), cv(Condition::SHARED), user(0), server(0),
1310     userBase(0), serverBase(0), buffers(0), frameCount(0),
1311     loopStart(UINT_MAX), loopEnd(UINT_MAX), loopCount(0), volumeLR(0),
1312     sendLevel(0), flags(0)
1313 {
1314 }
1315 
stepUser(uint32_t frameCount)1316 uint32_t audio_track_cblk_t::stepUser(uint32_t frameCount)
1317 {
1318     uint32_t u = this->user;
1319 
1320     u += frameCount;
1321     // Ensure that user is never ahead of server for AudioRecord
1322     if (flags & CBLK_DIRECTION_MSK) {
1323         // If stepServer() has been called once, switch to normal obtainBuffer() timeout period
1324         if (bufferTimeoutMs == MAX_STARTUP_TIMEOUT_MS-1) {
1325             bufferTimeoutMs = MAX_RUN_TIMEOUT_MS;
1326         }
1327     } else if (u > this->server) {
1328         LOGW("stepServer occured after track reset");
1329         u = this->server;
1330     }
1331 
1332     if (u >= userBase + this->frameCount) {
1333         userBase += this->frameCount;
1334     }
1335 
1336     this->user = u;
1337 
1338     // Clear flow control error condition as new data has been written/read to/from buffer.
1339     if (flags & CBLK_UNDERRUN_MSK) {
1340         android_atomic_and(~CBLK_UNDERRUN_MSK, &flags);
1341     }
1342 
1343     return u;
1344 }
1345 
stepServer(uint32_t frameCount)1346 bool audio_track_cblk_t::stepServer(uint32_t frameCount)
1347 {
1348     if (!tryLock()) {
1349         LOGW("stepServer() could not lock cblk");
1350         return false;
1351     }
1352 
1353     uint32_t s = this->server;
1354 
1355     s += frameCount;
1356     if (flags & CBLK_DIRECTION_MSK) {
1357         // Mark that we have read the first buffer so that next time stepUser() is called
1358         // we switch to normal obtainBuffer() timeout period
1359         if (bufferTimeoutMs == MAX_STARTUP_TIMEOUT_MS) {
1360             bufferTimeoutMs = MAX_STARTUP_TIMEOUT_MS - 1;
1361         }
1362         // It is possible that we receive a flush()
1363         // while the mixer is processing a block: in this case,
1364         // stepServer() is called After the flush() has reset u & s and
1365         // we have s > u
1366         if (s > this->user) {
1367             LOGW("stepServer occured after track reset");
1368             s = this->user;
1369         }
1370     }
1371 
1372     if (s >= loopEnd) {
1373         LOGW_IF(s > loopEnd, "stepServer: s %u > loopEnd %u", s, loopEnd);
1374         s = loopStart;
1375         if (--loopCount == 0) {
1376             loopEnd = UINT_MAX;
1377             loopStart = UINT_MAX;
1378         }
1379     }
1380     if (s >= serverBase + this->frameCount) {
1381         serverBase += this->frameCount;
1382     }
1383 
1384     this->server = s;
1385 
1386     if (!(flags & CBLK_INVALID_MSK)) {
1387         cv.signal();
1388     }
1389     lock.unlock();
1390     return true;
1391 }
1392 
buffer(uint32_t offset) const1393 void* audio_track_cblk_t::buffer(uint32_t offset) const
1394 {
1395     return (int8_t *)this->buffers + (offset - userBase) * this->frameSize;
1396 }
1397 
framesAvailable()1398 uint32_t audio_track_cblk_t::framesAvailable()
1399 {
1400     Mutex::Autolock _l(lock);
1401     return framesAvailable_l();
1402 }
1403 
framesAvailable_l()1404 uint32_t audio_track_cblk_t::framesAvailable_l()
1405 {
1406     uint32_t u = this->user;
1407     uint32_t s = this->server;
1408 
1409     if (flags & CBLK_DIRECTION_MSK) {
1410         uint32_t limit = (s < loopStart) ? s : loopStart;
1411         return limit + frameCount - u;
1412     } else {
1413         return frameCount + u - s;
1414     }
1415 }
1416 
framesReady()1417 uint32_t audio_track_cblk_t::framesReady()
1418 {
1419     uint32_t u = this->user;
1420     uint32_t s = this->server;
1421 
1422     if (flags & CBLK_DIRECTION_MSK) {
1423         if (u < loopEnd) {
1424             return u - s;
1425         } else {
1426             // do not block on mutex shared with client on AudioFlinger side
1427             if (!tryLock()) {
1428                 LOGW("framesReady() could not lock cblk");
1429                 return 0;
1430             }
1431             uint32_t frames = UINT_MAX;
1432             if (loopCount >= 0) {
1433                 frames = (loopEnd - loopStart)*loopCount + u - s;
1434             }
1435             lock.unlock();
1436             return frames;
1437         }
1438     } else {
1439         return s - u;
1440     }
1441 }
1442 
tryLock()1443 bool audio_track_cblk_t::tryLock()
1444 {
1445     // the code below simulates lock-with-timeout
1446     // we MUST do this to protect the AudioFlinger server
1447     // as this lock is shared with the client.
1448     status_t err;
1449 
1450     err = lock.tryLock();
1451     if (err == -EBUSY) { // just wait a bit
1452         usleep(1000);
1453         err = lock.tryLock();
1454     }
1455     if (err != NO_ERROR) {
1456         // probably, the client just died.
1457         return false;
1458     }
1459     return true;
1460 }
1461 
1462 // -------------------------------------------------------------------------
1463 
1464 }; // namespace android
1465 
1466