use {hpack, ConnectionError}; use frame::{self, Frame, Kind}; use frame::DEFAULT_SETTINGS_HEADER_TABLE_SIZE; use tokio_io::AsyncWrite; use futures::*; use bytes::{Bytes, BytesMut, Buf}; use std::io::{self, Write}; pub struct FramedRead { inner: T, // hpack decoder state hpack: hpack::Decoder, } impl FramedRead where T: Stream, T: AsyncWrite, { pub fn new(inner: T) -> FramedRead { FramedRead { inner: inner, hpack: hpack::Decoder::new(DEFAULT_SETTINGS_HEADER_TABLE_SIZE), } } } impl FramedRead { fn decode_frame(&mut self, mut bytes: Bytes) -> Result, ConnectionError> { // Parse the head let head = frame::Head::parse(&bytes); let frame = match head.kind() { Kind::Data => unimplemented!(), Kind::Headers => unimplemented!(), Kind::Priority => unimplemented!(), Kind::Reset => unimplemented!(), Kind::Settings => { let frame = try!(frame::Settings::load(head, &bytes[frame::HEADER_LEN..])); frame.into() } Kind::PushPromise => unimplemented!(), Kind::Ping => unimplemented!(), Kind::GoAway => unimplemented!(), Kind::WindowUpdate => unimplemented!(), Kind::Continuation => unimplemented!(), Kind::Unknown => return Ok(None), }; Ok(Some(frame)) } } impl Stream for FramedRead where T: Stream, { type Item = Frame; type Error = ConnectionError; fn poll(&mut self) -> Poll, ConnectionError> { loop { let mut bytes = match try_ready!(self.inner.poll()) { Some(bytes) => bytes.freeze(), None => return Ok(Async::Ready(None)), }; if let Some(frame) = try!(self.decode_frame(bytes)) { return Ok(Async::Ready(Some(frame))); } } } } impl Sink for FramedRead { type SinkItem = T::SinkItem; type SinkError = T::SinkError; fn start_send(&mut self, item: T::SinkItem) -> StartSend { self.inner.start_send(item) } fn poll_complete(&mut self) -> Poll<(), T::SinkError> { self.inner.poll_complete() } } impl io::Write for FramedRead { fn write(&mut self, src: &[u8]) -> io::Result { self.inner.write(src) } fn flush(&mut self) -> io::Result<()> { self.inner.flush() } } impl AsyncWrite for FramedRead { fn shutdown(&mut self) -> Poll<(), io::Error> { self.inner.shutdown() } fn write_buf(&mut self, buf: &mut B) -> Poll { self.inner.write_buf(buf) } }