Chromium Code Reviews| Index: webrtc/video/video_encoder.cc |
| diff --git a/webrtc/video/video_encoder.cc b/webrtc/video/video_encoder.cc |
| index 8847a1072e10be02e2a04ace53a792d9521448ff..93721a28639eb5085b9013e7c65ba2f904fb74e9 100644 |
| --- a/webrtc/video/video_encoder.cc |
| +++ b/webrtc/video/video_encoder.cc |
| @@ -50,15 +50,46 @@ VideoEncoder::EncoderType CodecToEncoderType(VideoCodecType codec_type) { |
| VideoEncoderSoftwareFallbackWrapper::VideoEncoderSoftwareFallbackWrapper( |
| VideoCodecType codec_type, |
| webrtc::VideoEncoder* encoder) |
| - : encoder_type_(CodecToEncoderType(codec_type)), |
| + : rates_set_(false), |
| + channel_parameters_set_(false), |
| + encoder_type_(CodecToEncoderType(codec_type)), |
| encoder_(encoder), |
| - callback_(nullptr) { |
| + callback_(nullptr) {} |
| + |
| +bool VideoEncoderSoftwareFallbackWrapper::InitFallbackEncoder() { |
|
pbos-webrtc
2015/09/09 14:31:02
Should this Release() an initialized encoder_ ?
noahric
2015/10/13 18:08:07
Done. Also added Release() calls to fallback_encod
|
| + CHECK(encoder_type_ != kUnsupportedCodec) |
| + << "Encoder requesting fallback to codec not supported in software."; |
| + fallback_encoder_.reset(VideoEncoder::Create(encoder_type_)); |
| + if (fallback_encoder_->InitEncode(&codec_settings_, number_of_cores_, |
| + max_payload_size_) != |
| + WEBRTC_VIDEO_CODEC_OK) { |
| + LOG(LS_ERROR) << "Failed to initialize software-encoder fallback."; |
| + fallback_encoder_.reset(); |
| + return false; |
| + } |
| + // Replay callback, rates, and channel parameters. |
| + if (callback_) |
| + fallback_encoder_->RegisterEncodeCompleteCallback(callback_); |
| + if (rates_set_) |
| + fallback_encoder_->SetRates(bitrate_, framerate_); |
| + if (channel_parameters_set_) |
| + fallback_encoder_->SetChannelParameters(packet_loss_, rtt_); |
| + return true; |
| } |
| int32_t VideoEncoderSoftwareFallbackWrapper::InitEncode( |
| const VideoCodec* codec_settings, |
| int32_t number_of_cores, |
| size_t max_payload_size) { |
| + // Store settings, in case we need to dynamically switch to the fallback |
| + // encoder after a failed Encode call. |
| + codec_settings_ = *codec_settings; |
| + number_of_cores_ = number_of_cores; |
| + max_payload_size_ = max_payload_size; |
| + // Clear bitrate/framerate override. |
| + rates_set_ = false; |
| + channel_parameters_set_ = false; |
| + |
| int32_t ret = |
| encoder_->InitEncode(codec_settings, number_of_cores, max_payload_size); |
| if (ret == WEBRTC_VIDEO_CODEC_OK || encoder_type_ == kUnsupportedCodec) { |
| @@ -68,16 +99,10 @@ int32_t VideoEncoderSoftwareFallbackWrapper::InitEncode( |
| return ret; |
| } |
| // Try to instantiate software codec. |
| - fallback_encoder_.reset(VideoEncoder::Create(encoder_type_)); |
| - if (fallback_encoder_->InitEncode(codec_settings, number_of_cores, |
| - max_payload_size) == |
| - WEBRTC_VIDEO_CODEC_OK) { |
| - if (callback_) |
| - fallback_encoder_->RegisterEncodeCompleteCallback(callback_); |
| + if (InitFallbackEncoder()) { |
| return WEBRTC_VIDEO_CODEC_OK; |
| } |
| - // Software encoder failed, reset and use original return code. |
| - fallback_encoder_.reset(); |
| + // Software encoder failed, use original return code. |
| return ret; |
| } |
| @@ -91,9 +116,10 @@ int32_t VideoEncoderSoftwareFallbackWrapper::RegisterEncodeCompleteCallback( |
| } |
| int32_t VideoEncoderSoftwareFallbackWrapper::Release() { |
| + int32_t ret = encoder_->Release(); |
|
pbos-webrtc
2015/09/09 14:30:24
Either encoder_ or fallback_encoder_ should be ini
noahric
2015/10/13 18:08:07
I'm worried about two things:
1) encoders not expe
|
| if (fallback_encoder_) |
| return fallback_encoder_->Release(); |
| - return encoder_->Release(); |
| + return ret; |
| } |
| int32_t VideoEncoderSoftwareFallbackWrapper::Encode( |
| @@ -102,12 +128,21 @@ int32_t VideoEncoderSoftwareFallbackWrapper::Encode( |
| const std::vector<VideoFrameType>* frame_types) { |
| if (fallback_encoder_) |
| return fallback_encoder_->Encode(frame, codec_specific_info, frame_types); |
| - return encoder_->Encode(frame, codec_specific_info, frame_types); |
| + int32_t ret = encoder_->Encode(frame, codec_specific_info, frame_types); |
| + // If requested, try a software fallback. |
| + if (ret == WEBRTC_VIDEO_CODEC_FALLBACK_SOFTWARE && InitFallbackEncoder()) { |
| + // Fallback was successful, so start using it with this frame. |
| + return fallback_encoder_->Encode(frame, codec_specific_info, frame_types); |
| + } |
| + return ret; |
| } |
| int32_t VideoEncoderSoftwareFallbackWrapper::SetChannelParameters( |
| uint32_t packet_loss, |
| int64_t rtt) { |
| + channel_parameters_set_ = true; |
| + packet_loss_ = packet_loss; |
| + rtt_ = rtt; |
| int32_t ret = encoder_->SetChannelParameters(packet_loss, rtt); |
| if (fallback_encoder_) |
| return fallback_encoder_->SetChannelParameters(packet_loss, rtt); |
| @@ -116,6 +151,9 @@ int32_t VideoEncoderSoftwareFallbackWrapper::SetChannelParameters( |
| int32_t VideoEncoderSoftwareFallbackWrapper::SetRates(uint32_t bitrate, |
| uint32_t framerate) { |
| + rates_set_ = true; |
| + bitrate_ = bitrate; |
| + framerate_ = framerate; |
| int32_t ret = encoder_->SetRates(bitrate, framerate); |
| if (fallback_encoder_) |
| return fallback_encoder_->SetRates(bitrate, framerate); |