OLD | NEW |
| (Empty) |
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 toy client, which connects to a specified port and sends QUIC | |
6 // request to that endpoint. | |
7 | |
8 #ifndef NET_TOOLS_QUIC_QUIC_CLIENT_H_ | |
9 #define NET_TOOLS_QUIC_QUIC_CLIENT_H_ | |
10 | |
11 #include <string> | |
12 | |
13 #include "base/basictypes.h" | |
14 #include "base/command_line.h" | |
15 #include "base/memory/scoped_ptr.h" | |
16 #include "base/strings/string_piece.h" | |
17 #include "net/base/ip_endpoint.h" | |
18 #include "net/quic/crypto/crypto_handshake.h" | |
19 #include "net/quic/quic_config.h" | |
20 #include "net/quic/quic_framer.h" | |
21 #include "net/quic/quic_packet_creator.h" | |
22 #include "net/tools/balsa/balsa_headers.h" | |
23 #include "net/tools/epoll_server/epoll_server.h" | |
24 #include "net/tools/quic/quic_client_session.h" | |
25 #include "net/tools/quic/quic_spdy_client_stream.h" | |
26 | |
27 namespace net { | |
28 | |
29 class ProofVerifier; | |
30 class QuicServerId; | |
31 | |
32 namespace tools { | |
33 | |
34 class QuicEpollConnectionHelper; | |
35 | |
36 namespace test { | |
37 class QuicClientPeer; | |
38 } // namespace test | |
39 | |
40 class QuicClient : public EpollCallbackInterface, | |
41 public QuicDataStream::Visitor { | |
42 public: | |
43 class ResponseListener { | |
44 public: | |
45 ResponseListener() {} | |
46 virtual ~ResponseListener() {} | |
47 virtual void OnCompleteResponse(QuicStreamId id, | |
48 const BalsaHeaders& response_headers, | |
49 const std::string& response_body) = 0; | |
50 }; | |
51 | |
52 // Create a quic client, which will have events managed by an externally owned | |
53 // EpollServer. | |
54 QuicClient(IPEndPoint server_address, | |
55 const QuicServerId& server_id, | |
56 const QuicVersionVector& supported_versions, | |
57 EpollServer* epoll_server); | |
58 QuicClient(IPEndPoint server_address, | |
59 const QuicServerId& server_id, | |
60 const QuicVersionVector& supported_versions, | |
61 const QuicConfig& config, | |
62 EpollServer* epoll_server); | |
63 | |
64 ~QuicClient() override; | |
65 | |
66 // Initializes the client to create a connection. Should be called exactly | |
67 // once before calling StartConnect or Connect. Returns true if the | |
68 // initialization succeeds, false otherwise. | |
69 bool Initialize(); | |
70 | |
71 // "Connect" to the QUIC server, including performing synchronous crypto | |
72 // handshake. | |
73 bool Connect(); | |
74 | |
75 // Start the crypto handshake. This can be done in place of the synchronous | |
76 // Connect(), but callers are responsible for making sure the crypto handshake | |
77 // completes. | |
78 void StartConnect(); | |
79 | |
80 // Returns true if the crypto handshake has yet to establish encryption. | |
81 // Returns false if encryption is active (even if the server hasn't confirmed | |
82 // the handshake) or if the connection has been closed. | |
83 bool EncryptionBeingEstablished(); | |
84 | |
85 // Disconnects from the QUIC server. | |
86 void Disconnect(); | |
87 | |
88 // Sends an HTTP request and does not wait for response before returning. | |
89 void SendRequest(const BalsaHeaders& headers, | |
90 base::StringPiece body, | |
91 bool fin); | |
92 | |
93 // Sends an HTTP request and waits for response before returning. | |
94 void SendRequestAndWaitForResponse(const BalsaHeaders& headers, | |
95 base::StringPiece body, | |
96 bool fin); | |
97 | |
98 // Sends a request simple GET for each URL in |args|, and then waits for | |
99 // each to complete. | |
100 void SendRequestsAndWaitForResponse(const | |
101 base::CommandLine::StringVector& args); | |
102 | |
103 // Returns a newly created QuicSpdyClientStream, owned by the | |
104 // QuicClient. | |
105 QuicSpdyClientStream* CreateReliableClientStream(); | |
106 | |
107 // Wait for events until the stream with the given ID is closed. | |
108 void WaitForStreamToClose(QuicStreamId id); | |
109 | |
110 // Wait for events until the handshake is confirmed. | |
111 void WaitForCryptoHandshakeConfirmed(); | |
112 | |
113 // Wait up to 50ms, and handle any events which occur. | |
114 // Returns true if there are any outstanding requests. | |
115 bool WaitForEvents(); | |
116 | |
117 // From EpollCallbackInterface | |
118 void OnRegistration(EpollServer* eps, int fd, int event_mask) override {} | |
119 void OnModification(int fd, int event_mask) override {} | |
120 void OnEvent(int fd, EpollEvent* event) override; | |
121 // |fd_| can be unregistered without the client being disconnected. This | |
122 // happens in b3m QuicProber where we unregister |fd_| to feed in events to | |
123 // the client from the SelectServer. | |
124 void OnUnregistration(int fd, bool replaced) override {} | |
125 void OnShutdown(EpollServer* eps, int fd) override {} | |
126 | |
127 // QuicDataStream::Visitor | |
128 void OnClose(QuicDataStream* stream) override; | |
129 | |
130 QuicClientSession* session() { return session_.get(); } | |
131 | |
132 bool connected() const; | |
133 bool goaway_received() const; | |
134 | |
135 void set_bind_to_address(IPAddressNumber address) { | |
136 bind_to_address_ = address; | |
137 } | |
138 | |
139 IPAddressNumber bind_to_address() const { return bind_to_address_; } | |
140 | |
141 void set_local_port(int local_port) { local_port_ = local_port; } | |
142 | |
143 const IPEndPoint& server_address() const { return server_address_; } | |
144 | |
145 const IPEndPoint& client_address() const { return client_address_; } | |
146 | |
147 int fd() { return fd_; } | |
148 | |
149 const QuicServerId& server_id() const { return server_id_; } | |
150 | |
151 // This should only be set before the initial Connect() | |
152 void set_server_id(const QuicServerId& server_id) { | |
153 server_id_ = server_id; | |
154 } | |
155 | |
156 void SetUserAgentID(const std::string& user_agent_id) { | |
157 crypto_config_.set_user_agent_id(user_agent_id); | |
158 } | |
159 | |
160 // SetProofVerifier sets the ProofVerifier that will be used to verify the | |
161 // server's certificate and takes ownership of |verifier|. | |
162 void SetProofVerifier(ProofVerifier* verifier) { | |
163 // TODO(rtenneti): We should set ProofVerifier in QuicClientSession. | |
164 crypto_config_.SetProofVerifier(verifier); | |
165 } | |
166 | |
167 // SetChannelIDSource sets a ChannelIDSource that will be called, when the | |
168 // server supports channel IDs, to obtain a channel ID for signing a message | |
169 // proving possession of the channel ID. This object takes ownership of | |
170 // |source|. | |
171 void SetChannelIDSource(ChannelIDSource* source) { | |
172 crypto_config_.SetChannelIDSource(source); | |
173 } | |
174 | |
175 void SetSupportedVersions(const QuicVersionVector& versions) { | |
176 supported_versions_ = versions; | |
177 } | |
178 | |
179 // Takes ownership of the listener. | |
180 void set_response_listener(ResponseListener* listener) { | |
181 response_listener_.reset(listener); | |
182 } | |
183 | |
184 QuicConfig* config() { return &config_; } | |
185 | |
186 void set_store_response(bool val) { store_response_ = val; } | |
187 | |
188 size_t latest_response_code() const; | |
189 const std::string& latest_response_headers() const; | |
190 const std::string& latest_response_body() const; | |
191 | |
192 protected: | |
193 virtual QuicConnectionId GenerateConnectionId(); | |
194 virtual QuicEpollConnectionHelper* CreateQuicConnectionHelper(); | |
195 virtual QuicPacketWriter* CreateQuicPacketWriter(); | |
196 | |
197 virtual int ReadPacket(char* buffer, | |
198 int buffer_len, | |
199 IPEndPoint* server_address, | |
200 IPAddressNumber* client_ip); | |
201 | |
202 EpollServer* epoll_server() { return epoll_server_; } | |
203 | |
204 private: | |
205 friend class net::tools::test::QuicClientPeer; | |
206 | |
207 // A packet writer factory that always returns the same writer | |
208 class DummyPacketWriterFactory : public QuicConnection::PacketWriterFactory { | |
209 public: | |
210 DummyPacketWriterFactory(QuicPacketWriter* writer); | |
211 ~DummyPacketWriterFactory() override; | |
212 | |
213 QuicPacketWriter* Create(QuicConnection* connection) const override; | |
214 | |
215 private: | |
216 QuicPacketWriter* writer_; | |
217 }; | |
218 | |
219 // Used during initialization: creates the UDP socket FD, sets socket options, | |
220 // and binds the socket to our address. | |
221 bool CreateUDPSocket(); | |
222 | |
223 // If the socket has been created, then unregister and close() the FD. | |
224 void CleanUpUDPSocket(); | |
225 | |
226 // Read a UDP packet and hand it to the framer. | |
227 bool ReadAndProcessPacket(); | |
228 | |
229 // Address of the server. | |
230 const IPEndPoint server_address_; | |
231 | |
232 // |server_id_| is a tuple (hostname, port, is_https) of the server. | |
233 QuicServerId server_id_; | |
234 | |
235 // config_ and crypto_config_ contain configuration and cached state about | |
236 // servers. | |
237 QuicConfig config_; | |
238 QuicCryptoClientConfig crypto_config_; | |
239 | |
240 // Address of the client if the client is connected to the server. | |
241 IPEndPoint client_address_; | |
242 | |
243 // If initialized, the address to bind to. | |
244 IPAddressNumber bind_to_address_; | |
245 // Local port to bind to. Initialize to 0. | |
246 int local_port_; | |
247 | |
248 // Writer used to actually send packets to the wire. Needs to outlive | |
249 // |session_|. | |
250 scoped_ptr<QuicPacketWriter> writer_; | |
251 | |
252 // Session which manages streams. | |
253 scoped_ptr<QuicClientSession> session_; | |
254 // Listens for events on the client socket. | |
255 EpollServer* epoll_server_; | |
256 // UDP socket. | |
257 int fd_; | |
258 | |
259 // Helper to be used by created connections. | |
260 scoped_ptr<QuicEpollConnectionHelper> helper_; | |
261 | |
262 // Listens for full responses. | |
263 scoped_ptr<ResponseListener> response_listener_; | |
264 | |
265 // Tracks if the client is initialized to connect. | |
266 bool initialized_; | |
267 | |
268 // If overflow_supported_ is true, this will be the number of packets dropped | |
269 // during the lifetime of the server. | |
270 QuicPacketCount packets_dropped_; | |
271 | |
272 // True if the kernel supports SO_RXQ_OVFL, the number of packets dropped | |
273 // because the socket would otherwise overflow. | |
274 bool overflow_supported_; | |
275 | |
276 // This vector contains QUIC versions which we currently support. | |
277 // This should be ordered such that the highest supported version is the first | |
278 // element, with subsequent elements in descending order (versions can be | |
279 // skipped as necessary). We will always pick supported_versions_[0] as the | |
280 // initial version to use. | |
281 QuicVersionVector supported_versions_; | |
282 | |
283 // If true, store the latest response code, headers, and body. | |
284 bool store_response_; | |
285 // HTTP response code from most recent response. | |
286 size_t latest_response_code_; | |
287 // HTTP headers from most recent response. | |
288 std::string latest_response_headers_; | |
289 // Body of most recent response. | |
290 std::string latest_response_body_; | |
291 | |
292 DISALLOW_COPY_AND_ASSIGN(QuicClient); | |
293 }; | |
294 | |
295 } // namespace tools | |
296 } // namespace net | |
297 | |
298 #endif // NET_TOOLS_QUIC_QUIC_CLIENT_H_ | |
OLD | NEW |