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

Side by Side Diff: net/server/web_socket_encoder.cc

Issue 1047623002: Support parsing a Sec-WebSocket-Extensions header with multiple elements (Closed) Base URL: https://chromium.googlesource.com/chromium/src.git@master
Patch Set: Clear extensions_ if errored Created 5 years, 8 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
1 // Copyright 2014 The Chromium Authors. All rights reserved. 1 // Copyright 2014 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/server/web_socket_encoder.h" 5 #include "net/server/web_socket_encoder.h"
6 6
7 #include "base/logging.h" 7 #include "base/logging.h"
8 #include "base/strings/string_number_conversions.h" 8 #include "base/strings/string_number_conversions.h"
9 #include "base/strings/stringprintf.h" 9 #include "base/strings/stringprintf.h"
10 #include "net/base/io_buffer.h" 10 #include "net/base/io_buffer.h"
(...skipping 215 matching lines...) Expand 10 before | Expand all | Expand 10 after
226 226
227 if (deflate) { 227 if (deflate) {
228 return new WebSocketEncoder(false /* is_server */, client_window_bits, 228 return new WebSocketEncoder(false /* is_server */, client_window_bits,
229 server_window_bits, client_no_context_takeover); 229 server_window_bits, client_no_context_takeover);
230 } else { 230 } else {
231 return new WebSocketEncoder(false /* is_server */); 231 return new WebSocketEncoder(false /* is_server */);
232 } 232 }
233 } 233 }
234 234
235 // static 235 // static
236 void WebSocketEncoder::ParseExtensions(const std::string& extensions, 236 void WebSocketEncoder::ParseExtensions(const std::string& header_value,
237 bool* deflate, 237 bool* deflate,
238 bool* has_client_window_bits, 238 bool* has_client_window_bits,
239 int* client_window_bits, 239 int* client_window_bits,
240 int* server_window_bits, 240 int* server_window_bits,
241 bool* client_no_context_takeover, 241 bool* client_no_context_takeover,
242 bool* server_no_context_takeover) { 242 bool* server_no_context_takeover) {
243 *deflate = false; 243 *deflate = false;
244 *has_client_window_bits = false; 244 *has_client_window_bits = false;
245 *client_window_bits = 15; 245 *client_window_bits = 15;
246 *server_window_bits = 15; 246 *server_window_bits = 15;
247 *client_no_context_takeover = false; 247 *client_no_context_takeover = false;
248 *server_no_context_takeover = false; 248 *server_no_context_takeover = false;
249 249
250 if (extensions.empty()) 250 if (header_value.empty())
251 return; 251 return;
252 252
253 // TODO(dgozman): split extensions header if another extension is introduced.
254 WebSocketExtensionParser parser; 253 WebSocketExtensionParser parser;
255 parser.Parse(extensions); 254 parser.Parse(header_value);
256 if (parser.has_error()) 255 if (parser.has_error())
257 return; 256 return;
258 if (parser.extension().name() != "permessage-deflate") 257 const std::vector<WebSocketExtension>& extensions = parser.extensions();
259 return; 258 // TODO(tyoshino): Fail if this method is used for parsing a response and
259 // there're multiple permessage-deflate extensions or there is any unknown
eroman 2015/03/31 21:11:12 there're --> there are there is any unknown --> th
tyoshino (SeeGerritForStatus) 2015/04/01 04:57:57 Done.
260 // extensions.
261 for (size_t i = 0; i < extensions.size(); ++i) {
eroman 2015/03/31 21:11:12 nit: You use a traditional for loop here, however
tyoshino (SeeGerritForStatus) 2015/04/01 04:57:57 Done.
262 if (extensions[i].name() != "permessage-deflate") {
263 continue;
264 }
260 265
261 const std::vector<WebSocketExtension::Parameter>& parameters = 266 const std::vector<WebSocketExtension::Parameter>& parameters =
262 parser.extension().parameters(); 267 extensions[i].parameters();
263 for (const auto& param : parameters) { 268 for (const auto& param : parameters) {
264 const std::string& name = param.name(); 269 const std::string& name = param.name();
265 if (name == "client_max_window_bits") { 270 // TODO(tyoshino): Fail the connection when an invalid value is given.
266 *has_client_window_bits = true; 271 if (name == "client_max_window_bits") {
267 if (param.HasValue()) { 272 *has_client_window_bits = true;
273 if (param.HasValue()) {
274 int bits = 0;
275 if (base::StringToInt(param.value(), &bits) && bits >= 8 &&
276 bits <= 15) {
277 *client_window_bits = bits;
278 }
279 }
280 }
281 if (name == "server_max_window_bits" && param.HasValue()) {
268 int bits = 0; 282 int bits = 0;
269 if (base::StringToInt(param.value(), &bits) && bits >= 8 && bits <= 15) 283 if (base::StringToInt(param.value(), &bits) && bits >= 8 && bits <= 15)
270 *client_window_bits = bits; 284 *server_window_bits = bits;
271 } 285 }
286 if (name == "client_no_context_takeover")
287 *client_no_context_takeover = true;
288 if (name == "server_no_context_takeover")
289 *server_no_context_takeover = true;
272 } 290 }
273 if (name == "server_max_window_bits" && param.HasValue()) { 291 *deflate = true;
274 int bits = 0; 292
275 if (base::StringToInt(param.value(), &bits) && bits >= 8 && bits <= 15) 293 break;
276 *server_window_bits = bits;
277 }
278 if (name == "client_no_context_takeover")
279 *client_no_context_takeover = true;
280 if (name == "server_no_context_takeover")
281 *server_no_context_takeover = true;
282 } 294 }
283 *deflate = true;
284 } 295 }
285 296
286 WebSocketEncoder::WebSocketEncoder(bool is_server) : is_server_(is_server) { 297 WebSocketEncoder::WebSocketEncoder(bool is_server) : is_server_(is_server) {
287 } 298 }
288 299
289 WebSocketEncoder::WebSocketEncoder(bool is_server, 300 WebSocketEncoder::WebSocketEncoder(bool is_server,
290 int deflate_bits, 301 int deflate_bits,
291 int inflate_bits, 302 int inflate_bits,
292 bool no_context_takeover) 303 bool no_context_takeover)
293 : is_server_(is_server) { 304 : is_server_(is_server) {
(...skipping 72 matching lines...) Expand 10 before | Expand all | Expand 10 after
366 return false; 377 return false;
367 scoped_refptr<IOBufferWithSize> buffer = 378 scoped_refptr<IOBufferWithSize> buffer =
368 deflater_->GetOutput(deflater_->CurrentOutputSize()); 379 deflater_->GetOutput(deflater_->CurrentOutputSize());
369 if (!buffer.get()) 380 if (!buffer.get())
370 return false; 381 return false;
371 *output = std::string(buffer->data(), buffer->size()); 382 *output = std::string(buffer->data(), buffer->size());
372 return true; 383 return true;
373 } 384 }
374 385
375 } // namespace net 386 } // namespace net
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698