Skip to content
This repository was archived by the owner on Jul 9, 2025. It is now read-only.

Commit 9b6fc77

Browse files
committed
Bug 1891082 - Implement CodecChangeMonitor for AAC in MediaChangeMonitor r=media-playback-reviewers,padenot
This patch implements a `CodecChangeMonitor` specifically for *AAC* format, which will later be integrated into the `MediaChangeMonitor`. The `CheckForChange` function within `CodecChangeMonitor` is designed to detect changes in the data format and signal `MediaChangeMonitor` to re-create and re-initialize the underlying decoder accordingly. When the data stream format changes from *ADTS* to *AAC*, the `CodecChangeMonitor` will add an AAC-specific configuration that is missing in *ADTS* for proper decoder configuration. Conversely, when the format switches from *AAC* to *ADTS*, it will reconfigure the decoder without the AAC-specific configuration. Depends on D219147 Differential Revision: https://phabricator.services.mozilla.com/D220505
1 parent ee6a610 commit 9b6fc77

File tree

1 file changed

+68
-0
lines changed

1 file changed

+68
-0
lines changed

dom/media/platforms/wrappers/MediaChangeMonitor.cpp

Lines changed: 68 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -6,6 +6,7 @@
66

77
#include "MediaChangeMonitor.h"
88

9+
#include "Adts.h"
910
#include "AnnexB.h"
1011
#include "H264.h"
1112
#include "H265.h"
@@ -588,6 +589,73 @@ class AV1ChangeMonitor : public MediaChangeMonitor::CodecChangeMonitor {
588589
};
589590
#endif
590591

592+
class AACCodecChangeMonitor : public MediaChangeMonitor::CodecChangeMonitor {
593+
public:
594+
explicit AACCodecChangeMonitor(const AudioInfo& aInfo)
595+
: mCurrentConfig(aInfo), mIsADTS(IsADTS(aInfo)) {}
596+
597+
bool CanBeInstantiated() const override { return true; }
598+
599+
MediaResult CheckForChange(MediaRawData* aSample) override {
600+
bool isADTS =
601+
ADTS::FrameHeader::MatchesSync(Span{aSample->Data(), aSample->Size()});
602+
if (isADTS != mIsADTS) {
603+
if (mIsADTS) {
604+
if (!MakeAACSpecificConfig()) {
605+
LOG("Failed to make AAC specific config");
606+
return MediaResult(NS_ERROR_DOM_MEDIA_DECODE_ERR);
607+
}
608+
LOG("Reconfiguring decoder adts -> raw aac, with maked AAC specific "
609+
"config: %zu bytes",
610+
mCurrentConfig.mCodecSpecificConfig
611+
.as<AudioCodecSpecificBinaryBlob>()
612+
.mBinaryBlob->Length());
613+
} else {
614+
LOG("Reconfiguring decoder raw aac -> adts");
615+
// Remove AAC specific config to configure a ADTS decoder.
616+
mCurrentConfig.mCodecSpecificConfig =
617+
AudioCodecSpecificVariant{NoCodecSpecificData{}};
618+
}
619+
620+
mIsADTS = isADTS;
621+
return MediaResult(NS_ERROR_DOM_MEDIA_NEED_NEW_DECODER);
622+
}
623+
return NS_OK;
624+
}
625+
626+
const TrackInfo& Config() const override { return mCurrentConfig; }
627+
628+
MediaResult PrepareSample(MediaDataDecoder::ConversionRequired aConversion,
629+
MediaRawData* aSample,
630+
bool aNeedKeyFrame) override {
631+
return NS_OK;
632+
}
633+
634+
private:
635+
static bool IsADTS(const AudioInfo& aInfo) {
636+
return !aInfo.mCodecSpecificConfig.is<AacCodecSpecificData>() &&
637+
!aInfo.mCodecSpecificConfig.is<AudioCodecSpecificBinaryBlob>();
638+
}
639+
640+
bool MakeAACSpecificConfig() {
641+
MOZ_ASSERT(IsADTS(mCurrentConfig));
642+
// If profile is not set, default to AAC-LC
643+
const uint8_t aacObjectType =
644+
mCurrentConfig.mProfile ? mCurrentConfig.mProfile : 2;
645+
auto r = ADTS::MakeSpecificConfig(aacObjectType, mCurrentConfig.mRate,
646+
mCurrentConfig.mChannels);
647+
if (r.isErr()) {
648+
return false;
649+
}
650+
mCurrentConfig.mCodecSpecificConfig =
651+
AudioCodecSpecificVariant{AudioCodecSpecificBinaryBlob{r.unwrap()}};
652+
return true;
653+
}
654+
655+
AudioInfo mCurrentConfig;
656+
bool mIsADTS;
657+
};
658+
591659
MediaChangeMonitor::MediaChangeMonitor(
592660
PDMFactory* aPDMFactory,
593661
UniquePtr<CodecChangeMonitor>&& aCodecChangeMonitor,

0 commit comments

Comments
 (0)