• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * libjingle
3  * Copyright 2004--2005, 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 #ifndef TALK_P2P_BASE_SESSIONMANAGER_H_
29 #define TALK_P2P_BASE_SESSIONMANAGER_H_
30 
31 #include <map>
32 #include <string>
33 #include <utility>
34 #include <vector>
35 
36 #include "talk/base/sigslot.h"
37 #include "talk/base/thread.h"
38 #include "talk/p2p/base/portallocator.h"
39 
40 namespace buzz {
41 class QName;
42 class XmlElement;
43 }
44 
45 namespace cricket {
46 
47 class Session;
48 class BaseSession;
49 class SessionClient;
50 
51 // SessionManager manages session instances
52 
53 class SessionManager : public sigslot::has_slots<> {
54  public:
55   SessionManager(PortAllocator *allocator,
56                  talk_base::Thread *worker_thread = NULL);
57   virtual ~SessionManager();
58 
port_allocator()59   PortAllocator *port_allocator() const { return allocator_; }
worker_thread()60   talk_base::Thread *worker_thread() const { return worker_thread_; }
signaling_thread()61   talk_base::Thread *signaling_thread() const { return signaling_thread_; }
62 
session_timeout()63   int session_timeout() const { return timeout_; }
set_session_timeout(int timeout)64   void set_session_timeout(int timeout) { timeout_ = timeout; }
65 
66   // Registers support for the given client.  If we receive an initiate
67   // describing a session of the given type, we will automatically create a
68   // Session object and notify this client.  The client may then accept or
69   // reject the session.
70   void AddClient(const std::string& content_type, SessionClient* client);
71   void RemoveClient(const std::string& content_type);
72   SessionClient* GetClient(const std::string& content_type);
73 
74   // Creates a new session.  The given name is the JID of the client on whose
75   // behalf we initiate the session.
76   Session *CreateSession(const std::string& local_name,
77                          const std::string& content_type);
78 
79   // Destroys the given session.
80   void DestroySession(Session *session);
81 
82   // Returns the session with the given ID or NULL if none exists.
83   Session *GetSession(const std::string& sid);
84 
85   // Terminates all of the sessions created by this manager.
86   void TerminateAll();
87 
88   // These are signaled whenever the set of existing sessions changes.
89   sigslot::signal2<Session *, bool> SignalSessionCreate;
90   sigslot::signal1<Session *> SignalSessionDestroy;
91 
92   // Determines whether the given stanza is intended for some session.
93   bool IsSessionMessage(const buzz::XmlElement* stanza);
94 
95   // Given a sid, initiator, and remote_name, this finds the matching Session
96   Session* FindSession(const std::string& sid,
97                        const std::string& remote_name);
98 
99   // Called when we receive a stanza for which IsSessionMessage is true.
100   void OnIncomingMessage(const buzz::XmlElement* stanza);
101 
102   // Called when we get a response to a message that we sent.
103   void OnIncomingResponse(const buzz::XmlElement* orig_stanza,
104                           const buzz::XmlElement* response_stanza);
105 
106   // Called if an attempted to send times out or an error is returned.  In the
107   // timeout case error_stanza will be NULL
108   void OnFailedSend(const buzz::XmlElement* orig_stanza,
109                     const buzz::XmlElement* error_stanza);
110 
111   // Signalled each time a session generates a signaling message to send.
112   // Also signalled on errors, but with a NULL session.
113   sigslot::signal2<SessionManager*,
114                    const buzz::XmlElement*> SignalOutgoingMessage;
115 
116   // Signaled before sessions try to send certain signaling messages.  The
117   // client should call OnSignalingReady once it is safe to send them.  These
118   // steps are taken so that we don't send signaling messages trying to
119   // re-establish the connectivity of a session when the client cannot send
120   // the messages (and would probably just drop them on the floor).
121   //
122   // Note: you can connect this directly to OnSignalingReady(), if a signalling
123   // check is not supported.
124   sigslot::signal0<> SignalRequestSignaling;
125   void OnSignalingReady();
126 
127  private:
128   typedef std::map<std::string, Session*> SessionMap;
129   typedef std::map<std::string, SessionClient*> ClientMap;
130 
131   PortAllocator *allocator_;
132   talk_base::Thread *signaling_thread_;
133   talk_base::Thread *worker_thread_;
134   int timeout_;
135   SessionMap session_map_;
136   ClientMap client_map_;
137 
138   // Helper function for CreateSession.  This is also invoked when we receive
139   // a message attempting to initiate a session with this client.
140   Session *CreateSession(const std::string& local_name,
141                          const std::string& initiator,
142                          const std::string& sid,
143                          const std::string& content_type,
144                          bool received_initiate);
145 
146   // Attempts to find a registered session type whose description appears as
147   // a child of the session element.  Such a child should be present indicating
148   // the application they hope to initiate.
149   std::string FindClient(const buzz::XmlElement* session);
150 
151   // Sends a message back to the other client indicating that we found an error
152   // in the stanza they sent.  name identifies the error, type is one of the
153   // standard XMPP types (cancel, continue, modify, auth, wait), and text is a
154   // description for debugging purposes.
155   void SendErrorMessage(const buzz::XmlElement* stanza,
156                         const buzz::QName& name,
157                         const std::string& type,
158                         const std::string& text,
159                         const buzz::XmlElement* extra_info);
160 
161   // Creates and returns an error message from the given components.  The
162   // caller is responsible for deleting this.
163   buzz::XmlElement* CreateErrorMessage(
164       const buzz::XmlElement* stanza,
165       const buzz::QName& name,
166       const std::string& type,
167       const std::string& text,
168       const buzz::XmlElement* extra_info);
169 
170   // Called each time a session requests signaling.
171   void OnRequestSignaling(Session* session);
172 
173   // Called each time a session has an outgoing message.
174   void OnOutgoingMessage(Session* session, const buzz::XmlElement* stanza);
175 
176   // Called each time a session has an error to send.
177   void OnErrorMessage(BaseSession* session,
178                       const buzz::XmlElement* stanza,
179                       const buzz::QName& name,
180                       const std::string& type,
181                       const std::string& text,
182                       const buzz::XmlElement* extra_info);
183 };
184 
185 }  // namespace cricket
186 
187 #endif  // TALK_P2P_BASE_SESSIONMANAGER_H_
188