Skip to content

Commit

Permalink
Add an on-by-default use_std feature to futures
Browse files Browse the repository at this point in the history
This commit adds a new Cargo feature to the `futures` crate, `use_std`, which is
enabled by default. The `futures` crate is now tagged as `#![no_std]` with extra
support like tasks, oneshot, and channels coming in through the `use_std`
feature. Most crates will likely depend on the `use_std` version, but that
shouldn't preclude those that don't want to!

Closes rust-lang#60
  • Loading branch information
alexcrichton committed Aug 20, 2016
1 parent 1f51080 commit a195a4e
Show file tree
Hide file tree
Showing 23 changed files with 132 additions and 93 deletions.
2 changes: 2 additions & 0 deletions .travis.yml
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,8 @@ sudo: false
before_script:
- pip install git+https://github.com/euclio/travis-cargo@kcov --user && export PATH=$HOME/.local/bin:$PATH
script:
- cargo build
- cargo build --no-default-features
- cargo test
- cargo test --manifest-path futures-io/Cargo.toml
- cargo test --manifest-path futures-iobuf/Cargo.toml
Expand Down
8 changes: 6 additions & 2 deletions Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -30,5 +30,9 @@ members = [
]

[dependencies]
log = "0.3"
scoped-tls = "0.1"
log = { version = "0.3", default-features = true }
scoped-tls = { version = "0.1", optional = true }

[features]
use_std = ["scoped-tls"]
default = ["use_std"]
2 changes: 2 additions & 0 deletions appveyor.yml
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,8 @@ install:
build: false

test_script:
- cargo build
- cargo build --no-default-features
- cargo test
- cargo test --manifest-path futures-io/Cargo.toml
- cargo test --manifest-path futures-iobuf/Cargo.toml
Expand Down
2 changes: 1 addition & 1 deletion src/chain.rs
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
use std::mem;
use core::mem;

use {Future, Poll};

Expand Down
2 changes: 2 additions & 0 deletions src/collect.rs
Original file line number Diff line number Diff line change
@@ -1,3 +1,5 @@
use std::prelude::v1::*;

use std::mem;

use {Future, IntoFuture, Poll};
Expand Down
2 changes: 1 addition & 1 deletion src/empty.rs
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
use std::marker;
use core::marker;

use {Future, Poll};

Expand Down
1 change: 1 addition & 0 deletions src/executor.rs
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,7 @@
//! is not currently used much by futures beyond `DEFAULT`.

use std::cell::{Cell, RefCell};
use std::prelude::v1::*;
use std::sync::Arc;

/// Encapsulation of a value which has the ability to execute arbitrary code.
Expand Down
2 changes: 1 addition & 1 deletion src/failed.rs
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
use std::marker;
use core::marker;

use {Future, Poll};

Expand Down
2 changes: 1 addition & 1 deletion src/finished.rs
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
use std::marker;
use core::marker;

use {Future, Poll};

Expand Down
2 changes: 2 additions & 0 deletions src/forget.rs
Original file line number Diff line number Diff line change
@@ -1,3 +1,5 @@
use std::prelude::v1::*;

use {Future, Poll};
use task::Task;

Expand Down
19 changes: 0 additions & 19 deletions src/impls.rs

This file was deleted.

2 changes: 1 addition & 1 deletion src/join.rs
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
#![allow(non_snake_case)]

use std::mem;
use core::mem;

use {Future, Poll, IntoFuture};

Expand Down
2 changes: 1 addition & 1 deletion src/lazy.rs
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
use std::mem;
use core::mem;

use {Future, IntoFuture, Poll};

Expand Down
92 changes: 63 additions & 29 deletions src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -149,42 +149,41 @@
//!
//! [README]: https://github.com/alexcrichton/futures-rs#futures-rs

#![no_std]
#![deny(missing_docs)]

use std::thread;

#[macro_use]
extern crate log;
#[cfg(feature = "use_std")]
extern crate scoped_tls;
#[macro_use]
#[cfg(feature = "use_std")]
extern crate std;

#[macro_use]
extern crate scoped_tls;
extern crate log;

// internal utilities
mod lock;
mod slot;
macro_rules! if_std {
($($i:item)*) => ($(
#[cfg(feature = "use_std")]
$i
)*)
}

#[macro_use]
mod poll;
pub use poll::Poll;

pub mod task;
pub mod executor;

// Primitive futures
mod collect;
mod done;
mod empty;
mod failed;
mod finished;
mod lazy;
mod oneshot;
pub use collect::{collect, Collect};
pub use done::{done, Done};
pub use empty::{empty, Empty};
pub use failed::{failed, Failed};
pub use finished::{finished, Finished};
pub use lazy::{lazy, Lazy};
pub use oneshot::{oneshot, Oneshot, Complete, Canceled};

// combinators
mod and_then;
Expand All @@ -195,7 +194,6 @@ mod map;
mod map_err;
mod or_else;
mod select;
mod select_all;
mod then;
pub use and_then::AndThen;
pub use flatten::Flatten;
Expand All @@ -205,16 +203,49 @@ pub use map::Map;
pub use map_err::MapErr;
pub use or_else::OrElse;
pub use select::{Select, SelectNext};
pub use select_all::{SelectAll, SelectAllNext, select_all};
pub use then::Then;

if_std! {
mod lock;
mod slot;
pub mod task;
pub mod executor;

mod collect;
mod oneshot;
mod select_all;
pub use collect::{collect, Collect};
pub use oneshot::{oneshot, Oneshot, Complete, Canceled};
pub use select_all::{SelectAll, SelectAllNext, select_all};

mod forget;

struct ThreadNotify(std::thread::Thread);

impl task::Notify for ThreadNotify {
fn notify(&self) {
self.0.unpark();
}
}

/// A type alias for `Box<Future + Send>`
pub type BoxFuture<T, E> = std::boxed::Box<Future<Item = T, Error = E> + Send>;

impl<F: ?Sized + Future> Future for std::boxed::Box<F> {
type Item = F::Item;
type Error = F::Error;

fn poll(&mut self) -> Poll<Self::Item, Self::Error> {
(**self).poll()
}
}
}

// streams
pub mod stream;

// impl details
mod chain;
mod impls;
mod forget;

/// Trait for types which are a placeholder of a value that will become
/// available at possible some later point in time.
Expand Down Expand Up @@ -351,9 +382,12 @@ pub trait Future {
///
/// This function does not attempt to catch panics. If the `poll` function
/// panics, panics will be propagated to the caller.
#[cfg(feature = "use_std")]
fn await(mut self) -> Result<Self::Item, Self::Error>
where Self: Sized
{
use std::thread;

let notify = ThreadNotify(thread::current());
let mut task = task::Task::new_notify(notify);
loop {
Expand All @@ -380,10 +414,11 @@ pub trait Future {
///
/// let a: BoxFuture<i32, i32> = done(Ok(1)).boxed();
/// ```
#[cfg(feature = "use_std")]
fn boxed(self) -> BoxFuture<Self::Item, Self::Error>
where Self: Sized + Send + 'static
{
Box::new(self)
::std::boxed::Box::new(self)
}

/// Map this future's result to a different type, returning a new future of
Expand Down Expand Up @@ -782,13 +817,20 @@ pub trait Future {
/// `futures-mio` crate provides a `Loop::run` method which pins the future
/// to the stack frame of that functionc all, allowing it to have a
/// non-`'static` lifetime.
#[cfg(feature = "use_std")]
fn forget(self) where Self: Sized + Send + 'static {
forget::forget(self);
}
}

/// A type alias for `Box<Future + Send>`
pub type BoxFuture<T, E> = Box<Future<Item = T, Error = E> + Send>;
impl<'a, F: ?Sized + Future> Future for &'a mut F {
type Item = F::Item;
type Error = F::Error;

fn poll(&mut self) -> Poll<Self::Item, Self::Error> {
(**self).poll()
}
}

// Just a helper function to ensure the futures we're returning all have the
// right implementations.
Expand Down Expand Up @@ -834,11 +876,3 @@ impl<T, E> IntoFuture for Result<T, E> {
done(self)
}
}

struct ThreadNotify(thread::Thread);

impl task::Notify for ThreadNotify {
fn notify(&self) {
self.0.unpark();
}
}
8 changes: 4 additions & 4 deletions src/lock.rs
Original file line number Diff line number Diff line change
Expand Up @@ -4,10 +4,10 @@
//! thing that ever blocks, so this is assisted with a fast user-space
//! implementation of a lock that can only have a `try_lock` operation.

use std::cell::UnsafeCell;
use std::ops::{Deref, DerefMut};
use std::sync::atomic::Ordering::{Acquire, Release};
use std::sync::atomic::AtomicBool;
use core::cell::UnsafeCell;
use core::ops::{Deref, DerefMut};
use core::sync::atomic::Ordering::{Acquire, Release};
use core::sync::atomic::AtomicBool;

/// A "mutex" around a value, similar to `std::sync::Mutex<T>`.
///
Expand Down
1 change: 1 addition & 0 deletions src/select_all.rs
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
use std::mem;
use std::prelude::v1::*;

use {Future, IntoFuture, Poll};

Expand Down
1 change: 1 addition & 0 deletions src/slot.rs
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,7 @@

#![allow(dead_code)] // imported in a few places

use std::prelude::v1::*;
use std::sync::atomic::{AtomicUsize, Ordering};

use lock::Lock;
Expand Down
2 changes: 2 additions & 0 deletions src/stream/buffered.rs
Original file line number Diff line number Diff line change
@@ -1,3 +1,5 @@
use std::prelude::v1::*;

use std::mem;

use {IntoFuture, Poll, Future};
Expand Down
2 changes: 2 additions & 0 deletions src/stream/collect.rs
Original file line number Diff line number Diff line change
@@ -1,3 +1,5 @@
use std::prelude::v1::*;

use std::mem;

use {Future, Poll};
Expand Down
2 changes: 1 addition & 1 deletion src/stream/fold.rs
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
use std::mem;
use core::mem;

use {Future, Poll, IntoFuture};
use stream::Stream;
Expand Down
20 changes: 0 additions & 20 deletions src/stream/impls.rs

This file was deleted.

Loading

0 comments on commit a195a4e

Please sign in to comment.