FFmpegVideoEncoder.h (3485B)
1 /* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */ 2 /* vim:set ts=2 sw=2 sts=2 et cindent: */ 3 /* This Source Code Form is subject to the terms of the Mozilla Public 4 * License, v. 2.0. If a copy of the MPL was not distributed with this 5 * file, You can obtain one at http://mozilla.org/MPL/2.0/. */ 6 7 #ifndef DOM_MEDIA_PLATFORMS_FFMPEG_FFMPEGVIDEOENCODER_H_ 8 #define DOM_MEDIA_PLATFORMS_FFMPEG_FFMPEGVIDEOENCODER_H_ 9 10 #include "FFmpegDataEncoder.h" 11 #include "FFmpegLibWrapper.h" 12 #include "PlatformEncoderModule.h" 13 #include "SimpleMap.h" 14 15 // This must be the last header included 16 #include "FFmpegLibs.h" 17 18 #if LIBAVCODEC_VERSION_MAJOR < 60 || defined(MOZ_WIDGET_ANDROID) 19 # define MOZ_FFMPEG_ENCODER_USE_DURATION_MAP 20 #endif 21 22 namespace mozilla { 23 24 template <int V> 25 class FFmpegVideoEncoder : public FFmpegDataEncoder<V> {}; 26 27 template <> 28 class FFmpegVideoEncoder<LIBAV_VER> final 29 : public FFmpegDataEncoder<LIBAV_VER> { 30 using PtsMap = SimpleMap<int64_t, int64_t, NoOpPolicy>; 31 32 public: 33 NS_INLINE_DECL_THREADSAFE_REFCOUNTING(FFmpegVideoEncoder, final); 34 35 FFmpegVideoEncoder(const FFmpegLibWrapper* aLib, AVCodecID aCodecID, 36 const RefPtr<TaskQueue>& aTaskQueue, 37 const EncoderConfig& aConfig); 38 39 RefPtr<InitPromise> Init() override; 40 41 nsCString GetDescriptionName() const override; 42 43 bool IsHardwareAccelerated(nsACString& aFailureReason) const override { 44 return mIsHardwareAccelerated; 45 } 46 47 protected: 48 virtual ~FFmpegVideoEncoder() = default; 49 // Methods only called on mTaskQueue. 50 virtual MediaResult InitEncoder() override; 51 bool ShouldTryHardware() const; 52 MediaResult InitEncoderInternal(bool aHardware); 53 #if LIBAVCODEC_VERSION_MAJOR >= 58 54 Result<EncodedData, MediaResult> EncodeInputWithModernAPIs( 55 RefPtr<const MediaData> aSample) override; 56 #endif 57 virtual Result<RefPtr<MediaRawData>, MediaResult> ToMediaRawData( 58 AVPacket* aPacket) override; 59 Result<already_AddRefed<MediaByteBuffer>, MediaResult> GetExtraData( 60 AVPacket* aPacket) override; 61 struct SVCSettings { 62 nsTArray<uint8_t> mTemporalLayerIds; 63 // A key-value pair for av_opt_set. 64 std::pair<nsCString, nsCString> mSettingKeyValue; 65 }; 66 bool SvcEnabled() const; 67 Maybe<SVCSettings> GetSVCSettings(); 68 struct H264Settings { 69 int mProfile; 70 int mLevel; 71 // A list of key-value pairs for av_opt_set. 72 nsTArray<std::pair<nsCString, nsCString>> mSettingKeyValuePairs; 73 }; 74 H264Settings GetH264Settings(const H264Specific& aH264Specific); 75 struct SVCInfo { 76 explicit SVCInfo(nsTArray<uint8_t>&& aTemporalLayerIds) 77 : mTemporalLayerIds(std::move(aTemporalLayerIds)), mCurrentIndex(0) {} 78 const nsTArray<uint8_t> mTemporalLayerIds; 79 size_t mCurrentIndex; 80 void UpdateTemporalLayerId(); 81 void ResetTemporalLayerId(); 82 uint8_t CurrentTemporalLayerId(); 83 }; 84 Maybe<SVCInfo> mSVCInfo{}; 85 // Can be accessed on any thread, but only written on during init. 86 Atomic<bool> mIsHardwareAccelerated{false}; 87 #ifdef MOZ_FFMPEG_ENCODER_USE_DURATION_MAP 88 bool mUseDurationMap = false; 89 #endif 90 // Some codecs use the input frames pts for rate control. We'd rather only use 91 // the duration. Synthetize fake pts based on integrating over the duration of 92 // input frames. 93 int64_t mFakePts = 0; 94 int64_t mCurrentFramePts = 0; 95 PtsMap mPtsMap; 96 RefPtr<MediaByteBuffer> mLastExtraData; 97 }; 98 99 } // namespace mozilla 100 101 #endif // DOM_MEDIA_PLATFORMS_FFMPEG_FFMPEGVIDEOENCODER_H_