AH263Assembler.cpp revision 8d342970108926c4ea355c90d26a2a353ec0fd47
139ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber/* 239ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber * Copyright (C) 2010 The Android Open Source Project 339ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber * 439ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber * Licensed under the Apache License, Version 2.0 (the "License"); 539ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber * you may not use this file except in compliance with the License. 639ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber * You may obtain a copy of the License at 739ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber * 839ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber * http://www.apache.org/licenses/LICENSE-2.0 939ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber * 1039ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber * Unless required by applicable law or agreed to in writing, software 1139ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber * distributed under the License is distributed on an "AS IS" BASIS, 1239ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 1339ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber * See the License for the specific language governing permissions and 1439ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber * limitations under the License. 1539ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber */ 1639ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber 1739ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber#include "AH263Assembler.h" 1839ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber 1939ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber#include "ARTPSource.h" 2039ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber 2139ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber#include <media/stagefright/foundation/ABuffer.h> 2239ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber#include <media/stagefright/foundation/ADebug.h> 2339ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber#include <media/stagefright/foundation/AMessage.h> 2439ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber#include <media/stagefright/foundation/hexdump.h> 2539ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber#include <media/stagefright/Utils.h> 2639ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber 2739ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Hubernamespace android { 2839ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber 2939ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas HuberAH263Assembler::AH263Assembler(const sp<AMessage> ¬ify) 3039ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber : mNotifyMsg(notify), 3139ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber mAccessUnitRTPTime(0), 3239ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber mNextExpectedSeqNoValid(false), 3339ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber mNextExpectedSeqNo(0), 3439ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber mAccessUnitDamaged(false) { 3539ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber} 3639ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber 3739ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas HuberAH263Assembler::~AH263Assembler() { 3839ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber} 3939ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber 4039ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas HuberARTPAssembler::AssemblyStatus AH263Assembler::assembleMore( 4139ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber const sp<ARTPSource> &source) { 4239ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber AssemblyStatus status = addPacket(source); 4339ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber if (status == MALFORMED_PACKET) { 4439ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber mAccessUnitDamaged = true; 4539ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber } 4639ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber return status; 4739ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber} 4839ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber 4939ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas HuberARTPAssembler::AssemblyStatus AH263Assembler::addPacket( 5039ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber const sp<ARTPSource> &source) { 5139ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber List<sp<ABuffer> > *queue = source->queue(); 5239ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber 5339ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber if (queue->empty()) { 5439ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber return NOT_ENOUGH_DATA; 5539ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber } 5639ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber 5739ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber if (mNextExpectedSeqNoValid) { 5839ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber List<sp<ABuffer> >::iterator it = queue->begin(); 5939ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber while (it != queue->end()) { 6039ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber if ((uint32_t)(*it)->int32Data() >= mNextExpectedSeqNo) { 6139ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber break; 6239ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber } 6339ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber 6439ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber it = queue->erase(it); 6539ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber } 6639ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber 6739ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber if (queue->empty()) { 6839ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber return NOT_ENOUGH_DATA; 6939ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber } 7039ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber } 7139ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber 7239ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber sp<ABuffer> buffer = *queue->begin(); 7339ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber 7439ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber if (!mNextExpectedSeqNoValid) { 7539ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber mNextExpectedSeqNoValid = true; 7639ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber mNextExpectedSeqNo = (uint32_t)buffer->int32Data(); 7739ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber } else if ((uint32_t)buffer->int32Data() != mNextExpectedSeqNo) { 7839ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber#if VERBOSE 7939ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber LOG(VERBOSE) << "Not the sequence number I expected"; 8039ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber#endif 8139ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber 8239ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber return WRONG_SEQUENCE_NUMBER; 8339ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber } 8439ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber 8539ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber uint32_t rtpTime; 8639ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber CHECK(buffer->meta()->findInt32("rtp-time", (int32_t *)&rtpTime)); 8739ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber 8839ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber if (mPackets.size() > 0 && rtpTime != mAccessUnitRTPTime) { 8939ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber submitAccessUnit(); 9039ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber } 9139ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber mAccessUnitRTPTime = rtpTime; 9239ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber 9339ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber // hexdump(buffer->data(), buffer->size()); 9439ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber 9539ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber if (buffer->size() < 2) { 9639ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber queue->erase(queue->begin()); 9739ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber ++mNextExpectedSeqNo; 9839ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber 9939ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber return MALFORMED_PACKET; 10039ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber } 10139ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber 10239ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber unsigned payloadHeader = U16_AT(buffer->data()); 10339ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber CHECK_EQ(payloadHeader >> 11, 0u); // RR=0 10439ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber unsigned P = (payloadHeader >> 10) & 1; 10539ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber CHECK_EQ((payloadHeader >> 9) & 1, 0u); // V=0 10639ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber CHECK_EQ((payloadHeader >> 3) & 0x3f, 0u); // PLEN=0 10739ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber CHECK_EQ(payloadHeader & 7, 0u); // PEBIT=0 10839ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber 10939ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber if (P) { 11039ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber buffer->data()[0] = 0x00; 11139ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber buffer->data()[1] = 0x00; 11239ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber } else { 113a6238a1e5b603ca2ccf3b2297c9bc8a141cf8559Andreas Huber buffer->setRange(buffer->offset() + 2, buffer->size() - 2); 11439ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber } 11539ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber 11639ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber mPackets.push_back(buffer); 11739ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber 11839ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber queue->erase(queue->begin()); 11939ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber ++mNextExpectedSeqNo; 12039ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber 12139ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber return OK; 12239ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber} 12339ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber 12439ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Hubervoid AH263Assembler::submitAccessUnit() { 12539ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber CHECK(!mPackets.empty()); 12639ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber 12739ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber#if VERBOSE 12839ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber LOG(VERBOSE) << "Access unit complete (" << mPackets.size() << " packets)"; 12939ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber#endif 13039ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber 13139ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber size_t totalSize = 0; 13239ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber List<sp<ABuffer> >::iterator it = mPackets.begin(); 13339ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber while (it != mPackets.end()) { 13439ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber const sp<ABuffer> &unit = *it; 13539ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber 13639ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber totalSize += unit->size(); 13739ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber ++it; 13839ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber } 13939ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber 14039ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber sp<ABuffer> accessUnit = new ABuffer(totalSize); 14139ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber size_t offset = 0; 14239ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber it = mPackets.begin(); 14339ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber while (it != mPackets.end()) { 14439ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber const sp<ABuffer> &unit = *it; 14539ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber 14639ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber memcpy((uint8_t *)accessUnit->data() + offset, 14739ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber unit->data(), unit->size()); 14839ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber 14939ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber offset += unit->size(); 15039ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber 15139ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber ++it; 15239ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber } 15339ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber 1548d342970108926c4ea355c90d26a2a353ec0fd47Andreas Huber CopyTimes(accessUnit, *mPackets.begin()); 15539ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber 15639ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber#if 0 15739ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber printf(mAccessUnitDamaged ? "X" : "."); 15839ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber fflush(stdout); 15939ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber#endif 16039ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber 16139ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber if (mAccessUnitDamaged) { 16239ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber accessUnit->meta()->setInt32("damaged", true); 16339ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber } 16439ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber 16539ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber mPackets.clear(); 16639ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber mAccessUnitDamaged = false; 16739ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber 16839ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber sp<AMessage> msg = mNotifyMsg->dup(); 16939ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber msg->setObject("access-unit", accessUnit); 17039ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber msg->post(); 17139ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber} 17239ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber 17339ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Hubervoid AH263Assembler::packetLost() { 17439ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber CHECK(mNextExpectedSeqNoValid); 17539ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber ++mNextExpectedSeqNo; 17639ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber 17739ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber mAccessUnitDamaged = true; 17839ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber} 17939ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber 18039ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Hubervoid AH263Assembler::onByeReceived() { 18139ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber sp<AMessage> msg = mNotifyMsg->dup(); 18239ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber msg->setInt32("eos", true); 18339ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber msg->post(); 18439ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber} 18539ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber 18639ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber} // namespace android 18739ddf8e0f18766f7ba1e3246b774aa6ebd93eea8Andreas Huber 188