/src/mozilla-central/dom/media/platforms/ffmpeg/FFmpegDataDecoder.cpp
Line | Count | Source (jump to first uncovered line) |
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 | | |
8 | | #include <string.h> |
9 | | #ifdef __GNUC__ |
10 | | #include <unistd.h> |
11 | | #endif |
12 | | |
13 | | #include "FFmpegLog.h" |
14 | | #include "FFmpegDataDecoder.h" |
15 | | #include "mozilla/TaskQueue.h" |
16 | | #include "prsystem.h" |
17 | | |
18 | | namespace mozilla { |
19 | | |
20 | | StaticMutex FFmpegDataDecoder<LIBAV_VER>::sMonitor; |
21 | | |
22 | | FFmpegDataDecoder<LIBAV_VER>::FFmpegDataDecoder(FFmpegLibWrapper* aLib, |
23 | | TaskQueue* aTaskQueue, |
24 | | AVCodecID aCodecID) |
25 | | : mLib(aLib) |
26 | | , mCodecContext(nullptr) |
27 | | , mCodecParser(nullptr) |
28 | | , mFrame(NULL) |
29 | | , mExtraData(nullptr) |
30 | | , mCodecID(aCodecID) |
31 | | , mTaskQueue(aTaskQueue) |
32 | | , mLastInputDts(media::TimeUnit::FromMicroseconds(INT64_MIN)) |
33 | 0 | { |
34 | 0 | MOZ_ASSERT(aLib); |
35 | 0 | MOZ_COUNT_CTOR(FFmpegDataDecoder); |
36 | 0 | } Unexecuted instantiation: mozilla::FFmpegDataDecoder<46465650>::FFmpegDataDecoder(mozilla::FFmpegLibWrapper*, mozilla::TaskQueue*, AVCodecID) Unexecuted instantiation: mozilla::FFmpegDataDecoder<53>::FFmpegDataDecoder(mozilla::FFmpegLibWrapper*, mozilla::TaskQueue*, CodecID) Unexecuted instantiation: mozilla::FFmpegDataDecoder<54>::FFmpegDataDecoder(mozilla::FFmpegLibWrapper*, mozilla::TaskQueue*, AVCodecID) Unexecuted instantiation: mozilla::FFmpegDataDecoder<55>::FFmpegDataDecoder(mozilla::FFmpegLibWrapper*, mozilla::TaskQueue*, AVCodecID) Unexecuted instantiation: mozilla::FFmpegDataDecoder<57>::FFmpegDataDecoder(mozilla::FFmpegLibWrapper*, mozilla::TaskQueue*, AVCodecID) Unexecuted instantiation: mozilla::FFmpegDataDecoder<58>::FFmpegDataDecoder(mozilla::FFmpegLibWrapper*, mozilla::TaskQueue*, AVCodecID) |
37 | | |
38 | | FFmpegDataDecoder<LIBAV_VER>::~FFmpegDataDecoder() |
39 | 0 | { |
40 | 0 | MOZ_COUNT_DTOR(FFmpegDataDecoder); |
41 | 0 | if (mCodecParser) { |
42 | 0 | mLib->av_parser_close(mCodecParser); |
43 | 0 | mCodecParser = nullptr; |
44 | 0 | } |
45 | 0 | } Unexecuted instantiation: mozilla::FFmpegDataDecoder<46465650>::~FFmpegDataDecoder() Unexecuted instantiation: mozilla::FFmpegDataDecoder<53>::~FFmpegDataDecoder() Unexecuted instantiation: mozilla::FFmpegDataDecoder<54>::~FFmpegDataDecoder() Unexecuted instantiation: mozilla::FFmpegDataDecoder<55>::~FFmpegDataDecoder() Unexecuted instantiation: mozilla::FFmpegDataDecoder<57>::~FFmpegDataDecoder() Unexecuted instantiation: mozilla::FFmpegDataDecoder<58>::~FFmpegDataDecoder() |
46 | | |
47 | | MediaResult |
48 | | FFmpegDataDecoder<LIBAV_VER>::InitDecoder() |
49 | 0 | { |
50 | 0 | FFMPEG_LOG("Initialising FFmpeg decoder."); |
51 | 0 |
|
52 | 0 | AVCodec* codec = FindAVCodec(mLib, mCodecID); |
53 | 0 | if (!codec) { |
54 | 0 | return MediaResult(NS_ERROR_DOM_MEDIA_FATAL_ERR, |
55 | 0 | RESULT_DETAIL("Couldn't find ffmpeg decoder")); |
56 | 0 | } |
57 | 0 |
|
58 | 0 | StaticMutexAutoLock mon(sMonitor); |
59 | 0 |
|
60 | 0 | if (!(mCodecContext = mLib->avcodec_alloc_context3(codec))) { |
61 | 0 | return MediaResult(NS_ERROR_OUT_OF_MEMORY, |
62 | 0 | RESULT_DETAIL("Couldn't init ffmpeg context")); |
63 | 0 | } |
64 | 0 |
|
65 | 0 | if (NeedParser()) { |
66 | 0 | MOZ_ASSERT(mCodecParser == nullptr); |
67 | 0 | mCodecParser = mLib->av_parser_init(mCodecID); |
68 | 0 | if (mCodecParser) { |
69 | 0 | mCodecParser->flags |= ParserFlags(); |
70 | 0 | } |
71 | 0 | } |
72 | 0 | mCodecContext->opaque = this; |
73 | 0 |
|
74 | 0 | InitCodecContext(); |
75 | 0 |
|
76 | 0 | if (mExtraData) { |
77 | 0 | mCodecContext->extradata_size = mExtraData->Length(); |
78 | 0 | // FFmpeg may use SIMD instructions to access the data which reads the |
79 | 0 | // data in 32 bytes block. Must ensure we have enough data to read. |
80 | 0 | uint32_t padding_size = |
81 | | #if LIBAVCODEC_VERSION_MAJOR >= 58 |
82 | 0 | AV_INPUT_BUFFER_PADDING_SIZE; |
83 | | #else |
84 | 0 | FF_INPUT_BUFFER_PADDING_SIZE; |
85 | | #endif |
86 | | mCodecContext->extradata = static_cast<uint8_t*>( |
87 | 0 | mLib->av_malloc(mExtraData->Length() + padding_size)); |
88 | 0 | if (!mCodecContext->extradata) { |
89 | 0 | return MediaResult(NS_ERROR_OUT_OF_MEMORY, |
90 | 0 | RESULT_DETAIL("Couldn't init ffmpeg extradata")); |
91 | 0 | } |
92 | 0 | memcpy(mCodecContext->extradata, |
93 | 0 | mExtraData->Elements(), |
94 | 0 | mExtraData->Length()); |
95 | 0 | } else { |
96 | 0 | mCodecContext->extradata_size = 0; |
97 | 0 | } |
98 | 0 |
|
99 | | #if LIBAVCODEC_VERSION_MAJOR < 57 |
100 | 0 | if (codec->capabilities & CODEC_CAP_DR1) { |
101 | 0 | mCodecContext->flags |= CODEC_FLAG_EMU_EDGE; |
102 | 0 | } |
103 | | #endif |
104 | |
|
105 | 0 | if (mLib->avcodec_open2(mCodecContext, codec, nullptr) < 0) { |
106 | 0 | mLib->avcodec_close(mCodecContext); |
107 | 0 | mLib->av_freep(&mCodecContext); |
108 | 0 | return MediaResult(NS_ERROR_DOM_MEDIA_FATAL_ERR, |
109 | 0 | RESULT_DETAIL("Couldn't initialise ffmpeg decoder")); |
110 | 0 | } |
111 | 0 |
|
112 | 0 | FFMPEG_LOG("FFmpeg init successful."); |
113 | 0 | return NS_OK; |
114 | 0 | } Unexecuted instantiation: mozilla::FFmpegDataDecoder<46465650>::InitDecoder() Unexecuted instantiation: mozilla::FFmpegDataDecoder<53>::InitDecoder() Unexecuted instantiation: mozilla::FFmpegDataDecoder<54>::InitDecoder() Unexecuted instantiation: mozilla::FFmpegDataDecoder<55>::InitDecoder() Unexecuted instantiation: mozilla::FFmpegDataDecoder<57>::InitDecoder() Unexecuted instantiation: mozilla::FFmpegDataDecoder<58>::InitDecoder() |
115 | | |
116 | | RefPtr<ShutdownPromise> |
117 | | FFmpegDataDecoder<LIBAV_VER>::Shutdown() |
118 | 0 | { |
119 | 0 | if (mTaskQueue) { |
120 | 0 | RefPtr<FFmpegDataDecoder<LIBAV_VER>> self = this; |
121 | 0 | return InvokeAsync(mTaskQueue, __func__, [self]() { |
122 | 0 | self->ProcessShutdown(); |
123 | 0 | return ShutdownPromise::CreateAndResolve(true, __func__); |
124 | 0 | }); Unexecuted instantiation: Unified_cpp_ffmpeg_ffvpx0.cpp:mozilla::FFmpegDataDecoder<46465650>::Shutdown()::$_0::operator()() const Unexecuted instantiation: Unified_cpp_ffmpeg_libav530.cpp:mozilla::FFmpegDataDecoder<53>::Shutdown()::$_0::operator()() const Unexecuted instantiation: Unified_cpp_ffmpeg_libav540.cpp:mozilla::FFmpegDataDecoder<54>::Shutdown()::$_0::operator()() const Unexecuted instantiation: Unified_cpp_ffmpeg_libav550.cpp:mozilla::FFmpegDataDecoder<55>::Shutdown()::$_0::operator()() const Unexecuted instantiation: Unified_cpp_ffmpeg_ffmpeg570.cpp:mozilla::FFmpegDataDecoder<57>::Shutdown()::$_0::operator()() const Unexecuted instantiation: Unified_cpp_ffmpeg_ffmpeg580.cpp:mozilla::FFmpegDataDecoder<58>::Shutdown()::$_0::operator()() const |
125 | 0 | } |
126 | 0 | ProcessShutdown(); |
127 | 0 | return ShutdownPromise::CreateAndResolve(true, __func__); |
128 | 0 | } Unexecuted instantiation: mozilla::FFmpegDataDecoder<46465650>::Shutdown() Unexecuted instantiation: mozilla::FFmpegDataDecoder<53>::Shutdown() Unexecuted instantiation: mozilla::FFmpegDataDecoder<54>::Shutdown() Unexecuted instantiation: mozilla::FFmpegDataDecoder<55>::Shutdown() Unexecuted instantiation: mozilla::FFmpegDataDecoder<57>::Shutdown() Unexecuted instantiation: mozilla::FFmpegDataDecoder<58>::Shutdown() |
129 | | |
130 | | RefPtr<MediaDataDecoder::DecodePromise> |
131 | | FFmpegDataDecoder<LIBAV_VER>::Decode(MediaRawData* aSample) |
132 | 0 | { |
133 | 0 | return InvokeAsync<MediaRawData*>(mTaskQueue, this, __func__, |
134 | 0 | &FFmpegDataDecoder::ProcessDecode, aSample); |
135 | 0 | } Unexecuted instantiation: mozilla::FFmpegDataDecoder<46465650>::Decode(mozilla::MediaRawData*) Unexecuted instantiation: mozilla::FFmpegDataDecoder<53>::Decode(mozilla::MediaRawData*) Unexecuted instantiation: mozilla::FFmpegDataDecoder<54>::Decode(mozilla::MediaRawData*) Unexecuted instantiation: mozilla::FFmpegDataDecoder<55>::Decode(mozilla::MediaRawData*) Unexecuted instantiation: mozilla::FFmpegDataDecoder<57>::Decode(mozilla::MediaRawData*) Unexecuted instantiation: mozilla::FFmpegDataDecoder<58>::Decode(mozilla::MediaRawData*) |
136 | | |
137 | | RefPtr<MediaDataDecoder::DecodePromise> |
138 | | FFmpegDataDecoder<LIBAV_VER>::ProcessDecode(MediaRawData* aSample) |
139 | 0 | { |
140 | 0 | bool gotFrame = false; |
141 | 0 | DecodedData results; |
142 | 0 | MediaResult rv = DoDecode(aSample, &gotFrame, results); |
143 | 0 | if (NS_FAILED(rv)) { |
144 | 0 | return DecodePromise::CreateAndReject(rv, __func__); |
145 | 0 | } |
146 | 0 | return DecodePromise::CreateAndResolve(std::move(results), __func__); |
147 | 0 | } Unexecuted instantiation: mozilla::FFmpegDataDecoder<46465650>::ProcessDecode(mozilla::MediaRawData*) Unexecuted instantiation: mozilla::FFmpegDataDecoder<53>::ProcessDecode(mozilla::MediaRawData*) Unexecuted instantiation: mozilla::FFmpegDataDecoder<54>::ProcessDecode(mozilla::MediaRawData*) Unexecuted instantiation: mozilla::FFmpegDataDecoder<55>::ProcessDecode(mozilla::MediaRawData*) Unexecuted instantiation: mozilla::FFmpegDataDecoder<57>::ProcessDecode(mozilla::MediaRawData*) Unexecuted instantiation: mozilla::FFmpegDataDecoder<58>::ProcessDecode(mozilla::MediaRawData*) |
148 | | |
149 | | MediaResult |
150 | | FFmpegDataDecoder<LIBAV_VER>::DoDecode(MediaRawData* aSample, bool* aGotFrame, |
151 | | MediaDataDecoder::DecodedData& aResults) |
152 | 0 | { |
153 | 0 | uint8_t* inputData = const_cast<uint8_t*>(aSample->Data()); |
154 | 0 | size_t inputSize = aSample->Size(); |
155 | 0 |
|
156 | 0 | mLastInputDts = aSample->mTimecode; |
157 | 0 |
|
158 | 0 | if (inputData && mCodecParser) { // inputData is null when draining. |
159 | 0 | if (aGotFrame) { |
160 | 0 | *aGotFrame = false; |
161 | 0 | } |
162 | 0 | while (inputSize) { |
163 | 0 | uint8_t* data = inputData; |
164 | 0 | int size = inputSize; |
165 | 0 | int len = mLib->av_parser_parse2( |
166 | 0 | mCodecParser, mCodecContext, &data, &size, inputData, inputSize, |
167 | 0 | aSample->mTime.ToMicroseconds(), aSample->mTimecode.ToMicroseconds(), |
168 | 0 | aSample->mOffset); |
169 | 0 | if (size_t(len) > inputSize) { |
170 | 0 | return NS_ERROR_DOM_MEDIA_DECODE_ERR; |
171 | 0 | } |
172 | 0 | if (size) { |
173 | 0 | bool gotFrame = false; |
174 | 0 | MediaResult rv = DoDecode(aSample, data, size, &gotFrame, aResults); |
175 | 0 | if (NS_FAILED(rv)) { |
176 | 0 | return rv; |
177 | 0 | } |
178 | 0 | if (gotFrame && aGotFrame) { |
179 | 0 | *aGotFrame = true; |
180 | 0 | } |
181 | 0 | } |
182 | 0 | inputData += len; |
183 | 0 | inputSize -= len; |
184 | 0 | } |
185 | 0 | return NS_OK; |
186 | 0 | } |
187 | 0 | return DoDecode(aSample, inputData, inputSize, aGotFrame, aResults); |
188 | 0 | } Unexecuted instantiation: mozilla::FFmpegDataDecoder<46465650>::DoDecode(mozilla::MediaRawData*, bool*, nsTArray<RefPtr<mozilla::MediaData> >&) Unexecuted instantiation: mozilla::FFmpegDataDecoder<53>::DoDecode(mozilla::MediaRawData*, bool*, nsTArray<RefPtr<mozilla::MediaData> >&) Unexecuted instantiation: mozilla::FFmpegDataDecoder<54>::DoDecode(mozilla::MediaRawData*, bool*, nsTArray<RefPtr<mozilla::MediaData> >&) Unexecuted instantiation: mozilla::FFmpegDataDecoder<55>::DoDecode(mozilla::MediaRawData*, bool*, nsTArray<RefPtr<mozilla::MediaData> >&) Unexecuted instantiation: mozilla::FFmpegDataDecoder<57>::DoDecode(mozilla::MediaRawData*, bool*, nsTArray<RefPtr<mozilla::MediaData> >&) Unexecuted instantiation: mozilla::FFmpegDataDecoder<58>::DoDecode(mozilla::MediaRawData*, bool*, nsTArray<RefPtr<mozilla::MediaData> >&) |
189 | | |
190 | | RefPtr<MediaDataDecoder::FlushPromise> |
191 | | FFmpegDataDecoder<LIBAV_VER>::Flush() |
192 | 0 | { |
193 | 0 | return InvokeAsync(mTaskQueue, this, __func__, |
194 | 0 | &FFmpegDataDecoder<LIBAV_VER>::ProcessFlush); |
195 | 0 | } Unexecuted instantiation: mozilla::FFmpegDataDecoder<46465650>::Flush() Unexecuted instantiation: mozilla::FFmpegDataDecoder<53>::Flush() Unexecuted instantiation: mozilla::FFmpegDataDecoder<54>::Flush() Unexecuted instantiation: mozilla::FFmpegDataDecoder<55>::Flush() Unexecuted instantiation: mozilla::FFmpegDataDecoder<57>::Flush() Unexecuted instantiation: mozilla::FFmpegDataDecoder<58>::Flush() |
196 | | |
197 | | RefPtr<MediaDataDecoder::DecodePromise> |
198 | | FFmpegDataDecoder<LIBAV_VER>::Drain() |
199 | 0 | { |
200 | 0 | return InvokeAsync(mTaskQueue, this, __func__, |
201 | 0 | &FFmpegDataDecoder<LIBAV_VER>::ProcessDrain); |
202 | 0 | } Unexecuted instantiation: mozilla::FFmpegDataDecoder<46465650>::Drain() Unexecuted instantiation: mozilla::FFmpegDataDecoder<53>::Drain() Unexecuted instantiation: mozilla::FFmpegDataDecoder<54>::Drain() Unexecuted instantiation: mozilla::FFmpegDataDecoder<55>::Drain() Unexecuted instantiation: mozilla::FFmpegDataDecoder<57>::Drain() Unexecuted instantiation: mozilla::FFmpegDataDecoder<58>::Drain() |
203 | | |
204 | | RefPtr<MediaDataDecoder::DecodePromise> |
205 | | FFmpegDataDecoder<LIBAV_VER>::ProcessDrain() |
206 | 0 | { |
207 | 0 | RefPtr<MediaRawData> empty(new MediaRawData()); |
208 | 0 | empty->mTimecode = mLastInputDts; |
209 | 0 | bool gotFrame = false; |
210 | 0 | DecodedData results; |
211 | 0 | while (NS_SUCCEEDED(DoDecode(empty, &gotFrame, results)) && |
212 | 0 | gotFrame) { |
213 | 0 | } |
214 | 0 | return DecodePromise::CreateAndResolve(std::move(results), __func__); |
215 | 0 | } Unexecuted instantiation: mozilla::FFmpegDataDecoder<46465650>::ProcessDrain() Unexecuted instantiation: mozilla::FFmpegDataDecoder<53>::ProcessDrain() Unexecuted instantiation: mozilla::FFmpegDataDecoder<54>::ProcessDrain() Unexecuted instantiation: mozilla::FFmpegDataDecoder<55>::ProcessDrain() Unexecuted instantiation: mozilla::FFmpegDataDecoder<57>::ProcessDrain() Unexecuted instantiation: mozilla::FFmpegDataDecoder<58>::ProcessDrain() |
216 | | |
217 | | RefPtr<MediaDataDecoder::FlushPromise> |
218 | | FFmpegDataDecoder<LIBAV_VER>::ProcessFlush() |
219 | 0 | { |
220 | 0 | MOZ_ASSERT(mTaskQueue->IsCurrentThreadIn()); |
221 | 0 | if (mCodecContext) { |
222 | 0 | mLib->avcodec_flush_buffers(mCodecContext); |
223 | 0 | } |
224 | 0 | if (mCodecParser) { |
225 | 0 | mLib->av_parser_close(mCodecParser); |
226 | 0 | mCodecParser = mLib->av_parser_init(mCodecID); |
227 | 0 | } |
228 | 0 | return FlushPromise::CreateAndResolve(true, __func__); |
229 | 0 | } Unexecuted instantiation: mozilla::FFmpegDataDecoder<46465650>::ProcessFlush() Unexecuted instantiation: mozilla::FFmpegDataDecoder<53>::ProcessFlush() Unexecuted instantiation: mozilla::FFmpegDataDecoder<54>::ProcessFlush() Unexecuted instantiation: mozilla::FFmpegDataDecoder<55>::ProcessFlush() Unexecuted instantiation: mozilla::FFmpegDataDecoder<57>::ProcessFlush() Unexecuted instantiation: mozilla::FFmpegDataDecoder<58>::ProcessFlush() |
230 | | |
231 | | void |
232 | | FFmpegDataDecoder<LIBAV_VER>::ProcessShutdown() |
233 | 0 | { |
234 | 0 | StaticMutexAutoLock mon(sMonitor); |
235 | 0 |
|
236 | 0 | if (mCodecContext) { |
237 | 0 | if (mCodecContext->extradata) { |
238 | 0 | mLib->av_freep(&mCodecContext->extradata); |
239 | 0 | } |
240 | 0 | mLib->avcodec_close(mCodecContext); |
241 | 0 | mLib->av_freep(&mCodecContext); |
242 | | #if LIBAVCODEC_VERSION_MAJOR >= 55 |
243 | | mLib->av_frame_free(&mFrame); |
244 | | #elif LIBAVCODEC_VERSION_MAJOR == 54 |
245 | | mLib->avcodec_free_frame(&mFrame); |
246 | | #else |
247 | | mLib->av_freep(&mFrame); |
248 | | #endif |
249 | | } |
250 | 0 | } Unexecuted instantiation: mozilla::FFmpegDataDecoder<46465650>::ProcessShutdown() Unexecuted instantiation: mozilla::FFmpegDataDecoder<53>::ProcessShutdown() Unexecuted instantiation: mozilla::FFmpegDataDecoder<54>::ProcessShutdown() Unexecuted instantiation: mozilla::FFmpegDataDecoder<55>::ProcessShutdown() Unexecuted instantiation: mozilla::FFmpegDataDecoder<57>::ProcessShutdown() Unexecuted instantiation: mozilla::FFmpegDataDecoder<58>::ProcessShutdown() |
251 | | |
252 | | AVFrame* |
253 | | FFmpegDataDecoder<LIBAV_VER>::PrepareFrame() |
254 | 0 | { |
255 | 0 | MOZ_ASSERT(mTaskQueue->IsCurrentThreadIn()); |
256 | | #if LIBAVCODEC_VERSION_MAJOR >= 55 |
257 | 0 | if (mFrame) { |
258 | 0 | mLib->av_frame_unref(mFrame); |
259 | 0 | } else { |
260 | 0 | mFrame = mLib->av_frame_alloc(); |
261 | 0 | } |
262 | | #elif LIBAVCODEC_VERSION_MAJOR == 54 |
263 | 0 | if (mFrame) { |
264 | 0 | mLib->avcodec_get_frame_defaults(mFrame); |
265 | 0 | } else { |
266 | 0 | mFrame = mLib->avcodec_alloc_frame(); |
267 | 0 | } |
268 | | #else |
269 | | mLib->av_freep(&mFrame); |
270 | | mFrame = mLib->avcodec_alloc_frame(); |
271 | | #endif |
272 | | return mFrame; |
273 | 0 | } Unexecuted instantiation: mozilla::FFmpegDataDecoder<46465650>::PrepareFrame() Unexecuted instantiation: mozilla::FFmpegDataDecoder<53>::PrepareFrame() Unexecuted instantiation: mozilla::FFmpegDataDecoder<54>::PrepareFrame() Unexecuted instantiation: mozilla::FFmpegDataDecoder<55>::PrepareFrame() Unexecuted instantiation: mozilla::FFmpegDataDecoder<57>::PrepareFrame() Unexecuted instantiation: mozilla::FFmpegDataDecoder<58>::PrepareFrame() |
274 | | |
275 | | /* static */ AVCodec* |
276 | | FFmpegDataDecoder<LIBAV_VER>::FindAVCodec(FFmpegLibWrapper* aLib, |
277 | | AVCodecID aCodec) |
278 | 0 | { |
279 | 0 | return aLib->avcodec_find_decoder(aCodec); |
280 | 0 | } Unexecuted instantiation: mozilla::FFmpegDataDecoder<46465650>::FindAVCodec(mozilla::FFmpegLibWrapper*, AVCodecID) Unexecuted instantiation: mozilla::FFmpegDataDecoder<53>::FindAVCodec(mozilla::FFmpegLibWrapper*, CodecID) Unexecuted instantiation: mozilla::FFmpegDataDecoder<54>::FindAVCodec(mozilla::FFmpegLibWrapper*, AVCodecID) Unexecuted instantiation: mozilla::FFmpegDataDecoder<55>::FindAVCodec(mozilla::FFmpegLibWrapper*, AVCodecID) Unexecuted instantiation: mozilla::FFmpegDataDecoder<57>::FindAVCodec(mozilla::FFmpegLibWrapper*, AVCodecID) Unexecuted instantiation: mozilla::FFmpegDataDecoder<58>::FindAVCodec(mozilla::FFmpegLibWrapper*, AVCodecID) |
281 | | |
282 | | } // namespace mozilla |