Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(34)

Side by Side Diff: net/tools/quic/quic_simple_client.cc

Issue 2368183003: Move QuicClient::ClientQuicDataToResend from QuicClient to QuicClientBase. (Closed)
Patch Set: Rebase Created 4 years, 2 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
« no previous file with comments | « net/tools/quic/quic_simple_client.h ('k') | no next file » | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. 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 2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file. 3 // found in the LICENSE file.
4 4
5 #include "net/tools/quic/quic_simple_client.h" 5 #include "net/tools/quic/quic_simple_client.h"
6 6
7 #include <utility> 7 #include <utility>
8 8
9 #include "base/logging.h" 9 #include "base/logging.h"
10 #include "base/run_loop.h" 10 #include "base/run_loop.h"
(...skipping 14 matching lines...) Expand all
25 #include "net/spdy/spdy_header_block.h" 25 #include "net/spdy/spdy_header_block.h"
26 #include "net/spdy/spdy_http_utils.h" 26 #include "net/spdy/spdy_http_utils.h"
27 #include "net/udp/udp_client_socket.h" 27 #include "net/udp/udp_client_socket.h"
28 28
29 using std::string; 29 using std::string;
30 using std::vector; 30 using std::vector;
31 using base::StringPiece; 31 using base::StringPiece;
32 32
33 namespace net { 33 namespace net {
34 34
35 void QuicSimpleClient::ClientQuicDataToResend::Resend() {
36 client_->SendRequest(*headers_, body_, fin_);
37 headers_ = nullptr;
38 }
39
40 QuicSimpleClient::QuicSimpleClient( 35 QuicSimpleClient::QuicSimpleClient(
41 IPEndPoint server_address, 36 IPEndPoint server_address,
42 const QuicServerId& server_id, 37 const QuicServerId& server_id,
43 const QuicVersionVector& supported_versions, 38 const QuicVersionVector& supported_versions,
44 std::unique_ptr<ProofVerifier> proof_verifier) 39 std::unique_ptr<ProofVerifier> proof_verifier)
45 : QuicClientBase(server_id, 40 : QuicClientBase(server_id,
46 supported_versions, 41 supported_versions,
47 QuicConfig(), 42 QuicConfig(),
48 CreateQuicConnectionHelper(), 43 CreateQuicConnectionHelper(),
49 CreateQuicAlarmFactory(), 44 CreateQuicAlarmFactory(),
(...skipping 104 matching lines...) Expand 10 before | Expand all | Expand 10 after
154 bool QuicSimpleClient::Connect() { 149 bool QuicSimpleClient::Connect() {
155 // Attempt multiple connects until the maximum number of client hellos have 150 // Attempt multiple connects until the maximum number of client hellos have
156 // been sent. 151 // been sent.
157 while (!connected() && 152 while (!connected() &&
158 GetNumSentClientHellos() <= QuicCryptoClientStream::kMaxClientHellos) { 153 GetNumSentClientHellos() <= QuicCryptoClientStream::kMaxClientHellos) {
159 StartConnect(); 154 StartConnect();
160 StartPacketReaderIfNotStarted(); 155 StartPacketReaderIfNotStarted();
161 while (EncryptionBeingEstablished()) { 156 while (EncryptionBeingEstablished()) {
162 WaitForEvents(); 157 WaitForEvents();
163 } 158 }
164 if (FLAGS_enable_quic_stateless_reject_support && connected() && 159 if (FLAGS_enable_quic_stateless_reject_support && connected()) {
165 !data_to_resend_on_connect_.empty()) { 160 // Resend any previously queued data.
166 // A connection has been established and there was previously queued data 161 ResendSavedData();
167 // to resend. Resend it and empty the queue.
168 std::vector<std::unique_ptr<QuicDataToResend>> old_data;
169 old_data.swap(data_to_resend_on_connect_);
170 for (const auto& data : old_data) {
171 data->Resend();
172 }
173 data_to_resend_on_connect_.clear();
174 } 162 }
175 if (session() != nullptr && 163 if (session() != nullptr &&
176 session()->error() != QUIC_CRYPTO_HANDSHAKE_STATELESS_REJECT) { 164 session()->error() != QUIC_CRYPTO_HANDSHAKE_STATELESS_REJECT) {
177 // We've successfully created a session but we're not connected, and there 165 // We've successfully created a session but we're not connected, and there
178 // is no stateless reject to recover from. Give up trying. 166 // is no stateless reject to recover from. Give up trying.
179 break; 167 break;
180 } 168 }
181 } 169 }
182 if (!connected() && 170 if (!connected() &&
183 GetNumSentClientHellos() > QuicCryptoClientStream::kMaxClientHellos && 171 GetNumSentClientHellos() > QuicCryptoClientStream::kMaxClientHellos &&
184 session() != nullptr && 172 session() != nullptr &&
185 session()->error() == QUIC_CRYPTO_HANDSHAKE_STATELESS_REJECT) { 173 session()->error() == QUIC_CRYPTO_HANDSHAKE_STATELESS_REJECT) {
186 // The overall connection failed due too many stateless rejects. 174 // The overall connection failed due too many stateless rejects.
187 set_connection_error(QUIC_CRYPTO_TOO_MANY_REJECTS); 175 set_connection_error(QUIC_CRYPTO_TOO_MANY_REJECTS);
188 } 176 }
189 return session()->connection()->connected(); 177 return session()->connection()->connected();
190 } 178 }
191 179
192 void QuicSimpleClient::StartConnect() { 180 void QuicSimpleClient::StartConnect() {
193 DCHECK(initialized_); 181 DCHECK(initialized_);
194 DCHECK(!connected()); 182 DCHECK(!connected());
195 183
196 set_writer(CreateQuicPacketWriter()); 184 set_writer(CreateQuicPacketWriter());
197 185
198 if (connected_or_attempting_connect()) { 186 if (connected_or_attempting_connect()) {
199 // If the last error was not a stateless reject, then the queued up data 187 // If the last error was not a stateless reject, then the queued up data
200 // does not need to be resent. 188 // does not need to be resent.
201 if (session()->error() != QUIC_CRYPTO_HANDSHAKE_STATELESS_REJECT) { 189 if (session()->error() != QUIC_CRYPTO_HANDSHAKE_STATELESS_REJECT) {
202 data_to_resend_on_connect_.clear(); 190 ClearDataToResend();
203 } 191 }
204 // Before we destroy the last session and create a new one, gather its stats 192 // Before we destroy the last session and create a new one, gather its stats
205 // and update the stats for the overall connection. 193 // and update the stats for the overall connection.
206 UpdateStats(); 194 UpdateStats();
207 } 195 }
208 196
209 CreateQuicClientSession(new QuicConnection( 197 CreateQuicClientSession(new QuicConnection(
210 GetNextConnectionId(), server_address_, helper(), alarm_factory(), 198 GetNextConnectionId(), server_address_, helper(), alarm_factory(),
211 writer(), 199 writer(),
212 /* owns_writer= */ false, Perspective::IS_CLIENT, supported_versions())); 200 /* owns_writer= */ false, Perspective::IS_CLIENT, supported_versions()));
213 201
214 session()->Initialize(); 202 session()->Initialize();
215 session()->CryptoConnect(); 203 session()->CryptoConnect();
216 set_connected_or_attempting_connect(true); 204 set_connected_or_attempting_connect(true);
217 } 205 }
218 206
219 void QuicSimpleClient::Disconnect() { 207 void QuicSimpleClient::Disconnect() {
220 DCHECK(initialized_); 208 DCHECK(initialized_);
221 209
222 if (connected()) { 210 if (connected()) {
223 session()->connection()->CloseConnection( 211 session()->connection()->CloseConnection(
224 QUIC_PEER_GOING_AWAY, "Client disconnecting", 212 QUIC_PEER_GOING_AWAY, "Client disconnecting",
225 ConnectionCloseBehavior::SEND_CONNECTION_CLOSE_PACKET); 213 ConnectionCloseBehavior::SEND_CONNECTION_CLOSE_PACKET);
226 } 214 }
227 data_to_resend_on_connect_.clear(); 215 ClearDataToResend();
228 216
229 reset_writer(); 217 reset_writer();
230 packet_reader_.reset(); 218 packet_reader_.reset();
231 packet_reader_started_ = false; 219 packet_reader_started_ = false;
232 220
233 initialized_ = false; 221 initialized_ = false;
234 } 222 }
235 223
236 void QuicSimpleClient::SendRequest(const SpdyHeaderBlock& headers, 224 void QuicSimpleClient::SendRequest(const SpdyHeaderBlock& headers,
237 StringPiece body, 225 StringPiece body,
238 bool fin) { 226 bool fin) {
227 QuicClientPushPromiseIndex::TryHandle* handle;
228 QuicAsyncStatus rv = push_promise_index()->Try(headers, this, &handle);
229 if (rv == QUIC_SUCCESS)
230 return;
231
232 if (rv == QUIC_PENDING) {
233 // May need to retry request if asynchronous rendezvous fails.
234 AddPromiseDataToResend(headers, body, fin);
235 return;
236 }
237
239 QuicSpdyClientStream* stream = CreateReliableClientStream(); 238 QuicSpdyClientStream* stream = CreateReliableClientStream();
240 if (stream == nullptr) { 239 if (stream == nullptr) {
241 LOG(DFATAL) << "stream creation failed!"; 240 QUIC_BUG << "stream creation failed!";
242 return; 241 return;
243 } 242 }
244 stream->set_visitor(this); 243 stream->set_visitor(this);
245 stream->SendRequest(headers.Clone(), body, fin); 244 stream->SendRequest(headers.Clone(), body, fin);
246 if (FLAGS_enable_quic_stateless_reject_support) { 245 // Record this in case we need to resend.
247 // Record this in case we need to resend. 246 MaybeAddDataToResend(headers, body, fin);
248 std::unique_ptr<SpdyHeaderBlock> new_headers(
249 new SpdyHeaderBlock(headers.Clone()));
250 auto data_to_resend =
251 new ClientQuicDataToResend(std::move(new_headers), body, fin, this);
252 MaybeAddQuicDataToResend(std::unique_ptr<QuicDataToResend>(data_to_resend));
253 }
254 }
255
256 void QuicSimpleClient::MaybeAddQuicDataToResend(
257 std::unique_ptr<QuicDataToResend> data_to_resend) {
258 DCHECK(FLAGS_enable_quic_stateless_reject_support);
259 if (session()->IsCryptoHandshakeConfirmed()) {
260 // The handshake is confirmed. No need to continue saving requests to
261 // resend.
262 data_to_resend_on_connect_.clear();
263 return;
264 }
265
266 // The handshake is not confirmed. Push the data onto the queue of data to
267 // resend if statelessly rejected.
268 data_to_resend_on_connect_.push_back(std::move(data_to_resend));
269 } 247 }
270 248
271 void QuicSimpleClient::SendRequestAndWaitForResponse( 249 void QuicSimpleClient::SendRequestAndWaitForResponse(
272 const SpdyHeaderBlock& headers, 250 const SpdyHeaderBlock& headers,
273 base::StringPiece body, 251 base::StringPiece body,
274 bool fin) { 252 bool fin) {
275 SendRequest(headers, body, fin); 253 SendRequest(headers, body, fin);
276 while (WaitForEvents()) { 254 while (WaitForEvents()) {
277 } 255 }
278 } 256 }
(...skipping 113 matching lines...) Expand 10 before | Expand all | Expand 10 after
392 session()->connection()->ProcessUdpPacket(local_address, peer_address, 370 session()->connection()->ProcessUdpPacket(local_address, peer_address,
393 packet); 371 packet);
394 if (!session()->connection()->connected()) { 372 if (!session()->connection()->connected()) {
395 return false; 373 return false;
396 } 374 }
397 375
398 return true; 376 return true;
399 } 377 }
400 378
401 } // namespace net 379 } // namespace net
OLDNEW
« no previous file with comments | « net/tools/quic/quic_simple_client.h ('k') | no next file » | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698