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

Side by Side Diff: net/quic/quartc/quartc_session.cc

Issue 2324833004: Define Stable API for WebRTC/Quartc (Closed)
Patch Set: Fix the issues when testing with WebRTC. 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
OLDNEW
(Empty)
1 // Copyright (c) 2016 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 #include "net/quic/quartc/quartc_session.h"
6
7 #include "base/rand_util.h"
8
9 namespace {
10
11 // Default priority for incoming QUIC streams.
12 // TODO(zhihuang): Determine if this value is correct.
13 static const net::SpdyPriority kDefaultPriority = 3;
14
15 // Arbitrary server port number for net::QuicCryptoClientConfig.
16 const int kQuicServerPort = 0;
17
18 // Length of HKDF input keying material, equal to its number of bytes.
19 // https://tools.ietf.org/html/rfc5869#section-2.2.
20 // TODO(zhihuang): Verify that input keying material length is correct.
21 const size_t kInputKeyingMaterialLength = 32;
22
23 // Used by QuicCryptoServerConfig to provide dummy proof credentials.
24 // TODO(zhihuang): Remove when secure P2P QUIC handshake is possible.
25 class DummyProofSource : public net::ProofSource {
26 public:
27 DummyProofSource() {}
28 ~DummyProofSource() override {}
29
30 // ProofSource override.
31 bool GetProof(const net::IPAddress& server_ip,
32 const std::string& hostname,
33 const std::string& server_config,
34 net::QuicVersion quic_version,
35 base::StringPiece chlo_hash,
36 scoped_refptr<net::ProofSource::Chain>* out_chain,
37 std::string* out_signature,
38 std::string* out_leaf_cert_sct) override {
39 std::vector<std::string> certs;
40 certs.push_back("Dummy cert");
41 *out_chain = new ProofSource::Chain(certs);
42 *out_signature = "Dummy signature";
43 *out_leaf_cert_sct = "Dummy timestamp";
44 return true;
45 }
46
47 void GetProof(const net::IPAddress& server_ip,
48 const std::string& hostname,
49 const std::string& server_config,
50 net::QuicVersion quic_version,
51 base::StringPiece chlo_hash,
52 std::unique_ptr<Callback> callback) override {}
53 };
54
55 // Used by QuicCryptoClientConfig to ignore the peer's credentials
56 // and establish an insecure QUIC connection.
57 // TODO(zhihuang): Remove when secure P2P QUIC handshake is possible.
58 class InsecureProofVerifier : public net::ProofVerifier {
59 public:
60 InsecureProofVerifier() {}
61 ~InsecureProofVerifier() override {}
62
63 // ProofVerifier override.
64 net::QuicAsyncStatus VerifyProof(
65 const std::string& hostname,
66 const uint16_t port,
67 const std::string& server_config,
68 net::QuicVersion quic_version,
69 base::StringPiece chlo_hash,
70 const std::vector<std::string>& certs,
71 const std::string& cert_sct,
72 const std::string& signature,
73 const net::ProofVerifyContext* context,
74 std::string* error_details,
75 std::unique_ptr<net::ProofVerifyDetails>* verify_details,
76 std::unique_ptr<net::ProofVerifierCallback> callback) override {
77 return net::QUIC_SUCCESS;
78 }
79
80 net::QuicAsyncStatus VerifyCertChain(
81 const std::string& hostname,
82 const std::vector<std::string>& certs,
83 const net::ProofVerifyContext* context,
84 std::string* error_details,
85 std::unique_ptr<net::ProofVerifyDetails>* details,
86 std::unique_ptr<net::ProofVerifierCallback> callback) override {
87 return net::QUIC_SUCCESS;
88 }
89 };
90 }
91
92 namespace net {
93
94 QuicConnectionId QuartcCryptoServerStreamHelper::GenerateConnectionIdForReject(
95 QuicConnectionId connection_id) const {
96 return 0;
97 }
98
99 bool QuartcCryptoServerStreamHelper::CanAcceptClientHello(
100 const CryptoHandshakeMessage& message,
101 const IPEndPoint& self_address,
102 std::string* error_details) const {
103 return true;
104 }
105
106 QuartcSession::QuartcSession(std::unique_ptr<QuicConnection> connection,
107 const QuicConfig& config,
108 const std::string& remote_fingerprint_value,
109 Perspective perspective,
110 QuicConnectionHelperInterface* helper)
111 : QuicSession(connection.get(), config),
112 remote_fingerprint_value_(remote_fingerprint_value),
113 perspective_(perspective),
114 connection_(std::move(connection)),
115 helper_(helper) {
116 // Initialization with default crypto configuration.
117 if (perspective_ == Perspective::IS_CLIENT) {
118 std::unique_ptr<ProofVerifier> proof_verifier(new InsecureProofVerifier);
119 quic_crypto_client_config_.reset(
120 new QuicCryptoClientConfig(std::move(proof_verifier)));
121 } else {
122 std::unique_ptr<ProofSource> proof_source(new DummyProofSource);
123 std::string source_address_token_secret =
124 base::RandBytesAsString(kInputKeyingMaterialLength);
125 quic_crypto_server_config_.reset(new QuicCryptoServerConfig(
126 source_address_token_secret, helper_->GetRandomGenerator(),
127 std::move(proof_source)));
128 // Provide server with serialized config string to prove ownership.
129 QuicCryptoServerConfig::ConfigOptions options;
130 quic_crypto_server_config_->AddDefaultConfig(helper_->GetRandomGenerator(),
131 helper_->GetClock(), options);
132 }
133 }
134
135 QuartcSession::~QuartcSession() {}
136
137 QuicCryptoStream* QuartcSession::GetCryptoStream() {
138 return crypto_stream_.get();
139 }
140
141 QuartcStream* QuartcSession::CreateOutgoingDynamicStream(
142 SpdyPriority priority) {
143 return CreateDataStream(GetNextOutgoingStreamId(), priority);
144 }
145
146 void QuartcSession::OnCryptoHandshakeEvent(CryptoHandshakeEvent event) {
147 QuicSession::OnCryptoHandshakeEvent(event);
148 if (event == HANDSHAKE_CONFIRMED) {
149 DCHECK(IsEncryptionEstablished());
150 DCHECK(IsCryptoHandshakeConfirmed());
151
152 DCHECK(session_delegate_);
153 session_delegate_->OnCryptoHandshakeComplete();
154 }
155 }
156
157 void QuartcSession::CloseStream(QuicStreamId stream_id) {
158 if (IsClosedStream(stream_id)) {
159 // When CloseStream has been called recursively (via
160 // ReliableQuicStream::OnClose), the stream is already closed so return.
161 return;
162 }
163 write_blocked_streams()->UnregisterStream(stream_id);
164 QuicSession::CloseStream(stream_id);
165 }
166
167 void QuartcSession::OnConnectionClosed(QuicErrorCode error,
168 const std::string& error_details,
169 ConnectionCloseSource source) {
170 QuicSession::OnConnectionClosed(error, error_details, source);
171 DCHECK(session_delegate_);
172 session_delegate_->OnConnectionClosed(
173 error, source == ConnectionCloseSource::FROM_PEER);
174 }
175
176 void QuartcSession::StartCryptoHandshake() {
177 if (perspective_ == Perspective::IS_CLIENT) {
178 QuicServerId server_id(remote_fingerprint_value_, kQuicServerPort);
179 QuicCryptoClientStream* crypto_stream =
180 new QuicCryptoClientStream(server_id, this, new ProofVerifyContext(),
181 quic_crypto_client_config_.get(), this);
182 crypto_stream_.reset(crypto_stream);
183 QuicSession::Initialize();
184 crypto_stream->CryptoConnect();
185 } else {
186 quic_compressed_certs_cache_.reset(new QuicCompressedCertsCache(
187 QuicCompressedCertsCache::kQuicCompressedCertsCacheSize));
188 bool use_stateless_rejects_if_peer_supported = false;
189 QuicCryptoServerStream* crypto_stream = new QuicCryptoServerStream(
190 quic_crypto_server_config_.get(), quic_compressed_certs_cache_.get(),
191 use_stateless_rejects_if_peer_supported, this, &stream_helper_);
192 crypto_stream_.reset(crypto_stream);
193 QuicSession::Initialize();
194 }
195 }
196
197 bool QuartcSession::ExportKeyingMaterial(const std::string& label,
198 const uint8_t* context,
199 size_t context_len,
200 bool used_context,
201 uint8_t* result,
202 size_t result_len) {
203 std::string quic_context(reinterpret_cast<const char*>(context), context_len);
204 std::string quic_result;
205 bool success = crypto_stream_->ExportKeyingMaterial(label, quic_context,
206 result_len, &quic_result);
207 quic_result.copy(reinterpret_cast<char*>(result), result_len);
208 DCHECK(quic_result.length() == result_len);
209 return success;
210 }
211
212 QuartcStreamInterface* QuartcSession::CreateOutgoingStream(
213 const OutgoingStreamParameters& param) {
214 // The |param| is for forward-compatibility. Not used for now.
215 return CreateOutgoingDynamicStream(kDefaultPriority);
216 }
217
218 void QuartcSession::SetDelegate(
219 QuartcSessionInterface::Delegate* session_delegate) {
220 if (session_delegate_) {
221 LOG(WARNING) << "The delegate for the session has already been set.";
222 }
223 session_delegate_ = session_delegate;
224 DCHECK(session_delegate_);
225 }
226
227 void QuartcSession::OnTransportCanWrite() {
228 if (HasDataToWrite()) {
229 connection()->OnCanWrite();
230 }
231 }
232
233 bool QuartcSession::OnTransportReceived(const char* data, size_t data_len) {
234 QuicReceivedPacket packet(data, data_len, clock_.Now());
235 ProcessUdpPacket(connection()->self_address(), connection()->peer_address(),
236 packet);
237 return true;
238 }
239
240 void QuartcSession::OnProofValid(
241 const QuicCryptoClientConfig::CachedState& cached) {
242 // TODO(zhihuang): Handle the proof verification.
243 }
244
245 void QuartcSession::OnProofVerifyDetailsAvailable(
246 const ProofVerifyDetails& verify_details) {
247 // TODO(zhihuang): Handle the proof verification.
248 }
249
250 void QuartcSession::SetClientCryptoConfig(
251 QuicCryptoClientConfig* client_config) {
252 quic_crypto_client_config_.reset(client_config);
253 }
254
255 void QuartcSession::SetServerCryptoConfig(
256 QuicCryptoServerConfig* server_config) {
257 quic_crypto_server_config_.reset(server_config);
258 }
259
260 ReliableQuicStream* QuartcSession::CreateIncomingDynamicStream(
261 QuicStreamId id) {
262 QuartcStream* stream = CreateDataStream(id, kDefaultPriority);
263 if (stream) {
264 DCHECK(session_delegate_);
265 session_delegate_->OnIncomingStream(stream);
266 }
267 return stream;
268 }
269
270 QuartcStream* QuartcSession::CreateDataStream(QuicStreamId id,
271 SpdyPriority priority) {
272 if (crypto_stream_ == nullptr || !crypto_stream_->encryption_established()) {
273 // Encryption not active so no stream created
274 return nullptr;
275 }
276 QuartcStream* stream = new QuartcStream(id, this);
277 if (stream) {
278 // Make QuicSession take ownership of the stream.
279 ActivateStream(stream);
280 // Register the stream to the QuicWriteBlockedList. |priority| is clamped
281 // between 0 and 7, with 0 being the highest priority and 7 the lowest
282 // priority.
283 write_blocked_streams()->RegisterStream(stream->id(), priority);
284 }
285 return stream;
286 }
287
288 } // namespace net
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698