1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. 2 // Use of this source code is governed by a BSD-style license that can be 3 // found in the LICENSE file. 4 // 5 // A server side dispatcher which dispatches a given client's data to their 6 // stream. 7 8 #ifndef NET_TOOLS_QUIC_QUIC_DISPATCHER_H_ 9 #define NET_TOOLS_QUIC_QUIC_DISPATCHER_H_ 10 11 #include <list> 12 13 #include "base/containers/hash_tables.h" 14 #include "base/memory/scoped_ptr.h" 15 #include "net/base/ip_endpoint.h" 16 #include "net/base/linked_hash_map.h" 17 #include "net/quic/quic_blocked_writer_interface.h" 18 #include "net/quic/quic_packet_writer.h" 19 #include "net/quic/quic_protocol.h" 20 #include "net/tools/epoll_server/epoll_server.h" 21 #include "net/tools/quic/quic_server_session.h" 22 #include "net/tools/quic/quic_time_wait_list_manager.h" 23 24 #if defined(COMPILER_GCC) 25 namespace BASE_HASH_NAMESPACE { 26 template<> 27 struct hash<net::QuicBlockedWriterInterface*> { 28 std::size_t operator()( 29 const net::QuicBlockedWriterInterface* ptr) const { 30 return hash<size_t>()(reinterpret_cast<size_t>(ptr)); 31 } 32 }; 33 } 34 #endif 35 36 namespace net { 37 38 class EpollServer; 39 class QuicConfig; 40 class QuicCryptoServerConfig; 41 class QuicSession; 42 43 namespace tools { 44 45 namespace test { 46 class QuicDispatcherPeer; 47 } // namespace test 48 49 class DeleteSessionsAlarm; 50 class QuicEpollConnectionHelper; 51 52 class QuicDispatcher : public QuicPacketWriter, public QuicSessionOwner { 53 public: 54 // Ideally we'd have a linked_hash_set: the boolean is unused. 55 typedef linked_hash_map<QuicBlockedWriterInterface*, bool> WriteBlockedList; 56 57 // Due to the way delete_sessions_closure_ is registered, the Dispatcher 58 // must live until epoll_server Shutdown. |supported_versions| specifies the 59 // list of supported QUIC versions. 60 QuicDispatcher(const QuicConfig& config, 61 const QuicCryptoServerConfig& crypto_config, 62 const QuicVersionVector& supported_versions, 63 int fd, 64 EpollServer* epoll_server); 65 virtual ~QuicDispatcher(); 66 67 // QuicPacketWriter 68 virtual WriteResult WritePacket( 69 const char* buffer, size_t buf_len, 70 const IPAddressNumber& self_address, 71 const IPEndPoint& peer_address, 72 QuicBlockedWriterInterface* writer) OVERRIDE; 73 virtual bool IsWriteBlockedDataBuffered() const OVERRIDE; 74 75 // Process the incoming packet by creating a new session, passing it to 76 // an existing session, or passing it to the TimeWaitListManager. 77 virtual void ProcessPacket(const IPEndPoint& server_address, 78 const IPEndPoint& client_address, 79 QuicGuid guid, 80 bool has_version_flag, 81 const QuicEncryptedPacket& packet); 82 83 // Called when the underyling connection becomes writable to allow 84 // queued writes to happen. 85 // 86 // Returns true if more writes are possible, false otherwise. 87 virtual bool OnCanWrite(); 88 89 // Sends ConnectionClose frames to all connected clients. 90 void Shutdown(); 91 92 // Ensure that the closed connection is cleaned up asynchronously. 93 virtual void OnConnectionClosed(QuicGuid guid, QuicErrorCode error) OVERRIDE; 94 95 // Sets the fd and creates a default packet writer with that fd. 96 void set_fd(int fd); 97 98 typedef base::hash_map<QuicGuid, QuicSession*> SessionMap; 99 100 virtual QuicSession* CreateQuicSession( 101 QuicGuid guid, 102 const IPEndPoint& server_address, 103 const IPEndPoint& client_address); 104 105 // Deletes all sessions on the closed session list and clears the list. 106 void DeleteSessions(); 107 108 const SessionMap& session_map() const { return session_map_; } 109 110 // Uses the specified |writer| instead of QuicSocketUtils and takes ownership 111 // of writer. 112 void UseWriter(QuicPacketWriter* writer); 113 114 WriteBlockedList* write_blocked_list() { return &write_blocked_list_; } 115 116 protected: 117 const QuicConfig& config_; 118 const QuicCryptoServerConfig& crypto_config_; 119 120 QuicTimeWaitListManager* time_wait_list_manager() { 121 return time_wait_list_manager_.get(); 122 } 123 124 QuicEpollConnectionHelper* helper() { return helper_.get(); } 125 EpollServer* epoll_server() { return epoll_server_; } 126 127 const QuicVersionVector& supported_versions() const { 128 return supported_versions_; 129 } 130 131 private: 132 friend class net::tools::test::QuicDispatcherPeer; 133 134 // Removes the session from the session map and write blocked list, and 135 // adds the GUID to the time-wait list. 136 void CleanUpSession(SessionMap::iterator it); 137 138 // The list of connections waiting to write. 139 WriteBlockedList write_blocked_list_; 140 141 SessionMap session_map_; 142 143 // Entity that manages guids in time wait state. 144 scoped_ptr<QuicTimeWaitListManager> time_wait_list_manager_; 145 146 // An alarm which deletes closed sessions. 147 scoped_ptr<DeleteSessionsAlarm> delete_sessions_alarm_; 148 149 // The list of closed but not-yet-deleted sessions. 150 std::list<QuicSession*> closed_session_list_; 151 152 EpollServer* epoll_server_; // Owned by the server. 153 154 // The connection for client-server communication 155 int fd_; 156 157 // True if the session is write blocked due to the socket returning EAGAIN. 158 // False if we have gotten a call to OnCanWrite after the last failed write. 159 bool write_blocked_; 160 161 // The helper used for all connections. 162 scoped_ptr<QuicEpollConnectionHelper> helper_; 163 164 // The writer to write to the socket with. 165 scoped_ptr<QuicPacketWriter> writer_; 166 167 // This vector contains QUIC versions which we currently support. 168 // This should be ordered such that the highest supported version is the first 169 // element, with subsequent elements in descending order (versions can be 170 // skipped as necessary). 171 const QuicVersionVector supported_versions_; 172 173 DISALLOW_COPY_AND_ASSIGN(QuicDispatcher); 174 }; 175 176 } // namespace tools 177 } // namespace net 178 179 #endif // NET_TOOLS_QUIC_QUIC_DISPATCHER_H_ 180