diff --git a/Cargo.lock b/Cargo.lock index d3a656dbf32..8f026590e50 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -19,6 +19,7 @@ dependencies = [ "scopeguard 0.1.2 (registry+https://github.com/rust-lang/crates.io-index)", "sha2 0.1.2 (registry+https://github.com/rust-lang/crates.io-index)", "tempdir 0.3.4 (registry+https://github.com/rust-lang/crates.io-index)", + "tempfile 2.1.4 (registry+https://github.com/rust-lang/crates.io-index)", "term 0.4.4 (registry+https://github.com/rust-lang/crates.io-index)", "time 0.1.35 (registry+https://github.com/rust-lang/crates.io-index)", "toml 0.1.30 (registry+https://github.com/rust-lang/crates.io-index)", @@ -728,6 +729,18 @@ dependencies = [ "rand 0.3.14 (registry+https://github.com/rust-lang/crates.io-index)", ] +[[package]] +name = "tempfile" +version = "2.1.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +dependencies = [ + "kernel32-sys 0.2.2 (registry+https://github.com/rust-lang/crates.io-index)", + "libc 0.2.14 (registry+https://github.com/rust-lang/crates.io-index)", + "rand 0.3.14 (registry+https://github.com/rust-lang/crates.io-index)", + "rustc_version 0.1.7 (registry+https://github.com/rust-lang/crates.io-index)", + "winapi 0.2.8 (registry+https://github.com/rust-lang/crates.io-index)", +] + [[package]] name = "term" version = "0.4.4" diff --git a/Cargo.toml b/Cargo.toml index d876bd09e26..cb7f60c9875 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -40,6 +40,7 @@ term = "0.4.4" itertools = "0.4.1" time = "0.1.34" tempdir = "0.3.4" +tempfile = "2.1.4" libc = "0.2.0" rand = "0.3.11" scopeguard = "0.1.2" diff --git a/src/rustup/command.rs b/src/rustup/command.rs index 44492150ef4..be5c3bab940 100644 --- a/src/rustup/command.rs +++ b/src/rustup/command.rs @@ -1,10 +1,12 @@ use std::env; use std::ffi::OsStr; +use std::fs::File; use std::io::{self, Write, BufRead, BufReader}; use std::path::PathBuf; use std::process::{self, Command, Stdio}; use std::time::Instant; use regex::Regex; +use tempfile::tempfile; use Cfg; use errors::*; @@ -29,6 +31,18 @@ pub fn run_command_for_dir>(cmd: Command, } fn telemetry_rustc>(mut cmd: Command, args: &[S], cfg: &Cfg) -> Result<()> { + #[cfg(unix)] + fn file_as_stdio(file: &File) -> Stdio { + use std::os::unix::io::{AsRawFd, FromRawFd}; + unsafe { Stdio::from_raw_fd(file.as_raw_fd()) } + } + + #[cfg(windows)] + fn file_as_stdio(file: &File) -> Stdio { + use std::os::windows::io::{AsRawHandle, FromRawHandle}; + unsafe { Stdio::from_raw_handle(file.as_raw_handle()) } + } + let now = Instant::now(); cmd.args(&args[1..]); @@ -44,15 +58,17 @@ fn telemetry_rustc>(mut cmd: Command, args: &[S], cfg: &Cfg) -> cmd.arg("always"); } + let cmd_err_file = tempfile().unwrap(); + let cmd_err_stdio = file_as_stdio(&cmd_err_file); + // FIXME rust-lang/rust#32254. It's not clear to me // when and why this is needed. let mut cmd = cmd.stdin(Stdio::inherit()) .stdout(Stdio::inherit()) - .stderr(Stdio::piped()) + .stderr(cmd_err_stdio) .spawn() .unwrap(); - let mut buffered_stderr = BufReader::new(cmd.stderr.take().unwrap()); let status = cmd.wait(); let duration = now.elapsed(); @@ -75,6 +91,8 @@ fn telemetry_rustc>(mut cmd: Command, args: &[S], cfg: &Cfg) -> let stderr = io::stderr(); let mut handle = stderr.lock(); + let mut buffered_stderr = BufReader::new(cmd_err_file); + while buffered_stderr.read_line(&mut buffer).unwrap() > 0 { let b = buffer.to_owned(); buffer.clear(); diff --git a/src/rustup/lib.rs b/src/rustup/lib.rs index 0501b2887e8..f3dda446994 100644 --- a/src/rustup/lib.rs +++ b/src/rustup/lib.rs @@ -9,6 +9,7 @@ extern crate url; extern crate regex; extern crate itertools; extern crate rustc_serialize; +extern crate tempfile; extern crate time; extern crate toml; #[cfg(unix)]