#599: H.264 improvements

This commit is contained in:
Cameron Kaiser 2020-04-14 22:33:40 -07:00
parent 2fa4af8eb2
commit 6428efdd0e
5 changed files with 38 additions and 11 deletions

View File

@ -8,6 +8,7 @@
#include <string.h>
#include <unistd.h>
#include <sys/sysctl.h>
#include "FFmpegLog.h"
#include "FFmpegDataDecoder.h"
@ -41,6 +42,7 @@ FFmpegDataDecoder<LIBAV_VER>::FFmpegDataDecoder(FlushableTaskQueue* aTaskQueue,
, mMonitor("FFMpegaDataDecoder")
, mIsFlushing(false)
, mCodecParser(nullptr)
, mHQ(false)
{
MOZ_COUNT_CTOR(FFmpegDataDecoder);
}
@ -108,10 +110,27 @@ FFmpegDataDecoder<LIBAV_VER>::InitDecoder()
// FFmpeg will call back to this to negotiate a video pixel format.
mCodecContext->get_format = ChoosePixelFormat;
mCodecContext->thread_count = PR_GetNumberOfProcessors();
//mCodecContext->thread_count = PR_GetNumberOfProcessors();
// PR_GetNumberOfProcessors() lies on TenFourFox. Get from sysctl().
// TenFourFox issue 599.
int mib[2] = { CTL_HW, HW_NCPU };
size_t len = sizeof(mCodecContext->thread_count);
if (sysctl(mib, 2, &(mCodecContext->thread_count), &len, NULL, 0) == -1)
mCodecContext->thread_count = 1;
#if DEBUG
fprintf(stderr, "FFmpeg using %d CPUs.\n", mCodecContext->thread_count);
#endif
mCodecContext->thread_type = FF_THREAD_SLICE | FF_THREAD_FRAME;
mCodecContext->thread_safe_callbacks = false;
if (!mHQ) {
// Enable skipping the loop filter and FFmpeg's lightly documented
// non-spec-compliant mode. TenFourFox issue 599. This is pushed here
// because this is not on the main thread, so we assert.
mCodecContext->flags2 |= CODEC_FLAG2_FAST;
mCodecContext->skip_loop_filter = AVDISCARD_ALL;
}
if (mExtraData) {
mCodecContext->extradata_size = mExtraData->Length();
// FFmpeg may use SIMD instructions to access the data which reads the

View File

@ -38,6 +38,7 @@ public:
static AVCodec* FindAVCodec(AVCodecID aCodec);
bool mHQ; // TenFourFox high quality mode (issue 599)
protected:
// Flush and Drain operation, always run
virtual void ProcessFlush();

View File

@ -19,14 +19,14 @@ class FFmpegDecoderModule : public PlatformDecoderModule
{
public:
static already_AddRefed<PlatformDecoderModule>
Create()
Create(bool hq)
{
RefPtr<PlatformDecoderModule> pdm = new FFmpegDecoderModule();
RefPtr<PlatformDecoderModule> pdm = new FFmpegDecoderModule(hq);
return pdm.forget();
}
FFmpegDecoderModule() {}
FFmpegDecoderModule(bool hq) : mHQ(hq) {}
virtual ~FFmpegDecoderModule() {}
already_AddRefed<MediaDataDecoder>
@ -75,6 +75,7 @@ public:
}
}
bool mHQ; // TenFourFox high quality mode (issue 599).
};
} // namespace mozilla

View File

@ -99,7 +99,7 @@ FFmpegH264Decoder<LIBAV_VER>::DecodeResult
FFmpegH264Decoder<LIBAV_VER>::DoDecodeFrame(MediaRawData* aSample)
{
MOZ_ASSERT(mTaskQueue->IsCurrentThreadIn());
if (PR_Now() < sLockOutDueToOOM) {
if (MOZ_UNLIKELY(PR_Now() < sLockOutDueToOOM)) {
// Halt further allocations.
NS_WARNING("** FFMPEG LOCKED OUT DUE TO OUT OF MEMORY **");
mCallback->Error();
@ -152,7 +152,7 @@ FFmpegH264Decoder<LIBAV_VER>::DoDecodeFrame(MediaRawData* aSample,
uint8_t* aData, int aSize)
{
MOZ_ASSERT(mTaskQueue->IsCurrentThreadIn());
if (PR_Now() < sLockOutDueToOOM) {
if (MOZ_UNLIKELY(PR_Now() < sLockOutDueToOOM)) {
// Halt further allocations.
NS_WARNING("** FFMPEG LOCKED OUT DUE TO OUT OF MEMORY **");
mCallback->Error();

View File

@ -17,6 +17,9 @@
#include <mach-o/dyld.h>
#endif /* XP_DARWIN */
/* TenFourFox issue 599 */
static bool sHQ = false;
namespace mozilla
{
@ -26,7 +29,7 @@ FFmpegRuntimeLinker::LinkStatus FFmpegRuntimeLinker::sLinkStatus =
template <int V> class FFmpegDecoderModule
{
public:
static already_AddRefed<PlatformDecoderModule> Create();
static already_AddRefed<PlatformDecoderModule> Create(bool hq);
};
static const char* sLibs[] = {
@ -175,6 +178,9 @@ FFmpegRuntimeLinker::Bind(const char* aLibName)
return false;
}
/* This is the only safe place to get preferences. TenFourFox issue 599. */
sHQ = Preferences::GetBool("tenfourfox.mp4.high_quality", false);
int version;
switch (major) {
case 53:
@ -243,11 +249,11 @@ FFmpegRuntimeLinker::CreateDecoderModule()
RefPtr<PlatformDecoderModule> module;
switch (major) {
case 53: module = FFmpegDecoderModule<53>::Create(); break;
case 54: module = FFmpegDecoderModule<54>::Create(); break;
case 53: module = FFmpegDecoderModule<53>::Create(sHQ); break;
case 54: module = FFmpegDecoderModule<54>::Create(sHQ); break;
case 55:
case 56: module = FFmpegDecoderModule<55>::Create(); break;
case 57: module = FFmpegDecoderModule<57>::Create(); break;
case 56: module = FFmpegDecoderModule<55>::Create(sHQ); break;
case 57: module = FFmpegDecoderModule<57>::Create(sHQ); break;
default: module = nullptr;
}
return module.forget();