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"
2690a92053219ae50ddf4bb54e3d54db2d309e2b8dAndreas Huber#include "Sender.h"
27d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber#include "TSPacketizer.h"
28e399acc9d9f3b7af72106c4209e4bb40de37aa6aAndreas Huber#include "include/avc_utils.h"
29d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber
30d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber#include <binder/IServiceManager.h>
31d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber#include <gui/ISurfaceComposer.h>
32d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber#include <gui/SurfaceComposerClient.h>
33b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber#include <media/IHDCP.h>
34e399acc9d9f3b7af72106c4209e4bb40de37aa6aAndreas Huber#include <media/stagefright/foundation/ABitReader.h>
35d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber#include <media/stagefright/foundation/ABuffer.h>
36d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber#include <media/stagefright/foundation/ADebug.h>
37d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber#include <media/stagefright/foundation/AMessage.h>
38d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber#include <media/stagefright/foundation/hexdump.h>
39082830f92373a1b9e512dbbfb940187ffa1c2c6fAndreas Huber#include <media/stagefright/AudioSource.h>
40d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber#include <media/stagefright/DataSource.h>
41d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber#include <media/stagefright/MediaDefs.h>
42d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber#include <media/stagefright/MediaErrors.h>
43d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber#include <media/stagefright/MediaExtractor.h>
44d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber#include <media/stagefright/MediaSource.h>
45d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber#include <media/stagefright/MetaData.h>
46d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber#include <media/stagefright/MPEG2TSWriter.h>
47d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber#include <media/stagefright/SurfaceMediaSource.h>
48d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber#include <media/stagefright/Utils.h>
49d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber
50d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber#include <OMX_IVCommon.h>
51d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber
52d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Hubernamespace android {
53d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber
5496fc6cc65ca93009a759a3a874b82a35771b9714Andreas Huberstruct WifiDisplaySource::PlaybackSession::Track : public AHandler {
5596fc6cc65ca93009a759a3a874b82a35771b9714Andreas Huber    enum {
5696fc6cc65ca93009a759a3a874b82a35771b9714Andreas Huber        kWhatStopped,
5796fc6cc65ca93009a759a3a874b82a35771b9714Andreas Huber    };
5896fc6cc65ca93009a759a3a874b82a35771b9714Andreas Huber
5996fc6cc65ca93009a759a3a874b82a35771b9714Andreas Huber    Track(const sp<AMessage> &notify,
6096fc6cc65ca93009a759a3a874b82a35771b9714Andreas Huber          const sp<ALooper> &pullLooper,
61e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber          const sp<ALooper> &codecLooper,
62e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber          const sp<MediaPuller> &mediaPuller,
63e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber          const sp<Converter> &converter);
64e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber
654a8b9a2363b7b7b4f98022e6d9aae8b8aa8e35e5Andreas Huber    void setRepeaterSource(const sp<RepeaterSource> &source);
664a8b9a2363b7b7b4f98022e6d9aae8b8aa8e35e5Andreas Huber
67d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber    sp<AMessage> getFormat();
68b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber    bool isAudio() const;
69d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber
70d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber    const sp<Converter> &converter() const;
71d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber    ssize_t packetizerTrackIndex() const;
72d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber
73d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber    void setPacketizerTrackIndex(size_t index);
74d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber
75e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber    status_t start();
7696fc6cc65ca93009a759a3a874b82a35771b9714Andreas Huber    void stopAsync();
7796fc6cc65ca93009a759a3a874b82a35771b9714Andreas Huber
7828e17ed7e2fbb254fb99481b74db85e427c905eeAndreas Huber    void queueAccessUnit(const sp<ABuffer> &accessUnit);
7928e17ed7e2fbb254fb99481b74db85e427c905eeAndreas Huber    sp<ABuffer> dequeueAccessUnit();
8028e17ed7e2fbb254fb99481b74db85e427c905eeAndreas Huber
8190a92053219ae50ddf4bb54e3d54db2d309e2b8dAndreas Huber    bool hasOutputBuffer(int64_t *timeUs) const;
8290a92053219ae50ddf4bb54e3d54db2d309e2b8dAndreas Huber    void queueOutputBuffer(const sp<ABuffer> &accessUnit);
8390a92053219ae50ddf4bb54e3d54db2d309e2b8dAndreas Huber    sp<ABuffer> dequeueOutputBuffer();
8490a92053219ae50ddf4bb54e3d54db2d309e2b8dAndreas Huber    bool isSuspended() const;
8590a92053219ae50ddf4bb54e3d54db2d309e2b8dAndreas Huber
8690a92053219ae50ddf4bb54e3d54db2d309e2b8dAndreas Huber    size_t countQueuedOutputBuffers() const {
8790a92053219ae50ddf4bb54e3d54db2d309e2b8dAndreas Huber        return mQueuedOutputBuffers.size();
8890a92053219ae50ddf4bb54e3d54db2d309e2b8dAndreas Huber    }
8990a92053219ae50ddf4bb54e3d54db2d309e2b8dAndreas Huber
904a8b9a2363b7b7b4f98022e6d9aae8b8aa8e35e5Andreas Huber    void requestIDRFrame();
914a8b9a2363b7b7b4f98022e6d9aae8b8aa8e35e5Andreas Huber
92d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huberprotected:
9396fc6cc65ca93009a759a3a874b82a35771b9714Andreas Huber    virtual void onMessageReceived(const sp<AMessage> &msg);
94d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber    virtual ~Track();
95d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber
96d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huberprivate:
9796fc6cc65ca93009a759a3a874b82a35771b9714Andreas Huber    enum {
9896fc6cc65ca93009a759a3a874b82a35771b9714Andreas Huber        kWhatMediaPullerStopped,
9996fc6cc65ca93009a759a3a874b82a35771b9714Andreas Huber    };
10096fc6cc65ca93009a759a3a874b82a35771b9714Andreas Huber
10196fc6cc65ca93009a759a3a874b82a35771b9714Andreas Huber    sp<AMessage> mNotify;
102e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber    sp<ALooper> mPullLooper;
103e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber    sp<ALooper> mCodecLooper;
104e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber    sp<MediaPuller> mMediaPuller;
105d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber    sp<Converter> mConverter;
106e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber    bool mStarted;
107d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber    ssize_t mPacketizerTrackIndex;
108b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber    bool mIsAudio;
10928e17ed7e2fbb254fb99481b74db85e427c905eeAndreas Huber    List<sp<ABuffer> > mQueuedAccessUnits;
1104a8b9a2363b7b7b4f98022e6d9aae8b8aa8e35e5Andreas Huber    sp<RepeaterSource> mRepeaterSource;
11190a92053219ae50ddf4bb54e3d54db2d309e2b8dAndreas Huber    List<sp<ABuffer> > mQueuedOutputBuffers;
11290a92053219ae50ddf4bb54e3d54db2d309e2b8dAndreas Huber    int64_t mLastOutputBufferQueuedTimeUs;
113b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber
114b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber    static bool IsAudioFormat(const sp<AMessage> &format);
115d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber
116d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber    DISALLOW_EVIL_CONSTRUCTORS(Track);
117d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber};
118d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber
119e1957358f11031a554c57d4fb46988dd6044acc1Andreas HuberWifiDisplaySource::PlaybackSession::Track::Track(
12096fc6cc65ca93009a759a3a874b82a35771b9714Andreas Huber        const sp<AMessage> &notify,
121e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber        const sp<ALooper> &pullLooper,
122e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber        const sp<ALooper> &codecLooper,
123e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber        const sp<MediaPuller> &mediaPuller,
124e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber        const sp<Converter> &converter)
12596fc6cc65ca93009a759a3a874b82a35771b9714Andreas Huber    : mNotify(notify),
12696fc6cc65ca93009a759a3a874b82a35771b9714Andreas Huber      mPullLooper(pullLooper),
127e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber      mCodecLooper(codecLooper),
128e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber      mMediaPuller(mediaPuller),
129e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber      mConverter(converter),
130e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber      mStarted(false),
131b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber      mPacketizerTrackIndex(-1),
13290a92053219ae50ddf4bb54e3d54db2d309e2b8dAndreas Huber      mIsAudio(IsAudioFormat(mConverter->getOutputFormat())),
13390a92053219ae50ddf4bb54e3d54db2d309e2b8dAndreas Huber      mLastOutputBufferQueuedTimeUs(-1ll) {
134d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber}
135d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber
136d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas HuberWifiDisplaySource::PlaybackSession::Track::~Track() {
13796fc6cc65ca93009a759a3a874b82a35771b9714Andreas Huber    CHECK(!mStarted);
138d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber}
139d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber
140b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber// static
141b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huberbool WifiDisplaySource::PlaybackSession::Track::IsAudioFormat(
142b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber        const sp<AMessage> &format) {
143b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber    AString mime;
144b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber    CHECK(format->findString("mime", &mime));
145b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber
146b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber    return !strncasecmp(mime.c_str(), "audio/", 6);
147b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber}
148b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber
149d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Hubersp<AMessage> WifiDisplaySource::PlaybackSession::Track::getFormat() {
150d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber    return mConverter->getOutputFormat();
151d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber}
152d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber
153b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huberbool WifiDisplaySource::PlaybackSession::Track::isAudio() const {
154b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber    return mIsAudio;
155b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber}
156b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber
157d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huberconst sp<Converter> &WifiDisplaySource::PlaybackSession::Track::converter() const {
158d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber    return mConverter;
159d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber}
160d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber
161d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huberssize_t WifiDisplaySource::PlaybackSession::Track::packetizerTrackIndex() const {
162d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber    return mPacketizerTrackIndex;
163d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber}
164d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber
165d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Hubervoid WifiDisplaySource::PlaybackSession::Track::setPacketizerTrackIndex(size_t index) {
166d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber    CHECK_LT(mPacketizerTrackIndex, 0);
167d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber    mPacketizerTrackIndex = index;
168d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber}
169d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber
170e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huberstatus_t WifiDisplaySource::PlaybackSession::Track::start() {
171ef7d3793fa9bbfb25253626ede9a020ee9280a17Andreas Huber    ALOGV("Track::start isAudio=%d", mIsAudio);
172ef7d3793fa9bbfb25253626ede9a020ee9280a17Andreas Huber
17396fc6cc65ca93009a759a3a874b82a35771b9714Andreas Huber    CHECK(!mStarted);
174e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber
175e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber    status_t err = OK;
176e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber
177e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber    if (mMediaPuller != NULL) {
178e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber        err = mMediaPuller->start();
179e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber    }
180e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber
181e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber    if (err == OK) {
182e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber        mStarted = true;
183e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber    }
184e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber
185e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber    return err;
186e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber}
187e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber
18896fc6cc65ca93009a759a3a874b82a35771b9714Andreas Hubervoid WifiDisplaySource::PlaybackSession::Track::stopAsync() {
18996fc6cc65ca93009a759a3a874b82a35771b9714Andreas Huber    ALOGV("Track::stopAsync isAudio=%d", mIsAudio);
190ef7d3793fa9bbfb25253626ede9a020ee9280a17Andreas Huber
19196fc6cc65ca93009a759a3a874b82a35771b9714Andreas Huber    mConverter->shutdownAsync();
19296fc6cc65ca93009a759a3a874b82a35771b9714Andreas Huber
19396fc6cc65ca93009a759a3a874b82a35771b9714Andreas Huber    sp<AMessage> msg = new AMessage(kWhatMediaPullerStopped, id());
194e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber
195ad0d97c7cf620e96a0b088dd9461645a3f8900b7Andreas Huber    if (mStarted && mMediaPuller != NULL) {
1964a8b9a2363b7b7b4f98022e6d9aae8b8aa8e35e5Andreas Huber        if (mRepeaterSource != NULL) {
1974a8b9a2363b7b7b4f98022e6d9aae8b8aa8e35e5Andreas Huber            // Let's unblock MediaPuller's MediaSource::read().
1984a8b9a2363b7b7b4f98022e6d9aae8b8aa8e35e5Andreas Huber            mRepeaterSource->wakeUp();
1994a8b9a2363b7b7b4f98022e6d9aae8b8aa8e35e5Andreas Huber        }
2004a8b9a2363b7b7b4f98022e6d9aae8b8aa8e35e5Andreas Huber
20196fc6cc65ca93009a759a3a874b82a35771b9714Andreas Huber        mMediaPuller->stopAsync(msg);
20296fc6cc65ca93009a759a3a874b82a35771b9714Andreas Huber    } else {
20396fc6cc65ca93009a759a3a874b82a35771b9714Andreas Huber        msg->post();
204e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber    }
20596fc6cc65ca93009a759a3a874b82a35771b9714Andreas Huber}
206e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber
20796fc6cc65ca93009a759a3a874b82a35771b9714Andreas Hubervoid WifiDisplaySource::PlaybackSession::Track::onMessageReceived(
20896fc6cc65ca93009a759a3a874b82a35771b9714Andreas Huber        const sp<AMessage> &msg) {
20996fc6cc65ca93009a759a3a874b82a35771b9714Andreas Huber    switch (msg->what()) {
21096fc6cc65ca93009a759a3a874b82a35771b9714Andreas Huber        case kWhatMediaPullerStopped:
21196fc6cc65ca93009a759a3a874b82a35771b9714Andreas Huber        {
21296fc6cc65ca93009a759a3a874b82a35771b9714Andreas Huber            mConverter.clear();
213a438123bd96c7faf145683876702387efe5628d9Andreas Huber
21496fc6cc65ca93009a759a3a874b82a35771b9714Andreas Huber            mStarted = false;
215e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber
21696fc6cc65ca93009a759a3a874b82a35771b9714Andreas Huber            sp<AMessage> notify = mNotify->dup();
21796fc6cc65ca93009a759a3a874b82a35771b9714Andreas Huber            notify->setInt32("what", kWhatStopped);
21896fc6cc65ca93009a759a3a874b82a35771b9714Andreas Huber            notify->post();
21977245813007cf903b4b73f5d0cd20313fbf0e510Andreas Huber
22077245813007cf903b4b73f5d0cd20313fbf0e510Andreas Huber            ALOGI("kWhatStopped %s posted", mIsAudio ? "audio" : "video");
22196fc6cc65ca93009a759a3a874b82a35771b9714Andreas Huber            break;
22296fc6cc65ca93009a759a3a874b82a35771b9714Andreas Huber        }
22396fc6cc65ca93009a759a3a874b82a35771b9714Andreas Huber
22496fc6cc65ca93009a759a3a874b82a35771b9714Andreas Huber        default:
22596fc6cc65ca93009a759a3a874b82a35771b9714Andreas Huber            TRESPASS();
22696fc6cc65ca93009a759a3a874b82a35771b9714Andreas Huber    }
227e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber}
228e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber
22928e17ed7e2fbb254fb99481b74db85e427c905eeAndreas Hubervoid WifiDisplaySource::PlaybackSession::Track::queueAccessUnit(
23028e17ed7e2fbb254fb99481b74db85e427c905eeAndreas Huber        const sp<ABuffer> &accessUnit) {
23128e17ed7e2fbb254fb99481b74db85e427c905eeAndreas Huber    mQueuedAccessUnits.push_back(accessUnit);
23228e17ed7e2fbb254fb99481b74db85e427c905eeAndreas Huber}
23328e17ed7e2fbb254fb99481b74db85e427c905eeAndreas Huber
23428e17ed7e2fbb254fb99481b74db85e427c905eeAndreas Hubersp<ABuffer> WifiDisplaySource::PlaybackSession::Track::dequeueAccessUnit() {
23528e17ed7e2fbb254fb99481b74db85e427c905eeAndreas Huber    if (mQueuedAccessUnits.empty()) {
23628e17ed7e2fbb254fb99481b74db85e427c905eeAndreas Huber        return NULL;
23728e17ed7e2fbb254fb99481b74db85e427c905eeAndreas Huber    }
23828e17ed7e2fbb254fb99481b74db85e427c905eeAndreas Huber
23928e17ed7e2fbb254fb99481b74db85e427c905eeAndreas Huber    sp<ABuffer> accessUnit = *mQueuedAccessUnits.begin();
24028e17ed7e2fbb254fb99481b74db85e427c905eeAndreas Huber    CHECK(accessUnit != NULL);
24128e17ed7e2fbb254fb99481b74db85e427c905eeAndreas Huber
24228e17ed7e2fbb254fb99481b74db85e427c905eeAndreas Huber    mQueuedAccessUnits.erase(mQueuedAccessUnits.begin());
24328e17ed7e2fbb254fb99481b74db85e427c905eeAndreas Huber
24428e17ed7e2fbb254fb99481b74db85e427c905eeAndreas Huber    return accessUnit;
24528e17ed7e2fbb254fb99481b74db85e427c905eeAndreas Huber}
24628e17ed7e2fbb254fb99481b74db85e427c905eeAndreas Huber
2474a8b9a2363b7b7b4f98022e6d9aae8b8aa8e35e5Andreas Hubervoid WifiDisplaySource::PlaybackSession::Track::setRepeaterSource(
2484a8b9a2363b7b7b4f98022e6d9aae8b8aa8e35e5Andreas Huber        const sp<RepeaterSource> &source) {
2494a8b9a2363b7b7b4f98022e6d9aae8b8aa8e35e5Andreas Huber    mRepeaterSource = source;
2504a8b9a2363b7b7b4f98022e6d9aae8b8aa8e35e5Andreas Huber}
2514a8b9a2363b7b7b4f98022e6d9aae8b8aa8e35e5Andreas Huber
2524a8b9a2363b7b7b4f98022e6d9aae8b8aa8e35e5Andreas Hubervoid WifiDisplaySource::PlaybackSession::Track::requestIDRFrame() {
2534a8b9a2363b7b7b4f98022e6d9aae8b8aa8e35e5Andreas Huber    if (mIsAudio) {
2544a8b9a2363b7b7b4f98022e6d9aae8b8aa8e35e5Andreas Huber        return;
2554a8b9a2363b7b7b4f98022e6d9aae8b8aa8e35e5Andreas Huber    }
2564a8b9a2363b7b7b4f98022e6d9aae8b8aa8e35e5Andreas Huber
2574a8b9a2363b7b7b4f98022e6d9aae8b8aa8e35e5Andreas Huber    if (mRepeaterSource != NULL) {
2584a8b9a2363b7b7b4f98022e6d9aae8b8aa8e35e5Andreas Huber        mRepeaterSource->wakeUp();
2594a8b9a2363b7b7b4f98022e6d9aae8b8aa8e35e5Andreas Huber    }
2604a8b9a2363b7b7b4f98022e6d9aae8b8aa8e35e5Andreas Huber
2614a8b9a2363b7b7b4f98022e6d9aae8b8aa8e35e5Andreas Huber    mConverter->requestIDRFrame();
2624a8b9a2363b7b7b4f98022e6d9aae8b8aa8e35e5Andreas Huber}
2634a8b9a2363b7b7b4f98022e6d9aae8b8aa8e35e5Andreas Huber
26490a92053219ae50ddf4bb54e3d54db2d309e2b8dAndreas Huberbool WifiDisplaySource::PlaybackSession::Track::hasOutputBuffer(
26590a92053219ae50ddf4bb54e3d54db2d309e2b8dAndreas Huber        int64_t *timeUs) const {
26690a92053219ae50ddf4bb54e3d54db2d309e2b8dAndreas Huber    *timeUs = 0ll;
26790a92053219ae50ddf4bb54e3d54db2d309e2b8dAndreas Huber
26890a92053219ae50ddf4bb54e3d54db2d309e2b8dAndreas Huber    if (mQueuedOutputBuffers.empty()) {
26990a92053219ae50ddf4bb54e3d54db2d309e2b8dAndreas Huber        return false;
27090a92053219ae50ddf4bb54e3d54db2d309e2b8dAndreas Huber    }
27190a92053219ae50ddf4bb54e3d54db2d309e2b8dAndreas Huber
27290a92053219ae50ddf4bb54e3d54db2d309e2b8dAndreas Huber    const sp<ABuffer> &outputBuffer = *mQueuedOutputBuffers.begin();
27390a92053219ae50ddf4bb54e3d54db2d309e2b8dAndreas Huber
27490a92053219ae50ddf4bb54e3d54db2d309e2b8dAndreas Huber    CHECK(outputBuffer->meta()->findInt64("timeUs", timeUs));
27590a92053219ae50ddf4bb54e3d54db2d309e2b8dAndreas Huber
27690a92053219ae50ddf4bb54e3d54db2d309e2b8dAndreas Huber    return true;
27790a92053219ae50ddf4bb54e3d54db2d309e2b8dAndreas Huber}
27890a92053219ae50ddf4bb54e3d54db2d309e2b8dAndreas Huber
27990a92053219ae50ddf4bb54e3d54db2d309e2b8dAndreas Hubervoid WifiDisplaySource::PlaybackSession::Track::queueOutputBuffer(
28090a92053219ae50ddf4bb54e3d54db2d309e2b8dAndreas Huber        const sp<ABuffer> &accessUnit) {
28190a92053219ae50ddf4bb54e3d54db2d309e2b8dAndreas Huber    mQueuedOutputBuffers.push_back(accessUnit);
28290a92053219ae50ddf4bb54e3d54db2d309e2b8dAndreas Huber
28390a92053219ae50ddf4bb54e3d54db2d309e2b8dAndreas Huber    mLastOutputBufferQueuedTimeUs = ALooper::GetNowUs();
28490a92053219ae50ddf4bb54e3d54db2d309e2b8dAndreas Huber}
28590a92053219ae50ddf4bb54e3d54db2d309e2b8dAndreas Huber
28690a92053219ae50ddf4bb54e3d54db2d309e2b8dAndreas Hubersp<ABuffer> WifiDisplaySource::PlaybackSession::Track::dequeueOutputBuffer() {
28790a92053219ae50ddf4bb54e3d54db2d309e2b8dAndreas Huber    CHECK(!mQueuedOutputBuffers.empty());
28890a92053219ae50ddf4bb54e3d54db2d309e2b8dAndreas Huber
28990a92053219ae50ddf4bb54e3d54db2d309e2b8dAndreas Huber    sp<ABuffer> outputBuffer = *mQueuedOutputBuffers.begin();
29090a92053219ae50ddf4bb54e3d54db2d309e2b8dAndreas Huber    mQueuedOutputBuffers.erase(mQueuedOutputBuffers.begin());
29190a92053219ae50ddf4bb54e3d54db2d309e2b8dAndreas Huber
29290a92053219ae50ddf4bb54e3d54db2d309e2b8dAndreas Huber    return outputBuffer;
29390a92053219ae50ddf4bb54e3d54db2d309e2b8dAndreas Huber}
29490a92053219ae50ddf4bb54e3d54db2d309e2b8dAndreas Huber
29590a92053219ae50ddf4bb54e3d54db2d309e2b8dAndreas Huberbool WifiDisplaySource::PlaybackSession::Track::isSuspended() const {
29690a92053219ae50ddf4bb54e3d54db2d309e2b8dAndreas Huber    if (!mQueuedOutputBuffers.empty()) {
29790a92053219ae50ddf4bb54e3d54db2d309e2b8dAndreas Huber        return false;
29890a92053219ae50ddf4bb54e3d54db2d309e2b8dAndreas Huber    }
29990a92053219ae50ddf4bb54e3d54db2d309e2b8dAndreas Huber
30090a92053219ae50ddf4bb54e3d54db2d309e2b8dAndreas Huber    if (mLastOutputBufferQueuedTimeUs < 0ll) {
30190a92053219ae50ddf4bb54e3d54db2d309e2b8dAndreas Huber        // We've never seen an output buffer queued, but tracks start
30290a92053219ae50ddf4bb54e3d54db2d309e2b8dAndreas Huber        // out live, not suspended.
30390a92053219ae50ddf4bb54e3d54db2d309e2b8dAndreas Huber        return false;
30490a92053219ae50ddf4bb54e3d54db2d309e2b8dAndreas Huber    }
30590a92053219ae50ddf4bb54e3d54db2d309e2b8dAndreas Huber
30690a92053219ae50ddf4bb54e3d54db2d309e2b8dAndreas Huber    // If we've not seen new output data for 60ms or more, we consider
30790a92053219ae50ddf4bb54e3d54db2d309e2b8dAndreas Huber    // this track suspended for the time being.
30890a92053219ae50ddf4bb54e3d54db2d309e2b8dAndreas Huber    return (ALooper::GetNowUs() - mLastOutputBufferQueuedTimeUs) > 60000ll;
30990a92053219ae50ddf4bb54e3d54db2d309e2b8dAndreas Huber}
31090a92053219ae50ddf4bb54e3d54db2d309e2b8dAndreas Huber
311d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber////////////////////////////////////////////////////////////////////////////////
312d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber
313d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas HuberWifiDisplaySource::PlaybackSession::PlaybackSession(
314d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber        const sp<ANetworkSession> &netSession,
3150b73d4730202fcad53aefc4314a06e7b95f442f0Andreas Huber        const sp<AMessage> &notify,
316bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber        const in_addr &interfaceAddr,
317b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber        const sp<IHDCP> &hdcp)
318d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber    : mNetSession(netSession),
319d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber      mNotify(notify),
320bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber      mInterfaceAddr(interfaceAddr),
321b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber      mHDCP(hdcp),
322ef7d3793fa9bbfb25253626ede9a020ee9280a17Andreas Huber      mWeAreDead(false),
323d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber      mLastLifesignUs(),
324e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber      mVideoTrackIndex(-1),
325d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber      mPrevTimeUs(-1ll),
32690a92053219ae50ddf4bb54e3d54db2d309e2b8dAndreas Huber      mAllTracksHavePacketizerIndex(false) {
327d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber}
328d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber
329d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huberstatus_t WifiDisplaySource::PlaybackSession::init(
330d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber        const char *clientIP, int32_t clientRtp, int32_t clientRtcp,
33190a92053219ae50ddf4bb54e3d54db2d309e2b8dAndreas Huber        Sender::TransportMode transportMode,
332e7bd24af08ef0722fb124a550662bcec48c56f86Andreas Huber        bool usePCMAudio) {
333e7bd24af08ef0722fb124a550662bcec48c56f86Andreas Huber    status_t err = setupPacketizer(usePCMAudio);
334d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber
335d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber    if (err != OK) {
336d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber        return err;
337d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber    }
338d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber
33990a92053219ae50ddf4bb54e3d54db2d309e2b8dAndreas Huber    sp<AMessage> notify = new AMessage(kWhatSenderNotify, id());
34090a92053219ae50ddf4bb54e3d54db2d309e2b8dAndreas Huber    mSender = new Sender(mNetSession, notify);
341d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber
34290a92053219ae50ddf4bb54e3d54db2d309e2b8dAndreas Huber    mSenderLooper = new ALooper;
34390a92053219ae50ddf4bb54e3d54db2d309e2b8dAndreas Huber    mSenderLooper->setName("sender_looper");
344efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber
34590a92053219ae50ddf4bb54e3d54db2d309e2b8dAndreas Huber    mSenderLooper->start(
34690a92053219ae50ddf4bb54e3d54db2d309e2b8dAndreas Huber            false /* runOnCallingThread */,
34790a92053219ae50ddf4bb54e3d54db2d309e2b8dAndreas Huber            false /* canCallJava */,
34890a92053219ae50ddf4bb54e3d54db2d309e2b8dAndreas Huber            PRIORITY_AUDIO);
349efd9c63dc846dd3dea2c979fe2a9d6770e73f9acAndreas Huber
35090a92053219ae50ddf4bb54e3d54db2d309e2b8dAndreas Huber    mSenderLooper->registerHandler(mSender);
351d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber
35290a92053219ae50ddf4bb54e3d54db2d309e2b8dAndreas Huber    err = mSender->init(clientIP, clientRtp, clientRtcp, transportMode);
353d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber
35490a92053219ae50ddf4bb54e3d54db2d309e2b8dAndreas Huber    if (err != OK) {
35590a92053219ae50ddf4bb54e3d54db2d309e2b8dAndreas Huber        return err;
356d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber    }
357d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber
358d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber    updateLiveness();
359d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber
360d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber    return OK;
361d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber}
362d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber
363d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas HuberWifiDisplaySource::PlaybackSession::~PlaybackSession() {
364d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber}
365d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber
366d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huberint32_t WifiDisplaySource::PlaybackSession::getRTPPort() const {
36790a92053219ae50ddf4bb54e3d54db2d309e2b8dAndreas Huber    return mSender->getRTPPort();
368d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber}
369d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber
370d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huberint64_t WifiDisplaySource::PlaybackSession::getLastLifesignUs() const {
371d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber    return mLastLifesignUs;
372d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber}
373d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber
374d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Hubervoid WifiDisplaySource::PlaybackSession::updateLiveness() {
375d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber    mLastLifesignUs = ALooper::GetNowUs();
376d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber}
377d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber
378d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huberstatus_t WifiDisplaySource::PlaybackSession::play() {
379d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber    updateLiveness();
380d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber
381bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber    return OK;
382bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber}
383bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber
384bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huberstatus_t WifiDisplaySource::PlaybackSession::finishPlay() {
38592f655fe351a5f2eb7d36123d2b687d6e7e3e913Andreas Huber    // XXX Give the dongle a second to bind its sockets.
38692f655fe351a5f2eb7d36123d2b687d6e7e3e913Andreas Huber    (new AMessage(kWhatFinishPlay, id()))->post(1000000ll);
387bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber    return OK;
388bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber}
389bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber
390bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huberstatus_t WifiDisplaySource::PlaybackSession::onFinishPlay() {
39190a92053219ae50ddf4bb54e3d54db2d309e2b8dAndreas Huber    return mSender->finishInit();
392bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber}
393bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber
394bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huberstatus_t WifiDisplaySource::PlaybackSession::onFinishPlay2() {
39590a92053219ae50ddf4bb54e3d54db2d309e2b8dAndreas Huber    mSender->scheduleSendSR();
396d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber
397e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber    for (size_t i = 0; i < mTracks.size(); ++i) {
39896fc6cc65ca93009a759a3a874b82a35771b9714Andreas Huber        CHECK_EQ((status_t)OK, mTracks.editValueAt(i)->start());
399e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber    }
400e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber
401bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber    sp<AMessage> notify = mNotify->dup();
402bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber    notify->setInt32("what", kWhatSessionEstablished);
403bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber    notify->post();
404bd08e2f93bafd02abf2c25d740e9fb8bce455a99Andreas Huber
405e1957358f11031a554c57d4fb46988dd6044acc1Andreas Huber    return OK;
406d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber}
407d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber
408d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huberstatus_t WifiDisplaySource::PlaybackSession::pause() {
409d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber    updateLiveness();
410d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber
411d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber    return OK;
412d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber}
413d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber
41496fc6cc65ca93009a759a3a874b82a35771b9714Andreas Hubervoid WifiDisplaySource::PlaybackSession::destroyAsync() {
41596fc6cc65ca93009a759a3a874b82a35771b9714Andreas Huber    ALOGI("destroyAsync");
416a438123bd96c7faf145683876702387efe5628d9Andreas Huber
41796fc6cc65ca93009a759a3a874b82a35771b9714Andreas Huber    for (size_t i = 0; i < mTracks.size(); ++i) {
41896fc6cc65ca93009a759a3a874b82a35771b9714Andreas Huber        mTracks.valueAt(i)->stopAsync();
419a438123bd96c7faf145683876702387efe5628d9Andreas Huber    }
420a438123bd96c7faf145683876702387efe5628d9Andreas Huber}
421a438123bd96c7faf145683876702387efe5628d9Andreas Huber
422d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Hubervoid WifiDisplaySource::PlaybackSession::onMessageReceived(
423d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber        const sp<AMessage> &msg) {
424d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber    switch (msg->what()) {
425d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber        case kWhatConverterNotify:
426d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber        {
4276360758ce2d171169d2a21e30266547ee4ac0fecAndreas Huber            if (mWeAreDead) {
4286360758ce2d171169d2a21e30266547ee4ac0fecAndreas Huber                ALOGV("dropping msg '%s' because we're dead",
4296360758ce2d171169d2a21e30266547ee4ac0fecAndreas Huber                      msg->debugString().c_str());
4306360758ce2d171169d2a21e30266547ee4ac0fecAndreas Huber
4316360758ce2d171169d2a21e30266547ee4ac0fecAndreas Huber                break;
4326360758ce2d171169d2a21e30266547ee4ac0fecAndreas Huber            }
4336360758ce2d171169d2a21e30266547ee4ac0fecAndreas Huber
434d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber            int32_t what;
435d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber            CHECK(msg->findInt32("what", &what));
436d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber
437d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber            size_t trackIndex;
438d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber            CHECK(msg->findSize("trackIndex", &trackIndex));
439d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber
440d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber            if (what == Converter::kWhatAccessUnit) {
441d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber                const sp<Track> &track = mTracks.valueFor(trackIndex);
442d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber
443d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber                ssize_t packetizerTrackIndex = track->packetizerTrackIndex();
444d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber
44528e17ed7e2fbb254fb99481b74db85e427c905eeAndreas Huber                if (packetizerTrackIndex < 0) {
446d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber                    packetizerTrackIndex =
447d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber                        mPacketizer->addTrack(track->getFormat());
448d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber
44928e17ed7e2fbb254fb99481b74db85e427c905eeAndreas Huber                    CHECK_GE(packetizerTrackIndex, 0);
450d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber
45128e17ed7e2fbb254fb99481b74db85e427c905eeAndreas Huber                    track->setPacketizerTrackIndex(packetizerTrackIndex);
452b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber
45328e17ed7e2fbb254fb99481b74db85e427c905eeAndreas Huber                    if (allTracksHavePacketizerIndex()) {
45428e17ed7e2fbb254fb99481b74db85e427c905eeAndreas Huber                        status_t err = packetizeQueuedAccessUnits();
455b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber
456b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber                        if (err != OK) {
457ef7d3793fa9bbfb25253626ede9a020ee9280a17Andreas Huber                            notifySessionDead();
458b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber                            break;
459b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber                        }
460b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber                    }
46128e17ed7e2fbb254fb99481b74db85e427c905eeAndreas Huber                }
462b8c7bd418f0ee5b88923b0e0817e3a4acc53cf8dAndreas Huber
46328e17ed7e2fbb254fb99481b74db85e427c905eeAndreas Huber                sp<ABuffer> accessUnit;
46428e17ed7e2fbb254fb99481b74db85e427c905eeAndreas Huber                CHECK(msg->findBuffer("accessUnit", &accessUnit));
465d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber
46628e17ed7e2fbb254fb99481b74db85e427c905eeAndreas Huber                if (!allTracksHavePacketizerIndex()) {
46728e17ed7e2fbb254fb99481b74db85e427c905eeAndreas Huber                    track->queueAccessUnit(accessUnit);
46828e17ed7e2fbb254fb99481b74db85e427c905eeAndreas Huber                    break;
46928e17ed7e2fbb254fb99481b74db85e427c905eeAndreas Huber                }
470d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber
47190a92053219ae50ddf4bb54e3d54db2d309e2b8dAndreas Huber                track->queueOutputBuffer(accessUnit);
472774df0dce0116c69b6d17f2e4a4912e06138e575Andreas Huber
47390a92053219ae50ddf4bb54e3d54db2d309e2b8dAndreas Huber                drainAccessUnits();
47428e17ed7e2fbb254fb99481b74db85e427c905eeAndreas Huber                break;
475d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber            } else if (what == Converter::kWhatEOS) {
476d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber                CHECK_EQ(what, Converter::kWhatEOS);
477d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber
478d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber                ALOGI("output EOS on track %d", trackIndex);
479d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber
480d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber                ssize_t index = mTracks.indexOfKey(trackIndex);
481d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber                CHECK_GE(index, 0);
482d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber
483d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber                const sp<Converter> &converter =
484d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber                    mTracks.valueAt(index)->converter();
485d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber                looper()->unregisterHandler(converter->id());
486d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber
487d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber                mTracks.removeItemsAt(index);
488d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber
489d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber                if (mTracks.isEmpty()) {
490d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber                    ALOGI("Reached EOS");
491d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber                }
492d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber            } else {
493d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber                CHECK_EQ(what, Converter::kWhatError);
494d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber
495d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber                status_t err;
496d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber                CHECK(msg->findInt32("err", &err));
497d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber
498d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber                ALOGE("converter signaled error %d", err);
499ea4bbfdcad9478ea19257fb19a32de68a2dfd958Andreas Huber
500ef7d3793fa9bbfb25253626ede9a020ee9280a17Andreas Huber                notifySessionDead();
501d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber            }
502d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber            break;
503d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber        }
504d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber
505