From 76bac5d33e09e8ae1b243c045584646431147cce Mon Sep 17 00:00:00 2001 From: Raph Levien Date: Tue, 18 Oct 2016 13:43:18 -0700 Subject: [PATCH] Add Fuchsia support Adds support for the x86_64-unknown-fuchsia target, which covers the Fuchsia operating system. --- mk/cfg/x86_64-unknown-fuchsia.mk | 1 + src/liballoc_jemalloc/build.rs | 2 +- src/librustc_back/target/fuchsia_base.rs | 39 +++ src/librustc_back/target/mod.rs | 3 + .../target/x86_64_unknown_fuchsia.rs | 30 ++ src/libstd/build.rs | 2 +- src/libstd/os/fuchsia/fs.rs | 103 +++++++ src/libstd/os/fuchsia/mod.rs | 16 + src/libstd/os/fuchsia/raw.rs | 275 ++++++++++++++++++ src/libstd/os/mod.rs | 1 + src/libstd/sys/unix/args.rs | 3 +- src/libstd/sys/unix/env.rs | 11 + src/libstd/sys/unix/ext/fs.rs | 1 + src/libstd/sys/unix/fs.rs | 3 +- src/libstd/sys/unix/mod.rs | 5 +- src/libstd/sys/unix/os.rs | 8 +- src/libstd/sys/unix/thread.rs | 4 + src/libstd/thread/local.rs | 72 +++-- src/libtest/lib.rs | 3 +- src/libunwind/build.rs | 2 + src/libunwind/libunwind.rs | 2 + 21 files changed, 548 insertions(+), 38 deletions(-) create mode 100644 mk/cfg/x86_64-unknown-fuchsia.mk create mode 100644 src/librustc_back/target/fuchsia_base.rs create mode 100644 src/librustc_back/target/x86_64_unknown_fuchsia.rs create mode 100644 src/libstd/os/fuchsia/fs.rs create mode 100644 src/libstd/os/fuchsia/mod.rs create mode 100644 src/libstd/os/fuchsia/raw.rs diff --git a/mk/cfg/x86_64-unknown-fuchsia.mk b/mk/cfg/x86_64-unknown-fuchsia.mk new file mode 100644 index 00000000000..34aee77ae21 --- /dev/null +++ b/mk/cfg/x86_64-unknown-fuchsia.mk @@ -0,0 +1 @@ +# rustbuild-only target diff --git a/src/liballoc_jemalloc/build.rs b/src/liballoc_jemalloc/build.rs index 369db8e75a3..08a1f8ae8c6 100644 --- a/src/liballoc_jemalloc/build.rs +++ b/src/liballoc_jemalloc/build.rs @@ -36,7 +36,7 @@ fn main() { // targets, which means we have to build the alloc_jemalloc crate // for targets like emscripten, even if we don't use it. if target.contains("rumprun") || target.contains("bitrig") || target.contains("openbsd") || - target.contains("msvc") || target.contains("emscripten") { + target.contains("msvc") || target.contains("emscripten") || target.contains("fuchsia") { println!("cargo:rustc-cfg=dummy_jemalloc"); return; } diff --git a/src/librustc_back/target/fuchsia_base.rs b/src/librustc_back/target/fuchsia_base.rs new file mode 100644 index 00000000000..e763d6d8fba --- /dev/null +++ b/src/librustc_back/target/fuchsia_base.rs @@ -0,0 +1,39 @@ +// Copyright 2014 The Rust Project Developers. See the COPYRIGHT +// file at the top-level directory of this distribution and at +// http://rust-lang.org/COPYRIGHT. +// +// Licensed under the Apache License, Version 2.0 or the MIT license +// , at your +// option. This file may not be copied, modified, or distributed +// except according to those terms. + +use target::TargetOptions; +use std::default::Default; + +pub fn opts() -> TargetOptions { + TargetOptions { + dynamic_linking: true, + executables: true, + linker_is_gnu: true, + has_rpath: true, + pre_link_args: vec![ + // We want to be able to strip as much executable code as possible + // from the linker command line, and this flag indicates to the + // linker that it can avoid linking in dynamic libraries that don't + // actually satisfy any symbols up to that point (as with many other + // resolutions the linker does). This option only applies to all + // following libraries so we're sure to pass it as one of the first + // arguments. + // TODO: doesn't seem to be supported by clang toolchain + //"-Wl,--as-needed".to_string(), + + // Always enable NX protection when it is available + //"-Wl,-z,noexecstack".to_string(), + ], + position_independent_executables: true, + exe_allocation_crate: "alloc_system".to_string(), + has_elf_tls: true, + .. Default::default() + } +} diff --git a/src/librustc_back/target/mod.rs b/src/librustc_back/target/mod.rs index 1843fc581f1..931080daef2 100644 --- a/src/librustc_back/target/mod.rs +++ b/src/librustc_back/target/mod.rs @@ -67,6 +67,7 @@ mod solaris_base; mod windows_base; mod windows_msvc_base; mod thumb_base; +mod fuchsia_base; pub type TargetResult = Result; @@ -175,6 +176,8 @@ supported_targets! { ("x86_64-apple-darwin", x86_64_apple_darwin), ("i686-apple-darwin", i686_apple_darwin), + ("x86_64-unknown-fuchsia", x86_64_unknown_fuchsia), + ("i386-apple-ios", i386_apple_ios), ("x86_64-apple-ios", x86_64_apple_ios), ("aarch64-apple-ios", aarch64_apple_ios), diff --git a/src/librustc_back/target/x86_64_unknown_fuchsia.rs b/src/librustc_back/target/x86_64_unknown_fuchsia.rs new file mode 100644 index 00000000000..08fe17a556e --- /dev/null +++ b/src/librustc_back/target/x86_64_unknown_fuchsia.rs @@ -0,0 +1,30 @@ +// Copyright 2016 The Rust Project Developers. See the COPYRIGHT +// file at the top-level directory of this distribution and at +// http://rust-lang.org/COPYRIGHT. +// +// Licensed under the Apache License, Version 2.0 or the MIT license +// , at your +// option. This file may not be copied, modified, or distributed +// except according to those terms. + +use target::{Target, TargetResult}; + +pub fn target() -> TargetResult { + let mut base = super::fuchsia_base::opts(); + base.cpu = "x86-64".to_string(); + base.max_atomic_width = Some(64); + base.pre_link_args.push("-m64".to_string()); + + Ok(Target { + llvm_target: "x86_64-unknown-fuchsia".to_string(), + target_endian: "little".to_string(), + target_pointer_width: "64".to_string(), + data_layout: "e-m:e-i64:64-f80:128-n8:16:32:64-S128".to_string(), + arch: "x86_64".to_string(), + target_os: "fuchsia".to_string(), + target_env: "".to_string(), + target_vendor: "unknown".to_string(), + options: base, + }) +} diff --git a/src/libstd/build.rs b/src/libstd/build.rs index c5732278db9..c811ed3bded 100644 --- a/src/libstd/build.rs +++ b/src/libstd/build.rs @@ -26,7 +26,7 @@ fn main() { let target = env::var("TARGET").expect("TARGET was not set"); let host = env::var("HOST").expect("HOST was not set"); if cfg!(feature = "backtrace") && !target.contains("apple") && !target.contains("msvc") && - !target.contains("emscripten") { + !target.contains("emscripten") && !target.contains("fuchsia") { build_libbacktrace(&host, &target); } diff --git a/src/libstd/os/fuchsia/fs.rs b/src/libstd/os/fuchsia/fs.rs new file mode 100644 index 00000000000..d22f9a628bd --- /dev/null +++ b/src/libstd/os/fuchsia/fs.rs @@ -0,0 +1,103 @@ +// Copyright 2016 The Rust Project Developers. See the COPYRIGHT +// file at the top-level directory of this distribution and at +// http://rust-lang.org/COPYRIGHT. +// +// Licensed under the Apache License, Version 2.0 or the MIT license +// , at your +// option. This file may not be copied, modified, or distributed +// except according to those terms. + +#![stable(feature = "metadata_ext", since = "1.1.0")] + +use fs::Metadata; +use sys_common::AsInner; + +/// OS-specific extension methods for `fs::Metadata` +#[stable(feature = "metadata_ext", since = "1.1.0")] +pub trait MetadataExt { + #[stable(feature = "metadata_ext2", since = "1.8.0")] + fn st_dev(&self) -> u64; + #[stable(feature = "metadata_ext2", since = "1.8.0")] + fn st_ino(&self) -> u64; + #[stable(feature = "metadata_ext2", since = "1.8.0")] + fn st_mode(&self) -> u32; + #[stable(feature = "metadata_ext2", since = "1.8.0")] + fn st_nlink(&self) -> u64; + #[stable(feature = "metadata_ext2", since = "1.8.0")] + fn st_uid(&self) -> u32; + #[stable(feature = "metadata_ext2", since = "1.8.0")] + fn st_gid(&self) -> u32; + #[stable(feature = "metadata_ext2", since = "1.8.0")] + fn st_rdev(&self) -> u64; + #[stable(feature = "metadata_ext2", since = "1.8.0")] + fn st_size(&self) -> u64; + #[stable(feature = "metadata_ext2", since = "1.8.0")] + fn st_atime(&self) -> i64; + #[stable(feature = "metadata_ext2", since = "1.8.0")] + fn st_atime_nsec(&self) -> i64; + #[stable(feature = "metadata_ext2", since = "1.8.0")] + fn st_mtime(&self) -> i64; + #[stable(feature = "metadata_ext2", since = "1.8.0")] + fn st_mtime_nsec(&self) -> i64; + #[stable(feature = "metadata_ext2", since = "1.8.0")] + fn st_ctime(&self) -> i64; + #[stable(feature = "metadata_ext2", since = "1.8.0")] + fn st_ctime_nsec(&self) -> i64; + #[stable(feature = "metadata_ext2", since = "1.8.0")] + fn st_blksize(&self) -> u64; + #[stable(feature = "metadata_ext2", since = "1.8.0")] + fn st_blocks(&self) -> u64; +} + +#[stable(feature = "metadata_ext", since = "1.1.0")] +impl MetadataExt for Metadata { + fn st_dev(&self) -> u64 { + self.as_inner().as_inner().st_dev as u64 + } + fn st_ino(&self) -> u64 { + self.as_inner().as_inner().st_ino as u64 + } + fn st_mode(&self) -> u32 { + self.as_inner().as_inner().st_mode as u32 + } + fn st_nlink(&self) -> u64 { + self.as_inner().as_inner().st_nlink as u64 + } + fn st_uid(&self) -> u32 { + self.as_inner().as_inner().st_uid as u32 + } + fn st_gid(&self) -> u32 { + self.as_inner().as_inner().st_gid as u32 + } + fn st_rdev(&self) -> u64 { + self.as_inner().as_inner().st_rdev as u64 + } + fn st_size(&self) -> u64 { + self.as_inner().as_inner().st_size as u64 + } + fn st_atime(&self) -> i64 { + self.as_inner().as_inner().st_atime as i64 + } + fn st_atime_nsec(&self) -> i64 { + self.as_inner().as_inner().st_atime_nsec as i64 + } + fn st_mtime(&self) -> i64 { + self.as_inner().as_inner().st_mtime as i64 + } + fn st_mtime_nsec(&self) -> i64 { + self.as_inner().as_inner().st_mtime_nsec as i64 + } + fn st_ctime(&self) -> i64 { + self.as_inner().as_inner().st_ctime as i64 + } + fn st_ctime_nsec(&self) -> i64 { + self.as_inner().as_inner().st_ctime_nsec as i64 + } + fn st_blksize(&self) -> u64 { + self.as_inner().as_inner().st_blksize as u64 + } + fn st_blocks(&self) -> u64 { + self.as_inner().as_inner().st_blocks as u64 + } +} diff --git a/src/libstd/os/fuchsia/mod.rs b/src/libstd/os/fuchsia/mod.rs new file mode 100644 index 00000000000..1ebcbba9147 --- /dev/null +++ b/src/libstd/os/fuchsia/mod.rs @@ -0,0 +1,16 @@ +// Copyright 2015 The Rust Project Developers. See the COPYRIGHT +// file at the top-level directory of this distribution and at +// http://rust-lang.org/COPYRIGHT. +// +// Licensed under the Apache License, Version 2.0 or the MIT license +// , at your +// option. This file may not be copied, modified, or distributed +// except according to those terms. + +//! Fuchsia-specific definitions + +#![stable(feature = "raw_ext", since = "1.1.0")] + +pub mod raw; +pub mod fs; diff --git a/src/libstd/os/fuchsia/raw.rs b/src/libstd/os/fuchsia/raw.rs new file mode 100644 index 00000000000..696c0c70aa9 --- /dev/null +++ b/src/libstd/os/fuchsia/raw.rs @@ -0,0 +1,275 @@ +// Copyright 2015 The Rust Project Developers. See the COPYRIGHT +// file at the top-level directory of this distribution and at +// http://rust-lang.org/COPYRIGHT. +// +// Licensed under the Apache License, Version 2.0 or the MIT license +// , at your +// option. This file may not be copied, modified, or distributed +// except according to those terms. + +//! Fuchsia-specific raw type definitions + +#![stable(feature = "raw_ext", since = "1.1.0")] +#![rustc_deprecated(since = "1.8.0", + reason = "these type aliases are no longer supported by \ + the standard library, the `libc` crate on \ + crates.io should be used instead for the correct \ + definitions")] +#![allow(deprecated)] + +use os::raw::c_ulong; + +#[stable(feature = "raw_ext", since = "1.1.0")] pub type dev_t = u64; +#[stable(feature = "raw_ext", since = "1.1.0")] pub type mode_t = u32; + +#[stable(feature = "pthread_t", since = "1.8.0")] +pub type pthread_t = c_ulong; + +#[doc(inline)] +#[stable(feature = "raw_ext", since = "1.1.0")] +pub use self::arch::{off_t, ino_t, nlink_t, blksize_t, blkcnt_t, stat, time_t}; + +#[cfg(any(target_arch = "x86", + target_arch = "le32", + target_arch = "powerpc", + target_arch = "arm"))] +mod arch { + use os::raw::{c_long, c_short, c_uint}; + + #[stable(feature = "raw_ext", since = "1.1.0")] pub type blkcnt_t = u64; + #[stable(feature = "raw_ext", since = "1.1.0")] pub type blksize_t = u64; + #[stable(feature = "raw_ext", since = "1.1.0")] pub type ino_t = u64; + #[stable(feature = "raw_ext", since = "1.1.0")] pub type nlink_t = u64; + #[stable(feature = "raw_ext", since = "1.1.0")] pub type off_t = u64; + #[stable(feature = "raw_ext", since = "1.1.0")] pub type time_t = i64; + + #[repr(C)] + #[derive(Clone)] + #[stable(feature = "raw_ext", since = "1.1.0")] + pub struct stat { + #[stable(feature = "raw_ext", since = "1.1.0")] + pub st_dev: u64, + #[stable(feature = "raw_ext", since = "1.1.0")] + pub __pad1: c_short, + #[stable(feature = "raw_ext", since = "1.1.0")] + pub __st_ino: u32, + #[stable(feature = "raw_ext", since = "1.1.0")] + pub st_mode: u32, + #[stable(feature = "raw_ext", since = "1.1.0")] + pub st_nlink: u32, + #[stable(feature = "raw_ext", since = "1.1.0")] + pub st_uid: u32, + #[stable(feature = "raw_ext", since = "1.1.0")] + pub st_gid: u32, + #[stable(feature = "raw_ext", since = "1.1.0")] + pub st_rdev: u64, + #[stable(feature = "raw_ext", since = "1.1.0")] + pub __pad2: c_uint, + #[stable(feature = "raw_ext", since = "1.1.0")] + pub st_size: i64, + #[stable(feature = "raw_ext", since = "1.1.0")] + pub st_blksize: i32, + #[stable(feature = "raw_ext", since = "1.1.0")] + pub st_blocks: i64, + #[stable(feature = "raw_ext", since = "1.1.0")] + pub st_atime: i32, + #[stable(feature = "raw_ext", since = "1.1.0")] + pub st_atime_nsec: c_long, + #[stable(feature = "raw_ext", since = "1.1.0")] + pub st_mtime: i32, + #[stable(feature = "raw_ext", since = "1.1.0")] + pub st_mtime_nsec: c_long, + #[stable(feature = "raw_ext", since = "1.1.0")] + pub st_ctime: i32, + #[stable(feature = "raw_ext", since = "1.1.0")] + pub st_ctime_nsec: c_long, + #[stable(feature = "raw_ext", since = "1.1.0")] + pub st_ino: u64, + } +} + +#[cfg(target_arch = "mips")] +mod arch { + use os::raw::{c_long, c_ulong}; + + #[cfg(target_env = "musl")] + #[stable(feature = "raw_ext", since = "1.1.0")] pub type blkcnt_t = i64; + #[cfg(not(target_env = "musl"))] + #[stable(feature = "raw_ext", since = "1.1.0")] pub type blkcnt_t = u64; + #[stable(feature = "raw_ext", since = "1.1.0")] pub type blksize_t = u64; + #[cfg(target_env = "musl")] + #[stable(feature = "raw_ext", since = "1.1.0")] pub type ino_t = u64; + #[cfg(not(target_env = "musl"))] + #[stable(feature = "raw_ext", since = "1.1.0")] pub type ino_t = u64; + #[stable(feature = "raw_ext", since = "1.1.0")] pub type nlink_t = u64; + #[cfg(target_env = "musl")] + #[stable(feature = "raw_ext", since = "1.1.0")] pub type off_t = u64; + #[cfg(not(target_env = "musl"))] + #[stable(feature = "raw_ext", since = "1.1.0")] pub type off_t = u64; + #[stable(feature = "raw_ext", since = "1.1.0")] pub type time_t = i64; + + #[repr(C)] + #[derive(Clone)] + #[stable(feature = "raw_ext", since = "1.1.0")] + pub struct stat { + #[stable(feature = "raw_ext", since = "1.1.0")] + pub st_dev: c_ulong, + #[stable(feature = "raw_ext", since = "1.1.0")] + pub st_pad1: [c_long; 3], + #[stable(feature = "raw_ext", since = "1.1.0")] + pub st_ino: u64, + #[stable(feature = "raw_ext", since = "1.1.0")] + pub st_mode: u32, + #[stable(feature = "raw_ext", since = "1.1.0")] + pub st_nlink: u32, + #[stable(feature = "raw_ext", since = "1.1.0")] + pub st_uid: u32, + #[stable(feature = "raw_ext", since = "1.1.0")] + pub st_gid: u32, + #[stable(feature = "raw_ext", since = "1.1.0")] + pub st_rdev: c_ulong, + #[stable(feature = "raw_ext", since = "1.1.0")] + pub st_pad2: [c_long; 2], + #[stable(feature = "raw_ext", since = "1.1.0")] + pub st_size: i64, + #[stable(feature = "raw_ext", since = "1.1.0")] + pub st_atime: i32, + #[stable(feature = "raw_ext", since = "1.1.0")] + pub st_atime_nsec: c_long, + #[stable(feature = "raw_ext", since = "1.1.0")] + pub st_mtime: i32, + #[stable(feature = "raw_ext", since = "1.1.0")] + pub st_mtime_nsec: c_long, + #[stable(feature = "raw_ext", since = "1.1.0")] + pub st_ctime: i32, + #[stable(feature = "raw_ext", since = "1.1.0")] + pub st_ctime_nsec: c_long, + #[stable(feature = "raw_ext", since = "1.1.0")] + pub st_blksize: i32, + #[stable(feature = "raw_ext", since = "1.1.0")] + pub st_blocks: i64, + #[stable(feature = "raw_ext", since = "1.1.0")] + pub st_pad5: [c_long; 14], + } +} + +#[cfg(target_arch = "mips64")] +mod arch { + pub use libc::{off_t, ino_t, nlink_t, blksize_t, blkcnt_t, stat, time_t}; +} + +#[cfg(target_arch = "s390x")] +mod arch { + pub use libc::{off_t, ino_t, nlink_t, blksize_t, blkcnt_t, stat, time_t}; +} + +#[cfg(target_arch = "aarch64")] +mod arch { + use os::raw::{c_long, c_int}; + + #[stable(feature = "raw_ext", since = "1.1.0")] pub type blkcnt_t = u64; + #[stable(feature = "raw_ext", since = "1.1.0")] pub type blksize_t = u64; + #[stable(feature = "raw_ext", since = "1.1.0")] pub type ino_t = u64; + #[stable(feature = "raw_ext", since = "1.1.0")] pub type nlink_t = u64; + #[stable(feature = "raw_ext", since = "1.1.0")] pub type off_t = u64; + #[stable(feature = "raw_ext", since = "1.1.0")] pub type time_t = i64; + + #[repr(C)] + #[derive(Clone)] + #[stable(feature = "raw_ext", since = "1.1.0")] + pub struct stat { + #[stable(feature = "raw_ext", since = "1.1.0")] + pub st_dev: u64, + #[stable(feature = "raw_ext", since = "1.1.0")] + pub st_ino: u64, + #[stable(feature = "raw_ext", since = "1.1.0")] + pub st_mode: u32, + #[stable(feature = "raw_ext", since = "1.1.0")] + pub st_nlink: u32, + #[stable(feature = "raw_ext", since = "1.1.0")] + pub st_uid: u32, + #[stable(feature = "raw_ext", since = "1.1.0")] + pub st_gid: u32, + #[stable(feature = "raw_ext", since = "1.1.0")] + pub st_rdev: u64, + #[stable(feature = "raw_ext", since = "1.1.0")] + pub __pad1: u64, + #[stable(feature = "raw_ext", since = "1.1.0")] + pub st_size: i64, + #[stable(feature = "raw_ext", since = "1.1.0")] + pub st_blksize: i32, + #[stable(feature = "raw_ext", since = "1.1.0")] + pub __pad2: c_int, + #[stable(feature = "raw_ext", since = "1.1.0")] + pub st_blocks: i64, + #[stable(feature = "raw_ext", since = "1.1.0")] + pub st_atime: i64, + #[stable(feature = "raw_ext", since = "1.1.0")] + pub st_atime_nsec: c_long, + #[stable(feature = "raw_ext", since = "1.1.0")] + pub st_mtime: i64, + #[stable(feature = "raw_ext", since = "1.1.0")] + pub st_mtime_nsec: c_long, + #[stable(feature = "raw_ext", since = "1.1.0")] + pub st_ctime: i64, + #[stable(feature = "raw_ext", since = "1.1.0")] + pub st_ctime_nsec: c_long, + #[stable(feature = "raw_ext", since = "1.1.0")] + pub __unused: [c_int; 2], + } +} + +#[cfg(target_arch = "x86_64")] +mod arch { + use os::raw::{c_long, c_int}; + + #[stable(feature = "raw_ext", since = "1.1.0")] pub type blkcnt_t = u64; + #[stable(feature = "raw_ext", since = "1.1.0")] pub type blksize_t = u64; + #[stable(feature = "raw_ext", since = "1.1.0")] pub type ino_t = u64; + #[stable(feature = "raw_ext", since = "1.1.0")] pub type nlink_t = u64; + #[stable(feature = "raw_ext", since = "1.1.0")] pub type off_t = u64; + #[stable(feature = "raw_ext", since = "1.1.0")] pub type time_t = i64; + + #[repr(C)] + #[derive(Clone)] + #[stable(feature = "raw_ext", since = "1.1.0")] + pub struct stat { + #[stable(feature = "raw_ext", since = "1.1.0")] + pub st_dev: u64, + #[stable(feature = "raw_ext", since = "1.1.0")] + pub st_ino: u64, + #[stable(feature = "raw_ext", since = "1.1.0")] + pub st_nlink: u64, + #[stable(feature = "raw_ext", since = "1.1.0")] + pub st_mode: u32, + #[stable(feature = "raw_ext", since = "1.1.0")] + pub st_uid: u32, + #[stable(feature = "raw_ext", since = "1.1.0")] + pub st_gid: u32, + #[stable(feature = "raw_ext", since = "1.1.0")] + pub __pad0: c_int, + #[stable(feature = "raw_ext", since = "1.1.0")] + pub st_rdev: u64, + #[stable(feature = "raw_ext", since = "1.1.0")] + pub st_size: i64, + #[stable(feature = "raw_ext", since = "1.1.0")] + pub st_blksize: i64, + #[stable(feature = "raw_ext", since = "1.1.0")] + pub st_blocks: i64, + #[stable(feature = "raw_ext", since = "1.1.0")] + pub st_atime: i64, + #[stable(feature = "raw_ext", since = "1.1.0")] + pub st_atime_nsec: c_long, + #[stable(feature = "raw_ext", since = "1.1.0")] + pub st_mtime: i64, + #[stable(feature = "raw_ext", since = "1.1.0")] + pub st_mtime_nsec: c_long, + #[stable(feature = "raw_ext", since = "1.1.0")] + pub st_ctime: i64, + #[stable(feature = "raw_ext", since = "1.1.0")] + pub st_ctime_nsec: c_long, + #[stable(feature = "raw_ext", since = "1.1.0")] + pub __unused: [c_long; 3], + } +} diff --git a/src/libstd/os/mod.rs b/src/libstd/os/mod.rs index 7622ef88693..366a1674156 100644 --- a/src/libstd/os/mod.rs +++ b/src/libstd/os/mod.rs @@ -33,5 +33,6 @@ pub use sys::ext as windows; #[cfg(target_os = "openbsd")] pub mod openbsd; #[cfg(target_os = "solaris")] pub mod solaris; #[cfg(target_os = "emscripten")] pub mod emscripten; +#[cfg(target_os = "fuchsia")] pub mod fuchsia; pub mod raw; diff --git a/src/libstd/sys/unix/args.rs b/src/libstd/sys/unix/args.rs index c64db333e51..c04fd863674 100644 --- a/src/libstd/sys/unix/args.rs +++ b/src/libstd/sys/unix/args.rs @@ -58,7 +58,8 @@ impl DoubleEndedIterator for Args { target_os = "openbsd", target_os = "solaris", target_os = "emscripten", - target_os = "haiku"))] + target_os = "haiku", + target_os = "fuchsia"))] mod imp { use os::unix::prelude::*; use mem; diff --git a/src/libstd/sys/unix/env.rs b/src/libstd/sys/unix/env.rs index 66ff2fec832..eff3a8c2a34 100644 --- a/src/libstd/sys/unix/env.rs +++ b/src/libstd/sys/unix/env.rs @@ -171,3 +171,14 @@ pub mod os { pub const EXE_SUFFIX: &'static str = ".js"; pub const EXE_EXTENSION: &'static str = "js"; } + +#[cfg(target_os = "fuchsia")] +pub mod os { + pub const FAMILY: &'static str = "unix"; + pub const OS: &'static str = "fuchsia"; + pub const DLL_PREFIX: &'static str = "lib"; + pub const DLL_SUFFIX: &'static str = ".so"; + pub const DLL_EXTENSION: &'static str = "so"; + pub const EXE_SUFFIX: &'static str = ""; + pub const EXE_EXTENSION: &'static str = ""; +} diff --git a/src/libstd/sys/unix/ext/fs.rs b/src/libstd/sys/unix/ext/fs.rs index fcfab051588..3ff21a07827 100644 --- a/src/libstd/sys/unix/ext/fs.rs +++ b/src/libstd/sys/unix/ext/fs.rs @@ -312,6 +312,7 @@ pub trait DirEntryExt { } #[stable(feature = "dir_entry_ext", since = "1.1.0")] +#[cfg(not(target_os = "fuchsia"))] impl DirEntryExt for fs::DirEntry { fn ino(&self) -> u64 { self.as_inner().ino() } } diff --git a/src/libstd/sys/unix/fs.rs b/src/libstd/sys/unix/fs.rs index b77008676b1..ee2887eb019 100644 --- a/src/libstd/sys/unix/fs.rs +++ b/src/libstd/sys/unix/fs.rs @@ -342,7 +342,8 @@ impl DirEntry { #[cfg(any(target_os = "android", target_os = "linux", target_os = "emscripten", - target_os = "haiku"))] + target_os = "haiku", + target_os = "fuchsia"))] fn name_bytes(&self) -> &[u8] { unsafe { CStr::from_ptr(self.entry.d_name.as_ptr()).to_bytes() diff --git a/src/libstd/sys/unix/mod.rs b/src/libstd/sys/unix/mod.rs index 501329772ce..66bc9d4a491 100644 --- a/src/libstd/sys/unix/mod.rs +++ b/src/libstd/sys/unix/mod.rs @@ -26,6 +26,7 @@ use libc; #[cfg(target_os = "openbsd")] pub use os::openbsd as platform; #[cfg(target_os = "solaris")] pub use os::solaris as platform; #[cfg(target_os = "emscripten")] pub use os::emscripten as platform; +#[cfg(target_os = "fuchsia")] pub use os::fuchsia as platform; #[macro_use] pub mod weak; @@ -88,11 +89,11 @@ pub fn init() { } } - #[cfg(not(any(target_os = "nacl", target_os = "emscripten")))] + #[cfg(not(any(target_os = "nacl", target_os = "emscripten", target_os="fuchsia")))] unsafe fn reset_sigpipe() { assert!(signal(libc::SIGPIPE, libc::SIG_IGN) != !0); } - #[cfg(any(target_os = "nacl", target_os = "emscripten"))] + #[cfg(any(target_os = "nacl", target_os = "emscripten", target_os="fuchsia"))] unsafe fn reset_sigpipe() {} } diff --git a/src/libstd/sys/unix/os.rs b/src/libstd/sys/unix/os.rs index 91f6ba80f83..e591f25cac1 100644 --- a/src/libstd/sys/unix/os.rs +++ b/src/libstd/sys/unix/os.rs @@ -38,7 +38,7 @@ static ENV_LOCK: Mutex = Mutex::new(); extern { #[cfg(not(target_os = "dragonfly"))] - #[cfg_attr(any(target_os = "linux", target_os = "emscripten"), + #[cfg_attr(any(target_os = "linux", target_os = "emscripten", target_os = "fuchsia"), link_name = "__errno_location")] #[cfg_attr(any(target_os = "bitrig", target_os = "netbsd", @@ -346,6 +346,12 @@ pub fn current_exe() -> io::Result { } } +#[cfg(target_os = "fuchsia")] +pub fn current_exe() -> io::Result { + use io::ErrorKind; + Err(io::Error::new(ErrorKind::Other, "Not yet implemented on fuchsia")) +} + pub struct Env { iter: vec::IntoIter<(OsString, OsString)>, _dont_send_or_sync_me: PhantomData<*mut ()>, diff --git a/src/libstd/sys/unix/thread.rs b/src/libstd/sys/unix/thread.rs index 87d82cdab97..df98d2e0169 100644 --- a/src/libstd/sys/unix/thread.rs +++ b/src/libstd/sys/unix/thread.rs @@ -135,6 +135,10 @@ impl Thread { pub fn set_name(_name: &CStr) { // Newlib, Illumos, Haiku, and Emscripten have no way to set a thread name. } + #[cfg(target_os = "fuchsia")] + pub fn set_name(_name: &CStr) { + // TODO: determine whether Fuchsia has a way to set a thread name. + } pub fn sleep(dur: Duration) { let mut secs = dur.as_secs(); diff --git a/src/libstd/thread/local.rs b/src/libstd/thread/local.rs index a333a7d967d..54d3f793045 100644 --- a/src/libstd/thread/local.rs +++ b/src/libstd/thread/local.rs @@ -358,36 +358,8 @@ pub mod elf { } } - // Since what appears to be glibc 2.18 this symbol has been shipped which - // GCC and clang both use to invoke destructors in thread_local globals, so - // let's do the same! - // - // Note, however, that we run on lots older linuxes, as well as cross - // compiling from a newer linux to an older linux, so we also have a - // fallback implementation to use as well. - // - // Due to rust-lang/rust#18804, make sure this is not generic! - #[cfg(target_os = "linux")] - unsafe fn register_dtor(t: *mut u8, dtor: unsafe extern fn(*mut u8)) { - use mem; - use libc; - use sys_common::thread_local as os; - - extern { - #[linkage = "extern_weak"] - static __dso_handle: *mut u8; - #[linkage = "extern_weak"] - static __cxa_thread_atexit_impl: *const libc::c_void; - } - if !__cxa_thread_atexit_impl.is_null() { - type F = unsafe extern fn(dtor: unsafe extern fn(*mut u8), - arg: *mut u8, - dso_handle: *mut u8) -> libc::c_int; - mem::transmute::<*const libc::c_void, F>(__cxa_thread_atexit_impl) - (dtor, t, &__dso_handle as *const _ as *mut _); - return - } - + #[cfg(any(target_os = "linux", target_os = "fuchsia"))] + unsafe fn register_dtor_fallback(t: *mut u8, dtor: unsafe extern fn(*mut u8)) { // The fallback implementation uses a vanilla OS-based TLS key to track // the list of destructors that need to be run for this thread. The key // then has its own destructor which runs all the other destructors. @@ -397,6 +369,8 @@ pub mod elf { // *should* be the case that this loop always terminates because we // provide the guarantee that a TLS key cannot be set after it is // flagged for destruction. + use sys_common::thread_local as os; + static DTORS: os::StaticKey = os::StaticKey::new(Some(run_dtors)); type List = Vec<(*mut u8, unsafe extern fn(*mut u8))>; if DTORS.get().is_null() { @@ -418,6 +392,37 @@ pub mod elf { } } + // Since what appears to be glibc 2.18 this symbol has been shipped which + // GCC and clang both use to invoke destructors in thread_local globals, so + // let's do the same! + // + // Note, however, that we run on lots older linuxes, as well as cross + // compiling from a newer linux to an older linux, so we also have a + // fallback implementation to use as well. + // + // Due to rust-lang/rust#18804, make sure this is not generic! + #[cfg(target_os = "linux")] + unsafe fn register_dtor(t: *mut u8, dtor: unsafe extern fn(*mut u8)) { + use mem; + use libc; + + extern { + #[linkage = "extern_weak"] + static __dso_handle: *mut u8; + #[linkage = "extern_weak"] + static __cxa_thread_atexit_impl: *const libc::c_void; + } + if !__cxa_thread_atexit_impl.is_null() { + type F = unsafe extern fn(dtor: unsafe extern fn(*mut u8), + arg: *mut u8, + dso_handle: *mut u8) -> libc::c_int; + mem::transmute::<*const libc::c_void, F>(__cxa_thread_atexit_impl) + (dtor, t, &__dso_handle as *const _ as *mut _); + return + } + register_dtor_fallback(t, dtor); + } + // OSX's analog of the above linux function is this _tlv_atexit function. // The disassembly of thread_local globals in C++ (at least produced by // clang) will have this show up in the output. @@ -430,6 +435,13 @@ pub mod elf { _tlv_atexit(dtor, t); } + // Just use the thread_local fallback implementation, at least until there's + // a more direct implementation. + #[cfg(target_os = "fuchsia")] + unsafe fn register_dtor(t: *mut u8, dtor: unsafe extern fn(*mut u8)) { + register_dtor_fallback(t, dtor); + } + pub unsafe extern fn destroy_value(ptr: *mut u8) { let ptr = ptr as *mut Key; // Right before we run the user destructor be sure to flag the diff --git a/src/libtest/lib.rs b/src/libtest/lib.rs index 625666e641c..8b0fd1ca0cb 100644 --- a/src/libtest/lib.rs +++ b/src/libtest/lib.rs @@ -1036,7 +1036,8 @@ fn get_concurrency() -> usize { target_os = "ios", target_os = "android", target_os = "solaris", - target_os = "emscripten"))] + target_os = "emscripten", + target_os = "fuchsia"))] fn num_cpus() -> usize { unsafe { libc::sysconf(libc::_SC_NPROCESSORS_ONLN) as usize } } diff --git a/src/libunwind/build.rs b/src/libunwind/build.rs index e1ddf8b4b7e..db41a368a16 100644 --- a/src/libunwind/build.rs +++ b/src/libunwind/build.rs @@ -35,5 +35,7 @@ fn main() { println!("cargo:rustc-link-lib=gcc_pic"); } else if target.contains("windows-gnu") { println!("cargo:rustc-link-lib=gcc_eh"); + } else if target.contains("fuchsia") { + println!("cargo:rustc-link-lib=unwind"); } } diff --git a/src/libunwind/libunwind.rs b/src/libunwind/libunwind.rs index c2edf754e49..bbac6c07c57 100644 --- a/src/libunwind/libunwind.rs +++ b/src/libunwind/libunwind.rs @@ -252,6 +252,8 @@ if #[cfg(not(all(target_os = "ios", target_arch = "arm")))] { any(target_arch = "x86", target_arch = "x86_64"), not(test)), link(name = "unwind", kind = "static"))] +#[cfg_attr(target_os = "fuchsia", + link(name = "unwind"))] #[cfg_attr(any(target_os = "android", target_os = "openbsd"), link(name = "gcc"))] #[cfg_attr(all(target_os = "netbsd", not(target_vendor = "rumprun")),