summaryrefslogtreecommitdiffstats
path: root/media/libstagefright/rtsp
diff options
context:
space:
mode:
authorAndreas Huber <andih@google.com>2012-05-17 12:12:39 -0700
committerAndreas Huber <andih@google.com>2012-05-17 12:12:39 -0700
commit8647bbe4420ca487467318404127f52c567e346b (patch)
tree6c6f23d84034a5e4ca0aee0542707bd0bca70570 /media/libstagefright/rtsp
parentcd28dc10d49c359566c69d48a29a6f0d3eefa6d9 (diff)
downloadframeworks_av-8647bbe4420ca487467318404127f52c567e346b.zip
frameworks_av-8647bbe4420ca487467318404127f52c567e346b.tar.gz
frameworks_av-8647bbe4420ca487467318404127f52c567e346b.tar.bz2
Prefix MPEG4-generic audio data with ADTS headers
to work around limitations of the new AAC decoder. Change-Id: I4988c7c39fedb7d04eb1ae2ba2d618aa6cb14e77 related-to-bug: 6488547
Diffstat (limited to 'media/libstagefright/rtsp')
-rw-r--r--media/libstagefright/rtsp/AMPEG4AudioAssembler.cpp22
-rw-r--r--media/libstagefright/rtsp/AMPEG4ElementaryAssembler.cpp52
-rw-r--r--media/libstagefright/rtsp/AMPEG4ElementaryAssembler.h5
-rw-r--r--media/libstagefright/rtsp/APacketSource.cpp1
-rw-r--r--media/libstagefright/rtsp/ARTPAssembler.cpp73
-rw-r--r--media/libstagefright/rtsp/ARTPAssembler.h10
6 files changed, 128 insertions, 35 deletions
diff --git a/media/libstagefright/rtsp/AMPEG4AudioAssembler.cpp b/media/libstagefright/rtsp/AMPEG4AudioAssembler.cpp
index 24c2f30..f9a44f0 100644
--- a/media/libstagefright/rtsp/AMPEG4AudioAssembler.cpp
+++ b/media/libstagefright/rtsp/AMPEG4AudioAssembler.cpp
@@ -534,27 +534,7 @@ void AMPEG4AudioAssembler::submitAccessUnit() {
LOG(VERBOSE) << "Access unit complete (" << mPackets.size() << " packets)";
#endif
- size_t totalSize = 0;
- List<sp<ABuffer> >::iterator it = mPackets.begin();
- while (it != mPackets.end()) {
- const sp<ABuffer> &unit = *it;
-
- totalSize += unit->size();
- ++it;
- }
-
- sp<ABuffer> accessUnit = new ABuffer(totalSize);
- size_t offset = 0;
- it = mPackets.begin();
- while (it != mPackets.end()) {
- const sp<ABuffer> &unit = *it;
-
- memcpy((uint8_t *)accessUnit->data() + offset,
- unit->data(), unit->size());
-
- ++it;
- }
-
+ sp<ABuffer> accessUnit = MakeCompoundFromPackets(mPackets);
accessUnit = removeLATMFraming(accessUnit);
CopyTimes(accessUnit, *mPackets.begin());
diff --git a/media/libstagefright/rtsp/AMPEG4ElementaryAssembler.cpp b/media/libstagefright/rtsp/AMPEG4ElementaryAssembler.cpp
index 687d72b..eefceba 100644
--- a/media/libstagefright/rtsp/AMPEG4ElementaryAssembler.cpp
+++ b/media/libstagefright/rtsp/AMPEG4ElementaryAssembler.cpp
@@ -21,6 +21,7 @@
#include "AMPEG4ElementaryAssembler.h"
#include "ARTPSource.h"
+#include "ASessionDescription.h"
#include <media/stagefright/foundation/ABitReader.h>
#include <media/stagefright/foundation/ABuffer.h>
@@ -85,6 +86,25 @@ static bool GetIntegerAttribute(
return true;
}
+static bool GetSampleRateIndex(int32_t sampleRate, size_t *tableIndex) {
+ static const int32_t kSampleRateTable[] = {
+ 96000, 88200, 64000, 48000, 44100, 32000,
+ 24000, 22050, 16000, 12000, 11025, 8000
+ };
+ const size_t kNumSampleRates =
+ sizeof(kSampleRateTable) / sizeof(kSampleRateTable[0]);
+
+ *tableIndex = 0;
+ for (size_t index = 0; index < kNumSampleRates; ++index) {
+ if (sampleRate == kSampleRateTable[index]) {
+ *tableIndex = index;
+ return true;
+ }
+ }
+
+ return false;
+}
+
// static
AMPEG4ElementaryAssembler::AMPEG4ElementaryAssembler(
const sp<AMessage> &notify, const AString &desc, const AString &params)
@@ -100,6 +120,8 @@ AMPEG4ElementaryAssembler::AMPEG4ElementaryAssembler(
mStreamStateIndication(0),
mAuxiliaryDataSizeLength(0),
mHasAUHeader(false),
+ mChannelConfig(0),
+ mSampleRateIndex(0),
mAccessUnitRTPTime(0),
mNextExpectedSeqNoValid(false),
mNextExpectedSeqNo(0),
@@ -163,6 +185,13 @@ AMPEG4ElementaryAssembler::AMPEG4ElementaryAssembler(
|| mDTSDeltaLength > 0
|| mRandomAccessIndication
|| mStreamStateIndication > 0;
+
+ int32_t sampleRate, numChannels;
+ ASessionDescription::ParseFormatDesc(
+ desc.c_str(), &sampleRate, &numChannels);
+
+ mChannelConfig = numChannels;
+ CHECK(GetSampleRateIndex(sampleRate, &mSampleRateIndex));
}
}
@@ -338,23 +367,18 @@ void AMPEG4ElementaryAssembler::submitAccessUnit() {
ALOGV("Access unit complete (%d nal units)", mPackets.size());
- size_t totalSize = 0;
- for (List<sp<ABuffer> >::iterator it = mPackets.begin();
- it != mPackets.end(); ++it) {
- totalSize += (*it)->size();
- }
+ sp<ABuffer> accessUnit;
- sp<ABuffer> accessUnit = new ABuffer(totalSize);
- size_t offset = 0;
- for (List<sp<ABuffer> >::iterator it = mPackets.begin();
- it != mPackets.end(); ++it) {
- sp<ABuffer> nal = *it;
- memcpy(accessUnit->data() + offset, nal->data(), nal->size());
- offset += nal->size();
+ if (mIsGeneric) {
+ accessUnit = MakeADTSCompoundFromAACFrames(
+ OMX_AUDIO_AACObjectLC - 1,
+ mSampleRateIndex,
+ mChannelConfig,
+ mPackets);
+ } else {
+ accessUnit = MakeCompoundFromPackets(mPackets);
}
- CopyTimes(accessUnit, *mPackets.begin());
-
#if 0
printf(mAccessUnitDamaged ? "X" : ".");
fflush(stdout);
diff --git a/media/libstagefright/rtsp/AMPEG4ElementaryAssembler.h b/media/libstagefright/rtsp/AMPEG4ElementaryAssembler.h
index 794bbcc..693fca5 100644
--- a/media/libstagefright/rtsp/AMPEG4ElementaryAssembler.h
+++ b/media/libstagefright/rtsp/AMPEG4ElementaryAssembler.h
@@ -25,6 +25,8 @@
#include <utils/List.h>
#include <utils/RefBase.h>
+#include <OMX_Audio.h>
+
namespace android {
struct ABuffer;
@@ -57,6 +59,9 @@ private:
unsigned mAuxiliaryDataSizeLength;
bool mHasAUHeader;
+ int32_t mChannelConfig;
+ size_t mSampleRateIndex;
+
uint32_t mAccessUnitRTPTime;
bool mNextExpectedSeqNoValid;
uint32_t mNextExpectedSeqNo;
diff --git a/media/libstagefright/rtsp/APacketSource.cpp b/media/libstagefright/rtsp/APacketSource.cpp
index 6cf1301..fc177d2 100644
--- a/media/libstagefright/rtsp/APacketSource.cpp
+++ b/media/libstagefright/rtsp/APacketSource.cpp
@@ -551,6 +551,7 @@ APacketSource::APacketSource(
mFormat->setInt32(kKeySampleRate, sampleRate);
mFormat->setInt32(kKeyChannelCount, numChannels);
+ mFormat->setInt32(kKeyIsADTS, true);
sp<ABuffer> codecSpecificData =
MakeAACCodecSpecificData2(params.c_str());
diff --git a/media/libstagefright/rtsp/ARTPAssembler.cpp b/media/libstagefright/rtsp/ARTPAssembler.cpp
index a897c10..1844bc5 100644
--- a/media/libstagefright/rtsp/ARTPAssembler.cpp
+++ b/media/libstagefright/rtsp/ARTPAssembler.cpp
@@ -74,4 +74,77 @@ void ARTPAssembler::CopyTimes(const sp<ABuffer> &to, const sp<ABuffer> &from) {
to->setInt32Data(from->int32Data());
}
+// static
+sp<ABuffer> ARTPAssembler::MakeADTSCompoundFromAACFrames(
+ unsigned profile,
+ unsigned samplingFreqIndex,
+ unsigned channelConfig,
+ const List<sp<ABuffer> > &frames) {
+ size_t totalSize = 0;
+ for (List<sp<ABuffer> >::const_iterator it = frames.begin();
+ it != frames.end(); ++it) {
+ // Each frame is prefixed by a 7 byte ADTS header
+ totalSize += (*it)->size() + 7;
+ }
+
+ sp<ABuffer> accessUnit = new ABuffer(totalSize);
+ size_t offset = 0;
+ for (List<sp<ABuffer> >::const_iterator it = frames.begin();
+ it != frames.end(); ++it) {
+ sp<ABuffer> nal = *it;
+ uint8_t *dst = accessUnit->data() + offset;
+
+ static const unsigned kADTSId = 0;
+ static const unsigned kADTSLayer = 0;
+ static const unsigned kADTSProtectionAbsent = 1;
+
+ unsigned frameLength = nal->size() + 7;
+
+ dst[0] = 0xff;
+
+ dst[1] =
+ 0xf0 | (kADTSId << 3) | (kADTSLayer << 1) | kADTSProtectionAbsent;
+
+ dst[2] = (profile << 6)
+ | (samplingFreqIndex << 2)
+ | (channelConfig >> 2);
+
+ dst[3] = ((channelConfig & 3) << 6) | (frameLength >> 11);
+
+ dst[4] = (frameLength >> 3) & 0xff;
+ dst[5] = (frameLength & 7) << 5;
+ dst[6] = 0x00;
+
+ memcpy(dst + 7, nal->data(), nal->size());
+ offset += nal->size() + 7;
+ }
+
+ CopyTimes(accessUnit, *frames.begin());
+
+ return accessUnit;
+}
+
+// static
+sp<ABuffer> ARTPAssembler::MakeCompoundFromPackets(
+ const List<sp<ABuffer> > &packets) {
+ size_t totalSize = 0;
+ for (List<sp<ABuffer> >::const_iterator it = packets.begin();
+ it != packets.end(); ++it) {
+ totalSize += (*it)->size();
+ }
+
+ sp<ABuffer> accessUnit = new ABuffer(totalSize);
+ size_t offset = 0;
+ for (List<sp<ABuffer> >::const_iterator it = packets.begin();
+ it != packets.end(); ++it) {
+ sp<ABuffer> nal = *it;
+ memcpy(accessUnit->data() + offset, nal->data(), nal->size());
+ offset += nal->size();
+ }
+
+ CopyTimes(accessUnit, *packets.begin());
+
+ return accessUnit;
+}
+
} // namespace android
diff --git a/media/libstagefright/rtsp/ARTPAssembler.h b/media/libstagefright/rtsp/ARTPAssembler.h
index 70ea186..7c147be 100644
--- a/media/libstagefright/rtsp/ARTPAssembler.h
+++ b/media/libstagefright/rtsp/ARTPAssembler.h
@@ -19,6 +19,7 @@
#define A_RTP_ASSEMBLER_H_
#include <media/stagefright/foundation/ABase.h>
+#include <utils/List.h>
#include <utils/RefBase.h>
namespace android {
@@ -45,6 +46,15 @@ protected:
static void CopyTimes(const sp<ABuffer> &to, const sp<ABuffer> &from);
+ static sp<ABuffer> MakeADTSCompoundFromAACFrames(
+ unsigned profile,
+ unsigned samplingFreqIndex,
+ unsigned channelConfig,
+ const List<sp<ABuffer> > &frames);
+
+ static sp<ABuffer> MakeCompoundFromPackets(
+ const List<sp<ABuffer> > &frames);
+
private:
int64_t mFirstFailureTimeUs;