OLD | NEW |
1 /* | 1 /* |
2 * Copyright 2004 The WebRTC Project Authors. All rights reserved. | 2 * Copyright 2004 The WebRTC Project Authors. All rights reserved. |
3 * | 3 * |
4 * Use of this source code is governed by a BSD-style license | 4 * Use of this source code is governed by a BSD-style license |
5 * that can be found in the LICENSE file in the root of the source | 5 * that can be found in the LICENSE file in the root of the source |
6 * tree. An additional intellectual property rights grant can be found | 6 * tree. An additional intellectual property rights grant can be found |
7 * in the file PATENTS. All contributing project authors may | 7 * in the file PATENTS. All contributing project authors may |
8 * be found in the AUTHORS file in the root of the source tree. | 8 * be found in the AUTHORS file in the root of the source tree. |
9 */ | 9 */ |
10 | 10 |
11 #ifndef WEBRTC_P2P_BASE_SESSION_H_ | 11 #ifndef WEBRTC_P2P_BASE_SESSION_H_ |
12 #define WEBRTC_P2P_BASE_SESSION_H_ | 12 #define WEBRTC_P2P_BASE_SESSION_H_ |
13 | 13 |
14 #include <list> | 14 #include <list> |
15 #include <map> | 15 #include <map> |
16 #include <string> | 16 #include <string> |
17 #include <vector> | 17 #include <vector> |
18 | 18 |
19 #include "webrtc/p2p/base/candidate.h" | |
20 #include "webrtc/p2p/base/port.h" | |
21 #include "webrtc/p2p/base/transport.h" | |
22 #include "webrtc/base/refcount.h" | 19 #include "webrtc/base/refcount.h" |
23 #include "webrtc/base/scoped_ptr.h" | 20 #include "webrtc/base/scoped_ptr.h" |
24 #include "webrtc/base/scoped_ref_ptr.h" | 21 #include "webrtc/base/scoped_ref_ptr.h" |
25 #include "webrtc/base/socketaddress.h" | 22 #include "webrtc/base/socketaddress.h" |
| 23 #include "webrtc/p2p/base/candidate.h" |
| 24 #include "webrtc/p2p/base/port.h" |
| 25 #include "webrtc/p2p/base/transport.h" |
26 | 26 |
27 namespace cricket { | 27 namespace cricket { |
28 | 28 |
29 class BaseSession; | 29 class BaseSession; |
30 class P2PTransportChannel; | 30 class P2PTransportChannel; |
31 class Transport; | 31 class Transport; |
32 class TransportChannel; | 32 class TransportChannel; |
33 class TransportChannelProxy; | 33 class TransportChannelProxy; |
34 class TransportChannelImpl; | 34 class TransportChannelImpl; |
35 | 35 class TransportController; |
36 typedef rtc::RefCountedObject<rtc::scoped_ptr<Transport> > | |
37 TransportWrapper; | |
38 | |
39 // Bundles a Transport and ChannelMap together. ChannelMap is used to | |
40 // create transport channels before receiving or sending a session | |
41 // initiate, and for speculatively connecting channels. Previously, a | |
42 // session had one ChannelMap and transport. Now, with multiple | |
43 // transports per session, we need multiple ChannelMaps as well. | |
44 | |
45 typedef std::map<int, TransportChannelProxy*> ChannelMap; | |
46 | |
47 class TransportProxy : public sigslot::has_slots<> { | |
48 public: | |
49 TransportProxy( | |
50 rtc::Thread* worker_thread, | |
51 const std::string& sid, | |
52 const std::string& content_name, | |
53 TransportWrapper* transport) | |
54 : worker_thread_(worker_thread), | |
55 sid_(sid), | |
56 content_name_(content_name), | |
57 transport_(transport), | |
58 connecting_(false), | |
59 negotiated_(false), | |
60 sent_candidates_(false), | |
61 candidates_allocated_(false), | |
62 local_description_set_(false), | |
63 remote_description_set_(false) { | |
64 transport_->get()->SignalCandidatesReady.connect( | |
65 this, &TransportProxy::OnTransportCandidatesReady); | |
66 } | |
67 ~TransportProxy(); | |
68 | |
69 const std::string& content_name() const { return content_name_; } | |
70 // TODO(juberti): It's not good form to expose the object you're wrapping, | |
71 // since callers can mutate it. Can we make this return a const Transport*? | |
72 Transport* impl() const { return transport_->get(); } | |
73 | |
74 const std::string& type() const; | |
75 bool negotiated() const { return negotiated_; } | |
76 const Candidates& sent_candidates() const { return sent_candidates_; } | |
77 const Candidates& unsent_candidates() const { return unsent_candidates_; } | |
78 bool candidates_allocated() const { return candidates_allocated_; } | |
79 void set_candidates_allocated(bool allocated) { | |
80 candidates_allocated_ = allocated; | |
81 } | |
82 | |
83 TransportChannel* GetChannel(int component); | |
84 TransportChannel* CreateChannel(int component); | |
85 bool HasChannel(int component); | |
86 void DestroyChannel(int component); | |
87 | |
88 void AddSentCandidates(const Candidates& candidates); | |
89 void AddUnsentCandidates(const Candidates& candidates); | |
90 void ClearSentCandidates() { sent_candidates_.clear(); } | |
91 void ClearUnsentCandidates() { unsent_candidates_.clear(); } | |
92 | |
93 // Start the connection process for any channels, creating impls if needed. | |
94 void ConnectChannels(); | |
95 // Hook up impls to the proxy channels. Doesn't change connect state. | |
96 void CompleteNegotiation(); | |
97 | |
98 // Mux this proxy onto the specified proxy's transport. | |
99 bool SetupMux(TransportProxy* proxy); | |
100 | |
101 // Simple functions that thunk down to the same functions on Transport. | |
102 void SetIceRole(IceRole role); | |
103 void SetIdentity(rtc::SSLIdentity* identity); | |
104 bool SetLocalTransportDescription(const TransportDescription& description, | |
105 ContentAction action, | |
106 std::string* error_desc); | |
107 bool SetRemoteTransportDescription(const TransportDescription& description, | |
108 ContentAction action, | |
109 std::string* error_desc); | |
110 void OnSignalingReady(); | |
111 bool OnRemoteCandidates(const Candidates& candidates, std::string* error); | |
112 | |
113 // Called when a transport signals that it has new candidates. | |
114 void OnTransportCandidatesReady(cricket::Transport* transport, | |
115 const Candidates& candidates) { | |
116 SignalCandidatesReady(this, candidates); | |
117 } | |
118 | |
119 bool local_description_set() const { | |
120 return local_description_set_; | |
121 } | |
122 bool remote_description_set() const { | |
123 return remote_description_set_; | |
124 } | |
125 | |
126 // Handles sending of ready candidates and receiving of remote candidates. | |
127 sigslot::signal2<TransportProxy*, | |
128 const std::vector<Candidate>&> SignalCandidatesReady; | |
129 | |
130 private: | |
131 TransportChannelProxy* GetChannelProxy(int component) const; | |
132 | |
133 // Creates a new channel on the Transport which causes the reference | |
134 // count to increment. | |
135 void CreateChannelImpl(int component); | |
136 void CreateChannelImpl_w(int component); | |
137 | |
138 // Manipulators of transportchannelimpl in channel proxy. | |
139 void SetChannelImplFromTransport(TransportChannelProxy* proxy, int component); | |
140 void SetChannelImplFromTransport_w(TransportChannelProxy* proxy, | |
141 int component); | |
142 void ReplaceChannelImpl(TransportChannelProxy* proxy, | |
143 TransportChannelImpl* impl); | |
144 void ReplaceChannelImpl_w(TransportChannelProxy* proxy, | |
145 TransportChannelImpl* impl); | |
146 | |
147 rtc::Thread* const worker_thread_; | |
148 const std::string sid_; | |
149 const std::string content_name_; | |
150 rtc::scoped_refptr<TransportWrapper> transport_; | |
151 bool connecting_; | |
152 bool negotiated_; | |
153 ChannelMap channels_; | |
154 Candidates sent_candidates_; | |
155 Candidates unsent_candidates_; | |
156 bool candidates_allocated_; | |
157 bool local_description_set_; | |
158 bool remote_description_set_; | |
159 }; | |
160 | |
161 typedef std::map<std::string, TransportProxy*> TransportMap; | |
162 | 36 |
163 // Statistics for all the transports of this session. | 37 // Statistics for all the transports of this session. |
164 typedef std::map<std::string, TransportStats> TransportStatsMap; | 38 typedef std::map<std::string, TransportStats> TransportStatsMap; |
165 typedef std::map<std::string, std::string> ProxyTransportMap; | 39 typedef std::map<std::string, std::string> ProxyTransportMap; |
166 | 40 |
167 // TODO(pthatcher): Think of a better name for this. We already have | 41 // TODO(pthatcher): Think of a better name for this. We already have |
168 // a TransportStats in transport.h. Perhaps TransportsStats? | 42 // a TransportStats in transport.h. Perhaps TransportsStats? |
169 struct SessionStats { | 43 struct SessionStats { |
170 ProxyTransportMap proxy_to_transport; | 44 ProxyTransportMap proxy_to_transport; |
171 TransportStatsMap transport_stats; | 45 TransportStatsMap transport_stats; |
(...skipping 43 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
215 ERROR_TRANSPORT = 5, // transport error of some kind | 89 ERROR_TRANSPORT = 5, // transport error of some kind |
216 }; | 90 }; |
217 | 91 |
218 // Convert State to a readable string. | 92 // Convert State to a readable string. |
219 static std::string StateToString(State state); | 93 static std::string StateToString(State state); |
220 | 94 |
221 BaseSession(rtc::Thread* signaling_thread, | 95 BaseSession(rtc::Thread* signaling_thread, |
222 rtc::Thread* worker_thread, | 96 rtc::Thread* worker_thread, |
223 PortAllocator* port_allocator, | 97 PortAllocator* port_allocator, |
224 const std::string& sid, | 98 const std::string& sid, |
225 const std::string& content_type, | |
226 bool initiator); | 99 bool initiator); |
227 virtual ~BaseSession(); | 100 virtual ~BaseSession(); |
228 | 101 |
229 // These are const to allow them to be called from const methods. | 102 // These are const to allow them to be called from const methods. |
230 rtc::Thread* signaling_thread() const { return signaling_thread_; } | 103 rtc::Thread* signaling_thread() const { return signaling_thread_; } |
231 rtc::Thread* worker_thread() const { return worker_thread_; } | 104 rtc::Thread* worker_thread() const { return worker_thread_; } |
232 PortAllocator* port_allocator() const { return port_allocator_; } | 105 PortAllocator* port_allocator() const { return port_allocator_; } |
233 | 106 |
234 // The ID of this session. | 107 // The ID of this session. |
235 const std::string& id() const { return sid_; } | 108 const std::string& id() const { return sid_; } |
236 | 109 |
237 // TODO(juberti): This data is largely redundant, as it can now be obtained | |
238 // from local/remote_description(). Remove these functions and members. | |
239 // Returns the XML namespace identifying the type of this session. | |
240 const std::string& content_type() const { return content_type_; } | |
241 // Returns the XML namespace identifying the transport used for this session. | |
242 const std::string& transport_type() const { return transport_type_; } | |
243 | |
244 // Indicates whether we initiated this session. | |
245 bool initiator() const { return initiator_; } | |
246 | |
247 // Returns the application-level description given by our client. | 110 // Returns the application-level description given by our client. |
248 // If we are the recipient, this will be NULL until we send an accept. | 111 // If we are the recipient, this will be NULL until we send an accept. |
249 const SessionDescription* local_description() const; | 112 const SessionDescription* local_description() const; |
250 | 113 |
251 // Returns the application-level description given by the other client. | 114 // Returns the application-level description given by the other client. |
252 // If we are the initiator, this will be NULL until we receive an accept. | 115 // If we are the initiator, this will be NULL until we receive an accept. |
253 const SessionDescription* remote_description() const; | 116 const SessionDescription* remote_description() const; |
254 | 117 |
255 SessionDescription* remote_description(); | 118 SessionDescription* remote_description(); |
256 | 119 |
257 // Takes ownership of SessionDescription* | 120 // Takes ownership of SessionDescription* |
258 void set_local_description(const SessionDescription* sdesc); | 121 void set_local_description(const SessionDescription* sdesc); |
259 | 122 |
260 // Takes ownership of SessionDescription* | 123 // Takes ownership of SessionDescription* |
261 void set_remote_description(SessionDescription* sdesc); | 124 void set_remote_description(SessionDescription* sdesc); |
262 | 125 |
| 126 void set_initiator(bool initiator); |
| 127 bool initiator() const { return initiator_; } |
| 128 |
263 const SessionDescription* initiator_description() const; | 129 const SessionDescription* initiator_description() const; |
264 | 130 |
265 // Returns the current state of the session. See the enum above for details. | 131 // Returns the current state of the session. See the enum above for details. |
266 // Each time the state changes, we will fire this signal. | 132 // Each time the state changes, we will fire this signal. |
267 State state() const { return state_; } | 133 State state() const { return state_; } |
268 sigslot::signal2<BaseSession* , State> SignalState; | 134 sigslot::signal2<BaseSession* , State> SignalState; |
269 | 135 |
270 // Returns the last error in the session. See the enum above for details. | 136 // Returns the last error in the session. See the enum above for details. |
271 // Each time the an error occurs, we will fire this signal. | 137 // Each time the an error occurs, we will fire this signal. |
272 Error error() const { return error_; } | 138 Error error() const { return error_; } |
273 const std::string& error_desc() const { return error_desc_; } | 139 const std::string& error_desc() const { return error_desc_; } |
274 sigslot::signal2<BaseSession* , Error> SignalError; | 140 sigslot::signal2<BaseSession* , Error> SignalError; |
275 | 141 |
276 // Updates the state, signaling if necessary. | 142 // Updates the state, signaling if necessary. |
277 virtual void SetState(State state); | 143 virtual void SetState(State state); |
278 | 144 |
279 // Updates the error state, signaling if necessary. | 145 // Updates the error state, signaling if necessary. |
280 // TODO(ronghuawu): remove the SetError method that doesn't take |error_desc|. | 146 // TODO(ronghuawu): remove the SetError method that doesn't take |error_desc|. |
281 virtual void SetError(Error error, const std::string& error_desc); | 147 virtual void SetError(Error error, const std::string& error_desc); |
282 | 148 |
283 // Fired when the remote description is updated, with the updated | |
284 // contents. | |
285 sigslot::signal2<BaseSession* , const ContentInfos&> | |
286 SignalRemoteDescriptionUpdate; | |
287 | |
288 // Fired when SetState is called (regardless if there's a state change), which | |
289 // indicates the session description might have be updated. | |
290 sigslot::signal2<BaseSession*, ContentAction> SignalNewLocalDescription; | |
291 | |
292 // Fired when SetState is called (regardless if there's a state change), which | |
293 // indicates the session description might have be updated. | |
294 sigslot::signal2<BaseSession*, ContentAction> SignalNewRemoteDescription; | |
295 | |
296 // Returns the transport that has been negotiated or NULL if | |
297 // negotiation is still in progress. | |
298 virtual Transport* GetTransport(const std::string& content_name); | |
299 | |
300 // Creates a new channel with the given names. This method may be called | |
301 // immediately after creating the session. However, the actual | |
302 // implementation may not be fixed until transport negotiation completes. | |
303 // This will usually be called from the worker thread, but that | |
304 // shouldn't be an issue since the main thread will be blocked in | |
305 // Send when doing so. | |
306 virtual TransportChannel* CreateChannel(const std::string& content_name, | |
307 int component); | |
308 | |
309 // Returns the channel with the given names. | |
310 virtual TransportChannel* GetChannel(const std::string& content_name, | |
311 int component); | |
312 | |
313 // Destroys the channel with the given names. | |
314 // This will usually be called from the worker thread, but that | |
315 // shouldn't be an issue since the main thread will be blocked in | |
316 // Send when doing so. | |
317 virtual void DestroyChannel(const std::string& content_name, | |
318 int component); | |
319 | |
320 rtc::SSLIdentity* identity() { return identity_; } | |
321 | |
322 // Set the ice connection receiving timeout. | |
323 void SetIceConnectionReceivingTimeout(int timeout_ms); | 149 void SetIceConnectionReceivingTimeout(int timeout_ms); |
324 | 150 |
325 protected: | 151 protected: |
326 // Specifies the identity to use in this session. | |
327 bool SetIdentity(rtc::SSLIdentity* identity); | |
328 | |
329 bool SetSslMaxProtocolVersion(rtc::SSLProtocolVersion version); | |
330 | |
331 bool PushdownTransportDescription(ContentSource source, | 152 bool PushdownTransportDescription(ContentSource source, |
332 ContentAction action, | 153 ContentAction action, |
333 std::string* error_desc); | 154 std::string* error_desc); |
334 void set_initiator(bool initiator) { initiator_ = initiator; } | |
335 | |
336 const TransportMap& transport_proxies() const { return transports_; } | |
337 // Get a TransportProxy by content_name or transport. NULL if not found. | |
338 TransportProxy* GetTransportProxy(const std::string& content_name); | |
339 void DestroyTransportProxy(const std::string& content_name); | |
340 // TransportProxy is owned by session. Return proxy just for convenience. | |
341 TransportProxy* GetOrCreateTransportProxy(const std::string& content_name); | |
342 // Creates the actual transport object. Overridable for testing. | |
343 virtual Transport* CreateTransport(const std::string& content_name); | |
344 | |
345 void OnSignalingReady(); | |
346 void SpeculativelyConnectAllTransportChannels(); | |
347 // Helper method to provide remote candidates to the transport. | |
348 bool OnRemoteCandidates(const std::string& content_name, | |
349 const Candidates& candidates, | |
350 std::string* error); | |
351 | |
352 // This method will mux transport channels by content_name. | |
353 // First content is used for muxing. | |
354 bool MaybeEnableMuxingSupport(); | |
355 | |
356 // Called when a transport requests signaling. | |
357 virtual void OnTransportRequestSignaling(Transport* transport) { | |
358 } | |
359 | |
360 // Called when the first channel of a transport begins connecting. We use | |
361 // this to start a timer, to make sure that the connection completes in a | |
362 // reasonable amount of time. | |
363 virtual void OnTransportConnecting(Transport* transport) { | |
364 } | |
365 | |
366 // Called when a transport changes its writable state. We track this to make | |
367 // sure that the transport becomes writable within a reasonable amount of | |
368 // time. If this does not occur, we signal an error. | |
369 virtual void OnTransportWritable(Transport* transport) { | |
370 } | |
371 virtual void OnTransportReadable(Transport* transport) { | |
372 } | |
373 | |
374 virtual void OnTransportReceiving(Transport* transport) { | |
375 } | |
376 | |
377 // Called when a transport has found its steady-state connections. | |
378 virtual void OnTransportCompleted(Transport* transport) { | |
379 } | |
380 | |
381 // Called when a transport has failed permanently. | |
382 virtual void OnTransportFailed(Transport* transport) { | |
383 } | |
384 | |
385 // Called when a transport signals that it has new candidates. | |
386 virtual void OnTransportProxyCandidatesReady(TransportProxy* proxy, | |
387 const Candidates& candidates) { | |
388 } | |
389 | |
390 virtual void OnTransportRouteChange( | |
391 Transport* transport, | |
392 int component, | |
393 const cricket::Candidate& remote_candidate) { | |
394 } | |
395 | |
396 virtual void OnTransportCandidatesAllocationDone(Transport* transport); | |
397 | |
398 // Called when all transport channels allocated required candidates. | |
399 // This method should be used as an indication of candidates gathering process | |
400 // is completed and application can now send local candidates list to remote. | |
401 virtual void OnCandidatesAllocationDone() { | |
402 } | |
403 | |
404 // Handles the ice role change callback from Transport. This must be | |
405 // propagated to all the transports. | |
406 virtual void OnRoleConflict(); | |
407 | 155 |
408 // Handles messages posted to us. | 156 // Handles messages posted to us. |
409 virtual void OnMessage(rtc::Message *pmsg); | 157 virtual void OnMessage(rtc::Message *pmsg); |
410 | 158 |
| 159 TransportController* transport_controller() { |
| 160 return transport_controller_.get(); |
| 161 } |
| 162 |
411 protected: | 163 protected: |
412 bool IsCandidateAllocationDone() const; | |
413 | |
414 State state_; | 164 State state_; |
415 Error error_; | 165 Error error_; |
416 std::string error_desc_; | 166 std::string error_desc_; |
417 | 167 |
418 // This method will delete the Transport and TransportChannelImpls | |
419 // and replace those with the Transport object of the first | |
420 // MediaContent in bundle_group. | |
421 bool BundleContentGroup(const ContentGroup* bundle_group); | |
422 | |
423 private: | 168 private: |
424 // Helper methods to push local and remote transport descriptions. | 169 // Helper methods to push local and remote transport descriptions. |
425 bool PushdownLocalTransportDescription( | 170 bool PushdownLocalTransportDescription( |
426 const SessionDescription* sdesc, ContentAction action, | 171 const SessionDescription* sdesc, ContentAction action, |
427 std::string* error_desc); | 172 std::string* error_desc); |
428 bool PushdownRemoteTransportDescription( | 173 bool PushdownRemoteTransportDescription( |
429 const SessionDescription* sdesc, ContentAction action, | 174 const SessionDescription* sdesc, ContentAction action, |
430 std::string* error_desc); | 175 std::string* error_desc); |
431 | 176 |
432 void MaybeCandidateAllocationDone(); | |
433 | |
434 // Log session state. | 177 // Log session state. |
435 void LogState(State old_state, State new_state); | 178 void LogState(State old_state, State new_state); |
436 | 179 |
437 // Returns true and the TransportInfo of the given |content_name| | 180 // Returns true and the TransportInfo of the given |content_name| |
438 // from |description|. Returns false if it's not available. | 181 // from |description|. Returns false if it's not available. |
439 static bool GetTransportDescription(const SessionDescription* description, | 182 static bool GetTransportDescription(const SessionDescription* description, |
440 const std::string& content_name, | 183 const std::string& content_name, |
441 TransportDescription* info); | 184 TransportDescription* info); |
442 | 185 |
443 rtc::Thread* const signaling_thread_; | 186 rtc::Thread* const signaling_thread_; |
444 rtc::Thread* const worker_thread_; | 187 rtc::Thread* const worker_thread_; |
445 PortAllocator* const port_allocator_; | 188 PortAllocator* const port_allocator_; |
446 const std::string sid_; | 189 const std::string sid_; |
447 const std::string content_type_; | |
448 const std::string transport_type_; | |
449 bool initiator_; | 190 bool initiator_; |
450 rtc::SSLIdentity* identity_; | 191 rtc::scoped_ptr<TransportController> transport_controller_; |
451 rtc::SSLProtocolVersion ssl_max_version_; | |
452 rtc::scoped_ptr<const SessionDescription> local_description_; | 192 rtc::scoped_ptr<const SessionDescription> local_description_; |
453 rtc::scoped_ptr<SessionDescription> remote_description_; | 193 rtc::scoped_ptr<SessionDescription> remote_description_; |
454 uint64 ice_tiebreaker_; | |
455 // This flag will be set to true after the first role switch. This flag | |
456 // will enable us to stop any role switch during the call. | |
457 bool role_switch_; | |
458 TransportMap transports_; | |
459 | |
460 // Timeout value in milliseconds for which no ICE connection receives | |
461 // any packets. | |
462 int ice_receiving_timeout_; | |
463 }; | 194 }; |
464 | 195 |
465 } // namespace cricket | 196 } // namespace cricket |
466 | 197 |
467 #endif // WEBRTC_P2P_BASE_SESSION_H_ | 198 #endif // WEBRTC_P2P_BASE_SESSION_H_ |
OLD | NEW |