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

Side by Side Diff: net/websockets/websocket_extension_parser.cc

Issue 23872029: Implement WebSocketExtensionParser (Closed) Base URL: https://chromium.googlesource.com/chromium/src.git@master
Patch Set: Created 7 years, 3 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 2013 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/websockets/websocket_extension_parser.h"
6
7 #include "base/strings/string_util.h"
8
9 namespace net {
10
11 WebSocketExtensionParser::WebSocketExtensionParser() {}
12
13 WebSocketExtensionParser::~WebSocketExtensionParser() {}
14
15 void WebSocketExtensionParser::Parse(const char* data, size_t size) {
16 current_ = data;
17 end_ = &data[size];
18 has_error_ = false;
19
20 ConsumeExtension(&extension_);
21 if (has_error_) return;
22 ConsumeSpaces();
23 has_error_ = has_error_ || (current_ != end_);
24 }
25
26 void WebSocketExtensionParser::Consume(char c) {
27 DCHECK(!has_error_);
28 ConsumeSpaces();
29 DCHECK(!has_error_);
30 if (current_ == end_) {
Adam Rice 2013/09/17 12:41:36 FYI: I would combine these two if statements, ie.
yhirano 2013/09/18 01:15:43 Done.
31 has_error_ = true;
32 return;
33 }
34 if (c != *current_) {
35 has_error_ = true;
36 return;
37 }
38 ++current_;
39 }
40
41 void WebSocketExtensionParser::ConsumeExtension(WebSocketExtension* extension) {
42 DCHECK(!has_error_);
43 base::StringPiece name;
44 ConsumeToken(&name);
45 if (has_error_) return;
46 *extension = WebSocketExtension(name.as_string());
47
48 while (ConsumeIfMatch(';')) {
49 WebSocketExtension::Parameter parameter("");
50 ConsumeExtensionParameter(&parameter);
51 if (has_error_) return;
52 extension->Add(parameter);
53 }
54 }
55
56 void WebSocketExtensionParser::ConsumeExtensionParameter(
57 WebSocketExtension::Parameter* parameter) {
58 DCHECK(!has_error_);
59 base::StringPiece name, value;
60 std::string value_string;
61
62 ConsumeToken(&name);
63 if (has_error_) return;
64 if (!ConsumeIfMatch('=')) {
65 *parameter = WebSocketExtension::Parameter(name.as_string());
66 return;
67 }
68
69 if (Lookahead('\"')) {
70 ConsumeQuotedToken(&value_string);
71 } else {
72 ConsumeToken(&value);
73 value_string = value.as_string();
74 }
75 if (has_error_) return;
76 *parameter = WebSocketExtension::Parameter(name.as_string(), value_string);
77 }
78
79 void WebSocketExtensionParser::ConsumeToken(base::StringPiece* token) {
80 DCHECK(!has_error_);
81 ConsumeSpaces();
82 DCHECK(!has_error_);
83 const char* head = current_;
84 while (current_ < end_ &&
85 !IsControl(current_[0]) && !IsSeparator(current_[0]))
86 ++current_;
87 if (current_ == head) {
88 has_error_ = true;
89 return;
90 }
91 *token = base::StringPiece(head, current_ - head);
92 }
93
94 void WebSocketExtensionParser::ConsumeQuotedToken(std::string* token) {
95 DCHECK(!has_error_);
96 Consume('"');
97 if (has_error_) return;
98 *token = "";
99 while (current_ < end_ && !IsControl(current_[0])) {
100 if (UnconsumedBytes() >= 2 && current_[0] == '\\') {
101 char next = current_[1];
102 if (IsControl(next) || IsSeparator(next)) break;
103 *token += next;
104 current_ += 2;
105 } else if (IsSeparator(current_[0])) {
106 break;
107 } else {
108 *token += current_[0];
109 ++current_;
110 }
111 }
112 Consume('"');
113 has_error_ = has_error_ || token->empty();
114 }
115
116 void WebSocketExtensionParser::ConsumeSpaces() {
117 DCHECK(!has_error_);
118 while (current_ < end_ && (current_[0] == ' ' || current_[0] == '\t'))
119 ++current_;
120 return;
121 }
122
123 bool WebSocketExtensionParser::Lookahead(char c) {
124 DCHECK(!has_error_);
125 const char* head = current_;
126
127 ConsumeSpaces();
128 if (!has_error_)
Adam Rice 2013/09/17 12:41:36 ConsumeSpaces() can no longer set has_error_, so t
yhirano 2013/09/18 01:15:43 Done.
129 Consume(c);
130
131 bool result = !has_error_;
132 current_ = head;
133 has_error_ = false;
134 return result;
135 }
136
137 bool WebSocketExtensionParser::ConsumeIfMatch(char c) {
Adam Rice 2013/09/17 12:41:36 Lookahead() and ConsumeIfMatch() are now very simi
yhirano 2013/09/18 01:15:43 I would like to keep them because they are both si
138 DCHECK(!has_error_);
139 const char* head = current_;
140
141 ConsumeSpaces();
142 if (!has_error_)
143 Consume(c);
144
145 if (has_error_) {
146 current_ = head;
147 has_error_ = false;
148 return false;
149 }
150 return true;
151 }
152
153 // static
154 bool WebSocketExtensionParser::IsControl(char c) {
155 return (0 <= c && c <= 31) || c == 127;
156 }
157
158 // static
159 bool WebSocketExtensionParser::IsSeparator(char c) {
160 const char separators[] = "()<>@,;:\\\"/[]?={} \t";
161 return strchr(separators, c);
162 }
163
164 } // namespace net
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698