Skip to content

Commit c38c94c

Browse files
noxseanmonstar
authored andcommitted
Make :status in requests be a stream error
1 parent 8520f06 commit c38c94c

File tree

4 files changed

+39
-4
lines changed

4 files changed

+39
-4
lines changed

src/frame/headers.rs

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -575,6 +575,11 @@ impl Pseudo {
575575
}
576576
}
577577

578+
#[cfg(feature = "unstable")]
579+
pub fn set_status(&mut self, value: StatusCode) {
580+
self.status = Some(value);
581+
}
582+
578583
pub fn set_scheme(&mut self, scheme: uri::Scheme) {
579584
let bytes_str = match scheme.as_str() {
580585
"http" => BytesStr::from_static("http"),

src/server.rs

Lines changed: 1 addition & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1410,10 +1410,8 @@ impl proto::Peer for Peer {
14101410
malformed!("malformed headers: missing method");
14111411
}
14121412

1413-
// Specifying :status for a request is a protocol error
14141413
if pseudo.status.is_some() {
1415-
tracing::trace!("malformed headers: :status field on request; PROTOCOL_ERROR");
1416-
return Err(Error::library_go_away(Reason::PROTOCOL_ERROR));
1414+
malformed!("malformed headers: :status field on request");
14171415
}
14181416

14191417
// Convert the URI

tests/h2-support/src/frames.rs

Lines changed: 9 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -2,7 +2,7 @@ use std::convert::TryInto;
22
use std::fmt;
33

44
use bytes::Bytes;
5-
use http::{self, HeaderMap};
5+
use http::{self, HeaderMap, StatusCode};
66

77
use h2::frame::{self, Frame, StreamId};
88

@@ -162,6 +162,14 @@ impl Mock<frame::Headers> {
162162
Mock(frame)
163163
}
164164

165+
pub fn status(self, value: StatusCode) -> Self {
166+
let (id, mut pseudo, fields) = self.into_parts();
167+
168+
pseudo.set_status(value);
169+
170+
Mock(frame::Headers::new(id, pseudo, fields))
171+
}
172+
165173
pub fn scheme(self, value: &str) -> Self {
166174
let (id, mut pseudo, fields) = self.into_parts();
167175
let value = value.parse().unwrap();

tests/h2-tests/tests/server.rs

Lines changed: 24 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1025,6 +1025,30 @@ async fn server_error_on_unclean_shutdown() {
10251025
srv.await.expect_err("should error");
10261026
}
10271027

1028+
#[tokio::test]
1029+
async fn server_error_on_status_in_request() {
1030+
h2_support::trace_init!();
1031+
1032+
let (io, mut client) = mock::new();
1033+
1034+
let client = async move {
1035+
let settings = client.assert_server_handshake().await;
1036+
assert_default_settings!(settings);
1037+
client
1038+
.send_frame(frames::headers(1).status(StatusCode::OK))
1039+
.await;
1040+
client.recv_frame(frames::reset(1).protocol_error()).await;
1041+
};
1042+
1043+
let srv = async move {
1044+
let mut srv = server::handshake(io).await.expect("handshake");
1045+
1046+
assert!(srv.next().await.is_none());
1047+
};
1048+
1049+
join(client, srv).await;
1050+
}
1051+
10281052
#[tokio::test]
10291053
async fn request_without_authority() {
10301054
h2_support::trace_init!();

0 commit comments

Comments
 (0)