MediaSender.cpp revision a556c4822fc205db0d27834ba5b637c351d73ffa
1a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber/*
2a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber * Copyright 2013, The Android Open Source Project
3a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber *
4a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber * Licensed under the Apache License, Version 2.0 (the "License");
5a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber * you may not use this file except in compliance with the License.
6a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber * You may obtain a copy of the License at
7a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber *
8a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber *     http://www.apache.org/licenses/LICENSE-2.0
9a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber *
10a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber * Unless required by applicable law or agreed to in writing, software
11a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber * distributed under the License is distributed on an "AS IS" BASIS,
12a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber * See the License for the specific language governing permissions and
14a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber * limitations under the License.
15a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber */
16a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber
17a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber//#define LOG_NDEBUG 0
18a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber#define LOG_TAG "MediaSender"
19a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber#include <utils/Log.h>
20a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber
21a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber#include "MediaSender.h"
22a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber
23a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber#include "ANetworkSession.h"
24a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber#include "rtp/RTPSender.h"
25a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber#include "source/TSPacketizer.h"
26a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber
27a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber#include "include/avc_utils.h"
28a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber
29a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber#include <media/IHDCP.h>
30a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber#include <media/stagefright/foundation/ABuffer.h>
31a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber#include <media/stagefright/foundation/ADebug.h>
32a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber#include <media/stagefright/foundation/AMessage.h>
33a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber
34a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Hubernamespace android {
35a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber
36a556c4822fc205db0d27834ba5b637c351d73ffaAndreas HuberMediaSender::MediaSender(
37a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber        const sp<ANetworkSession> &netSession,
38a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber        const sp<AMessage> &notify)
39a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber    : mNetSession(netSession),
40a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber      mNotify(notify),
41a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber      mMode(MODE_UNDEFINED),
42a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber      mGeneration(0),
43a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber      mPrevTimeUs(-1ll),
44a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber      mInitDoneCount(0) {
45a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber}
46a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber
47a556c4822fc205db0d27834ba5b637c351d73ffaAndreas HuberMediaSender::~MediaSender() {
48a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber}
49a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber
50a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huberstatus_t MediaSender::setHDCP(const sp<IHDCP> &hdcp) {
51a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber    if (mMode != MODE_UNDEFINED) {
52a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber        return INVALID_OPERATION;
53a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber    }
54a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber
55a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber    mHDCP = hdcp;
56a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber
57a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber    return OK;
58a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber}
59a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber
60a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huberssize_t MediaSender::addTrack(const sp<AMessage> &format, uint32_t flags) {
61a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber    if (mMode != MODE_UNDEFINED) {
62a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber        return INVALID_OPERATION;
63a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber    }
64a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber
65a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber    TrackInfo info;
66a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber    info.mFormat = format;
67a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber    info.mFlags = flags;
68a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber    info.mPacketizerTrackIndex = -1;
69a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber
70a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber    AString mime;
71a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber    CHECK(format->findString("mime", &mime));
72a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber    info.mIsAudio = !strncasecmp("audio/", mime.c_str(), 6);
73a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber
74a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber    size_t index = mTrackInfos.size();
75a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber    mTrackInfos.push_back(info);
76a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber
77a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber    return index;
78a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber}
79a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber
80a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huberstatus_t MediaSender::initAsync(
81a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber        ssize_t trackIndex,
82a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber        RTPSender::TransportMode transportMode,
83a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber        const char *remoteHost,
84a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber        int32_t remoteRTPPort,
85a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber        int32_t remoteRTCPPort,
86a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber        int32_t *localRTPPort) {
87a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber    if (trackIndex < 0) {
88a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber        if (mMode != MODE_UNDEFINED) {
89a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber            return INVALID_OPERATION;
90a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber        }
91a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber
92a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber        mTSPacketizer = new TSPacketizer;
93a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber
94a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber        status_t err = OK;
95a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber        for (size_t i = 0; i < mTrackInfos.size(); ++i) {
96a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber            TrackInfo *info = &mTrackInfos.editItemAt(i);
97a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber
98a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber            sp<AMessage> trackFormat = info->mFormat;
99a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber            if (mHDCP != NULL && !info->mIsAudio) {
100a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber                // HDCP2.0 _and_ HDCP 2.1 specs say to set the version
101a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber                // inside the HDCP descriptor to 0x20!!!
102a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber                trackFormat->setInt32("hdcp-version", 0x20);
103a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber            }
104a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber
105a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber            ssize_t packetizerTrackIndex =
106a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber                mTSPacketizer->addTrack(trackFormat);
107a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber
108a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber            if (packetizerTrackIndex < 0) {
109a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber                err = packetizerTrackIndex;
110a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber                break;
111a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber            }
112a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber
113a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber            info->mPacketizerTrackIndex = packetizerTrackIndex;
114a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber        }
115a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber
116a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber        if (err == OK) {
117a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber            sp<AMessage> notify = new AMessage(kWhatSenderNotify, id());
118a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber            notify->setInt32("generation", mGeneration);
119a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber            mTSSender = new RTPSender(mNetSession, notify);
120a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber            looper()->registerHandler(mTSSender);
121a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber
122a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber            err = mTSSender->initAsync(
123a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber                    transportMode,
124a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber                    remoteHost,
125a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber                    remoteRTPPort,
126a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber                    remoteRTCPPort,
127a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber                    localRTPPort);
128a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber
129a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber            if (err != OK) {
130a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber                looper()->unregisterHandler(mTSSender->id());
131a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber                mTSSender.clear();
132a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber            }
133a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber        }
134a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber
135a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber        if (err != OK) {
136a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber            for (size_t i = 0; i < mTrackInfos.size(); ++i) {
137a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber                TrackInfo *info = &mTrackInfos.editItemAt(i);
138a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber                info->mPacketizerTrackIndex = -1;
139a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber            }
140a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber
141a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber            mTSPacketizer.clear();
142a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber            return err;
143a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber        }
144a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber
145a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber        mMode = MODE_TRANSPORT_STREAM;
146a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber        mInitDoneCount = 1;
147a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber
148a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber        return OK;
149a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber    }
150a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber
151a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber    if (mMode == MODE_TRANSPORT_STREAM) {
152a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber        return INVALID_OPERATION;
153a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber    }
154a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber
155a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber    if ((size_t)trackIndex >= mTrackInfos.size()) {
156a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber        return -ERANGE;
157a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber    }
158a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber
159a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber    TrackInfo *info = &mTrackInfos.editItemAt(trackIndex);
160a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber
161a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber    if (info->mSender != NULL) {
162a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber        return INVALID_OPERATION;
163a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber    }
164a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber
165a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber    sp<AMessage> notify = new AMessage(kWhatSenderNotify, id());
166a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber    notify->setInt32("generation", mGeneration);
167a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber    notify->setSize("trackIndex", trackIndex);
168a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber
169a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber    info->mSender = new RTPSender(mNetSession, notify);
170a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber    looper()->registerHandler(info->mSender);
171a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber
172a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber    status_t err = info->mSender->initAsync(
173a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber            transportMode,
174a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber            remoteHost,
175a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber            remoteRTPPort,
176a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber            remoteRTCPPort,
177a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber            localRTPPort);
178a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber
179a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber    if (err != OK) {
180a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber        looper()->unregisterHandler(info->mSender->id());
181a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber        info->mSender.clear();
182a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber
183a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber        return err;
184a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber    }
185a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber
186a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber    if (mMode == MODE_UNDEFINED) {
187a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber        mInitDoneCount = mTrackInfos.size();
188a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber    }
189a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber
190a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber    mMode = MODE_ELEMENTARY_STREAMS;
191a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber
192a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber    return OK;
193a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber}
194a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber
195a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huberstatus_t MediaSender::queueAccessUnit(
196a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber        size_t trackIndex, const sp<ABuffer> &accessUnit) {
197a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber    if (mMode == MODE_UNDEFINED) {
198a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber        return INVALID_OPERATION;
199a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber    }
200a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber
201a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber    if (trackIndex >= mTrackInfos.size()) {
202a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber        return -ERANGE;
203a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber    }
204a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber
205a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber    if (mMode == MODE_TRANSPORT_STREAM) {
206a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber        TrackInfo *info = &mTrackInfos.editItemAt(trackIndex);
207a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber        info->mAccessUnits.push_back(accessUnit);
208a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber
209a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber        mTSPacketizer->extractCSDIfNecessary(info->mPacketizerTrackIndex);
210a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber
211a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber        for (;;) {
212a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber            ssize_t minTrackIndex = -1;
213a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber            int64_t minTimeUs = -1ll;
214a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber
215a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber            for (size_t i = 0; i < mTrackInfos.size(); ++i) {
216a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber                const TrackInfo &info = mTrackInfos.itemAt(i);
217a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber
218a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber                if (info.mAccessUnits.empty()) {
219a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber                    minTrackIndex = -1;
220a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber                    minTimeUs = -1ll;
221a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber                    break;
222a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber                }
223a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber
224a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber                int64_t timeUs;
225a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber                const sp<ABuffer> &accessUnit = *info.mAccessUnits.begin();
226a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber                CHECK(accessUnit->meta()->findInt64("timeUs", &timeUs));
227a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber
228a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber                if (minTrackIndex < 0 || timeUs < minTimeUs) {
229a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber                    minTrackIndex = i;
230a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber                    minTimeUs = timeUs;
231a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber                }
232a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber            }
233a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber
234a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber            if (minTrackIndex < 0) {
235a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber                return OK;
236a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber            }
237a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber
238a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber            TrackInfo *info = &mTrackInfos.editItemAt(minTrackIndex);
239a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber            sp<ABuffer> accessUnit = *info->mAccessUnits.begin();
240a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber            info->mAccessUnits.erase(info->mAccessUnits.begin());
241a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber
242a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber            sp<ABuffer> tsPackets;
243a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber            status_t err = packetizeAccessUnit(
244a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber                    minTrackIndex, accessUnit, &tsPackets);
245a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber
246a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber            if (err == OK) {
247a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber                err = mTSSender->queueBuffer(
248a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber                        tsPackets,
249a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber                        33 /* packetType */,
250a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber                        RTPSender::PACKETIZATION_TRANSPORT_STREAM);
251a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber            }
252a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber
253a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber            if (err != OK) {
254a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber                return err;
255a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber            }
256a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber        }
257a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber    }
258a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber
259a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber    TrackInfo *info = &mTrackInfos.editItemAt(trackIndex);
260a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber
261a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber    return info->mSender->queueBuffer(
262a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber            accessUnit,
263a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber            info->mIsAudio ? 96 : 97 /* packetType */,
264a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber            info->mIsAudio
265a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber                ? RTPSender::PACKETIZATION_AAC : RTPSender::PACKETIZATION_H264);
266a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber}
267a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber
268a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Hubervoid MediaSender::onMessageReceived(const sp<AMessage> &msg) {
269a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber    switch (msg->what()) {
270a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber        case kWhatSenderNotify:
271a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber        {
272a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber            int32_t generation;
273a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber            CHECK(msg->findInt32("generation", &generation));
274a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber            if (generation != mGeneration) {
275a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber                break;
276a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber            }
277a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber
278a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber            onSenderNotify(msg);
279a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber            break;
280a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber        }
281a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber
282a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber        default:
283a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber            TRESPASS();
284a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber    }
285a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber}
286a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber
287a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Hubervoid MediaSender::onSenderNotify(const sp<AMessage> &msg) {
288a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber    int32_t what;
289a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber    CHECK(msg->findInt32("what", &what));
290a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber
291a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber    switch (what) {
292a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber        case RTPSender::kWhatInitDone:
293a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber        {
294a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber            --mInitDoneCount;
295a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber
296a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber            int32_t err;
297a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber            CHECK(msg->findInt32("err", &err));
298a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber
299a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber            if (err != OK) {
300a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber                notifyInitDone(err);
301a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber                ++mGeneration;
302a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber                break;
303a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber            }
304a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber
305a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber            if (mInitDoneCount == 0) {
306a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber                notifyInitDone(OK);
307a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber            }
308a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber            break;
309a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber        }
310a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber
311a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber        case RTPSender::kWhatError:
312a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber        {
313a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber            int32_t err;
314a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber            CHECK(msg->findInt32("err", &err));
315a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber
316a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber            notifyError(err);
317a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber            break;
318a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber        }
319a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber
320a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber        default:
321a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber            TRESPASS();
322a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber    }
323a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber}
324a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber
325a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Hubervoid MediaSender::notifyInitDone(status_t err) {
326a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber    sp<AMessage> notify = mNotify->dup();
327a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber    notify->setInt32("what", kWhatInitDone);
328a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber    notify->setInt32("err", err);
329a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber    notify->post();
330a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber}
331a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber
332a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Hubervoid MediaSender::notifyError(status_t err) {
333a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber    sp<AMessage> notify = mNotify->dup();
334a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber    notify->setInt32("what", kWhatError);
335a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber    notify->setInt32("err", err);
336a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber    notify->post();
337a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber}
338a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber
339a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huberstatus_t MediaSender::packetizeAccessUnit(
340a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber        size_t trackIndex,
341a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber        sp<ABuffer> accessUnit,
342a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber        sp<ABuffer> *tsPackets) {
343a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber    const TrackInfo &info = mTrackInfos.itemAt(trackIndex);
344a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber
345a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber    uint32_t flags = 0;
346a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber
347a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber    bool isHDCPEncrypted = false;
348a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber    uint64_t inputCTR;
349a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber    uint8_t HDCP_private_data[16];
350a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber
351a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber    bool manuallyPrependSPSPPS =
352a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber        !info.mIsAudio
353a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber        && (info.mFlags & FLAG_MANUALLY_PREPEND_SPS_PPS)
354a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber        && IsIDR(accessUnit);
355a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber
356a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber    if (mHDCP != NULL && !info.mIsAudio) {
357a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber        isHDCPEncrypted = true;
358a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber
359a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber        if (manuallyPrependSPSPPS) {
360a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber            accessUnit = mTSPacketizer->prependCSD(
361a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber                    info.mPacketizerTrackIndex, accessUnit);
362a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber        }
363a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber
364a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber        status_t err = mHDCP->encrypt(
365a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber                accessUnit->data(), accessUnit->size(),
366a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber                trackIndex  /* streamCTR */,
367a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber                &inputCTR,
368a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber                accessUnit->data());
369a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber
370a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber        if (err != OK) {
371a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber            ALOGE("Failed to HDCP-encrypt media data (err %d)",
372a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber                  err);
373a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber
374a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber            return err;
375a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber        }
376a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber
377a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber        HDCP_private_data[0] = 0x00;
378a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber
379a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber        HDCP_private_data[1] =
380a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber            (((trackIndex >> 30) & 3) << 1) | 1;
381a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber
382a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber        HDCP_private_data[2] = (trackIndex >> 22) & 0xff;
383a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber
384a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber        HDCP_private_data[3] =
385a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber            (((trackIndex >> 15) & 0x7f) << 1) | 1;
386a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber
387a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber        HDCP_private_data[4] = (trackIndex >> 7) & 0xff;
388a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber
389a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber        HDCP_private_data[5] =
390a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber            ((trackIndex & 0x7f) << 1) | 1;
391a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber
392a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber        HDCP_private_data[6] = 0x00;
393a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber
394a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber        HDCP_private_data[7] =
395a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber            (((inputCTR >> 60) & 0x0f) << 1) | 1;
396a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber
397a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber        HDCP_private_data[8] = (inputCTR >> 52) & 0xff;
398a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber
399a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber        HDCP_private_data[9] =
400a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber            (((inputCTR >> 45) & 0x7f) << 1) | 1;
401a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber
402a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber        HDCP_private_data[10] = (inputCTR >> 37) & 0xff;
403a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber
404a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber        HDCP_private_data[11] =
405a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber            (((inputCTR >> 30) & 0x7f) << 1) | 1;
406a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber
407a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber        HDCP_private_data[12] = (inputCTR >> 22) & 0xff;
408a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber
409a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber        HDCP_private_data[13] =
410a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber            (((inputCTR >> 15) & 0x7f) << 1) | 1;
411a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber
412a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber        HDCP_private_data[14] = (inputCTR >> 7) & 0xff;
413a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber
414a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber        HDCP_private_data[15] =
415a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber            ((inputCTR & 0x7f) << 1) | 1;
416a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber
417a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber        flags |= TSPacketizer::IS_ENCRYPTED;
418a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber    } else if (manuallyPrependSPSPPS) {
419a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber        flags |= TSPacketizer::PREPEND_SPS_PPS_TO_IDR_FRAMES;
420a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber    }
421a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber
422a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber    int64_t timeUs = ALooper::GetNowUs();
423a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber    if (mPrevTimeUs < 0ll || mPrevTimeUs + 100000ll <= timeUs) {
424a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber        flags |= TSPacketizer::EMIT_PCR;
425a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber        flags |= TSPacketizer::EMIT_PAT_AND_PMT;
426a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber
427a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber        mPrevTimeUs = timeUs;
428a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber    }
429a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber
430a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber    mTSPacketizer->packetize(
431a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber            info.mPacketizerTrackIndex,
432a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber            accessUnit,
433a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber            tsPackets,
434a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber            flags,
435a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber            !isHDCPEncrypted ? NULL : HDCP_private_data,
436a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber            !isHDCPEncrypted ? 0 : sizeof(HDCP_private_data),
437a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber            info.mIsAudio ? 2 : 0 /* numStuffingBytes */);
438a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber
439a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber    return OK;
440a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber}
441a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber
442a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber}  // namespace android
443a556c4822fc205db0d27834ba5b637c351d73ffaAndreas Huber
444