1 /* 2 * libjingle 3 * Copyright 2011, 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 // This file contains classes used for handling signaling between 29 // two PeerConnections. 30 31 #ifndef TALK_APP_WEBRTC_ROAPSIGNALING_H_ 32 #define TALK_APP_WEBRTC_ROAPSIGNALING_H_ 33 34 #include <string> 35 36 #include "talk/app/webrtc/jsep.h" 37 #include "talk/app/webrtc/roaperrorcodes.h" 38 #include "talk/app/webrtc/roapsession.h" 39 #include "talk/base/scoped_ptr.h" 40 #include "talk/base/scoped_ref_ptr.h" 41 #include "talk/base/sigslot.h" 42 43 namespace cricket { 44 class ChannelManager; 45 class Candidate; 46 typedef std::vector<Candidate> Candidates; 47 } 48 49 namespace talk_base { 50 class Thread; 51 } 52 53 namespace webrtc { 54 class MediaStreamSignaling; 55 class StreamCollection; 56 class StreamCollectionInterface; 57 class MediaStreamInterface; 58 59 // RoapSignaling is a class responsible for handling signaling 60 // between two PeerConnection objects. 61 // 62 // RoapSignaling is Thread-compatible and all non-const methods are 63 // expected to be called on the signaling thread. 64 // 65 // Note that before RoapSignaling can process an answer or create an 66 // offer OnIceComplete has to be called. The last request to create an offer 67 // or process an answer will be processed after OnIceComplete has been 68 // called. 69 // 70 // Call CreateOffer to negotiate new local streams to send. 71 // Call ProcessSignalingMessage when a new message has been received from the 72 // remote peer. This might result in one or more signals being triggered to 73 // indicate changes in the offer from the the remote peer or a detected error. 74 // RoapSignaling creates Offers and Answers asynchronous on the 75 // signaling thread. 76 // 77 // Example usage: Creating an offer with one audio track. 78 // 79 // class ProviderImpl : public JsepInterface { 80 // ... 81 // }; 82 // 83 // void OnSignalingMessage(const std::string& smessage) { ... } 84 // 85 // ProviderImpl impl; 86 // RoapSignaling pc(talk_base::Thread::Current(), &impl); 87 // 88 // // Connect the function OnSignalingMessage to the signal 89 // // SignalNewPeerConnectionMessage. 90 // pc.SignalNewPeerConnectionMessage.connect(&OnSignalingMessage); 91 // 92 // // Initialize RoapSignaling by providing the candidates for 93 // // this session. 94 // pc.OnCandidatesReady(candidates); 95 // // Create an offer with one stream with one audio track. 96 // AudioTrack audio; 97 // MediaStream local_stream1; 98 // local_stream1.AddTrack(&audio); 99 // StreamCollection local_streams; 100 // local_streams.AddStream(&local_stream1) 101 // pc.CreateOffer(&local_streams); 102 // // When the offer has been created, OnsignalingMessage is called 103 // // with the offer in a string. Provide this offer to the remote 104 // // PeerConnection. The remote PeerConnection will then respond with an answer 105 // // string. Provide this answer string to RoapSignaling. 106 // pc.ProcessSignalingMessage(remote_message, &local_streams); 107 108 class RoapSignaling : public IceCandidateObserver { 109 public: 110 enum State { 111 // RoapSignaling is new. Ice has not started. 112 kNew, 113 // Ice has started. Awaiting the local candidates. 114 kInitializing, 115 // Ready to sent new offer or receive a new offer. 116 kIdle, 117 // An offer has been sent and expect an answer. 118 kWaitingForAnswer, 119 // An answer has been sent and expect an ok message. 120 kWaitingForOK, 121 // SendShutdown has been called. No more messages are processed. 122 kShutingDown, 123 // Shutdown message has been received or the remote peer has answered ok 124 // to a sent shutdown message. 125 kShutdownComplete, 126 }; 127 128 // Constructs a RoapSignaling instance. 129 // provider - Implementation of the JsepInterface interface. 130 RoapSignaling(MediaStreamSignaling* mediastream_signaling_, 131 JsepInterface* provider); 132 virtual ~RoapSignaling(); 133 134 // Process a received offer/answer from the remote peer. 135 // local_streams must be the collection of streams the peerconnection 136 // currently would like to send. 137 void ProcessSignalingMessage(const std::string& message, 138 StreamCollectionInterface* local_streams); 139 140 // Creates an offer containing all tracks in local_streams. 141 // When the offer is ready it is signaled by SignalNewPeerConnectionMessage. 142 // When the remote peer is ready to receive media on a stream , the state of 143 // the local streams will change to kLive. 144 void CreateOffer(StreamCollectionInterface* local_streams); 145 146 // Creates a ShutDown message to be sent to the remote peer. 147 // When the message is ready it is signaled by SignalNewPeerConnectionMessage. 148 // After calling this no more offers or answers to offers can be created. 149 void SendShutDown(); 150 151 // Implements IceCandidateObserver interface. 152 // OnIceComplete is called when all local candidates have been collected. 153 // This tell RoapSignaling that it is ready to respond to offers 154 // or create offer messages. 155 virtual void OnIceComplete(); 156 157 // Implements IceCandidateObserver interface. 158 // OnIceCandidate is called when a local candidate has been collected. 159 virtual void OnIceCandidate(const IceCandidateInterface* candidate); 160 161 // Returns the current state. GetState()162 State GetState() const { return state_; } 163 164 // A new ROAP message is ready to be sent. The listener to this signal is 165 // supposed to deliver this message to the remote peer. 166 sigslot::signal1<const std::string&> SignalNewPeerConnectionMessage; 167 168 // The signaling state has changed. 169 sigslot::signal1<State> SignalStateChange; 170 171 // Remote PeerConnection sent an error message. 172 sigslot::signal1<RoapErrorCode> SignalErrorMessageReceived; 173 174 private: 175 typedef std::list<talk_base::scoped_refptr<StreamCollectionInterface> > 176 StreamCollectionList; 177 178 // Change the State and triggers the SignalStateChange signal. 179 void ChangeState(State new_state); 180 181 // This is called by CreateOffer. Creates an offer based on the first stream 182 // collection in |queued_local_streams_|. 183 void InitializeSendingOffer(); 184 // Serializes and sends |local_desc| 185 void SendOffer(const SessionDescriptionInterface* local_desc); 186 187 // This is called by ProcessSignalingMessage when a remote offer 188 // has been received. 189 void InitializeSendingAnswer(StreamCollectionInterface* local_streams); 190 // Serializes and sends |local_desc_|. 191 void SendAnswer(); 192 193 // Notifies the |provider_| about the shutdown. 194 // This is either initiated by ProcessSignalingMessage when a remote shutdown 195 // message has been received or by a call to SendShutDown. 196 void DoShutDown(); 197 198 // Process session description from the remote peer. 199 bool ProcessRemoteDescription(const std::string& sdp, 200 JsepInterface::Action action); 201 202 // Updates the state of local streams based on the answer_desc and the streams 203 // that have been negotiated in negotiated_streams. 204 void UpdateSendingLocalStreams( 205 const cricket::SessionDescription* answer_desc, 206 StreamCollectionInterface* negotiated_streams); 207 208 MediaStreamSignaling* stream_signaling_; 209 JsepInterface* provider_; 210 State state_; 211 212 // Flag indicating RoapSignaling was called with an offer while 213 // RoapSignaling is in kInitializing state. 214 bool received_pre_offer_; 215 216 // LocalStreams queued for later use if CreateOffer 217 // is called while RoapSignaling is in kNew state or 218 // CreateOffer is called while RoapSignaling is currently sending 219 // an offer. 220 StreamCollectionList queued_local_streams_; 221 222 // The local session description of the local MediaStreams that is being 223 // negotiated. 224 talk_base::scoped_ptr<SessionDescriptionInterface> local_desc_; 225 226 // Local MediaStreams being negotiated. 227 talk_base::scoped_refptr<StreamCollection> local_streams_; 228 229 // roap_session_ holds the ROAP-specific session state and is used for 230 // creating a parsing ROAP messages. 231 RoapSession roap_session_; 232 233 DISALLOW_COPY_AND_ASSIGN(RoapSignaling); 234 }; 235 236 } // namespace webrtc 237 238 #endif // TALK_APP_WEBRTC_ROAPSIGNALING_H_ 239