1 /*
2 * Copyright (C) 2009 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 #include <inttypes.h>
18
19 //#define LOG_NDEBUG 0
20 #define LOG_TAG "AudioPlayer"
21 #include <utils/Log.h>
22 #include <cutils/compiler.h>
23
24 #include <binder/IPCThreadState.h>
25 #include <media/AudioTrack.h>
26 #include <media/MediaSource.h>
27 #include <media/openmax/OMX_Audio.h>
28 #include <media/stagefright/foundation/ADebug.h>
29 #include <media/stagefright/foundation/ALookup.h>
30 #include <media/stagefright/foundation/ALooper.h>
31 #include <media/stagefright/MediaDefs.h>
32 #include <media/stagefright/MediaErrors.h>
33 #include <media/stagefright/MetaData.h>
34 #include <media/stagefright/Utils.h>
35
36 #include "AudioPlayer.h"
37
38 namespace android {
39
AudioPlayer(const sp<MediaPlayerBase::AudioSink> & audioSink,uint32_t flags)40 AudioPlayer::AudioPlayer(
41 const sp<MediaPlayerBase::AudioSink> &audioSink,
42 uint32_t flags)
43 : mInputBuffer(NULL),
44 mSampleRate(0),
45 mLatencyUs(0),
46 mFrameSize(0),
47 mNumFramesPlayed(0),
48 mNumFramesPlayedSysTimeUs(ALooper::GetNowUs()),
49 mPositionTimeMediaUs(-1),
50 mPositionTimeRealUs(-1),
51 mSeeking(false),
52 mReachedEOS(false),
53 mFinalStatus(OK),
54 mSeekTimeUs(0),
55 mStarted(false),
56 mIsFirstBuffer(false),
57 mFirstBufferResult(OK),
58 mFirstBuffer(NULL),
59 mAudioSink(audioSink),
60 mPlaying(false),
61 mStartPosUs(0),
62 mCreateFlags(flags) {
63 }
64
~AudioPlayer()65 AudioPlayer::~AudioPlayer() {
66 if (mStarted) {
67 reset();
68 }
69 }
70
setSource(const sp<MediaSource> & source)71 void AudioPlayer::setSource(const sp<MediaSource> &source) {
72 CHECK(mSource == NULL);
73 mSource = source;
74 }
75
76 ALookup<audio_format_t, int32_t> sAudioFormatToPcmEncoding {
77 {
78 { AUDIO_FORMAT_PCM_16_BIT, kAudioEncodingPcm16bit },
79 { AUDIO_FORMAT_PCM_8_BIT, kAudioEncodingPcm8bit },
80 { AUDIO_FORMAT_PCM_FLOAT, kAudioEncodingPcmFloat },
81 }
82 };
83
start(bool sourceAlreadyStarted)84 status_t AudioPlayer::start(bool sourceAlreadyStarted) {
85 CHECK(!mStarted);
86 CHECK(mSource != NULL);
87
88 status_t err;
89 if (!sourceAlreadyStarted) {
90 err = mSource->start();
91
92 if (err != OK) {
93 return err;
94 }
95 }
96
97 // We allow an optional INFO_FORMAT_CHANGED at the very beginning
98 // of playback, if there is one, getFormat below will retrieve the
99 // updated format, if there isn't, we'll stash away the valid buffer
100 // of data to be used on the first audio callback.
101
102 CHECK(mFirstBuffer == NULL);
103
104 MediaSource::ReadOptions options;
105 if (mSeeking) {
106 options.setSeekTo(mSeekTimeUs);
107 mSeeking = false;
108 }
109
110 mFirstBufferResult = mSource->read(&mFirstBuffer, &options);
111 if (mFirstBufferResult == INFO_FORMAT_CHANGED) {
112 ALOGV("INFO_FORMAT_CHANGED!!!");
113
114 CHECK(mFirstBuffer == NULL);
115 mFirstBufferResult = OK;
116 mIsFirstBuffer = false;
117 } else {
118 mIsFirstBuffer = true;
119 }
120
121 sp<MetaData> format = mSource->getFormat();
122
123 if (format == NULL) {
124 ALOGE("No metadata b/118620871");
125 android_errorWriteLog(0x534e4554, "118620871");
126 return BAD_VALUE;
127 }
128
129 const char *mime;
130 bool success = format->findCString(kKeyMIMEType, &mime);
131 CHECK(success);
132 CHECK(useOffload() || !strcasecmp(mime, MEDIA_MIMETYPE_AUDIO_RAW));
133
134 success = format->findInt32(kKeySampleRate, &mSampleRate);
135 CHECK(success);
136
137 int32_t numChannels, channelMask;
138 success = format->findInt32(kKeyChannelCount, &numChannels);
139 CHECK(success);
140
141 if(!format->findInt32(kKeyChannelMask, &channelMask)) {
142 // log only when there's a risk of ambiguity of channel mask selection
143 ALOGI_IF(numChannels > 2,
144 "source format didn't specify channel mask, using (%d) channel order", numChannels);
145 channelMask = CHANNEL_MASK_USE_CHANNEL_ORDER;
146 }
147
148 audio_format_t audioFormat = AUDIO_FORMAT_PCM_16_BIT;
149 int32_t pcmEncoding;
150 if (format->findInt32(kKeyPcmEncoding, &pcmEncoding)) {
151 sAudioFormatToPcmEncoding.map(pcmEncoding, &audioFormat);
152 }
153
154 if (useOffload()) {
155 if (mapMimeToAudioFormat(audioFormat, mime) != OK) {
156 ALOGE("Couldn't map mime type \"%s\" to a valid AudioSystem::audio_format", mime);
157 audioFormat = AUDIO_FORMAT_INVALID;
158 } else {
159 ALOGV("Mime type \"%s\" mapped to audio_format 0x%x", mime, audioFormat);
160 }
161
162 int32_t aacaot = -1;
163 if ((audioFormat == AUDIO_FORMAT_AAC) && format->findInt32(kKeyAACAOT, &aacaot)) {
164 // Redefine AAC format corrosponding to aac profile
165 mapAACProfileToAudioFormat(audioFormat,(OMX_AUDIO_AACPROFILETYPE) aacaot);
166 }
167 }
168
169 int avgBitRate = -1;
170 format->findInt32(kKeyBitRate, &avgBitRate);
171
172 if (mAudioSink.get() != NULL) {
173
174 uint32_t flags = AUDIO_OUTPUT_FLAG_NONE;
175 audio_offload_info_t offloadInfo = AUDIO_INFO_INITIALIZER;
176
177 if (allowDeepBuffering()) {
178 flags |= AUDIO_OUTPUT_FLAG_DEEP_BUFFER;
179 }
180 if (useOffload()) {
181 flags |= AUDIO_OUTPUT_FLAG_COMPRESS_OFFLOAD;
182
183 int64_t durationUs;
184 if (format->findInt64(kKeyDuration, &durationUs)) {
185 offloadInfo.duration_us = durationUs;
186 } else {
187 offloadInfo.duration_us = -1;
188 }
189
190 offloadInfo.sample_rate = mSampleRate;
191 offloadInfo.channel_mask = channelMask;
192 offloadInfo.format = audioFormat;
193 offloadInfo.stream_type = AUDIO_STREAM_MUSIC;
194 offloadInfo.bit_rate = avgBitRate;
195 offloadInfo.has_video = ((mCreateFlags & HAS_VIDEO) != 0);
196 offloadInfo.is_streaming = ((mCreateFlags & IS_STREAMING) != 0);
197 }
198
199 status_t err = mAudioSink->open(
200 mSampleRate, numChannels, channelMask, audioFormat,
201 DEFAULT_AUDIOSINK_BUFFERCOUNT,
202 &AudioPlayer::AudioSinkCallback,
203 this,
204 (audio_output_flags_t)flags,
205 useOffload() ? &offloadInfo : NULL);
206
207 if (err == OK) {
208 mLatencyUs = (int64_t)mAudioSink->latency() * 1000;
209 mFrameSize = mAudioSink->frameSize();
210
211 if (useOffload()) {
212 // If the playback is offloaded to h/w we pass the
213 // HAL some metadata information
214 // We don't want to do this for PCM because it will be going
215 // through the AudioFlinger mixer before reaching the hardware
216 sendMetaDataToHal(mAudioSink, format);
217 }
218
219 err = mAudioSink->start();
220 // do not alter behavior for non offloaded tracks: ignore start status.
221 if (!useOffload()) {
222 err = OK;
223 }
224 }
225
226 if (err != OK) {
227 if (mFirstBuffer != NULL) {
228 mFirstBuffer->release();
229 mFirstBuffer = NULL;
230 }
231
232 if (!sourceAlreadyStarted) {
233 mSource->stop();
234 }
235
236 return err;
237 }
238
239 } else {
240 // playing to an AudioTrack, set up mask if necessary
241 audio_channel_mask_t audioMask = channelMask == CHANNEL_MASK_USE_CHANNEL_ORDER ?
242 audio_channel_out_mask_from_count(numChannels) : channelMask;
243 if (0 == audioMask) {
244 return BAD_VALUE;
245 }
246
247 mAudioTrack = new AudioTrack(
248 AUDIO_STREAM_MUSIC, mSampleRate, AUDIO_FORMAT_PCM_16_BIT, audioMask,
249 0 /*frameCount*/, AUDIO_OUTPUT_FLAG_NONE, &AudioCallback, this,
250 0 /*notificationFrames*/);
251
252 if ((err = mAudioTrack->initCheck()) != OK) {
253 mAudioTrack.clear();
254
255 if (mFirstBuffer != NULL) {
256 mFirstBuffer->release();
257 mFirstBuffer = NULL;
258 }
259
260 if (!sourceAlreadyStarted) {
261 mSource->stop();
262 }
263
264 return err;
265 }
266
267 mLatencyUs = (int64_t)mAudioTrack->latency() * 1000;
268 mFrameSize = mAudioTrack->frameSize();
269
270 mAudioTrack->start();
271 }
272
273 mStarted = true;
274 mPlaying = true;
275
276 return OK;
277 }
278
pause(bool playPendingSamples)279 void AudioPlayer::pause(bool playPendingSamples) {
280 CHECK(mStarted);
281
282 if (playPendingSamples) {
283 if (mAudioSink.get() != NULL) {
284 mAudioSink->stop();
285 } else {
286 mAudioTrack->stop();
287 }
288
289 mNumFramesPlayed = 0;
290 mNumFramesPlayedSysTimeUs = ALooper::GetNowUs();
291 } else {
292 if (mAudioSink.get() != NULL) {
293 mAudioSink->pause();
294 } else {
295 mAudioTrack->pause();
296 }
297 }
298
299 mPlaying = false;
300 }
301
resume()302 status_t AudioPlayer::resume() {
303 CHECK(mStarted);
304 status_t err;
305
306 if (mAudioSink.get() != NULL) {
307 err = mAudioSink->start();
308 } else {
309 err = mAudioTrack->start();
310 }
311
312 if (err == OK) {
313 mPlaying = true;
314 }
315
316 return err;
317 }
318
reset()319 void AudioPlayer::reset() {
320 CHECK(mStarted);
321
322 ALOGV("reset: mPlaying=%d mReachedEOS=%d useOffload=%d",
323 mPlaying, mReachedEOS, useOffload() );
324
325 if (mAudioSink.get() != NULL) {
326 mAudioSink->stop();
327 // If we're closing and have reached EOS, we don't want to flush
328 // the track because if it is offloaded there could be a small
329 // amount of residual data in the hardware buffer which we must
330 // play to give gapless playback.
331 // But if we're resetting when paused or before we've reached EOS
332 // we can't be doing a gapless playback and there could be a large
333 // amount of data queued in the hardware if the track is offloaded,
334 // so we must flush to prevent a track switch being delayed playing
335 // the buffered data that we don't want now
336 if (!mPlaying || !mReachedEOS) {
337 mAudioSink->flush();
338 }
339
340 mAudioSink->close();
341 } else {
342 mAudioTrack->stop();
343
344 if (!mPlaying || !mReachedEOS) {
345 mAudioTrack->flush();
346 }
347
348 mAudioTrack.clear();
349 }
350
351 // Make sure to release any buffer we hold onto so that the
352 // source is able to stop().
353
354 if (mFirstBuffer != NULL) {
355 mFirstBuffer->release();
356 mFirstBuffer = NULL;
357 }
358
359 if (mInputBuffer != NULL) {
360 ALOGV("AudioPlayer releasing input buffer.");
361
362 mInputBuffer->release();
363 mInputBuffer = NULL;
364 }
365
366 mSource->stop();
367
368 // The following hack is necessary to ensure that the OMX
369 // component is completely released by the time we may try
370 // to instantiate it again.
371 // When offloading, the OMX component is not used so this hack
372 // is not needed
373 if (!useOffload()) {
374 wp<MediaSource> tmp = mSource;
375 mSource.clear();
376 while (tmp.promote() != NULL) {
377 usleep(1000);
378 }
379 } else {
380 mSource.clear();
381 }
382 IPCThreadState::self()->flushCommands();
383
384 mNumFramesPlayed = 0;
385 mNumFramesPlayedSysTimeUs = ALooper::GetNowUs();
386 mPositionTimeMediaUs = -1;
387 mPositionTimeRealUs = -1;
388 mSeeking = false;
389 mSeekTimeUs = 0;
390 mReachedEOS = false;
391 mFinalStatus = OK;
392 mStarted = false;
393 mPlaying = false;
394 mStartPosUs = 0;
395 }
396
397 // static
AudioCallback(int event,void * user,void * info)398 void AudioPlayer::AudioCallback(int event, void *user, void *info) {
399 static_cast<AudioPlayer *>(user)->AudioCallback(event, info);
400 }
401
reachedEOS(status_t * finalStatus)402 bool AudioPlayer::reachedEOS(status_t *finalStatus) {
403 *finalStatus = OK;
404
405 Mutex::Autolock autoLock(mLock);
406 *finalStatus = mFinalStatus;
407 return mReachedEOS;
408 }
409
setPlaybackRate(const AudioPlaybackRate & rate)410 status_t AudioPlayer::setPlaybackRate(const AudioPlaybackRate &rate) {
411 if (mAudioSink.get() != NULL) {
412 return mAudioSink->setPlaybackRate(rate);
413 } else if (mAudioTrack != 0){
414 return mAudioTrack->setPlaybackRate(rate);
415 } else {
416 return NO_INIT;
417 }
418 }
419
getPlaybackRate(AudioPlaybackRate * rate)420 status_t AudioPlayer::getPlaybackRate(AudioPlaybackRate *rate /* nonnull */) {
421 if (mAudioSink.get() != NULL) {
422 return mAudioSink->getPlaybackRate(rate);
423 } else if (mAudioTrack != 0) {
424 *rate = mAudioTrack->getPlaybackRate();
425 return OK;
426 } else {
427 return NO_INIT;
428 }
429 }
430
431 // static
AudioSinkCallback(MediaPlayerBase::AudioSink *,void * buffer,size_t size,void * cookie,MediaPlayerBase::AudioSink::cb_event_t event)432 size_t AudioPlayer::AudioSinkCallback(
433 MediaPlayerBase::AudioSink * /* audioSink */,
434 void *buffer, size_t size, void *cookie,
435 MediaPlayerBase::AudioSink::cb_event_t event) {
436 AudioPlayer *me = (AudioPlayer *)cookie;
437
438 switch(event) {
439 case MediaPlayerBase::AudioSink::CB_EVENT_FILL_BUFFER:
440 return me->fillBuffer(buffer, size);
441
442 case MediaPlayerBase::AudioSink::CB_EVENT_STREAM_END:
443 ALOGV("AudioSinkCallback: stream end");
444 me->mReachedEOS = true;
445 break;
446
447 case MediaPlayerBase::AudioSink::CB_EVENT_TEAR_DOWN:
448 ALOGV("AudioSinkCallback: Tear down event");
449 break;
450 }
451
452 return 0;
453 }
454
AudioCallback(int event,void * info)455 void AudioPlayer::AudioCallback(int event, void *info) {
456 switch (event) {
457 case AudioTrack::EVENT_MORE_DATA:
458 {
459 AudioTrack::Buffer *buffer = (AudioTrack::Buffer *)info;
460 size_t numBytesWritten = fillBuffer(buffer->raw, buffer->size);
461 buffer->size = numBytesWritten;
462 }
463 break;
464
465 case AudioTrack::EVENT_STREAM_END:
466 mReachedEOS = true;
467 break;
468 }
469 }
470
fillBuffer(void * data,size_t size)471 size_t AudioPlayer::fillBuffer(void *data, size_t size) {
472 if (mNumFramesPlayed == 0) {
473 ALOGV("AudioCallback");
474 }
475
476 if (mReachedEOS) {
477 return 0;
478 }
479
480 size_t size_done = 0;
481 size_t size_remaining = size;
482 while (size_remaining > 0) {
483 MediaSource::ReadOptions options;
484 bool refreshSeekTime = false;
485
486 {
487 Mutex::Autolock autoLock(mLock);
488
489 if (mSeeking) {
490 if (mIsFirstBuffer) {
491 if (mFirstBuffer != NULL) {
492 mFirstBuffer->release();
493 mFirstBuffer = NULL;
494 }
495 mIsFirstBuffer = false;
496 }
497
498 options.setSeekTo(mSeekTimeUs);
499 refreshSeekTime = true;
500
501 if (mInputBuffer != NULL) {
502 mInputBuffer->release();
503 mInputBuffer = NULL;
504 }
505
506 mSeeking = false;
507 }
508 }
509
510 if (mInputBuffer == NULL) {
511 status_t err;
512
513 if (mIsFirstBuffer) {
514 mInputBuffer = mFirstBuffer;
515 mFirstBuffer = NULL;
516 err = mFirstBufferResult;
517
518 mIsFirstBuffer = false;
519 } else {
520 err = mSource->read(&mInputBuffer, &options);
521 }
522
523 CHECK((err == OK && mInputBuffer != NULL)
524 || (err != OK && mInputBuffer == NULL));
525
526 Mutex::Autolock autoLock(mLock);
527
528 if (err != OK) {
529 if (!mReachedEOS) {
530 if (useOffload()) {
531 // no more buffers to push - stop() and wait for STREAM_END
532 // don't set mReachedEOS until stream end received
533 if (mAudioSink != NULL) {
534 mAudioSink->stop();
535 } else {
536 mAudioTrack->stop();
537 }
538 } else {
539 mReachedEOS = true;
540 }
541 }
542
543 mFinalStatus = err;
544 break;
545 }
546
547 if (mAudioSink != NULL) {
548 mLatencyUs = (int64_t)mAudioSink->latency() * 1000;
549 } else {
550 mLatencyUs = (int64_t)mAudioTrack->latency() * 1000;
551 }
552
553 if(mInputBuffer->range_length() != 0) {
554 CHECK(mInputBuffer->meta_data().findInt64(
555 kKeyTime, &mPositionTimeMediaUs));
556 }
557
558 // need to adjust the mStartPosUs for offload decoding since parser
559 // might not be able to get the exact seek time requested.
560 if (refreshSeekTime) {
561 if (useOffload()) {
562 mStartPosUs = mPositionTimeMediaUs;
563 ALOGV("adjust seek time to: %.2f", mStartPosUs/ 1E6);
564 }
565 // clear seek time with mLock locked and once we have valid mPositionTimeMediaUs
566 // and mPositionTimeRealUs
567 // before clearing mSeekTimeUs check if a new seek request has been received while
568 // we were reading from the source with mLock released.
569 if (!mSeeking) {
570 mSeekTimeUs = 0;
571 }
572 }
573
574 if (!useOffload()) {
575 mPositionTimeRealUs =
576 ((mNumFramesPlayed + size_done / mFrameSize) * 1000000)
577 / mSampleRate;
578 ALOGV("buffer->size() = %zu, "
579 "mPositionTimeMediaUs=%.2f mPositionTimeRealUs=%.2f",
580 mInputBuffer->range_length(),
581 mPositionTimeMediaUs / 1E6, mPositionTimeRealUs / 1E6);
582 }
583
584 }
585
586 if (mInputBuffer->range_length() == 0) {
587 mInputBuffer->release();
588 mInputBuffer = NULL;
589
590 continue;
591 }
592
593 size_t copy = size_remaining;
594 if (copy > mInputBuffer->range_length()) {
595 copy = mInputBuffer->range_length();
596 }
597
598 memcpy((char *)data + size_done,
599 (const char *)mInputBuffer->data() + mInputBuffer->range_offset(),
600 copy);
601
602 mInputBuffer->set_range(mInputBuffer->range_offset() + copy,
603 mInputBuffer->range_length() - copy);
604
605 size_done += copy;
606 size_remaining -= copy;
607 }
608
609 if (useOffload()) {
610 // We must ask the hardware what it has played
611 mPositionTimeRealUs = getOutputPlayPositionUs_l();
612 ALOGV("mPositionTimeMediaUs=%.2f mPositionTimeRealUs=%.2f",
613 mPositionTimeMediaUs / 1E6, mPositionTimeRealUs / 1E6);
614 }
615
616 {
617 Mutex::Autolock autoLock(mLock);
618 mNumFramesPlayed += size_done / mFrameSize;
619 mNumFramesPlayedSysTimeUs = ALooper::GetNowUs();
620 }
621
622 return size_done;
623 }
624
getOutputPlayPositionUs_l()625 int64_t AudioPlayer::getOutputPlayPositionUs_l()
626 {
627 uint32_t playedSamples = 0;
628 uint32_t sampleRate;
629 if (mAudioSink != NULL) {
630 mAudioSink->getPosition(&playedSamples);
631 sampleRate = mAudioSink->getSampleRate();
632 } else {
633 mAudioTrack->getPosition(&playedSamples);
634 sampleRate = mAudioTrack->getSampleRate();
635 }
636 if (sampleRate != 0) {
637 mSampleRate = sampleRate;
638 }
639
640 int64_t playedUs;
641 if (mSampleRate != 0) {
642 playedUs = (static_cast<int64_t>(playedSamples) * 1000000 ) / mSampleRate;
643 } else {
644 playedUs = 0;
645 }
646
647 // HAL position is relative to the first buffer we sent at mStartPosUs
648 const int64_t renderedDuration = mStartPosUs + playedUs;
649 ALOGV("getOutputPlayPositionUs_l %" PRId64, renderedDuration);
650 return renderedDuration;
651 }
652
seekTo(int64_t time_us)653 status_t AudioPlayer::seekTo(int64_t time_us) {
654 Mutex::Autolock autoLock(mLock);
655
656 ALOGV("seekTo( %" PRId64 " )", time_us);
657
658 mSeeking = true;
659 mPositionTimeRealUs = mPositionTimeMediaUs = -1;
660 mReachedEOS = false;
661 mSeekTimeUs = time_us;
662 mStartPosUs = time_us;
663
664 // Flush resets the number of played frames
665 mNumFramesPlayed = 0;
666 mNumFramesPlayedSysTimeUs = ALooper::GetNowUs();
667
668 if (mAudioSink != NULL) {
669 if (mPlaying) {
670 mAudioSink->pause();
671 }
672 mAudioSink->flush();
673 if (mPlaying) {
674 mAudioSink->start();
675 }
676 } else {
677 if (mPlaying) {
678 mAudioTrack->pause();
679 }
680 mAudioTrack->flush();
681 if (mPlaying) {
682 mAudioTrack->start();
683 }
684 }
685
686 return OK;
687 }
688
689 }
690