mirror of
https://github.com/tokio-rs/tokio.git
synced 2026-09-09 00:00:08 +02:00
Compare commits
12
Commits
tokio-1.5.0
...
v0.2.x
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
2afa276c8c | ||
|
|
312c981e3f | ||
|
|
62e24b710c | ||
|
|
dccc58aa37 | ||
|
|
95b943506b | ||
|
|
3d17488d9a | ||
|
|
c63057ebc5 | ||
|
|
1016de28fc | ||
|
|
d2ad49aa6e | ||
|
|
85d8029e9b | ||
|
|
b69d4a6108 | ||
|
|
a517dbf605 |
+36
-14
@@ -25,7 +25,7 @@ jobs:
|
||||
- features
|
||||
- minrust
|
||||
- fmt
|
||||
- clippy
|
||||
# - clippy
|
||||
- docs
|
||||
- loom
|
||||
steps:
|
||||
@@ -171,6 +171,26 @@ jobs:
|
||||
- name: "test --workspace --all-features"
|
||||
run: cargo check --workspace --all-features
|
||||
|
||||
minimal-versions:
|
||||
name: minimal-versions
|
||||
runs-on: ubuntu-latest
|
||||
steps:
|
||||
- uses: actions/checkout@v2
|
||||
- uses: actions-rs/toolchain@v1
|
||||
with:
|
||||
toolchain: ${{ env.nightly }}
|
||||
override: true
|
||||
- name: Install cargo-hack
|
||||
run: cargo install cargo-hack
|
||||
- name: "check --all-features -Z minimal-versions"
|
||||
run: |
|
||||
# Remove dev-dependencies from Cargo.toml to prevent the next `cargo update`
|
||||
# from determining minimal versions based on dev-dependencies.
|
||||
cargo hack --remove-dev-deps --workspace
|
||||
# Update Cargo.lock to minimal version dependencies.
|
||||
cargo update -Z minimal-versions
|
||||
cargo check --all-features
|
||||
|
||||
fmt:
|
||||
name: fmt
|
||||
runs-on: ubuntu-latest
|
||||
@@ -190,19 +210,21 @@ jobs:
|
||||
exit 1
|
||||
fi
|
||||
|
||||
clippy:
|
||||
name: clippy
|
||||
runs-on: ubuntu-latest
|
||||
steps:
|
||||
- uses: actions/checkout@v2
|
||||
- name: Install Rust
|
||||
run: rustup update stable
|
||||
- name: Install clippy
|
||||
run: rustup component add clippy
|
||||
|
||||
# Run clippy
|
||||
- name: "clippy --all"
|
||||
run: cargo clippy --all --tests
|
||||
# This branch no longer actively developed. Most commits to this
|
||||
# branch are backporting and should not be blocked by clippy.
|
||||
# clippy:
|
||||
# name: clippy
|
||||
# runs-on: ubuntu-latest
|
||||
# steps:
|
||||
# - uses: actions/checkout@v2
|
||||
# - name: Install Rust
|
||||
# run: rustup update stable
|
||||
# - name: Install clippy
|
||||
# run: rustup component add clippy
|
||||
#
|
||||
# # Run clippy
|
||||
# - name: "clippy --all"
|
||||
# run: cargo clippy --all --tests
|
||||
|
||||
docs:
|
||||
name: docs
|
||||
|
||||
@@ -1,9 +1,17 @@
|
||||
# 0.2.5 (February 27, 2019)
|
||||
# 0.2.6 (November 11, 2020)
|
||||
|
||||
### Changes
|
||||
|
||||
- disambiguate the built-in `#[test]` attribute in macro expansion ([#2503])
|
||||
- warn about renaming the Tokio dependency ([#2521])
|
||||
- various documentation changes ([#2683], [#2697])
|
||||
|
||||
# 0.2.5 (February 27, 2020)
|
||||
|
||||
### Fixed
|
||||
- doc improvements ([#2225]).
|
||||
|
||||
# 0.2.4 (January 27, 2019)
|
||||
# 0.2.4 (January 27, 2020)
|
||||
|
||||
### Fixed
|
||||
- generics on `#[tokio::main]` function ([#2177]).
|
||||
@@ -11,12 +19,12 @@
|
||||
### Added
|
||||
- support for `tokio::select!` ([#2152]).
|
||||
|
||||
# 0.2.3 (January 7, 2019)
|
||||
# 0.2.3 (January 7, 2020)
|
||||
|
||||
### Fixed
|
||||
- Revert breaking change.
|
||||
|
||||
# 0.2.2 (January 7, 2019)
|
||||
# 0.2.2 (January 7, 2020)
|
||||
|
||||
### Added
|
||||
- General refactoring and inclusion of additional runtime options ([#2022] and [#2038])
|
||||
@@ -30,6 +38,10 @@
|
||||
|
||||
- Initial release
|
||||
|
||||
[#2697]: https://github.com/tokio-rs/tokio/pull/2697
|
||||
[#2683]: https://github.com/tokio-rs/tokio/pull/2683
|
||||
[#2521]: https://github.com/tokio-rs/tokio/pull/2521
|
||||
[#2503]: https://github.com/tokio-rs/tokio/pull/2503
|
||||
[#2225]: https://github.com/tokio-rs/tokio/pull/2225
|
||||
[#2177]: https://github.com/tokio-rs/tokio/pull/2177
|
||||
[#2152]: https://github.com/tokio-rs/tokio/pull/2152
|
||||
|
||||
@@ -6,14 +6,14 @@ name = "tokio-macros"
|
||||
# - Update doc url
|
||||
# - Cargo.toml
|
||||
# - Update CHANGELOG.md.
|
||||
# - Create "v0.1.x" git tag.
|
||||
version = "0.2.5"
|
||||
# - Create "v0.2.x" git tag.
|
||||
version = "0.2.6"
|
||||
edition = "2018"
|
||||
authors = ["Tokio Contributors <[email protected]>"]
|
||||
license = "MIT"
|
||||
repository = "https://github.com/tokio-rs/tokio"
|
||||
homepage = "https://tokio.rs"
|
||||
documentation = "https://docs.rs/tokio-macros/0.2.5/tokio_macros"
|
||||
documentation = "https://docs.rs/tokio-macros/0.2.6/tokio_macros"
|
||||
description = """
|
||||
Tokio's proc macros.
|
||||
"""
|
||||
|
||||
@@ -1,3 +1,5 @@
|
||||
#![allow(clippy::unnecessary_lazy_evaluations)]
|
||||
|
||||
use proc_macro::TokenStream;
|
||||
use quote::quote;
|
||||
use std::num::NonZeroUsize;
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
#![doc(html_root_url = "https://docs.rs/tokio-macros/0.2.5")]
|
||||
#![doc(html_root_url = "https://docs.rs/tokio-macros/0.2.6")]
|
||||
#![allow(clippy::needless_doctest_main)]
|
||||
#![warn(
|
||||
missing_debug_implementations,
|
||||
|
||||
@@ -29,6 +29,7 @@ full = ["codec", "udp", "compat"]
|
||||
compat = ["futures-io",]
|
||||
codec = ["tokio/stream"]
|
||||
udp = ["tokio/udp"]
|
||||
rt = ["tokio/rt-core"]
|
||||
|
||||
[dependencies]
|
||||
tokio = { version = "0.2.5", path = "../tokio" }
|
||||
@@ -37,7 +38,7 @@ bytes = "0.5.0"
|
||||
futures-core = "0.3.0"
|
||||
futures-sink = "0.3.0"
|
||||
futures-io = { version = "0.3.0", optional = true }
|
||||
log = "0.4"
|
||||
log = "0.4.6"
|
||||
pin-project-lite = "0.1.4"
|
||||
|
||||
[dev-dependencies]
|
||||
|
||||
@@ -18,6 +18,16 @@ macro_rules! cfg_compat {
|
||||
}
|
||||
}
|
||||
|
||||
macro_rules! cfg_rt {
|
||||
($($item:item)*) => {
|
||||
$(
|
||||
#[cfg(feature = "rt")]
|
||||
#[cfg_attr(docsrs, doc(cfg(feature = "rt")))]
|
||||
$item
|
||||
)*
|
||||
}
|
||||
}
|
||||
|
||||
macro_rules! cfg_udp {
|
||||
($($item:item)*) => {
|
||||
$(
|
||||
|
||||
@@ -0,0 +1,78 @@
|
||||
//! Tokio context aware futures utilities.
|
||||
//!
|
||||
//! This module includes utilities around integrating tokio with other runtimes
|
||||
//! by allowing the context to be attached to futures. This allows spawning
|
||||
//! futures on other executors while still using tokio to drive them. This
|
||||
//! can be useful if you need to use a tokio based library in an executor/runtime
|
||||
//! that does not provide a tokio context.
|
||||
|
||||
use pin_project_lite::pin_project;
|
||||
use std::{
|
||||
future::Future,
|
||||
pin::Pin,
|
||||
task::{Context, Poll},
|
||||
};
|
||||
use tokio::runtime::Handle;
|
||||
|
||||
pin_project! {
|
||||
/// `TokioContext` allows connecting a custom executor with the tokio runtime.
|
||||
///
|
||||
/// It contains a `Handle` to the runtime. A handle to the runtime can be
|
||||
/// obtain by calling the `Runtime::handle()` method.
|
||||
pub struct TokioContext<F> {
|
||||
#[pin]
|
||||
inner: F,
|
||||
handle: Handle,
|
||||
}
|
||||
}
|
||||
|
||||
impl<F: Future> Future for TokioContext<F> {
|
||||
type Output = F::Output;
|
||||
|
||||
fn poll(self: Pin<&mut Self>, cx: &mut Context<'_>) -> Poll<Self::Output> {
|
||||
let me = self.project();
|
||||
let handle = me.handle;
|
||||
let fut = me.inner;
|
||||
|
||||
handle.enter(|| fut.poll(cx))
|
||||
}
|
||||
}
|
||||
|
||||
/// Trait extension that simplifies bundling a `Handle` with a `Future`.
|
||||
pub trait HandleExt {
|
||||
/// Convenience method that takes a Future and returns a `TokioContext`.
|
||||
///
|
||||
/// # Example: calling Tokio Runtime from a custom ThreadPool
|
||||
///
|
||||
/// ```no_run
|
||||
/// use tokio_util::context::HandleExt;
|
||||
/// use tokio::time::{delay_for, Duration};
|
||||
///
|
||||
/// let mut rt = tokio::runtime::Builder::new()
|
||||
/// .threaded_scheduler()
|
||||
/// .enable_all()
|
||||
/// .build().unwrap();
|
||||
///
|
||||
/// let rt2 = tokio::runtime::Builder::new()
|
||||
/// .threaded_scheduler()
|
||||
/// .build().unwrap();
|
||||
///
|
||||
/// let fut = delay_for(Duration::from_millis(2));
|
||||
///
|
||||
/// rt.block_on(
|
||||
/// rt2
|
||||
/// .handle()
|
||||
/// .wrap(async { delay_for(Duration::from_millis(2)).await }),
|
||||
/// );
|
||||
///```
|
||||
fn wrap<F: Future>(&self, fut: F) -> TokioContext<F>;
|
||||
}
|
||||
|
||||
impl HandleExt for Handle {
|
||||
fn wrap<F: Future>(&self, fut: F) -> TokioContext<F> {
|
||||
TokioContext {
|
||||
inner: fut,
|
||||
handle: self.clone(),
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -35,3 +35,7 @@ cfg_udp! {
|
||||
cfg_compat! {
|
||||
pub mod compat;
|
||||
}
|
||||
|
||||
cfg_rt! {
|
||||
pub mod context;
|
||||
}
|
||||
|
||||
@@ -0,0 +1,29 @@
|
||||
#![warn(rust_2018_idioms)]
|
||||
#![cfg(feature = "rt")]
|
||||
|
||||
use tokio::runtime::Builder;
|
||||
use tokio::time::*;
|
||||
use tokio_util::context::HandleExt;
|
||||
|
||||
#[test]
|
||||
fn tokio_context_with_another_runtime() {
|
||||
let mut rt1 = Builder::new()
|
||||
.threaded_scheduler()
|
||||
.core_threads(1)
|
||||
// no timer!
|
||||
.build()
|
||||
.unwrap();
|
||||
let rt2 = Builder::new()
|
||||
.threaded_scheduler()
|
||||
.core_threads(1)
|
||||
.enable_all()
|
||||
.build()
|
||||
.unwrap();
|
||||
|
||||
// Without the `HandleExt.wrap()` there would be a panic because there is
|
||||
// no timer running, since it would be referencing runtime r1.
|
||||
let _ = rt1.block_on(
|
||||
rt2.handle()
|
||||
.wrap(async move { delay_for(Duration::from_millis(2)).await }),
|
||||
);
|
||||
}
|
||||
@@ -1,3 +1,52 @@
|
||||
# 0.2.25 (January 28, 2021)
|
||||
|
||||
### Changes
|
||||
|
||||
- chore: upgrade mio dependency (#3207)
|
||||
- runtime: update panic messages to include version (#3460)
|
||||
|
||||
### Fixes
|
||||
|
||||
- task: add missing feature flags for `task_local` (#3236)
|
||||
|
||||
# 0.2.24 (December 7, 2020)
|
||||
|
||||
### Fixes
|
||||
|
||||
- sync: fix mpsc bug related to closing the channel (#3215)
|
||||
|
||||
# 0.2.23 (November 12, 2020)
|
||||
|
||||
### Fixes
|
||||
|
||||
- time: report correct error for timers that exceed max duration (#2023)
|
||||
- time: fix resetting expired timers causing panics (#2587)
|
||||
- macros: silence `unreachable_code` warning in `select!` (#2678)
|
||||
- rt: fix potential leak during runtime shutdown (#2649)
|
||||
- sync: fix missing notification during mpsc close (#2854)
|
||||
|
||||
### Changes
|
||||
|
||||
- io: always re-export `std::io` (#2606)
|
||||
- dependencies: update `parking_lot` dependency to 0.11.0 (#2676)
|
||||
- io: rewrite `read_to_end` and `read_to_string` (#2560)
|
||||
- coop: reset coop budget when blocking in `block_on` (#2711)
|
||||
- sync: better Debug for Mutex (#2725)
|
||||
- net: make `UnixListener::poll_accept` public (#2880)
|
||||
- dep: raise `lazy_static` to `1.4.0` (#3132)
|
||||
- dep: raise `slab` to `0.4.2` (#3132)
|
||||
|
||||
### Added
|
||||
|
||||
- io: add `io::duplex()` as bidirectional reader/writer (#2661)
|
||||
- net: introduce split and `into_split` on `UnixDatagram` (#2557)
|
||||
- net: ensure that unix sockets have both `split` and `into_split` (#2687)
|
||||
- net: add `try_recv`/`from` & `try_send`/`to` to UnixDatagram (#1677)
|
||||
- net: Add `UdpSocket::{try_send,try_send_to}` methods (#1979)
|
||||
- net: implement `ToSocketAddrs` for `(String, u16)` (#2724)
|
||||
- io: add `ReaderStream` (#2714)
|
||||
- sync: implement map methods (#2771)
|
||||
|
||||
# 0.2.22 (July 21, 2020)
|
||||
|
||||
### Fixes
|
||||
|
||||
+6
-6
@@ -8,12 +8,12 @@ name = "tokio"
|
||||
# - README.md
|
||||
# - Update CHANGELOG.md.
|
||||
# - Create "v0.2.x" git tag.
|
||||
version = "0.2.22"
|
||||
version = "0.2.25"
|
||||
edition = "2018"
|
||||
authors = ["Tokio Contributors <[email protected]>"]
|
||||
license = "MIT"
|
||||
readme = "README.md"
|
||||
documentation = "https://docs.rs/tokio/0.2.22/tokio/"
|
||||
documentation = "https://docs.rs/tokio/0.2.25/tokio/"
|
||||
repository = "https://github.com/tokio-rs/tokio"
|
||||
homepage = "https://tokio.rs"
|
||||
description = """
|
||||
@@ -91,7 +91,7 @@ udp = ["io-driver"]
|
||||
uds = ["io-driver", "mio-uds", "libc"]
|
||||
|
||||
[dependencies]
|
||||
tokio-macros = { version = "0.2.4", path = "../tokio-macros", optional = true }
|
||||
tokio-macros = { version = "0.2.6", optional = true }
|
||||
|
||||
bytes = "0.5.0"
|
||||
pin-project-lite = "0.1.1"
|
||||
@@ -99,13 +99,13 @@ pin-project-lite = "0.1.1"
|
||||
# Everything else is optional...
|
||||
fnv = { version = "1.0.6", optional = true }
|
||||
futures-core = { version = "0.3.0", optional = true }
|
||||
lazy_static = { version = "1.0.2", optional = true }
|
||||
lazy_static = { version = "1.4.0", optional = true }
|
||||
memchr = { version = "2.2", optional = true }
|
||||
mio = { version = "0.6.20", optional = true }
|
||||
mio = { version = "0.6.23", optional = true }
|
||||
iovec = { version = "0.1.4", optional = true }
|
||||
num_cpus = { version = "1.8.0", optional = true }
|
||||
parking_lot = { version = "0.11.0", optional = true } # Not in full
|
||||
slab = { version = "0.4.1", optional = true } # Backs `DelayQueue`
|
||||
slab = { version = "0.4.2", optional = true } # Backs `DelayQueue`
|
||||
tracing = { version = "0.1.16", default-features = false, features = ["std"], optional = true } # Not in full
|
||||
|
||||
[target.'cfg(unix)'.dependencies]
|
||||
|
||||
@@ -200,8 +200,9 @@ impl Handle {
|
||||
///
|
||||
/// This function panics if there is no current reactor set.
|
||||
pub(super) fn current() -> Self {
|
||||
context::io_handle()
|
||||
.expect("there is no reactor running, must be called from the context of Tokio runtime")
|
||||
context::io_handle().expect(
|
||||
"there is no reactor running, must be called from the context of a Tokio 0.2.x runtime",
|
||||
)
|
||||
}
|
||||
|
||||
/// Forces a reactor blocked in a call to `turn` to wakeup, or otherwise
|
||||
|
||||
+4
-2
@@ -1,8 +1,10 @@
|
||||
#![doc(html_root_url = "https://docs.rs/tokio/0.2.22")]
|
||||
#![doc(html_root_url = "https://docs.rs/tokio/0.2.25")]
|
||||
#![allow(
|
||||
clippy::cognitive_complexity,
|
||||
clippy::large_enum_variant,
|
||||
clippy::needless_doctest_main
|
||||
clippy::needless_doctest_main,
|
||||
clippy::match_like_matches_macro,
|
||||
clippy::stable_sort_primitive
|
||||
)]
|
||||
#![warn(
|
||||
missing_debug_implementations,
|
||||
|
||||
@@ -185,10 +185,10 @@ impl TcpListener {
|
||||
poll_fn(|cx| self.poll_accept(cx)).await
|
||||
}
|
||||
|
||||
/// Attempts to poll `SocketAddr` and `TcpStream` bound to this address.
|
||||
/// Polls to accept a new incoming connection to this listener.
|
||||
///
|
||||
/// In case if I/O resource isn't ready yet, `Poll::Pending` is returned and
|
||||
/// current task will be notified by a waker.
|
||||
/// If there is no connection to accept, `Poll::Pending` is returned and
|
||||
/// the current task will be notified by a waker.
|
||||
pub fn poll_accept(
|
||||
&mut self,
|
||||
cx: &mut Context<'_>,
|
||||
|
||||
@@ -104,7 +104,11 @@ impl UnixListener {
|
||||
poll_fn(|cx| self.poll_accept(cx)).await
|
||||
}
|
||||
|
||||
pub(crate) fn poll_accept(
|
||||
/// Polls to accept a new incoming connection to this listener.
|
||||
///
|
||||
/// If there is no connection to accept, `Poll::Pending` is returned and
|
||||
/// the current task will be notified by a waker.
|
||||
pub fn poll_accept(
|
||||
&mut self,
|
||||
cx: &mut Context<'_>,
|
||||
) -> Poll<io::Result<(UnixStream, SocketAddr)>> {
|
||||
|
||||
@@ -115,7 +115,7 @@ impl Handle {
|
||||
/// # }
|
||||
/// ```
|
||||
pub fn current() -> Self {
|
||||
context::current().expect("not currently running on the Tokio runtime.")
|
||||
context::current().expect("not currently running on a Tokio 0.2.x runtime.")
|
||||
}
|
||||
|
||||
/// Returns a Handle view over the currently running Runtime
|
||||
|
||||
@@ -957,7 +957,6 @@ where
|
||||
|
||||
#[cfg(feature = "stream")]
|
||||
#[doc(hidden)]
|
||||
#[deprecated(since = "0.2.21", note = "use `into_stream()`")]
|
||||
impl<T> crate::stream::Stream for Receiver<T>
|
||||
where
|
||||
T: Clone,
|
||||
|
||||
@@ -917,6 +917,10 @@ impl Waiter {
|
||||
let mut curr = WaiterState(self.state.load(Acquire));
|
||||
|
||||
loop {
|
||||
if curr.is_closed() {
|
||||
return 0;
|
||||
}
|
||||
|
||||
if !curr.is_queued() {
|
||||
assert_eq!(0, curr.permits_to_acquire());
|
||||
}
|
||||
|
||||
@@ -128,7 +128,7 @@ doc_rt_core! {
|
||||
T::Output: Send + 'static,
|
||||
{
|
||||
let spawn_handle = runtime::context::spawn_handle()
|
||||
.expect("must be called from the context of Tokio runtime configured with either `basic_scheduler` or `threaded_scheduler`");
|
||||
.expect("must be called from the context of a Tokio 0.2.x runtime configured with either `basic_scheduler` or `threaded_scheduler`");
|
||||
let task = crate::util::trace::task(task, "task");
|
||||
spawn_handle.spawn(task)
|
||||
}
|
||||
|
||||
@@ -31,6 +31,7 @@ use std::{fmt, thread};
|
||||
///
|
||||
/// [`tokio::task::LocalKey`]: struct@crate::task::LocalKey
|
||||
#[macro_export]
|
||||
#[cfg_attr(docsrs, doc(cfg(all(feature = "rt-util", feature = "rt-core"))))]
|
||||
macro_rules! task_local {
|
||||
// empty (base case for the recursion)
|
||||
() => {};
|
||||
@@ -90,6 +91,7 @@ macro_rules! __task_local_inner {
|
||||
/// # }
|
||||
/// ```
|
||||
/// [`std::thread::LocalKey`]: struct@std::thread::LocalKey
|
||||
#[cfg_attr(docsrs, doc(cfg(all(feature = "rt-util", feature = "rt-core"))))]
|
||||
pub struct LocalKey<T: 'static> {
|
||||
#[doc(hidden)]
|
||||
pub inner: thread::LocalKey<RefCell<Option<T>>>,
|
||||
|
||||
@@ -21,8 +21,9 @@ impl Handle {
|
||||
///
|
||||
/// This function panics if there is no current timer set.
|
||||
pub(crate) fn current() -> Self {
|
||||
context::time_handle()
|
||||
.expect("there is no timer running, must be called from the context of Tokio runtime")
|
||||
context::time_handle().expect(
|
||||
"there is no timer running, must be called from the context of a Tokio 0.2.x runtime",
|
||||
)
|
||||
}
|
||||
|
||||
/// Tries to return a strong ref to the inner
|
||||
|
||||
@@ -1,4 +1,5 @@
|
||||
#![allow(clippy::blacklisted_name)]
|
||||
#![allow(clippy::blacklisted_name, clippy::stable_sort_primitive)]
|
||||
|
||||
use tokio::sync::{mpsc, oneshot};
|
||||
use tokio::task;
|
||||
use tokio_test::{assert_ok, assert_pending, assert_ready};
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
#![allow(clippy::needless_range_loop)]
|
||||
#![allow(clippy::needless_range_loop, clippy::stable_sort_primitive)]
|
||||
#![warn(rust_2018_idioms)]
|
||||
#![cfg(feature = "full")]
|
||||
|
||||
|
||||
@@ -1,3 +1,5 @@
|
||||
#![allow(clippy::stable_sort_primitive)]
|
||||
|
||||
use tokio::stream::{self, pending, Stream, StreamExt, StreamMap};
|
||||
use tokio::sync::mpsc;
|
||||
use tokio_test::{assert_ok, assert_pending, assert_ready, task};
|
||||
@@ -213,8 +215,8 @@ fn new_capacity_zero() {
|
||||
let map = StreamMap::<&str, stream::Pending<()>>::new();
|
||||
assert_eq!(0, map.capacity());
|
||||
|
||||
let keys = map.keys().collect::<Vec<_>>();
|
||||
assert!(keys.is_empty());
|
||||
let mut keys = map.keys();
|
||||
assert!(keys.next().is_none());
|
||||
}
|
||||
|
||||
#[test]
|
||||
@@ -222,8 +224,8 @@ fn with_capacity() {
|
||||
let map = StreamMap::<&str, stream::Pending<()>>::with_capacity(10);
|
||||
assert!(10 <= map.capacity());
|
||||
|
||||
let keys = map.keys().collect::<Vec<_>>();
|
||||
assert!(keys.is_empty());
|
||||
let mut keys = map.keys();
|
||||
assert!(keys.next().is_none());
|
||||
}
|
||||
|
||||
#[test]
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
#![allow(clippy::cognitive_complexity)]
|
||||
#![allow(clippy::cognitive_complexity, clippy::match_like_matches_macro)]
|
||||
#![warn(rust_2018_idioms)]
|
||||
#![cfg(feature = "sync")]
|
||||
|
||||
|
||||
@@ -512,3 +512,27 @@ fn ready_close_cancel_bounded() {
|
||||
|
||||
assert!(recv.is_woken());
|
||||
}
|
||||
|
||||
#[tokio::test]
|
||||
async fn permit_available_not_acquired_close() {
|
||||
use futures::future::poll_fn;
|
||||
|
||||
let (mut tx1, mut rx) = mpsc::channel::<()>(1);
|
||||
let mut tx2 = tx1.clone();
|
||||
|
||||
{
|
||||
let mut ready = task::spawn(poll_fn(|cx| tx1.poll_ready(cx)));
|
||||
assert_ready_ok!(ready.poll());
|
||||
}
|
||||
|
||||
let mut ready = task::spawn(poll_fn(|cx| tx2.poll_ready(cx)));
|
||||
assert_pending!(ready.poll());
|
||||
|
||||
rx.close();
|
||||
|
||||
drop(tx1);
|
||||
assert!(ready.is_woken());
|
||||
|
||||
drop(tx2);
|
||||
assert!(rx.recv().await.is_none());
|
||||
}
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
#![allow(clippy::blacklisted_name)]
|
||||
#![allow(clippy::blacklisted_name, clippy::stable_sort_primitive)]
|
||||
#![warn(rust_2018_idioms)]
|
||||
#![cfg(feature = "full")]
|
||||
|
||||
|
||||
Reference in New Issue
Block a user