11#![ deny( unsafe_op_in_unsafe_fn) ]
22
3+ use super :: err2io;
34use super :: fd:: WasiFd ;
45use crate :: convert:: TryFrom ;
56use crate :: fmt;
@@ -87,24 +88,24 @@ impl TcpStream {
8788 unsupported ( )
8889 }
8990
90- pub fn read ( & self , _ : & mut [ u8 ] ) -> io:: Result < usize > {
91- unsupported ( )
91+ pub fn read ( & self , buf : & mut [ u8 ] ) -> io:: Result < usize > {
92+ self . read_vectored ( & mut [ IoSliceMut :: new ( buf ) ] )
9293 }
9394
94- pub fn read_vectored ( & self , _ : & mut [ IoSliceMut < ' _ > ] ) -> io:: Result < usize > {
95- unsupported ( )
95+ pub fn read_vectored ( & self , bufs : & mut [ IoSliceMut < ' _ > ] ) -> io:: Result < usize > {
96+ self . socket ( ) . as_inner ( ) . read ( bufs )
9697 }
9798
9899 pub fn is_read_vectored ( & self ) -> bool {
99100 true
100101 }
101102
102- pub fn write ( & self , _ : & [ u8 ] ) -> io:: Result < usize > {
103- unsupported ( )
103+ pub fn write ( & self , buf : & [ u8 ] ) -> io:: Result < usize > {
104+ self . write_vectored ( & [ IoSlice :: new ( buf ) ] )
104105 }
105106
106- pub fn write_vectored ( & self , _ : & [ IoSlice < ' _ > ] ) -> io:: Result < usize > {
107- unsupported ( )
107+ pub fn write_vectored ( & self , bufs : & [ IoSlice < ' _ > ] ) -> io:: Result < usize > {
108+ self . socket ( ) . as_inner ( ) . write ( bufs )
108109 }
109110
110111 pub fn is_write_vectored ( & self ) -> bool {
@@ -155,8 +156,23 @@ impl TcpStream {
155156 unsupported ( )
156157 }
157158
158- pub fn set_nonblocking ( & self , _: bool ) -> io:: Result < ( ) > {
159- unsupported ( )
159+ pub fn set_nonblocking ( & self , state : bool ) -> io:: Result < ( ) > {
160+ let fdstat = unsafe {
161+ wasi:: fd_fdstat_get ( self . socket ( ) . as_inner ( ) . as_raw_fd ( ) as wasi:: Fd ) . map_err ( err2io) ?
162+ } ;
163+
164+ let mut flags = fdstat. fs_flags ;
165+
166+ if state {
167+ flags |= wasi:: FDFLAGS_NONBLOCK ;
168+ } else {
169+ flags &= !wasi:: FDFLAGS_NONBLOCK ;
170+ }
171+
172+ unsafe {
173+ wasi:: fd_fdstat_set_flags ( self . socket ( ) . as_inner ( ) . as_raw_fd ( ) as wasi:: Fd , flags)
174+ . map_err ( err2io)
175+ }
160176 }
161177
162178 pub fn socket ( & self ) -> & Socket {
@@ -194,7 +210,16 @@ impl TcpListener {
194210 }
195211
196212 pub fn accept ( & self ) -> io:: Result < ( TcpStream , SocketAddr ) > {
197- unsupported ( )
213+ let fd = unsafe {
214+ wasi:: sock_accept ( self . as_inner ( ) . as_inner ( ) . as_raw_fd ( ) as _ , 0 ) . map_err ( err2io) ?
215+ } ;
216+
217+ Ok ( (
218+ TcpStream :: from_inner ( unsafe { Socket :: from_raw_fd ( fd as _ ) } ) ,
219+ // WASI has no concept of SocketAddr yet
220+ // return an unspecified IPv4Addr
221+ SocketAddr :: new ( Ipv4Addr :: UNSPECIFIED . into ( ) , 0 ) ,
222+ ) )
198223 }
199224
200225 pub fn duplicate ( & self ) -> io:: Result < TcpListener > {
@@ -221,8 +246,23 @@ impl TcpListener {
221246 unsupported ( )
222247 }
223248
224- pub fn set_nonblocking ( & self , _: bool ) -> io:: Result < ( ) > {
225- unsupported ( )
249+ pub fn set_nonblocking ( & self , state : bool ) -> io:: Result < ( ) > {
250+ let fdstat = unsafe {
251+ wasi:: fd_fdstat_get ( self . socket ( ) . as_inner ( ) . as_raw_fd ( ) as wasi:: Fd ) . map_err ( err2io) ?
252+ } ;
253+
254+ let mut flags = fdstat. fs_flags ;
255+
256+ if state {
257+ flags |= wasi:: FDFLAGS_NONBLOCK ;
258+ } else {
259+ flags &= !wasi:: FDFLAGS_NONBLOCK ;
260+ }
261+
262+ unsafe {
263+ wasi:: fd_fdstat_set_flags ( self . socket ( ) . as_inner ( ) . as_raw_fd ( ) as wasi:: Fd , flags)
264+ . map_err ( err2io)
265+ }
226266 }
227267
228268 pub fn socket ( & self ) -> & Socket {
0 commit comments