//! A Rust library for build scripts to automatically configure code based on
//! compiler support.  Code snippets are dynamically tested to see if the `rustc`
//! will accept them, rather than hard-coding specific version support.
//!
//!
//! ## Usage
//!
//! Add this to your `Cargo.toml`:
//!
//! ```toml
//! [build-dependencies]
//! autocfg = "1"
//! ```
//!
//! Then use it in your `build.rs` script to detect compiler features.  For
//! example, to test for 128-bit integer support, it might look like:
//!
//! ```rust
//! extern crate autocfg;
//!
//! fn main() {
//! #   // Normally, cargo will set `OUT_DIR` for build scripts.
//! #   std::env::set_var("OUT_DIR", "target");
//!     let ac = autocfg::new();
//!     ac.emit_has_type("i128");
//!
//!     // (optional) We don't need to rerun for anything external.
//!     autocfg::rerun_path("build.rs");
//! }
//! ```
//!
//! If the type test succeeds, this will write a `cargo:rustc-cfg=has_i128` line
//! for Cargo, which translates to Rust arguments `--cfg has_i128`.  Then in the
//! rest of your Rust code, you can add `#[cfg(has_i128)]` conditions on code that
//! should only be used when the compiler supports it.
//!
//! ## Caution
//!
//! Many of the probing methods of `AutoCfg` document the particular template they
//! use, **subject to change**. The inputs are not validated to make sure they are
//! semantically correct for their expected use, so it's _possible_ to escape and
//! inject something unintended. However, such abuse is unsupported and will not
//! be considered when making changes to the templates.

#![deny(missing_debug_implementations)]
#![deny(missing_docs)]
// allow future warnings that can't be fixed while keeping 1.0 compatibility
#![allow(unknown_lints)]
#![allow(bare_trait_objects)]
#![allow(ellipsis_inclusive_range_patterns)]

/// Local macro to avoid `std::try!`, deprecated in Rust 1.39.
macro_rules! try {
    ($result:expr) => {
        match $result {
            Ok(value) => value,
            Err(error) => return Err(error),
        }
    };
}

use std::env;
use std::ffi::OsString;
use std::fs;
use std::io::{stderr, Write};
use std::path::PathBuf;
use std::process::{Command, Stdio};
#[allow(deprecated)]
use std::sync::atomic::ATOMIC_USIZE_INIT;
use std::sync::atomic::{AtomicUsize, Ordering};

mod error;
pub use error::Error;

mod version;
use version::Version;

#[cfg(test)]
mod tests;

/// Helper to detect compiler features for `cfg` output in build scripts.
#[derive(Clone, Debug)]
pub struct AutoCfg {
    out_dir: PathBuf,
    rustc: PathBuf,
    rustc_version: Version,
    target: Option<OsString>,
    no_std: bool,
    rustflags: Option<Vec<String>>,
}

/// Writes a config flag for rustc on standard out.
///
/// This looks like: `cargo:rustc-cfg=CFG`
///
/// Cargo will use this in arguments to rustc, like `--cfg CFG`.
pub fn emit(cfg: &str) {
    println!("cargo:rustc-cfg={}", cfg);
}

/// Writes a line telling Cargo to rerun the build script if `path` changes.
///
/// This looks like: `cargo:rerun-if-changed=PATH`
///
/// This requires at least cargo 0.7.0, corresponding to rustc 1.6.0.  Earlier
/// versions of cargo will simply ignore the directive.
pub fn rerun_path(path: &str) {
    println!("cargo:rerun-if-changed={}", path);
}

/// Writes a line telling Cargo to rerun the build script if the environment
/// variable `var` changes.
///
/// This looks like: `cargo:rerun-if-env-changed=VAR`
///
/// This requires at least cargo 0.21.0, corresponding to rustc 1.20.0.  Earlier
/// versions of cargo will simply ignore the directive.
pub fn rerun_env(var: &str) {
    println!("cargo:rerun-if-env-changed={}", var);
}

/// Create a new `AutoCfg` instance.
///
/// # Panics
///
/// Panics if `AutoCfg::new()` returns an error.
pub fn new() -> AutoCfg {
    AutoCfg::new().unwrap()
}

impl AutoCfg {
    /// Create a new `AutoCfg` instance.
    ///
    /// # Common errors
    ///
    /// - `rustc` can't be executed, from `RUSTC` or in the `PATH`.
    /// - The version output from `rustc` can't be parsed.
    /// - `OUT_DIR` is not set in the environment, or is not a writable directory.
    ///
    pub fn new() -> Result<Self, Error> {
        match env::var_os("OUT_DIR") {
            Some(d) => Self::with_dir(d),
            None => Err(error::from_str("no OUT_DIR specified!")),
        }
    }

    /// Create a new `AutoCfg` instance with the specified output directory.
    ///
    /// # Common errors
    ///
    /// - `rustc` can't be executed, from `RUSTC` or in the `PATH`.
    /// - The version output from `rustc` can't be parsed.
    /// - `dir` is not a writable directory.
    ///
    pub fn with_dir<T: Into<PathBuf>>(dir: T) -> Result<Self, Error> {
        let rustc = env::var_os("RUSTC").unwrap_or_else(|| "rustc".into());
        let rustc: PathBuf = rustc.into();
        let rustc_version = try!(Version::from_rustc(&rustc));

        // Sanity check the output directory
        let dir = dir.into();
        let meta = try!(fs::metadata(&dir).map_err(error::from_io));
        if !meta.is_dir() || meta.permissions().readonly() {
            return Err(error::from_str("output path is not a writable directory"));
        }

        // Cargo only applies RUSTFLAGS for building TARGET artifact in
        // cross-compilation environment. Sadly, we don't have a way to detect
        // when we're building HOST artifact in a cross-compilation environment,
        // so for now we only apply RUSTFLAGS when cross-compiling an artifact.
        //
        // See https://github.com/cuviper/autocfg/pull/10#issuecomment-527575030.
        let rustflags = if env::var_os("TARGET") != env::var_os("HOST") {
            env::var("RUSTFLAGS").ok().map(|rustflags| {
                // This is meant to match how cargo handles the RUSTFLAG environment
                // variable.
                // See https://github.com/rust-lang/cargo/blob/69aea5b6f69add7c51cca939a79644080c0b0ba0/src/cargo/core/compiler/build_context/target_info.rs#L434-L441
                rustflags
                    .split(' ')
                    .map(str::trim)
                    .filter(|s| !s.is_empty())
                    .map(str::to_string)
                    .collect::<Vec<String>>()
            })
        } else {
            None
        };

        let mut ac = AutoCfg {
            out_dir: dir,
            rustc: rustc,
            rustc_version: rustc_version,
            target: env::var_os("TARGET"),
            no_std: false,
            rustflags: rustflags,
        };

        // Sanity check with and without `std`.
        if !ac.probe("").unwrap_or(false) {
            ac.no_std = true;
            if !ac.probe("").unwrap_or(false) {
                // Neither worked, so assume nothing...
                ac.no_std = false;
                let warning = b"warning: autocfg could not probe for `std`\n";
                stderr().write_all(warning).ok();
            }
        }
        Ok(ac)
    }

    /// Test whether the current `rustc` reports a version greater than
    /// or equal to "`major`.`minor`".
    pub fn probe_rustc_version(&self, major: usize, minor: usize) -> bool {
        self.rustc_version >= Version::new(major, minor, 0)
    }

    /// Sets a `cfg` value of the form `rustc_major_minor`, like `rustc_1_29`,
    /// if the current `rustc` is at least that version.
    pub fn emit_rustc_version(&self, major: usize, minor: usize) {
        if self.probe_rustc_version(major, minor) {
            emit(&format!("rustc_{}_{}", major, minor));
        }
    }

    fn probe<T: AsRef<[u8]>>(&self, code: T) -> Result<bool, Error> {
        #[allow(deprecated)]
        static ID: AtomicUsize = ATOMIC_USIZE_INIT;

        let id = ID.fetch_add(1, Ordering::Relaxed);
        let mut command = Command::new(&self.rustc);
        command
            .arg("--crate-name")
            .arg(format!("probe{}", id))
            .arg("--crate-type=lib")
            .arg("--out-dir")
            .arg(&self.out_dir)
            .arg("--emit=llvm-ir");

        if let &Some(ref rustflags) = &self.rustflags {
            command.args(rustflags);
        }

        if let Some(target) = self.target.as_ref() {
            command.arg("--target").arg(target);
        }

        command.arg("-").stdin(Stdio::piped());
        let mut child = try!(command.spawn().map_err(error::from_io));
        let mut stdin = child.stdin.take().expect("rustc stdin");

        if self.no_std {
            try!(stdin.write_all(b"#![no_std]\n").map_err(error::from_io));
        }
        try!(stdin.write_all(code.as_ref()).map_err(error::from_io));
        drop(stdin);

        let status = try!(child.wait().map_err(error::from_io));
        Ok(status.success())
    }

    /// Tests whether the given sysroot crate can be used.
    ///
    /// The test code is subject to change, but currently looks like:
    ///
    /// ```ignore
    /// extern crate CRATE as probe;
    /// ```
    pub fn probe_sysroot_crate(&self, name: &str) -> bool {
        self.probe(format!("extern crate {} as probe;", name)) // `as _` wasn't stabilized until Rust 1.33
            .unwrap_or(false)
    }

    /// Emits a config value `has_CRATE` if `probe_sysroot_crate` returns true.
    pub fn emit_sysroot_crate(&self, name: &str) {
        if self.probe_sysroot_crate(name) {
            emit(&format!("has_{}", mangle(name)));
        }
    }

    /// Tests whether the given path can be used.
    ///
    /// The test code is subject to change, but currently looks like:
    ///
    /// ```ignore
    /// pub use PATH;
    /// ```
    pub fn probe_path(&self, path: &str) -> bool {
        self.probe(format!("pub use {};", path)).unwrap_or(false)
    }

    /// Emits a config value `has_PATH` if `probe_path` returns true.
    ///
    /// Any non-identifier characters in the `path` will be replaced with
    /// `_` in the generated config value.
    pub fn emit_has_path(&self, path: &str) {
        if self.probe_path(path) {
            emit(&format!("has_{}", mangle(path)));
        }
    }

    /// Emits the given `cfg` value if `probe_path` returns true.
    pub fn emit_path_cfg(&self, path: &str, cfg: &str) {
        if self.probe_path(path) {
            emit(cfg);
        }
    }

    /// Tests whether the given trait can be used.
    ///
    /// The test code is subject to change, but currently looks like:
    ///
    /// ```ignore
    /// pub trait Probe: TRAIT + Sized {}
    /// ```
    pub fn probe_trait(&self, name: &str) -> bool {
        self.probe(format!("pub trait Probe: {} + Sized {{}}", name))
            .unwrap_or(false)
    }

    /// Emits a config value `has_TRAIT` if `probe_trait` returns true.
    ///
    /// Any non-identifier characters in the trait `name` will be replaced with
    /// `_` in the generated config value.
    pub fn emit_has_trait(&self, name: &str) {
        if self.probe_trait(name) {
            emit(&format!("has_{}", mangle(name)));
        }
    }

    /// Emits the given `cfg` value if `probe_trait` returns true.
    pub fn emit_trait_cfg(&self, name: &str, cfg: &str) {
        if self.probe_trait(name) {
            emit(cfg);
        }
    }

    /// Tests whether the given type can be used.
    ///
    /// The test code is subject to change, but currently looks like:
    ///
    /// ```ignore
    /// pub type Probe = TYPE;
    /// ```
    pub fn probe_type(&self, name: &str) -> bool {
        self.probe(format!("pub type Probe = {};", name))
            .unwrap_or(false)
    }

    /// Emits a config value `has_TYPE` if `probe_type` returns true.
    ///
    /// Any non-identifier characters in the type `name` will be replaced with
    /// `_` in the generated config value.
    pub fn emit_has_type(&self, name: &str) {
        if self.probe_type(name) {
            emit(&format!("has_{}", mangle(name)));
        }
    }

    /// Emits the given `cfg` value if `probe_type` returns true.
    pub fn emit_type_cfg(&self, name: &str, cfg: &str) {
        if self.probe_type(name) {
            emit(cfg);
        }
    }

    /// Tests whether the given expression can be used.
    ///
    /// The test code is subject to change, but currently looks like:
    ///
    /// ```ignore
    /// pub fn probe() { let _ = EXPR; }
    /// ```
    pub fn probe_expression(&self, expr: &str) -> bool {
        self.probe(format!("pub fn probe() {{ let _ = {}; }}", expr))
            .unwrap_or(false)
    }

    /// Emits the given `cfg` value if `probe_expression` returns true.
    pub fn emit_expression_cfg(&self, expr: &str, cfg: &str) {
        if self.probe_expression(expr) {
            emit(cfg);
        }
    }

    /// Tests whether the given constant expression can be used.
    ///
    /// The test code is subject to change, but currently looks like:
    ///
    /// ```ignore
    /// pub const PROBE: () = ((), EXPR).0;
    /// ```
    pub fn probe_constant(&self, expr: &str) -> bool {
        self.probe(format!("pub const PROBE: () = ((), {}).0;", expr))
            .unwrap_or(false)
    }

    /// Emits the given `cfg` value if `probe_constant` returns true.
    pub fn emit_constant_cfg(&self, expr: &str, cfg: &str) {
        if self.probe_constant(expr) {
            emit(cfg);
        }
    }
}

fn mangle(s: &str) -> String {
    s.chars()
        .map(|c| match c {
            'A'...'Z' | 'a'...'z' | '0'...'9' => c,
            _ => '_',
        })
        .collect()
}
