| // Copyright (c) 2012 The Chromium Authors. All rights reserved. |
| // Use of this source code is governed by a BSD-style license that can be |
| // found in the LICENSE file. |
| |
| #ifndef REMOTING_PROTOCOL_JINGLE_SESSION_H_ |
| #define REMOTING_PROTOCOL_JINGLE_SESSION_H_ |
| |
| #include <string> |
| #include <vector> |
| |
| #include "base/macros.h" |
| #include "base/memory/ref_counted.h" |
| #include "base/rand_util.h" |
| #include "base/strings/string_number_conversions.h" |
| #include "base/threading/thread_checker.h" |
| #include "base/timer/timer.h" |
| #include "crypto/rsa_private_key.h" |
| #include "net/base/completion_callback.h" |
| #include "remoting/protocol/authenticator.h" |
| #include "remoting/protocol/datagram_channel_factory.h" |
| #include "remoting/protocol/jingle_messages.h" |
| #include "remoting/protocol/session.h" |
| #include "remoting/protocol/session_config.h" |
| #include "remoting/signaling/iq_sender.h" |
| |
| namespace remoting { |
| namespace protocol { |
| |
| class JingleSessionManager; |
| class Transport; |
| |
| // JingleSessionManager and JingleSession implement the subset of the |
| // Jingle protocol used in Chromoting. Instances of this class are |
| // created by the JingleSessionManager. |
| class JingleSession : public Session { |
| public: |
| ~JingleSession() override; |
| |
| // Session interface. |
| void SetEventHandler(Session::EventHandler* event_handler) override; |
| ErrorCode error() override; |
| const std::string& jid() override; |
| const SessionConfig& config() override; |
| void SetTransport(Transport* transport) override; |
| void Close(protocol::ErrorCode error) override; |
| void AddPlugin(SessionPlugin* plugin) override; |
| |
| private: |
| friend class JingleSessionManager; |
| |
| typedef base::Callback<void(JingleMessageReply::ErrorType)> ReplyCallback; |
| |
| explicit JingleSession(JingleSessionManager* session_manager); |
| |
| // Start connection by sending session-initiate message. |
| void StartConnection(const SignalingAddress& peer_address, |
| std::unique_ptr<Authenticator> authenticator); |
| |
| // Called by JingleSessionManager for incoming connections. |
| void InitializeIncomingConnection( |
| const std::string& message_id, |
| const JingleMessage& initiate_message, |
| std::unique_ptr<Authenticator> authenticator); |
| void AcceptIncomingConnection(const JingleMessage& initiate_message); |
| |
| // Callback for Transport interface to send transport-info messages. |
| void SendTransportInfo(std::unique_ptr<buzz::XmlElement> transport_info); |
| |
| // Sends |message| to the peer. The session is closed if the send fails or no |
| // response is received within a reasonable time. All other responses are |
| // ignored. |
| void SendMessage(std::unique_ptr<JingleMessage> message); |
| |
| // Iq response handler. |
| void OnMessageResponse(JingleMessage::ActionType request_type, |
| IqRequest* request, |
| const buzz::XmlElement* response); |
| |
| // Response handler for transport-info responses. Transport-info timeouts are |
| // ignored and don't terminate connection. |
| void OnTransportInfoResponse(IqRequest* request, |
| const buzz::XmlElement* response); |
| |
| // Called by JingleSessionManager on incoming |message|. Must call |
| // |reply_callback| to send reply message before sending any other |
| // messages. |
| void OnIncomingMessage(const std::string& id, |
| std::unique_ptr<JingleMessage> message, |
| const ReplyCallback& reply_callback); |
| |
| // Called by OnIncomingMessage() to process the incoming Jingle messages |
| // in the same order that they are sent. |
| void ProcessIncomingMessage(std::unique_ptr<JingleMessage> message, |
| const ReplyCallback& reply_callback); |
| |
| // Message handlers for incoming messages. |
| void OnAccept(std::unique_ptr<JingleMessage> message, |
| const ReplyCallback& reply_callback); |
| void OnSessionInfo(std::unique_ptr<JingleMessage> message, |
| const ReplyCallback& reply_callback); |
| void OnTransportInfo(std::unique_ptr<JingleMessage> message, |
| const ReplyCallback& reply_callback); |
| void OnTerminate(std::unique_ptr<JingleMessage> message, |
| const ReplyCallback& reply_callback); |
| |
| // Called from OnAccept() to initialize session config. |
| bool InitializeConfigFromDescription(const ContentDescription* description); |
| |
| // Called after the initial incoming authenticator message is processed. |
| void ContinueAcceptIncomingConnection(); |
| |
| // Called after subsequent authenticator messages are processed. |
| void ProcessAuthenticationStep(); |
| |
| // Called when authentication is finished. |
| void OnAuthenticated(); |
| |
| // Sets |state_| to |new_state| and calls state change callback. |
| void SetState(State new_state); |
| |
| // Returns true if the state of the session is not CLOSED or FAILED |
| bool is_session_active(); |
| |
| // Executes all plugins against incoming JingleMessage. |
| void ProcessIncomingPluginMessage(const JingleMessage& message); |
| |
| // Executes all plugins against outgoing JingleMessage. |
| void AddPluginAttachments(JingleMessage* message); |
| |
| // Sends session-initiate message. |
| void SendSessionInitiateMessage(); |
| |
| // Returns the value of the ID attribute of the next outgoing set IQ with the |
| // sequence ID encoded. |
| std::string GetNextOutgoingId(); |
| |
| base::ThreadChecker thread_checker_; |
| |
| JingleSessionManager* session_manager_; |
| SignalingAddress peer_address_; |
| Session::EventHandler* event_handler_; |
| |
| std::string session_id_; |
| State state_; |
| ErrorCode error_; |
| |
| std::unique_ptr<SessionConfig> config_; |
| |
| std::unique_ptr<Authenticator> authenticator_; |
| |
| Transport* transport_ = nullptr; |
| |
| // Pending Iq requests. Used for all messages except transport-info. |
| std::vector<std::unique_ptr<IqRequest>> pending_requests_; |
| |
| // Pending transport-info requests. |
| std::vector<std::unique_ptr<IqRequest>> transport_info_requests_; |
| |
| struct PendingMessage { |
| PendingMessage(); |
| PendingMessage(PendingMessage&& moved); |
| PendingMessage(std::unique_ptr<JingleMessage> message, |
| const ReplyCallback& reply_callback); |
| ~PendingMessage(); |
| PendingMessage& operator=(PendingMessage&& moved); |
| std::unique_ptr<JingleMessage> message; |
| ReplyCallback reply_callback; |
| }; |
| |
| // A message queue to guarantee the incoming messages are processed in order. |
| class OrderedMessageQueue; |
| std::unique_ptr<OrderedMessageQueue> message_queue_; |
| |
| // This prefix is necessary to disambiguate between the ID's sent from the |
| // client and the ID's sent from the host. |
| std::string outgoing_id_prefix_ = base::NumberToString(base::RandUint64()); |
| int next_outgoing_id_ = 0; |
| |
| // Transport info messages that are received while the session is being |
| // authenticated. |
| std::vector<PendingMessage> pending_transport_info_; |
| |
| // The SessionPlugins attached to this session. |
| std::vector<SessionPlugin*> plugins_; |
| |
| base::WeakPtrFactory<JingleSession> weak_factory_; |
| |
| DISALLOW_COPY_AND_ASSIGN(JingleSession); |
| }; |
| |
| } // namespace protocol |
| } // namespace remoting |
| |
| #endif // REMOTING_PROTOCOL_JINGLE_SESSION_H_ |