Update talk to 60923971
Review URL: https://webrtc-codereview.appspot.com/7909004
git-svn-id: http://webrtc.googlecode.com/svn/trunk@5475 4adac7df-926f-26a2-2b94-8c16560cd09d
diff --git a/talk/media/webrtc/webrtcvoiceengine.cc b/talk/media/webrtc/webrtcvoiceengine.cc
index b4b96d1..4ad2ff5 100644
--- a/talk/media/webrtc/webrtcvoiceengine.cc
+++ b/talk/media/webrtc/webrtcvoiceengine.cc
@@ -1639,17 +1639,68 @@
return CreateVoiceChannel(voe_wrapper_sc_.get());
}
-// This struct relies on the generated copy constructor and assignment operator
-// since it is used in an stl::map.
-struct WebRtcVoiceMediaChannel::WebRtcVoiceChannelInfo {
- WebRtcVoiceChannelInfo() : channel(-1), renderer(NULL) {}
- WebRtcVoiceChannelInfo(int ch, AudioRenderer* r)
- : channel(ch),
- renderer(r) {}
- ~WebRtcVoiceChannelInfo() {}
+class WebRtcVoiceMediaChannel::WebRtcVoiceChannelRenderer
+ : public AudioRenderer::Sink {
+ public:
+ WebRtcVoiceChannelRenderer(int ch,
+ webrtc::AudioTransport* voe_audio_transport)
+ : channel_(ch),
+ voe_audio_transport_(voe_audio_transport),
+ renderer_(NULL) {
+ }
+ virtual ~WebRtcVoiceChannelRenderer() {
+ Stop();
+ }
- int channel;
- AudioRenderer* renderer;
+ // Starts the rendering by setting a sink to the renderer to get data
+ // callback.
+ // TODO(xians): Make sure Start() is called only once.
+ void Start(AudioRenderer* renderer) {
+ ASSERT(renderer != NULL);
+ if (renderer_) {
+ ASSERT(renderer_ == renderer);
+ return;
+ }
+
+ // TODO(xians): Remove AddChannel() call after Chrome turns on APM
+ // in getUserMedia by default.
+ renderer->AddChannel(channel_);
+ renderer->SetSink(this);
+ renderer_ = renderer;
+ }
+
+ // Stops rendering by setting the sink of the renderer to NULL. No data
+ // callback will be received after this method.
+ void Stop() {
+ if (!renderer_)
+ return;
+
+ renderer_->RemoveChannel(channel_);
+ renderer_->SetSink(NULL);
+ renderer_ = NULL;
+ }
+
+ // AudioRenderer::Sink implementation.
+ virtual void OnData(const void* audio_data,
+ int bits_per_sample,
+ int sample_rate,
+ int number_of_channels,
+ int number_of_frames) OVERRIDE {
+ // TODO(xians): Make new interface in AudioTransport to pass the data to
+ // WebRtc VoE channel.
+ }
+
+ // Accessor to the VoE channel ID.
+ int channel() const { return channel_; }
+
+ private:
+ const int channel_;
+ webrtc::AudioTransport* const voe_audio_transport_;
+
+ // Raw pointer to AudioRenderer owned by LocalAudioTrackHandler.
+ // PeerConnection will make sure invalidating the pointer before the object
+ // goes away.
+ AudioRenderer* renderer_;
};
// WebRtcVoiceMediaChannel
@@ -1841,8 +1892,8 @@
for (ChannelMap::iterator it = receive_channels_.begin();
it != receive_channels_.end() && ret; ++it) {
if (engine()->voe()->codec()->SetRecPayloadType(
- it->second.channel, voe_codec) == -1) {
- LOG_RTCERR2(SetRecPayloadType, it->second.channel,
+ it->second->channel(), voe_codec) == -1) {
+ LOG_RTCERR2(SetRecPayloadType, it->second->channel(),
ToString(voe_codec));
ret = false;
}
@@ -2047,7 +2098,7 @@
send_codecs_ = codecs;
for (ChannelMap::iterator iter = send_channels_.begin();
iter != send_channels_.end(); ++iter) {
- if (!SetSendCodecs(iter->second.channel, codecs)) {
+ if (!SetSendCodecs(iter->second->channel(), codecs)) {
return false;
}
}
@@ -2061,7 +2112,7 @@
bool nack_enabled) {
for (ChannelMap::const_iterator it = channels.begin();
it != channels.end(); ++it) {
- SetNack(it->second.channel, nack_enabled);
+ SetNack(it->second->channel(), nack_enabled);
}
}
@@ -2081,7 +2132,7 @@
<< ", bitrate=" << send_codec.rate;
for (ChannelMap::iterator iter = send_channels_.begin();
iter != send_channels_.end(); ++iter) {
- if (!SetSendCodec(iter->second.channel, send_codec))
+ if (!SetSendCodec(iter->second->channel(), send_codec))
return false;
}
@@ -2132,9 +2183,9 @@
for (ChannelMap::const_iterator iter = send_channels_.begin();
iter != send_channels_.end(); ++iter) {
if (engine()->voe()->rtp()->SetRTPAudioLevelIndicationStatus(
- iter->second.channel, enable, id) == -1) {
+ iter->second->channel(), enable, id) == -1) {
LOG_RTCERR3(SetRTPAudioLevelIndicationStatus,
- iter->second.channel, enable, id);
+ iter->second->channel(), enable, id);
return false;
}
}
@@ -2168,9 +2219,9 @@
}
for (ChannelMap::iterator it = receive_channels_.begin();
it != receive_channels_.end() && result; ++it) {
- if (!SetPlayout(it->second.channel, playout)) {
+ if (!SetPlayout(it->second->channel(), playout)) {
LOG(LS_ERROR) << "SetPlayout " << playout << " on channel "
- << it->second.channel << " failed";
+ << it->second->channel() << " failed";
result = false;
}
}
@@ -2208,7 +2259,7 @@
// Change the settings on each send channel.
for (ChannelMap::iterator iter = send_channels_.begin();
iter != send_channels_.end(); ++iter) {
- if (!ChangeSend(iter->second.channel, send))
+ if (!ChangeSend(iter->second->channel(), send))
return false;
}
@@ -2280,7 +2331,7 @@
bool default_channel_is_available = true;
for (ChannelMap::const_iterator iter = send_channels_.begin();
iter != send_channels_.end(); ++iter) {
- if (IsDefaultChannel(iter->second.channel)) {
+ if (IsDefaultChannel(iter->second->channel())) {
default_channel_is_available = false;
break;
}
@@ -2300,7 +2351,15 @@
// Save the channel to send_channels_, so that RemoveSendStream() can still
// delete the channel in case failure happens below.
- send_channels_[sp.first_ssrc()] = WebRtcVoiceChannelInfo(channel, NULL);
+#ifdef USE_WEBRTC_DEV_BRANCH
+ webrtc::AudioTransport* audio_transport =
+ engine()->voe()->base()->audio_transport();
+#else
+ webrtc::AudioTransport* audio_transport = NULL;
+#endif
+ send_channels_.insert(std::make_pair(
+ sp.first_ssrc(),
+ new WebRtcVoiceChannelRenderer(channel, audio_transport)));
// Set the send (local) SSRC.
// If there are multiple send SSRCs, we can only set the first one here, and
@@ -2319,10 +2378,10 @@
for (ChannelMap::const_iterator it = receive_channels_.begin();
it != receive_channels_.end(); ++it) {
// Only update the SSRC for non-default channels.
- if (!IsDefaultChannel(it->second.channel)) {
- if (engine()->voe()->rtp()->SetLocalSSRC(it->second.channel,
+ if (!IsDefaultChannel(it->second->channel())) {
+ if (engine()->voe()->rtp()->SetLocalSSRC(it->second->channel(),
sp.first_ssrc()) != 0) {
- LOG_RTCERR2(SetLocalSSRC, it->second.channel, sp.first_ssrc());
+ LOG_RTCERR2(SetLocalSSRC, it->second->channel(), sp.first_ssrc());
return false;
}
}
@@ -2349,12 +2408,13 @@
return false;
}
- int channel = it->second.channel;
+ int channel = it->second->channel();
ChangeSend(channel, SEND_NOTHING);
- // Notify the audio renderer that the send channel is going away.
- if (it->second.renderer)
- it->second.renderer->RemoveChannel(channel);
+ // Delete the WebRtcVoiceChannelRenderer object connected to the channel,
+ // this will disconnect the audio renderer with the send channel.
+ delete it->second;
+ send_channels_.erase(it);
if (IsDefaultChannel(channel)) {
// Do not delete the default channel since the receive channels depend on
@@ -2368,7 +2428,6 @@
return false;
}
- send_channels_.erase(it);
if (send_channels_.empty())
ChangeSend(SEND_NOTHING);
@@ -2394,12 +2453,19 @@
// Reuse default channel for recv stream in non-conference mode call
// when the default channel is not being used.
+#ifdef USE_WEBRTC_DEV_BRANCH
+ webrtc::AudioTransport* audio_transport =
+ engine()->voe()->base()->audio_transport();
+#else
+ webrtc::AudioTransport* audio_transport = NULL;
+#endif
if (!InConferenceMode() && default_receive_ssrc_ == 0) {
LOG(LS_INFO) << "Recv stream " << sp.first_ssrc()
<< " reuse default channel";
default_receive_ssrc_ = sp.first_ssrc();
receive_channels_.insert(std::make_pair(
- default_receive_ssrc_, WebRtcVoiceChannelInfo(voe_channel(), NULL)));
+ default_receive_ssrc_,
+ new WebRtcVoiceChannelRenderer(voe_channel(), audio_transport)));
return SetPlayout(voe_channel(), playout_);
}
@@ -2416,7 +2482,8 @@
}
receive_channels_.insert(
- std::make_pair(ssrc, WebRtcVoiceChannelInfo(channel, NULL)));
+ std::make_pair(
+ ssrc, new WebRtcVoiceChannelRenderer(channel, audio_transport)));
LOG(LS_INFO) << "New audio stream " << ssrc
<< " registered to VoiceEngine channel #"
@@ -2493,34 +2560,28 @@
return false;
}
+ // Delete the WebRtcVoiceChannelRenderer object connected to the channel, this
+ // will disconnect the audio renderer with the receive channel.
+ // Cache the channel before the deletion.
+ const int channel = it->second->channel();
+ delete it->second;
+ receive_channels_.erase(it);
+
if (ssrc == default_receive_ssrc_) {
- ASSERT(IsDefaultChannel(it->second.channel));
+ ASSERT(IsDefaultChannel(channel));
// Recycle the default channel is for recv stream.
if (playout_)
SetPlayout(voe_channel(), false);
- if (it->second.renderer)
- it->second.renderer->RemoveChannel(voe_channel());
-
default_receive_ssrc_ = 0;
- receive_channels_.erase(it);
return true;
}
- // Non default channel.
- // Notify the renderer that channel is going away.
- if (it->second.renderer)
- it->second.renderer->RemoveChannel(it->second.channel);
-
LOG(LS_INFO) << "Removing audio stream " << ssrc
- << " with VoiceEngine channel #" << it->second.channel << ".";
- if (!DeleteChannel(it->second.channel)) {
- // Erase the entry anyhow.
- receive_channels_.erase(it);
+ << " with VoiceEngine channel #" << channel << ".";
+ if (!DeleteChannel(channel))
return false;
- }
- receive_channels_.erase(it);
bool enable_default_channel_playout = false;
if (receive_channels_.empty()) {
// The last stream was removed. We can now enable the default
@@ -2558,19 +2619,11 @@
return true;
}
- AudioRenderer* remote_renderer = it->second.renderer;
- if (renderer) {
- ASSERT(remote_renderer == NULL || remote_renderer == renderer);
- if (!remote_renderer) {
- renderer->AddChannel(it->second.channel);
- }
- } else if (remote_renderer) {
- // |renderer| == NULL, remove the channel from the renderer.
- remote_renderer->RemoveChannel(it->second.channel);
- }
+ if (renderer)
+ it->second->Start(renderer);
+ else
+ it->second->Stop();
- // Assign the new value to the struct.
- it->second.renderer = renderer;
return true;
}
@@ -2588,17 +2641,11 @@
return true;
}
- AudioRenderer* local_renderer = it->second.renderer;
- if (renderer) {
- ASSERT(local_renderer == NULL || local_renderer == renderer);
- if (!local_renderer)
- renderer->AddChannel(it->second.channel);
- } else if (local_renderer) {
- local_renderer->RemoveChannel(it->second.channel);
- }
+ if (renderer)
+ it->second->Start(renderer);
+ else
+ it->second->Stop();
- // Assign the new value to the struct.
- it->second.renderer = renderer;
return true;
}
@@ -2609,7 +2656,7 @@
actives->clear();
for (ChannelMap::iterator it = receive_channels_.begin();
it != receive_channels_.end(); ++it) {
- int level = GetOutputLevel(it->second.channel);
+ int level = GetOutputLevel(it->second->channel());
if (level > 0) {
actives->push_back(std::make_pair(it->first, level));
}
@@ -2622,7 +2669,7 @@
int highest = GetOutputLevel(voe_channel());
for (ChannelMap::iterator it = receive_channels_.begin();
it != receive_channels_.end(); ++it) {
- int level = GetOutputLevel(it->second.channel);
+ int level = GetOutputLevel(it->second->channel());
highest = talk_base::_max(level, highest);
}
return highest;
@@ -2665,7 +2712,7 @@
channels.push_back(voe_channel());
for (ChannelMap::const_iterator it = receive_channels_.begin();
it != receive_channels_.end(); ++it) {
- channels.push_back(it->second.channel);
+ channels.push_back(it->second->channel());
}
} else { // Collect only the channel of the specified ssrc.
int channel = GetReceiveChannelNum(ssrc);
@@ -2801,7 +2848,7 @@
bool default_channel_is_inuse = false;
for (ChannelMap::const_iterator iter = send_channels_.begin();
iter != send_channels_.end(); ++iter) {
- if (IsDefaultChannel(iter->second.channel)) {
+ if (IsDefaultChannel(iter->second->channel())) {
default_channel_is_inuse = true;
break;
}
@@ -2809,7 +2856,7 @@
if (default_channel_is_inuse) {
channel = voe_channel();
} else if (!send_channels_.empty()) {
- channel = send_channels_.begin()->second.channel;
+ channel = send_channels_.begin()->second->channel();
}
} else {
channel = GetSendChannelNum(ssrc);
@@ -2907,11 +2954,12 @@
for (ChannelMap::iterator iter = send_channels_.begin();
iter != send_channels_.end(); ++iter) {
// Make sure not sending the same packet to default channel more than once.
- if (IsDefaultChannel(iter->second.channel) && has_sent_to_default_channel)
+ if (IsDefaultChannel(iter->second->channel()) &&
+ has_sent_to_default_channel)
continue;
engine()->voe()->network()->ReceivedRTCPPacket(
- iter->second.channel,
+ iter->second->channel(),
packet->data(),
static_cast<unsigned int>(packet->length()));
}
@@ -3022,7 +3070,7 @@
for (ChannelMap::const_iterator channel_iter = send_channels_.begin();
channel_iter != send_channels_.end(); ++channel_iter) {
- const int channel = channel_iter->second.channel;
+ const int channel = channel_iter->second->channel();
// Fill in the sender info, based on what we know, and what the
// remote side told us it got from its RTCP report.
@@ -3094,7 +3142,7 @@
std::vector<int> channels;
for (ChannelMap::const_iterator it = receive_channels_.begin();
it != receive_channels_.end(); ++it) {
- channels.push_back(it->second.channel);
+ channels.push_back(it->second->channel());
}
if (channels.empty()) {
channels.push_back(voe_channel());
@@ -3172,7 +3220,7 @@
// Check whether this is a sending channel.
for (ChannelMap::const_iterator it = send_channels_.begin();
it != send_channels_.end(); ++it) {
- if (it->second.channel == channel_num) {
+ if (it->second->channel() == channel_num) {
// This is a sending channel.
uint32 local_ssrc = 0;
if (engine()->voe()->rtp()->GetLocalSSRC(
@@ -3186,7 +3234,7 @@
// Check whether this is a receiving channel.
for (ChannelMap::const_iterator it = receive_channels_.begin();
it != receive_channels_.end(); ++it) {
- if (it->second.channel == channel_num) {
+ if (it->second->channel() == channel_num) {
*ssrc = it->first;
return true;
}
@@ -3214,14 +3262,14 @@
int WebRtcVoiceMediaChannel::GetReceiveChannelNum(uint32 ssrc) {
ChannelMap::iterator it = receive_channels_.find(ssrc);
if (it != receive_channels_.end())
- return it->second.channel;
+ return it->second->channel();
return (ssrc == default_receive_ssrc_) ? voe_channel() : -1;
}
int WebRtcVoiceMediaChannel::GetSendChannelNum(uint32 ssrc) {
ChannelMap::iterator it = send_channels_.find(ssrc);
if (it != send_channels_.end())
- return it->second.channel;
+ return it->second->channel();
return -1;
}