OLD | NEW |
1 // Copyright (c) 2013 The Chromium Authors. All rights reserved. | 1 // Copyright (c) 2013 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_spdy_server_stream.h" | 5 #include "net/tools/quic/quic_spdy_server_stream.h" |
6 | 6 |
7 #include "base/strings/string_number_conversions.h" | 7 #include "base/strings/string_number_conversions.h" |
8 #include "base/strings/string_piece.h" | 8 #include "base/strings/string_piece.h" |
9 #include "net/quic/quic_connection.h" | 9 #include "net/quic/quic_connection.h" |
10 #include "net/quic/quic_protocol.h" | 10 #include "net/quic/quic_protocol.h" |
(...skipping 28 matching lines...) Expand all Loading... |
39 | 39 |
40 class QuicSpdyServerStreamPeer : public QuicSpdyServerStream { | 40 class QuicSpdyServerStreamPeer : public QuicSpdyServerStream { |
41 public: | 41 public: |
42 QuicSpdyServerStreamPeer(QuicStreamId stream_id, QuicSession* session) | 42 QuicSpdyServerStreamPeer(QuicStreamId stream_id, QuicSession* session) |
43 : QuicSpdyServerStream(stream_id, session) { | 43 : QuicSpdyServerStream(stream_id, session) { |
44 } | 44 } |
45 | 45 |
46 using QuicSpdyServerStream::SendResponse; | 46 using QuicSpdyServerStream::SendResponse; |
47 using QuicSpdyServerStream::SendErrorResponse; | 47 using QuicSpdyServerStream::SendErrorResponse; |
48 | 48 |
49 BalsaHeaders* mutable_headers() { | 49 SpdyHeaderBlock* mutable_headers() { |
50 return &headers_; | 50 return &request_headers_; |
51 } | 51 } |
52 | 52 |
53 static void SendResponse(QuicSpdyServerStream* stream) { | 53 static void SendResponse(QuicSpdyServerStream* stream) { |
54 stream->SendResponse(); | 54 stream->SendResponse(); |
55 } | 55 } |
56 | 56 |
57 static void SendErrorResponse(QuicSpdyServerStream* stream) { | 57 static void SendErrorResponse(QuicSpdyServerStream* stream) { |
58 stream->SendResponse(); | 58 stream->SendResponse(); |
59 } | 59 } |
60 | 60 |
61 static const string& body(QuicSpdyServerStream* stream) { | 61 static const string& body(QuicSpdyServerStream* stream) { |
62 return stream->body_; | 62 return stream->body_; |
63 } | 63 } |
64 | 64 |
65 static const BalsaHeaders& headers(QuicSpdyServerStream* stream) { | 65 static const SpdyHeaderBlock& headers(QuicSpdyServerStream* stream) { |
66 return stream->headers_; | 66 return stream->request_headers_; |
67 } | 67 } |
68 }; | 68 }; |
69 | 69 |
70 namespace { | 70 namespace { |
71 | 71 |
72 class QuicSpdyServerStreamTest : public ::testing::TestWithParam<QuicVersion> { | 72 class QuicSpdyServerStreamTest : public ::testing::TestWithParam<QuicVersion> { |
73 public: | 73 public: |
74 QuicSpdyServerStreamTest() | 74 QuicSpdyServerStreamTest() |
75 : connection_( | 75 : connection_( |
76 new StrictMock<MockConnection>(Perspective::IS_SERVER, | 76 new StrictMock<MockConnection>(Perspective::IS_SERVER, |
77 SupportedVersions(GetParam()))), | 77 SupportedVersions(GetParam()))), |
78 session_(connection_), | 78 session_(connection_), |
79 body_("hello world") { | 79 body_("hello world") { |
80 BalsaHeaders request_headers; | 80 SpdyHeaderBlock request_headers; |
81 request_headers.SetRequestFirstlineFromStringPieces( | 81 request_headers[":host"] = ""; |
82 "POST", "https://www.google.com/", "HTTP/1.1"); | 82 request_headers[":path"] = "/"; |
83 request_headers.ReplaceOrAppendHeader("content-length", "11"); | 83 request_headers[":method"] = "POST"; |
| 84 request_headers[":version"] = "HTTP/1.1"; |
| 85 request_headers["content-length"] = "11"; |
84 | 86 |
85 headers_string_ = SpdyUtils::SerializeRequestHeaders(request_headers); | 87 headers_string_ = SpdyUtils::SerializeUncompressedHeaders(request_headers); |
86 | 88 |
87 // New streams rely on having the peer's flow control receive window | 89 // New streams rely on having the peer's flow control receive window |
88 // negotiated in the config. | 90 // negotiated in the config. |
89 session_.config()->SetInitialStreamFlowControlWindowToSend( | 91 session_.config()->SetInitialStreamFlowControlWindowToSend( |
90 kInitialStreamFlowControlWindowForTest); | 92 kInitialStreamFlowControlWindowForTest); |
91 session_.config()->SetInitialSessionFlowControlWindowToSend( | 93 session_.config()->SetInitialSessionFlowControlWindowToSend( |
92 kInitialSessionFlowControlWindowForTest); | 94 kInitialSessionFlowControlWindowForTest); |
93 stream_.reset(new QuicSpdyServerStreamPeer(3, &session_)); | 95 stream_.reset(new QuicSpdyServerStreamPeer(3, &session_)); |
94 | 96 |
95 QuicInMemoryCachePeer::ResetForTests(); | 97 QuicInMemoryCachePeer::ResetForTests(); |
| 98 |
96 string host = ""; | 99 string host = ""; |
97 string path = "/foo"; | 100 string path = "/foo"; |
98 SpdyHeaderBlock response_headers; | 101 SpdyHeaderBlock response_headers; |
99 StringPiece body("Yum"); | 102 StringPiece body("Yum"); |
100 QuicInMemoryCache::GetInstance()->AddResponse(host, path, response_headers, | 103 QuicInMemoryCache::GetInstance()->AddResponse(host, path, response_headers, |
101 body); | 104 body); |
102 } | 105 } |
103 | 106 |
104 ~QuicSpdyServerStreamTest() override { | 107 ~QuicSpdyServerStreamTest() override { |
105 QuicInMemoryCachePeer::ResetForTests(); | 108 QuicInMemoryCachePeer::ResetForTests(); |
106 } | 109 } |
107 | 110 |
108 const string& StreamBody() { | 111 const string& StreamBody() { |
109 return QuicSpdyServerStreamPeer::body(stream_.get()); | 112 return QuicSpdyServerStreamPeer::body(stream_.get()); |
110 } | 113 } |
111 | 114 |
112 const BalsaHeaders& StreamHeaders() { | 115 const string& StreamHeadersValue(const string& key) { |
113 return QuicSpdyServerStreamPeer::headers(stream_.get()); | 116 return (*stream_->mutable_headers())[key]; |
114 } | 117 } |
115 | 118 |
116 BalsaHeaders response_headers_; | 119 SpdyHeaderBlock response_headers_; |
117 EpollServer eps_; | 120 EpollServer eps_; |
118 StrictMock<MockConnection>* connection_; | 121 StrictMock<MockConnection>* connection_; |
119 StrictMock<MockSession> session_; | 122 StrictMock<MockSession> session_; |
120 scoped_ptr<QuicSpdyServerStreamPeer> stream_; | 123 scoped_ptr<QuicSpdyServerStreamPeer> stream_; |
121 string headers_string_; | 124 string headers_string_; |
122 string body_; | 125 string body_; |
123 }; | 126 }; |
124 | 127 |
125 QuicConsumedData ConsumeAllData( | 128 QuicConsumedData ConsumeAllData( |
126 QuicStreamId id, | 129 QuicStreamId id, |
127 const IOVector& data, | 130 const IOVector& data, |
128 QuicStreamOffset offset, | 131 QuicStreamOffset offset, |
129 bool fin, | 132 bool fin, |
130 FecProtection /*fec_protection_*/, | 133 FecProtection /*fec_protection_*/, |
131 QuicAckNotifier::DelegateInterface* /*ack_notifier_delegate*/) { | 134 QuicAckNotifier::DelegateInterface* /*ack_notifier_delegate*/) { |
132 return QuicConsumedData(data.TotalBufferSize(), fin); | 135 return QuicConsumedData(data.TotalBufferSize(), fin); |
133 } | 136 } |
134 | 137 |
135 INSTANTIATE_TEST_CASE_P(Tests, QuicSpdyServerStreamTest, | 138 INSTANTIATE_TEST_CASE_P(Tests, QuicSpdyServerStreamTest, |
136 ::testing::ValuesIn(QuicSupportedVersions())); | 139 ::testing::ValuesIn(QuicSupportedVersions())); |
137 | 140 |
138 TEST_P(QuicSpdyServerStreamTest, TestFraming) { | 141 TEST_P(QuicSpdyServerStreamTest, TestFraming) { |
139 EXPECT_CALL(session_, WritevData(_, _, _, _, _, _)).Times(AnyNumber()). | 142 EXPECT_CALL(session_, WritevData(_, _, _, _, _, _)).Times(AnyNumber()). |
140 WillRepeatedly(Invoke(ConsumeAllData)); | 143 WillRepeatedly(Invoke(ConsumeAllData)); |
141 | 144 stream_->OnStreamHeaders(headers_string_); |
142 EXPECT_EQ(headers_string_.size(), stream_->ProcessData( | 145 stream_->OnStreamHeadersComplete(false, headers_string_.size()); |
143 headers_string_.c_str(), headers_string_.size())); | |
144 EXPECT_EQ(body_.size(), stream_->ProcessData(body_.c_str(), body_.size())); | 146 EXPECT_EQ(body_.size(), stream_->ProcessData(body_.c_str(), body_.size())); |
145 EXPECT_EQ(11u, StreamHeaders().content_length()); | 147 EXPECT_EQ("11", StreamHeadersValue("content-length")); |
146 EXPECT_EQ("https://www.google.com/", StreamHeaders().request_uri()); | 148 EXPECT_EQ("/", StreamHeadersValue(":path")); |
147 EXPECT_EQ("POST", StreamHeaders().request_method()); | 149 EXPECT_EQ("POST", StreamHeadersValue(":method")); |
148 EXPECT_EQ(body_, StreamBody()); | 150 EXPECT_EQ(body_, StreamBody()); |
149 } | 151 } |
150 | 152 |
151 TEST_P(QuicSpdyServerStreamTest, TestFramingOnePacket) { | 153 TEST_P(QuicSpdyServerStreamTest, TestFramingOnePacket) { |
152 EXPECT_CALL(session_, WritevData(_, _, _, _, _, _)).Times(AnyNumber()). | 154 EXPECT_CALL(session_, WritevData(_, _, _, _, _, _)).Times(AnyNumber()). |
153 WillRepeatedly(Invoke(ConsumeAllData)); | 155 WillRepeatedly(Invoke(ConsumeAllData)); |
154 | 156 |
155 string message = headers_string_ + body_; | 157 stream_->OnStreamHeaders(headers_string_); |
156 | 158 stream_->OnStreamHeadersComplete(false, headers_string_.size()); |
157 EXPECT_EQ(message.size(), stream_->ProcessData( | 159 EXPECT_EQ(body_.size(), stream_->ProcessData(body_.c_str(), body_.size())); |
158 message.c_str(), message.size())); | 160 EXPECT_EQ("11", StreamHeadersValue("content-length")); |
159 EXPECT_EQ(11u, StreamHeaders().content_length()); | 161 EXPECT_EQ("/", StreamHeadersValue(":path")); |
160 EXPECT_EQ("https://www.google.com/", StreamHeaders().request_uri()); | 162 EXPECT_EQ("POST", StreamHeadersValue(":method")); |
161 EXPECT_EQ("POST", StreamHeaders().request_method()); | |
162 EXPECT_EQ(body_, StreamBody()); | 163 EXPECT_EQ(body_, StreamBody()); |
163 } | 164 } |
164 | 165 |
165 TEST_P(QuicSpdyServerStreamTest, TestFramingExtraData) { | 166 TEST_P(QuicSpdyServerStreamTest, TestFramingExtraData) { |
166 string large_body = "hello world!!!!!!"; | 167 string large_body = "hello world!!!!!!"; |
167 | 168 |
168 // We'll automatically write out an error (headers + body) | 169 // We'll automatically write out an error (headers + body) |
169 EXPECT_CALL(session_, WritevData(_, _, _, _, _, _)).Times(AnyNumber()). | 170 EXPECT_CALL(session_, WritevData(_, _, _, _, _, _)).Times(AnyNumber()). |
170 WillRepeatedly(Invoke(ConsumeAllData)); | 171 WillRepeatedly(Invoke(ConsumeAllData)); |
171 | 172 |
172 EXPECT_EQ(headers_string_.size(), stream_->ProcessData( | 173 stream_->OnStreamHeaders(headers_string_); |
173 headers_string_.c_str(), headers_string_.size())); | 174 stream_->OnStreamHeadersComplete(false, headers_string_.size()); |
| 175 EXPECT_EQ(body_.size(), stream_->ProcessData(body_.c_str(), body_.size())); |
174 // Content length is still 11. This will register as an error and we won't | 176 // Content length is still 11. This will register as an error and we won't |
175 // accept the bytes. | 177 // accept the bytes. |
176 stream_->ProcessData(large_body.c_str(), large_body.size()); | 178 stream_->ProcessData(large_body.c_str(), large_body.size()); |
177 EXPECT_EQ(11u, StreamHeaders().content_length()); | 179 EXPECT_EQ("11", StreamHeadersValue("content-length")); |
178 EXPECT_EQ("https://www.google.com/", StreamHeaders().request_uri()); | 180 EXPECT_EQ("/", StreamHeadersValue(":path")); |
179 EXPECT_EQ("POST", StreamHeaders().request_method()); | 181 EXPECT_EQ("POST", StreamHeadersValue(":method")); |
180 } | 182 } |
181 | 183 |
182 TEST_P(QuicSpdyServerStreamTest, TestSendResponse) { | 184 TEST_P(QuicSpdyServerStreamTest, TestSendResponse) { |
183 BalsaHeaders* request_headers = stream_->mutable_headers(); | 185 SpdyHeaderBlock* request_headers = stream_->mutable_headers(); |
184 request_headers->SetRequestFirstlineFromStringPieces( | 186 (*request_headers)[":path"] = "/foo"; |
185 "GET", | 187 (*request_headers)[":host"] = ""; |
186 "https://www.google.com/foo", | 188 (*request_headers)[":version"] = "HTTP/1.1"; |
187 "HTTP/1.1"); | 189 (*request_headers)[":method"] = "GET"; |
188 | 190 |
189 response_headers_.SetResponseFirstlineFromStringPieces( | 191 response_headers_[":version"] = "HTTP/1.1"; |
190 "HTTP/1.1", "200", "OK"); | 192 response_headers_[":status"] = "200 OK"; |
191 response_headers_.ReplaceOrAppendHeader("content-length", "3"); | 193 response_headers_["content-length"] = "3"; |
192 | 194 |
193 InSequence s; | 195 InSequence s; |
194 EXPECT_CALL(session_, WritevData(kHeadersStreamId, _, 0, false, _, nullptr)); | 196 EXPECT_CALL(session_, WritevData(kHeadersStreamId, _, 0, false, _, nullptr)); |
195 EXPECT_CALL(session_, WritevData(_, _, _, _, _, _)).Times(1). | 197 EXPECT_CALL(session_, WritevData(_, _, _, _, _, _)).Times(1). |
196 WillOnce(Return(QuicConsumedData(3, true))); | 198 WillOnce(Return(QuicConsumedData(3, true))); |
197 | 199 |
198 QuicSpdyServerStreamPeer::SendResponse(stream_.get()); | 200 QuicSpdyServerStreamPeer::SendResponse(stream_.get()); |
199 EXPECT_TRUE(stream_->read_side_closed()); | 201 EXPECT_TRUE(stream_->read_side_closed()); |
200 EXPECT_TRUE(stream_->write_side_closed()); | 202 EXPECT_TRUE(stream_->write_side_closed()); |
201 } | 203 } |
202 | 204 |
203 TEST_P(QuicSpdyServerStreamTest, TestSendErrorResponse) { | 205 TEST_P(QuicSpdyServerStreamTest, TestSendErrorResponse) { |
204 response_headers_.SetResponseFirstlineFromStringPieces( | 206 response_headers_[":version"] = "HTTP/1.1"; |
205 "HTTP/1.1", "500", "Server Error"); | 207 response_headers_[":status"] = "500 Server Error"; |
206 response_headers_.ReplaceOrAppendHeader("content-length", "3"); | 208 response_headers_["content-length"] = "3"; |
207 | 209 |
208 InSequence s; | 210 InSequence s; |
209 EXPECT_CALL(session_, WritevData(kHeadersStreamId, _, 0, false, _, nullptr)); | 211 EXPECT_CALL(session_, WritevData(kHeadersStreamId, _, 0, false, _, nullptr)); |
210 EXPECT_CALL(session_, WritevData(_, _, _, _, _, _)).Times(1). | 212 EXPECT_CALL(session_, WritevData(_, _, _, _, _, _)).Times(1). |
211 WillOnce(Return(QuicConsumedData(3, true))); | 213 WillOnce(Return(QuicConsumedData(3, true))); |
212 | 214 |
213 QuicSpdyServerStreamPeer::SendErrorResponse(stream_.get()); | 215 QuicSpdyServerStreamPeer::SendErrorResponse(stream_.get()); |
214 EXPECT_TRUE(stream_->read_side_closed()); | 216 EXPECT_TRUE(stream_->read_side_closed()); |
215 EXPECT_TRUE(stream_->write_side_closed()); | 217 EXPECT_TRUE(stream_->write_side_closed()); |
216 } | 218 } |
(...skipping 25 matching lines...) Expand all Loading... |
242 StringPiece data(arr, arraysize(arr)); | 244 StringPiece data(arr, arraysize(arr)); |
243 QuicStreamFrame frame(stream_->id(), true, 0, MakeIOVector(data)); | 245 QuicStreamFrame frame(stream_->id(), true, 0, MakeIOVector(data)); |
244 // Verify that we don't crash when we get a invalid headers in stream frame. | 246 // Verify that we don't crash when we get a invalid headers in stream frame. |
245 stream_->OnStreamFrame(frame); | 247 stream_->OnStreamFrame(frame); |
246 } | 248 } |
247 | 249 |
248 } // namespace | 250 } // namespace |
249 } // namespace test | 251 } // namespace test |
250 } // namespace tools | 252 } // namespace tools |
251 } // namespace net | 253 } // namespace net |
OLD | NEW |