From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: Received: from firstgate.proxmox.com (firstgate.proxmox.com [212.224.123.68]) (using TLSv1.3 with cipher TLS_AES_256_GCM_SHA384 (256/256 bits) key-exchange X25519 server-signature RSA-PSS (2048 bits)) (No client certificate requested) by lists.proxmox.com (Postfix) with ESMTPS id 08D3462E2D for ; Tue, 14 Jul 2020 13:10:33 +0200 (CEST) Received: from firstgate.proxmox.com (localhost [127.0.0.1]) by firstgate.proxmox.com (Proxmox) with ESMTP id 0035E261A7 for ; Tue, 14 Jul 2020 13:10:03 +0200 (CEST) Received: from proxmox-new.maurer-it.com (proxmox-new.maurer-it.com [212.186.127.180]) (using TLSv1.3 with cipher TLS_AES_256_GCM_SHA384 (256/256 bits) key-exchange X25519 server-signature RSA-PSS (2048 bits)) (No client certificate requested) by firstgate.proxmox.com (Proxmox) with ESMTPS id CC50A26144 for ; Tue, 14 Jul 2020 13:09:58 +0200 (CEST) Received: from proxmox-new.maurer-it.com (localhost.localdomain [127.0.0.1]) by proxmox-new.maurer-it.com (Proxmox) with ESMTP id 99A6D44200 for ; Tue, 14 Jul 2020 13:09:58 +0200 (CEST) From: Dominik Csapak To: pbs-devel@lists.proxmox.com Date: Tue, 14 Jul 2020 13:09:53 +0200 Message-Id: <20200714110957.31884-6-d.csapak@proxmox.com> X-Mailer: git-send-email 2.20.1 In-Reply-To: <20200714110957.31884-1-d.csapak@proxmox.com> References: <20200714110957.31884-1-d.csapak@proxmox.com> MIME-Version: 1.0 Content-Transfer-Encoding: 8bit X-SPAM-LEVEL: Spam detection results: 0 KAM_DMARC_STATUS 0.01 Test Rule for DKIM or SPF Failure with Strict Alignment KAM_LAZY_DOMAIN_SECURITY 1 Sending domain does not have any anti-forgery methods NO_DNS_FOR_FROM 0.379 Envelope sender has no MX or A DNS records RCVD_IN_DNSWL_MED -2.3 Sender listed at https://www.dnswl.org/, medium trust SPF_HELO_NONE 0.001 SPF: HELO does not publish an SPF Record SPF_NONE 0.001 SPF: sender does not publish an SPF Record URIBL_BLOCKED 0.001 ADMINISTRATOR NOTICE: The query to URIBL was blocked. See http://wiki.apache.org/spamassassin/DnsBlocklists#dnsbl-block for more information. [websocket.rs] Subject: [pbs-devel] [PATCH proxmox 5/9] proxmox/tools/websocket: use io::Error and Result explicitely X-BeenThere: pbs-devel@lists.proxmox.com X-Mailman-Version: 2.1.29 Precedence: list List-Id: Proxmox Backup Server development discussion List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , X-List-Received-Date: Tue, 14 Jul 2020 11:10:33 -0000 and add a helper struct for the ReadResult (so that the types are properly documented) Signed-off-by: Dominik Csapak --- proxmox/src/tools/websocket.rs | 46 ++++++++++++++++++++-------------- 1 file changed, 27 insertions(+), 19 deletions(-) diff --git a/proxmox/src/tools/websocket.rs b/proxmox/src/tools/websocket.rs index d59b7ad..078225a 100644 --- a/proxmox/src/tools/websocket.rs +++ b/proxmox/src/tools/websocket.rs @@ -7,14 +7,16 @@ use std::pin::Pin; use std::task::{Context, Poll}; use std::cmp::min; -use std::io::{self, Error, ErrorKind}; +use std::io::{self, ErrorKind}; use std::future::Future; use tokio::io::{AsyncWrite, AsyncRead, AsyncReadExt}; +use anyhow::{bail, format_err, Error}; use futures::future::FutureExt; use futures::ready; +use crate::io_format_err; use crate::tools::byte_buffer::ByteBuffer; #[repr(u8)] @@ -129,7 +131,7 @@ pub fn create_frame( let first_byte = 0b10000000 | (frametype as u8); let len = data.len(); if (frametype as u8) & 0b00001000 > 0 && len > 125 { - return Err(Error::new( + return Err(io::Error::new( ErrorKind::InvalidData, "Control frames cannot have data longer than 125 bytes", )); @@ -200,7 +202,7 @@ impl AsyncWrite for WebSocketWriter { self: Pin<&mut Self>, cx: &mut Context, buf: &[u8], - ) -> Poll> { + ) -> Poll> { let this = Pin::get_mut(self); let frametype = match this.text { @@ -233,18 +235,18 @@ impl AsyncWrite for WebSocketWriter { }, Err(err) => { eprintln!("error in writer: {}", err); - return Poll::Ready(Err(Error::new(ErrorKind::Other, err))) + return Poll::Ready(Err(err)) }, } } } - fn poll_flush(self: Pin<&mut Self>, cx: &mut Context) -> Poll> { + fn poll_flush(self: Pin<&mut Self>, cx: &mut Context) -> Poll> { let this = Pin::get_mut(self); Pin::new(&mut this.writer).poll_flush(cx) } - fn poll_shutdown(self: Pin<&mut Self>, cx: &mut Context) -> Poll> { + fn poll_shutdown(self: Pin<&mut Self>, cx: &mut Context) -> Poll> { let this = Pin::get_mut(self); Pin::new(&mut this.writer).poll_shutdown(cx) } @@ -303,7 +305,7 @@ impl FrameHeader { /// # Ok(()) /// # } /// ``` - pub fn try_from_bytes(data: &[u8]) -> Result, Error> { + pub fn try_from_bytes(data: &[u8]) -> io::Result> { let len = data.len(); if len < 2 { return Ok(Err(2 - len)); @@ -313,7 +315,7 @@ impl FrameHeader { // we do not support extensions if data[0] & 0b01110000 > 0 { - return Err(Error::new( + return Err(io::Error::new( ErrorKind::InvalidData, "Extensions not supported", )); @@ -328,12 +330,12 @@ impl FrameHeader { 9 => OpCode::Ping, 10 => OpCode::Pong, other => { - return Err(Error::new(ErrorKind::InvalidData, format!("Unknown OpCode {}", other))); + return Err(io::Error::new(ErrorKind::InvalidData, format!("Unknown OpCode {}", other))); } }; if !fin && frametype.is_control() { - return Err(Error::new( + return Err(io::Error::new( ErrorKind::InvalidData, "Control frames cannot be fragmented", )); @@ -366,7 +368,7 @@ impl FrameHeader { } if payload_len > 125 && frametype.is_control() { - return Err(Error::new( + return Err(io::Error::new( ErrorKind::InvalidData, "Control frames cannot carry more than 125 bytes of data", )); @@ -430,9 +432,15 @@ impl WebSocketReader { } } +struct ReadResult { + len: usize, + reader: R, + buffer: ByteBuffer, +} + enum ReaderState { NoData, - WaitingForData(Pin> + Send + 'static>>), + WaitingForData(Pin>> + Send + 'static>>), HaveData, } @@ -443,7 +451,7 @@ impl AsyncRead for WebSocketReader self: Pin<&mut Self>, cx: &mut Context, buf: &mut [u8], - ) -> Poll> { + ) -> Poll> { let this = Pin::get_mut(self); let mut offset = 0; @@ -452,25 +460,25 @@ impl AsyncRead for WebSocketReader ReaderState::NoData => { let mut reader = match this.reader.take() { Some(reader) => reader, - None => return Poll::Ready(Err(Error::new(ErrorKind::Other, "no reader"))), + None => return Poll::Ready(Err(io_format_err!("no reader"))), }; let mut buffer = match this.read_buffer.take() { Some(buffer) => buffer, - None => return Poll::Ready(Err(Error::new(ErrorKind::Other, "no buffer"))), + None => return Poll::Ready(Err(io_format_err!("no buffer"))), }; let future = async move { buffer.read_from_async(&mut reader) .await - .map(move |len| (len, reader, buffer)) + .map(move |len| ReadResult { len, reader, buffer }) }; this.state = ReaderState::WaitingForData(future.boxed()); }, ReaderState::WaitingForData(ref mut future) => { match ready!(future.as_mut().poll(cx)) { - Ok((len, reader, buffer)) => { + Ok(ReadResult { len, reader, buffer }) => { this.reader = Some(reader); this.read_buffer = Some(buffer); this.state = ReaderState::HaveData; @@ -478,13 +486,13 @@ impl AsyncRead for WebSocketReader return Poll::Ready(Ok(0)); } }, - Err(err) => return Poll::Ready(Err(Error::new(ErrorKind::Other, err))), + Err(err) => return Poll::Ready(Err(err)), } }, ReaderState::HaveData => { let mut read_buffer = match this.read_buffer.take() { Some(read_buffer) => read_buffer, - None => return Poll::Ready(Err(Error::new(ErrorKind::Other, "no buffer"))), + None => return Poll::Ready(Err(io_format_err!("no buffer"))), }; let mut header = match this.header.take() { -- 2.20.1