android_AudioSfDecoder.cpp revision 5050a75e342ce45794d56666cddde3d46472acc7
1/*
2 * Copyright (C) 2011 The Android Open Source Project
3 *
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
7 *
8 *      http://www.apache.org/licenses/LICENSE-2.0
9 *
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
15 */
16
17//#define USE_LOG SLAndroidLogLevel_Debug
18
19#include "sles_allinclusive.h"
20#include "android/android_AudioSfDecoder.h"
21
22#include <media/stagefright/foundation/ADebug.h>
23
24
25#define SIZE_CACHED_HIGH_BYTES 1000000
26#define SIZE_CACHED_MED_BYTES   700000
27#define SIZE_CACHED_LOW_BYTES   400000
28
29namespace android {
30
31// keep in sync with the entries of kPcmDecodeMetadataKeys[] defined in android_AudioSfDecoder.h
32#define ANDROID_KEY_INDEX_PCMFORMAT_NUMCHANNELS   0
33#define ANDROID_KEY_INDEX_PCMFORMAT_SAMPLESPERSEC 1
34#define ANDROID_KEY_INDEX_PCMFORMAT_BITSPERSAMPLE 2
35#define ANDROID_KEY_INDEX_PCMFORMAT_CONTAINERSIZE 3
36#define ANDROID_KEY_INDEX_PCMFORMAT_CHANNELMASK   4
37#define ANDROID_KEY_INDEX_PCMFORMAT_ENDIANNESS    5
38
39//--------------------------------------------------------------------------------------------------
40AudioSfDecoder::AudioSfDecoder(const AudioPlayback_Parameters* params) : GenericPlayer(params),
41        mDataSource(0),
42        mAudioSource(0),
43        mAudioSourceStarted(false),
44        mBitrate(-1),
45        mChannelMask(UNKNOWN_CHANNELMASK),
46        mDurationUsec(ANDROID_UNKNOWN_TIME),
47        mDecodeBuffer(NULL),
48        mSeekTimeMsec(0),
49        mLastDecodedPositionUs(ANDROID_UNKNOWN_TIME),
50        mPcmFormatKeyCount(0)
51{
52    SL_LOGD("AudioSfDecoder::AudioSfDecoder()");
53}
54
55
56AudioSfDecoder::~AudioSfDecoder() {
57    SL_LOGD("AudioSfDecoder::~AudioSfDecoder()");
58}
59
60
61void AudioSfDecoder::preDestroy() {
62    GenericPlayer::preDestroy();
63    SL_LOGD("AudioSfDecoder::preDestroy()");
64    {
65        Mutex::Autolock _l(mBufferSourceLock);
66
67        if (NULL != mDecodeBuffer) {
68            mDecodeBuffer->release();
69            mDecodeBuffer = NULL;
70        }
71
72        if ((mAudioSource != 0) && mAudioSourceStarted) {
73            mAudioSource->stop();
74            mAudioSourceStarted = false;
75        }
76    }
77}
78
79
80//--------------------------------------------------
81void AudioSfDecoder::play() {
82    SL_LOGD("AudioSfDecoder::play");
83
84    GenericPlayer::play();
85    (new AMessage(kWhatDecode, id()))->post();
86}
87
88
89void AudioSfDecoder::getPositionMsec(int* msec) {
90    int64_t timeUsec = getPositionUsec();
91    if (timeUsec == ANDROID_UNKNOWN_TIME) {
92        *msec = ANDROID_UNKNOWN_TIME;
93    } else {
94        mPositionMsec = timeUsec / 1000;
95        *msec = mPositionMsec;
96    }
97}
98
99
100void AudioSfDecoder::startPrefetch_async() {
101    SL_LOGV("AudioSfDecoder::startPrefetch_async()");
102
103    if (wantPrefetch()) {
104        SL_LOGV("AudioSfDecoder::startPrefetch_async(): sending check cache msg");
105
106        mStateFlags |= kFlagPreparing | kFlagBuffering;
107
108        (new AMessage(kWhatCheckCache, id()))->post();
109    }
110}
111
112
113//--------------------------------------------------
114uint32_t AudioSfDecoder::getPcmFormatKeyCount() {
115    android::Mutex::Autolock autoLock(mPcmFormatLock);
116    return mPcmFormatKeyCount;
117}
118
119
120//--------------------------------------------------
121bool AudioSfDecoder::getPcmFormatKeySize(uint32_t index, uint32_t* pKeySize) {
122    uint32_t keyCount = getPcmFormatKeyCount();
123    if (index >= keyCount) {
124        return false;
125    } else {
126        *pKeySize = strlen(kPcmDecodeMetadataKeys[index]) +1;
127        return true;
128    }
129}
130
131
132//--------------------------------------------------
133bool AudioSfDecoder::getPcmFormatKeyName(uint32_t index, uint32_t keySize, char* keyName) {
134    uint32_t actualKeySize;
135    if (!getPcmFormatKeySize(index, &actualKeySize)) {
136        return false;
137    }
138    if (keySize < actualKeySize) {
139        return false;
140    }
141    strncpy(keyName, kPcmDecodeMetadataKeys[index], actualKeySize);
142    return true;
143}
144
145
146//--------------------------------------------------
147bool AudioSfDecoder::getPcmFormatValueSize(uint32_t index, uint32_t* pValueSize) {
148    uint32_t keyCount = getPcmFormatKeyCount();
149    if (index >= keyCount) {
150        *pValueSize = 0;
151        return false;
152    } else {
153        *pValueSize = sizeof(uint32_t);
154        return true;
155    }
156}
157
158
159//--------------------------------------------------
160bool AudioSfDecoder::getPcmFormatKeyValue(uint32_t index, uint32_t size, uint32_t* pValue) {
161    uint32_t valueSize = 0;
162    if (!getPcmFormatValueSize(index, &valueSize)) {
163        return false;
164    } else if (size != valueSize) {
165        // this ensures we are accessing mPcmFormatValues with a valid size for that index
166        SL_LOGE("Error retrieving metadata value at index %d: using size of %d, should be %d",
167                index, size, valueSize);
168        return false;
169    } else {
170        *pValue = mPcmFormatValues[index];
171        return true;
172    }
173}
174
175
176//--------------------------------------------------
177// Event handlers
178//  it is strictly verboten to call those methods outside of the event loop
179
180// Initializes the data and audio sources, and update the PCM format info
181// post-condition: upon successful initialization based on the player data locator
182//    GenericPlayer::onPrepare() was called
183//    mDataSource != 0
184//    mAudioSource != 0
185//    mAudioSourceStarted == true
186void AudioSfDecoder::onPrepare() {
187    SL_LOGD("AudioSfDecoder::onPrepare()");
188    Mutex::Autolock _l(mBufferSourceLock);
189
190    // Initialize the PCM format info with the known parameters before the start of the decode
191    mPcmFormatValues[ANDROID_KEY_INDEX_PCMFORMAT_BITSPERSAMPLE] = SL_PCMSAMPLEFORMAT_FIXED_16;
192    mPcmFormatValues[ANDROID_KEY_INDEX_PCMFORMAT_CONTAINERSIZE] = 16;
193    mPcmFormatValues[ANDROID_KEY_INDEX_PCMFORMAT_ENDIANNESS] = SL_BYTEORDER_LITTLEENDIAN;
194    //    initialization with the default values: they will be replaced by the actual values
195    //      once the decoder has figured them out
196    mPcmFormatValues[ANDROID_KEY_INDEX_PCMFORMAT_NUMCHANNELS] = mChannelCount;
197    mPcmFormatValues[ANDROID_KEY_INDEX_PCMFORMAT_SAMPLESPERSEC] = mSampleRateHz;
198    mPcmFormatValues[ANDROID_KEY_INDEX_PCMFORMAT_CHANNELMASK] = mChannelMask;
199
200    //---------------------------------
201    // Instantiate and initialize the data source for the decoder
202    sp<DataSource> dataSource;
203
204    switch (mDataLocatorType) {
205
206    case kDataLocatorNone:
207        SL_LOGE("AudioSfDecoder::onPrepare: no data locator set");
208        notifyPrepared(MEDIA_ERROR_BASE);
209        return;
210
211    case kDataLocatorUri:
212        dataSource = DataSource::CreateFromURI(mDataLocator.uriRef);
213        if (dataSource == NULL) {
214            SL_LOGE("AudioSfDecoder::onPrepare(): Error opening %s", mDataLocator.uriRef);
215            notifyPrepared(MEDIA_ERROR_BASE);
216            return;
217        }
218        break;
219
220    case kDataLocatorFd:
221    {
222        dataSource = new FileSource(
223                mDataLocator.fdi.fd, mDataLocator.fdi.offset, mDataLocator.fdi.length);
224        status_t err = dataSource->initCheck();
225        if (err != OK) {
226            notifyPrepared(err);
227            return;
228        }
229        break;
230    }
231
232    default:
233        TRESPASS();
234    }
235
236    //---------------------------------
237    // Instanciate and initialize the decoder attached to the data source
238    sp<MediaExtractor> extractor = MediaExtractor::Create(dataSource);
239    if (extractor == NULL) {
240        SL_LOGE("AudioSfDecoder::onPrepare: Could not instantiate extractor.");
241        notifyPrepared(ERROR_UNSUPPORTED);
242        return;
243    }
244
245    ssize_t audioTrackIndex = -1;
246    bool isRawAudio = false;
247    for (size_t i = 0; i < extractor->countTracks(); ++i) {
248        sp<MetaData> meta = extractor->getTrackMetaData(i);
249
250        const char *mime;
251        CHECK(meta->findCString(kKeyMIMEType, &mime));
252
253        if (!strncasecmp("audio/", mime, 6)) {
254            audioTrackIndex = i;
255
256            if (!strcasecmp(MEDIA_MIMETYPE_AUDIO_RAW, mime)) {
257                isRawAudio = true;
258            }
259            break;
260        }
261    }
262
263    if (audioTrackIndex < 0) {
264        SL_LOGE("AudioSfDecoder::onPrepare: Could not find a supported audio track.");
265        notifyPrepared(ERROR_UNSUPPORTED);
266        return;
267    }
268
269    sp<MediaSource> source = extractor->getTrack(audioTrackIndex);
270    sp<MetaData> meta = source->getFormat();
271
272    // we can't trust the OMXCodec (if there is one) to issue a INFO_FORMAT_CHANGED so we want
273    // to have some meaningful values as soon as possible.
274    bool hasChannelCount = meta->findInt32(kKeyChannelCount, &mChannelCount);
275    int32_t sr;
276    bool hasSampleRate = meta->findInt32(kKeySampleRate, &sr);
277    if (hasSampleRate) {
278        mSampleRateHz = (uint32_t) sr;
279    }
280
281    off64_t size;
282    int64_t durationUs;
283    if (dataSource->getSize(&size) == OK
284            && meta->findInt64(kKeyDuration, &durationUs)) {
285        if (durationUs != 0) {
286            mBitrate = size * 8000000ll / durationUs;  // in bits/sec
287        } else {
288            mBitrate = -1;
289        }
290        mDurationUsec = durationUs;
291        mDurationMsec = durationUs / 1000;
292    } else {
293        mBitrate = -1;
294        mDurationUsec = ANDROID_UNKNOWN_TIME;
295        mDurationMsec = ANDROID_UNKNOWN_TIME;
296    }
297
298    // the audio content is not raw PCM, so we need a decoder
299    if (!isRawAudio) {
300        OMXClient client;
301        CHECK_EQ(client.connect(), (status_t)OK);
302
303        source = OMXCodec::Create(
304                client.interface(), meta, false /* createEncoder */,
305                source);
306
307        if (source == NULL) {
308            SL_LOGE("AudioSfDecoder::onPrepare: Could not instantiate decoder.");
309            notifyPrepared(ERROR_UNSUPPORTED);
310            return;
311        }
312
313        meta = source->getFormat();
314    }
315
316
317    if (source->start() != OK) {
318        SL_LOGE("AudioSfDecoder::onPrepare: Failed to start source/decoder.");
319        notifyPrepared(MEDIA_ERROR_BASE);
320        return;
321    }
322
323    //---------------------------------
324    // The data source, and audio source (a decoder if required) are ready to be used
325    mDataSource = dataSource;
326    mAudioSource = source;
327    mAudioSourceStarted = true;
328
329    if (!hasChannelCount) {
330        CHECK(meta->findInt32(kKeyChannelCount, &mChannelCount));
331    }
332
333    if (!hasSampleRate) {
334        CHECK(meta->findInt32(kKeySampleRate, &sr));
335        mSampleRateHz = (uint32_t) sr;
336    }
337    // FIXME add code below once channel mask support is in, currently initialized to default
338    //    if (meta->findInt32(kKeyChannelMask, &mChannelMask)) {
339    //        mPcmFormatValues[ANDROID_KEY_INDEX_PCMFORMAT_CHANNELMASK] = mChannelMask;
340    //    }
341
342    if (!wantPrefetch()) {
343        SL_LOGV("AudioSfDecoder::onPrepare: no need to prefetch");
344        // doesn't need prefetching, notify good to go
345        mCacheStatus = kStatusHigh;
346        mCacheFill = 1000;
347        notifyStatus();
348        notifyCacheFill();
349    }
350
351    {
352        android::Mutex::Autolock autoLock(mPcmFormatLock);
353        mPcmFormatKeyCount = NB_PCMMETADATA_KEYS;
354        mPcmFormatValues[ANDROID_KEY_INDEX_PCMFORMAT_SAMPLESPERSEC] = mSampleRateHz;
355        mPcmFormatValues[ANDROID_KEY_INDEX_PCMFORMAT_NUMCHANNELS] = mChannelCount;
356    }
357
358    // at this point we have enough information about the source to create the sink that
359    // will consume the data
360    createAudioSink();
361
362    GenericPlayer::onPrepare();
363    SL_LOGD("AudioSfDecoder::onPrepare() done, mStateFlags=0x%x", mStateFlags);
364}
365
366
367void AudioSfDecoder::onPause() {
368    SL_LOGV("AudioSfDecoder::onPause()");
369    GenericPlayer::onPause();
370    pauseAudioSink();
371}
372
373
374void AudioSfDecoder::onPlay() {
375    SL_LOGV("AudioSfDecoder::onPlay()");
376    GenericPlayer::onPlay();
377    startAudioSink();
378}
379
380
381void AudioSfDecoder::onSeek(const sp<AMessage> &msg) {
382    SL_LOGV("AudioSfDecoder::onSeek");
383    int64_t timeMsec;
384    CHECK(msg->findInt64(WHATPARAM_SEEK_SEEKTIME_MS, &timeMsec));
385
386    Mutex::Autolock _l(mTimeLock);
387    mStateFlags |= kFlagSeeking;
388    mSeekTimeMsec = timeMsec;
389    mLastDecodedPositionUs = ANDROID_UNKNOWN_TIME;
390}
391
392
393void AudioSfDecoder::onLoop(const sp<AMessage> &msg) {
394    SL_LOGV("AudioSfDecoder::onLoop");
395    int32_t loop;
396    CHECK(msg->findInt32(WHATPARAM_LOOP_LOOPING, &loop));
397
398    if (loop) {
399        //SL_LOGV("AudioSfDecoder::onLoop start looping");
400        mStateFlags |= kFlagLooping;
401    } else {
402        //SL_LOGV("AudioSfDecoder::onLoop stop looping");
403        mStateFlags &= ~kFlagLooping;
404    }
405}
406
407
408void AudioSfDecoder::onCheckCache(const sp<AMessage> &msg) {
409    //SL_LOGV("AudioSfDecoder::onCheckCache");
410    bool eos;
411    CacheStatus_t status = getCacheRemaining(&eos);
412
413    if (eos || status == kStatusHigh
414            || ((mStateFlags & kFlagPreparing) && (status >= kStatusEnough))) {
415        if (mStateFlags & kFlagPlaying) {
416            startAudioSink();
417        }
418        mStateFlags &= ~kFlagBuffering;
419
420        SL_LOGV("AudioSfDecoder::onCheckCache: buffering done.");
421
422        if (mStateFlags & kFlagPreparing) {
423            //SL_LOGV("AudioSfDecoder::onCheckCache: preparation done.");
424            mStateFlags &= ~kFlagPreparing;
425        }
426
427        if (mStateFlags & kFlagPlaying) {
428            (new AMessage(kWhatDecode, id()))->post();
429        }
430        return;
431    }
432
433    msg->post(100000);
434}
435
436
437void AudioSfDecoder::onDecode() {
438    SL_LOGV("AudioSfDecoder::onDecode");
439
440    //-------------------------------- Need to buffer some more before decoding?
441    bool eos;
442    if (mDataSource == 0) {
443        // application set play state to paused which failed, then set play state to playing
444        return;
445    }
446
447    if (wantPrefetch()
448            && (getCacheRemaining(&eos) == kStatusLow)
449            && !eos) {
450        SL_LOGV("buffering more.");
451
452        if (mStateFlags & kFlagPlaying) {
453            pauseAudioSink();
454        }
455        mStateFlags |= kFlagBuffering;
456        (new AMessage(kWhatCheckCache, id()))->post(100000);
457        return;
458    }
459
460    if (!(mStateFlags & (kFlagPlaying | kFlagBuffering | kFlagPreparing))) {
461        // don't decode if we're not buffering, prefetching or playing
462        //SL_LOGV("don't decode: not buffering, prefetching or playing");
463        return;
464    }
465
466    //-------------------------------- Decode
467    status_t err;
468    MediaSource::ReadOptions readOptions;
469    if (mStateFlags & kFlagSeeking) {
470        assert(mSeekTimeMsec != ANDROID_UNKNOWN_TIME);
471        readOptions.setSeekTo(mSeekTimeMsec * 1000);
472    }
473
474    int64_t timeUsec = ANDROID_UNKNOWN_TIME;
475    {
476        Mutex::Autolock _l(mBufferSourceLock);
477
478        if (NULL != mDecodeBuffer) {
479            // the current decoded buffer hasn't been rendered, drop it
480            mDecodeBuffer->release();
481            mDecodeBuffer = NULL;
482        }
483        if(!mAudioSourceStarted) {
484            return;
485        }
486        err = mAudioSource->read(&mDecodeBuffer, &readOptions);
487        if (err == OK) {
488            CHECK(mDecodeBuffer->meta_data()->findInt64(kKeyTime, &timeUsec));
489        }
490    }
491
492    {
493        Mutex::Autolock _l(mTimeLock);
494        if (mStateFlags & kFlagSeeking) {
495            mStateFlags &= ~kFlagSeeking;
496            mSeekTimeMsec = ANDROID_UNKNOWN_TIME;
497        }
498        if (timeUsec != ANDROID_UNKNOWN_TIME) {
499            mLastDecodedPositionUs = timeUsec;
500        }
501    }
502
503    //-------------------------------- Handle return of decode
504    if (err != OK) {
505        bool continueDecoding = false;
506        switch(err) {
507            case ERROR_END_OF_STREAM:
508                if (0 < mDurationUsec) {
509                    Mutex::Autolock _l(mTimeLock);
510                    mLastDecodedPositionUs = mDurationUsec;
511                }
512                // handle notification and looping at end of stream
513                if (mStateFlags & kFlagPlaying) {
514                    notify(PLAYEREVENT_ENDOFSTREAM, 1, true);
515                }
516                if (mStateFlags & kFlagLooping) {
517                    seek(0);
518                    // kick-off decoding again
519                    continueDecoding = true;
520                }
521                break;
522            case INFO_FORMAT_CHANGED:
523                SL_LOGD("MediaSource::read encountered INFO_FORMAT_CHANGED");
524                // reconfigure output
525                {
526                    Mutex::Autolock _l(mBufferSourceLock);
527                    hasNewDecodeParams();
528                }
529                continueDecoding = true;
530                break;
531            case INFO_DISCONTINUITY:
532                SL_LOGD("MediaSource::read encountered INFO_DISCONTINUITY");
533                continueDecoding = true;
534                break;
535            default:
536                SL_LOGE("MediaSource::read returned error %d", err);
537                break;
538        }
539        if (continueDecoding) {
540            if (NULL == mDecodeBuffer) {
541                (new AMessage(kWhatDecode, id()))->post();
542                return;
543            }
544        } else {
545            return;
546        }
547    }
548
549    //-------------------------------- Render
550    sp<AMessage> msg = new AMessage(kWhatRender, id());
551    msg->post();
552}
553
554
555void AudioSfDecoder::onRender() {
556    //SL_LOGV("AudioSfDecoder::onRender");
557
558    Mutex::Autolock _l(mBufferSourceLock);
559
560    if (NULL == mDecodeBuffer) {
561        // nothing to render, move along
562        SL_LOGV("AudioSfDecoder::onRender NULL buffer, exiting");
563        return;
564    }
565
566    mDecodeBuffer->release();
567    mDecodeBuffer = NULL;
568
569}
570
571
572void AudioSfDecoder::onMessageReceived(const sp<AMessage> &msg) {
573    switch (msg->what()) {
574        case kWhatPrepare:
575            onPrepare();
576            break;
577
578        case kWhatDecode:
579            onDecode();
580            break;
581
582        case kWhatRender:
583            onRender();
584            break;
585
586        case kWhatCheckCache:
587            onCheckCache(msg);
588            break;
589
590        case kWhatNotif:
591            onNotify(msg);
592            break;
593
594        case kWhatPlay:
595            onPlay();
596            break;
597
598        case kWhatPause:
599            onPause();
600            break;
601
602/*
603        case kWhatSeek:
604            onSeek(msg);
605            break;
606
607        case kWhatLoop:
608            onLoop(msg);
609            break;
610*/
611        default:
612            GenericPlayer::onMessageReceived(msg);
613            break;
614    }
615}
616
617//--------------------------------------------------
618// Prepared state, prefetch status notifications
619void AudioSfDecoder::notifyPrepared(status_t prepareRes) {
620    notify(PLAYEREVENT_PREPARED, (int32_t)prepareRes, true);
621
622}
623
624
625void AudioSfDecoder::onNotify(const sp<AMessage> &msg) {
626    notif_cbf_t notifyClient;
627    void*       notifyUser;
628    {
629        android::Mutex::Autolock autoLock(mNotifyClientLock);
630        if (NULL == mNotifyClient) {
631            return;
632        } else {
633            notifyClient = mNotifyClient;
634            notifyUser   = mNotifyUser;
635        }
636    }
637    int32_t val;
638    if (msg->findInt32(PLAYEREVENT_PREFETCHSTATUSCHANGE, &val)) {
639        SL_LOGV("\tASfPlayer notifying %s = %d", PLAYEREVENT_PREFETCHSTATUSCHANGE, val);
640        notifyClient(kEventPrefetchStatusChange, val, 0, notifyUser);
641    }
642    else if (msg->findInt32(PLAYEREVENT_PREFETCHFILLLEVELUPDATE, &val)) {
643        SL_LOGV("\tASfPlayer notifying %s = %d", PLAYEREVENT_PREFETCHFILLLEVELUPDATE, val);
644        notifyClient(kEventPrefetchFillLevelUpdate, val, 0, notifyUser);
645    }
646    else if (msg->findInt32(PLAYEREVENT_ENDOFSTREAM, &val)) {
647        SL_LOGV("\tASfPlayer notifying %s = %d", PLAYEREVENT_ENDOFSTREAM, val);
648        notifyClient(kEventEndOfStream, val, 0, notifyUser);
649    }
650    else {
651        GenericPlayer::onNotify(msg);
652    }
653}
654
655
656//--------------------------------------------------
657// Private utility functions
658
659bool AudioSfDecoder::wantPrefetch() {
660    if (mDataSource != 0) {
661        return (mDataSource->flags() & DataSource::kWantsPrefetching);
662    } else {
663        // happens if an improper data locator was passed, if the media extractor couldn't be
664        //  initialized, if there is no audio track in the media, if the OMX decoder couldn't be
665        //  instantiated, if the source couldn't be opened, or if the MediaSource
666        //  couldn't be started
667        SL_LOGV("AudioSfDecoder::wantPrefetch() tries to access NULL mDataSource");
668        return false;
669    }
670}
671
672
673int64_t AudioSfDecoder::getPositionUsec() {
674    Mutex::Autolock _l(mTimeLock);
675    if (mStateFlags & kFlagSeeking) {
676        return mSeekTimeMsec * 1000;
677    } else {
678        if (mLastDecodedPositionUs < 0) {
679            return ANDROID_UNKNOWN_TIME;
680        } else {
681            return mLastDecodedPositionUs;
682        }
683    }
684}
685
686
687CacheStatus_t AudioSfDecoder::getCacheRemaining(bool *eos) {
688    sp<NuCachedSource2> cachedSource =
689        static_cast<NuCachedSource2 *>(mDataSource.get());
690
691    CacheStatus_t oldStatus = mCacheStatus;
692
693    status_t finalStatus;
694    size_t dataRemaining = cachedSource->approxDataRemaining(&finalStatus);
695    *eos = (finalStatus != OK);
696
697    CHECK_GE(mBitrate, 0);
698
699    int64_t dataRemainingUs = dataRemaining * 8000000ll / mBitrate;
700    //SL_LOGV("AudioSfDecoder::getCacheRemaining: approx %.2f secs remaining (eos=%d)",
701    //       dataRemainingUs / 1E6, *eos);
702
703    if (*eos) {
704        // data is buffered up to the end of the stream, it can't get any better than this
705        mCacheStatus = kStatusHigh;
706        mCacheFill = 1000;
707
708    } else {
709        if (mDurationUsec > 0) {
710            // known duration:
711
712            //   fill level is ratio of how much has been played + how much is
713            //   cached, divided by total duration
714            uint32_t currentPositionUsec = getPositionUsec();
715            if (currentPositionUsec == ANDROID_UNKNOWN_TIME) {
716                // if we don't know where we are, assume the worst for the fill ratio
717                currentPositionUsec = 0;
718            }
719            if (mDurationUsec > 0) {
720                mCacheFill = (int16_t) ((1000.0
721                        * (double)(currentPositionUsec + dataRemainingUs) / mDurationUsec));
722            } else {
723                mCacheFill = 0;
724            }
725            //SL_LOGV("cacheFill = %d", mCacheFill);
726
727            //   cache status is evaluated against duration thresholds
728            if (dataRemainingUs > DURATION_CACHED_HIGH_MS*1000) {
729                mCacheStatus = kStatusHigh;
730                //LOGV("high");
731            } else if (dataRemainingUs > DURATION_CACHED_MED_MS*1000) {
732                //LOGV("enough");
733                mCacheStatus = kStatusEnough;
734            } else if (dataRemainingUs < DURATION_CACHED_LOW_MS*1000) {
735                //LOGV("low");
736                mCacheStatus = kStatusLow;
737            } else {
738                mCacheStatus = kStatusIntermediate;
739            }
740
741        } else {
742            // unknown duration:
743
744            //   cache status is evaluated against cache amount thresholds
745            //   (no duration so we don't have the bitrate either, could be derived from format?)
746            if (dataRemaining > SIZE_CACHED_HIGH_BYTES) {
747                mCacheStatus = kStatusHigh;
748            } else if (dataRemaining > SIZE_CACHED_MED_BYTES) {
749                mCacheStatus = kStatusEnough;
750            } else if (dataRemaining < SIZE_CACHED_LOW_BYTES) {
751                mCacheStatus = kStatusLow;
752            } else {
753                mCacheStatus = kStatusIntermediate;
754            }
755        }
756
757    }
758
759    if (oldStatus != mCacheStatus) {
760        notifyStatus();
761    }
762
763    if (abs(mCacheFill - mLastNotifiedCacheFill) > mCacheFillNotifThreshold) {
764        notifyCacheFill();
765    }
766
767    return mCacheStatus;
768}
769
770
771void AudioSfDecoder::hasNewDecodeParams() {
772
773    if ((mAudioSource != 0) && mAudioSourceStarted) {
774        sp<MetaData> meta = mAudioSource->getFormat();
775
776        CHECK(meta->findInt32(kKeyChannelCount, &mChannelCount));
777
778        SL_LOGV("old sample rate = %d", mSampleRateHz);
779        int32_t sr;
780        CHECK(meta->findInt32(kKeySampleRate, &sr));
781        mSampleRateHz = (uint32_t) sr;
782        SL_LOGV("found new sample rate = %d", mSampleRateHz);
783
784        {
785            android::Mutex::Autolock autoLock(mPcmFormatLock);
786            mPcmFormatValues[ANDROID_KEY_INDEX_PCMFORMAT_NUMCHANNELS] = mChannelCount;
787            mPcmFormatValues[ANDROID_KEY_INDEX_PCMFORMAT_SAMPLESPERSEC] = mSampleRateHz;
788        }
789    }
790
791    // alert users of those params
792    updateAudioSink();
793}
794
795} // namespace android
796