RTSPSource.cpp revision 81e68448f3361eaf8618930471fdc3c21bdf5cbc
12bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber/* 22bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber * Copyright (C) 2010 The Android Open Source Project 32bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber * 42bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber * Licensed under the Apache License, Version 2.0 (the "License"); 52bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber * you may not use this file except in compliance with the License. 62bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber * You may obtain a copy of the License at 72bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber * 82bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber * http://www.apache.org/licenses/LICENSE-2.0 92bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber * 102bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber * Unless required by applicable law or agreed to in writing, software 112bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber * distributed under the License is distributed on an "AS IS" BASIS, 122bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 132bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber * See the License for the specific language governing permissions and 142bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber * limitations under the License. 152bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber */ 162bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 172bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber//#define LOG_NDEBUG 0 182bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber#define LOG_TAG "RTSPSource" 192bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber#include <utils/Log.h> 202bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 212bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber#include "RTSPSource.h" 222bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 232bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber#include "AnotherPacketSource.h" 242bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber#include "MyHandler.h" 2581dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé#include "SDPLoader.h" 262bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 271b86fe063badb5f28c467ade39be0f4008688947Andreas Huber#include <media/IMediaHTTPService.h> 2849694688c82214f5fd9e969e177c9e126a240a26Andreas Huber#include <media/stagefright/MediaDefs.h> 292bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber#include <media/stagefright/MetaData.h> 302bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 312bfdd428c56c7524d1a11979f200a1762866032dAndreas Hubernamespace android { 322bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 33cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönssonconst int64_t kNearEOSTimeoutUs = 2000000ll; // 2 secs 34cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson 352bfdd428c56c7524d1a11979f200a1762866032dAndreas HuberNuPlayer::RTSPSource::RTSPSource( 365ab368af38fefacc4009e3ab1c1bbd00e62b3bcfAndreas Huber const sp<AMessage> ¬ify, 371b86fe063badb5f28c467ade39be0f4008688947Andreas Huber const sp<IMediaHTTPService> &httpService, 382bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber const char *url, 392bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber const KeyedVector<String8, String8> *headers, 402bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber bool uidValid, 4181dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé uid_t uid, 4281dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé bool isSDP) 435ab368af38fefacc4009e3ab1c1bbd00e62b3bcfAndreas Huber : Source(notify), 441b86fe063badb5f28c467ade39be0f4008688947Andreas Huber mHTTPService(httpService), 455ab368af38fefacc4009e3ab1c1bbd00e62b3bcfAndreas Huber mURL(url), 462bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber mUIDValid(uidValid), 472bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber mUID(uid), 482bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber mFlags(0), 4981dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé mIsSDP(isSDP), 502bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber mState(DISCONNECTED), 512bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber mFinalResult(OK), 52ee736e9e74c5368db8d63214513c85cb74bb0183Andreas Huber mDisconnectReplyID(0), 53cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson mBuffering(true), 54cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson mSeekGeneration(0), 55cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson mEOSTimeoutAudio(0), 56cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson mEOSTimeoutVideo(0) { 572bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber if (headers) { 582bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber mExtraHeaders = *headers; 592bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 602bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber ssize_t index = 612bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber mExtraHeaders.indexOfKey(String8("x-hide-urls-from-log")); 622bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 632bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber if (index >= 0) { 642bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber mFlags |= kFlagIncognito; 652bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 662bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber mExtraHeaders.removeItemsAt(index); 672bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber } 682bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber } 692bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber} 702bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 712bfdd428c56c7524d1a11979f200a1762866032dAndreas HuberNuPlayer::RTSPSource::~RTSPSource() { 72602f5bbd7596ec3fe447fde4329d5d4f0b370835Andreas Huber if (mLooper != NULL) { 73602f5bbd7596ec3fe447fde4329d5d4f0b370835Andreas Huber mLooper->stop(); 74602f5bbd7596ec3fe447fde4329d5d4f0b370835Andreas Huber } 752bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber} 762bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 7757cea553cb19235553463412db5ad04c99835411Andreas Hubervoid NuPlayer::RTSPSource::prepareAsync() { 782bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber if (mLooper == NULL) { 792bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber mLooper = new ALooper; 802bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber mLooper->setName("rtsp"); 812bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber mLooper->start(); 822bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 832bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber mReflector = new AHandlerReflector<RTSPSource>(this); 842bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber mLooper->registerHandler(mReflector); 852bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber } 862bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 872bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber CHECK(mHandler == NULL); 8881dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé CHECK(mSDPLoader == NULL); 892bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 902bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber sp<AMessage> notify = new AMessage(kWhatNotify, mReflector->id()); 912bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 922bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber CHECK_EQ(mState, (int)DISCONNECTED); 932bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber mState = CONNECTING; 942bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 9581dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé if (mIsSDP) { 9681dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé mSDPLoader = new SDPLoader(notify, 9781dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé (mFlags & kFlagIncognito) ? SDPLoader::kFlagIncognito : 0, 9881e68448f3361eaf8618930471fdc3c21bdf5cbcAndreas Huber mHTTPService); 9981dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé 10057cea553cb19235553463412db5ad04c99835411Andreas Huber mSDPLoader->load( 10157cea553cb19235553463412db5ad04c99835411Andreas Huber mURL.c_str(), mExtraHeaders.isEmpty() ? NULL : &mExtraHeaders); 10281dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé } else { 10381dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé mHandler = new MyHandler(mURL.c_str(), notify, mUIDValid, mUID); 10481dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé mLooper->registerHandler(mHandler); 10581dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé 10681dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé mHandler->connect(); 10781dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé } 108cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson 109cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson sp<AMessage> notifyStart = dupNotify(); 110cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson notifyStart->setInt32("what", kWhatBufferingStart); 111cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson notifyStart->post(); 11257cea553cb19235553463412db5ad04c99835411Andreas Huber} 11357cea553cb19235553463412db5ad04c99835411Andreas Huber 11457cea553cb19235553463412db5ad04c99835411Andreas Hubervoid NuPlayer::RTSPSource::start() { 1152bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber} 1162bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 1172bfdd428c56c7524d1a11979f200a1762866032dAndreas Hubervoid NuPlayer::RTSPSource::stop() { 1185834181d3f168acb8ff4bf3eff1fd1186afb0bd4James Dong if (mLooper == NULL) { 1195834181d3f168acb8ff4bf3eff1fd1186afb0bd4James Dong return; 1205834181d3f168acb8ff4bf3eff1fd1186afb0bd4James Dong } 1212bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber sp<AMessage> msg = new AMessage(kWhatDisconnect, mReflector->id()); 1222bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 1232bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber sp<AMessage> dummy; 1242bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber msg->postAndAwaitResponse(&dummy); 1252bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber} 1262bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 12746d13e3606b87d71379287672b54b50d0d9aa5ccRoger Jönssonvoid NuPlayer::RTSPSource::pause() { 12846d13e3606b87d71379287672b54b50d0d9aa5ccRoger Jönsson int64_t mediaDurationUs = 0; 12946d13e3606b87d71379287672b54b50d0d9aa5ccRoger Jönsson getDuration(&mediaDurationUs); 13046d13e3606b87d71379287672b54b50d0d9aa5ccRoger Jönsson for (size_t index = 0; index < mTracks.size(); index++) { 13146d13e3606b87d71379287672b54b50d0d9aa5ccRoger Jönsson TrackInfo *info = &mTracks.editItemAt(index); 13246d13e3606b87d71379287672b54b50d0d9aa5ccRoger Jönsson sp<AnotherPacketSource> source = info->mSource; 13346d13e3606b87d71379287672b54b50d0d9aa5ccRoger Jönsson 13446d13e3606b87d71379287672b54b50d0d9aa5ccRoger Jönsson // Check if EOS or ERROR is received 13546d13e3606b87d71379287672b54b50d0d9aa5ccRoger Jönsson if (source != NULL && source->isFinished(mediaDurationUs)) { 13646d13e3606b87d71379287672b54b50d0d9aa5ccRoger Jönsson return; 13746d13e3606b87d71379287672b54b50d0d9aa5ccRoger Jönsson } 13846d13e3606b87d71379287672b54b50d0d9aa5ccRoger Jönsson } 13946d13e3606b87d71379287672b54b50d0d9aa5ccRoger Jönsson mHandler->pause(); 14046d13e3606b87d71379287672b54b50d0d9aa5ccRoger Jönsson} 14146d13e3606b87d71379287672b54b50d0d9aa5ccRoger Jönsson 14246d13e3606b87d71379287672b54b50d0d9aa5ccRoger Jönssonvoid NuPlayer::RTSPSource::resume() { 14346d13e3606b87d71379287672b54b50d0d9aa5ccRoger Jönsson mHandler->resume(); 14446d13e3606b87d71379287672b54b50d0d9aa5ccRoger Jönsson} 14546d13e3606b87d71379287672b54b50d0d9aa5ccRoger Jönsson 1462bfdd428c56c7524d1a11979f200a1762866032dAndreas Huberstatus_t NuPlayer::RTSPSource::feedMoreTSData() { 1472bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber return mFinalResult; 1482bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber} 1492bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 150840667883fd09d44015716d79bc3ac4d60edc0f0Andreas Hubersp<MetaData> NuPlayer::RTSPSource::getFormatMeta(bool audio) { 1512bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber sp<AnotherPacketSource> source = getSource(audio); 1522bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 1532bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber if (source == NULL) { 1542bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber return NULL; 1552bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber } 1562bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 1572bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber return source->getFormat(); 1582bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber} 1592bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 160bfd4d0d9fe0033abf3f55b94f30f6a58846a875eAndreas Huberbool NuPlayer::RTSPSource::haveSufficientDataOnAllTracks() { 161bfd4d0d9fe0033abf3f55b94f30f6a58846a875eAndreas Huber // We're going to buffer at least 2 secs worth data on all tracks before 162bfd4d0d9fe0033abf3f55b94f30f6a58846a875eAndreas Huber // starting playback (both at startup and after a seek). 163bfd4d0d9fe0033abf3f55b94f30f6a58846a875eAndreas Huber 164bfd4d0d9fe0033abf3f55b94f30f6a58846a875eAndreas Huber static const int64_t kMinDurationUs = 2000000ll; 165bfd4d0d9fe0033abf3f55b94f30f6a58846a875eAndreas Huber 166cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson int64_t mediaDurationUs = 0; 167cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson getDuration(&mediaDurationUs); 168cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson if ((mAudioTrack != NULL && mAudioTrack->isFinished(mediaDurationUs)) 169cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson || (mVideoTrack != NULL && mVideoTrack->isFinished(mediaDurationUs))) { 170cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson return true; 171cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson } 172cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson 173bfd4d0d9fe0033abf3f55b94f30f6a58846a875eAndreas Huber status_t err; 174bfd4d0d9fe0033abf3f55b94f30f6a58846a875eAndreas Huber int64_t durationUs; 175bfd4d0d9fe0033abf3f55b94f30f6a58846a875eAndreas Huber if (mAudioTrack != NULL 176bfd4d0d9fe0033abf3f55b94f30f6a58846a875eAndreas Huber && (durationUs = mAudioTrack->getBufferedDurationUs(&err)) 177bfd4d0d9fe0033abf3f55b94f30f6a58846a875eAndreas Huber < kMinDurationUs 178bfd4d0d9fe0033abf3f55b94f30f6a58846a875eAndreas Huber && err == OK) { 179bfd4d0d9fe0033abf3f55b94f30f6a58846a875eAndreas Huber ALOGV("audio track doesn't have enough data yet. (%.2f secs buffered)", 180bfd4d0d9fe0033abf3f55b94f30f6a58846a875eAndreas Huber durationUs / 1E6); 181bfd4d0d9fe0033abf3f55b94f30f6a58846a875eAndreas Huber return false; 182bfd4d0d9fe0033abf3f55b94f30f6a58846a875eAndreas Huber } 183bfd4d0d9fe0033abf3f55b94f30f6a58846a875eAndreas Huber 184bfd4d0d9fe0033abf3f55b94f30f6a58846a875eAndreas Huber if (mVideoTrack != NULL 185bfd4d0d9fe0033abf3f55b94f30f6a58846a875eAndreas Huber && (durationUs = mVideoTrack->getBufferedDurationUs(&err)) 186bfd4d0d9fe0033abf3f55b94f30f6a58846a875eAndreas Huber < kMinDurationUs 187bfd4d0d9fe0033abf3f55b94f30f6a58846a875eAndreas Huber && err == OK) { 188bfd4d0d9fe0033abf3f55b94f30f6a58846a875eAndreas Huber ALOGV("video track doesn't have enough data yet. (%.2f secs buffered)", 189bfd4d0d9fe0033abf3f55b94f30f6a58846a875eAndreas Huber durationUs / 1E6); 190bfd4d0d9fe0033abf3f55b94f30f6a58846a875eAndreas Huber return false; 191bfd4d0d9fe0033abf3f55b94f30f6a58846a875eAndreas Huber } 192bfd4d0d9fe0033abf3f55b94f30f6a58846a875eAndreas Huber 193bfd4d0d9fe0033abf3f55b94f30f6a58846a875eAndreas Huber return true; 194bfd4d0d9fe0033abf3f55b94f30f6a58846a875eAndreas Huber} 195bfd4d0d9fe0033abf3f55b94f30f6a58846a875eAndreas Huber 1962bfdd428c56c7524d1a11979f200a1762866032dAndreas Huberstatus_t NuPlayer::RTSPSource::dequeueAccessUnit( 1972bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber bool audio, sp<ABuffer> *accessUnit) { 198cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson if (mBuffering) { 199bfd4d0d9fe0033abf3f55b94f30f6a58846a875eAndreas Huber if (!haveSufficientDataOnAllTracks()) { 200bfd4d0d9fe0033abf3f55b94f30f6a58846a875eAndreas Huber return -EWOULDBLOCK; 201bfd4d0d9fe0033abf3f55b94f30f6a58846a875eAndreas Huber } 202bfd4d0d9fe0033abf3f55b94f30f6a58846a875eAndreas Huber 203cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson mBuffering = false; 204cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson 205cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson sp<AMessage> notify = dupNotify(); 206cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson notify->setInt32("what", kWhatBufferingEnd); 207cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson notify->post(); 208bfd4d0d9fe0033abf3f55b94f30f6a58846a875eAndreas Huber } 209bfd4d0d9fe0033abf3f55b94f30f6a58846a875eAndreas Huber 2102bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber sp<AnotherPacketSource> source = getSource(audio); 2112bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 2122bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber if (source == NULL) { 2132bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber return -EWOULDBLOCK; 2142bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber } 2152bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 2162bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber status_t finalResult; 2172bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber if (!source->hasBufferAvailable(&finalResult)) { 218cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson if (finalResult == OK) { 219cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson int64_t mediaDurationUs = 0; 220cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson getDuration(&mediaDurationUs); 221cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson sp<AnotherPacketSource> otherSource = getSource(!audio); 222cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson status_t otherFinalResult; 223cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson 224cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson // If other source already signaled EOS, this source should also signal EOS 225cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson if (otherSource != NULL && 226cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson !otherSource->hasBufferAvailable(&otherFinalResult) && 227cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson otherFinalResult == ERROR_END_OF_STREAM) { 228cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson source->signalEOS(ERROR_END_OF_STREAM); 229cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson return ERROR_END_OF_STREAM; 230cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson } 231cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson 232cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson // If this source has detected near end, give it some time to retrieve more 233cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson // data before signaling EOS 234cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson if (source->isFinished(mediaDurationUs)) { 235cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson int64_t eosTimeout = audio ? mEOSTimeoutAudio : mEOSTimeoutVideo; 236cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson if (eosTimeout == 0) { 237cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson setEOSTimeout(audio, ALooper::GetNowUs()); 238cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson } else if ((ALooper::GetNowUs() - eosTimeout) > kNearEOSTimeoutUs) { 239cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson setEOSTimeout(audio, 0); 240cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson source->signalEOS(ERROR_END_OF_STREAM); 241cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson return ERROR_END_OF_STREAM; 242cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson } 243cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson return -EWOULDBLOCK; 244cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson } 245cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson 246cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson if (!(otherSource != NULL && otherSource->isFinished(mediaDurationUs))) { 247cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson // We should not enter buffering mode 248cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson // if any of the sources already have detected EOS. 249cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson mBuffering = true; 250cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson 251cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson sp<AMessage> notify = dupNotify(); 252cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson notify->setInt32("what", kWhatBufferingStart); 253cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson notify->post(); 254cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson } 255cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson 256cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson return -EWOULDBLOCK; 257cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson } 258cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson return finalResult; 2592bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber } 2602bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 261cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson setEOSTimeout(audio, 0); 262cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson 2632bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber return source->dequeueAccessUnit(accessUnit); 2642bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber} 2652bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 2662bfdd428c56c7524d1a11979f200a1762866032dAndreas Hubersp<AnotherPacketSource> NuPlayer::RTSPSource::getSource(bool audio) { 26749694688c82214f5fd9e969e177c9e126a240a26Andreas Huber if (mTSParser != NULL) { 26849694688c82214f5fd9e969e177c9e126a240a26Andreas Huber sp<MediaSource> source = mTSParser->getSource( 26949694688c82214f5fd9e969e177c9e126a240a26Andreas Huber audio ? ATSParser::AUDIO : ATSParser::VIDEO); 27049694688c82214f5fd9e969e177c9e126a240a26Andreas Huber 27149694688c82214f5fd9e969e177c9e126a240a26Andreas Huber return static_cast<AnotherPacketSource *>(source.get()); 27249694688c82214f5fd9e969e177c9e126a240a26Andreas Huber } 27349694688c82214f5fd9e969e177c9e126a240a26Andreas Huber 2742bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber return audio ? mAudioTrack : mVideoTrack; 2752bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber} 2762bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 277cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönssonvoid NuPlayer::RTSPSource::setEOSTimeout(bool audio, int64_t timeout) { 278cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson if (audio) { 279cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson mEOSTimeoutAudio = timeout; 280cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson } else { 281cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson mEOSTimeoutVideo = timeout; 282cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson } 283cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson} 284cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson 2852bfdd428c56c7524d1a11979f200a1762866032dAndreas Huberstatus_t NuPlayer::RTSPSource::getDuration(int64_t *durationUs) { 2862bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber *durationUs = 0ll; 2872bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 2882bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber int64_t audioDurationUs; 2892bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber if (mAudioTrack != NULL 2902bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber && mAudioTrack->getFormat()->findInt64( 2912bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber kKeyDuration, &audioDurationUs) 2922bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber && audioDurationUs > *durationUs) { 2932bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber *durationUs = audioDurationUs; 2942bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber } 2952bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 2962bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber int64_t videoDurationUs; 2972bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber if (mVideoTrack != NULL 2982bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber && mVideoTrack->getFormat()->findInt64( 2992bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber kKeyDuration, &videoDurationUs) 3002bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber && videoDurationUs > *durationUs) { 3012bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber *durationUs = videoDurationUs; 3022bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber } 3032bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 3042bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber return OK; 3052bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber} 3062bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 3072bfdd428c56c7524d1a11979f200a1762866032dAndreas Huberstatus_t NuPlayer::RTSPSource::seekTo(int64_t seekTimeUs) { 308ee736e9e74c5368db8d63214513c85cb74bb0183Andreas Huber sp<AMessage> msg = new AMessage(kWhatPerformSeek, mReflector->id()); 309ee736e9e74c5368db8d63214513c85cb74bb0183Andreas Huber msg->setInt32("generation", ++mSeekGeneration); 310ee736e9e74c5368db8d63214513c85cb74bb0183Andreas Huber msg->setInt64("timeUs", seekTimeUs); 311ee736e9e74c5368db8d63214513c85cb74bb0183Andreas Huber msg->post(200000ll); 312ee736e9e74c5368db8d63214513c85cb74bb0183Andreas Huber 313ee736e9e74c5368db8d63214513c85cb74bb0183Andreas Huber return OK; 314ee736e9e74c5368db8d63214513c85cb74bb0183Andreas Huber} 315ee736e9e74c5368db8d63214513c85cb74bb0183Andreas Huber 316ee736e9e74c5368db8d63214513c85cb74bb0183Andreas Hubervoid NuPlayer::RTSPSource::performSeek(int64_t seekTimeUs) { 3172bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber if (mState != CONNECTED) { 318ee736e9e74c5368db8d63214513c85cb74bb0183Andreas Huber return; 3192bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber } 3202bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 3212bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber mState = SEEKING; 3222bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber mHandler->seek(seekTimeUs); 3232bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber} 3242bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 3252bfdd428c56c7524d1a11979f200a1762866032dAndreas Hubervoid NuPlayer::RTSPSource::onMessageReceived(const sp<AMessage> &msg) { 3262bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber if (msg->what() == kWhatDisconnect) { 3272bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber uint32_t replyID; 3282bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber CHECK(msg->senderAwaitsResponse(&replyID)); 3292bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 3302bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber mDisconnectReplyID = replyID; 3312bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber finishDisconnectIfPossible(); 3322bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber return; 333ee736e9e74c5368db8d63214513c85cb74bb0183Andreas Huber } else if (msg->what() == kWhatPerformSeek) { 334ee736e9e74c5368db8d63214513c85cb74bb0183Andreas Huber int32_t generation; 335ee736e9e74c5368db8d63214513c85cb74bb0183Andreas Huber CHECK(msg->findInt32("generation", &generation)); 336ee736e9e74c5368db8d63214513c85cb74bb0183Andreas Huber 337ee736e9e74c5368db8d63214513c85cb74bb0183Andreas Huber if (generation != mSeekGeneration) { 338ee736e9e74c5368db8d63214513c85cb74bb0183Andreas Huber // obsolete. 339ee736e9e74c5368db8d63214513c85cb74bb0183Andreas Huber return; 340ee736e9e74c5368db8d63214513c85cb74bb0183Andreas Huber } 341ee736e9e74c5368db8d63214513c85cb74bb0183Andreas Huber 342ee736e9e74c5368db8d63214513c85cb74bb0183Andreas Huber int64_t seekTimeUs; 343ee736e9e74c5368db8d63214513c85cb74bb0183Andreas Huber CHECK(msg->findInt64("timeUs", &seekTimeUs)); 344ee736e9e74c5368db8d63214513c85cb74bb0183Andreas Huber 345ee736e9e74c5368db8d63214513c85cb74bb0183Andreas Huber performSeek(seekTimeUs); 346ee736e9e74c5368db8d63214513c85cb74bb0183Andreas Huber return; 3472bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber } 3482bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 3492bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber CHECK_EQ(msg->what(), (int)kWhatNotify); 3502bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 3512bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber int32_t what; 3522bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber CHECK(msg->findInt32("what", &what)); 3532bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 3542bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber switch (what) { 3552bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber case MyHandler::kWhatConnected: 3567f475c34ffc8e35345f2cceee2ef56a50bb5fea6Andreas Huber { 3572bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber onConnected(); 3587f475c34ffc8e35345f2cceee2ef56a50bb5fea6Andreas Huber 3597f475c34ffc8e35345f2cceee2ef56a50bb5fea6Andreas Huber notifyVideoSizeChanged(0, 0); 3607f475c34ffc8e35345f2cceee2ef56a50bb5fea6Andreas Huber 3617f475c34ffc8e35345f2cceee2ef56a50bb5fea6Andreas Huber uint32_t flags = 0; 3627f475c34ffc8e35345f2cceee2ef56a50bb5fea6Andreas Huber 3637f475c34ffc8e35345f2cceee2ef56a50bb5fea6Andreas Huber if (mHandler->isSeekable()) { 3644b7069dac546ad21cf62ca6132d50ea41857d08eChong Zhang flags = FLAG_CAN_PAUSE 3654b7069dac546ad21cf62ca6132d50ea41857d08eChong Zhang | FLAG_CAN_SEEK 3664b7069dac546ad21cf62ca6132d50ea41857d08eChong Zhang | FLAG_CAN_SEEK_BACKWARD 3674b7069dac546ad21cf62ca6132d50ea41857d08eChong Zhang | FLAG_CAN_SEEK_FORWARD; 3687f475c34ffc8e35345f2cceee2ef56a50bb5fea6Andreas Huber } 3697f475c34ffc8e35345f2cceee2ef56a50bb5fea6Andreas Huber 3707f475c34ffc8e35345f2cceee2ef56a50bb5fea6Andreas Huber notifyFlagsChanged(flags); 3717f475c34ffc8e35345f2cceee2ef56a50bb5fea6Andreas Huber notifyPrepared(); 3722bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber break; 3737f475c34ffc8e35345f2cceee2ef56a50bb5fea6Andreas Huber } 3742bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 3752bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber case MyHandler::kWhatDisconnected: 3767f475c34ffc8e35345f2cceee2ef56a50bb5fea6Andreas Huber { 3772bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber onDisconnected(msg); 3782bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber break; 3797f475c34ffc8e35345f2cceee2ef56a50bb5fea6Andreas Huber } 3802bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 3812bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber case MyHandler::kWhatSeekDone: 3822bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber { 3832bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber mState = CONNECTED; 3842bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber break; 3852bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber } 3862bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 3872bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber case MyHandler::kWhatAccessUnit: 3882bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber { 3892bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber size_t trackIndex; 3902bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber CHECK(msg->findSize("trackIndex", &trackIndex)); 39149694688c82214f5fd9e969e177c9e126a240a26Andreas Huber 39249694688c82214f5fd9e969e177c9e126a240a26Andreas Huber if (mTSParser == NULL) { 39349694688c82214f5fd9e969e177c9e126a240a26Andreas Huber CHECK_LT(trackIndex, mTracks.size()); 39449694688c82214f5fd9e969e177c9e126a240a26Andreas Huber } else { 39549694688c82214f5fd9e969e177c9e126a240a26Andreas Huber CHECK_EQ(trackIndex, 0u); 39649694688c82214f5fd9e969e177c9e126a240a26Andreas Huber } 3972bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 3982d8bedd05437b6fccdbc6bf70f673ffd86744d59Andreas Huber sp<ABuffer> accessUnit; 3992d8bedd05437b6fccdbc6bf70f673ffd86744d59Andreas Huber CHECK(msg->findBuffer("accessUnit", &accessUnit)); 4002bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 4012bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber int32_t damaged; 4022bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber if (accessUnit->meta()->findInt32("damaged", &damaged) 4032bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber && damaged) { 404df64d15042bbd5e0e4933ac49bf3c177dd94752cSteve Block ALOGI("dropping damaged access unit."); 4052bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber break; 4062bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber } 4072bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 40849694688c82214f5fd9e969e177c9e126a240a26Andreas Huber if (mTSParser != NULL) { 40949694688c82214f5fd9e969e177c9e126a240a26Andreas Huber size_t offset = 0; 41049694688c82214f5fd9e969e177c9e126a240a26Andreas Huber status_t err = OK; 41149694688c82214f5fd9e969e177c9e126a240a26Andreas Huber while (offset + 188 <= accessUnit->size()) { 41249694688c82214f5fd9e969e177c9e126a240a26Andreas Huber err = mTSParser->feedTSPacket( 41349694688c82214f5fd9e969e177c9e126a240a26Andreas Huber accessUnit->data() + offset, 188); 41449694688c82214f5fd9e969e177c9e126a240a26Andreas Huber if (err != OK) { 41549694688c82214f5fd9e969e177c9e126a240a26Andreas Huber break; 41649694688c82214f5fd9e969e177c9e126a240a26Andreas Huber } 41749694688c82214f5fd9e969e177c9e126a240a26Andreas Huber 41849694688c82214f5fd9e969e177c9e126a240a26Andreas Huber offset += 188; 41949694688c82214f5fd9e969e177c9e126a240a26Andreas Huber } 42049694688c82214f5fd9e969e177c9e126a240a26Andreas Huber 42149694688c82214f5fd9e969e177c9e126a240a26Andreas Huber if (offset < accessUnit->size()) { 42249694688c82214f5fd9e969e177c9e126a240a26Andreas Huber err = ERROR_MALFORMED; 42349694688c82214f5fd9e969e177c9e126a240a26Andreas Huber } 42449694688c82214f5fd9e969e177c9e126a240a26Andreas Huber 42549694688c82214f5fd9e969e177c9e126a240a26Andreas Huber if (err != OK) { 42649694688c82214f5fd9e969e177c9e126a240a26Andreas Huber sp<AnotherPacketSource> source = getSource(false /* audio */); 42749694688c82214f5fd9e969e177c9e126a240a26Andreas Huber if (source != NULL) { 42849694688c82214f5fd9e969e177c9e126a240a26Andreas Huber source->signalEOS(err); 42949694688c82214f5fd9e969e177c9e126a240a26Andreas Huber } 43049694688c82214f5fd9e969e177c9e126a240a26Andreas Huber 43149694688c82214f5fd9e969e177c9e126a240a26Andreas Huber source = getSource(true /* audio */); 43249694688c82214f5fd9e969e177c9e126a240a26Andreas Huber if (source != NULL) { 43349694688c82214f5fd9e969e177c9e126a240a26Andreas Huber source->signalEOS(err); 43449694688c82214f5fd9e969e177c9e126a240a26Andreas Huber } 43549694688c82214f5fd9e969e177c9e126a240a26Andreas Huber } 43649694688c82214f5fd9e969e177c9e126a240a26Andreas Huber break; 43749694688c82214f5fd9e969e177c9e126a240a26Andreas Huber } 43849694688c82214f5fd9e969e177c9e126a240a26Andreas Huber 4391906e5c7492b9cbc88601365536a69e9a490c963Andreas Huber TrackInfo *info = &mTracks.editItemAt(trackIndex); 4401906e5c7492b9cbc88601365536a69e9a490c963Andreas Huber 4411906e5c7492b9cbc88601365536a69e9a490c963Andreas Huber sp<AnotherPacketSource> source = info->mSource; 4422bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber if (source != NULL) { 4432bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber uint32_t rtpTime; 4442bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber CHECK(accessUnit->meta()->findInt32("rtp-time", (int32_t *)&rtpTime)); 4452bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 4461906e5c7492b9cbc88601365536a69e9a490c963Andreas Huber if (!info->mNPTMappingValid) { 4471906e5c7492b9cbc88601365536a69e9a490c963Andreas Huber // This is a live stream, we didn't receive any normal 448c9d1696d214d2175327067ccc1991bcb36976404Andreas Huber // playtime mapping. We won't map to npt time. 449c9d1696d214d2175327067ccc1991bcb36976404Andreas Huber source->queueAccessUnit(accessUnit); 450c9d1696d214d2175327067ccc1991bcb36976404Andreas Huber break; 4511906e5c7492b9cbc88601365536a69e9a490c963Andreas Huber } 4521906e5c7492b9cbc88601365536a69e9a490c963Andreas Huber 4532bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber int64_t nptUs = 4541906e5c7492b9cbc88601365536a69e9a490c963Andreas Huber ((double)rtpTime - (double)info->mRTPTime) 4551906e5c7492b9cbc88601365536a69e9a490c963Andreas Huber / info->mTimeScale 4562bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber * 1000000ll 4571906e5c7492b9cbc88601365536a69e9a490c963Andreas Huber + info->mNormalPlaytimeUs; 4582bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 4592bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber accessUnit->meta()->setInt64("timeUs", nptUs); 4602bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 4612bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber source->queueAccessUnit(accessUnit); 4622bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber } 4632bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber break; 4642bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber } 4652bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 4662bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber case MyHandler::kWhatEOS: 4672bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber { 4682bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber int32_t finalResult; 4692bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber CHECK(msg->findInt32("finalResult", &finalResult)); 4702bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber CHECK_NE(finalResult, (status_t)OK); 4712bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 47249694688c82214f5fd9e969e177c9e126a240a26Andreas Huber if (mTSParser != NULL) { 47349694688c82214f5fd9e969e177c9e126a240a26Andreas Huber sp<AnotherPacketSource> source = getSource(false /* audio */); 47449694688c82214f5fd9e969e177c9e126a240a26Andreas Huber if (source != NULL) { 47549694688c82214f5fd9e969e177c9e126a240a26Andreas Huber source->signalEOS(finalResult); 47649694688c82214f5fd9e969e177c9e126a240a26Andreas Huber } 47749694688c82214f5fd9e969e177c9e126a240a26Andreas Huber 47849694688c82214f5fd9e969e177c9e126a240a26Andreas Huber source = getSource(true /* audio */); 47949694688c82214f5fd9e969e177c9e126a240a26Andreas Huber if (source != NULL) { 48049694688c82214f5fd9e969e177c9e126a240a26Andreas Huber source->signalEOS(finalResult); 48149694688c82214f5fd9e969e177c9e126a240a26Andreas Huber } 48249694688c82214f5fd9e969e177c9e126a240a26Andreas Huber 48349694688c82214f5fd9e969e177c9e126a240a26Andreas Huber return; 48449694688c82214f5fd9e969e177c9e126a240a26Andreas Huber } 48549694688c82214f5fd9e969e177c9e126a240a26Andreas Huber 48649694688c82214f5fd9e969e177c9e126a240a26Andreas Huber size_t trackIndex; 48749694688c82214f5fd9e969e177c9e126a240a26Andreas Huber CHECK(msg->findSize("trackIndex", &trackIndex)); 48849694688c82214f5fd9e969e177c9e126a240a26Andreas Huber CHECK_LT(trackIndex, mTracks.size()); 48949694688c82214f5fd9e969e177c9e126a240a26Andreas Huber 4902bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber TrackInfo *info = &mTracks.editItemAt(trackIndex); 4912bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber sp<AnotherPacketSource> source = info->mSource; 4922bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber if (source != NULL) { 4932bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber source->signalEOS(finalResult); 4942bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber } 4952bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 4962bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber break; 4972bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber } 4982bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 4992bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber case MyHandler::kWhatSeekDiscontinuity: 5002bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber { 5012bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber size_t trackIndex; 5022bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber CHECK(msg->findSize("trackIndex", &trackIndex)); 5032bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber CHECK_LT(trackIndex, mTracks.size()); 5042bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 5052bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber TrackInfo *info = &mTracks.editItemAt(trackIndex); 5062bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber sp<AnotherPacketSource> source = info->mSource; 5072bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber if (source != NULL) { 5082bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber source->queueDiscontinuity(ATSParser::DISCONTINUITY_SEEK, NULL); 5092bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber } 5102bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 5112bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber break; 5122bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber } 5132bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 5142bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber case MyHandler::kWhatNormalPlayTimeMapping: 5152bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber { 5162bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber size_t trackIndex; 5172bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber CHECK(msg->findSize("trackIndex", &trackIndex)); 5182bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber CHECK_LT(trackIndex, mTracks.size()); 5192bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 5202bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber uint32_t rtpTime; 5212bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber CHECK(msg->findInt32("rtpTime", (int32_t *)&rtpTime)); 5222bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 5232bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber int64_t nptUs; 5242bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber CHECK(msg->findInt64("nptUs", &nptUs)); 5252bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 5262bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber TrackInfo *info = &mTracks.editItemAt(trackIndex); 5272bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber info->mRTPTime = rtpTime; 5282bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber info->mNormalPlaytimeUs = nptUs; 5291906e5c7492b9cbc88601365536a69e9a490c963Andreas Huber info->mNPTMappingValid = true; 5302bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber break; 5312bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber } 5322bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 53381dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé case SDPLoader::kWhatSDPLoaded: 53481dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé { 53581dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé onSDPLoaded(msg); 53681dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé break; 53781dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé } 53881dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé 5392bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber default: 5402bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber TRESPASS(); 5412bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber } 5422bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber} 5432bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 5442bfdd428c56c7524d1a11979f200a1762866032dAndreas Hubervoid NuPlayer::RTSPSource::onConnected() { 5452bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber CHECK(mAudioTrack == NULL); 5462bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber CHECK(mVideoTrack == NULL); 5472bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 5482bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber size_t numTracks = mHandler->countTracks(); 5492bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber for (size_t i = 0; i < numTracks; ++i) { 5502bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber int32_t timeScale; 5512bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber sp<MetaData> format = mHandler->getTrackFormat(i, &timeScale); 5522bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 5532bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber const char *mime; 5542bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber CHECK(format->findCString(kKeyMIMEType, &mime)); 5552bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 55649694688c82214f5fd9e969e177c9e126a240a26Andreas Huber if (!strcasecmp(mime, MEDIA_MIMETYPE_CONTAINER_MPEG2TS)) { 55749694688c82214f5fd9e969e177c9e126a240a26Andreas Huber // Very special case for MPEG2 Transport Streams. 55849694688c82214f5fd9e969e177c9e126a240a26Andreas Huber CHECK_EQ(numTracks, 1u); 55949694688c82214f5fd9e969e177c9e126a240a26Andreas Huber 56049694688c82214f5fd9e969e177c9e126a240a26Andreas Huber mTSParser = new ATSParser; 56149694688c82214f5fd9e969e177c9e126a240a26Andreas Huber return; 56249694688c82214f5fd9e969e177c9e126a240a26Andreas Huber } 56349694688c82214f5fd9e969e177c9e126a240a26Andreas Huber 5642bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber bool isAudio = !strncasecmp(mime, "audio/", 6); 5652bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber bool isVideo = !strncasecmp(mime, "video/", 6); 5662bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 5672bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber TrackInfo info; 5682bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber info.mTimeScale = timeScale; 5692bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber info.mRTPTime = 0; 5702bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber info.mNormalPlaytimeUs = 0ll; 5711906e5c7492b9cbc88601365536a69e9a490c963Andreas Huber info.mNPTMappingValid = false; 5722bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 5732bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber if ((isAudio && mAudioTrack == NULL) 5742bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber || (isVideo && mVideoTrack == NULL)) { 5752bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber sp<AnotherPacketSource> source = new AnotherPacketSource(format); 5762bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 5772bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber if (isAudio) { 5782bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber mAudioTrack = source; 5792bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber } else { 5802bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber mVideoTrack = source; 5812bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber } 5822bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 5832bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber info.mSource = source; 5842bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber } 5852bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 5862bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber mTracks.push(info); 5872bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber } 5882bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 5892bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber mState = CONNECTED; 5902bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber} 5912bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 59281dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhévoid NuPlayer::RTSPSource::onSDPLoaded(const sp<AMessage> &msg) { 59381dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé status_t err; 59481dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé CHECK(msg->findInt32("result", &err)); 59581dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé 59681dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé mSDPLoader.clear(); 59781dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé 59881dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé if (mDisconnectReplyID != 0) { 59981dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé err = UNKNOWN_ERROR; 60081dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé } 60181dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé 60281dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé if (err == OK) { 60381dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé sp<ASessionDescription> desc; 60481dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé sp<RefBase> obj; 60581dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé CHECK(msg->findObject("description", &obj)); 60681dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé desc = static_cast<ASessionDescription *>(obj.get()); 60781dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé 60881dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé AString rtspUri; 60981dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé if (!desc->findAttribute(0, "a=control", &rtspUri)) { 61081dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé ALOGE("Unable to find url in SDP"); 61181dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé err = UNKNOWN_ERROR; 61281dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé } else { 61381dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé sp<AMessage> notify = new AMessage(kWhatNotify, mReflector->id()); 61481dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé 61581dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé mHandler = new MyHandler(rtspUri.c_str(), notify, mUIDValid, mUID); 61681dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé mLooper->registerHandler(mHandler); 61781dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé 61881dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé mHandler->loadSDP(desc); 61981dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé } 62081dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé } 62181dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé 62281dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé if (err != OK) { 6237f475c34ffc8e35345f2cceee2ef56a50bb5fea6Andreas Huber if (mState == CONNECTING) { 6247f475c34ffc8e35345f2cceee2ef56a50bb5fea6Andreas Huber // We're still in the preparation phase, signal that it 6257f475c34ffc8e35345f2cceee2ef56a50bb5fea6Andreas Huber // failed. 6267f475c34ffc8e35345f2cceee2ef56a50bb5fea6Andreas Huber notifyPrepared(err); 6277f475c34ffc8e35345f2cceee2ef56a50bb5fea6Andreas Huber } 6287f475c34ffc8e35345f2cceee2ef56a50bb5fea6Andreas Huber 62981dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé mState = DISCONNECTED; 63081dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé mFinalResult = err; 63181dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé 63281dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé if (mDisconnectReplyID != 0) { 63381dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé finishDisconnectIfPossible(); 63481dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé } 63581dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé } 63681dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé} 63781dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé 6382bfdd428c56c7524d1a11979f200a1762866032dAndreas Hubervoid NuPlayer::RTSPSource::onDisconnected(const sp<AMessage> &msg) { 6390ad03bc59d090a0455f858d2f629834c105f6f37Fredrik Rosin if (mState == DISCONNECTED) { 6400ad03bc59d090a0455f858d2f629834c105f6f37Fredrik Rosin return; 6410ad03bc59d090a0455f858d2f629834c105f6f37Fredrik Rosin } 6420ad03bc59d090a0455f858d2f629834c105f6f37Fredrik Rosin 6432bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber status_t err; 6442bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber CHECK(msg->findInt32("result", &err)); 6452bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber CHECK_NE(err, (status_t)OK); 6462bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 6472bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber mLooper->unregisterHandler(mHandler->id()); 6482bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber mHandler.clear(); 6492bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 6507f475c34ffc8e35345f2cceee2ef56a50bb5fea6Andreas Huber if (mState == CONNECTING) { 6517f475c34ffc8e35345f2cceee2ef56a50bb5fea6Andreas Huber // We're still in the preparation phase, signal that it 6527f475c34ffc8e35345f2cceee2ef56a50bb5fea6Andreas Huber // failed. 6537f475c34ffc8e35345f2cceee2ef56a50bb5fea6Andreas Huber notifyPrepared(err); 6547f475c34ffc8e35345f2cceee2ef56a50bb5fea6Andreas Huber } 6557f475c34ffc8e35345f2cceee2ef56a50bb5fea6Andreas Huber 6562bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber mState = DISCONNECTED; 6572bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber mFinalResult = err; 6582bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 6592bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber if (mDisconnectReplyID != 0) { 6602bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber finishDisconnectIfPossible(); 6612bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber } 6622bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber} 6632bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 6642bfdd428c56c7524d1a11979f200a1762866032dAndreas Hubervoid NuPlayer::RTSPSource::finishDisconnectIfPossible() { 6652bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber if (mState != DISCONNECTED) { 66681dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé if (mHandler != NULL) { 66781dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé mHandler->disconnect(); 66881dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé } else if (mSDPLoader != NULL) { 66981dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé mSDPLoader->cancel(); 67081dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé } 6712bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber return; 6722bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber } 6732bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 6742bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber (new AMessage)->postReply(mDisconnectReplyID); 6752bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber mDisconnectReplyID = 0; 6762bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber} 6772bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 6782bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber} // namespace android 679