PlaybackSession.cpp revision efd9c63dc846dd3dea2c979fe2a9d6770e73f9ac
1d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber/* 2d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber * Copyright 2012, The Android Open Source Project 3d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber * 4d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber * Licensed under the Apache License, Version 2.0 (the "License"); 5d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber * you may not use this file except in compliance with the License. 6d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber * You may obtain a copy of the License at 7d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber * 8d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber * http://www.apache.org/licenses/LICENSE-2.0 9d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber * 10d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber * Unless required by applicable law or agreed to in writing, software 11d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber * distributed under the License is distributed on an "AS IS" BASIS, 12d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber * See the License for the specific language governing permissions and 14d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber * limitations under the License. 15d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber */ 16d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 17d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber//#define LOG_NDEBUG 0 18d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber#define LOG_TAG "PlaybackSession" 19d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber#include <utils/Log.h> 20d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 21d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber#include "PlaybackSession.h" 22d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 23d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber#include "Converter.h" 24e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber#include "MediaPuller.h" 25d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber#include "RepeaterSource.h" 26d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber#include "Serializer.h" 27d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber#include "TSPacketizer.h" 28d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 29d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber#include <binder/IServiceManager.h> 30d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber#include <gui/ISurfaceComposer.h> 31d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber#include <gui/SurfaceComposerClient.h> 32b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber#include <media/IHDCP.h> 33d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber#include <media/stagefright/foundation/ABuffer.h> 34d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber#include <media/stagefright/foundation/ADebug.h> 35d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber#include <media/stagefright/foundation/AMessage.h> 36d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber#include <media/stagefright/foundation/hexdump.h> 37082830f92373a1b9e512dbbfb940187ffa1c2c6fAndreas Huber#include <media/stagefright/AudioSource.h> 38d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber#include <media/stagefright/DataSource.h> 39d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber#include <media/stagefright/MediaDefs.h> 40d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber#include <media/stagefright/MediaErrors.h> 41d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber#include <media/stagefright/MediaExtractor.h> 42d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber#include <media/stagefright/MediaSource.h> 43d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber#include <media/stagefright/MetaData.h> 44d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber#include <media/stagefright/MPEG2TSWriter.h> 45d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber#include <media/stagefright/SurfaceMediaSource.h> 46d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber#include <media/stagefright/Utils.h> 47d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 48d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber#include <OMX_IVCommon.h> 49d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 50bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber//#define FAKE_VIDEO 1 51bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber#define USE_SERIALIZER 0 52d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 53d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Hubernamespace android { 54d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 55d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huberstatic size_t kMaxRTPPacketSize = 1500; 56d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huberstatic size_t kMaxNumTSPacketsPerRTPPacket = (kMaxRTPPacketSize - 12) / 188; 57d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 58d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huberstruct WifiDisplaySource::PlaybackSession::Track : public RefBase { 59e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber Track(const sp<ALooper> &pullLooper, 60e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber const sp<ALooper> &codecLooper, 61e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber const sp<MediaPuller> &mediaPuller, 62e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber const sp<Converter> &converter); 63e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber 64d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber Track(const sp<AMessage> &format); 65d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 66d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber sp<AMessage> getFormat(); 67b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber bool isAudio() const; 68d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 69d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber const sp<Converter> &converter() const; 70d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber ssize_t packetizerTrackIndex() const; 71d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 72d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber void setPacketizerTrackIndex(size_t index); 73d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 74e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber status_t start(); 75e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber status_t stop(); 76e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber 77d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huberprotected: 78d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber virtual ~Track(); 79d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 80d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huberprivate: 81e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber sp<ALooper> mPullLooper; 82e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber sp<ALooper> mCodecLooper; 83e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber sp<MediaPuller> mMediaPuller; 84d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber sp<Converter> mConverter; 85d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber sp<AMessage> mFormat; 86e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber bool mStarted; 87d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber ssize_t mPacketizerTrackIndex; 88b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber bool mIsAudio; 89b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber 90b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber static bool IsAudioFormat(const sp<AMessage> &format); 91d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 92d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber DISALLOW_EVIL_CONSTRUCTORS(Track); 93d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber}; 94d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 95e1957358f11031a554c57d4fb46988dd6044acc1Andreas HuberWifiDisplaySource::PlaybackSession::Track::Track( 96e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber const sp<ALooper> &pullLooper, 97e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber const sp<ALooper> &codecLooper, 98e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber const sp<MediaPuller> &mediaPuller, 99e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber const sp<Converter> &converter) 100e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber : mPullLooper(pullLooper), 101e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber mCodecLooper(codecLooper), 102e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber mMediaPuller(mediaPuller), 103e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber mConverter(converter), 104e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber mStarted(false), 105b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber mPacketizerTrackIndex(-1), 106b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber mIsAudio(IsAudioFormat(mConverter->getOutputFormat())) { 107d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber} 108d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 109d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas HuberWifiDisplaySource::PlaybackSession::Track::Track(const sp<AMessage> &format) 110d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber : mFormat(format), 111b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber mPacketizerTrackIndex(-1), 112b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber mIsAudio(IsAudioFormat(mFormat)) { 113d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber} 114d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 115d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas HuberWifiDisplaySource::PlaybackSession::Track::~Track() { 116e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber stop(); 117d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber} 118d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 119b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber// static 120b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huberbool WifiDisplaySource::PlaybackSession::Track::IsAudioFormat( 121b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber const sp<AMessage> &format) { 122b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber AString mime; 123b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber CHECK(format->findString("mime", &mime)); 124b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber 125b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber return !strncasecmp(mime.c_str(), "audio/", 6); 126b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber} 127b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber 128d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Hubersp<AMessage> WifiDisplaySource::PlaybackSession::Track::getFormat() { 129d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber if (mFormat != NULL) { 130d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber return mFormat; 131d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber } 132d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 133d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber return mConverter->getOutputFormat(); 134d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber} 135d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 136b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huberbool WifiDisplaySource::PlaybackSession::Track::isAudio() const { 137b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber return mIsAudio; 138b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber} 139b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber 140d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huberconst sp<Converter> &WifiDisplaySource::PlaybackSession::Track::converter() const { 141d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber return mConverter; 142d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber} 143d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 144d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huberssize_t WifiDisplaySource::PlaybackSession::Track::packetizerTrackIndex() const { 145d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber return mPacketizerTrackIndex; 146d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber} 147d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 148d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Hubervoid WifiDisplaySource::PlaybackSession::Track::setPacketizerTrackIndex(size_t index) { 149d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber CHECK_LT(mPacketizerTrackIndex, 0); 150d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber mPacketizerTrackIndex = index; 151d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber} 152d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 153e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huberstatus_t WifiDisplaySource::PlaybackSession::Track::start() { 154e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber if (mStarted) { 155e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber return INVALID_OPERATION; 156e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber } 157e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber 158e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber status_t err = OK; 159e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber 160e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber if (mMediaPuller != NULL) { 161e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber err = mMediaPuller->start(); 162e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber } 163e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber 164e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber if (err == OK) { 165e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber mStarted = true; 166e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber } 167e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber 168e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber return err; 169e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber} 170e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber 171e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huberstatus_t WifiDisplaySource::PlaybackSession::Track::stop() { 172e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber if (!mStarted) { 173e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber return INVALID_OPERATION; 174e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber } 175e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber 176e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber status_t err = OK; 177e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber 178e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber if (mMediaPuller != NULL) { 179e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber err = mMediaPuller->stop(); 180e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber } 181e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber 182a438123bd96c7faf145683876702387efe5628d9Andreas Huber mConverter.clear(); 183a438123bd96c7faf145683876702387efe5628d9Andreas Huber 184e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber mStarted = false; 185e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber 186e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber return err; 187e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber} 188e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber 189d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber//////////////////////////////////////////////////////////////////////////////// 190d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 191d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas HuberWifiDisplaySource::PlaybackSession::PlaybackSession( 192d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber const sp<ANetworkSession> &netSession, 1930b73d4730202fcad53aefc4314a06e7b95f442f0Andreas Huber const sp<AMessage> ¬ify, 194bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber const in_addr &interfaceAddr, 195b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber bool legacyMode, 196b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber const sp<IHDCP> &hdcp) 197d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber : mNetSession(netSession), 198d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber mNotify(notify), 199bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber mInterfaceAddr(interfaceAddr), 2000b73d4730202fcad53aefc4314a06e7b95f442f0Andreas Huber mLegacyMode(legacyMode), 201b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber mHDCP(hdcp), 202d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber mLastLifesignUs(), 203e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber mVideoTrackIndex(-1), 204d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber mTSQueue(new ABuffer(12 + kMaxNumTSPacketsPerRTPPacket * 188)), 205d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber mPrevTimeUs(-1ll), 206bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber mTransportMode(TRANSPORT_UDP), 207d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber mRTPChannel(0), 208d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber mRTCPChannel(0), 209d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber mRTPPort(0), 210d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber mRTPSessionID(0), 211d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber mRTCPSessionID(0), 212efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber#if ENABLE_RETRANSMISSION 213efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber mRTPRetransmissionSessionID(0), 214efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber mRTCPRetransmissionSessionID(0), 215efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber#endif 216bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber mClientRTPPort(0), 217bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber mClientRTCPPort(0), 218bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber mRTPConnected(false), 219bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber mRTCPConnected(false), 220d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber mRTPSeqNo(0), 221efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber#if ENABLE_RETRANSMISSION 222efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber mRTPRetransmissionSeqNo(0), 223efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber#endif 224d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber mLastNTPTime(0), 225d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber mLastRTPTime(0), 226d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber mNumRTPSent(0), 227d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber mNumRTPOctetsSent(0), 228d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber mNumSRsSent(0), 229d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber mSendSRPending(false), 230d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber mFirstPacketTimeUs(-1ll), 231dca352880e210e0ca0ff39de074540d3640ecfabAndreas Huber mHistoryLength(0), 232dca352880e210e0ca0ff39de074540d3640ecfabAndreas Huber mTotalBytesSent(0ll) 233774df0dce0116c69b6d17f2e4a4912e06138e575Andreas Huber#if LOG_TRANSPORT_STREAM 234774df0dce0116c69b6d17f2e4a4912e06138e575Andreas Huber ,mLogFile(NULL) 235774df0dce0116c69b6d17f2e4a4912e06138e575Andreas Huber#endif 236774df0dce0116c69b6d17f2e4a4912e06138e575Andreas Huber{ 237d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber mTSQueue->setRange(0, 12); 238774df0dce0116c69b6d17f2e4a4912e06138e575Andreas Huber 239774df0dce0116c69b6d17f2e4a4912e06138e575Andreas Huber#if LOG_TRANSPORT_STREAM 240774df0dce0116c69b6d17f2e4a4912e06138e575Andreas Huber mLogFile = fopen("/system/etc/log.ts", "wb"); 241774df0dce0116c69b6d17f2e4a4912e06138e575Andreas Huber#endif 242d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber} 243d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 244d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huberstatus_t WifiDisplaySource::PlaybackSession::init( 245d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber const char *clientIP, int32_t clientRtp, int32_t clientRtcp, 246bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber TransportMode transportMode) { 247bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber mClientIP = clientIP; 248bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber 249d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber status_t err = setupPacketizer(); 250d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 251d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber if (err != OK) { 252d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber return err; 253d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber } 254d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 255bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber mTransportMode = transportMode; 256bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber 257bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber if (transportMode == TRANSPORT_TCP_INTERLEAVED) { 258d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber mRTPChannel = clientRtp; 259d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber mRTCPChannel = clientRtcp; 260d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber mRTPPort = 0; 261d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber mRTPSessionID = 0; 262d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber mRTCPSessionID = 0; 263d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 264d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber updateLiveness(); 265d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber return OK; 266d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber } 267d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 268d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber mRTPChannel = 0; 269d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber mRTCPChannel = 0; 270d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 271bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber if (mTransportMode == TRANSPORT_TCP) { 272bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber // XXX This is wrong, we need to allocate sockets here, we only 273bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber // need to do this because the dongles are not establishing their 274bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber // end until after PLAY instead of before SETUP. 275bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber mRTPPort = 20000; 276bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber mRTPSessionID = 0; 277bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber mRTCPSessionID = 0; 278bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber mClientRTPPort = clientRtp; 279bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber mClientRTCPPort = clientRtcp; 280bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber 281bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber updateLiveness(); 282bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber return OK; 283bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber } 284bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber 285d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber int serverRtp; 286d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 287d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber sp<AMessage> rtpNotify = new AMessage(kWhatRTPNotify, id()); 288d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber sp<AMessage> rtcpNotify = new AMessage(kWhatRTCPNotify, id()); 289efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber 290efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber#if ENABLE_RETRANSMISSION 291efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber sp<AMessage> rtpRetransmissionNotify = 292efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber new AMessage(kWhatRTPRetransmissionNotify, id()); 293efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber 294efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber sp<AMessage> rtcpRetransmissionNotify = 295efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber new AMessage(kWhatRTCPRetransmissionNotify, id()); 296efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber#endif 297efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber 298d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber for (serverRtp = 15550;; serverRtp += 2) { 299d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber int32_t rtpSession; 300bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber if (mTransportMode == TRANSPORT_UDP) { 301bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber err = mNetSession->createUDPSession( 302bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber serverRtp, clientIP, clientRtp, 303bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber rtpNotify, &rtpSession); 304bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber } else { 305bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber err = mNetSession->createTCPDatagramSession( 306bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber serverRtp, clientIP, clientRtp, 307bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber rtpNotify, &rtpSession); 308bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber } 309d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 310d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber if (err != OK) { 311d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber ALOGI("failed to create RTP socket on port %d", serverRtp); 312d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber continue; 313d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber } 314d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 315efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber int32_t rtcpSession = 0; 316d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 317efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber if (clientRtcp >= 0) { 318efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber if (mTransportMode == TRANSPORT_UDP) { 319efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber err = mNetSession->createUDPSession( 320efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber serverRtp + 1, clientIP, clientRtcp, 321efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber rtcpNotify, &rtcpSession); 322efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber } else { 323efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber err = mNetSession->createTCPDatagramSession( 324efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber serverRtp + 1, clientIP, clientRtcp, 325efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber rtcpNotify, &rtcpSession); 326efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber } 327d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 328efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber if (err != OK) { 329efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber ALOGI("failed to create RTCP socket on port %d", serverRtp + 1); 330efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber 331efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber mNetSession->destroySession(rtpSession); 332efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber continue; 333efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber } 334d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber } 335d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 336efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber#if ENABLE_RETRANSMISSION 337bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber if (mTransportMode == TRANSPORT_UDP) { 338efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber int32_t rtpRetransmissionSession; 339efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber 340bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber err = mNetSession->createUDPSession( 341efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber serverRtp + kRetransmissionPortOffset, 342efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber clientIP, 343efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber clientRtp + kRetransmissionPortOffset, 344efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber rtpRetransmissionNotify, 345efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber &rtpRetransmissionSession); 346efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber 347efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber if (err != OK) { 348efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber mNetSession->destroySession(rtcpSession); 349efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber mNetSession->destroySession(rtpSession); 350efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber continue; 351efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber } 352d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 353efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber CHECK_GE(clientRtcp, 0); 354d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 355efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber int32_t rtcpRetransmissionSession; 356efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber err = mNetSession->createUDPSession( 357efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber serverRtp + 1 + kRetransmissionPortOffset, 358efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber clientIP, 359efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber clientRtp + 1 + kRetransmissionPortOffset, 360efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber rtcpRetransmissionNotify, 361efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber &rtcpRetransmissionSession); 362efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber 363efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber if (err != OK) { 364efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber mNetSession->destroySession(rtpRetransmissionSession); 365efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber mNetSession->destroySession(rtcpSession); 366efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber mNetSession->destroySession(rtpSession); 367efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber continue; 368efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber } 369efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber 370efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber mRTPRetransmissionSessionID = rtpRetransmissionSession; 371efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber mRTCPRetransmissionSessionID = rtcpRetransmissionSession; 372efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber 373efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber ALOGI("rtpRetransmissionSessionID = %d, " 374efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber "rtcpRetransmissionSessionID = %d", 375efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber rtpRetransmissionSession, rtcpRetransmissionSession); 376d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber } 377efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber#endif 378efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber 379efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber mRTPPort = serverRtp; 380efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber mRTPSessionID = rtpSession; 381efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber mRTCPSessionID = rtcpSession; 382d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 383efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber ALOGI("rtpSessionID = %d, rtcpSessionID = %d", rtpSession, rtcpSession); 384efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber break; 385d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber } 386d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 387d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber if (mRTPPort == 0) { 388d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber return UNKNOWN_ERROR; 389d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber } 390d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 391d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber updateLiveness(); 392d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 393d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber return OK; 394d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber} 395d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 396d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas HuberWifiDisplaySource::PlaybackSession::~PlaybackSession() { 397774df0dce0116c69b6d17f2e4a4912e06138e575Andreas Huber#if LOG_TRANSPORT_STREAM 398774df0dce0116c69b6d17f2e4a4912e06138e575Andreas Huber if (mLogFile != NULL) { 399774df0dce0116c69b6d17f2e4a4912e06138e575Andreas Huber fclose(mLogFile); 400774df0dce0116c69b6d17f2e4a4912e06138e575Andreas Huber mLogFile = NULL; 401774df0dce0116c69b6d17f2e4a4912e06138e575Andreas Huber } 402774df0dce0116c69b6d17f2e4a4912e06138e575Andreas Huber#endif 403d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber} 404d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 405d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huberint32_t WifiDisplaySource::PlaybackSession::getRTPPort() const { 406d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber return mRTPPort; 407d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber} 408d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 409d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huberint64_t WifiDisplaySource::PlaybackSession::getLastLifesignUs() const { 410d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber return mLastLifesignUs; 411d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber} 412d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 413d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Hubervoid WifiDisplaySource::PlaybackSession::updateLiveness() { 414d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber mLastLifesignUs = ALooper::GetNowUs(); 415d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber} 416d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 417d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huberstatus_t WifiDisplaySource::PlaybackSession::play() { 418d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber updateLiveness(); 419d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 420bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber return OK; 421bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber} 422bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber 423bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huberstatus_t WifiDisplaySource::PlaybackSession::finishPlay() { 424bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber // XXX Give the dongle 3 secs to bind its sockets. 425bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber (new AMessage(kWhatFinishPlay, id()))->post(3000000ll); 426bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber return OK; 427bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber} 428bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber 429bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huberstatus_t WifiDisplaySource::PlaybackSession::onFinishPlay() { 430bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber if (mTransportMode != TRANSPORT_TCP) { 431bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber return onFinishPlay2(); 432bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber } 433bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber 434bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber sp<AMessage> rtpNotify = new AMessage(kWhatRTPNotify, id()); 435bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber 436bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber status_t err = mNetSession->createTCPDatagramSession( 437bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber mRTPPort, mClientIP.c_str(), mClientRTPPort, 438bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber rtpNotify, &mRTPSessionID); 439bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber 440bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber if (err != OK) { 441bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber return err; 442bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber } 443bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber 444bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber if (mClientRTCPPort >= 0) { 445bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber sp<AMessage> rtcpNotify = new AMessage(kWhatRTCPNotify, id()); 446bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber 447bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber err = mNetSession->createTCPDatagramSession( 448bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber mRTPPort + 1, mClientIP.c_str(), mClientRTCPPort, 449bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber rtcpNotify, &mRTCPSessionID); 450bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber } 451bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber 452bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber return err; 453bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber} 454bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber 455bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huberstatus_t WifiDisplaySource::PlaybackSession::onFinishPlay2() { 456d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber if (mRTCPSessionID != 0) { 457d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber scheduleSendSR(); 458d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber } 459d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 460e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber if (mSerializer != NULL) { 461e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber return mSerializer->start(); 462e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber } 463e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber 464e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber for (size_t i = 0; i < mTracks.size(); ++i) { 465e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber status_t err = mTracks.editValueAt(i)->start(); 466e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber 467e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber if (err != OK) { 468e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber for (size_t j = 0; j < i; ++j) { 469e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber mTracks.editValueAt(j)->stop(); 470e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber } 471e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber 472e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber return err; 473e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber } 474e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber } 475e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber 476bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber sp<AMessage> notify = mNotify->dup(); 477bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber notify->setInt32("what", kWhatSessionEstablished); 478bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber notify->post(); 479bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber 480e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber return OK; 481d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber} 482d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 483d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huberstatus_t WifiDisplaySource::PlaybackSession::pause() { 484d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber updateLiveness(); 485d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 486d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber return OK; 487d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber} 488d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 489a438123bd96c7faf145683876702387efe5628d9Andreas Huberstatus_t WifiDisplaySource::PlaybackSession::destroy() { 490a438123bd96c7faf145683876702387efe5628d9Andreas Huber mTracks.clear(); 491a438123bd96c7faf145683876702387efe5628d9Andreas Huber 492a438123bd96c7faf145683876702387efe5628d9Andreas Huber mPacketizer.clear(); 493a438123bd96c7faf145683876702387efe5628d9Andreas Huber 494a438123bd96c7faf145683876702387efe5628d9Andreas Huber if (mSerializer != NULL) { 495a438123bd96c7faf145683876702387efe5628d9Andreas Huber mSerializer->stop(); 496a438123bd96c7faf145683876702387efe5628d9Andreas Huber 497a438123bd96c7faf145683876702387efe5628d9Andreas Huber looper()->unregisterHandler(mSerializer->id()); 498a438123bd96c7faf145683876702387efe5628d9Andreas Huber mSerializer.clear(); 499a438123bd96c7faf145683876702387efe5628d9Andreas Huber } 500a438123bd96c7faf145683876702387efe5628d9Andreas Huber 501a438123bd96c7faf145683876702387efe5628d9Andreas Huber mTracks.clear(); 502a438123bd96c7faf145683876702387efe5628d9Andreas Huber 503a438123bd96c7faf145683876702387efe5628d9Andreas Huber if (mSerializerLooper != NULL) { 504a438123bd96c7faf145683876702387efe5628d9Andreas Huber mSerializerLooper->stop(); 505a438123bd96c7faf145683876702387efe5628d9Andreas Huber mSerializerLooper.clear(); 506a438123bd96c7faf145683876702387efe5628d9Andreas Huber } 507a438123bd96c7faf145683876702387efe5628d9Andreas Huber 508a438123bd96c7faf145683876702387efe5628d9Andreas Huber if (mLegacyMode) { 509a438123bd96c7faf145683876702387efe5628d9Andreas Huber sp<IServiceManager> sm = defaultServiceManager(); 510a438123bd96c7faf145683876702387efe5628d9Andreas Huber sp<IBinder> binder = sm->getService(String16("SurfaceFlinger")); 511a438123bd96c7faf145683876702387efe5628d9Andreas Huber sp<ISurfaceComposer> service = interface_cast<ISurfaceComposer>(binder); 512a438123bd96c7faf145683876702387efe5628d9Andreas Huber CHECK(service != NULL); 513a438123bd96c7faf145683876702387efe5628d9Andreas Huber 514a438123bd96c7faf145683876702387efe5628d9Andreas Huber service->connectDisplay(NULL); 515a438123bd96c7faf145683876702387efe5628d9Andreas Huber } 516a438123bd96c7faf145683876702387efe5628d9Andreas Huber 517efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber#if ENABLE_RETRANSMISSION 518efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber if (mRTCPRetransmissionSessionID != 0) { 519efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber mNetSession->destroySession(mRTCPRetransmissionSessionID); 520efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber } 521efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber 522efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber if (mRTPRetransmissionSessionID != 0) { 523efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber mNetSession->destroySession(mRTPRetransmissionSessionID); 524efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber } 525efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber#endif 526efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber 527a438123bd96c7faf145683876702387efe5628d9Andreas Huber if (mRTCPSessionID != 0) { 528a438123bd96c7faf145683876702387efe5628d9Andreas Huber mNetSession->destroySession(mRTCPSessionID); 529a438123bd96c7faf145683876702387efe5628d9Andreas Huber } 530a438123bd96c7faf145683876702387efe5628d9Andreas Huber 531a438123bd96c7faf145683876702387efe5628d9Andreas Huber if (mRTPSessionID != 0) { 532a438123bd96c7faf145683876702387efe5628d9Andreas Huber mNetSession->destroySession(mRTPSessionID); 533a438123bd96c7faf145683876702387efe5628d9Andreas Huber } 534a438123bd96c7faf145683876702387efe5628d9Andreas Huber 535a438123bd96c7faf145683876702387efe5628d9Andreas Huber return OK; 536a438123bd96c7faf145683876702387efe5628d9Andreas Huber} 537a438123bd96c7faf145683876702387efe5628d9Andreas Huber 538d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Hubervoid WifiDisplaySource::PlaybackSession::onMessageReceived( 539d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber const sp<AMessage> &msg) { 540d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber switch (msg->what()) { 541d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber case kWhatRTPNotify: 542d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber case kWhatRTCPNotify: 543efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber#if ENABLE_RETRANSMISSION 544efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber case kWhatRTPRetransmissionNotify: 545efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber case kWhatRTCPRetransmissionNotify: 546efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber#endif 547d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber { 548d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber int32_t reason; 549d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber CHECK(msg->findInt32("reason", &reason)); 550d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 551d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber switch (reason) { 552d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber case ANetworkSession::kWhatError: 553d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber { 554d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber int32_t sessionID; 555d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber CHECK(msg->findInt32("sessionID", &sessionID)); 556d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 557d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber int32_t err; 558d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber CHECK(msg->findInt32("err", &err)); 559d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 560d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber int32_t errorOccuredDuringSend; 561d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber CHECK(msg->findInt32("send", &errorOccuredDuringSend)); 562d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 563d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber AString detail; 564d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber CHECK(msg->findString("detail", &detail)); 565d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 566efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber if ((msg->what() == kWhatRTPNotify 567efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber#if ENABLE_RETRANSMISSION 568efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber || msg->what() == kWhatRTPRetransmissionNotify 569efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber#endif 570efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber ) && !errorOccuredDuringSend) { 571d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber // This is ok, we don't expect to receive anything on 572d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber // the RTP socket. 573d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber break; 574d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber } 575d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 576d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber ALOGE("An error occurred during %s in session %d " 577d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber "(%d, '%s' (%s)).", 578d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber errorOccuredDuringSend ? "send" : "receive", 579d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber sessionID, 580d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber err, 581d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber detail.c_str(), 582d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber strerror(-err)); 583d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 584d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber mNetSession->destroySession(sessionID); 585d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 586d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber if (sessionID == mRTPSessionID) { 587d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber mRTPSessionID = 0; 588d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber } else if (sessionID == mRTCPSessionID) { 589d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber mRTCPSessionID = 0; 590d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber } 591efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber#if ENABLE_RETRANSMISSION 592efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber else if (sessionID == mRTPRetransmissionSessionID) { 593efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber mRTPRetransmissionSessionID = 0; 594efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber } else if (sessionID == mRTCPRetransmissionSessionID) { 595efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber mRTCPRetransmissionSessionID = 0; 596efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber } 597efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber#endif 598d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 599d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber // Inform WifiDisplaySource of our premature death (wish). 600d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber sp<AMessage> notify = mNotify->dup(); 601d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber notify->setInt32("what", kWhatSessionDead); 602d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber notify->post(); 603d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber break; 604d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber } 605d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 606d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber case ANetworkSession::kWhatDatagram: 607d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber { 608d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber int32_t sessionID; 609d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber CHECK(msg->findInt32("sessionID", &sessionID)); 610d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 611d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber sp<ABuffer> data; 612d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber CHECK(msg->findBuffer("data", &data)); 613d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 614d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber status_t err; 615efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber if (msg->what() == kWhatRTCPNotify 616efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber#if ENABLE_RETRANSMISSION 617efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber || msg->what() == kWhatRTCPRetransmissionNotify 618efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber#endif 619efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber ) 620efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber { 621d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber err = parseRTCP(data); 622d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber } 623d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber break; 624d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber } 625d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 626bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber case ANetworkSession::kWhatConnected: 627bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber { 628bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber CHECK_EQ(mTransportMode, TRANSPORT_TCP); 629bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber 630bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber int32_t sessionID; 631bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber CHECK(msg->findInt32("sessionID", &sessionID)); 632bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber 633bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber if (sessionID == mRTPSessionID) { 634bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber CHECK(!mRTPConnected); 635bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber mRTPConnected = true; 636bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber ALOGI("RTP Session now connected."); 637bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber } else if (sessionID == mRTCPSessionID) { 638bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber CHECK(!mRTCPConnected); 639bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber mRTCPConnected = true; 640bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber ALOGI("RTCP Session now connected."); 641bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber } else { 642bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber TRESPASS(); 643bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber } 644bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber 645bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber if (mRTPConnected 646bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber && (mClientRTCPPort < 0 || mRTCPConnected)) { 647bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber onFinishPlay2(); 648bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber } 649bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber break; 650bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber } 651bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber 652d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber default: 653d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber TRESPASS(); 654d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber } 655d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber break; 656d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber } 657d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 658d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber case kWhatSendSR: 659d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber { 660d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber mSendSRPending = false; 661d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 662d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber if (mRTCPSessionID == 0) { 663d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber break; 664d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber } 665d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 666d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber onSendSR(); 667d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 668d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber scheduleSendSR(); 669d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber break; 670d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber } 671d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 672d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber case kWhatSerializerNotify: 673d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber { 674d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber int32_t what; 675d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber CHECK(msg->findInt32("what", &what)); 676d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 677d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber if (what == Serializer::kWhatEOS) { 678d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber ALOGI("input eos"); 679d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 680d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber for (size_t i = 0; i < mTracks.size(); ++i) { 681d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber#if FAKE_VIDEO 682d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber sp<AMessage> msg = new AMessage(kWhatConverterNotify, id()); 683d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber msg->setInt32("what", Converter::kWhatEOS); 684d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber msg->setSize("trackIndex", i); 685d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber msg->post(); 686d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber#else 687d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber mTracks.valueAt(i)->converter()->signalEOS(); 688d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber#endif 689d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber } 690d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber } else { 691d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber CHECK_EQ(what, Serializer::kWhatAccessUnit); 692d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 693d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber size_t trackIndex; 694d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber CHECK(msg->findSize("trackIndex", &trackIndex)); 695d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 696d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber sp<ABuffer> accessUnit; 697d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber CHECK(msg->findBuffer("accessUnit", &accessUnit)); 698d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 699d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber#if FAKE_VIDEO 700d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber int64_t timeUs; 701d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber CHECK(accessUnit->meta()->findInt64("timeUs", &timeUs)); 702d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 703d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber void *mbuf; 704d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber CHECK(accessUnit->meta()->findPointer("mediaBuffer", &mbuf)); 705d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 706d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber ((MediaBuffer *)mbuf)->release(); 707d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber mbuf = NULL; 708d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 709d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber sp<AMessage> msg = new AMessage(kWhatConverterNotify, id()); 710d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber msg->setInt32("what", Converter::kWhatAccessUnit); 711d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber msg->setSize("trackIndex", trackIndex); 712d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber msg->setBuffer("accessUnit", accessUnit); 713d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber msg->post(); 714d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber#else 715d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber mTracks.valueFor(trackIndex)->converter() 716d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber ->feedAccessUnit(accessUnit); 717d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber#endif 718d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber } 719d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber break; 720d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber } 721d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 722d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber case kWhatConverterNotify: 723d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber { 724d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber int32_t what; 725d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber CHECK(msg->findInt32("what", &what)); 726d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 727d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber size_t trackIndex; 728d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber CHECK(msg->findSize("trackIndex", &trackIndex)); 729d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 730d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber if (what == Converter::kWhatAccessUnit) { 731d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber const sp<Track> &track = mTracks.valueFor(trackIndex); 732d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 733d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber uint32_t flags = 0; 734d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 735d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber ssize_t packetizerTrackIndex = track->packetizerTrackIndex(); 736d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber if (packetizerTrackIndex < 0) { 737d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber flags = TSPacketizer::EMIT_PAT_AND_PMT; 738d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 739d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber packetizerTrackIndex = 740d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber mPacketizer->addTrack(track->getFormat()); 741d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 742d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber if (packetizerTrackIndex >= 0) { 743d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber track->setPacketizerTrackIndex(packetizerTrackIndex); 744d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber } 745d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber } 746d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 747d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber if (packetizerTrackIndex >= 0) { 748d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber sp<ABuffer> accessUnit; 749d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber CHECK(msg->findBuffer("accessUnit", &accessUnit)); 750d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 751b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber bool isHDCPEncrypted = false; 752b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber uint64_t inputCTR; 753b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber uint8_t HDCP_private_data[16]; 754b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber if (mHDCP != NULL && !track->isAudio()) { 755b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber isHDCPEncrypted = true; 756b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber 757b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber status_t err = mHDCP->encrypt( 758b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber accessUnit->data(), accessUnit->size(), 759b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber trackIndex /* streamCTR */, 760b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber &inputCTR, 761b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber accessUnit->data()); 762b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber 763b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber if (err != OK) { 764b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber ALOGI("Failed to HDCP-encrypt media data (err %d)", 765b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber err); 766b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber 767b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber // Inform WifiDisplaySource of our premature death 768b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber // (wish). 769b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber sp<AMessage> notify = mNotify->dup(); 770b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber notify->setInt32("what", kWhatSessionDead); 771b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber notify->post(); 772b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber break; 773b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber } 774b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber 775b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber HDCP_private_data[0] = 0x00; 776b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber 777b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber HDCP_private_data[1] = 778b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber (((trackIndex >> 30) & 3) << 1) | 1; 779b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber 780b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber HDCP_private_data[2] = (trackIndex >> 22) & 0xff; 781b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber 782b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber HDCP_private_data[3] = 783b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber (((trackIndex >> 15) & 0x7f) << 1) | 1; 784b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber 785b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber HDCP_private_data[4] = (trackIndex >> 7) & 0xff; 786b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber 787b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber HDCP_private_data[5] = 788b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber ((trackIndex & 0x7f) << 1) | 1; 789b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber 790b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber HDCP_private_data[6] = 0x00; 791b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber 792b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber HDCP_private_data[7] = 793b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber (((inputCTR >> 60) & 0x0f) << 1) | 1; 794b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber 795b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber HDCP_private_data[8] = (inputCTR >> 52) & 0xff; 796b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber 797b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber HDCP_private_data[9] = 798b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber (((inputCTR >> 45) & 0x7f) << 1) | 1; 799b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber 800b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber HDCP_private_data[10] = (inputCTR >> 37) & 0xff; 801b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber 802b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber HDCP_private_data[11] = 803b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber (((inputCTR >> 30) & 0x7f) << 1) | 1; 804b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber 805b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber HDCP_private_data[12] = (inputCTR >> 22) & 0xff; 806b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber 807b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber HDCP_private_data[13] = 808b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber (((inputCTR >> 15) & 0x7f) << 1) | 1; 809b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber 810b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber HDCP_private_data[14] = (inputCTR >> 7) & 0xff; 811b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber 812b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber HDCP_private_data[15] = 813b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber ((inputCTR & 0x7f) << 1) | 1; 814b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber 815b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber flags |= TSPacketizer::IS_ENCRYPTED; 816b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber } 817b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber 818d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber int64_t timeUs; 819d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber CHECK(accessUnit->meta()->findInt64("timeUs", &timeUs)); 820d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 821d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber if (mPrevTimeUs < 0ll || mPrevTimeUs + 100000ll >= timeUs) { 822d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber flags |= TSPacketizer::EMIT_PCR; 823d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber mPrevTimeUs = timeUs; 824d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber } 825d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 826d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber sp<ABuffer> packets; 827d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber mPacketizer->packetize( 828b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber packetizerTrackIndex, accessUnit, &packets, flags, 829b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber isHDCPEncrypted ? NULL : HDCP_private_data, 830b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber isHDCPEncrypted ? 0 : sizeof(HDCP_private_data)); 831d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 832d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber for (size_t offset = 0; 833d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber offset < packets->size(); offset += 188) { 834d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber bool lastTSPacket = (offset + 188 >= packets->size()); 835d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 836e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber // We're only going to flush video, audio packets are 837e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber // much more frequent and would waste all that space 838e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber // available in a full sized UDP packet. 839e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber bool flush = 840e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber lastTSPacket 841e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber && ((ssize_t)trackIndex == mVideoTrackIndex); 842e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber 843d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber appendTSData( 844d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber packets->data() + offset, 845d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 188, 846d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber true /* timeDiscontinuity */, 847e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber flush); 848d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber } 849774df0dce0116c69b6d17f2e4a4912e06138e575Andreas Huber 850774df0dce0116c69b6d17f2e4a4912e06138e575Andreas Huber#if LOG_TRANSPORT_STREAM 851774df0dce0116c69b6d17f2e4a4912e06138e575Andreas Huber if (mLogFile != NULL) { 852774df0dce0116c69b6d17f2e4a4912e06138e575Andreas Huber fwrite(packets->data(), 1, packets->size(), mLogFile); 853774df0dce0116c69b6d17f2e4a4912e06138e575Andreas Huber } 854774df0dce0116c69b6d17f2e4a4912e06138e575Andreas Huber#endif 855d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber } 856d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber } else if (what == Converter::kWhatEOS) { 857d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber CHECK_EQ(what, Converter::kWhatEOS); 858d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 859d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber ALOGI("output EOS on track %d", trackIndex); 860d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 861d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber ssize_t index = mTracks.indexOfKey(trackIndex); 862d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber CHECK_GE(index, 0); 863d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 864d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber#if !FAKE_VIDEO 865d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber const sp<Converter> &converter = 866d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber mTracks.valueAt(index)->converter(); 867d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber looper()->unregisterHandler(converter->id()); 868d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber#endif 869d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 870d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber mTracks.removeItemsAt(index); 871d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 872d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber if (mTracks.isEmpty()) { 873d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber ALOGI("Reached EOS"); 874d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber } 875d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber } else { 876d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber CHECK_EQ(what, Converter::kWhatError); 877d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 878d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber status_t err; 879d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber CHECK(msg->findInt32("err", &err)); 880d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 881d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber ALOGE("converter signaled error %d", err); 882d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber } 883d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber break; 884d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber } 885d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 886bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber case kWhatFinishPlay: 887bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber { 888bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber onFinishPlay(); 889bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber break; 890bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber } 891bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber 892d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber default: 893d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber TRESPASS(); 894d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber } 895d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber} 896d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 897d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huberstatus_t WifiDisplaySource::PlaybackSession::setupPacketizer() { 898d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber sp<AMessage> msg = new AMessage(kWhatSerializerNotify, id()); 899d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 900e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber mPacketizer = new TSPacketizer; 901d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 902d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber#if FAKE_VIDEO 903e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber return addFakeSources(); 904d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber#else 905e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber status_t err = addVideoSource(); 906d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 907e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber if (err != OK) { 908e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber return err; 909e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber } 910e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber 911e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber return addAudioSource(); 912e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber#endif 913e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber} 914d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 915e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huberstatus_t WifiDisplaySource::PlaybackSession::addFakeSources() { 916d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber#if FAKE_VIDEO 917e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber mSerializerLooper = new ALooper; 918e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber mSerializerLooper->setName("serializer_looper"); 919e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber mSerializerLooper->start(); 920e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber 921e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber sp<AMessage> msg = new AMessage(kWhatSerializerNotify, id()); 922e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber mSerializer = new Serializer( 923e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber true /* throttled */, msg); 924e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber 925e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber mSerializerLooper->registerHandler(mSerializer); 926e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber 927d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber DataSource::RegisterDefaultSniffers(); 928d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 929d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber sp<DataSource> dataSource = 930d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber DataSource::CreateFromURI( 931d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber "/system/etc/inception_1500.mp4"); 932d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 933d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber CHECK(dataSource != NULL); 934d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 935d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber sp<MediaExtractor> extractor = MediaExtractor::Create(dataSource); 936d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber CHECK(extractor != NULL); 937d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 938d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber bool haveAudio = false; 939d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber bool haveVideo = false; 940d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber for (size_t i = 0; i < extractor->countTracks(); ++i) { 941d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber sp<MetaData> meta = extractor->getTrackMetaData(i); 942d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 943d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber const char *mime; 944d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber CHECK(meta->findCString(kKeyMIMEType, &mime)); 945d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 946d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber bool useTrack = false; 947d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber if (!strncasecmp(mime, "audio/", 6) && !haveAudio) { 948d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber useTrack = true; 949d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber haveAudio = true; 950d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber } else if (!strncasecmp(mime, "video/", 6) && !haveVideo) { 951d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber useTrack = true; 952d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber haveVideo = true; 953d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber } 954d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 955d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber if (!useTrack) { 956d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber continue; 957d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber } 958d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 959d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber sp<MediaSource> source = extractor->getTrack(i); 960d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 961d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber ssize_t index = mSerializer->addSource(source); 962d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber CHECK_GE(index, 0); 963d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 964d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber sp<AMessage> format; 965d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber status_t err = convertMetaDataToMessage(source->getFormat(), &format); 966d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber CHECK_EQ(err, (status_t)OK); 967d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 968d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber mTracks.add(index, new Track(format)); 969d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber } 970d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber CHECK(haveAudio || haveVideo); 971e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber#endif 972d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 973e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber return OK; 974e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber} 975d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 976e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huberstatus_t WifiDisplaySource::PlaybackSession::addSource( 977e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber bool isVideo, const sp<MediaSource> &source, size_t *numInputBuffers) { 978e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber#if USE_SERIALIZER 979e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber if (mSerializer == NULL) { 980e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber mSerializerLooper = new ALooper; 981e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber mSerializerLooper->setName("serializer_looper"); 982e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber mSerializerLooper->start(); 983e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber 984e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber sp<AMessage> msg = new AMessage(kWhatSerializerNotify, id()); 985e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber mSerializer = new Serializer( 986e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber false /* throttled */, msg); 987e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber 988e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber mSerializerLooper->registerHandler(mSerializer); 989e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber } 990d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber#else 991e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber sp<ALooper> pullLooper = new ALooper; 992e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber pullLooper->setName("pull_looper"); 993e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber 994e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber pullLooper->start( 995e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber false /* runOnCallingThread */, 996e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber false /* canCallJava */, 997e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber PRIORITY_DEFAULT); 998d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber#endif 999d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 1000e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber sp<ALooper> codecLooper = new ALooper; 1001e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber codecLooper->setName("codec_looper"); 1002e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber 1003e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber codecLooper->start( 1004e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber false /* runOnCallingThread */, 1005e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber false /* canCallJava */, 1006e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber PRIORITY_DEFAULT); 1007e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber 1008e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber size_t trackIndex; 1009e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber 1010e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber sp<AMessage> notify; 1011e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber 1012e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber#if USE_SERIALIZER 1013e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber trackIndex = mSerializer->addSource(source); 1014e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber#else 1015e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber trackIndex = mTracks.size(); 1016e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber 1017e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber notify = new AMessage(kWhatSerializerNotify, id()); 1018e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber notify->setSize("trackIndex", trackIndex); 1019e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber sp<MediaPuller> puller = new MediaPuller(source, notify); 1020e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber pullLooper->registerHandler(puller); 1021e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber#endif 1022d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 1023d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber sp<AMessage> format; 1024d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber status_t err = convertMetaDataToMessage(source->getFormat(), &format); 1025d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber CHECK_EQ(err, (status_t)OK); 1026d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 1027e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber if (isVideo) { 1028e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber format->setInt32("store-metadata-in-buffers", true); 1029d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 1030e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber format->setInt32( 1031e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber "color-format", OMX_COLOR_FormatAndroidOpaque); 1032e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber } 1033d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 1034e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber notify = new AMessage(kWhatConverterNotify, id()); 1035e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber notify->setSize("trackIndex", trackIndex); 1036d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 1037d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber sp<Converter> converter = 1038e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber new Converter(notify, codecLooper, format); 103966e72bc85fb762876baff60ef29de729da93cf26Andreas Huber CHECK_EQ(converter->initCheck(), (status_t)OK); 104066e72bc85fb762876baff60ef29de729da93cf26Andreas Huber 1041d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber looper()->registerHandler(converter); 1042d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 1043e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber if (numInputBuffers != NULL) { 1044e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber *numInputBuffers = converter->getInputBufferCount(); 1045e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber } 104666e72bc85fb762876baff60ef29de729da93cf26Andreas Huber 1047e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber#if USE_SERIALIZER 1048e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber mTracks.add(trackIndex, new Track(NULL, codecLooper, NULL, converter)); 1049e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber#else 1050e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber mTracks.add(trackIndex, new Track(pullLooper, codecLooper, puller, converter)); 1051e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber#endif 1052e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber 1053e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber if (isVideo) { 1054e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber mVideoTrackIndex = trackIndex; 1055e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber } 1056e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber 1057e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber return OK; 1058e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber} 1059e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber 1060e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huberstatus_t WifiDisplaySource::PlaybackSession::addVideoSource() { 1061e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber sp<SurfaceMediaSource> source = new SurfaceMediaSource(width(), height()); 1062e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber 1063e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber sp<MediaSource> videoSource = 1064e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber new RepeaterSource(source, 30.0 /* rateHz */); 1065e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber 1066e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber size_t numInputBuffers; 1067e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber status_t err = addSource(true /* isVideo */, videoSource, &numInputBuffers); 1068e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber 1069e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber if (err != OK) { 1070e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber return err; 1071e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber } 107266e72bc85fb762876baff60ef29de729da93cf26Andreas Huber 107366e72bc85fb762876baff60ef29de729da93cf26Andreas Huber // Add one reference to account for the serializer. 10745a832f87b680ead3606c4448a0a82c0e556d1b93Andreas Huber err = source->setMaxAcquiredBufferCount(numInputBuffers); 107566e72bc85fb762876baff60ef29de729da93cf26Andreas Huber CHECK_EQ(err, (status_t)OK); 107666e72bc85fb762876baff60ef29de729da93cf26Andreas Huber 10770b73d4730202fcad53aefc4314a06e7b95f442f0Andreas Huber mBufferQueue = source->getBufferQueue(); 10780b73d4730202fcad53aefc4314a06e7b95f442f0Andreas Huber 10790b73d4730202fcad53aefc4314a06e7b95f442f0Andreas Huber if (mLegacyMode) { 1080e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber sp<IServiceManager> sm = defaultServiceManager(); 1081e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber sp<IBinder> binder = sm->getService(String16("SurfaceFlinger")); 1082e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber sp<ISurfaceComposer> service = interface_cast<ISurfaceComposer>(binder); 1083e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber CHECK(service != NULL); 1084e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber 10850b73d4730202fcad53aefc4314a06e7b95f442f0Andreas Huber service->connectDisplay(mBufferQueue); 10860b73d4730202fcad53aefc4314a06e7b95f442f0Andreas Huber } 1087d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 1088e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber return OK; 1089e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber} 1090e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber 1091e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huberstatus_t WifiDisplaySource::PlaybackSession::addAudioSource() { 1092082830f92373a1b9e512dbbfb940187ffa1c2c6fAndreas Huber sp<AudioSource> audioSource = new AudioSource( 10931646a0fed94c30a44128b3c379736def4b332033Andreas Huber AUDIO_SOURCE_REMOTE_SUBMIX, 1094082830f92373a1b9e512dbbfb940187ffa1c2c6fAndreas Huber 48000 /* sampleRate */, 10951646a0fed94c30a44128b3c379736def4b332033Andreas Huber 2 /* channelCount */); 1096082830f92373a1b9e512dbbfb940187ffa1c2c6fAndreas Huber 10977977e85f7287f2b0e7a5de94e853e6073736e03bAndreas Huber if (audioSource->initCheck() == OK) { 10987977e85f7287f2b0e7a5de94e853e6073736e03bAndreas Huber audioSource->setUseLooperTime(true); 1099082830f92373a1b9e512dbbfb940187ffa1c2c6fAndreas Huber 1100e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber return addSource( 1101e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber false /* isVideo */, audioSource, NULL /* numInputBuffers */); 11027977e85f7287f2b0e7a5de94e853e6073736e03bAndreas Huber } 1103e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber 1104e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber ALOGW("Unable to instantiate audio source"); 1105082830f92373a1b9e512dbbfb940187ffa1c2c6fAndreas Huber 1106d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber return OK; 1107d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber} 1108d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 11090b73d4730202fcad53aefc4314a06e7b95f442f0Andreas Hubersp<ISurfaceTexture> WifiDisplaySource::PlaybackSession::getSurfaceTexture() { 11100b73d4730202fcad53aefc4314a06e7b95f442f0Andreas Huber return mBufferQueue; 11110b73d4730202fcad53aefc4314a06e7b95f442f0Andreas Huber} 11120b73d4730202fcad53aefc4314a06e7b95f442f0Andreas Huber 11130b73d4730202fcad53aefc4314a06e7b95f442f0Andreas Huberint32_t WifiDisplaySource::PlaybackSession::width() const { 11147977e85f7287f2b0e7a5de94e853e6073736e03bAndreas Huber return mLegacyMode ? 720 : 1280; 11150b73d4730202fcad53aefc4314a06e7b95f442f0Andreas Huber} 11160b73d4730202fcad53aefc4314a06e7b95f442f0Andreas Huber 11170b73d4730202fcad53aefc4314a06e7b95f442f0Andreas Huberint32_t WifiDisplaySource::PlaybackSession::height() const { 11187977e85f7287f2b0e7a5de94e853e6073736e03bAndreas Huber return mLegacyMode ? 1280 : 720; 11190b73d4730202fcad53aefc4314a06e7b95f442f0Andreas Huber} 11200b73d4730202fcad53aefc4314a06e7b95f442f0Andreas Huber 1121d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Hubervoid WifiDisplaySource::PlaybackSession::scheduleSendSR() { 1122d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber if (mSendSRPending) { 1123d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber return; 1124d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber } 1125d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 1126d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber mSendSRPending = true; 1127d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber (new AMessage(kWhatSendSR, id()))->post(kSendSRIntervalUs); 1128d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber} 1129d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 1130d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Hubervoid WifiDisplaySource::PlaybackSession::addSR(const sp<ABuffer> &buffer) { 1131d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber uint8_t *data = buffer->data() + buffer->size(); 1132d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 1133d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber // TODO: Use macros/utility functions to clean up all the bitshifts below. 1134d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 1135d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber data[0] = 0x80 | 0; 1136d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber data[1] = 200; // SR 1137d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber data[2] = 0; 1138d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber data[3] = 6; 1139d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber data[4] = kSourceID >> 24; 1140d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber data[5] = (kSourceID >> 16) & 0xff; 1141d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber data[6] = (kSourceID >> 8) & 0xff; 1142d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber data[7] = kSourceID & 0xff; 1143d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 1144d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber data[8] = mLastNTPTime >> (64 - 8); 1145d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber data[9] = (mLastNTPTime >> (64 - 16)) & 0xff; 1146d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber data[10] = (mLastNTPTime >> (64 - 24)) & 0xff; 1147d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber data[11] = (mLastNTPTime >> 32) & 0xff; 1148d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber data[12] = (mLastNTPTime >> 24) & 0xff; 1149d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber data[13] = (mLastNTPTime >> 16) & 0xff; 1150d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber data[14] = (mLastNTPTime >> 8) & 0xff; 1151d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber data[15] = mLastNTPTime & 0xff; 1152d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 1153d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber data[16] = (mLastRTPTime >> 24) & 0xff; 1154d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber data[17] = (mLastRTPTime >> 16) & 0xff; 1155d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber data[18] = (mLastRTPTime >> 8) & 0xff; 1156d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber data[19] = mLastRTPTime & 0xff; 1157d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 1158d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber data[20] = mNumRTPSent >> 24; 1159d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber data[21] = (mNumRTPSent >> 16) & 0xff; 1160d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber data[22] = (mNumRTPSent >> 8) & 0xff; 1161d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber data[23] = mNumRTPSent & 0xff; 1162d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 1163d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber data[24] = mNumRTPOctetsSent >> 24; 1164d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber data[25] = (mNumRTPOctetsSent >> 16) & 0xff; 1165d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber data[26] = (mNumRTPOctetsSent >> 8) & 0xff; 1166d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber data[27] = mNumRTPOctetsSent & 0xff; 1167d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 1168d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber buffer->setRange(buffer->offset(), buffer->size() + 28); 1169d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber} 1170d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 1171d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Hubervoid WifiDisplaySource::PlaybackSession::addSDES(const sp<ABuffer> &buffer) { 1172d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber uint8_t *data = buffer->data() + buffer->size(); 1173d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber data[0] = 0x80 | 1; 1174d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber data[1] = 202; // SDES 1175d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber data[4] = kSourceID >> 24; 1176d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber data[5] = (kSourceID >> 16) & 0xff; 1177d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber data[6] = (kSourceID >> 8) & 0xff; 1178d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber data[7] = kSourceID & 0xff; 1179d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 1180d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber size_t offset = 8; 1181d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 1182d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber data[offset++] = 1; // CNAME 1183d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 1184d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber static const char *kCNAME = "someone@somewhere"; 1185d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber data[offset++] = strlen(kCNAME); 1186d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 1187d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber memcpy(&data[offset], kCNAME, strlen(kCNAME)); 1188d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber offset += strlen(kCNAME); 1189d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 1190d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber data[offset++] = 7; // NOTE 1191d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 1192d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber static const char *kNOTE = "Hell's frozen over."; 1193d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber data[offset++] = strlen(kNOTE); 1194d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 1195d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber memcpy(&data[offset], kNOTE, strlen(kNOTE)); 1196d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber offset += strlen(kNOTE); 1197d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 1198d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber data[offset++] = 0; 1199d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 1200d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber if ((offset % 4) > 0) { 1201d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber size_t count = 4 - (offset % 4); 1202d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber switch (count) { 1203d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber case 3: 1204d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber data[offset++] = 0; 1205d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber case 2: 1206d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber data[offset++] = 0; 1207d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber case 1: 1208d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber data[offset++] = 0; 1209d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber } 1210d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber } 1211d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 1212d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber size_t numWords = (offset / 4) - 1; 1213d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber data[2] = numWords >> 8; 1214d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber data[3] = numWords & 0xff; 1215d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 1216d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber buffer->setRange(buffer->offset(), buffer->size() + offset); 1217d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber} 1218d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 1219d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber// static 1220d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huberuint64_t WifiDisplaySource::PlaybackSession::GetNowNTP() { 1221d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber uint64_t nowUs = ALooper::GetNowUs(); 1222d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 1223d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber nowUs += ((70ll * 365 + 17) * 24) * 60 * 60 * 1000000ll; 1224d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 1225d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber uint64_t hi = nowUs / 1000000ll; 1226d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber uint64_t lo = ((1ll << 32) * (nowUs % 1000000ll)) / 1000000ll; 1227d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 1228d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber return (hi << 32) | lo; 1229d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber} 1230d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 1231d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Hubervoid WifiDisplaySource::PlaybackSession::onSendSR() { 1232d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber sp<ABuffer> buffer = new ABuffer(1500); 1233d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber buffer->setRange(0, 0); 1234d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 1235d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber addSR(buffer); 1236d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber addSDES(buffer); 1237d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 1238bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber if (mTransportMode == TRANSPORT_TCP_INTERLEAVED) { 1239d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber sp<AMessage> notify = mNotify->dup(); 1240d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber notify->setInt32("what", kWhatBinaryData); 1241d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber notify->setInt32("channel", mRTCPChannel); 1242d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber notify->setBuffer("data", buffer); 1243d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber notify->post(); 1244d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber } else { 1245bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber sendPacket(mRTCPSessionID, buffer->data(), buffer->size()); 1246d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber } 1247d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 1248d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber ++mNumSRsSent; 1249d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber} 1250d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 1251d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huberssize_t WifiDisplaySource::PlaybackSession::appendTSData( 1252d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber const void *data, size_t size, bool timeDiscontinuity, bool flush) { 1253d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber CHECK_EQ(size, 188); 1254d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 1255d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber CHECK_LE(mTSQueue->size() + size, mTSQueue->capacity()); 1256d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 1257d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber memcpy(mTSQueue->data() + mTSQueue->size(), data, size); 1258d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber mTSQueue->setRange(0, mTSQueue->size() + size); 1259d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 1260d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber if (flush || mTSQueue->size() == mTSQueue->capacity()) { 1261d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber // flush 1262d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 1263d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber int64_t nowUs = ALooper::GetNowUs(); 1264d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber if (mFirstPacketTimeUs < 0ll) { 1265d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber mFirstPacketTimeUs = nowUs; 1266d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber } 1267d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 1268d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber // 90kHz time scale 1269d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber uint32_t rtpTime = ((nowUs - mFirstPacketTimeUs) * 9ll) / 100ll; 1270d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 1271d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber uint8_t *rtp = mTSQueue->data(); 1272d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber rtp[0] = 0x80; 1273d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber rtp[1] = 33 | (timeDiscontinuity ? (1 << 7) : 0); // M-bit 1274d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber rtp[2] = (mRTPSeqNo >> 8) & 0xff; 1275d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber rtp[3] = mRTPSeqNo & 0xff; 1276d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber rtp[4] = rtpTime >> 24; 1277d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber rtp[5] = (rtpTime >> 16) & 0xff; 1278d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber rtp[6] = (rtpTime >> 8) & 0xff; 1279d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber rtp[7] = rtpTime & 0xff; 1280d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber rtp[8] = kSourceID >> 24; 1281d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber rtp[9] = (kSourceID >> 16) & 0xff; 1282d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber rtp[10] = (kSourceID >> 8) & 0xff; 1283d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber rtp[11] = kSourceID & 0xff; 1284d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 1285d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber ++mRTPSeqNo; 1286d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber ++mNumRTPSent; 1287d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber mNumRTPOctetsSent += mTSQueue->size() - 12; 1288d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 1289d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber mLastRTPTime = rtpTime; 1290d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber mLastNTPTime = GetNowNTP(); 1291d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 1292bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber if (mTransportMode == TRANSPORT_TCP_INTERLEAVED) { 1293d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber sp<AMessage> notify = mNotify->dup(); 1294d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber notify->setInt32("what", kWhatBinaryData); 1295d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 1296d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber sp<ABuffer> data = new ABuffer(mTSQueue->size()); 1297d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber memcpy(data->data(), rtp, mTSQueue->size()); 1298d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 1299d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber notify->setInt32("channel", mRTPChannel); 1300d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber notify->setBuffer("data", data); 1301d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber notify->post(); 1302d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber } else { 1303bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber sendPacket(mRTPSessionID, rtp, mTSQueue->size()); 1304dca352880e210e0ca0ff39de074540d3640ecfabAndreas Huber 1305dca352880e210e0ca0ff39de074540d3640ecfabAndreas Huber mTotalBytesSent += mTSQueue->size(); 1306dca352880e210e0ca0ff39de074540d3640ecfabAndreas Huber int64_t delayUs = ALooper::GetNowUs() - mFirstPacketTimeUs; 1307dca352880e210e0ca0ff39de074540d3640ecfabAndreas Huber 1308dca352880e210e0ca0ff39de074540d3640ecfabAndreas Huber if (delayUs > 0ll) { 1309dca352880e210e0ca0ff39de074540d3640ecfabAndreas Huber ALOGV("approx. net bandwidth used: %.2f Mbit/sec", 1310dca352880e210e0ca0ff39de074540d3640ecfabAndreas Huber mTotalBytesSent * 8.0 / delayUs); 1311dca352880e210e0ca0ff39de074540d3640ecfabAndreas Huber } 1312d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber } 1313d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 1314d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber mTSQueue->setInt32Data(mRTPSeqNo - 1); 1315d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber mHistory.push_back(mTSQueue); 1316d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber ++mHistoryLength; 1317d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 1318d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber if (mHistoryLength > kMaxHistoryLength) { 1319d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber mTSQueue = *mHistory.begin(); 1320d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber mHistory.erase(mHistory.begin()); 1321d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 1322d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber --mHistoryLength; 1323d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber } else { 1324d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber mTSQueue = new ABuffer(12 + kMaxNumTSPacketsPerRTPPacket * 188); 1325d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber } 1326d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 1327d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber mTSQueue->setRange(0, 12); 1328d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber } 1329d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 1330d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber return size; 1331d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber} 1332d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 1333d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huberstatus_t WifiDisplaySource::PlaybackSession::parseRTCP( 1334d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber const sp<ABuffer> &buffer) { 1335d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber const uint8_t *data = buffer->data(); 1336d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber size_t size = buffer->size(); 1337d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 1338d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber while (size > 0) { 1339d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber if (size < 8) { 1340d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber // Too short to be a valid RTCP header 1341d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber return ERROR_MALFORMED; 1342d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber } 1343d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 1344d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber if ((data[0] >> 6) != 2) { 1345d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber // Unsupported version. 1346d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber return ERROR_UNSUPPORTED; 1347d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber } 1348d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 1349d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber if (data[0] & 0x20) { 1350d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber // Padding present. 1351d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 1352d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber size_t paddingLength = data[size - 1]; 1353d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 1354d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber if (paddingLength + 12 > size) { 1355d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber // If we removed this much padding we'd end up with something 1356d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber // that's too short to be a valid RTP header. 1357d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber return ERROR_MALFORMED; 1358d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber } 1359d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 1360d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber size -= paddingLength; 1361d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber } 1362d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 1363d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber size_t headerLength = 4 * (data[2] << 8 | data[3]) + 4; 1364d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 1365d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber if (size < headerLength) { 1366d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber // Only received a partial packet? 1367d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber return ERROR_MALFORMED; 1368d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber } 1369d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 1370d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber switch (data[1]) { 1371d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber case 200: 1372d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber case 201: // RR 1373d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber case 202: // SDES 1374d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber case 203: 1375d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber case 204: // APP 1376d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber break; 1377d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 1378efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber#if ENABLE_RETRANSMISSION 1379d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber case 205: // TSFB (transport layer specific feedback) 1380d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber parseTSFB(data, headerLength); 1381d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber break; 1382efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber#endif 1383d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 1384d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber case 206: // PSFB (payload specific feedback) 1385d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber hexdump(data, headerLength); 1386d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber break; 1387d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 1388d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber default: 1389d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber { 1390d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber ALOGW("Unknown RTCP packet type %u of size %d", 1391d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber (unsigned)data[1], headerLength); 1392d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber break; 1393d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber } 1394d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber } 1395d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 1396d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber data += headerLength; 1397d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber size -= headerLength; 1398d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber } 1399d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 1400d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber return OK; 1401d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber} 1402d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 1403efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber#if ENABLE_RETRANSMISSION 1404d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huberstatus_t WifiDisplaySource::PlaybackSession::parseTSFB( 1405d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber const uint8_t *data, size_t size) { 1406d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber if ((data[0] & 0x1f) != 1) { 1407d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber return ERROR_UNSUPPORTED; // We only support NACK for now. 1408d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber } 1409d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 1410d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber uint32_t srcId = U32_AT(&data[8]); 1411d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber if (srcId != kSourceID) { 1412d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber return ERROR_MALFORMED; 1413d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber } 1414d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 1415d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber for (size_t i = 12; i < size; i += 4) { 1416d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber uint16_t seqNo = U16_AT(&data[i]); 1417d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber uint16_t blp = U16_AT(&data[i + 2]); 1418d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 1419d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber List<sp<ABuffer> >::iterator it = mHistory.begin(); 1420efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber bool foundSeqNo = false; 1421d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber while (it != mHistory.end()) { 1422d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber const sp<ABuffer> &buffer = *it; 1423d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 1424d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber uint16_t bufferSeqNo = buffer->int32Data() & 0xffff; 1425d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 1426efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber bool retransmit = false; 1427d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber if (bufferSeqNo == seqNo) { 1428efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber retransmit = true; 1429efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber } else if (blp != 0) { 1430efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber for (size_t i = 0; i < 16; ++i) { 1431efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber if ((blp & (1 << i)) 1432efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber && (bufferSeqNo == ((seqNo + i + 1) & 0xffff))) { 1433efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber blp &= ~(1 << i); 1434efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber retransmit = true; 1435efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber } 1436efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber } 1437efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber } 1438d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 1439efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber if (retransmit) { 1440efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber ALOGI("retransmitting seqNo %d", bufferSeqNo); 1441efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber 1442efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber sp<ABuffer> retransRTP = new ABuffer(2 + buffer->size()); 1443efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber uint8_t *rtp = retransRTP->data(); 1444efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber memcpy(rtp, buffer->data(), 12); 1445efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber rtp[2] = (mRTPRetransmissionSeqNo >> 8) & 0xff; 1446efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber rtp[3] = mRTPRetransmissionSeqNo & 0xff; 1447efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber rtp[12] = (bufferSeqNo >> 8) & 0xff; 1448efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber rtp[13] = bufferSeqNo & 0xff; 1449efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber memcpy(&rtp[14], buffer->data() + 12, buffer->size() - 12); 1450efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber 1451efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber ++mRTPRetransmissionSeqNo; 1452efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber 1453efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber sendPacket( 1454efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber mRTPRetransmissionSessionID, 1455efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber retransRTP->data(), retransRTP->size()); 1456efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber 1457efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber if (bufferSeqNo == seqNo) { 1458efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber foundSeqNo = true; 1459efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber } 1460efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber 1461efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber if (foundSeqNo && blp == 0) { 1462efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber break; 1463efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber } 1464d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber } 1465d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 1466d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber ++it; 1467d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber } 1468d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 1469efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber if (!foundSeqNo || blp != 0) { 1470efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber ALOGI("Some sequence numbers were no longer available for " 1471efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber "retransmission"); 1472d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber } 1473d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber } 1474d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 1475d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber return OK; 1476d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber} 1477efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber#endif 1478d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 1479496238cc7551d414067dcbbb4fe3bd801f205f95Andreas Hubervoid WifiDisplaySource::PlaybackSession::requestIDRFrame() { 1480496238cc7551d414067dcbbb4fe3bd801f205f95Andreas Huber for (size_t i = 0; i < mTracks.size(); ++i) { 1481496238cc7551d414067dcbbb4fe3bd801f205f95Andreas Huber const sp<Track> &track = mTracks.valueAt(i); 1482496238cc7551d414067dcbbb4fe3bd801f205f95Andreas Huber 1483496238cc7551d414067dcbbb4fe3bd801f205f95Andreas Huber track->converter()->requestIDRFrame(); 1484496238cc7551d414067dcbbb4fe3bd801f205f95Andreas Huber } 1485496238cc7551d414067dcbbb4fe3bd801f205f95Andreas Huber} 1486496238cc7551d414067dcbbb4fe3bd801f205f95Andreas Huber 1487bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huberstatus_t WifiDisplaySource::PlaybackSession::sendPacket( 1488bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber int32_t sessionID, const void *data, size_t size) { 1489bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber return mNetSession->sendRequest(sessionID, data, size); 1490bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber} 1491bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber 1492d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber} // namespace android 1493d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 1494