OLD | NEW |
1 /* | 1 /* |
2 * Copyright (c) 2012 The WebRTC project authors. All Rights Reserved. | 2 * Copyright (c) 2012 The WebRTC project authors. All Rights Reserved. |
3 * | 3 * |
4 * Use of this source code is governed by a BSD-style license | 4 * Use of this source code is governed by a BSD-style license |
5 * that can be found in the LICENSE file in the root of the source | 5 * that can be found in the LICENSE file in the root of the source |
6 * tree. An additional intellectual property rights grant can be found | 6 * tree. An additional intellectual property rights grant can be found |
7 * in the file PATENTS. All contributing project authors may | 7 * in the file PATENTS. All contributing project authors may |
8 * be found in the AUTHORS file in the root of the source tree. | 8 * be found in the AUTHORS file in the root of the source tree. |
9 */ | 9 */ |
10 | 10 |
| 11 #include "webrtc/modules/video_coding/generic_decoder.h" |
| 12 |
11 #include "webrtc/base/checks.h" | 13 #include "webrtc/base/checks.h" |
12 #include "webrtc/base/logging.h" | 14 #include "webrtc/base/logging.h" |
13 #include "webrtc/base/timeutils.h" | 15 #include "webrtc/base/timeutils.h" |
14 #include "webrtc/base/trace_event.h" | 16 #include "webrtc/base/trace_event.h" |
15 #include "webrtc/modules/video_coding/include/video_coding.h" | 17 #include "webrtc/modules/video_coding/include/video_coding.h" |
16 #include "webrtc/modules/video_coding/generic_decoder.h" | |
17 #include "webrtc/modules/video_coding/internal_defines.h" | 18 #include "webrtc/modules/video_coding/internal_defines.h" |
18 #include "webrtc/system_wrappers/include/clock.h" | 19 #include "webrtc/system_wrappers/include/clock.h" |
19 | 20 |
20 namespace webrtc { | 21 namespace webrtc { |
21 | 22 |
22 VCMDecodedFrameCallback::VCMDecodedFrameCallback(VCMTiming* timing, | 23 VCMDecodedFrameCallback::VCMDecodedFrameCallback(VCMTiming* timing, |
23 Clock* clock) | 24 Clock* clock) |
24 : _clock(clock), | 25 : _clock(clock), |
25 _timing(timing), | 26 _timing(timing), |
26 _timestampMap(kDecoderFrameMemoryLength), | 27 _timestampMap(kDecoderFrameMemoryLength), |
(...skipping 122 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
149 if (_timestampMap.Pop(timestamp) == NULL) { | 150 if (_timestampMap.Pop(timestamp) == NULL) { |
150 return VCM_GENERAL_ERROR; | 151 return VCM_GENERAL_ERROR; |
151 } | 152 } |
152 return VCM_OK; | 153 return VCM_OK; |
153 } | 154 } |
154 | 155 |
155 VCMGenericDecoder::VCMGenericDecoder(VideoDecoder* decoder, bool isExternal) | 156 VCMGenericDecoder::VCMGenericDecoder(VideoDecoder* decoder, bool isExternal) |
156 : _callback(NULL), | 157 : _callback(NULL), |
157 _frameInfos(), | 158 _frameInfos(), |
158 _nextFrameInfoIdx(0), | 159 _nextFrameInfoIdx(0), |
159 _decoder(decoder), | 160 decoder_(decoder), |
160 _codecType(kVideoCodecUnknown), | 161 _codecType(kVideoCodecUnknown), |
161 _isExternal(isExternal), | 162 _isExternal(isExternal), |
162 _keyFrameDecoded(false), | 163 _last_keyframe_content_type(VideoContentType::UNSPECIFIED) { |
163 _last_keyframe_content_type(VideoContentType::UNSPECIFIED) {} | 164 RTC_DCHECK(decoder_); |
| 165 } |
164 | 166 |
165 VCMGenericDecoder::~VCMGenericDecoder() {} | 167 VCMGenericDecoder::~VCMGenericDecoder() { |
| 168 decoder_->Release(); |
| 169 if (_isExternal) |
| 170 decoder_.release(); |
| 171 RTC_DCHECK(_isExternal || !decoder_); |
| 172 } |
166 | 173 |
167 int32_t VCMGenericDecoder::InitDecode(const VideoCodec* settings, | 174 int32_t VCMGenericDecoder::InitDecode(const VideoCodec* settings, |
168 int32_t numberOfCores) { | 175 int32_t numberOfCores) { |
169 TRACE_EVENT0("webrtc", "VCMGenericDecoder::InitDecode"); | 176 TRACE_EVENT0("webrtc", "VCMGenericDecoder::InitDecode"); |
170 _codecType = settings->codecType; | 177 _codecType = settings->codecType; |
171 | 178 |
172 return _decoder->InitDecode(settings, numberOfCores); | 179 return decoder_->InitDecode(settings, numberOfCores); |
173 } | 180 } |
174 | 181 |
175 int32_t VCMGenericDecoder::Decode(const VCMEncodedFrame& frame, int64_t nowMs) { | 182 int32_t VCMGenericDecoder::Decode(const VCMEncodedFrame& frame, int64_t nowMs) { |
176 TRACE_EVENT1("webrtc", "VCMGenericDecoder::Decode", "timestamp", | 183 TRACE_EVENT1("webrtc", "VCMGenericDecoder::Decode", "timestamp", |
177 frame.EncodedImage()._timeStamp); | 184 frame.EncodedImage()._timeStamp); |
178 _frameInfos[_nextFrameInfoIdx].decodeStartTimeMs = nowMs; | 185 _frameInfos[_nextFrameInfoIdx].decodeStartTimeMs = nowMs; |
179 _frameInfos[_nextFrameInfoIdx].renderTimeMs = frame.RenderTimeMs(); | 186 _frameInfos[_nextFrameInfoIdx].renderTimeMs = frame.RenderTimeMs(); |
180 _frameInfos[_nextFrameInfoIdx].rotation = frame.rotation(); | 187 _frameInfos[_nextFrameInfoIdx].rotation = frame.rotation(); |
181 _frameInfos[_nextFrameInfoIdx].timing = frame.video_timing(); | 188 _frameInfos[_nextFrameInfoIdx].timing = frame.video_timing(); |
182 // Set correctly only for key frames. Thus, use latest key frame | 189 // Set correctly only for key frames. Thus, use latest key frame |
183 // content type. If the corresponding key frame was lost, decode will fail | 190 // content type. If the corresponding key frame was lost, decode will fail |
184 // and content type will be ignored. | 191 // and content type will be ignored. |
185 if (frame.FrameType() == kVideoFrameKey) { | 192 if (frame.FrameType() == kVideoFrameKey) { |
186 _frameInfos[_nextFrameInfoIdx].content_type = frame.contentType(); | 193 _frameInfos[_nextFrameInfoIdx].content_type = frame.contentType(); |
187 _last_keyframe_content_type = frame.contentType(); | 194 _last_keyframe_content_type = frame.contentType(); |
188 } else { | 195 } else { |
189 _frameInfos[_nextFrameInfoIdx].content_type = _last_keyframe_content_type; | 196 _frameInfos[_nextFrameInfoIdx].content_type = _last_keyframe_content_type; |
190 } | 197 } |
191 _callback->Map(frame.TimeStamp(), &_frameInfos[_nextFrameInfoIdx]); | 198 _callback->Map(frame.TimeStamp(), &_frameInfos[_nextFrameInfoIdx]); |
192 | 199 |
193 _nextFrameInfoIdx = (_nextFrameInfoIdx + 1) % kDecoderFrameMemoryLength; | 200 _nextFrameInfoIdx = (_nextFrameInfoIdx + 1) % kDecoderFrameMemoryLength; |
194 const RTPFragmentationHeader dummy_header; | 201 const RTPFragmentationHeader dummy_header; |
195 int32_t ret = _decoder->Decode(frame.EncodedImage(), frame.MissingFrame(), | 202 int32_t ret = decoder_->Decode(frame.EncodedImage(), frame.MissingFrame(), |
196 &dummy_header, | 203 &dummy_header, |
197 frame.CodecSpecific(), frame.RenderTimeMs()); | 204 frame.CodecSpecific(), frame.RenderTimeMs()); |
198 | 205 |
199 _callback->OnDecoderImplementationName(_decoder->ImplementationName()); | 206 _callback->OnDecoderImplementationName(decoder_->ImplementationName()); |
200 if (ret < WEBRTC_VIDEO_CODEC_OK) { | 207 if (ret < WEBRTC_VIDEO_CODEC_OK) { |
201 LOG(LS_WARNING) << "Failed to decode frame with timestamp " | 208 LOG(LS_WARNING) << "Failed to decode frame with timestamp " |
202 << frame.TimeStamp() << ", error code: " << ret; | 209 << frame.TimeStamp() << ", error code: " << ret; |
203 _callback->Pop(frame.TimeStamp()); | 210 _callback->Pop(frame.TimeStamp()); |
204 return ret; | 211 return ret; |
205 } else if (ret == WEBRTC_VIDEO_CODEC_NO_OUTPUT || | 212 } else if (ret == WEBRTC_VIDEO_CODEC_NO_OUTPUT || |
206 ret == WEBRTC_VIDEO_CODEC_REQUEST_SLI) { | 213 ret == WEBRTC_VIDEO_CODEC_REQUEST_SLI) { |
207 // No output | 214 // No output |
208 _callback->Pop(frame.TimeStamp()); | 215 _callback->Pop(frame.TimeStamp()); |
209 } | 216 } |
210 return ret; | 217 return ret; |
211 } | 218 } |
212 | 219 |
213 int32_t VCMGenericDecoder::Release() { | |
214 return _decoder->Release(); | |
215 } | |
216 | |
217 int32_t VCMGenericDecoder::RegisterDecodeCompleteCallback( | 220 int32_t VCMGenericDecoder::RegisterDecodeCompleteCallback( |
218 VCMDecodedFrameCallback* callback) { | 221 VCMDecodedFrameCallback* callback) { |
219 _callback = callback; | 222 _callback = callback; |
220 return _decoder->RegisterDecodeCompleteCallback(callback); | 223 return decoder_->RegisterDecodeCompleteCallback(callback); |
221 } | |
222 | |
223 bool VCMGenericDecoder::External() const { | |
224 return _isExternal; | |
225 } | 224 } |
226 | 225 |
227 bool VCMGenericDecoder::PrefersLateDecoding() const { | 226 bool VCMGenericDecoder::PrefersLateDecoding() const { |
228 return _decoder->PrefersLateDecoding(); | 227 return decoder_->PrefersLateDecoding(); |
229 } | 228 } |
230 | 229 |
231 } // namespace webrtc | 230 } // namespace webrtc |
OLD | NEW |