Skip to content

Commit 87d08f0

Browse files
taiki-ecramertj
authored andcommitted
impl traits for more pinned pointers and ?Sized types
1 parent 6dc39b0 commit 87d08f0

File tree

7 files changed

+115
-58
lines changed

7 files changed

+115
-58
lines changed

futures-core/src/future/mod.rs

Lines changed: 28 additions & 29 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,6 @@
11
//! Futures.
22
3+
use core::ops::DerefMut;
34
use core::pin::Pin;
45
use core::task::{Context, Poll};
56

@@ -21,40 +22,19 @@ pub trait FusedFuture {
2122
fn is_terminated(&self) -> bool;
2223
}
2324

24-
impl<F: FusedFuture> FusedFuture for Pin<&mut F> {
25-
fn is_terminated(&self) -> bool {
26-
<F as FusedFuture>::is_terminated(&**self)
27-
}
28-
}
29-
3025
impl<F: FusedFuture + ?Sized> FusedFuture for &mut F {
3126
fn is_terminated(&self) -> bool {
3227
<F as FusedFuture>::is_terminated(&**self)
3328
}
3429
}
3530

36-
#[cfg(feature = "alloc")]
37-
mod if_alloc {
38-
use alloc::boxed::Box;
39-
use super::*;
40-
41-
impl<F: FusedFuture + ?Sized> FusedFuture for Box<F> {
42-
fn is_terminated(&self) -> bool {
43-
<F as FusedFuture>::is_terminated(&**self)
44-
}
45-
}
46-
47-
impl<F: FusedFuture + ?Sized> FusedFuture for Pin<Box<F>> {
48-
fn is_terminated(&self) -> bool {
49-
<F as FusedFuture>::is_terminated(&**self)
50-
}
51-
}
52-
53-
#[cfg(feature = "std")]
54-
impl<F: FusedFuture> FusedFuture for std::panic::AssertUnwindSafe<F> {
55-
fn is_terminated(&self) -> bool {
56-
<F as FusedFuture>::is_terminated(&**self)
57-
}
31+
impl<P> FusedFuture for Pin<P>
32+
where
33+
P: DerefMut + Unpin,
34+
P::Target: FusedFuture,
35+
{
36+
fn is_terminated(&self) -> bool {
37+
<P::Target as FusedFuture>::is_terminated(&**self)
5838
}
5939
}
6040

@@ -79,7 +59,7 @@ pub trait TryFuture {
7959
}
8060

8161
impl<F, T, E> TryFuture for F
82-
where F: Future<Output = Result<T, E>>
62+
where F: ?Sized + Future<Output = Result<T, E>>
8363
{
8464
type Ok = T;
8565
type Error = E;
@@ -89,3 +69,22 @@ impl<F, T, E> TryFuture for F
8969
self.poll(cx)
9070
}
9171
}
72+
73+
#[cfg(feature = "alloc")]
74+
mod if_alloc {
75+
use alloc::boxed::Box;
76+
use super::*;
77+
78+
impl<F: FusedFuture + ?Sized> FusedFuture for Box<F> {
79+
fn is_terminated(&self) -> bool {
80+
<F as FusedFuture>::is_terminated(&**self)
81+
}
82+
}
83+
84+
#[cfg(feature = "std")]
85+
impl<F: FusedFuture> FusedFuture for std::panic::AssertUnwindSafe<F> {
86+
fn is_terminated(&self) -> bool {
87+
<F as FusedFuture>::is_terminated(&**self)
88+
}
89+
}
90+
}

futures-core/src/stream/mod.rs

Lines changed: 25 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
//! Asynchronous streams.
22
3-
use core::ops;
3+
use core::ops::DerefMut;
44
use core::pin::Pin;
55
use core::task::{Context, Poll};
66

@@ -68,7 +68,7 @@ impl<S: ?Sized + Stream + Unpin> Stream for &mut S {
6868

6969
impl<P> Stream for Pin<P>
7070
where
71-
P: ops::DerefMut + Unpin,
71+
P: DerefMut + Unpin,
7272
P::Target: Stream,
7373
{
7474
type Item = <P::Target as Stream>::Item;
@@ -94,6 +94,22 @@ pub trait FusedStream {
9494
fn is_terminated(&self) -> bool;
9595
}
9696

97+
impl<F: ?Sized + FusedStream> FusedStream for &mut F {
98+
fn is_terminated(&self) -> bool {
99+
<F as FusedStream>::is_terminated(&**self)
100+
}
101+
}
102+
103+
impl<P> FusedStream for Pin<P>
104+
where
105+
P: DerefMut + Unpin,
106+
P::Target: FusedStream,
107+
{
108+
fn is_terminated(&self) -> bool {
109+
<P::Target as FusedStream>::is_terminated(&**self)
110+
}
111+
}
112+
97113
/// A convenience for streams that return `Result` values that includes
98114
/// a variety of adapters tailored to such futures.
99115
pub trait TryStream {
@@ -113,7 +129,7 @@ pub trait TryStream {
113129
}
114130

115131
impl<S, T, E> TryStream for S
116-
where S: Stream<Item = Result<T, E>>
132+
where S: ?Sized + Stream<Item = Result<T, E>>
117133
{
118134
type Ok = T;
119135
type Error = E;
@@ -163,4 +179,10 @@ mod if_alloc {
163179
Poll::Ready(self.pop_front())
164180
}
165181
}
182+
183+
impl<S: ?Sized + FusedStream> FusedStream for Box<S> {
184+
fn is_terminated(&self) -> bool {
185+
<S as FusedStream>::is_terminated(&**self)
186+
}
187+
}
166188
}

futures-core/src/task/spawn.rs

Lines changed: 22 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -78,6 +78,28 @@ impl SpawnError {
7878
}
7979
}
8080

81+
impl<Sp: ?Sized + Spawn> Spawn for &mut Sp {
82+
fn spawn_obj(&mut self, future: FutureObj<'static, ()>)
83+
-> Result<(), SpawnError> {
84+
Sp::spawn_obj(self, future)
85+
}
86+
87+
fn status(&self) -> Result<(), SpawnError> {
88+
Sp::status(self)
89+
}
90+
}
91+
92+
impl<Sp: ?Sized + LocalSpawn> LocalSpawn for &mut Sp {
93+
fn spawn_local_obj(&mut self, future: LocalFutureObj<'static, ()>)
94+
-> Result<(), SpawnError> {
95+
Sp::spawn_local_obj(self, future)
96+
}
97+
98+
fn status_local(&self) -> Result<(), SpawnError> {
99+
Sp::status_local(self)
100+
}
101+
}
102+
81103
#[cfg(feature = "alloc")]
82104
mod if_alloc {
83105
use alloc::boxed::Box;

futures-io/src/lib.rs

Lines changed: 23 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -18,6 +18,7 @@ mod if_std {
1818
use std::boxed::Box;
1919
use std::cmp;
2020
use std::io as StdIo;
21+
use std::ops::DerefMut;
2122
use std::pin::Pin;
2223
use std::ptr;
2324

@@ -270,21 +271,25 @@ mod if_std {
270271
deref_async_read!();
271272
}
272273

273-
impl<T: ?Sized + AsyncRead> AsyncRead for Pin<&mut T> {
274+
impl<P> AsyncRead for Pin<P>
275+
where
276+
P: DerefMut + Unpin,
277+
P::Target: AsyncRead,
278+
{
274279
unsafe fn initializer(&self) -> Initializer {
275280
(**self).initializer()
276281
}
277282

278-
fn poll_read(mut self: Pin<&mut Self>, cx: &mut Context<'_>, buf: &mut [u8])
283+
fn poll_read(self: Pin<&mut Self>, cx: &mut Context<'_>, buf: &mut [u8])
279284
-> Poll<Result<usize>>
280285
{
281-
T::poll_read((*self).as_mut(), cx, buf)
286+
Pin::get_mut(self).as_mut().poll_read(cx, buf)
282287
}
283288

284-
fn poll_vectored_read(mut self: Pin<&mut Self>, cx: &mut Context<'_>, vec: &mut [&mut IoVec])
289+
fn poll_vectored_read(self: Pin<&mut Self>, cx: &mut Context<'_>, vec: &mut [&mut IoVec])
285290
-> Poll<Result<usize>>
286291
{
287-
T::poll_vectored_read((*self).as_mut(), cx, vec)
292+
Pin::get_mut(self).as_mut().poll_vectored_read(cx, vec)
288293
}
289294
}
290295

@@ -348,25 +353,29 @@ mod if_std {
348353
deref_async_write!();
349354
}
350355

351-
impl<T: ?Sized + AsyncWrite> AsyncWrite for Pin<&mut T> {
352-
fn poll_write(mut self: Pin<&mut Self>, cx: &mut Context<'_>, buf: &[u8])
356+
impl<P> AsyncWrite for Pin<P>
357+
where
358+
P: DerefMut + Unpin,
359+
P::Target: AsyncWrite,
360+
{
361+
fn poll_write(self: Pin<&mut Self>, cx: &mut Context<'_>, buf: &[u8])
353362
-> Poll<Result<usize>>
354363
{
355-
T::poll_write((*self).as_mut(), cx, buf)
364+
Pin::get_mut(self).as_mut().poll_write(cx, buf)
356365
}
357366

358-
fn poll_vectored_write(mut self: Pin<&mut Self>, cx: &mut Context<'_>, vec: &[&IoVec])
367+
fn poll_vectored_write(self: Pin<&mut Self>, cx: &mut Context<'_>, vec: &[&IoVec])
359368
-> Poll<Result<usize>>
360369
{
361-
T::poll_vectored_write((*self).as_mut(), cx, vec)
370+
Pin::get_mut(self).as_mut().poll_vectored_write(cx, vec)
362371
}
363372

364-
fn poll_flush(mut self: Pin<&mut Self>, cx: &mut Context<'_>) -> Poll<Result<()>> {
365-
T::poll_flush((*self).as_mut(), cx)
373+
fn poll_flush(self: Pin<&mut Self>, cx: &mut Context<'_>) -> Poll<Result<()>> {
374+
Pin::get_mut(self).as_mut().poll_flush(cx)
366375
}
367376

368-
fn poll_close(mut self: Pin<&mut Self>, cx: &mut Context<'_>) -> Poll<Result<()>> {
369-
T::poll_close((*self).as_mut(), cx)
377+
fn poll_close(self: Pin<&mut Self>, cx: &mut Context<'_>) -> Poll<Result<()>> {
378+
Pin::get_mut(self).as_mut().poll_close(cx)
370379
}
371380
}
372381

futures-sink/src/lib.rs

Lines changed: 15 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -13,6 +13,7 @@
1313
extern crate alloc;
1414

1515
use futures_core::task::{Context, Poll};
16+
use core::ops::DerefMut;
1617
use core::pin::Pin;
1718

1819
/// A `Sink` is a value into which other values can be sent, asynchronously.
@@ -130,23 +131,27 @@ impl<S: ?Sized + Sink<Item> + Unpin, Item> Sink<Item> for &mut S {
130131
}
131132
}
132133

133-
impl<S: ?Sized + Sink<Item>, Item> Sink<Item> for Pin<&mut S> {
134-
type SinkError = S::SinkError;
134+
impl<P, Item> Sink<Item> for Pin<P>
135+
where
136+
P: DerefMut + Unpin,
137+
P::Target: Sink<Item>,
138+
{
139+
type SinkError = <P::Target as Sink<Item>>::SinkError;
135140

136-
fn poll_ready(mut self: Pin<&mut Self>, cx: &mut Context<'_>) -> Poll<Result<(), Self::SinkError>> {
137-
S::poll_ready((*self).as_mut(), cx)
141+
fn poll_ready(self: Pin<&mut Self>, cx: &mut Context<'_>) -> Poll<Result<(), Self::SinkError>> {
142+
Pin::get_mut(self).as_mut().poll_ready(cx)
138143
}
139144

140-
fn start_send(mut self: Pin<&mut Self>, item: Item) -> Result<(), Self::SinkError> {
141-
S::start_send((*self).as_mut(), item)
145+
fn start_send(self: Pin<&mut Self>, item: Item) -> Result<(), Self::SinkError> {
146+
Pin::get_mut(self).as_mut().start_send(item)
142147
}
143148

144-
fn poll_flush(mut self: Pin<&mut Self>, cx: &mut Context<'_>) -> Poll<Result<(), Self::SinkError>> {
145-
S::poll_flush((*self).as_mut(), cx)
149+
fn poll_flush(self: Pin<&mut Self>, cx: &mut Context<'_>) -> Poll<Result<(), Self::SinkError>> {
150+
Pin::get_mut(self).as_mut().poll_flush(cx)
146151
}
147152

148-
fn poll_close(mut self: Pin<&mut Self>, cx: &mut Context<'_>) -> Poll<Result<(), Self::SinkError>> {
149-
S::poll_close((*self).as_mut(), cx)
153+
fn poll_close(self: Pin<&mut Self>, cx: &mut Context<'_>) -> Poll<Result<(), Self::SinkError>> {
154+
Pin::get_mut(self).as_mut().poll_close(cx)
150155
}
151156
}
152157

futures-util/src/try_future/mod.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -62,7 +62,7 @@ pub use self::unwrap_or_else::UnwrapOrElse;
6262
mod try_chain;
6363
pub(crate) use self::try_chain::{TryChain, TryChainAction};
6464

65-
impl<Fut: TryFuture> TryFutureExt for Fut {}
65+
impl<Fut: ?Sized + TryFuture> TryFutureExt for Fut {}
6666

6767
/// Adapters specific to [`Result`]-returning futures
6868
pub trait TryFutureExt: TryFuture {

futures-util/src/try_stream/mod.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -69,7 +69,7 @@ mod into_async_read;
6969
#[cfg(feature = "std")]
7070
pub use self::into_async_read::IntoAsyncRead;
7171

72-
impl<S: TryStream> TryStreamExt for S {}
72+
impl<S: ?Sized + TryStream> TryStreamExt for S {}
7373

7474
/// Adapters specific to `Result`-returning streams
7575
pub trait TryStreamExt: TryStream {

0 commit comments

Comments
 (0)