stdworld 0.1.1

signal-safe std replacement
Documentation
#![no_std]

//! Welcome to stdworld! This crate is an alternative to the Rust std crate,
//! with a focus on use-cases not supported by Rust.
//!
//! # Motivation: Issues with std
//!
//! While Rust works fine for a lot of use-cases, there are some use-cases
//! that Rust either neglects, such as code/library unloading, or is actively
//! hostile against, such as signal handling.
//!
//! This crate provides a library-only approach that addresses those use-cases.
//!
//! # Structure
//!
//! This crate is structured in modules analogous to Rust's own std. However,
//! these are explicitly **not** drop-in replacements! Many of them differ in
//! safety (often with the stdworld equivalent being safe), but all of them
//! differ in types.
//!
//! # Stability
//!
//! This crate is currently unusable.
//!
//! You can look at the code tho.
//!
//! # Acknowledgements
//!
//! This crate was inspired by crates such as `qcell` and our own `selfref`. We
//! would also like to thank the various trans developers. Finally, we would
//! like to blame tom7, for getting his PhD in 2008.

// TODO find a way to enforce no_std in user crates. find a way to enforce std
// is not in the user crate sysroot.
// "rust is safe" our ass. if it were safe this crate wouldn't fucking exist.
// oh well.

pub mod os {
    pub struct OsStr {
        _tbd: (),
    }

    pub struct OsString {
        _tbd: (),
    }
}

/// APIs to interact with signal handling.
pub mod signal {
    // to start off, we can always expose the C standard safe functions, and,
    // on POSIX, also the POSIX standard safe functions.
    // but then we have 2 ways to handle signal-unsafe functions:
    // the C way, where none of them are available.
    // OR
    // the POSIX way, where the entire thing is extremely context-sensitive.
    // the POSIX way is less restrictive, but much much harder to encode in
    // the type system. especially as we have to support the C way regardless,
    // since we're not targeting POSIX-only here.
    // unfortunately we currently do not know if we can fulfill both signal
    // safety styles in a single std replacement crate.
}

/// APIs to interact with the program environment.
pub mod env {
    use crate::os::{OsStr, OsString};

    pub struct VarsOs {
        _tbd: ()
    }

    /// Sets an environment variable.
    pub fn set_var<W: EnvAccess, K: AsRef<OsStr>, V: AsRef<OsStr>>(w: W, key: K, value: V) {
        // NYI
    }
    /// Fetches an environment variable.
    pub fn var_os<W: EnvAccess, K: AsRef<OsStr>>(w: W, key: K) -> Option<OsString> {
        // NYI
        None
    }
    /// Iterates through environment variables.
    pub fn vars_os<W: EnvAccess>(w: W) -> VarsOs {
        VarsOs { _tbd: () }
    }

    /// Marker trait to indicate a world that is allowed to access environment
    /// variables.
    pub unsafe trait EnvAccess {}
}

/// APIs to interact with threads.
pub mod thread {
    /// Spawn a new thread.
    pub fn spawn<W: ThreadAccess, F, T>(w: W, f: F) -> JoinHandle<T>
    where
        F: FnOnce(<W as ThreadAccess>::World) -> T + Send + 'static,
        T: Send + 'static,
    {
        // NYI
        JoinHandle { _t: None }
    }

    /// Marker trait to indicate a world that is allowed to spawn threads.
    pub unsafe trait ThreadAccess {
        /// World type used in the spawned thread.
        type World;
    }

    pub struct JoinHandle<T> {
        _t: Option<T>,
    }
}

/// The world as seen by an application's main thread.
pub struct MainWorld {
    _tbd: (),
}

unsafe impl env::EnvAccess for MainWorld {}
unsafe impl thread::ThreadAccess for MainWorld {
    type World = ThreadWorld;
}

/// The world as seen by an application's other threads.
pub struct ThreadWorld {
    _tbd: (),
}

unsafe impl thread::ThreadAccess for ThreadWorld {
    type World = ThreadWorld;
}

/// The world as seen by an unloadable plugin running on an application's main
/// thread.
pub struct UnloadableMainWorld {
    _tbd: (),
}

unsafe impl env::EnvAccess for UnloadableMainWorld {}

impl MainWorld {
    unsafe fn new() -> MainWorld {
        MainWorld { _tbd: () }
    }
}

impl ThreadWorld {
    unsafe fn new() -> ThreadWorld {
        ThreadWorld { _tbd: () }
    }
}

impl UnloadableMainWorld {
    unsafe fn new() -> UnloadableMainWorld {
        UnloadableMainWorld { _tbd: () }
    }
}