-
-
Notifications
You must be signed in to change notification settings - Fork 300
Open
Labels
Description
This method
Lines 830 to 922 in 6a75f23
fn load( | |
&mut self, | |
src: &mut BytesMut, | |
max_header_list_size: usize, | |
decoder: &mut hpack::Decoder, | |
) -> Result<(), Error> { | |
let mut reg = !self.fields.is_empty(); | |
let mut malformed = false; | |
let mut headers_size = self.calculate_header_list_size(); | |
macro_rules! set_pseudo { | |
($field:ident, $val:expr) => {{ | |
if reg { | |
tracing::trace!("load_hpack; header malformed -- pseudo not at head of block"); | |
malformed = true; | |
} else if self.pseudo.$field.is_some() { | |
tracing::trace!("load_hpack; header malformed -- repeated pseudo"); | |
malformed = true; | |
} else { | |
let __val = $val; | |
headers_size += | |
decoded_header_size(stringify!($field).len() + 1, __val.as_str().len()); | |
if headers_size < max_header_list_size { | |
self.pseudo.$field = Some(__val); | |
} else if !self.is_over_size { | |
tracing::trace!("load_hpack; header list size over max"); | |
self.is_over_size = true; | |
} | |
} | |
}}; | |
} | |
let mut cursor = Cursor::new(src); | |
// If the header frame is malformed, we still have to continue decoding | |
// the headers. A malformed header frame is a stream level error, but | |
// the hpack state is connection level. In order to maintain correct | |
// state for other streams, the hpack decoding process must complete. | |
let res = decoder.decode(&mut cursor, |header| { | |
use crate::hpack::Header::*; | |
match header { | |
Field { name, value } => { | |
// Connection level header fields are not supported and must | |
// result in a protocol error. | |
if name == header::CONNECTION | |
|| name == header::TRANSFER_ENCODING | |
|| name == header::UPGRADE | |
|| name == "keep-alive" | |
|| name == "proxy-connection" | |
{ | |
tracing::trace!("load_hpack; connection level header"); | |
malformed = true; | |
} else if name == header::TE && value != "trailers" { | |
tracing::trace!( | |
"load_hpack; TE header not set to trailers; val={:?}", | |
value | |
); | |
malformed = true; | |
} else { | |
reg = true; | |
headers_size += decoded_header_size(name.as_str().len(), value.len()); | |
if headers_size < max_header_list_size { | |
self.fields.append(name, value); | |
} else if !self.is_over_size { | |
tracing::trace!("load_hpack; header list size over max"); | |
self.is_over_size = true; | |
} | |
} | |
} | |
Authority(v) => set_pseudo!(authority, v), | |
Method(v) => set_pseudo!(method, v), | |
Scheme(v) => set_pseudo!(scheme, v), | |
Path(v) => set_pseudo!(path, v), | |
Protocol(v) => set_pseudo!(protocol, v), | |
Status(v) => set_pseudo!(status, v), | |
} | |
}); | |
if let Err(e) = res { | |
tracing::trace!("hpack decoding error; err={:?}", e); | |
return Err(e.into()); | |
} | |
if malformed { | |
tracing::trace!("malformed message"); | |
return Err(Error::MalformedMessage); | |
} | |
Ok(()) | |
} |
It's directly related to hyperium/http#603