Remove ViE interface usage from VideoReceiveStream.

References channels and underlying objects directly instead of using
interfaces referenced with channel id. Channel creation is still done as
before for now.

BUG=1695
R=stefan@webrtc.org
TBR=mflodman@webrtc.org

Review URL: https://webrtc-codereview.appspot.com/46849004

Cr-Commit-Position: refs/heads/master@{#8958}
This commit is contained in:
Peter Boström 2015-04-09 14:35:37 +02:00
parent 15cf019a00
commit 76c53d36bc
12 changed files with 149 additions and 108 deletions

View File

@ -699,6 +699,13 @@ class FakeWebRtcVideoEngine
return 0;
}
WEBRTC_STUB(CreateChannelWithoutDefaultEncoder, (int&, int original_channel));
webrtc::ChannelGroup* GetChannelGroup(int channel_id) override {
return nullptr;
}
webrtc::ViEChannel* GetChannel(int channel_id) override { return nullptr; }
webrtc::ViEEncoder* GetEncoder(int channel_id) override { return nullptr; }
webrtc::ViERenderManager* GetRenderManager() override { return nullptr; }
WEBRTC_FUNC(CreateReceiveChannel, (int& channel, int original_channel)) {
return CreateChannel(channel, original_channel);
}

View File

@ -62,15 +62,12 @@ class Call {
};
struct Config {
explicit Config(newapi::Transport* send_transport)
: webrtc_config(NULL),
send_transport(send_transport),
: send_transport(send_transport),
voice_engine(NULL),
overuse_callback(NULL) {}
static const int kDefaultStartBitrateBps;
webrtc::Config* webrtc_config;
newapi::Transport* send_transport;
// VoiceEngine used for audio/video synchronization for this Call.
@ -108,9 +105,6 @@ class Call {
static Call* Create(const Call::Config& config);
static Call* Create(const Call::Config& config,
const webrtc::Config& webrtc_config);
virtual VideoSendStream* CreateVideoSendStream(
const VideoSendStream::Config& config,
const VideoEncoderConfig& encoder_config) = 0;

View File

@ -157,6 +157,7 @@ class Call : public webrtc::Call, public PacketReceiver {
ViEBase* base_;
ViENetwork* network_;
int base_channel_id_;
ChannelGroup* channel_group_;
rtc::scoped_ptr<VideoRender> external_render_;
@ -165,9 +166,7 @@ class Call : public webrtc::Call, public PacketReceiver {
} // namespace internal
Call* Call::Create(const Call::Config& config) {
VideoEngine* video_engine = config.webrtc_config != nullptr
? VideoEngine::Create(*config.webrtc_config)
: VideoEngine::Create();
VideoEngine* video_engine = VideoEngine::Create();
DCHECK(video_engine != nullptr);
return new internal::Call(video_engine, config);
@ -221,6 +220,7 @@ Call::Call(webrtc::VideoEngine* video_engine, const Call::Config& config)
base_->CreateChannel(base_channel_id_);
DCHECK(base_channel_id_ != -1);
channel_group_ = base_->GetChannelGroup(base_channel_id_);
network_->SetBitrateConfig(base_channel_id_,
config_.bitrate_config.min_bitrate_bps,
@ -309,6 +309,7 @@ VideoReceiveStream* Call::CreateVideoReceiveStream(
LOG(LS_INFO) << "CreateVideoReceiveStream: " << config.ToString();
VideoReceiveStream* receive_stream =
new VideoReceiveStream(video_engine_,
channel_group_,
config,
config_.send_transport,
config_.voice_engine,

View File

@ -132,6 +132,7 @@ VideoCodec CreateDecoderVideoCodec(const VideoReceiveStream::Decoder& decoder) {
} // namespace
VideoReceiveStream::VideoReceiveStream(webrtc::VideoEngine* video_engine,
ChannelGroup* channel_group,
const VideoReceiveStream::Config& config,
newapi::Transport* transport,
webrtc::VoiceEngine* voice_engine,
@ -140,17 +141,19 @@ VideoReceiveStream::VideoReceiveStream(webrtc::VideoEngine* video_engine,
encoded_frame_proxy_(config.pre_decode_callback),
config_(config),
clock_(Clock::GetRealTimeClock()),
channel_group_(channel_group),
voe_sync_interface_(nullptr),
channel_(-1) {
video_engine_base_ = ViEBase::GetInterface(video_engine);
video_engine_base_->CreateReceiveChannel(channel_, base_channel);
DCHECK(channel_ != -1);
rtp_rtcp_ = ViERTP_RTCP::GetInterface(video_engine);
DCHECK(rtp_rtcp_ != nullptr);
vie_channel_ = video_engine_base_->GetChannel(channel_);
vie_render_manager_ = video_engine_base_->GetRenderManager();
// TODO(pbos): This is not fine grained enough...
rtp_rtcp_->SetNACKStatus(channel_, config_.rtp.nack.rtp_history_ms > 0);
rtp_rtcp_->SetKeyFrameRequestMethod(channel_, kViEKeyFrameRequestPliRtcp);
vie_channel_->SetNACKStatus(config_.rtp.nack.rtp_history_ms > 0);
vie_channel_->SetKeyFrameRequestMethod(kKeyFrameReqPliRtcp);
SetRtcpMode(config_.rtp.rtcp_mode);
DCHECK(config_.rtp.remote_ssrc != 0);
@ -158,18 +161,20 @@ VideoReceiveStream::VideoReceiveStream(webrtc::VideoEngine* video_engine,
DCHECK(config_.rtp.local_ssrc != 0);
DCHECK(config_.rtp.remote_ssrc != config_.rtp.local_ssrc);
rtp_rtcp_->SetLocalSSRC(channel_, config_.rtp.local_ssrc);
vie_channel_->SetSSRC(config_.rtp.local_ssrc, kViEStreamTypeNormal, 0);
// TODO(pbos): Support multiple RTX, per video payload.
Config::Rtp::RtxMap::const_iterator it = config_.rtp.rtx.begin();
if (it != config_.rtp.rtx.end()) {
DCHECK(it->second.ssrc != 0);
DCHECK(it->second.payload_type != 0);
rtp_rtcp_->SetRemoteSSRCType(channel_, kViEStreamTypeRtx, it->second.ssrc);
rtp_rtcp_->SetRtxReceivePayloadType(channel_, it->second.payload_type);
vie_channel_->SetRemoteSSRCType(kViEStreamTypeRtx, it->second.ssrc);
vie_channel_->SetRtxReceivePayloadType(it->second.payload_type);
}
rtp_rtcp_->SetRembStatus(channel_, false, config_.rtp.remb);
// TODO(pbos): Remove channel_group_ usage from VideoReceiveStream. This
// should be configured in call.cc.
channel_group_->SetChannelRembStatus(false, config_.rtp.remb, vie_channel_);
for (size_t i = 0; i < config_.rtp.extensions.size(); ++i) {
const std::string& extension = config_.rtp.extensions[i].name;
@ -178,24 +183,17 @@ VideoReceiveStream::VideoReceiveStream(webrtc::VideoEngine* video_engine,
DCHECK_GE(id, 1);
DCHECK_LE(id, 14);
if (extension == RtpExtension::kTOffset) {
CHECK_EQ(0,
rtp_rtcp_->SetReceiveTimestampOffsetStatus(channel_, true, id));
CHECK_EQ(0, vie_channel_->SetReceiveTimestampOffsetStatus(true, id));
} else if (extension == RtpExtension::kAbsSendTime) {
CHECK_EQ(0,
rtp_rtcp_->SetReceiveAbsoluteSendTimeStatus(channel_, true, id));
CHECK_EQ(0, vie_channel_->SetReceiveAbsoluteSendTimeStatus(true, id));
} else if (extension == RtpExtension::kVideoRotation) {
CHECK_EQ(0, rtp_rtcp_->SetReceiveVideoRotationStatus(channel_, true, id));
CHECK_EQ(0, vie_channel_->SetReceiveVideoRotationStatus(true, id));
} else {
RTC_NOTREACHED() << "Unsupported RTP extension.";
}
}
network_ = ViENetwork::GetInterface(video_engine);
DCHECK(network_ != nullptr);
network_->RegisterSendTransport(channel_, transport_adapter_);
codec_ = ViECodec::GetInterface(video_engine);
vie_channel_->RegisterSendTransport(&transport_adapter_);
if (config_.rtp.fec.ulpfec_payload_type != -1) {
// ULPFEC without RED doesn't make sense.
@ -205,7 +203,7 @@ VideoReceiveStream::VideoReceiveStream(webrtc::VideoEngine* video_engine,
codec.codecType = kVideoCodecULPFEC;
strcpy(codec.plName, "ulpfec");
codec.plType = config_.rtp.fec.ulpfec_payload_type;
CHECK_EQ(0, codec_->SetReceiveCodec(channel_, codec));
CHECK_EQ(0, vie_channel_->SetReceiveCodec(codec));
}
if (config_.rtp.fec.red_payload_type != -1) {
VideoCodec codec;
@ -213,97 +211,86 @@ VideoReceiveStream::VideoReceiveStream(webrtc::VideoEngine* video_engine,
codec.codecType = kVideoCodecRED;
strcpy(codec.plName, "red");
codec.plType = config_.rtp.fec.red_payload_type;
CHECK_EQ(0, codec_->SetReceiveCodec(channel_, codec));
CHECK_EQ(0, vie_channel_->SetReceiveCodec(codec));
}
if (config.rtp.rtcp_xr.receiver_reference_time_report)
vie_channel_->SetRtcpXrRrtrStatus(true);
stats_proxy_.reset(
new ReceiveStatisticsProxy(config_.rtp.remote_ssrc, clock_));
CHECK_EQ(0, rtp_rtcp_->RegisterReceiveChannelRtcpStatisticsCallback(
channel_, stats_proxy_.get()));
CHECK_EQ(0, rtp_rtcp_->RegisterReceiveChannelRtpStatisticsCallback(
channel_, stats_proxy_.get()));
CHECK_EQ(0, rtp_rtcp_->RegisterRtcpPacketTypeCounterObserver(
channel_, stats_proxy_.get()));
CHECK_EQ(0, codec_->RegisterDecoderObserver(channel_, *stats_proxy_));
vie_channel_->RegisterReceiveChannelRtcpStatisticsCallback(
stats_proxy_.get());
vie_channel_->RegisterReceiveChannelRtpStatisticsCallback(stats_proxy_.get());
vie_channel_->RegisterRtcpPacketTypeCounterObserver(stats_proxy_.get());
vie_channel_->RegisterCodecObserver(stats_proxy_.get());
video_engine_base_->RegisterReceiveStatisticsProxy(channel_,
stats_proxy_.get());
vie_channel_->RegisterReceiveStatisticsProxy(stats_proxy_.get());
external_codec_ = ViEExternalCodec::GetInterface(video_engine);
DCHECK(!config_.decoders.empty());
for (size_t i = 0; i < config_.decoders.size(); ++i) {
const Decoder& decoder = config_.decoders[i];
CHECK_EQ(0, external_codec_->RegisterExternalReceiveCodec(
channel_, decoder.payload_type, decoder.decoder,
decoder.is_renderer, decoder.expected_delay_ms));
CHECK_EQ(0, vie_channel_->RegisterExternalDecoder(
decoder.payload_type, decoder.decoder, decoder.is_renderer,
decoder.expected_delay_ms));
VideoCodec codec = CreateDecoderVideoCodec(decoder);
CHECK_EQ(0, codec_->SetReceiveCodec(channel_, codec));
CHECK_EQ(0, vie_channel_->SetReceiveCodec(codec));
}
render_ = ViERender::GetInterface(video_engine);
DCHECK(render_ != nullptr);
render_->AddRenderer(channel_, kVideoI420, this);
// Register a renderer without a window handle, at depth 0, that covers the
// entire rendered area (0->1 both axes). This registers a renderer that
// renders the entire video.
vie_renderer_ = vie_render_manager_->AddRenderStream(channel_, nullptr, 0,
0.0f, 0.0f, 1.0f, 1.0f);
vie_renderer_->SetExternalRenderer(channel_, kVideoI420, this);
vie_channel_->RegisterFrameCallback(channel_, vie_renderer_);
if (voice_engine && config_.audio_channel_id != -1) {
video_engine_base_->SetVoiceEngine(voice_engine);
video_engine_base_->ConnectAudioChannel(channel_, config_.audio_channel_id);
voe_sync_interface_ = VoEVideoSync::GetInterface(voice_engine);
vie_channel_->SetVoiceChannel(config.audio_channel_id, voe_sync_interface_);
}
image_process_ = ViEImageProcess::GetInterface(video_engine);
if (config.pre_decode_callback) {
image_process_->RegisterPreDecodeImageCallback(channel_,
&encoded_frame_proxy_);
}
image_process_->RegisterPreRenderCallback(channel_, this);
if (config.rtp.rtcp_xr.receiver_reference_time_report) {
rtp_rtcp_->SetRtcpXrRrtrStatus(channel_, true);
}
if (config.pre_decode_callback)
vie_channel_->RegisterPreDecodeImageCallback(&encoded_frame_proxy_);
vie_channel_->RegisterPreRenderCallback(this);
}
VideoReceiveStream::~VideoReceiveStream() {
image_process_->DeRegisterPreRenderCallback(channel_);
image_process_->DeRegisterPreDecodeCallback(channel_);
vie_channel_->RegisterPreRenderCallback(nullptr);
vie_channel_->RegisterPreDecodeImageCallback(nullptr);
render_->RemoveRenderer(channel_);
vie_channel_->DeregisterFrameCallback(vie_renderer_);
vie_render_manager_->RemoveRenderStream(channel_);
for (size_t i = 0; i < config_.decoders.size(); ++i) {
external_codec_->DeRegisterExternalReceiveCodec(
channel_, config_.decoders[i].payload_type);
for (size_t i = 0; i < config_.decoders.size(); ++i)
vie_channel_->DeRegisterExternalDecoder(config_.decoders[i].payload_type);
vie_channel_->DeregisterSendTransport();
if (voe_sync_interface_ != nullptr) {
vie_channel_->SetVoiceChannel(-1, nullptr);
voe_sync_interface_->Release();
}
network_->DeregisterSendTransport(channel_);
video_engine_base_->SetVoiceEngine(nullptr);
image_process_->Release();
external_codec_->Release();
codec_->DeregisterDecoderObserver(channel_);
rtp_rtcp_->DeregisterReceiveChannelRtpStatisticsCallback(channel_,
stats_proxy_.get());
rtp_rtcp_->DeregisterReceiveChannelRtcpStatisticsCallback(channel_,
stats_proxy_.get());
rtp_rtcp_->RegisterRtcpPacketTypeCounterObserver(channel_, nullptr);
codec_->Release();
network_->Release();
render_->Release();
rtp_rtcp_->Release();
vie_channel_->RegisterCodecObserver(nullptr);
vie_channel_->RegisterReceiveChannelRtpStatisticsCallback(nullptr);
vie_channel_->RegisterReceiveChannelRtcpStatisticsCallback(nullptr);
vie_channel_->RegisterRtcpPacketTypeCounterObserver(nullptr);
video_engine_base_->DeleteChannel(channel_);
video_engine_base_->Release();
}
void VideoReceiveStream::Start() {
transport_adapter_.Enable();
CHECK_EQ(0, render_->StartRender(channel_));
CHECK_EQ(0, video_engine_base_->StartReceive(channel_));
vie_renderer_->StartRender();
vie_channel_->StartReceive();
}
void VideoReceiveStream::Stop() {
CHECK_EQ(0, render_->StopRender(channel_));
CHECK_EQ(0, video_engine_base_->StopReceive(channel_));
vie_renderer_->StopRender();
vie_channel_->StopReceive();
transport_adapter_.Disable();
}
@ -312,12 +299,11 @@ VideoReceiveStream::Stats VideoReceiveStream::GetStats() const {
}
bool VideoReceiveStream::DeliverRtcp(const uint8_t* packet, size_t length) {
return network_->ReceivedRTCPPacket(channel_, packet, length) == 0;
return vie_channel_->ReceivedRTCPPacket(packet, length) == 0;
}
bool VideoReceiveStream::DeliverRtp(const uint8_t* packet, size_t length) {
return network_->ReceivedRTPPacket(channel_, packet, length, PacketTime()) ==
0;
return vie_channel_->ReceivedRTPPacket(packet, length, PacketTime()) == 0;
}
void VideoReceiveStream::FrameCallback(I420VideoFrame* video_frame) {
@ -364,18 +350,17 @@ bool VideoReceiveStream::IsTextureSupported() {
void VideoReceiveStream::SignalNetworkState(Call::NetworkState state) {
if (state == Call::kNetworkUp)
SetRtcpMode(config_.rtp.rtcp_mode);
network_->SetNetworkTransmissionState(channel_, state == Call::kNetworkUp);
if (state == Call::kNetworkDown)
rtp_rtcp_->SetRTCPStatus(channel_, kRtcpNone);
vie_channel_->SetRTCPMode(kRtcpOff);
}
void VideoReceiveStream::SetRtcpMode(newapi::RtcpMode mode) {
switch (mode) {
case newapi::kRtcpCompound:
rtp_rtcp_->SetRTCPStatus(channel_, kRtcpCompound_RFC4585);
vie_channel_->SetRTCPMode(kRtcpCompound);
break;
case newapi::kRtcpReducedSize:
rtp_rtcp_->SetRTCPStatus(channel_, kRtcpNonCompound_RFC5506);
vie_channel_->SetRTCPMode(kRtcpNonCompound);
break;
}
}

View File

@ -22,6 +22,11 @@
#include "webrtc/video/receive_statistics_proxy.h"
#include "webrtc/video/transport_adapter.h"
#include "webrtc/video_engine/include/vie_render.h"
#include "webrtc/video_engine/vie_channel.h"
#include "webrtc/video_engine/vie_channel_group.h"
#include "webrtc/video_engine/vie_encoder.h"
#include "webrtc/video_engine/vie_render_manager.h"
#include "webrtc/video_engine/vie_renderer.h"
#include "webrtc/video_receive_stream.h"
namespace webrtc {
@ -43,6 +48,7 @@ class VideoReceiveStream : public webrtc::VideoReceiveStream,
public ExternalRenderer {
public:
VideoReceiveStream(webrtc::VideoEngine* video_engine,
ChannelGroup* channel_group,
const VideoReceiveStream::Config& config,
newapi::Transport* transport,
webrtc::VoiceEngine* voice_engine,
@ -82,13 +88,14 @@ class VideoReceiveStream : public webrtc::VideoReceiveStream,
const VideoReceiveStream::Config config_;
Clock* const clock_;
ChannelGroup* const channel_group_;
ViEChannel* vie_channel_;
ViERenderManager* vie_render_manager_;
ViERenderer* vie_renderer_;
ViEBase* video_engine_base_;
ViECodec* codec_;
ViEExternalCodec* external_codec_;
ViENetwork* network_;
ViERender* render_;
ViERTP_RTCP* rtp_rtcp_;
ViEImageProcess* image_process_;
VoEVideoSync* voe_sync_interface_;
rtc::scoped_ptr<ReceiveStatisticsProxy> stats_proxy_;

View File

@ -28,6 +28,14 @@ class VoiceEngine;
class ReceiveStatisticsProxy;
class SendStatisticsProxy;
// Internal-class forward declarations, used to break out implementations for
// the new video API to remove interface dependencies to the VideoEngine API
// See webrtc:1695.
class ChannelGroup;
class ViEChannel;
class ViEEncoder;
class ViERenderManager;
// CpuOveruseObserver is called when a system overuse is detected and
// VideoEngine cannot keep up the encoding frequency.
class CpuOveruseObserver {
@ -190,6 +198,11 @@ class WEBRTC_DLLEXPORT ViEBase {
virtual int CreateChannelWithoutDefaultEncoder(int& video_channel,
int original_channel) = 0;
virtual ChannelGroup* GetChannelGroup(int channel_id) = 0;
virtual ViEChannel* GetChannel(int channel_id) = 0;
virtual ViEEncoder* GetEncoder(int channel_id) = 0;
virtual ViERenderManager* GetRenderManager() = 0;
// Creates a new channel grouped together with |original_channel|. The channel
// can only receive video and it is assumed the remote end-point is the same
// as for |original_channel|.

View File

@ -13,6 +13,7 @@
#include <string>
#include <utility>
#include "webrtc/base/checks.h"
#include "webrtc/engine_configurations.h"
#include "webrtc/modules/rtp_rtcp/interface/rtp_rtcp.h"
#include "webrtc/modules/video_coding/main/interface/video_coding.h"
@ -195,6 +196,28 @@ int ViEBaseImpl::CreateChannelWithoutDefaultEncoder(
return CreateChannel(video_channel, original_channel, true, true);
}
ChannelGroup* ViEBaseImpl::GetChannelGroup(int channel_id) {
return shared_data_.channel_manager()->GetChannelGroup(channel_id);
}
ViEChannel* ViEBaseImpl::GetChannel(int channel_id) {
ViEChannelManagerScoped cs(*(shared_data_.channel_manager()));
ViEChannel* vie_channel = cs.Channel(channel_id);
DCHECK(vie_channel);
return vie_channel;
}
ViEEncoder* ViEBaseImpl::GetEncoder(int channel_id) {
ViEChannelManagerScoped cs(*(shared_data_.channel_manager()));
ViEEncoder* vie_encoder = cs.Encoder(channel_id);
DCHECK(vie_encoder);
return vie_encoder;
}
ViERenderManager* ViEBaseImpl::GetRenderManager() {
return shared_data_.render_manager();
}
int ViEBaseImpl::CreateReceiveChannel(int& video_channel, // NOLINT
int original_channel) {
return CreateChannel(video_channel, original_channel, false, true);

View File

@ -50,6 +50,11 @@ class ViEBaseImpl
virtual int CreateChannelWithoutDefaultEncoder(int& video_channel, // NOLINT
int original_channel);
ChannelGroup* GetChannelGroup(int channel_id) override;
ViEChannel* GetChannel(int channel_id) override;
ViEEncoder* GetEncoder(int channel_id) override;
ViERenderManager* GetRenderManager() override;
virtual int CreateReceiveChannel(int& video_channel, // NOLINT
int original_channel);
virtual int DeleteChannel(const int video_channel);

View File

@ -285,7 +285,7 @@ void ChannelGroup::DeleteChannel(int channel_id) {
DCHECK(vie_encoder != NULL);
call_stats_->DeregisterStatsObserver(vie_channel->GetStatsObserver());
SetChannelRembStatus(channel_id, false, false, vie_channel);
SetChannelRembStatus(false, false, vie_channel);
// If we're owning the encoder, remove the feedback and stop all encoding
// threads and processing. This must be done before deleting the channel.
@ -446,8 +446,7 @@ int64_t ChannelGroup::GetPacerQueuingDelayMs() const {
return pacer_->QueueInMs();
}
void ChannelGroup::SetChannelRembStatus(int channel_id,
bool sender,
void ChannelGroup::SetChannelRembStatus(bool sender,
bool receiver,
ViEChannel* channel) {
// Update the channel state.

View File

@ -64,10 +64,7 @@ class ChannelGroup : public BitrateObserver {
void SetSyncInterface(VoEVideoSync* sync_interface);
void SetChannelRembStatus(int channel_id,
bool sender,
bool receiver,
ViEChannel* channel);
void SetChannelRembStatus(bool sender, bool receiver, ViEChannel* channel);
BitrateController* GetBitrateController() const;
CallStats* GetCallStats() const;

View File

@ -12,6 +12,7 @@
#include <vector>
#include "webrtc/base/checks.h"
#include "webrtc/common.h"
#include "webrtc/engine_configurations.h"
#include "webrtc/modules/rtp_rtcp/interface/rtp_rtcp.h"
@ -134,6 +135,13 @@ int ViEChannelManager::CreateChannel(int* channel_id,
return 0;
}
ChannelGroup* ViEChannelManager::GetChannelGroup(int channel_id) {
CriticalSectionScoped cs(channel_id_critsect_);
ChannelGroup* group = FindGroup(channel_id);
DCHECK(group);
return group;
}
int ViEChannelManager::DeleteChannel(int channel_id) {
ChannelGroup* group = NULL;
{
@ -224,7 +232,7 @@ bool ViEChannelManager::SetRembStatus(int channel_id, bool sender,
ViEChannel* channel = ViEChannelPtr(channel_id);
assert(channel);
group->SetChannelRembStatus(channel_id, sender, receiver, channel);
group->SetChannelRembStatus(sender, receiver, channel);
return true;
}

View File

@ -59,6 +59,8 @@ class ViEChannelManager: private ViEManagerBase {
bool sender,
bool disable_default_encoder);
ChannelGroup* GetChannelGroup(int channel_id);
// Deletes a channel.
int DeleteChannel(int channel_id);