Update To 11.40.268.0
[platform/framework/web/crosswalk.git] / src / third_party / libjingle / source / talk / session / media / call.cc
1 /*
2  * libjingle
3  * Copyright 2004 Google Inc.
4  *
5  * Redistribution and use in source and binary forms, with or without
6  * modification, are permitted provided that the following conditions are met:
7  *
8  *  1. Redistributions of source code must retain the above copyright notice,
9  *     this list of conditions and the following disclaimer.
10  *  2. Redistributions in binary form must reproduce the above copyright notice,
11  *     this list of conditions and the following disclaimer in the documentation
12  *     and/or other materials provided with the distribution.
13  *  3. The name of the author may not be used to endorse or promote products
14  *     derived from this software without specific prior written permission.
15  *
16  * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR IMPLIED
17  * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
18  * MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO
19  * EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
20  * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
21  * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS;
22  * OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
23  * WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
24  * OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
25  * ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
26  */
27
28 #include <string>
29 #include "talk/media/base/constants.h"
30 #include "talk/media/base/screencastid.h"
31 #include "webrtc/p2p/base/parsing.h"
32 #include "talk/session/media/call.h"
33 #include "talk/session/media/currentspeakermonitor.h"
34 #include "talk/session/media/mediasessionclient.h"
35 #include "webrtc/base/helpers.h"
36 #include "webrtc/base/logging.h"
37 #include "webrtc/base/thread.h"
38 #include "webrtc/base/window.h"
39
40 namespace cricket {
41
42 const uint32 MSG_CHECKAUTODESTROY = 1;
43 const uint32 MSG_TERMINATECALL = 2;
44 const uint32 MSG_PLAYDTMF = 3;
45
46 namespace {
47 const int kDTMFDelay = 300;  // msec
48 const size_t kMaxDTMFDigits = 30;
49 const int kSendToVoicemailTimeout = 1000*20;
50 const int kNoVoicemailTimeout = 1000*180;
51 const int kMediaMonitorInterval = 1000*15;
52 // In order to be the same as the server-side switching, this must be 100.
53 const int kAudioMonitorPollPeriodMillis = 100;
54
55 // V is a pointer type.
56 template<class K, class V>
57 V FindOrNull(const std::map<K, V>& map,
58              const K& key) {
59   typename std::map<K, V>::const_iterator it = map.find(key);
60   return (it != map.end()) ? it->second : NULL;
61 }
62
63
64 bool ContentContainsCrypto(const cricket::ContentInfo* content) {
65   if (content != NULL) {
66     const cricket::MediaContentDescription* desc =
67         static_cast<const cricket::MediaContentDescription*>(
68             content->description);
69     if (!desc || desc->cryptos().empty()) {
70       return false;
71     }
72   }
73   return true;
74 }
75
76 }
77
78 AudioSourceProxy::AudioSourceProxy(Call* call)
79     : call_(call) {
80   call_->SignalAudioMonitor.connect(this, &AudioSourceProxy::OnAudioMonitor);
81   call_->SignalMediaStreamsUpdate.connect(
82       this, &AudioSourceProxy::OnMediaStreamsUpdate);
83 }
84
85 void AudioSourceProxy::OnAudioMonitor(Call* call, const AudioInfo& info) {
86   SignalAudioMonitor(this, info);
87 }
88
89 void AudioSourceProxy::OnMediaStreamsUpdate(Call* call, Session* session,
90     const MediaStreams& added, const MediaStreams& removed) {
91   SignalMediaStreamsUpdate(this, session, added, removed);
92 }
93
94 Call::Call(MediaSessionClient* session_client)
95     : id_(rtc::CreateRandomId()),
96       session_client_(session_client),
97       has_video_(false),
98       has_data_(false),
99       muted_(false),
100       video_muted_(false),
101       send_to_voicemail_(true),
102       playing_dtmf_(false) {
103   audio_source_proxy_.reset(new AudioSourceProxy(this));
104 }
105
106 Call::~Call() {
107   while (media_session_map_.begin() != media_session_map_.end()) {
108     Session* session = media_session_map_.begin()->second.session;
109     RemoveSession(session);
110     session_client_->session_manager()->DestroySession(session);
111   }
112   rtc::Thread::Current()->Clear(this);
113 }
114
115 Session* Call::InitiateSession(const buzz::Jid& to,
116                                const buzz::Jid& initiator,
117                                const CallOptions& options) {
118   std::string id;
119   std::string initiator_name = initiator.Str();
120   return InternalInitiateSession(id, to, initiator_name, options);
121 }
122
123 Session *Call::InitiateSession(const std::string& id,
124                                const buzz::Jid& to,
125                                const CallOptions& options) {
126   std::string initiator_name;
127   return InternalInitiateSession(id, to, initiator_name, options);
128 }
129
130 void Call::IncomingSession(Session* session, const SessionDescription* offer) {
131   AddSession(session, offer);
132
133   // Make sure the session knows about the incoming ssrcs. This needs to be done
134   // prior to the SignalSessionState call, because that may trigger handling of
135   // these new SSRCs, so they need to be registered before then.
136   UpdateRemoteMediaStreams(session, offer->contents(), false);
137
138   // Missed the first state, the initiate, which is needed by
139   // call_client.
140   SignalSessionState(this, session, Session::STATE_RECEIVEDINITIATE);
141 }
142
143 void Call::AcceptSession(Session* session,
144                          const cricket::CallOptions& options) {
145   MediaSessionMap::iterator it = media_session_map_.find(session->id());
146   if (it != media_session_map_.end()) {
147     const SessionDescription* answer = session_client_->CreateAnswer(
148         session->remote_description(), options);
149     it->second.session->Accept(answer);
150   }
151 }
152
153 void Call::RejectSession(Session* session) {
154   // Assume polite decline.
155   MediaSessionMap::iterator it = media_session_map_.find(session->id());
156   if (it != media_session_map_.end())
157     it->second.session->Reject(STR_TERMINATE_DECLINE);
158 }
159
160 void Call::TerminateSession(Session* session) {
161   MediaSessionMap::iterator it = media_session_map_.find(session->id());
162   if (it != media_session_map_.end()) {
163     // Assume polite terminations.
164     it->second.session->Terminate();
165   }
166 }
167
168 void Call::Terminate() {
169   // Copy the list so that we can iterate over it in a stable way
170   std::vector<Session*> sessions = this->sessions();
171
172   // There may be more than one session to terminate
173   std::vector<Session*>::iterator it;
174   for (it = sessions.begin(); it != sessions.end(); ++it) {
175     TerminateSession(*it);
176   }
177 }
178
179 bool Call::SendViewRequest(Session* session,
180                            const ViewRequest& view_request) {
181   StaticVideoViews::const_iterator it;
182   for (it = view_request.static_video_views.begin();
183        it != view_request.static_video_views.end(); ++it) {
184     StreamParams found_stream;
185     bool found = false;
186     MediaStreams* recv_streams = GetMediaStreams(session);
187     if (recv_streams)
188       found = recv_streams->GetVideoStream(it->selector, &found_stream);
189     if (!found) {
190       LOG(LS_WARNING) << "Trying to send view request for ("
191                       << it->selector.ssrc << ", '"
192                       << it->selector.groupid << "', '"
193                       << it->selector.streamid << "'"
194                       << ") is not in the local streams.";
195       return false;
196     }
197   }
198
199   XmlElements elems;
200   WriteError error;
201   if (!WriteJingleViewRequest(CN_VIDEO, view_request, &elems, &error)) {
202     LOG(LS_ERROR) << "Couldn't write out view request: " << error.text;
203     return false;
204   }
205
206   return session->SendInfoMessage(elems, session->remote_name());
207 }
208
209 void Call::SetVideoRenderer(Session* session, uint32 ssrc,
210                             VideoRenderer* renderer) {
211   VideoChannel* video_channel = GetVideoChannel(session);
212   if (video_channel) {
213     video_channel->SetRenderer(ssrc, renderer);
214     LOG(LS_INFO) << "Set renderer of ssrc " << ssrc
215                  << " to " << renderer << ".";
216   } else {
217     LOG(LS_INFO) << "Failed to set renderer of ssrc " << ssrc << ".";
218   }
219 }
220
221 void Call::OnMessage(rtc::Message* message) {
222   switch (message->message_id) {
223   case MSG_CHECKAUTODESTROY:
224     // If no more sessions for this call, delete it
225     if (media_session_map_.empty())
226       session_client_->DestroyCall(this);
227     break;
228   case MSG_TERMINATECALL:
229     // Signal to the user that a timeout has happened and the call should
230     // be sent to voicemail.
231     if (send_to_voicemail_) {
232       SignalSetupToCallVoicemail();
233     }
234
235     // Callee didn't answer - terminate call
236     Terminate();
237     break;
238   case MSG_PLAYDTMF:
239     ContinuePlayDTMF();
240   }
241 }
242
243 std::vector<Session*> Call::sessions() {
244   std::vector<Session*> sessions;
245   MediaSessionMap::iterator it;
246   for (it = media_session_map_.begin(); it != media_session_map_.end(); ++it)
247     sessions.push_back(it->second.session);
248
249   return sessions;
250 }
251
252 bool Call::AddSession(Session* session, const SessionDescription* offer) {
253   bool succeeded = true;
254   MediaSession media_session;
255   media_session.session = session;
256   media_session.voice_channel = NULL;
257   media_session.video_channel = NULL;
258   media_session.data_channel = NULL;
259   media_session.recv_streams = NULL;
260
261   const ContentInfo* audio_offer = GetFirstAudioContent(offer);
262   const ContentInfo* video_offer = GetFirstVideoContent(offer);
263   const ContentInfo* data_offer = GetFirstDataContent(offer);
264   has_video_ = (video_offer != NULL);
265   has_data_ = (data_offer != NULL);
266
267   ASSERT(audio_offer != NULL);
268   // Create voice channel and start a media monitor.
269   media_session.voice_channel =
270       session_client_->channel_manager()->CreateVoiceChannel(
271           session, audio_offer->name, has_video_);
272   // voice_channel can be NULL in case of NullVoiceEngine.
273   if (media_session.voice_channel) {
274     media_session.voice_channel->SignalMediaMonitor.connect(
275         this, &Call::OnMediaMonitor);
276     media_session.voice_channel->StartMediaMonitor(kMediaMonitorInterval);
277   } else {
278     succeeded = false;
279   }
280
281   // If desired, create video channel and start a media monitor.
282   if (has_video_ && succeeded) {
283     media_session.video_channel =
284         session_client_->channel_manager()->CreateVideoChannel(
285             session,
286             video_offer->name,
287             true,
288             VideoOptions(),
289             media_session.voice_channel);
290     // video_channel can be NULL in case of NullVideoEngine.
291     if (media_session.video_channel) {
292       media_session.video_channel->SignalMediaMonitor.connect(
293           this, &Call::OnMediaMonitor);
294       media_session.video_channel->StartMediaMonitor(kMediaMonitorInterval);
295     } else {
296       succeeded = false;
297     }
298   }
299
300   // If desired, create data channel.
301   if (has_data_ && succeeded) {
302     const DataContentDescription* data = GetFirstDataContentDescription(offer);
303     if (data == NULL) {
304       succeeded = false;
305     } else {
306       DataChannelType data_channel_type = DCT_RTP;
307       if ((data->protocol() == kMediaProtocolSctp) ||
308           (data->protocol() == kMediaProtocolDtlsSctp)) {
309         data_channel_type = DCT_SCTP;
310       }
311
312       bool rtcp = false;
313       media_session.data_channel =
314           session_client_->channel_manager()->CreateDataChannel(
315               session, data_offer->name, rtcp, data_channel_type);
316       if (media_session.data_channel) {
317         media_session.data_channel->SignalDataReceived.connect(
318             this, &Call::OnDataReceived);
319       } else {
320         succeeded = false;
321       }
322     }
323   }
324
325   if (succeeded) {
326     // Add session to list, create channels for this session.
327     media_session.recv_streams = new MediaStreams;
328     media_session_map_[session->id()] = media_session;
329     session->SignalState.connect(this, &Call::OnSessionState);
330     session->SignalError.connect(this, &Call::OnSessionError);
331     session->SignalInfoMessage.connect(
332         this, &Call::OnSessionInfoMessage);
333     session->SignalRemoteDescriptionUpdate.connect(
334         this, &Call::OnRemoteDescriptionUpdate);
335     session->SignalReceivedTerminateReason
336       .connect(this, &Call::OnReceivedTerminateReason);
337
338     // If this call has the focus, enable this session's channels.
339     if (session_client_->GetFocus() == this) {
340       EnableSessionChannels(session, true);
341     }
342
343     // Signal client.
344     SignalAddSession(this, session);
345   }
346
347   return succeeded;
348 }
349
350 void Call::RemoveSession(Session* session) {
351   MediaSessionMap::iterator it = media_session_map_.find(session->id());
352   if (it == media_session_map_.end())
353     return;
354
355   // Remove all the screencasts, if they haven't been already.
356   while (!it->second.started_screencasts.empty()) {
357     uint32 ssrc = it->second.started_screencasts.begin()->first;
358     if (!StopScreencastWithoutSendingUpdate(it->second.session, ssrc)) {
359       LOG(LS_ERROR) << "Unable to stop screencast with ssrc " << ssrc;
360       ASSERT(false);
361     }
362   }
363
364   // Destroy video channel
365   VideoChannel* video_channel = it->second.video_channel;
366   if (video_channel != NULL)
367     session_client_->channel_manager()->DestroyVideoChannel(video_channel);
368
369   // Destroy voice channel
370   VoiceChannel* voice_channel = it->second.voice_channel;
371   if (voice_channel != NULL)
372     session_client_->channel_manager()->DestroyVoiceChannel(voice_channel);
373
374   // Destroy data channel
375   DataChannel* data_channel = it->second.data_channel;
376   if (data_channel != NULL)
377     session_client_->channel_manager()->DestroyDataChannel(data_channel);
378
379   delete it->second.recv_streams;
380   media_session_map_.erase(it);
381
382   // Destroy speaker monitor
383   StopSpeakerMonitor(session);
384
385   // Signal client
386   SignalRemoveSession(this, session);
387
388   // The call auto destroys when the last session is removed
389   rtc::Thread::Current()->Post(this, MSG_CHECKAUTODESTROY);
390 }
391
392 VoiceChannel* Call::GetVoiceChannel(Session* session) const {
393   MediaSessionMap::const_iterator it = media_session_map_.find(session->id());
394   return (it != media_session_map_.end()) ? it->second.voice_channel : NULL;
395 }
396
397 VideoChannel* Call::GetVideoChannel(Session* session) const {
398   MediaSessionMap::const_iterator it = media_session_map_.find(session->id());
399   return (it != media_session_map_.end()) ? it->second.video_channel : NULL;
400 }
401
402 DataChannel* Call::GetDataChannel(Session* session) const {
403   MediaSessionMap::const_iterator it = media_session_map_.find(session->id());
404   return (it != media_session_map_.end()) ? it->second.data_channel : NULL;
405 }
406
407 MediaStreams* Call::GetMediaStreams(Session* session) const {
408   MediaSessionMap::const_iterator it = media_session_map_.find(session->id());
409   return (it != media_session_map_.end()) ? it->second.recv_streams : NULL;
410 }
411
412 void Call::EnableChannels(bool enable) {
413   MediaSessionMap::iterator it;
414   for (it = media_session_map_.begin(); it != media_session_map_.end(); ++it) {
415     EnableSessionChannels(it->second.session, enable);
416   }
417 }
418
419 void Call::EnableSessionChannels(Session* session, bool enable) {
420   MediaSessionMap::iterator it = media_session_map_.find(session->id());
421   if (it == media_session_map_.end())
422     return;
423
424   VoiceChannel* voice_channel = it->second.voice_channel;
425   VideoChannel* video_channel = it->second.video_channel;
426   DataChannel* data_channel = it->second.data_channel;
427   if (voice_channel != NULL)
428     voice_channel->Enable(enable);
429   if (video_channel != NULL)
430     video_channel->Enable(enable);
431   if (data_channel != NULL)
432     data_channel->Enable(enable);
433 }
434
435 void Call::Mute(bool mute) {
436   muted_ = mute;
437   MediaSessionMap::iterator it;
438   for (it = media_session_map_.begin(); it != media_session_map_.end(); ++it) {
439     if (it->second.voice_channel != NULL)
440       it->second.voice_channel->MuteStream(0, mute);
441   }
442 }
443
444 void Call::MuteVideo(bool mute) {
445   video_muted_ = mute;
446   MediaSessionMap::iterator it;
447   for (it = media_session_map_.begin(); it != media_session_map_.end(); ++it) {
448     if (it->second.video_channel != NULL)
449       it->second.video_channel->MuteStream(0, mute);
450   }
451 }
452
453 bool Call::SendData(Session* session,
454                     const SendDataParams& params,
455                     const rtc::Buffer& payload,
456                     SendDataResult* result) {
457   DataChannel* data_channel = GetDataChannel(session);
458   if (!data_channel) {
459     LOG(LS_WARNING) << "Could not send data: no data channel.";
460     return false;
461   }
462
463   return data_channel->SendData(params, payload, result);
464 }
465
466 void Call::PressDTMF(int event) {
467   // Queue up this digit
468   if (queued_dtmf_.size() < kMaxDTMFDigits) {
469     LOG(LS_INFO) << "Call::PressDTMF(" << event << ")";
470
471     queued_dtmf_.push_back(event);
472
473     if (!playing_dtmf_) {
474       ContinuePlayDTMF();
475     }
476   }
477 }
478
479 cricket::VideoFormat ScreencastFormatFromFps(int fps) {
480   // The capturer pretty much ignore this, but just in case we give it
481   // a resolution big enough to cover any expected desktop.  In any
482   // case, it can't be 0x0, or the CaptureManager will fail to use it.
483   return cricket::VideoFormat(
484       1, 1,
485       cricket::VideoFormat::FpsToInterval(fps), cricket::FOURCC_ANY);
486 }
487
488 bool Call::StartScreencast(Session* session,
489                            const std::string& streamid, uint32 ssrc,
490                            const ScreencastId& screenid, int fps) {
491   MediaSessionMap::iterator it = media_session_map_.find(session->id());
492   if (it == media_session_map_.end()) {
493     return false;
494   }
495
496   VideoChannel *video_channel = GetVideoChannel(session);
497   if (!video_channel) {
498     LOG(LS_WARNING) << "Cannot add screencast"
499                     << " because there is no video channel.";
500     return false;
501   }
502
503   VideoCapturer* capturer = session_client_->channel_manager()->
504       CreateScreenCapturer(screenid);
505   if (!capturer) {
506     LOG(LS_WARNING) << "Could not create screencast capturer.";
507     return false;
508   }
509
510   if (!video_channel->AddScreencast(ssrc, capturer)) {
511     delete capturer;
512     LOG(LS_WARNING) << "Could not add screencast capturer.";
513     return false;
514   }
515
516   VideoFormat format = ScreencastFormatFromFps(fps);
517   if (!session_client_->channel_manager()->StartVideoCapture(
518           capturer, format)) {
519     LOG(LS_WARNING) << "Could not start video capture.";
520     video_channel->RemoveScreencast(ssrc);
521     return false;
522   }
523
524   if (!video_channel->SetCapturer(ssrc, capturer)) {
525     LOG(LS_WARNING) << "Could not start sending screencast.";
526     session_client_->channel_manager()->StopVideoCapture(
527         capturer, ScreencastFormatFromFps(fps));
528     video_channel->RemoveScreencast(ssrc);
529   }
530
531   // TODO(pthatcher): Once the CaptureManager has a nicer interface
532   // for removing captures (such as having StartCapture return a
533   // handle), remove this StartedCapture stuff.
534   it->second.started_screencasts.insert(
535       std::make_pair(ssrc, StartedCapture(capturer, format)));
536
537   // TODO(pthatcher): Verify we aren't re-using an existing id or
538   // ssrc.
539   StreamParams stream;
540   stream.id = streamid;
541   stream.ssrcs.push_back(ssrc);
542   VideoContentDescription* video = CreateVideoStreamUpdate(stream);
543
544   // TODO(pthatcher): Wait until view request before sending video.
545   video_channel->SetLocalContent(video, CA_UPDATE, NULL);
546   SendVideoStreamUpdate(session, video);
547   return true;
548 }
549
550 bool Call::StopScreencast(Session* session,
551                           const std::string& streamid, uint32 ssrc) {
552   if (!StopScreencastWithoutSendingUpdate(session, ssrc)) {
553     return false;
554   }
555
556   VideoChannel *video_channel = GetVideoChannel(session);
557   if (!video_channel) {
558     LOG(LS_WARNING) << "Cannot add screencast"
559                     << " because there is no video channel.";
560     return false;
561   }
562
563   StreamParams stream;
564   stream.id = streamid;
565   // No ssrcs
566   VideoContentDescription* video = CreateVideoStreamUpdate(stream);
567
568   video_channel->SetLocalContent(video, CA_UPDATE, NULL);
569   SendVideoStreamUpdate(session, video);
570   return true;
571 }
572
573 bool Call::StopScreencastWithoutSendingUpdate(
574     Session* session, uint32 ssrc) {
575   MediaSessionMap::iterator it = media_session_map_.find(session->id());
576   if (it == media_session_map_.end()) {
577     return false;
578   }
579
580   VideoChannel *video_channel = GetVideoChannel(session);
581   if (!video_channel) {
582     LOG(LS_WARNING) << "Cannot remove screencast"
583                     << " because there is no video channel.";
584     return false;
585   }
586
587   StartedScreencastMap::const_iterator screencast_iter =
588       it->second.started_screencasts.find(ssrc);
589   if (screencast_iter == it->second.started_screencasts.end()) {
590     LOG(LS_WARNING) << "Could not stop screencast " << ssrc
591                     << " because there is no capturer.";
592     return false;
593   }
594
595   VideoCapturer* capturer = screencast_iter->second.capturer;
596   VideoFormat format = screencast_iter->second.format;
597   video_channel->SetCapturer(ssrc, NULL);
598   if (!session_client_->channel_manager()->StopVideoCapture(
599           capturer, format)) {
600     LOG(LS_WARNING) << "Could not stop screencast " << ssrc
601                     << " because could not stop capture.";
602     return false;
603   }
604   video_channel->RemoveScreencast(ssrc);
605   it->second.started_screencasts.erase(ssrc);
606   return true;
607 }
608
609 VideoContentDescription* Call::CreateVideoStreamUpdate(
610     const StreamParams& stream) {
611   VideoContentDescription* video = new VideoContentDescription();
612   video->set_multistream(true);
613   video->set_partial(true);
614   video->AddStream(stream);
615   return video;
616 }
617
618 void Call::SendVideoStreamUpdate(
619     Session* session, VideoContentDescription* video) {
620   // Takes the ownership of |video|.
621   rtc::scoped_ptr<VideoContentDescription> description(video);
622   const ContentInfo* video_info =
623       GetFirstVideoContent(session->local_description());
624   if (video_info == NULL) {
625     LOG(LS_WARNING) << "Cannot send stream update for video.";
626     return;
627   }
628
629   std::vector<ContentInfo> contents;
630   contents.push_back(
631       ContentInfo(video_info->name, video_info->type, description.get()));
632
633   session->SendDescriptionInfoMessage(contents);
634 }
635
636 void Call::ContinuePlayDTMF() {
637   playing_dtmf_ = false;
638
639   // Check to see if we have a queued tone
640   if (queued_dtmf_.size() > 0) {
641     playing_dtmf_ = true;
642
643     int tone = queued_dtmf_.front();
644     queued_dtmf_.pop_front();
645
646     LOG(LS_INFO) << "Call::ContinuePlayDTMF(" << tone << ")";
647     for (MediaSessionMap::iterator it = media_session_map_.begin();
648          it != media_session_map_.end(); ++it) {
649       if (it->second.voice_channel != NULL) {
650         it->second.voice_channel->PressDTMF(tone, true);
651       }
652     }
653
654     // Post a message to play the next tone or at least clear the playing_dtmf_
655     // bit.
656     rtc::Thread::Current()->PostDelayed(kDTMFDelay, this, MSG_PLAYDTMF);
657   }
658 }
659
660 void Call::Join(Call* call, bool enable) {
661   for (MediaSessionMap::iterator it = call->media_session_map_.begin();
662        it != call->media_session_map_.end(); ++it) {
663     // Shouldn't already exist.
664     ASSERT(media_session_map_.find(it->first) == media_session_map_.end());
665     media_session_map_[it->first] = it->second;
666
667     it->second.session->SignalState.connect(this, &Call::OnSessionState);
668     it->second.session->SignalError.connect(this, &Call::OnSessionError);
669     it->second.session->SignalReceivedTerminateReason
670       .connect(this, &Call::OnReceivedTerminateReason);
671
672     EnableSessionChannels(it->second.session, enable);
673   }
674
675   // Moved all the sessions over, so the other call should no longer have any.
676   call->media_session_map_.clear();
677 }
678
679 void Call::StartConnectionMonitor(Session* session, int cms) {
680   VoiceChannel* voice_channel = GetVoiceChannel(session);
681   if (voice_channel) {
682     voice_channel->SignalConnectionMonitor.connect(this,
683         &Call::OnConnectionMonitor);
684     voice_channel->StartConnectionMonitor(cms);
685   }
686
687   VideoChannel* video_channel = GetVideoChannel(session);
688   if (video_channel) {
689     video_channel->SignalConnectionMonitor.connect(this,
690         &Call::OnConnectionMonitor);
691     video_channel->StartConnectionMonitor(cms);
692   }
693 }
694
695 void Call::StopConnectionMonitor(Session* session) {
696   VoiceChannel* voice_channel = GetVoiceChannel(session);
697   if (voice_channel) {
698     voice_channel->StopConnectionMonitor();
699     voice_channel->SignalConnectionMonitor.disconnect(this);
700   }
701
702   VideoChannel* video_channel = GetVideoChannel(session);
703   if (video_channel) {
704     video_channel->StopConnectionMonitor();
705     video_channel->SignalConnectionMonitor.disconnect(this);
706   }
707 }
708
709 void Call::StartAudioMonitor(Session* session, int cms) {
710   VoiceChannel* voice_channel = GetVoiceChannel(session);
711   if (voice_channel) {
712     voice_channel->SignalAudioMonitor.connect(this, &Call::OnAudioMonitor);
713     voice_channel->StartAudioMonitor(cms);
714   }
715 }
716
717 void Call::StopAudioMonitor(Session* session) {
718   VoiceChannel* voice_channel = GetVoiceChannel(session);
719   if (voice_channel) {
720     voice_channel->StopAudioMonitor();
721     voice_channel->SignalAudioMonitor.disconnect(this);
722   }
723 }
724
725 bool Call::IsAudioMonitorRunning(Session* session) {
726   VoiceChannel* voice_channel = GetVoiceChannel(session);
727   if (voice_channel) {
728     return voice_channel->IsAudioMonitorRunning();
729   } else {
730     return false;
731   }
732 }
733
734 void Call::StartSpeakerMonitor(Session* session) {
735   if (speaker_monitor_map_.find(session->id()) == speaker_monitor_map_.end()) {
736     if (!IsAudioMonitorRunning(session)) {
737       StartAudioMonitor(session, kAudioMonitorPollPeriodMillis);
738     }
739     CurrentSpeakerMonitor* speaker_monitor =
740         new cricket::CurrentSpeakerMonitor(
741             audio_source_proxy_.get(), session);
742     speaker_monitor->SignalUpdate.connect(this, &Call::OnSpeakerMonitor);
743     speaker_monitor->Start();
744     speaker_monitor_map_[session->id()] = speaker_monitor;
745   } else {
746     LOG(LS_WARNING) << "Already started speaker monitor for session "
747                     << session->id() << ".";
748   }
749 }
750
751 void Call::StopSpeakerMonitor(Session* session) {
752   if (speaker_monitor_map_.find(session->id()) == speaker_monitor_map_.end()) {
753     LOG(LS_WARNING) << "Speaker monitor for session "
754                     << session->id() << " already stopped.";
755   } else {
756     CurrentSpeakerMonitor* monitor = speaker_monitor_map_[session->id()];
757     monitor->Stop();
758     speaker_monitor_map_.erase(session->id());
759     delete monitor;
760   }
761 }
762
763 void Call::OnConnectionMonitor(VoiceChannel* channel,
764                                const std::vector<ConnectionInfo> &infos) {
765   SignalConnectionMonitor(this, infos);
766 }
767
768 void Call::OnMediaMonitor(VoiceChannel* channel, const VoiceMediaInfo& info) {
769   last_voice_media_info_ = info;
770   SignalMediaMonitor(this, info);
771 }
772
773 void Call::OnAudioMonitor(VoiceChannel* channel, const AudioInfo& info) {
774   SignalAudioMonitor(this, info);
775 }
776
777 void Call::OnSpeakerMonitor(CurrentSpeakerMonitor* monitor, uint32 ssrc) {
778   Session* session = static_cast<Session*>(monitor->session());
779   MediaStreams* recv_streams = GetMediaStreams(session);
780   if (recv_streams) {
781     StreamParams stream;
782     recv_streams->GetAudioStream(StreamSelector(ssrc), &stream);
783     SignalSpeakerMonitor(this, session, stream);
784   }
785 }
786
787 void Call::OnConnectionMonitor(VideoChannel* channel,
788                                const std::vector<ConnectionInfo> &infos) {
789   SignalVideoConnectionMonitor(this, infos);
790 }
791
792 void Call::OnMediaMonitor(VideoChannel* channel, const VideoMediaInfo& info) {
793   SignalVideoMediaMonitor(this, info);
794 }
795
796 void Call::OnDataReceived(DataChannel* channel,
797                           const ReceiveDataParams& params,
798                           const rtc::Buffer& payload) {
799   SignalDataReceived(this, params, payload);
800 }
801
802 uint32 Call::id() {
803   return id_;
804 }
805
806 void Call::OnSessionState(BaseSession* base_session, BaseSession::State state) {
807   Session* session = static_cast<Session*>(base_session);
808   switch (state) {
809     case Session::STATE_RECEIVEDACCEPT:
810       UpdateRemoteMediaStreams(session,
811           session->remote_description()->contents(), false);
812       session_client_->session_manager()->signaling_thread()->Clear(this,
813           MSG_TERMINATECALL);
814       break;
815     case Session::STATE_RECEIVEDREJECT:
816     case Session::STATE_RECEIVEDTERMINATE:
817       session_client_->session_manager()->signaling_thread()->Clear(this,
818           MSG_TERMINATECALL);
819       break;
820     default:
821       break;
822   }
823   SignalSessionState(this, session, state);
824 }
825
826 void Call::OnSessionError(BaseSession* base_session, Session::Error error) {
827   session_client_->session_manager()->signaling_thread()->Clear(this,
828       MSG_TERMINATECALL);
829   SignalSessionError(this, static_cast<Session*>(base_session), error);
830 }
831
832 void Call::OnSessionInfoMessage(Session* session,
833                                 const buzz::XmlElement* action_elem) {
834   if (!IsJingleViewRequest(action_elem)) {
835     return;
836   }
837
838   ViewRequest view_request;
839   ParseError error;
840   if (!ParseJingleViewRequest(action_elem, &view_request, &error)) {
841     LOG(LS_WARNING) << "Failed to parse view request: " << error.text;
842     return;
843   }
844
845   VideoChannel* video_channel = GetVideoChannel(session);
846   if (video_channel == NULL) {
847     LOG(LS_WARNING) << "Ignore view request since we have no video channel.";
848     return;
849   }
850
851   if (!video_channel->ApplyViewRequest(view_request)) {
852     LOG(LS_WARNING) << "Failed to ApplyViewRequest.";
853   }
854 }
855
856 void Call::OnRemoteDescriptionUpdate(BaseSession* base_session,
857                                      const ContentInfos& updated_contents) {
858   Session* session = static_cast<Session*>(base_session);
859
860   const ContentInfo* audio_content = GetFirstAudioContent(updated_contents);
861   if (audio_content) {
862     const AudioContentDescription* audio_update =
863         static_cast<const AudioContentDescription*>(audio_content->description);
864     if (!audio_update->codecs().empty()) {
865       UpdateVoiceChannelRemoteContent(session, audio_update);
866     }
867   }
868
869   const ContentInfo* video_content = GetFirstVideoContent(updated_contents);
870   if (video_content) {
871     const VideoContentDescription* video_update =
872         static_cast<const VideoContentDescription*>(video_content->description);
873     if (!video_update->codecs().empty()) {
874       UpdateVideoChannelRemoteContent(session, video_update);
875     }
876   }
877
878   const ContentInfo* data_content = GetFirstDataContent(updated_contents);
879   if (data_content) {
880     const DataContentDescription* data_update =
881         static_cast<const DataContentDescription*>(data_content->description);
882     if (!data_update->codecs().empty()) {
883       UpdateDataChannelRemoteContent(session, data_update);
884     }
885   }
886
887   UpdateRemoteMediaStreams(session, updated_contents, true);
888 }
889
890 bool Call::UpdateVoiceChannelRemoteContent(
891     Session* session, const AudioContentDescription* audio) {
892   VoiceChannel* voice_channel = GetVoiceChannel(session);
893   if (!voice_channel->SetRemoteContent(audio, CA_UPDATE, NULL)) {
894     const std::string error_desc =
895         "Failure in audio SetRemoteContent with CA_UPDATE";
896     LOG(LS_ERROR) << error_desc;
897     session->SetError(BaseSession::ERROR_CONTENT, error_desc);
898     return false;
899   }
900   return true;
901 }
902
903 bool Call::UpdateVideoChannelRemoteContent(
904     Session* session, const VideoContentDescription* video) {
905   VideoChannel* video_channel = GetVideoChannel(session);
906   if (!video_channel->SetRemoteContent(video, CA_UPDATE, NULL)) {
907     const std::string error_desc =
908         "Failure in video SetRemoteContent with CA_UPDATE";
909     LOG(LS_ERROR) << error_desc;
910     session->SetError(BaseSession::ERROR_CONTENT, error_desc);
911     return false;
912   }
913   return true;
914 }
915
916 bool Call::UpdateDataChannelRemoteContent(
917     Session* session, const DataContentDescription* data) {
918   DataChannel* data_channel = GetDataChannel(session);
919   if (!data_channel->SetRemoteContent(data, CA_UPDATE, NULL)) {
920     const std::string error_desc =
921         "Failure in data SetRemoteContent with CA_UPDATE";
922     LOG(LS_ERROR) << error_desc;
923     session->SetError(BaseSession::ERROR_CONTENT, error_desc);
924     return false;
925   }
926   return true;
927 }
928
929 void Call::UpdateRemoteMediaStreams(Session* session,
930                                     const ContentInfos& updated_contents,
931                                     bool update_channels) {
932   MediaStreams* recv_streams = GetMediaStreams(session);
933   if (!recv_streams)
934     return;
935
936   cricket::MediaStreams added_streams;
937   cricket::MediaStreams removed_streams;
938
939   const ContentInfo* audio_content = GetFirstAudioContent(updated_contents);
940   if (audio_content) {
941     const AudioContentDescription* audio_update =
942         static_cast<const AudioContentDescription*>(audio_content->description);
943     UpdateRecvStreams(audio_update->streams(),
944                       update_channels ? GetVoiceChannel(session) : NULL,
945                       recv_streams->mutable_audio(),
946                       added_streams.mutable_audio(),
947                       removed_streams.mutable_audio());
948   }
949
950   const ContentInfo* video_content = GetFirstVideoContent(updated_contents);
951   if (video_content) {
952     const VideoContentDescription* video_update =
953         static_cast<const VideoContentDescription*>(video_content->description);
954     UpdateRecvStreams(video_update->streams(),
955                       update_channels ? GetVideoChannel(session) : NULL,
956                       recv_streams->mutable_video(),
957                       added_streams.mutable_video(),
958                       removed_streams.mutable_video());
959   }
960
961   const ContentInfo* data_content = GetFirstDataContent(updated_contents);
962   if (data_content) {
963     const DataContentDescription* data_update =
964         static_cast<const DataContentDescription*>(data_content->description);
965     UpdateRecvStreams(data_update->streams(),
966                       update_channels ? GetDataChannel(session) : NULL,
967                       recv_streams->mutable_data(),
968                       added_streams.mutable_data(),
969                       removed_streams.mutable_data());
970   }
971
972   if (!added_streams.empty() || !removed_streams.empty()) {
973     SignalMediaStreamsUpdate(this, session, added_streams, removed_streams);
974   }
975 }
976
977 void FindStreamChanges(const std::vector<StreamParams>& streams,
978                        const std::vector<StreamParams>& updates,
979                        std::vector<StreamParams>* added_streams,
980                        std::vector<StreamParams>* removed_streams) {
981   for (std::vector<StreamParams>::const_iterator update = updates.begin();
982        update != updates.end(); ++update) {
983     StreamParams stream;
984     if (GetStreamByIds(streams, update->groupid, update->id, &stream)) {
985       if (!update->has_ssrcs()) {
986         removed_streams->push_back(stream);
987       }
988     } else {
989       // There's a bug on reflector that will send <stream>s even
990       // though there is not ssrc (which means there isn't really a
991       // stream).  To work around it, we simply ignore new <stream>s
992       // that don't have any ssrcs.
993       if (update->has_ssrcs()) {
994         added_streams->push_back(*update);
995       }
996     }
997   }
998 }
999
1000 void Call::UpdateRecvStreams(const std::vector<StreamParams>& update_streams,
1001                              BaseChannel* channel,
1002                              std::vector<StreamParams>* recv_streams,
1003                              std::vector<StreamParams>* added_streams,
1004                              std::vector<StreamParams>* removed_streams) {
1005   FindStreamChanges(*recv_streams,
1006                     update_streams, added_streams, removed_streams);
1007   AddRecvStreams(*added_streams,
1008                  channel, recv_streams);
1009   RemoveRecvStreams(*removed_streams,
1010                     channel, recv_streams);
1011 }
1012
1013 void Call::AddRecvStreams(const std::vector<StreamParams>& added_streams,
1014                           BaseChannel* channel,
1015                           std::vector<StreamParams>* recv_streams) {
1016   std::vector<StreamParams>::const_iterator stream;
1017   for (stream = added_streams.begin();
1018        stream != added_streams.end();
1019        ++stream) {
1020     AddRecvStream(*stream, channel, recv_streams);
1021   }
1022 }
1023
1024 void Call::AddRecvStream(const StreamParams& stream,
1025                          BaseChannel* channel,
1026                          std::vector<StreamParams>* recv_streams) {
1027   if (channel && stream.has_ssrcs()) {
1028     channel->AddRecvStream(stream);
1029   }
1030   recv_streams->push_back(stream);
1031 }
1032
1033 void Call::RemoveRecvStreams(const std::vector<StreamParams>& removed_streams,
1034                              BaseChannel* channel,
1035                              std::vector<StreamParams>* recv_streams) {
1036   std::vector<StreamParams>::const_iterator stream;
1037   for (stream = removed_streams.begin();
1038        stream != removed_streams.end();
1039        ++stream) {
1040     RemoveRecvStream(*stream, channel, recv_streams);
1041   }
1042 }
1043
1044 void Call::RemoveRecvStream(const StreamParams& stream,
1045                             BaseChannel* channel,
1046                             std::vector<StreamParams>* recv_streams) {
1047   if (channel && stream.has_ssrcs()) {
1048     // TODO(pthatcher): Change RemoveRecvStream to take a stream argument.
1049     channel->RemoveRecvStream(stream.first_ssrc());
1050   }
1051   RemoveStreamByIds(recv_streams, stream.groupid, stream.id);
1052 }
1053
1054 void Call::OnReceivedTerminateReason(Session* session,
1055                                      const std::string& reason) {
1056   session_client_->session_manager()->signaling_thread()->Clear(this,
1057     MSG_TERMINATECALL);
1058   SignalReceivedTerminateReason(this, session, reason);
1059 }
1060
1061 // TODO(mdodd): Get ride of this method since all Hangouts are using a secure
1062 // connection.
1063 bool Call::secure() const {
1064   if (session_client_->secure() == SEC_DISABLED) {
1065     return false;
1066   }
1067
1068   bool ret = true;
1069   int i = 0;
1070
1071   MediaSessionMap::const_iterator it;
1072   for (it = media_session_map_.begin(); it != media_session_map_.end(); ++it) {
1073     LOG_F(LS_VERBOSE) << "session[" << i
1074                       << "], check local and remote descriptions";
1075     i++;
1076
1077     if (!SessionDescriptionContainsCrypto(
1078             it->second.session->local_description()) ||
1079         !SessionDescriptionContainsCrypto(
1080             it->second.session->remote_description())) {
1081       ret = false;
1082       break;
1083     }
1084   }
1085
1086   LOG_F(LS_VERBOSE) << "secure=" << ret;
1087   return ret;
1088 }
1089
1090 bool Call::SessionDescriptionContainsCrypto(
1091     const SessionDescription* sdesc) const {
1092   if (sdesc == NULL) {
1093     LOG_F(LS_VERBOSE) << "sessionDescription is NULL";
1094     return false;
1095   }
1096
1097   return ContentContainsCrypto(sdesc->GetContentByName(CN_AUDIO)) &&
1098          ContentContainsCrypto(sdesc->GetContentByName(CN_VIDEO));
1099 }
1100
1101 Session* Call::InternalInitiateSession(const std::string& id,
1102                                        const buzz::Jid& to,
1103                                        const std::string& initiator_name,
1104                                        const CallOptions& options) {
1105   const SessionDescription* offer = session_client_->CreateOffer(options);
1106
1107   Session* session = session_client_->CreateSession(id, this);
1108   // Only override the initiator_name if it was manually supplied. Otherwise,
1109   // session_client_ will supply the local jid as initiator in CreateOffer.
1110   if (!initiator_name.empty()) {
1111     session->set_initiator_name(initiator_name);
1112   }
1113
1114   AddSession(session, offer);
1115   session->Initiate(to.Str(), offer);
1116
1117   // After this timeout, terminate the call because the callee isn't
1118   // answering
1119   session_client_->session_manager()->signaling_thread()->Clear(this,
1120       MSG_TERMINATECALL);
1121   session_client_->session_manager()->signaling_thread()->PostDelayed(
1122     send_to_voicemail_ ? kSendToVoicemailTimeout : kNoVoicemailTimeout,
1123     this, MSG_TERMINATECALL);
1124   return session;
1125 }
1126
1127 AudioSourceProxy* Call::GetAudioSourceProxy() {
1128   return audio_source_proxy_.get();
1129 }
1130
1131 }  // namespace cricket