RTSPSource.cpp revision 4b7069dac546ad21cf62ca6132d50ea41857d08e
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 2749694688c82214f5fd9e969e177c9e126a240a26Andreas Huber#include <media/stagefright/MediaDefs.h> 282bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber#include <media/stagefright/MetaData.h> 292bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 302bfdd428c56c7524d1a11979f200a1762866032dAndreas Hubernamespace android { 312bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 32cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönssonconst int64_t kNearEOSTimeoutUs = 2000000ll; // 2 secs 33cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson 342bfdd428c56c7524d1a11979f200a1762866032dAndreas HuberNuPlayer::RTSPSource::RTSPSource( 355ab368af38fefacc4009e3ab1c1bbd00e62b3bcfAndreas Huber const sp<AMessage> ¬ify, 362bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber const char *url, 372bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber const KeyedVector<String8, String8> *headers, 382bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber bool uidValid, 3981dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé uid_t uid, 4081dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé bool isSDP) 415ab368af38fefacc4009e3ab1c1bbd00e62b3bcfAndreas Huber : Source(notify), 425ab368af38fefacc4009e3ab1c1bbd00e62b3bcfAndreas Huber mURL(url), 432bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber mUIDValid(uidValid), 442bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber mUID(uid), 452bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber mFlags(0), 4681dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé mIsSDP(isSDP), 472bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber mState(DISCONNECTED), 482bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber mFinalResult(OK), 49ee736e9e74c5368db8d63214513c85cb74bb0183Andreas Huber mDisconnectReplyID(0), 50cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson mBuffering(true), 51cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson mSeekGeneration(0), 52cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson mEOSTimeoutAudio(0), 53cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson mEOSTimeoutVideo(0) { 542bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber if (headers) { 552bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber mExtraHeaders = *headers; 562bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 572bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber ssize_t index = 582bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber mExtraHeaders.indexOfKey(String8("x-hide-urls-from-log")); 592bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 602bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber if (index >= 0) { 612bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber mFlags |= kFlagIncognito; 622bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 632bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber mExtraHeaders.removeItemsAt(index); 642bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber } 652bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber } 662bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber} 672bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 682bfdd428c56c7524d1a11979f200a1762866032dAndreas HuberNuPlayer::RTSPSource::~RTSPSource() { 69602f5bbd7596ec3fe447fde4329d5d4f0b370835Andreas Huber if (mLooper != NULL) { 70602f5bbd7596ec3fe447fde4329d5d4f0b370835Andreas Huber mLooper->stop(); 71602f5bbd7596ec3fe447fde4329d5d4f0b370835Andreas Huber } 722bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber} 732bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 7457cea553cb19235553463412db5ad04c99835411Andreas Hubervoid NuPlayer::RTSPSource::prepareAsync() { 752bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber if (mLooper == NULL) { 762bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber mLooper = new ALooper; 772bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber mLooper->setName("rtsp"); 782bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber mLooper->start(); 792bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 802bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber mReflector = new AHandlerReflector<RTSPSource>(this); 812bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber mLooper->registerHandler(mReflector); 822bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber } 832bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 842bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber CHECK(mHandler == NULL); 8581dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé CHECK(mSDPLoader == NULL); 862bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 872bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber sp<AMessage> notify = new AMessage(kWhatNotify, mReflector->id()); 882bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 892bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber CHECK_EQ(mState, (int)DISCONNECTED); 902bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber mState = CONNECTING; 912bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 9281dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé if (mIsSDP) { 9381dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé mSDPLoader = new SDPLoader(notify, 9481dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé (mFlags & kFlagIncognito) ? SDPLoader::kFlagIncognito : 0, 9581dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé mUIDValid, mUID); 9681dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé 9757cea553cb19235553463412db5ad04c99835411Andreas Huber mSDPLoader->load( 9857cea553cb19235553463412db5ad04c99835411Andreas Huber mURL.c_str(), mExtraHeaders.isEmpty() ? NULL : &mExtraHeaders); 9981dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé } else { 10081dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé mHandler = new MyHandler(mURL.c_str(), notify, mUIDValid, mUID); 10181dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé mLooper->registerHandler(mHandler); 10281dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé 10381dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé mHandler->connect(); 10481dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé } 105cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson 106cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson sp<AMessage> notifyStart = dupNotify(); 107cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson notifyStart->setInt32("what", kWhatBufferingStart); 108cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson notifyStart->post(); 10957cea553cb19235553463412db5ad04c99835411Andreas Huber} 11057cea553cb19235553463412db5ad04c99835411Andreas Huber 11157cea553cb19235553463412db5ad04c99835411Andreas Hubervoid NuPlayer::RTSPSource::start() { 1122bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber} 1132bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 1142bfdd428c56c7524d1a11979f200a1762866032dAndreas Hubervoid NuPlayer::RTSPSource::stop() { 1155834181d3f168acb8ff4bf3eff1fd1186afb0bd4James Dong if (mLooper == NULL) { 1165834181d3f168acb8ff4bf3eff1fd1186afb0bd4James Dong return; 1175834181d3f168acb8ff4bf3eff1fd1186afb0bd4James Dong } 1182bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber sp<AMessage> msg = new AMessage(kWhatDisconnect, mReflector->id()); 1192bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 1202bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber sp<AMessage> dummy; 1212bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber msg->postAndAwaitResponse(&dummy); 1222bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber} 1232bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 12446d13e3606b87d71379287672b54b50d0d9aa5ccRoger Jönssonvoid NuPlayer::RTSPSource::pause() { 12546d13e3606b87d71379287672b54b50d0d9aa5ccRoger Jönsson int64_t mediaDurationUs = 0; 12646d13e3606b87d71379287672b54b50d0d9aa5ccRoger Jönsson getDuration(&mediaDurationUs); 12746d13e3606b87d71379287672b54b50d0d9aa5ccRoger Jönsson for (size_t index = 0; index < mTracks.size(); index++) { 12846d13e3606b87d71379287672b54b50d0d9aa5ccRoger Jönsson TrackInfo *info = &mTracks.editItemAt(index); 12946d13e3606b87d71379287672b54b50d0d9aa5ccRoger Jönsson sp<AnotherPacketSource> source = info->mSource; 13046d13e3606b87d71379287672b54b50d0d9aa5ccRoger Jönsson 13146d13e3606b87d71379287672b54b50d0d9aa5ccRoger Jönsson // Check if EOS or ERROR is received 13246d13e3606b87d71379287672b54b50d0d9aa5ccRoger Jönsson if (source != NULL && source->isFinished(mediaDurationUs)) { 13346d13e3606b87d71379287672b54b50d0d9aa5ccRoger Jönsson return; 13446d13e3606b87d71379287672b54b50d0d9aa5ccRoger Jönsson } 13546d13e3606b87d71379287672b54b50d0d9aa5ccRoger Jönsson } 13646d13e3606b87d71379287672b54b50d0d9aa5ccRoger Jönsson mHandler->pause(); 13746d13e3606b87d71379287672b54b50d0d9aa5ccRoger Jönsson} 13846d13e3606b87d71379287672b54b50d0d9aa5ccRoger Jönsson 13946d13e3606b87d71379287672b54b50d0d9aa5ccRoger Jönssonvoid NuPlayer::RTSPSource::resume() { 14046d13e3606b87d71379287672b54b50d0d9aa5ccRoger Jönsson mHandler->resume(); 14146d13e3606b87d71379287672b54b50d0d9aa5ccRoger Jönsson} 14246d13e3606b87d71379287672b54b50d0d9aa5ccRoger Jönsson 1432bfdd428c56c7524d1a11979f200a1762866032dAndreas Huberstatus_t NuPlayer::RTSPSource::feedMoreTSData() { 1442bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber return mFinalResult; 1452bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber} 1462bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 147840667883fd09d44015716d79bc3ac4d60edc0f0Andreas Hubersp<MetaData> NuPlayer::RTSPSource::getFormatMeta(bool audio) { 1482bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber sp<AnotherPacketSource> source = getSource(audio); 1492bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 1502bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber if (source == NULL) { 1512bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber return NULL; 1522bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber } 1532bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 1542bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber return source->getFormat(); 1552bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber} 1562bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 157bfd4d0d9fe0033abf3f55b94f30f6a58846a875eAndreas Huberbool NuPlayer::RTSPSource::haveSufficientDataOnAllTracks() { 158bfd4d0d9fe0033abf3f55b94f30f6a58846a875eAndreas Huber // We're going to buffer at least 2 secs worth data on all tracks before 159bfd4d0d9fe0033abf3f55b94f30f6a58846a875eAndreas Huber // starting playback (both at startup and after a seek). 160bfd4d0d9fe0033abf3f55b94f30f6a58846a875eAndreas Huber 161bfd4d0d9fe0033abf3f55b94f30f6a58846a875eAndreas Huber static const int64_t kMinDurationUs = 2000000ll; 162bfd4d0d9fe0033abf3f55b94f30f6a58846a875eAndreas Huber 163cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson int64_t mediaDurationUs = 0; 164cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson getDuration(&mediaDurationUs); 165cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson if ((mAudioTrack != NULL && mAudioTrack->isFinished(mediaDurationUs)) 166cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson || (mVideoTrack != NULL && mVideoTrack->isFinished(mediaDurationUs))) { 167cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson return true; 168cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson } 169cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson 170bfd4d0d9fe0033abf3f55b94f30f6a58846a875eAndreas Huber status_t err; 171bfd4d0d9fe0033abf3f55b94f30f6a58846a875eAndreas Huber int64_t durationUs; 172bfd4d0d9fe0033abf3f55b94f30f6a58846a875eAndreas Huber if (mAudioTrack != NULL 173bfd4d0d9fe0033abf3f55b94f30f6a58846a875eAndreas Huber && (durationUs = mAudioTrack->getBufferedDurationUs(&err)) 174bfd4d0d9fe0033abf3f55b94f30f6a58846a875eAndreas Huber < kMinDurationUs 175bfd4d0d9fe0033abf3f55b94f30f6a58846a875eAndreas Huber && err == OK) { 176bfd4d0d9fe0033abf3f55b94f30f6a58846a875eAndreas Huber ALOGV("audio track doesn't have enough data yet. (%.2f secs buffered)", 177bfd4d0d9fe0033abf3f55b94f30f6a58846a875eAndreas Huber durationUs / 1E6); 178bfd4d0d9fe0033abf3f55b94f30f6a58846a875eAndreas Huber return false; 179bfd4d0d9fe0033abf3f55b94f30f6a58846a875eAndreas Huber } 180bfd4d0d9fe0033abf3f55b94f30f6a58846a875eAndreas Huber 181bfd4d0d9fe0033abf3f55b94f30f6a58846a875eAndreas Huber if (mVideoTrack != NULL 182bfd4d0d9fe0033abf3f55b94f30f6a58846a875eAndreas Huber && (durationUs = mVideoTrack->getBufferedDurationUs(&err)) 183bfd4d0d9fe0033abf3f55b94f30f6a58846a875eAndreas Huber < kMinDurationUs 184bfd4d0d9fe0033abf3f55b94f30f6a58846a875eAndreas Huber && err == OK) { 185bfd4d0d9fe0033abf3f55b94f30f6a58846a875eAndreas Huber ALOGV("video track doesn't have enough data yet. (%.2f secs buffered)", 186bfd4d0d9fe0033abf3f55b94f30f6a58846a875eAndreas Huber durationUs / 1E6); 187bfd4d0d9fe0033abf3f55b94f30f6a58846a875eAndreas Huber return false; 188bfd4d0d9fe0033abf3f55b94f30f6a58846a875eAndreas Huber } 189bfd4d0d9fe0033abf3f55b94f30f6a58846a875eAndreas Huber 190bfd4d0d9fe0033abf3f55b94f30f6a58846a875eAndreas Huber return true; 191bfd4d0d9fe0033abf3f55b94f30f6a58846a875eAndreas Huber} 192bfd4d0d9fe0033abf3f55b94f30f6a58846a875eAndreas Huber 1932bfdd428c56c7524d1a11979f200a1762866032dAndreas Huberstatus_t NuPlayer::RTSPSource::dequeueAccessUnit( 1942bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber bool audio, sp<ABuffer> *accessUnit) { 195cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson if (mBuffering) { 196bfd4d0d9fe0033abf3f55b94f30f6a58846a875eAndreas Huber if (!haveSufficientDataOnAllTracks()) { 197bfd4d0d9fe0033abf3f55b94f30f6a58846a875eAndreas Huber return -EWOULDBLOCK; 198bfd4d0d9fe0033abf3f55b94f30f6a58846a875eAndreas Huber } 199bfd4d0d9fe0033abf3f55b94f30f6a58846a875eAndreas Huber 200cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson mBuffering = false; 201cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson 202cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson sp<AMessage> notify = dupNotify(); 203cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson notify->setInt32("what", kWhatBufferingEnd); 204cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson notify->post(); 205bfd4d0d9fe0033abf3f55b94f30f6a58846a875eAndreas Huber } 206bfd4d0d9fe0033abf3f55b94f30f6a58846a875eAndreas Huber 2072bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber sp<AnotherPacketSource> source = getSource(audio); 2082bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 2092bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber if (source == NULL) { 2102bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber return -EWOULDBLOCK; 2112bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber } 2122bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 2132bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber status_t finalResult; 2142bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber if (!source->hasBufferAvailable(&finalResult)) { 215cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson if (finalResult == OK) { 216cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson int64_t mediaDurationUs = 0; 217cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson getDuration(&mediaDurationUs); 218cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson sp<AnotherPacketSource> otherSource = getSource(!audio); 219cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson status_t otherFinalResult; 220cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson 221cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson // If other source already signaled EOS, this source should also signal EOS 222cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson if (otherSource != NULL && 223cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson !otherSource->hasBufferAvailable(&otherFinalResult) && 224cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson otherFinalResult == ERROR_END_OF_STREAM) { 225cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson source->signalEOS(ERROR_END_OF_STREAM); 226cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson return ERROR_END_OF_STREAM; 227cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson } 228cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson 229cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson // If this source has detected near end, give it some time to retrieve more 230cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson // data before signaling EOS 231cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson if (source->isFinished(mediaDurationUs)) { 232cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson int64_t eosTimeout = audio ? mEOSTimeoutAudio : mEOSTimeoutVideo; 233cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson if (eosTimeout == 0) { 234cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson setEOSTimeout(audio, ALooper::GetNowUs()); 235cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson } else if ((ALooper::GetNowUs() - eosTimeout) > kNearEOSTimeoutUs) { 236cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson setEOSTimeout(audio, 0); 237cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson source->signalEOS(ERROR_END_OF_STREAM); 238cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson return ERROR_END_OF_STREAM; 239cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson } 240cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson return -EWOULDBLOCK; 241cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson } 242cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson 243cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson if (!(otherSource != NULL && otherSource->isFinished(mediaDurationUs))) { 244cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson // We should not enter buffering mode 245cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson // if any of the sources already have detected EOS. 246cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson mBuffering = true; 247cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson 248cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson sp<AMessage> notify = dupNotify(); 249cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson notify->setInt32("what", kWhatBufferingStart); 250cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson notify->post(); 251cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson } 252cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson 253cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson return -EWOULDBLOCK; 254cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson } 255cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson return finalResult; 2562bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber } 2572bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 258cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson setEOSTimeout(audio, 0); 259cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson 2602bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber return source->dequeueAccessUnit(accessUnit); 2612bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber} 2622bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 2632bfdd428c56c7524d1a11979f200a1762866032dAndreas Hubersp<AnotherPacketSource> NuPlayer::RTSPSource::getSource(bool audio) { 26449694688c82214f5fd9e969e177c9e126a240a26Andreas Huber if (mTSParser != NULL) { 26549694688c82214f5fd9e969e177c9e126a240a26Andreas Huber sp<MediaSource> source = mTSParser->getSource( 26649694688c82214f5fd9e969e177c9e126a240a26Andreas Huber audio ? ATSParser::AUDIO : ATSParser::VIDEO); 26749694688c82214f5fd9e969e177c9e126a240a26Andreas Huber 26849694688c82214f5fd9e969e177c9e126a240a26Andreas Huber return static_cast<AnotherPacketSource *>(source.get()); 26949694688c82214f5fd9e969e177c9e126a240a26Andreas Huber } 27049694688c82214f5fd9e969e177c9e126a240a26Andreas Huber 2712bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber return audio ? mAudioTrack : mVideoTrack; 2722bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber} 2732bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 274cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönssonvoid NuPlayer::RTSPSource::setEOSTimeout(bool audio, int64_t timeout) { 275cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson if (audio) { 276cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson mEOSTimeoutAudio = timeout; 277cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson } else { 278cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson mEOSTimeoutVideo = timeout; 279cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson } 280cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson} 281cfc3083927df14bf82403b20a45ae303a01c39f5Roger Jönsson 2822bfdd428c56c7524d1a11979f200a1762866032dAndreas Huberstatus_t NuPlayer::RTSPSource::getDuration(int64_t *durationUs) { 2832bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber *durationUs = 0ll; 2842bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 2852bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber int64_t audioDurationUs; 2862bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber if (mAudioTrack != NULL 2872bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber && mAudioTrack->getFormat()->findInt64( 2882bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber kKeyDuration, &audioDurationUs) 2892bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber && audioDurationUs > *durationUs) { 2902bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber *durationUs = audioDurationUs; 2912bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber } 2922bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 2932bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber int64_t videoDurationUs; 2942bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber if (mVideoTrack != NULL 2952bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber && mVideoTrack->getFormat()->findInt64( 2962bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber kKeyDuration, &videoDurationUs) 2972bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber && videoDurationUs > *durationUs) { 2982bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber *durationUs = videoDurationUs; 2992bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber } 3002bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 3012bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber return OK; 3022bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber} 3032bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 3042bfdd428c56c7524d1a11979f200a1762866032dAndreas Huberstatus_t NuPlayer::RTSPSource::seekTo(int64_t seekTimeUs) { 305ee736e9e74c5368db8d63214513c85cb74bb0183Andreas Huber sp<AMessage> msg = new AMessage(kWhatPerformSeek, mReflector->id()); 306ee736e9e74c5368db8d63214513c85cb74bb0183Andreas Huber msg->setInt32("generation", ++mSeekGeneration); 307ee736e9e74c5368db8d63214513c85cb74bb0183Andreas Huber msg->setInt64("timeUs", seekTimeUs); 308ee736e9e74c5368db8d63214513c85cb74bb0183Andreas Huber msg->post(200000ll); 309ee736e9e74c5368db8d63214513c85cb74bb0183Andreas Huber 310ee736e9e74c5368db8d63214513c85cb74bb0183Andreas Huber return OK; 311ee736e9e74c5368db8d63214513c85cb74bb0183Andreas Huber} 312ee736e9e74c5368db8d63214513c85cb74bb0183Andreas Huber 313ee736e9e74c5368db8d63214513c85cb74bb0183Andreas Hubervoid NuPlayer::RTSPSource::performSeek(int64_t seekTimeUs) { 3142bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber if (mState != CONNECTED) { 315ee736e9e74c5368db8d63214513c85cb74bb0183Andreas Huber return; 3162bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber } 3172bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 3182bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber mState = SEEKING; 3192bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber mHandler->seek(seekTimeUs); 3202bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber} 3212bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 3222bfdd428c56c7524d1a11979f200a1762866032dAndreas Hubervoid NuPlayer::RTSPSource::onMessageReceived(const sp<AMessage> &msg) { 3232bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber if (msg->what() == kWhatDisconnect) { 3242bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber uint32_t replyID; 3252bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber CHECK(msg->senderAwaitsResponse(&replyID)); 3262bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 3272bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber mDisconnectReplyID = replyID; 3282bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber finishDisconnectIfPossible(); 3292bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber return; 330ee736e9e74c5368db8d63214513c85cb74bb0183Andreas Huber } else if (msg->what() == kWhatPerformSeek) { 331ee736e9e74c5368db8d63214513c85cb74bb0183Andreas Huber int32_t generation; 332ee736e9e74c5368db8d63214513c85cb74bb0183Andreas Huber CHECK(msg->findInt32("generation", &generation)); 333ee736e9e74c5368db8d63214513c85cb74bb0183Andreas Huber 334ee736e9e74c5368db8d63214513c85cb74bb0183Andreas Huber if (generation != mSeekGeneration) { 335ee736e9e74c5368db8d63214513c85cb74bb0183Andreas Huber // obsolete. 336ee736e9e74c5368db8d63214513c85cb74bb0183Andreas Huber return; 337ee736e9e74c5368db8d63214513c85cb74bb0183Andreas Huber } 338ee736e9e74c5368db8d63214513c85cb74bb0183Andreas Huber 339ee736e9e74c5368db8d63214513c85cb74bb0183Andreas Huber int64_t seekTimeUs; 340ee736e9e74c5368db8d63214513c85cb74bb0183Andreas Huber CHECK(msg->findInt64("timeUs", &seekTimeUs)); 341ee736e9e74c5368db8d63214513c85cb74bb0183Andreas Huber 342ee736e9e74c5368db8d63214513c85cb74bb0183Andreas Huber performSeek(seekTimeUs); 343ee736e9e74c5368db8d63214513c85cb74bb0183Andreas Huber return; 3442bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber } 3452bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 3462bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber CHECK_EQ(msg->what(), (int)kWhatNotify); 3472bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 3482bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber int32_t what; 3492bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber CHECK(msg->findInt32("what", &what)); 3502bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 3512bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber switch (what) { 3522bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber case MyHandler::kWhatConnected: 3537f475c34ffc8e35345f2cceee2ef56a50bb5fea6Andreas Huber { 3542bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber onConnected(); 3557f475c34ffc8e35345f2cceee2ef56a50bb5fea6Andreas Huber 3567f475c34ffc8e35345f2cceee2ef56a50bb5fea6Andreas Huber notifyVideoSizeChanged(0, 0); 3577f475c34ffc8e35345f2cceee2ef56a50bb5fea6Andreas Huber 3587f475c34ffc8e35345f2cceee2ef56a50bb5fea6Andreas Huber uint32_t flags = 0; 3597f475c34ffc8e35345f2cceee2ef56a50bb5fea6Andreas Huber 3607f475c34ffc8e35345f2cceee2ef56a50bb5fea6Andreas Huber if (mHandler->isSeekable()) { 3614b7069dac546ad21cf62ca6132d50ea41857d08eChong Zhang flags = FLAG_CAN_PAUSE 3624b7069dac546ad21cf62ca6132d50ea41857d08eChong Zhang | FLAG_CAN_SEEK 3634b7069dac546ad21cf62ca6132d50ea41857d08eChong Zhang | FLAG_CAN_SEEK_BACKWARD 3644b7069dac546ad21cf62ca6132d50ea41857d08eChong Zhang | FLAG_CAN_SEEK_FORWARD; 3657f475c34ffc8e35345f2cceee2ef56a50bb5fea6Andreas Huber } 3667f475c34ffc8e35345f2cceee2ef56a50bb5fea6Andreas Huber 3677f475c34ffc8e35345f2cceee2ef56a50bb5fea6Andreas Huber notifyFlagsChanged(flags); 3687f475c34ffc8e35345f2cceee2ef56a50bb5fea6Andreas Huber notifyPrepared(); 3692bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber break; 3707f475c34ffc8e35345f2cceee2ef56a50bb5fea6Andreas Huber } 3712bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 3722bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber case MyHandler::kWhatDisconnected: 3737f475c34ffc8e35345f2cceee2ef56a50bb5fea6Andreas Huber { 3742bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber onDisconnected(msg); 3752bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber break; 3767f475c34ffc8e35345f2cceee2ef56a50bb5fea6Andreas Huber } 3772bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 3782bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber case MyHandler::kWhatSeekDone: 3792bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber { 3802bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber mState = CONNECTED; 3812bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber break; 3822bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber } 3832bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 3842bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber case MyHandler::kWhatAccessUnit: 3852bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber { 3862bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber size_t trackIndex; 3872bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber CHECK(msg->findSize("trackIndex", &trackIndex)); 38849694688c82214f5fd9e969e177c9e126a240a26Andreas Huber 38949694688c82214f5fd9e969e177c9e126a240a26Andreas Huber if (mTSParser == NULL) { 39049694688c82214f5fd9e969e177c9e126a240a26Andreas Huber CHECK_LT(trackIndex, mTracks.size()); 39149694688c82214f5fd9e969e177c9e126a240a26Andreas Huber } else { 39249694688c82214f5fd9e969e177c9e126a240a26Andreas Huber CHECK_EQ(trackIndex, 0u); 39349694688c82214f5fd9e969e177c9e126a240a26Andreas Huber } 3942bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 3952d8bedd05437b6fccdbc6bf70f673ffd86744d59Andreas Huber sp<ABuffer> accessUnit; 3962d8bedd05437b6fccdbc6bf70f673ffd86744d59Andreas Huber CHECK(msg->findBuffer("accessUnit", &accessUnit)); 3972bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 3982bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber int32_t damaged; 3992bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber if (accessUnit->meta()->findInt32("damaged", &damaged) 4002bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber && damaged) { 401df64d15042bbd5e0e4933ac49bf3c177dd94752cSteve Block ALOGI("dropping damaged access unit."); 4022bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber break; 4032bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber } 4042bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 40549694688c82214f5fd9e969e177c9e126a240a26Andreas Huber if (mTSParser != NULL) { 40649694688c82214f5fd9e969e177c9e126a240a26Andreas Huber size_t offset = 0; 40749694688c82214f5fd9e969e177c9e126a240a26Andreas Huber status_t err = OK; 40849694688c82214f5fd9e969e177c9e126a240a26Andreas Huber while (offset + 188 <= accessUnit->size()) { 40949694688c82214f5fd9e969e177c9e126a240a26Andreas Huber err = mTSParser->feedTSPacket( 41049694688c82214f5fd9e969e177c9e126a240a26Andreas Huber accessUnit->data() + offset, 188); 41149694688c82214f5fd9e969e177c9e126a240a26Andreas Huber if (err != OK) { 41249694688c82214f5fd9e969e177c9e126a240a26Andreas Huber break; 41349694688c82214f5fd9e969e177c9e126a240a26Andreas Huber } 41449694688c82214f5fd9e969e177c9e126a240a26Andreas Huber 41549694688c82214f5fd9e969e177c9e126a240a26Andreas Huber offset += 188; 41649694688c82214f5fd9e969e177c9e126a240a26Andreas Huber } 41749694688c82214f5fd9e969e177c9e126a240a26Andreas Huber 41849694688c82214f5fd9e969e177c9e126a240a26Andreas Huber if (offset < accessUnit->size()) { 41949694688c82214f5fd9e969e177c9e126a240a26Andreas Huber err = ERROR_MALFORMED; 42049694688c82214f5fd9e969e177c9e126a240a26Andreas Huber } 42149694688c82214f5fd9e969e177c9e126a240a26Andreas Huber 42249694688c82214f5fd9e969e177c9e126a240a26Andreas Huber if (err != OK) { 42349694688c82214f5fd9e969e177c9e126a240a26Andreas Huber sp<AnotherPacketSource> source = getSource(false /* audio */); 42449694688c82214f5fd9e969e177c9e126a240a26Andreas Huber if (source != NULL) { 42549694688c82214f5fd9e969e177c9e126a240a26Andreas Huber source->signalEOS(err); 42649694688c82214f5fd9e969e177c9e126a240a26Andreas Huber } 42749694688c82214f5fd9e969e177c9e126a240a26Andreas Huber 42849694688c82214f5fd9e969e177c9e126a240a26Andreas Huber source = getSource(true /* audio */); 42949694688c82214f5fd9e969e177c9e126a240a26Andreas Huber if (source != NULL) { 43049694688c82214f5fd9e969e177c9e126a240a26Andreas Huber source->signalEOS(err); 43149694688c82214f5fd9e969e177c9e126a240a26Andreas Huber } 43249694688c82214f5fd9e969e177c9e126a240a26Andreas Huber } 43349694688c82214f5fd9e969e177c9e126a240a26Andreas Huber break; 43449694688c82214f5fd9e969e177c9e126a240a26Andreas Huber } 43549694688c82214f5fd9e969e177c9e126a240a26Andreas Huber 4361906e5c7492b9cbc88601365536a69e9a490c963Andreas Huber TrackInfo *info = &mTracks.editItemAt(trackIndex); 4371906e5c7492b9cbc88601365536a69e9a490c963Andreas Huber 4381906e5c7492b9cbc88601365536a69e9a490c963Andreas Huber sp<AnotherPacketSource> source = info->mSource; 4392bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber if (source != NULL) { 4402bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber uint32_t rtpTime; 4412bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber CHECK(accessUnit->meta()->findInt32("rtp-time", (int32_t *)&rtpTime)); 4422bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 4431906e5c7492b9cbc88601365536a69e9a490c963Andreas Huber if (!info->mNPTMappingValid) { 4441906e5c7492b9cbc88601365536a69e9a490c963Andreas Huber // This is a live stream, we didn't receive any normal 445c9d1696d214d2175327067ccc1991bcb36976404Andreas Huber // playtime mapping. We won't map to npt time. 446c9d1696d214d2175327067ccc1991bcb36976404Andreas Huber source->queueAccessUnit(accessUnit); 447c9d1696d214d2175327067ccc1991bcb36976404Andreas Huber break; 4481906e5c7492b9cbc88601365536a69e9a490c963Andreas Huber } 4491906e5c7492b9cbc88601365536a69e9a490c963Andreas Huber 4502bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber int64_t nptUs = 4511906e5c7492b9cbc88601365536a69e9a490c963Andreas Huber ((double)rtpTime - (double)info->mRTPTime) 4521906e5c7492b9cbc88601365536a69e9a490c963Andreas Huber / info->mTimeScale 4532bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber * 1000000ll 4541906e5c7492b9cbc88601365536a69e9a490c963Andreas Huber + info->mNormalPlaytimeUs; 4552bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 4562bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber accessUnit->meta()->setInt64("timeUs", nptUs); 4572bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 4582bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber source->queueAccessUnit(accessUnit); 4592bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber } 4602bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber break; 4612bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber } 4622bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 4632bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber case MyHandler::kWhatEOS: 4642bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber { 4652bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber int32_t finalResult; 4662bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber CHECK(msg->findInt32("finalResult", &finalResult)); 4672bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber CHECK_NE(finalResult, (status_t)OK); 4682bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 46949694688c82214f5fd9e969e177c9e126a240a26Andreas Huber if (mTSParser != NULL) { 47049694688c82214f5fd9e969e177c9e126a240a26Andreas Huber sp<AnotherPacketSource> source = getSource(false /* audio */); 47149694688c82214f5fd9e969e177c9e126a240a26Andreas Huber if (source != NULL) { 47249694688c82214f5fd9e969e177c9e126a240a26Andreas Huber source->signalEOS(finalResult); 47349694688c82214f5fd9e969e177c9e126a240a26Andreas Huber } 47449694688c82214f5fd9e969e177c9e126a240a26Andreas Huber 47549694688c82214f5fd9e969e177c9e126a240a26Andreas Huber source = getSource(true /* audio */); 47649694688c82214f5fd9e969e177c9e126a240a26Andreas Huber if (source != NULL) { 47749694688c82214f5fd9e969e177c9e126a240a26Andreas Huber source->signalEOS(finalResult); 47849694688c82214f5fd9e969e177c9e126a240a26Andreas Huber } 47949694688c82214f5fd9e969e177c9e126a240a26Andreas Huber 48049694688c82214f5fd9e969e177c9e126a240a26Andreas Huber return; 48149694688c82214f5fd9e969e177c9e126a240a26Andreas Huber } 48249694688c82214f5fd9e969e177c9e126a240a26Andreas Huber 48349694688c82214f5fd9e969e177c9e126a240a26Andreas Huber size_t trackIndex; 48449694688c82214f5fd9e969e177c9e126a240a26Andreas Huber CHECK(msg->findSize("trackIndex", &trackIndex)); 48549694688c82214f5fd9e969e177c9e126a240a26Andreas Huber CHECK_LT(trackIndex, mTracks.size()); 48649694688c82214f5fd9e969e177c9e126a240a26Andreas Huber 4872bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber TrackInfo *info = &mTracks.editItemAt(trackIndex); 4882bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber sp<AnotherPacketSource> source = info->mSource; 4892bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber if (source != NULL) { 4902bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber source->signalEOS(finalResult); 4912bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber } 4922bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 4932bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber break; 4942bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber } 4952bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 4962bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber case MyHandler::kWhatSeekDiscontinuity: 4972bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber { 4982bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber size_t trackIndex; 4992bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber CHECK(msg->findSize("trackIndex", &trackIndex)); 5002bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber CHECK_LT(trackIndex, mTracks.size()); 5012bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 5022bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber TrackInfo *info = &mTracks.editItemAt(trackIndex); 5032bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber sp<AnotherPacketSource> source = info->mSource; 5042bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber if (source != NULL) { 5052bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber source->queueDiscontinuity(ATSParser::DISCONTINUITY_SEEK, NULL); 5062bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber } 5072bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 5082bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber break; 5092bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber } 5102bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 5112bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber case MyHandler::kWhatNormalPlayTimeMapping: 5122bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber { 5132bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber size_t trackIndex; 5142bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber CHECK(msg->findSize("trackIndex", &trackIndex)); 5152bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber CHECK_LT(trackIndex, mTracks.size()); 5162bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 5172bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber uint32_t rtpTime; 5182bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber CHECK(msg->findInt32("rtpTime", (int32_t *)&rtpTime)); 5192bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 5202bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber int64_t nptUs; 5212bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber CHECK(msg->findInt64("nptUs", &nptUs)); 5222bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 5232bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber TrackInfo *info = &mTracks.editItemAt(trackIndex); 5242bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber info->mRTPTime = rtpTime; 5252bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber info->mNormalPlaytimeUs = nptUs; 5261906e5c7492b9cbc88601365536a69e9a490c963Andreas Huber info->mNPTMappingValid = true; 5272bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber break; 5282bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber } 5292bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 53081dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé case SDPLoader::kWhatSDPLoaded: 53181dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé { 53281dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé onSDPLoaded(msg); 53381dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé break; 53481dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé } 53581dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé 5362bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber default: 5372bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber TRESPASS(); 5382bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber } 5392bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber} 5402bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 5412bfdd428c56c7524d1a11979f200a1762866032dAndreas Hubervoid NuPlayer::RTSPSource::onConnected() { 5422bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber CHECK(mAudioTrack == NULL); 5432bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber CHECK(mVideoTrack == NULL); 5442bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 5452bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber size_t numTracks = mHandler->countTracks(); 5462bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber for (size_t i = 0; i < numTracks; ++i) { 5472bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber int32_t timeScale; 5482bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber sp<MetaData> format = mHandler->getTrackFormat(i, &timeScale); 5492bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 5502bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber const char *mime; 5512bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber CHECK(format->findCString(kKeyMIMEType, &mime)); 5522bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 55349694688c82214f5fd9e969e177c9e126a240a26Andreas Huber if (!strcasecmp(mime, MEDIA_MIMETYPE_CONTAINER_MPEG2TS)) { 55449694688c82214f5fd9e969e177c9e126a240a26Andreas Huber // Very special case for MPEG2 Transport Streams. 55549694688c82214f5fd9e969e177c9e126a240a26Andreas Huber CHECK_EQ(numTracks, 1u); 55649694688c82214f5fd9e969e177c9e126a240a26Andreas Huber 55749694688c82214f5fd9e969e177c9e126a240a26Andreas Huber mTSParser = new ATSParser; 55849694688c82214f5fd9e969e177c9e126a240a26Andreas Huber return; 55949694688c82214f5fd9e969e177c9e126a240a26Andreas Huber } 56049694688c82214f5fd9e969e177c9e126a240a26Andreas Huber 5612bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber bool isAudio = !strncasecmp(mime, "audio/", 6); 5622bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber bool isVideo = !strncasecmp(mime, "video/", 6); 5632bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 5642bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber TrackInfo info; 5652bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber info.mTimeScale = timeScale; 5662bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber info.mRTPTime = 0; 5672bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber info.mNormalPlaytimeUs = 0ll; 5681906e5c7492b9cbc88601365536a69e9a490c963Andreas Huber info.mNPTMappingValid = false; 5692bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 5702bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber if ((isAudio && mAudioTrack == NULL) 5712bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber || (isVideo && mVideoTrack == NULL)) { 5722bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber sp<AnotherPacketSource> source = new AnotherPacketSource(format); 5732bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 5742bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber if (isAudio) { 5752bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber mAudioTrack = source; 5762bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber } else { 5772bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber mVideoTrack = source; 5782bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber } 5792bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 5802bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber info.mSource = source; 5812bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber } 5822bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 5832bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber mTracks.push(info); 5842bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber } 5852bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 5862bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber mState = CONNECTED; 5872bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber} 5882bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 58981dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhévoid NuPlayer::RTSPSource::onSDPLoaded(const sp<AMessage> &msg) { 59081dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé status_t err; 59181dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé CHECK(msg->findInt32("result", &err)); 59281dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé 59381dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé mSDPLoader.clear(); 59481dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé 59581dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé if (mDisconnectReplyID != 0) { 59681dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé err = UNKNOWN_ERROR; 59781dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé } 59881dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé 59981dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé if (err == OK) { 60081dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé sp<ASessionDescription> desc; 60181dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé sp<RefBase> obj; 60281dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé CHECK(msg->findObject("description", &obj)); 60381dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé desc = static_cast<ASessionDescription *>(obj.get()); 60481dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé 60581dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé AString rtspUri; 60681dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé if (!desc->findAttribute(0, "a=control", &rtspUri)) { 60781dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé ALOGE("Unable to find url in SDP"); 60881dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé err = UNKNOWN_ERROR; 60981dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé } else { 61081dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé sp<AMessage> notify = new AMessage(kWhatNotify, mReflector->id()); 61181dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé 61281dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé mHandler = new MyHandler(rtspUri.c_str(), notify, mUIDValid, mUID); 61381dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé mLooper->registerHandler(mHandler); 61481dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé 61581dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé mHandler->loadSDP(desc); 61681dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé } 61781dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé } 61881dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé 61981dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé if (err != OK) { 6207f475c34ffc8e35345f2cceee2ef56a50bb5fea6Andreas Huber if (mState == CONNECTING) { 6217f475c34ffc8e35345f2cceee2ef56a50bb5fea6Andreas Huber // We're still in the preparation phase, signal that it 6227f475c34ffc8e35345f2cceee2ef56a50bb5fea6Andreas Huber // failed. 6237f475c34ffc8e35345f2cceee2ef56a50bb5fea6Andreas Huber notifyPrepared(err); 6247f475c34ffc8e35345f2cceee2ef56a50bb5fea6Andreas Huber } 6257f475c34ffc8e35345f2cceee2ef56a50bb5fea6Andreas Huber 62681dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé mState = DISCONNECTED; 62781dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé mFinalResult = err; 62881dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé 62981dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé if (mDisconnectReplyID != 0) { 63081dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé finishDisconnectIfPossible(); 63181dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé } 63281dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé } 63381dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé} 63481dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé 6352bfdd428c56c7524d1a11979f200a1762866032dAndreas Hubervoid NuPlayer::RTSPSource::onDisconnected(const sp<AMessage> &msg) { 6360ad03bc59d090a0455f858d2f629834c105f6f37Fredrik Rosin if (mState == DISCONNECTED) { 6370ad03bc59d090a0455f858d2f629834c105f6f37Fredrik Rosin return; 6380ad03bc59d090a0455f858d2f629834c105f6f37Fredrik Rosin } 6390ad03bc59d090a0455f858d2f629834c105f6f37Fredrik Rosin 6402bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber status_t err; 6412bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber CHECK(msg->findInt32("result", &err)); 6422bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber CHECK_NE(err, (status_t)OK); 6432bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 6442bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber mLooper->unregisterHandler(mHandler->id()); 6452bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber mHandler.clear(); 6462bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 6477f475c34ffc8e35345f2cceee2ef56a50bb5fea6Andreas Huber if (mState == CONNECTING) { 6487f475c34ffc8e35345f2cceee2ef56a50bb5fea6Andreas Huber // We're still in the preparation phase, signal that it 6497f475c34ffc8e35345f2cceee2ef56a50bb5fea6Andreas Huber // failed. 6507f475c34ffc8e35345f2cceee2ef56a50bb5fea6Andreas Huber notifyPrepared(err); 6517f475c34ffc8e35345f2cceee2ef56a50bb5fea6Andreas Huber } 6527f475c34ffc8e35345f2cceee2ef56a50bb5fea6Andreas Huber 6532bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber mState = DISCONNECTED; 6542bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber mFinalResult = err; 6552bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 6562bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber if (mDisconnectReplyID != 0) { 6572bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber finishDisconnectIfPossible(); 6582bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber } 6592bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber} 6602bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 6612bfdd428c56c7524d1a11979f200a1762866032dAndreas Hubervoid NuPlayer::RTSPSource::finishDisconnectIfPossible() { 6622bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber if (mState != DISCONNECTED) { 66381dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé if (mHandler != NULL) { 66481dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé mHandler->disconnect(); 66581dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé } else if (mSDPLoader != NULL) { 66681dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé mSDPLoader->cancel(); 66781dd60e0340ddcf7f1d5fb80b6c30906fabf201aOscar Rydhé } 6682bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber return; 6692bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber } 6702bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 6712bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber (new AMessage)->postReply(mDisconnectReplyID); 6722bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber mDisconnectReplyID = 0; 6732bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber} 6742bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber 6752bfdd428c56c7524d1a11979f200a1762866032dAndreas Huber} // namespace android 676