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 35641e0c718da1c58e5b89379f60465c4e564ebb73Robert Shih// Buffer Underflow/Prepare/StartServer/Overflow Marks 36641e0c718da1c58e5b89379f60465c4e564ebb73Robert Shihconst int64_t NuPlayer::RTSPSource::kUnderflowMarkUs = 1000000ll; 37641e0c718da1c58e5b89379f60465c4e564ebb73Robert Shihconst int64_t NuPlayer::RTSPSource::kPrepareMarkUs = 3000000ll; 38641e0c718da1c58e5b89379f60465c4e564ebb73Robert Shihconst int64_t NuPlayer::RTSPSource::kStartServerMarkUs = 5000000ll; 39641e0c718da1c58e5b89379f60465c4e564ebb73Robert Shihconst int64_t NuPlayer::RTSPSource::kOverflowMarkUs = 10000000ll; 40641e0c718da1c58e5b89379f60465c4e564ebb73Robert Shih 412bfdd428c56c7524d1a11979f200a1762866032dAndreas HuberNuPlayer::RTSPSource::RTSPSource( 425ab368af38fefacc4009e3ab1c1bbd00e62b3bcfAndreas Huber const sp<AMessage> ¬ify, 431b86fe063badb5f28c467ade39be0f4008688947Andreas Huber const sp<IMediaHTTPService> &httpService, 442bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber const char *url, 452bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber const KeyedVector<String8, String8> *headers, 462bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber bool uidValid, 4781dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé uid_t uid, 4881dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé bool isSDP) 495ab368af38fefacc4009e3ab1c1bbd00e62b3bcfAndreas Huber : Source(notify), 501b86fe063badb5f28c467ade39be0f4008688947Andreas Huber mHTTPService(httpService), 515ab368af38fefacc4009e3ab1c1bbd00e62b3bcfAndreas Huber mURL(url), 522bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber mUIDValid(uidValid), 532bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber mUID(uid), 542bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber mFlags(0), 5581dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé mIsSDP(isSDP), 562bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber mState(DISCONNECTED), 572bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber mFinalResult(OK), 58ee736e9e74c5368db8d63214513c85cb74bb0183Andreas Huber mDisconnectReplyID(0), 59180d1b96ee2312f1056a58e26884a89d25ab62c8Chong Zhang mBuffering(false), 60641e0c718da1c58e5b89379f60465c4e564ebb73Robert Shih mInPreparationPhase(true), 61cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson mSeekGeneration(0), 62cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson mEOSTimeoutAudio(0), 63cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson mEOSTimeoutVideo(0) { 642bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber if (headers) { 652bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber mExtraHeaders = *headers; 662bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 672bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber ssize_t index = 682bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber mExtraHeaders.indexOfKey(String8("x-hide-urls-from-log")); 692bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 702bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber if (index >= 0) { 712bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber mFlags |= kFlagIncognito; 722bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 732bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber mExtraHeaders.removeItemsAt(index); 742bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber } 752bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber } 762bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber} 772bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 782bfdd428c56c7524d1a11979f200a1762866032dAndreas HuberNuPlayer::RTSPSource::~RTSPSource() { 79602f5bbd7596ec3fe447fde4329d5d4f0b370835Andreas Huber if (mLooper != NULL) { 801228d6b175de8b21787cbe0c6c4bb5642f4d555eChong Zhang mLooper->unregisterHandler(id()); 81602f5bbd7596ec3fe447fde4329d5d4f0b370835Andreas Huber mLooper->stop(); 82602f5bbd7596ec3fe447fde4329d5d4f0b370835Andreas Huber } 832bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber} 842bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 8557cea553cb19235553463412db5ad04c99835411Andreas Hubervoid NuPlayer::RTSPSource::prepareAsync() { 86ce84b2240497cd0923e190ae115e319e4c17d303Wei Jia if (mIsSDP && mHTTPService == NULL) { 87ce84b2240497cd0923e190ae115e319e4c17d303Wei Jia notifyPrepared(BAD_VALUE); 88ce84b2240497cd0923e190ae115e319e4c17d303Wei Jia return; 89ce84b2240497cd0923e190ae115e319e4c17d303Wei Jia } 90ce84b2240497cd0923e190ae115e319e4c17d303Wei Jia 912bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber if (mLooper == NULL) { 922bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber mLooper = new ALooper; 932bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber mLooper->setName("rtsp"); 942bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber mLooper->start(); 952bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 961228d6b175de8b21787cbe0c6c4bb5642f4d555eChong Zhang mLooper->registerHandler(this); 972bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber } 982bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 992bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber CHECK(mHandler == NULL); 10081dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé CHECK(mSDPLoader == NULL); 1012bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 1021d15ab58bf8239069ef343de6cb21aabf3ef7d78Lajos Molnar sp<AMessage> notify = new AMessage(kWhatNotify, this); 1032bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 1042bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber CHECK_EQ(mState, (int)DISCONNECTED); 1052bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber mState = CONNECTING; 1062bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 10781dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé if (mIsSDP) { 10881dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé mSDPLoader = new SDPLoader(notify, 10981dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé (mFlags & kFlagIncognito) ? SDPLoader::kFlagIncognito : 0, 11081e68448f3361eaf8618930471fdc3c21bdf5cbcAndreas Huber mHTTPService); 11181dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé 11257cea553cb19235553463412db5ad04c99835411Andreas Huber mSDPLoader->load( 11357cea553cb19235553463412db5ad04c99835411Andreas Huber mURL.c_str(), mExtraHeaders.isEmpty() ? NULL : &mExtraHeaders); 11481dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé } else { 11581dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé mHandler = new MyHandler(mURL.c_str(), notify, mUIDValid, mUID); 11681dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé mLooper->registerHandler(mHandler); 11781dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé 11881dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé mHandler->connect(); 11981dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé } 120cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson 121180d1b96ee2312f1056a58e26884a89d25ab62c8Chong Zhang startBufferingIfNecessary(); 12257cea553cb19235553463412db5ad04c99835411Andreas Huber} 12357cea553cb19235553463412db5ad04c99835411Andreas Huber 12457cea553cb19235553463412db5ad04c99835411Andreas Hubervoid NuPlayer::RTSPSource::start() { 1252bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber} 1262bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 1272bfdd428c56c7524d1a11979f200a1762866032dAndreas Hubervoid NuPlayer::RTSPSource::stop() { 1285834181d3f168acb8ff4bf3eff1fd1186afb0bd4James Dong if (mLooper == NULL) { 1295834181d3f168acb8ff4bf3eff1fd1186afb0bd4James Dong return; 1305834181d3f168acb8ff4bf3eff1fd1186afb0bd4James Dong } 1311d15ab58bf8239069ef343de6cb21aabf3ef7d78Lajos Molnar sp<AMessage> msg = new AMessage(kWhatDisconnect, this); 1322bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 1332bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber sp<AMessage> dummy; 1342bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber msg->postAndAwaitResponse(&dummy); 1352bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber} 1362bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 1372bfdd428c56c7524d1a11979f200a1762866032dAndreas Huberstatus_t NuPlayer::RTSPSource::feedMoreTSData() { 138180d1b96ee2312f1056a58e26884a89d25ab62c8Chong Zhang Mutex::Autolock _l(mBufferingLock); 1392bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber return mFinalResult; 1402bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber} 1412bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 142840667883fd09d44015716d79bc3ac4d60edc0f0Andreas Hubersp<MetaData> NuPlayer::RTSPSource::getFormatMeta(bool audio) { 1432bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber sp<AnotherPacketSource> source = getSource(audio); 1442bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 1452bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber if (source == NULL) { 1462bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber return NULL; 1472bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber } 1482bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 1492bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber return source->getFormat(); 1502bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber} 1512bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 152bfd4d0d9fe0033abf3f55b94f30f6a58846a875eAndreas Huberbool NuPlayer::RTSPSource::haveSufficientDataOnAllTracks() { 153bfd4d0d9fe0033abf3f55b94f30f6a58846a875eAndreas Huber // We're going to buffer at least 2 secs worth data on all tracks before 154bfd4d0d9fe0033abf3f55b94f30f6a58846a875eAndreas Huber // starting playback (both at startup and after a seek). 155bfd4d0d9fe0033abf3f55b94f30f6a58846a875eAndreas Huber 156bfd4d0d9fe0033abf3f55b94f30f6a58846a875eAndreas Huber static const int64_t kMinDurationUs = 2000000ll; 157bfd4d0d9fe0033abf3f55b94f30f6a58846a875eAndreas Huber 158cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson int64_t mediaDurationUs = 0; 159cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson getDuration(&mediaDurationUs); 160cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson if ((mAudioTrack != NULL && mAudioTrack->isFinished(mediaDurationUs)) 161cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson || (mVideoTrack != NULL && mVideoTrack->isFinished(mediaDurationUs))) { 162cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson return true; 163cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson } 164cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson 165bfd4d0d9fe0033abf3f55b94f30f6a58846a875eAndreas Huber status_t err; 166bfd4d0d9fe0033abf3f55b94f30f6a58846a875eAndreas Huber int64_t durationUs; 167bfd4d0d9fe0033abf3f55b94f30f6a58846a875eAndreas Huber if (mAudioTrack != NULL 168bfd4d0d9fe0033abf3f55b94f30f6a58846a875eAndreas Huber && (durationUs = mAudioTrack->getBufferedDurationUs(&err)) 169bfd4d0d9fe0033abf3f55b94f30f6a58846a875eAndreas Huber < kMinDurationUs 170bfd4d0d9fe0033abf3f55b94f30f6a58846a875eAndreas Huber && err == OK) { 171bfd4d0d9fe0033abf3f55b94f30f6a58846a875eAndreas Huber ALOGV("audio track doesn't have enough data yet. (%.2f secs buffered)", 172bfd4d0d9fe0033abf3f55b94f30f6a58846a875eAndreas Huber durationUs / 1E6); 173bfd4d0d9fe0033abf3f55b94f30f6a58846a875eAndreas Huber return false; 174bfd4d0d9fe0033abf3f55b94f30f6a58846a875eAndreas Huber } 175bfd4d0d9fe0033abf3f55b94f30f6a58846a875eAndreas Huber 176bfd4d0d9fe0033abf3f55b94f30f6a58846a875eAndreas Huber if (mVideoTrack != NULL 177bfd4d0d9fe0033abf3f55b94f30f6a58846a875eAndreas Huber && (durationUs = mVideoTrack->getBufferedDurationUs(&err)) 178bfd4d0d9fe0033abf3f55b94f30f6a58846a875eAndreas Huber < kMinDurationUs 179bfd4d0d9fe0033abf3f55b94f30f6a58846a875eAndreas Huber && err == OK) { 180bfd4d0d9fe0033abf3f55b94f30f6a58846a875eAndreas Huber ALOGV("video track doesn't have enough data yet. (%.2f secs buffered)", 181bfd4d0d9fe0033abf3f55b94f30f6a58846a875eAndreas Huber durationUs / 1E6); 182bfd4d0d9fe0033abf3f55b94f30f6a58846a875eAndreas Huber return false; 183bfd4d0d9fe0033abf3f55b94f30f6a58846a875eAndreas Huber } 184bfd4d0d9fe0033abf3f55b94f30f6a58846a875eAndreas Huber 185bfd4d0d9fe0033abf3f55b94f30f6a58846a875eAndreas Huber return true; 186bfd4d0d9fe0033abf3f55b94f30f6a58846a875eAndreas Huber} 187bfd4d0d9fe0033abf3f55b94f30f6a58846a875eAndreas Huber 1882bfdd428c56c7524d1a11979f200a1762866032dAndreas Huberstatus_t NuPlayer::RTSPSource::dequeueAccessUnit( 1892bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber bool audio, sp<ABuffer> *accessUnit) { 190180d1b96ee2312f1056a58e26884a89d25ab62c8Chong Zhang if (!stopBufferingIfNecessary()) { 191180d1b96ee2312f1056a58e26884a89d25ab62c8Chong Zhang return -EWOULDBLOCK; 192bfd4d0d9fe0033abf3f55b94f30f6a58846a875eAndreas Huber } 193bfd4d0d9fe0033abf3f55b94f30f6a58846a875eAndreas Huber 1942bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber sp<AnotherPacketSource> source = getSource(audio); 1952bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 1962bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber if (source == NULL) { 1972bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber return -EWOULDBLOCK; 1982bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber } 1992bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 2002bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber status_t finalResult; 2012bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber if (!source->hasBufferAvailable(&finalResult)) { 202cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson if (finalResult == OK) { 203cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson int64_t mediaDurationUs = 0; 204cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson getDuration(&mediaDurationUs); 205cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson sp<AnotherPacketSource> otherSource = getSource(!audio); 206cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson status_t otherFinalResult; 207cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson 208cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson // If other source already signaled EOS, this source should also signal EOS 209cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson if (otherSource != NULL && 210cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson !otherSource->hasBufferAvailable(&otherFinalResult) && 211cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson otherFinalResult == ERROR_END_OF_STREAM) { 212cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson source->signalEOS(ERROR_END_OF_STREAM); 213cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson return ERROR_END_OF_STREAM; 214cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson } 215cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson 216cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson // If this source has detected near end, give it some time to retrieve more 217cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson // data before signaling EOS 218cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson if (source->isFinished(mediaDurationUs)) { 219cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson int64_t eosTimeout = audio ? mEOSTimeoutAudio : mEOSTimeoutVideo; 220cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson if (eosTimeout == 0) { 221cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson setEOSTimeout(audio, ALooper::GetNowUs()); 222cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson } else if ((ALooper::GetNowUs() - eosTimeout) > kNearEOSTimeoutUs) { 223cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson setEOSTimeout(audio, 0); 224cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson source->signalEOS(ERROR_END_OF_STREAM); 225cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson return ERROR_END_OF_STREAM; 226cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson } 227cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson return -EWOULDBLOCK; 228cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson } 229cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson 230cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson if (!(otherSource != NULL && otherSource->isFinished(mediaDurationUs))) { 231cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson // We should not enter buffering mode 232cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson // if any of the sources already have detected EOS. 233180d1b96ee2312f1056a58e26884a89d25ab62c8Chong Zhang startBufferingIfNecessary(); 234cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson } 235cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson 236cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson return -EWOULDBLOCK; 237cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson } 238cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson return finalResult; 2392bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber } 2402bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 241cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson setEOSTimeout(audio, 0); 242cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson 2432bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber return source->dequeueAccessUnit(accessUnit); 2442bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber} 2452bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 2462bfdd428c56c7524d1a11979f200a1762866032dAndreas Hubersp<AnotherPacketSource> NuPlayer::RTSPSource::getSource(bool audio) { 24749694688c82214f5fd9e969e177c9e126a240a26Andreas Huber if (mTSParser != NULL) { 24849694688c82214f5fd9e969e177c9e126a240a26Andreas Huber sp<MediaSource> source = mTSParser->getSource( 24949694688c82214f5fd9e969e177c9e126a240a26Andreas Huber audio ? ATSParser::AUDIO : ATSParser::VIDEO); 25049694688c82214f5fd9e969e177c9e126a240a26Andreas Huber 25149694688c82214f5fd9e969e177c9e126a240a26Andreas Huber return static_cast<AnotherPacketSource *>(source.get()); 25249694688c82214f5fd9e969e177c9e126a240a26Andreas Huber } 25349694688c82214f5fd9e969e177c9e126a240a26Andreas Huber 2542bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber return audio ? mAudioTrack : mVideoTrack; 2552bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber} 2562bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 257cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönssonvoid NuPlayer::RTSPSource::setEOSTimeout(bool audio, int64_t timeout) { 258cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson if (audio) { 259cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson mEOSTimeoutAudio = timeout; 260cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson } else { 261cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson mEOSTimeoutVideo = timeout; 262cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson } 263cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson} 264cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson 2652bfdd428c56c7524d1a11979f200a1762866032dAndreas Huberstatus_t NuPlayer::RTSPSource::getDuration(int64_t *durationUs) { 2662bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber *durationUs = 0ll; 2672bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 2682bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber int64_t audioDurationUs; 2692bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber if (mAudioTrack != NULL 2702bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber && mAudioTrack->getFormat()->findInt64( 2712bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber kKeyDuration, &audioDurationUs) 2722bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber && audioDurationUs > *durationUs) { 2732bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber *durationUs = audioDurationUs; 2742bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber } 2752bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 2762bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber int64_t videoDurationUs; 2772bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber if (mVideoTrack != NULL 2782bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber && mVideoTrack->getFormat()->findInt64( 2792bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber kKeyDuration, &videoDurationUs) 2802bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber && videoDurationUs > *durationUs) { 2812bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber *durationUs = videoDurationUs; 2822bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber } 2832bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 2842bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber return OK; 2852bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber} 2862bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 2872bfdd428c56c7524d1a11979f200a1762866032dAndreas Huberstatus_t NuPlayer::RTSPSource::seekTo(int64_t seekTimeUs) { 2881d15ab58bf8239069ef343de6cb21aabf3ef7d78Lajos Molnar sp<AMessage> msg = new AMessage(kWhatPerformSeek, this); 289ee736e9e74c5368db8d63214513c85cb74bb0183Andreas Huber msg->setInt32("generation", ++mSeekGeneration); 290ee736e9e74c5368db8d63214513c85cb74bb0183Andreas Huber msg->setInt64("timeUs", seekTimeUs); 291ee736e9e74c5368db8d63214513c85cb74bb0183Andreas Huber 2928d237a5ce1e3c1dbc1d538f47e68cff2cc52d799Robert Shih sp<AMessage> response; 2938d237a5ce1e3c1dbc1d538f47e68cff2cc52d799Robert Shih status_t err = msg->postAndAwaitResponse(&response); 2948d237a5ce1e3c1dbc1d538f47e68cff2cc52d799Robert Shih if (err == OK && response != NULL) { 2958d237a5ce1e3c1dbc1d538f47e68cff2cc52d799Robert Shih CHECK(response->findInt32("err", &err)); 2968d237a5ce1e3c1dbc1d538f47e68cff2cc52d799Robert Shih } 2978d237a5ce1e3c1dbc1d538f47e68cff2cc52d799Robert Shih 2988d237a5ce1e3c1dbc1d538f47e68cff2cc52d799Robert Shih return err; 299ee736e9e74c5368db8d63214513c85cb74bb0183Andreas Huber} 300ee736e9e74c5368db8d63214513c85cb74bb0183Andreas Huber 301ee736e9e74c5368db8d63214513c85cb74bb0183Andreas Hubervoid NuPlayer::RTSPSource::performSeek(int64_t seekTimeUs) { 3022bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber if (mState != CONNECTED) { 3038d237a5ce1e3c1dbc1d538f47e68cff2cc52d799Robert Shih finishSeek(INVALID_OPERATION); 304ee736e9e74c5368db8d63214513c85cb74bb0183Andreas Huber return; 3052bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber } 3062bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 3072bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber mState = SEEKING; 3082bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber mHandler->seek(seekTimeUs); 3092bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber} 3102bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 311641e0c718da1c58e5b89379f60465c4e564ebb73Robert Shihvoid NuPlayer::RTSPSource::schedulePollBuffering() { 312641e0c718da1c58e5b89379f60465c4e564ebb73Robert Shih sp<AMessage> msg = new AMessage(kWhatPollBuffering, this); 313641e0c718da1c58e5b89379f60465c4e564ebb73Robert Shih msg->post(1000000ll); // 1 second intervals 314641e0c718da1c58e5b89379f60465c4e564ebb73Robert Shih} 315641e0c718da1c58e5b89379f60465c4e564ebb73Robert Shih 316641e0c718da1c58e5b89379f60465c4e564ebb73Robert Shihvoid NuPlayer::RTSPSource::checkBuffering( 317641e0c718da1c58e5b89379f60465c4e564ebb73Robert Shih bool *prepared, bool *underflow, bool *overflow, bool *startServer) { 318641e0c718da1c58e5b89379f60465c4e564ebb73Robert Shih size_t numTracks = mTracks.size(); 319641e0c718da1c58e5b89379f60465c4e564ebb73Robert Shih size_t preparedCount, underflowCount, overflowCount, startCount; 320641e0c718da1c58e5b89379f60465c4e564ebb73Robert Shih preparedCount = underflowCount = overflowCount = startCount = 0; 321641e0c718da1c58e5b89379f60465c4e564ebb73Robert Shih for (size_t i = 0; i < numTracks; ++i) { 322641e0c718da1c58e5b89379f60465c4e564ebb73Robert Shih status_t finalResult; 323641e0c718da1c58e5b89379f60465c4e564ebb73Robert Shih TrackInfo *info = &mTracks.editItemAt(i); 324641e0c718da1c58e5b89379f60465c4e564ebb73Robert Shih sp<AnotherPacketSource> src = info->mSource; 325641e0c718da1c58e5b89379f60465c4e564ebb73Robert Shih int64_t bufferedDurationUs = src->getBufferedDurationUs(&finalResult); 326641e0c718da1c58e5b89379f60465c4e564ebb73Robert Shih 327641e0c718da1c58e5b89379f60465c4e564ebb73Robert Shih // isFinished when duration is 0 checks for EOS result only 328641e0c718da1c58e5b89379f60465c4e564ebb73Robert Shih if (bufferedDurationUs > kPrepareMarkUs || src->isFinished(/* duration */ 0)) { 329641e0c718da1c58e5b89379f60465c4e564ebb73Robert Shih ++preparedCount; 330641e0c718da1c58e5b89379f60465c4e564ebb73Robert Shih } 331641e0c718da1c58e5b89379f60465c4e564ebb73Robert Shih 332641e0c718da1c58e5b89379f60465c4e564ebb73Robert Shih if (src->isFinished(/* duration */ 0)) { 333641e0c718da1c58e5b89379f60465c4e564ebb73Robert Shih ++overflowCount; 334641e0c718da1c58e5b89379f60465c4e564ebb73Robert Shih } else { 335641e0c718da1c58e5b89379f60465c4e564ebb73Robert Shih if (bufferedDurationUs < kUnderflowMarkUs) { 336641e0c718da1c58e5b89379f60465c4e564ebb73Robert Shih ++underflowCount; 337641e0c718da1c58e5b89379f60465c4e564ebb73Robert Shih } 338641e0c718da1c58e5b89379f60465c4e564ebb73Robert Shih if (bufferedDurationUs > kOverflowMarkUs) { 339641e0c718da1c58e5b89379f60465c4e564ebb73Robert Shih ++overflowCount; 340641e0c718da1c58e5b89379f60465c4e564ebb73Robert Shih } 341641e0c718da1c58e5b89379f60465c4e564ebb73Robert Shih if (bufferedDurationUs < kStartServerMarkUs) { 342641e0c718da1c58e5b89379f60465c4e564ebb73Robert Shih ++startCount; 343641e0c718da1c58e5b89379f60465c4e564ebb73Robert Shih } 344641e0c718da1c58e5b89379f60465c4e564ebb73Robert Shih } 345641e0c718da1c58e5b89379f60465c4e564ebb73Robert Shih } 346641e0c718da1c58e5b89379f60465c4e564ebb73Robert Shih 347641e0c718da1c58e5b89379f60465c4e564ebb73Robert Shih *prepared = (preparedCount == numTracks); 348641e0c718da1c58e5b89379f60465c4e564ebb73Robert Shih *underflow = (underflowCount > 0); 349641e0c718da1c58e5b89379f60465c4e564ebb73Robert Shih *overflow = (overflowCount == numTracks); 350641e0c718da1c58e5b89379f60465c4e564ebb73Robert Shih *startServer = (startCount > 0); 351641e0c718da1c58e5b89379f60465c4e564ebb73Robert Shih} 352641e0c718da1c58e5b89379f60465c4e564ebb73Robert Shih 353641e0c718da1c58e5b89379f60465c4e564ebb73Robert Shihvoid NuPlayer::RTSPSource::onPollBuffering() { 354641e0c718da1c58e5b89379f60465c4e564ebb73Robert Shih bool prepared, underflow, overflow, startServer; 355641e0c718da1c58e5b89379f60465c4e564ebb73Robert Shih checkBuffering(&prepared, &underflow, &overflow, &startServer); 356641e0c718da1c58e5b89379f60465c4e564ebb73Robert Shih 357641e0c718da1c58e5b89379f60465c4e564ebb73Robert Shih if (prepared && mInPreparationPhase) { 358641e0c718da1c58e5b89379f60465c4e564ebb73Robert Shih mInPreparationPhase = false; 359641e0c718da1c58e5b89379f60465c4e564ebb73Robert Shih notifyPrepared(); 360641e0c718da1c58e5b89379f60465c4e564ebb73Robert Shih } 361641e0c718da1c58e5b89379f60465c4e564ebb73Robert Shih 362641e0c718da1c58e5b89379f60465c4e564ebb73Robert Shih if (!mInPreparationPhase && underflow) { 363641e0c718da1c58e5b89379f60465c4e564ebb73Robert Shih startBufferingIfNecessary(); 364641e0c718da1c58e5b89379f60465c4e564ebb73Robert Shih } 365641e0c718da1c58e5b89379f60465c4e564ebb73Robert Shih 366641e0c718da1c58e5b89379f60465c4e564ebb73Robert Shih if (overflow && mHandler != NULL) { 367641e0c718da1c58e5b89379f60465c4e564ebb73Robert Shih stopBufferingIfNecessary(); 368641e0c718da1c58e5b89379f60465c4e564ebb73Robert Shih mHandler->pause(); 369641e0c718da1c58e5b89379f60465c4e564ebb73Robert Shih } 370641e0c718da1c58e5b89379f60465c4e564ebb73Robert Shih 371641e0c718da1c58e5b89379f60465c4e564ebb73Robert Shih if (startServer && mHandler != NULL) { 372641e0c718da1c58e5b89379f60465c4e564ebb73Robert Shih mHandler->resume(); 373641e0c718da1c58e5b89379f60465c4e564ebb73Robert Shih } 374641e0c718da1c58e5b89379f60465c4e564ebb73Robert Shih 375641e0c718da1c58e5b89379f60465c4e564ebb73Robert Shih schedulePollBuffering(); 376641e0c718da1c58e5b89379f60465c4e564ebb73Robert Shih} 377641e0c718da1c58e5b89379f60465c4e564ebb73Robert Shih 3782bfdd428c56c7524d1a11979f200a1762866032dAndreas Hubervoid NuPlayer::RTSPSource::onMessageReceived(const sp<AMessage> &msg) { 3792bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber if (msg->what() == kWhatDisconnect) { 3803f27436a9346f043f52265da1e6a74cde2bffd4dLajos Molnar sp<AReplyToken> replyID; 3812bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber CHECK(msg->senderAwaitsResponse(&replyID)); 3822bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 3832bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber mDisconnectReplyID = replyID; 3842bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber finishDisconnectIfPossible(); 3852bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber return; 386ee736e9e74c5368db8d63214513c85cb74bb0183Andreas Huber } else if (msg->what() == kWhatPerformSeek) { 387ee736e9e74c5368db8d63214513c85cb74bb0183Andreas Huber int32_t generation; 388ee736e9e74c5368db8d63214513c85cb74bb0183Andreas Huber CHECK(msg->findInt32("generation", &generation)); 3898d237a5ce1e3c1dbc1d538f47e68cff2cc52d799Robert Shih CHECK(msg->senderAwaitsResponse(&mSeekReplyID)); 390ee736e9e74c5368db8d63214513c85cb74bb0183Andreas Huber 391ee736e9e74c5368db8d63214513c85cb74bb0183Andreas Huber if (generation != mSeekGeneration) { 392ee736e9e74c5368db8d63214513c85cb74bb0183Andreas Huber // obsolete. 3938d237a5ce1e3c1dbc1d538f47e68cff2cc52d799Robert Shih finishSeek(OK); 394ee736e9e74c5368db8d63214513c85cb74bb0183Andreas Huber return; 395ee736e9e74c5368db8d63214513c85cb74bb0183Andreas Huber } 396ee736e9e74c5368db8d63214513c85cb74bb0183Andreas Huber 397ee736e9e74c5368db8d63214513c85cb74bb0183Andreas Huber int64_t seekTimeUs; 398ee736e9e74c5368db8d63214513c85cb74bb0183Andreas Huber CHECK(msg->findInt64("timeUs", &seekTimeUs)); 399ee736e9e74c5368db8d63214513c85cb74bb0183Andreas Huber 400ee736e9e74c5368db8d63214513c85cb74bb0183Andreas Huber performSeek(seekTimeUs); 401ee736e9e74c5368db8d63214513c85cb74bb0183Andreas Huber return; 402641e0c718da1c58e5b89379f60465c4e564ebb73Robert Shih } else if (msg->what() == kWhatPollBuffering) { 403641e0c718da1c58e5b89379f60465c4e564ebb73Robert Shih onPollBuffering(); 404641e0c718da1c58e5b89379f60465c4e564ebb73Robert Shih return; 4052bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber } 4062bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 4072bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber CHECK_EQ(msg->what(), (int)kWhatNotify); 4082bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 4092bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber int32_t what; 4102bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber CHECK(msg->findInt32("what", &what)); 4112bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 4122bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber switch (what) { 4132bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber case MyHandler::kWhatConnected: 4147f475c34ffc8e35345f2cceee2ef56a50bb5fea6Andreas Huber { 4152bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber onConnected(); 4167f475c34ffc8e35345f2cceee2ef56a50bb5fea6Andreas Huber 417ced1c2f8f6c422063092f5cc5c675ccdebb2dc10Chong Zhang notifyVideoSizeChanged(); 4187f475c34ffc8e35345f2cceee2ef56a50bb5fea6Andreas Huber 4197f475c34ffc8e35345f2cceee2ef56a50bb5fea6Andreas Huber uint32_t flags = 0; 4207f475c34ffc8e35345f2cceee2ef56a50bb5fea6Andreas Huber 4217f475c34ffc8e35345f2cceee2ef56a50bb5fea6Andreas Huber if (mHandler->isSeekable()) { 4224b7069dac546ad21cf62ca6132d50ea41857d08eChong Zhang flags = FLAG_CAN_PAUSE 4234b7069dac546ad21cf62ca6132d50ea41857d08eChong Zhang | FLAG_CAN_SEEK 4244b7069dac546ad21cf62ca6132d50ea41857d08eChong Zhang | FLAG_CAN_SEEK_BACKWARD 4254b7069dac546ad21cf62ca6132d50ea41857d08eChong Zhang | FLAG_CAN_SEEK_FORWARD; 4267f475c34ffc8e35345f2cceee2ef56a50bb5fea6Andreas Huber } 4277f475c34ffc8e35345f2cceee2ef56a50bb5fea6Andreas Huber 4287f475c34ffc8e35345f2cceee2ef56a50bb5fea6Andreas Huber notifyFlagsChanged(flags); 429641e0c718da1c58e5b89379f60465c4e564ebb73Robert Shih schedulePollBuffering(); 4302bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber break; 4317f475c34ffc8e35345f2cceee2ef56a50bb5fea6Andreas Huber } 4322bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 4332bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber case MyHandler::kWhatDisconnected: 4347f475c34ffc8e35345f2cceee2ef56a50bb5fea6Andreas Huber { 4352bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber onDisconnected(msg); 4362bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber break; 4377f475c34ffc8e35345f2cceee2ef56a50bb5fea6Andreas Huber } 4382bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 4392bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber case MyHandler::kWhatSeekDone: 4402bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber { 4412bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber mState = CONNECTED; 4424ad74b2b4507c8b2714b7b7584578d2d43ae2633Wei Jia // Unblock seekTo here in case we attempted to seek in a live stream 4434ad74b2b4507c8b2714b7b7584578d2d43ae2633Wei Jia finishSeek(OK); 4448d237a5ce1e3c1dbc1d538f47e68cff2cc52d799Robert Shih break; 4458d237a5ce1e3c1dbc1d538f47e68cff2cc52d799Robert Shih } 4468d237a5ce1e3c1dbc1d538f47e68cff2cc52d799Robert Shih 4478d237a5ce1e3c1dbc1d538f47e68cff2cc52d799Robert Shih case MyHandler::kWhatSeekPaused: 4488d237a5ce1e3c1dbc1d538f47e68cff2cc52d799Robert Shih { 4498d237a5ce1e3c1dbc1d538f47e68cff2cc52d799Robert Shih sp<AnotherPacketSource> source = getSource(true /* audio */); 4508d237a5ce1e3c1dbc1d538f47e68cff2cc52d799Robert Shih if (source != NULL) { 4518d237a5ce1e3c1dbc1d538f47e68cff2cc52d799Robert Shih source->queueDiscontinuity(ATSParser::DISCONTINUITY_NONE, 4528d237a5ce1e3c1dbc1d538f47e68cff2cc52d799Robert Shih /* extra */ NULL, 4538d237a5ce1e3c1dbc1d538f47e68cff2cc52d799Robert Shih /* discard */ true); 4548d237a5ce1e3c1dbc1d538f47e68cff2cc52d799Robert Shih } 4558d237a5ce1e3c1dbc1d538f47e68cff2cc52d799Robert Shih source = getSource(false /* video */); 4568d237a5ce1e3c1dbc1d538f47e68cff2cc52d799Robert Shih if (source != NULL) { 4578d237a5ce1e3c1dbc1d538f47e68cff2cc52d799Robert Shih source->queueDiscontinuity(ATSParser::DISCONTINUITY_NONE, 4588d237a5ce1e3c1dbc1d538f47e68cff2cc52d799Robert Shih /* extra */ NULL, 4598d237a5ce1e3c1dbc1d538f47e68cff2cc52d799Robert Shih /* discard */ true); 4608d237a5ce1e3c1dbc1d538f47e68cff2cc52d799Robert Shih }; 4618d237a5ce1e3c1dbc1d538f47e68cff2cc52d799Robert Shih 4628d237a5ce1e3c1dbc1d538f47e68cff2cc52d799Robert Shih status_t err = OK; 4638d237a5ce1e3c1dbc1d538f47e68cff2cc52d799Robert Shih msg->findInt32("err", &err); 4648d237a5ce1e3c1dbc1d538f47e68cff2cc52d799Robert Shih 4658d237a5ce1e3c1dbc1d538f47e68cff2cc52d799Robert Shih if (err == OK) { 4668d237a5ce1e3c1dbc1d538f47e68cff2cc52d799Robert Shih int64_t timeUs; 4678d237a5ce1e3c1dbc1d538f47e68cff2cc52d799Robert Shih CHECK(msg->findInt64("time", &timeUs)); 4688d237a5ce1e3c1dbc1d538f47e68cff2cc52d799Robert Shih mHandler->continueSeekAfterPause(timeUs); 4694ad74b2b4507c8b2714b7b7584578d2d43ae2633Wei Jia } else { 4704ad74b2b4507c8b2714b7b7584578d2d43ae2633Wei Jia finishSeek(err); 4718d237a5ce1e3c1dbc1d538f47e68cff2cc52d799Robert Shih } 4722bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber break; 4732bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber } 4742bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 4752bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber case MyHandler::kWhatAccessUnit: 4762bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber { 4772bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber size_t trackIndex; 4782bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber CHECK(msg->findSize("trackIndex", &trackIndex)); 47949694688c82214f5fd9e969e177c9e126a240a26Andreas Huber 48049694688c82214f5fd9e969e177c9e126a240a26Andreas Huber if (mTSParser == NULL) { 48149694688c82214f5fd9e969e177c9e126a240a26Andreas Huber CHECK_LT(trackIndex, mTracks.size()); 48249694688c82214f5fd9e969e177c9e126a240a26Andreas Huber } else { 48349694688c82214f5fd9e969e177c9e126a240a26Andreas Huber CHECK_EQ(trackIndex, 0u); 48449694688c82214f5fd9e969e177c9e126a240a26Andreas Huber } 4852bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 4862d8bedd05437b6fccdbc6bf70f673ffd86744d59Andreas Huber sp<ABuffer> accessUnit; 4872d8bedd05437b6fccdbc6bf70f673ffd86744d59Andreas Huber CHECK(msg->findBuffer("accessUnit", &accessUnit)); 4882bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 4892bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber int32_t damaged; 4902bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber if (accessUnit->meta()->findInt32("damaged", &damaged) 4912bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber && damaged) { 492df64d15042bbd5e0e4933ac49bf3c177dd94752cSteve Block ALOGI("dropping damaged access unit."); 4932bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber break; 4942bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber } 4952bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 49649694688c82214f5fd9e969e177c9e126a240a26Andreas Huber if (mTSParser != NULL) { 49749694688c82214f5fd9e969e177c9e126a240a26Andreas Huber size_t offset = 0; 49849694688c82214f5fd9e969e177c9e126a240a26Andreas Huber status_t err = OK; 49949694688c82214f5fd9e969e177c9e126a240a26Andreas Huber while (offset + 188 <= accessUnit->size()) { 50049694688c82214f5fd9e969e177c9e126a240a26Andreas Huber err = mTSParser->feedTSPacket( 50149694688c82214f5fd9e969e177c9e126a240a26Andreas Huber accessUnit->data() + offset, 188); 50249694688c82214f5fd9e969e177c9e126a240a26Andreas Huber if (err != OK) { 50349694688c82214f5fd9e969e177c9e126a240a26Andreas Huber break; 50449694688c82214f5fd9e969e177c9e126a240a26Andreas Huber } 50549694688c82214f5fd9e969e177c9e126a240a26Andreas Huber 50649694688c82214f5fd9e969e177c9e126a240a26Andreas Huber offset += 188; 50749694688c82214f5fd9e969e177c9e126a240a26Andreas Huber } 50849694688c82214f5fd9e969e177c9e126a240a26Andreas Huber 50949694688c82214f5fd9e969e177c9e126a240a26Andreas Huber if (offset < accessUnit->size()) { 51049694688c82214f5fd9e969e177c9e126a240a26Andreas Huber err = ERROR_MALFORMED; 51149694688c82214f5fd9e969e177c9e126a240a26Andreas Huber } 51249694688c82214f5fd9e969e177c9e126a240a26Andreas Huber 51349694688c82214f5fd9e969e177c9e126a240a26Andreas Huber if (err != OK) { 51449694688c82214f5fd9e969e177c9e126a240a26Andreas Huber sp<AnotherPacketSource> source = getSource(false /* audio */); 51549694688c82214f5fd9e969e177c9e126a240a26Andreas Huber if (source != NULL) { 51649694688c82214f5fd9e969e177c9e126a240a26Andreas Huber source->signalEOS(err); 51749694688c82214f5fd9e969e177c9e126a240a26Andreas Huber } 51849694688c82214f5fd9e969e177c9e126a240a26Andreas Huber 51949694688c82214f5fd9e969e177c9e126a240a26Andreas Huber source = getSource(true /* audio */); 52049694688c82214f5fd9e969e177c9e126a240a26Andreas Huber if (source != NULL) { 52149694688c82214f5fd9e969e177c9e126a240a26Andreas Huber source->signalEOS(err); 52249694688c82214f5fd9e969e177c9e126a240a26Andreas Huber } 52349694688c82214f5fd9e969e177c9e126a240a26Andreas Huber } 52449694688c82214f5fd9e969e177c9e126a240a26Andreas Huber break; 52549694688c82214f5fd9e969e177c9e126a240a26Andreas Huber } 52649694688c82214f5fd9e969e177c9e126a240a26Andreas Huber 5271906e5c7492b9cbc88601365536a69e9a490c963Andreas Huber TrackInfo *info = &mTracks.editItemAt(trackIndex); 5281906e5c7492b9cbc88601365536a69e9a490c963Andreas Huber 5291906e5c7492b9cbc88601365536a69e9a490c963Andreas Huber sp<AnotherPacketSource> source = info->mSource; 5302bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber if (source != NULL) { 5312bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber uint32_t rtpTime; 5322bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber CHECK(accessUnit->meta()->findInt32("rtp-time", (int32_t *)&rtpTime)); 5332bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 5341906e5c7492b9cbc88601365536a69e9a490c963Andreas Huber if (!info->mNPTMappingValid) { 5351906e5c7492b9cbc88601365536a69e9a490c963Andreas Huber // This is a live stream, we didn't receive any normal 536c9d1696d214d2175327067ccc1991bcb36976404Andreas Huber // playtime mapping. We won't map to npt time. 537c9d1696d214d2175327067ccc1991bcb36976404Andreas Huber source->queueAccessUnit(accessUnit); 538c9d1696d214d2175327067ccc1991bcb36976404Andreas Huber break; 5391906e5c7492b9cbc88601365536a69e9a490c963Andreas Huber } 5401906e5c7492b9cbc88601365536a69e9a490c963Andreas Huber 5412bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber int64_t nptUs = 5421906e5c7492b9cbc88601365536a69e9a490c963Andreas Huber ((double)rtpTime - (double)info->mRTPTime) 5431906e5c7492b9cbc88601365536a69e9a490c963Andreas Huber / info->mTimeScale 5442bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber * 1000000ll 5451906e5c7492b9cbc88601365536a69e9a490c963Andreas Huber + info->mNormalPlaytimeUs; 5462bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 5472bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber accessUnit->meta()->setInt64("timeUs", nptUs); 5482bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 5492bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber source->queueAccessUnit(accessUnit); 5502bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber } 5512bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber break; 5522bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber } 5532bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 5542bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber case MyHandler::kWhatEOS: 5552bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber { 5562bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber int32_t finalResult; 5572bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber CHECK(msg->findInt32("finalResult", &finalResult)); 5582bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber CHECK_NE(finalResult, (status_t)OK); 5592bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 56049694688c82214f5fd9e969e177c9e126a240a26Andreas Huber if (mTSParser != NULL) { 56149694688c82214f5fd9e969e177c9e126a240a26Andreas Huber sp<AnotherPacketSource> source = getSource(false /* audio */); 56249694688c82214f5fd9e969e177c9e126a240a26Andreas Huber if (source != NULL) { 56349694688c82214f5fd9e969e177c9e126a240a26Andreas Huber source->signalEOS(finalResult); 56449694688c82214f5fd9e969e177c9e126a240a26Andreas Huber } 56549694688c82214f5fd9e969e177c9e126a240a26Andreas Huber 56649694688c82214f5fd9e969e177c9e126a240a26Andreas Huber source = getSource(true /* audio */); 56749694688c82214f5fd9e969e177c9e126a240a26Andreas Huber if (source != NULL) { 56849694688c82214f5fd9e969e177c9e126a240a26Andreas Huber source->signalEOS(finalResult); 56949694688c82214f5fd9e969e177c9e126a240a26Andreas Huber } 57049694688c82214f5fd9e969e177c9e126a240a26Andreas Huber 57149694688c82214f5fd9e969e177c9e126a240a26Andreas Huber return; 57249694688c82214f5fd9e969e177c9e126a240a26Andreas Huber } 57349694688c82214f5fd9e969e177c9e126a240a26Andreas Huber 57449694688c82214f5fd9e969e177c9e126a240a26Andreas Huber size_t trackIndex; 57549694688c82214f5fd9e969e177c9e126a240a26Andreas Huber CHECK(msg->findSize("trackIndex", &trackIndex)); 57649694688c82214f5fd9e969e177c9e126a240a26Andreas Huber CHECK_LT(trackIndex, mTracks.size()); 57749694688c82214f5fd9e969e177c9e126a240a26Andreas Huber 5782bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber TrackInfo *info = &mTracks.editItemAt(trackIndex); 5792bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber sp<AnotherPacketSource> source = info->mSource; 5802bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber if (source != NULL) { 5812bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber source->signalEOS(finalResult); 5822bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber } 5832bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 5842bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber break; 5852bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber } 5862bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 5872bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber case MyHandler::kWhatSeekDiscontinuity: 5882bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber { 5892bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber size_t trackIndex; 5902bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber CHECK(msg->findSize("trackIndex", &trackIndex)); 5912bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber CHECK_LT(trackIndex, mTracks.size()); 5922bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 5932bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber TrackInfo *info = &mTracks.editItemAt(trackIndex); 5942bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber sp<AnotherPacketSource> source = info->mSource; 5952bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber if (source != NULL) { 596632740c58119a132ce19f6d498e39c5c3773971aChong Zhang source->queueDiscontinuity( 597fef808d42a9c94b0b5ef3c3d5fb0a090edbc42daWei Jia ATSParser::DISCONTINUITY_TIME, 598632740c58119a132ce19f6d498e39c5c3773971aChong Zhang NULL, 599632740c58119a132ce19f6d498e39c5c3773971aChong Zhang true /* discard */); 6002bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber } 6012bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 6022bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber break; 6032bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber } 6042bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 6052bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber case MyHandler::kWhatNormalPlayTimeMapping: 6062bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber { 6072bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber size_t trackIndex; 6082bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber CHECK(msg->findSize("trackIndex", &trackIndex)); 6092bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber CHECK_LT(trackIndex, mTracks.size()); 6102bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 6112bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber uint32_t rtpTime; 6122bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber CHECK(msg->findInt32("rtpTime", (int32_t *)&rtpTime)); 6132bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 6142bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber int64_t nptUs; 6152bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber CHECK(msg->findInt64("nptUs", &nptUs)); 6162bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 6172bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber TrackInfo *info = &mTracks.editItemAt(trackIndex); 6182bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber info->mRTPTime = rtpTime; 6192bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber info->mNormalPlaytimeUs = nptUs; 6201906e5c7492b9cbc88601365536a69e9a490c963Andreas Huber info->mNPTMappingValid = true; 6212bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber break; 6222bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber } 6232bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 62481dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé case SDPLoader::kWhatSDPLoaded: 62581dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé { 62681dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé onSDPLoaded(msg); 62781dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé break; 62881dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé } 62981dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé 6302bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber default: 6312bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber TRESPASS(); 6322bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber } 6332bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber} 6342bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 6352bfdd428c56c7524d1a11979f200a1762866032dAndreas Hubervoid NuPlayer::RTSPSource::onConnected() { 6362bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber CHECK(mAudioTrack == NULL); 6372bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber CHECK(mVideoTrack == NULL); 6382bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 6392bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber size_t numTracks = mHandler->countTracks(); 6402bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber for (size_t i = 0; i < numTracks; ++i) { 6412bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber int32_t timeScale; 6422bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber sp<MetaData> format = mHandler->getTrackFormat(i, &timeScale); 6432bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 6442bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber const char *mime; 6452bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber CHECK(format->findCString(kKeyMIMEType, &mime)); 6462bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 64749694688c82214f5fd9e969e177c9e126a240a26Andreas Huber if (!strcasecmp(mime, MEDIA_MIMETYPE_CONTAINER_MPEG2TS)) { 64849694688c82214f5fd9e969e177c9e126a240a26Andreas Huber // Very special case for MPEG2 Transport Streams. 64949694688c82214f5fd9e969e177c9e126a240a26Andreas Huber CHECK_EQ(numTracks, 1u); 65049694688c82214f5fd9e969e177c9e126a240a26Andreas Huber 65149694688c82214f5fd9e969e177c9e126a240a26Andreas Huber mTSParser = new ATSParser; 65249694688c82214f5fd9e969e177c9e126a240a26Andreas Huber return; 65349694688c82214f5fd9e969e177c9e126a240a26Andreas Huber } 65449694688c82214f5fd9e969e177c9e126a240a26Andreas Huber 6552bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber bool isAudio = !strncasecmp(mime, "audio/", 6); 6562bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber bool isVideo = !strncasecmp(mime, "video/", 6); 6572bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 6582bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber TrackInfo info; 6592bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber info.mTimeScale = timeScale; 6602bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber info.mRTPTime = 0; 6612bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber info.mNormalPlaytimeUs = 0ll; 6621906e5c7492b9cbc88601365536a69e9a490c963Andreas Huber info.mNPTMappingValid = false; 6632bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 6642bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber if ((isAudio && mAudioTrack == NULL) 6652bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber || (isVideo && mVideoTrack == NULL)) { 6662bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber sp<AnotherPacketSource> source = new AnotherPacketSource(format); 6672bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 6682bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber if (isAudio) { 6692bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber mAudioTrack = source; 6702bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber } else { 6712bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber mVideoTrack = source; 6722bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber } 6732bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 6742bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber info.mSource = source; 6752bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber } 6762bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 6772bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber mTracks.push(info); 6782bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber } 6792bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 6802bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber mState = CONNECTED; 6812bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber} 6822bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 68381dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhévoid NuPlayer::RTSPSource::onSDPLoaded(const sp<AMessage> &msg) { 68481dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé status_t err; 68581dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé CHECK(msg->findInt32("result", &err)); 68681dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé 68781dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé mSDPLoader.clear(); 68881dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé 68981dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé if (mDisconnectReplyID != 0) { 69081dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé err = UNKNOWN_ERROR; 69181dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé } 69281dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé 69381dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé if (err == OK) { 69481dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé sp<ASessionDescription> desc; 69581dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé sp<RefBase> obj; 69681dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé CHECK(msg->findObject("description", &obj)); 69781dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé desc = static_cast<ASessionDescription *>(obj.get()); 69881dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé 69981dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé AString rtspUri; 70081dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé if (!desc->findAttribute(0, "a=control", &rtspUri)) { 70181dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé ALOGE("Unable to find url in SDP"); 70281dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé err = UNKNOWN_ERROR; 70381dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé } else { 7041d15ab58bf8239069ef343de6cb21aabf3ef7d78Lajos Molnar sp<AMessage> notify = new AMessage(kWhatNotify, this); 70581dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé 70681dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé mHandler = new MyHandler(rtspUri.c_str(), notify, mUIDValid, mUID); 70781dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé mLooper->registerHandler(mHandler); 70881dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé 70981dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé mHandler->loadSDP(desc); 71081dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé } 71181dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé } 71281dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé 71381dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé if (err != OK) { 7147f475c34ffc8e35345f2cceee2ef56a50bb5fea6Andreas Huber if (mState == CONNECTING) { 7157f475c34ffc8e35345f2cceee2ef56a50bb5fea6Andreas Huber // We're still in the preparation phase, signal that it 7167f475c34ffc8e35345f2cceee2ef56a50bb5fea6Andreas Huber // failed. 7177f475c34ffc8e35345f2cceee2ef56a50bb5fea6Andreas Huber notifyPrepared(err); 7187f475c34ffc8e35345f2cceee2ef56a50bb5fea6Andreas Huber } 7197f475c34ffc8e35345f2cceee2ef56a50bb5fea6Andreas Huber 72081dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé mState = DISCONNECTED; 721180d1b96ee2312f1056a58e26884a89d25ab62c8Chong Zhang setError(err); 72281dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé 72381dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé if (mDisconnectReplyID != 0) { 72481dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé finishDisconnectIfPossible(); 72581dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé } 72681dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé } 72781dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé} 72881dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé 7292bfdd428c56c7524d1a11979f200a1762866032dAndreas Hubervoid NuPlayer::RTSPSource::onDisconnected(const sp<AMessage> &msg) { 7300ad03bc59d090a0455f858d2f629834c105f6f37Fredrik Rosin if (mState == DISCONNECTED) { 7310ad03bc59d090a0455f858d2f629834c105f6f37Fredrik Rosin return; 7320ad03bc59d090a0455f858d2f629834c105f6f37Fredrik Rosin } 7330ad03bc59d090a0455f858d2f629834c105f6f37Fredrik Rosin 7342bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber status_t err; 7352bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber CHECK(msg->findInt32("result", &err)); 7362bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber CHECK_NE(err, (status_t)OK); 7372bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 7382bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber mLooper->unregisterHandler(mHandler->id()); 7392bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber mHandler.clear(); 7402bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 7417f475c34ffc8e35345f2cceee2ef56a50bb5fea6Andreas Huber if (mState == CONNECTING) { 7427f475c34ffc8e35345f2cceee2ef56a50bb5fea6Andreas Huber // We're still in the preparation phase, signal that it 7437f475c34ffc8e35345f2cceee2ef56a50bb5fea6Andreas Huber // failed. 7447f475c34ffc8e35345f2cceee2ef56a50bb5fea6Andreas Huber notifyPrepared(err); 7457f475c34ffc8e35345f2cceee2ef56a50bb5fea6Andreas Huber } 7467f475c34ffc8e35345f2cceee2ef56a50bb5fea6Andreas Huber 7472bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber mState = DISCONNECTED; 748180d1b96ee2312f1056a58e26884a89d25ab62c8Chong Zhang setError(err); 7492bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 7502bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber if (mDisconnectReplyID != 0) { 7512bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber finishDisconnectIfPossible(); 7522bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber } 7532bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber} 7542bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 7552bfdd428c56c7524d1a11979f200a1762866032dAndreas Hubervoid NuPlayer::RTSPSource::finishDisconnectIfPossible() { 7562bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber if (mState != DISCONNECTED) { 75781dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé if (mHandler != NULL) { 75881dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé mHandler->disconnect(); 75981dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé } else if (mSDPLoader != NULL) { 76081dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé mSDPLoader->cancel(); 76181dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé } 7622bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber return; 7632bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber } 7642bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 7652bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber (new AMessage)->postReply(mDisconnectReplyID); 7662bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber mDisconnectReplyID = 0; 7672bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber} 7682bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 769180d1b96ee2312f1056a58e26884a89d25ab62c8Chong Zhangvoid NuPlayer::RTSPSource::setError(status_t err) { 770180d1b96ee2312f1056a58e26884a89d25ab62c8Chong Zhang Mutex::Autolock _l(mBufferingLock); 771180d1b96ee2312f1056a58e26884a89d25ab62c8Chong Zhang mFinalResult = err; 772180d1b96ee2312f1056a58e26884a89d25ab62c8Chong Zhang} 773180d1b96ee2312f1056a58e26884a89d25ab62c8Chong Zhang 774180d1b96ee2312f1056a58e26884a89d25ab62c8Chong Zhangvoid NuPlayer::RTSPSource::startBufferingIfNecessary() { 775180d1b96ee2312f1056a58e26884a89d25ab62c8Chong Zhang Mutex::Autolock _l(mBufferingLock); 776180d1b96ee2312f1056a58e26884a89d25ab62c8Chong Zhang 777180d1b96ee2312f1056a58e26884a89d25ab62c8Chong Zhang if (!mBuffering) { 778180d1b96ee2312f1056a58e26884a89d25ab62c8Chong Zhang mBuffering = true; 779180d1b96ee2312f1056a58e26884a89d25ab62c8Chong Zhang 780180d1b96ee2312f1056a58e26884a89d25ab62c8Chong Zhang sp<AMessage> notify = dupNotify(); 781c9ff2009a0a010eeaba80d76493fbf33fcb561c8Wei Jia notify->setInt32("what", kWhatPauseOnBufferingStart); 782180d1b96ee2312f1056a58e26884a89d25ab62c8Chong Zhang notify->post(); 783180d1b96ee2312f1056a58e26884a89d25ab62c8Chong Zhang } 784180d1b96ee2312f1056a58e26884a89d25ab62c8Chong Zhang} 785180d1b96ee2312f1056a58e26884a89d25ab62c8Chong Zhang 786180d1b96ee2312f1056a58e26884a89d25ab62c8Chong Zhangbool NuPlayer::RTSPSource::stopBufferingIfNecessary() { 787180d1b96ee2312f1056a58e26884a89d25ab62c8Chong Zhang Mutex::Autolock _l(mBufferingLock); 788180d1b96ee2312f1056a58e26884a89d25ab62c8Chong Zhang 789180d1b96ee2312f1056a58e26884a89d25ab62c8Chong Zhang if (mBuffering) { 790180d1b96ee2312f1056a58e26884a89d25ab62c8Chong Zhang if (!haveSufficientDataOnAllTracks()) { 791180d1b96ee2312f1056a58e26884a89d25ab62c8Chong Zhang return false; 792180d1b96ee2312f1056a58e26884a89d25ab62c8Chong Zhang } 793180d1b96ee2312f1056a58e26884a89d25ab62c8Chong Zhang 794180d1b96ee2312f1056a58e26884a89d25ab62c8Chong Zhang mBuffering = false; 795180d1b96ee2312f1056a58e26884a89d25ab62c8Chong Zhang 796180d1b96ee2312f1056a58e26884a89d25ab62c8Chong Zhang sp<AMessage> notify = dupNotify(); 797c9ff2009a0a010eeaba80d76493fbf33fcb561c8Wei Jia notify->setInt32("what", kWhatResumeOnBufferingEnd); 798180d1b96ee2312f1056a58e26884a89d25ab62c8Chong Zhang notify->post(); 799180d1b96ee2312f1056a58e26884a89d25ab62c8Chong Zhang } 800180d1b96ee2312f1056a58e26884a89d25ab62c8Chong Zhang 801180d1b96ee2312f1056a58e26884a89d25ab62c8Chong Zhang return true; 802180d1b96ee2312f1056a58e26884a89d25ab62c8Chong Zhang} 803180d1b96ee2312f1056a58e26884a89d25ab62c8Chong Zhang 8048d237a5ce1e3c1dbc1d538f47e68cff2cc52d799Robert Shihvoid NuPlayer::RTSPSource::finishSeek(status_t err) { 8054ad74b2b4507c8b2714b7b7584578d2d43ae2633Wei Jia if (mSeekReplyID == NULL) { 8064ad74b2b4507c8b2714b7b7584578d2d43ae2633Wei Jia return; 8074ad74b2b4507c8b2714b7b7584578d2d43ae2633Wei Jia } 8088d237a5ce1e3c1dbc1d538f47e68cff2cc52d799Robert Shih sp<AMessage> seekReply = new AMessage; 8098d237a5ce1e3c1dbc1d538f47e68cff2cc52d799Robert Shih seekReply->setInt32("err", err); 8108d237a5ce1e3c1dbc1d538f47e68cff2cc52d799Robert Shih seekReply->postReply(mSeekReplyID); 8118d237a5ce1e3c1dbc1d538f47e68cff2cc52d799Robert Shih mSeekReplyID = NULL; 8128d237a5ce1e3c1dbc1d538f47e68cff2cc52d799Robert Shih} 813180d1b96ee2312f1056a58e26884a89d25ab62c8Chong Zhang 8142bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber} // namespace android 815