From 1c6b4d546dc1a7118cc3a9e940ae98f2a342f34a Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Hugo=20Beauz=C3=A9e-Luyssen?= Date: Mon, 27 May 2019 15:51:44 +0200 Subject: [PATCH 01/16] rustc: codegen: Build import library for all windows targets So far it is assumed that using a DLL as a -l parameter argument is ok, but the assumption doesn't hold when compiling the native code with llvm. In which case, an import library is required, so let's build one This also requires the cargo counterpart to add the import library in the stamp files, at least when compiling libstd. Otherwise, the files don't get uplifted --- src/bootstrap/compile.rs | 1 + src/librustc_codegen_ssa/back/linker.rs | 20 ++++++++++++++++++++ 2 files changed, 21 insertions(+) diff --git a/src/bootstrap/compile.rs b/src/bootstrap/compile.rs index 576267e6948f5..bbc7556157ba8 100644 --- a/src/bootstrap/compile.rs +++ b/src/bootstrap/compile.rs @@ -1130,6 +1130,7 @@ pub fn run_cargo(builder: &Builder<'_>, // Skip files like executables if !filename.ends_with(".rlib") && !filename.ends_with(".lib") && + !filename.ends_with(".a") && !is_dylib(&filename) && !(is_check && filename.ends_with(".rmeta")) { continue; diff --git a/src/librustc_codegen_ssa/back/linker.rs b/src/librustc_codegen_ssa/back/linker.rs index 32696d46cd577..d660d99325136 100644 --- a/src/librustc_codegen_ssa/back/linker.rs +++ b/src/librustc_codegen_ssa/back/linker.rs @@ -368,6 +368,26 @@ impl<'a> Linker for GccLinker<'a> { } } else { self.cmd.arg("-shared"); + if self.sess.target.target.options.is_like_windows { + // The output filename already contains `dll_suffix` so + // the resulting import library will have a name in the + // form of libfoo.dll.a + let implib_name = out_filename + .file_name() + .and_then(|file| file.to_str()) + .map(|file| format!("{}{}{}", + self.sess.target.target.options.staticlib_prefix, + file, + self.sess.target.target.options.staticlib_suffix)); + if let Some(implib_name) = implib_name { + let implib = out_filename + .parent() + .map(|dir| dir.join(&implib_name)); + if let Some(implib) = implib { + self.linker_arg(&format!("--out-implib,{}", (*implib).to_str().unwrap())); + } + } + } } } From c1b6716a3d75bf7f5d726088e3b3aca673c99358 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Hugo=20Beauz=C3=A9e-Luyssen?= Date: Mon, 27 May 2019 15:55:06 +0200 Subject: [PATCH 02/16] libstd: windows: compat: Allow use of attributes --- src/libstd/sys/windows/compat.rs | 2 ++ 1 file changed, 2 insertions(+) diff --git a/src/libstd/sys/windows/compat.rs b/src/libstd/sys/windows/compat.rs index 748c1616d1d32..544b2087f92e0 100644 --- a/src/libstd/sys/windows/compat.rs +++ b/src/libstd/sys/windows/compat.rs @@ -37,12 +37,14 @@ pub fn store_func(ptr: &AtomicUsize, module: &str, symbol: &str, macro_rules! compat_fn { ($module:ident: $( + $(#[$meta:meta])* pub fn $symbol:ident($($argname:ident: $argtype:ty),*) -> $rettype:ty { $($body:expr);* } )*) => ($( #[allow(unused_variables)] + $(#[$meta])* pub unsafe fn $symbol($($argname: $argtype),*) -> $rettype { use crate::sync::atomic::{AtomicUsize, Ordering}; use crate::mem; From 863cd6bc801506309e641aab33fa13787078ac34 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Hugo=20Beauz=C3=A9e-Luyssen?= Date: Mon, 27 May 2019 16:32:00 +0200 Subject: [PATCH 03/16] bootstrap: Build startup object for all windows-gnu target So that uwp-windows-gnu also gets its startup objects built --- src/bootstrap/compile.rs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/bootstrap/compile.rs b/src/bootstrap/compile.rs index bbc7556157ba8..413902252ebe8 100644 --- a/src/bootstrap/compile.rs +++ b/src/bootstrap/compile.rs @@ -326,7 +326,7 @@ impl Step for StartupObjects { fn run(self, builder: &Builder<'_>) { let for_compiler = self.compiler; let target = self.target; - if !target.contains("pc-windows-gnu") { + if !target.contains("windows-gnu") { return } From e5d7043e3d1c7ea3e8178d699e847af897c03244 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Hugo=20Beauz=C3=A9e-Luyssen?= Date: Mon, 27 May 2019 16:33:00 +0200 Subject: [PATCH 04/16] std: Link UWP with allowed libraries only --- src/libstd/build.rs | 2 ++ 1 file changed, 2 insertions(+) diff --git a/src/libstd/build.rs b/src/libstd/build.rs index 7a6c97ebaa226..1071cfbf6ef11 100644 --- a/src/libstd/build.rs +++ b/src/libstd/build.rs @@ -39,6 +39,8 @@ fn main() { println!("cargo:rustc-link-lib=framework=Security"); println!("cargo:rustc-link-lib=framework=Foundation"); println!("cargo:rustc-link-lib=resolv"); + } else if target.contains("uwp") { + println!("cargo:rustc-link-lib=ws2_32"); } else if target.contains("windows") { println!("cargo:rustc-link-lib=advapi32"); println!("cargo:rustc-link-lib=ws2_32"); From 98f9bba25e26ddcc0a4a0279ec25e005baa0509c Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Hugo=20Beauz=C3=A9e-Luyssen?= Date: Mon, 27 May 2019 16:38:21 +0200 Subject: [PATCH 05/16] libunwind: Use libunwind when targeting UWP libgcc's support is using forbidden functions --- src/libunwind/build.rs | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/src/libunwind/build.rs b/src/libunwind/build.rs index 20280aa3c4130..c59f797fcbf44 100644 --- a/src/libunwind/build.rs +++ b/src/libunwind/build.rs @@ -28,9 +28,11 @@ fn main() { println!("cargo:rustc-link-lib=gcc_s"); } else if target.contains("dragonfly") { println!("cargo:rustc-link-lib=gcc_pic"); - } else if target.contains("windows-gnu") { + } else if target.contains("pc-windows-gnu") { println!("cargo:rustc-link-lib=static-nobundle=gcc_eh"); println!("cargo:rustc-link-lib=static-nobundle=pthread"); + } else if target.contains("uwp-windows-gnu") { + println!("cargo:rustc-link-lib=unwind"); } else if target.contains("fuchsia") { println!("cargo:rustc-link-lib=unwind"); } else if target.contains("haiku") { From 20eb746f3d0b32eed95c4c8464e6a16b552eee5b Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Hugo=20Beauz=C3=A9e-Luyssen?= Date: Mon, 27 May 2019 16:41:52 +0200 Subject: [PATCH 06/16] std: rand: Use BCrypt on UWP As Rtl* functions are not allowed there --- src/libstd/build.rs | 2 ++ src/libstd/sys/windows/c.rs | 27 +++++++++++++++++++++++++-- src/libstd/sys/windows/rand.rs | 18 ++++++++++++++++++ 3 files changed, 45 insertions(+), 2 deletions(-) diff --git a/src/libstd/build.rs b/src/libstd/build.rs index 1071cfbf6ef11..20397369387cb 100644 --- a/src/libstd/build.rs +++ b/src/libstd/build.rs @@ -41,6 +41,8 @@ fn main() { println!("cargo:rustc-link-lib=resolv"); } else if target.contains("uwp") { println!("cargo:rustc-link-lib=ws2_32"); + // For BCryptGenRandom + println!("cargo:rustc-link-lib=bcrypt"); } else if target.contains("windows") { println!("cargo:rustc-link-lib=advapi32"); println!("cargo:rustc-link-lib=ws2_32"); diff --git a/src/libstd/sys/windows/c.rs b/src/libstd/sys/windows/c.rs index 6ad338660c338..42f9a0ca6b4ba 100644 --- a/src/libstd/sys/windows/c.rs +++ b/src/libstd/sys/windows/c.rs @@ -4,6 +4,10 @@ #![cfg_attr(test, allow(dead_code))] #![unstable(issue = "0", feature = "windows_c")] +macro_rules! ifdef { + ($($t:tt)*) => ($($t)*) +} + use crate::os::raw::{c_int, c_uint, c_ulong, c_long, c_longlong, c_ushort, c_char}; use crate::ptr; @@ -655,6 +659,27 @@ pub struct timeval { pub tv_usec: c_long, } +// Functions forbidden when targeting UWP +#[cfg(not(target_vendor = "uwp"))] +ifdef! { + extern "system" { + #[link_name = "SystemFunction036"] + pub fn RtlGenRandom(RandomBuffer: *mut u8, RandomBufferLength: ULONG) -> BOOLEAN; + } +} + +// UWP specific functions & types +#[cfg(target_vendor = "uwp")] +ifdef! { + pub const BCRYPT_USE_SYSTEM_PREFERRED_RNG: DWORD = 0x00000002; + + extern "system" { + pub fn BCryptGenRandom(hAlgorithm: LPVOID, pBuffer: *mut u8, + cbBuffer: ULONG, dwFlags: ULONG) -> LONG; + } +} + +// Shared between Desktop & UWP extern "system" { pub fn WSAStartup(wVersionRequested: WORD, lpWSAData: LPWSADATA) -> c_int; @@ -950,8 +975,6 @@ extern "system" { exceptfds: *mut fd_set, timeout: *const timeval) -> c_int; - #[link_name = "SystemFunction036"] - pub fn RtlGenRandom(RandomBuffer: *mut u8, RandomBufferLength: ULONG) -> BOOLEAN; pub fn GetProcessHeap() -> HANDLE; pub fn HeapAlloc(hHeap: HANDLE, dwFlags: DWORD, dwBytes: SIZE_T) -> LPVOID; diff --git a/src/libstd/sys/windows/rand.rs b/src/libstd/sys/windows/rand.rs index 0193f4defa1ff..c9bcb5d741514 100644 --- a/src/libstd/sys/windows/rand.rs +++ b/src/libstd/sys/windows/rand.rs @@ -2,6 +2,7 @@ use crate::io; use crate::mem; use crate::sys::c; +#[cfg(not(target_vendor = "uwp"))] pub fn hashmap_random_keys() -> (u64, u64) { let mut v = (0, 0); let ret = unsafe { @@ -14,3 +15,20 @@ pub fn hashmap_random_keys() -> (u64, u64) { } return v } + +#[cfg(target_vendor = "uwp")] +pub fn hashmap_random_keys() -> (u64, u64) { + use crate::ptr; + + let mut v = (0, 0); + let ret = unsafe { + c::BCryptGenRandom(ptr::null_mut(), &mut v as *mut _ as *mut u8, + mem::size_of_val(&v) as c::ULONG, + c::BCRYPT_USE_SYSTEM_PREFERRED_RNG) + }; + if ret != 0 { + panic!("couldn't generate random bytes: {}", + io::Error::last_os_error()); + } + return v +} From 0f15466080e46429d9906872b849994cedc5fa11 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Hugo=20Beauz=C3=A9e-Luyssen?= Date: Mon, 27 May 2019 16:51:29 +0200 Subject: [PATCH 07/16] std: win: Don't use SetHandleInformation on UWP Attempt to create sockets with the WSA_FLAG_NO_HANDLE_INHERIT flag, and handle the potential error gracefully (as the flag isn't support on Windows 7 before SP1) --- src/libstd/sys/windows/c.rs | 13 +++++--- src/libstd/sys/windows/net.rs | 51 ++++++++++++++++++++++++++----- src/libstd/sys/windows/pipe.rs | 9 +++++- src/libstd/sys/windows/process.rs | 7 +---- 4 files changed, 61 insertions(+), 19 deletions(-) diff --git a/src/libstd/sys/windows/c.rs b/src/libstd/sys/windows/c.rs index 42f9a0ca6b4ba..5f8bab2f2f5bd 100644 --- a/src/libstd/sys/windows/c.rs +++ b/src/libstd/sys/windows/c.rs @@ -125,6 +125,7 @@ impl Clone for WIN32_FIND_DATAW { } pub const WSA_FLAG_OVERLAPPED: DWORD = 0x01; +pub const WSA_FLAG_NO_HANDLE_INHERIT: DWORD = 0x80; pub const WSADESCRIPTION_LEN: usize = 256; pub const WSASYS_STATUS_LEN: usize = 128; @@ -134,6 +135,7 @@ pub const INVALID_SOCKET: SOCKET = !0; pub const WSAEACCES: c_int = 10013; pub const WSAEINVAL: c_int = 10022; pub const WSAEWOULDBLOCK: c_int = 10035; +pub const WSAEPROTOTYPE: c_int = 10041; pub const WSAEADDRINUSE: c_int = 10048; pub const WSAEADDRNOTAVAIL: c_int = 10049; pub const WSAECONNABORTED: c_int = 10053; @@ -161,8 +163,6 @@ pub const STD_INPUT_HANDLE: DWORD = -10i32 as DWORD; pub const STD_OUTPUT_HANDLE: DWORD = -11i32 as DWORD; pub const STD_ERROR_HANDLE: DWORD = -12i32 as DWORD; -pub const HANDLE_FLAG_INHERIT: DWORD = 0x00000001; - pub const PROGRESS_CONTINUE: DWORD = 0; pub const ERROR_FILE_NOT_FOUND: DWORD = 2; @@ -662,9 +662,15 @@ pub struct timeval { // Functions forbidden when targeting UWP #[cfg(not(target_vendor = "uwp"))] ifdef! { + pub const HANDLE_FLAG_INHERIT: DWORD = 0x00000001; + extern "system" { #[link_name = "SystemFunction036"] pub fn RtlGenRandom(RandomBuffer: *mut u8, RandomBufferLength: ULONG) -> BOOLEAN; + + pub fn SetHandleInformation(hObject: HANDLE, + dwMask: DWORD, + dwFlags: DWORD) -> BOOL; } } @@ -774,9 +780,6 @@ extern "system" { pub fn GetUserProfileDirectoryW(hToken: HANDLE, lpProfileDir: LPWSTR, lpcchSize: *mut DWORD) -> BOOL; - pub fn SetHandleInformation(hObject: HANDLE, - dwMask: DWORD, - dwFlags: DWORD) -> BOOL; pub fn CopyFileExW(lpExistingFileName: LPCWSTR, lpNewFileName: LPCWSTR, lpProgressRoutine: LPPROGRESS_ROUTINE, diff --git a/src/libstd/sys/windows/net.rs b/src/libstd/sys/windows/net.rs index 7dd1af5441bfb..32f4011fb3219 100644 --- a/src/libstd/sys/windows/net.rs +++ b/src/libstd/sys/windows/net.rs @@ -97,12 +97,26 @@ impl Socket { }; let socket = unsafe { match c::WSASocketW(fam, ty, 0, ptr::null_mut(), 0, - c::WSA_FLAG_OVERLAPPED) { - c::INVALID_SOCKET => Err(last_error()), + c::WSA_FLAG_OVERLAPPED | c::WSA_FLAG_NO_HANDLE_INHERIT) { + c::INVALID_SOCKET => { + match c::WSAGetLastError() { + c::WSAEPROTOTYPE => { + match c::WSASocketW(fam, ty, 0, ptr::null_mut(), 0, + c::WSA_FLAG_OVERLAPPED) { + c::INVALID_SOCKET => Err(last_error()), + n => { + let s = Socket(n); + s.set_no_inherit()?; + Ok(s) + }, + } + }, + n => Err(io::Error::from_raw_os_error(n)), + } + }, n => Ok(Socket(n)), } }?; - socket.set_no_inherit()?; Ok(socket) } @@ -168,7 +182,6 @@ impl Socket { n => Ok(Socket(n)), } }?; - socket.set_no_inherit()?; Ok(socket) } @@ -178,16 +191,34 @@ impl Socket { cvt(c::WSADuplicateSocketW(self.0, c::GetCurrentProcessId(), &mut info))?; + match c::WSASocketW(info.iAddressFamily, info.iSocketType, info.iProtocol, &mut info, 0, - c::WSA_FLAG_OVERLAPPED) { - c::INVALID_SOCKET => Err(last_error()), + c::WSA_FLAG_OVERLAPPED | c::WSA_FLAG_NO_HANDLE_INHERIT) { + c::INVALID_SOCKET => { + match c::WSAGetLastError() { + c::WSAEPROTOTYPE => { + match c::WSASocketW(info.iAddressFamily, + info.iSocketType, + info.iProtocol, + &mut info, 0, + c::WSA_FLAG_OVERLAPPED) { + c::INVALID_SOCKET => Err(last_error()), + n => { + let s = Socket(n); + s.set_no_inherit()?; + Ok(s) + }, + } + }, + n => Err(io::Error::from_raw_os_error(n)), + } + }, n => Ok(Socket(n)), } }?; - socket.set_no_inherit()?; Ok(socket) } @@ -312,6 +343,7 @@ impl Socket { } } + #[cfg(not(target_vendor = "uwp"))] fn set_no_inherit(&self) -> io::Result<()> { sys::cvt(unsafe { c::SetHandleInformation(self.0 as c::HANDLE, @@ -319,6 +351,11 @@ impl Socket { }).map(|_| ()) } + #[cfg(target_vendor = "uwp")] + fn set_no_inherit(&self) -> io::Result<()> { + Err(io::Error::new(io::ErrorKind::Other, "Unavailable on UWP")) + } + pub fn shutdown(&self, how: Shutdown) -> io::Result<()> { let how = match how { Shutdown::Write => c::SD_SEND, diff --git a/src/libstd/sys/windows/pipe.rs b/src/libstd/sys/windows/pipe.rs index 493ee8a9a2d7c..64b4aade6e4b8 100644 --- a/src/libstd/sys/windows/pipe.rs +++ b/src/libstd/sys/windows/pipe.rs @@ -45,7 +45,7 @@ pub struct Pipes { /// mode. This means that technically speaking it should only ever be used /// with `OVERLAPPED` instances, but also works out ok if it's only ever used /// once at a time (which we do indeed guarantee). -pub fn anon_pipe(ours_readable: bool) -> io::Result { +pub fn anon_pipe(ours_readable: bool, their_handle_inheritable: bool) -> io::Result { // Note that we specifically do *not* use `CreatePipe` here because // unfortunately the anonymous pipes returned do not support overlapped // operations. Instead, we create a "hopefully unique" name and create a @@ -137,6 +137,13 @@ pub fn anon_pipe(ours_readable: bool) -> io::Result { opts.write(ours_readable); opts.read(!ours_readable); opts.share_mode(0); + let size = mem::size_of::(); + let mut sa = c::SECURITY_ATTRIBUTES { + nLength: size as c::DWORD, + lpSecurityDescriptor: ptr::null_mut(), + bInheritHandle: their_handle_inheritable as i32, + }; + opts.security_attributes(&mut sa); let theirs = File::open(Path::new(&name), &opts)?; let theirs = AnonPipe { inner: theirs.into_handle() }; diff --git a/src/libstd/sys/windows/process.rs b/src/libstd/sys/windows/process.rs index e39b7ae889025..05e0ca6706453 100644 --- a/src/libstd/sys/windows/process.rs +++ b/src/libstd/sys/windows/process.rs @@ -267,13 +267,8 @@ impl Stdio { Stdio::MakePipe => { let ours_readable = stdio_id != c::STD_INPUT_HANDLE; - let pipes = pipe::anon_pipe(ours_readable)?; + let pipes = pipe::anon_pipe(ours_readable, true)?; *pipe = Some(pipes.ours); - cvt(unsafe { - c::SetHandleInformation(pipes.theirs.handle().raw(), - c::HANDLE_FLAG_INHERIT, - c::HANDLE_FLAG_INHERIT) - })?; Ok(pipes.theirs.into_handle()) } From 5466e9fb3851898676ed7b38b81acb13458768d3 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Hugo=20Beauz=C3=A9e-Luyssen?= Date: Mon, 27 May 2019 16:44:06 +0200 Subject: [PATCH 08/16] std: win: Don't expose link() on UWP Or rather expose it, but always return an error --- src/libstd/sys/windows/c.rs | 8 ++++---- src/libstd/sys/windows/fs.rs | 7 +++++++ 2 files changed, 11 insertions(+), 4 deletions(-) diff --git a/src/libstd/sys/windows/c.rs b/src/libstd/sys/windows/c.rs index 5f8bab2f2f5bd..f9cf94cd1bd45 100644 --- a/src/libstd/sys/windows/c.rs +++ b/src/libstd/sys/windows/c.rs @@ -671,6 +671,10 @@ ifdef! { pub fn SetHandleInformation(hObject: HANDLE, dwMask: DWORD, dwFlags: DWORD) -> BOOL; + pub fn CreateHardLinkW(lpSymlinkFileName: LPCWSTR, + lpTargetFileName: LPCWSTR, + lpSecurityAttributes: LPSECURITY_ATTRIBUTES) + -> BOOL; } } @@ -885,10 +889,6 @@ extern "system" { lpOverlapped: LPOVERLAPPED) -> BOOL; pub fn CloseHandle(hObject: HANDLE) -> BOOL; - pub fn CreateHardLinkW(lpSymlinkFileName: LPCWSTR, - lpTargetFileName: LPCWSTR, - lpSecurityAttributes: LPSECURITY_ATTRIBUTES) - -> BOOL; pub fn MoveFileExW(lpExistingFileName: LPCWSTR, lpNewFileName: LPCWSTR, dwFlags: DWORD) diff --git a/src/libstd/sys/windows/fs.rs b/src/libstd/sys/windows/fs.rs index d5cb205c85f52..f6f64a008bbfe 100644 --- a/src/libstd/sys/windows/fs.rs +++ b/src/libstd/sys/windows/fs.rs @@ -670,6 +670,7 @@ pub fn symlink_inner(src: &Path, dst: &Path, dir: bool) -> io::Result<()> { Ok(()) } +#[cfg(not(target_vendor = "uwp"))] pub fn link(src: &Path, dst: &Path) -> io::Result<()> { let src = to_u16s(src)?; let dst = to_u16s(dst)?; @@ -679,6 +680,12 @@ pub fn link(src: &Path, dst: &Path) -> io::Result<()> { Ok(()) } +#[cfg(target_vendor = "uwp")] +pub fn link(_src: &Path, _dst: &Path) -> io::Result<()> { + return Err(io::Error::new(io::ErrorKind::Other, + "hard link are not supported on UWP")); +} + pub fn stat(path: &Path) -> io::Result { let mut opts = OpenOptions::new(); // No read or write permissions are necessary From b514557acb0300c9f2d3755c0b133335251e4b00 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Hugo=20Beauz=C3=A9e-Luyssen?= Date: Mon, 27 May 2019 17:07:33 +0200 Subject: [PATCH 09/16] std: win: Don't use GetUserProfileDirectoryW on UWP --- src/libstd/sys/windows/c.rs | 16 +++++++++------- src/libstd/sys/windows/os.rs | 23 +++++++++++++++++------ 2 files changed, 26 insertions(+), 13 deletions(-) diff --git a/src/libstd/sys/windows/c.rs b/src/libstd/sys/windows/c.rs index f9cf94cd1bd45..fe2226a754a0f 100644 --- a/src/libstd/sys/windows/c.rs +++ b/src/libstd/sys/windows/c.rs @@ -147,7 +147,6 @@ pub const WSAECONNREFUSED: c_int = 10061; pub const MAX_PROTOCOL_CHAIN: DWORD = 7; -pub const TOKEN_READ: DWORD = 0x20008; pub const MAXIMUM_REPARSE_DATA_BUFFER_SIZE: usize = 16 * 1024; pub const FSCTL_GET_REPARSE_POINT: DWORD = 0x900a8; pub const IO_REPARSE_TAG_SYMLINK: DWORD = 0xa000000c; @@ -664,10 +663,19 @@ pub struct timeval { ifdef! { pub const HANDLE_FLAG_INHERIT: DWORD = 0x00000001; + pub const TOKEN_READ: DWORD = 0x20008; + extern "system" { #[link_name = "SystemFunction036"] pub fn RtlGenRandom(RandomBuffer: *mut u8, RandomBufferLength: ULONG) -> BOOLEAN; + // Allowed but unused by UWP + pub fn OpenProcessToken(ProcessHandle: HANDLE, + DesiredAccess: DWORD, + TokenHandle: *mut HANDLE) -> BOOL; + pub fn GetUserProfileDirectoryW(hToken: HANDLE, + lpProfileDir: LPWSTR, + lpcchSize: *mut DWORD) -> BOOL; pub fn SetHandleInformation(hObject: HANDLE, dwMask: DWORD, dwFlags: DWORD) -> BOOL; @@ -754,9 +762,6 @@ extern "system" { pub fn GetCommandLineW() -> *mut LPCWSTR; pub fn GetTempPathW(nBufferLength: DWORD, lpBuffer: LPCWSTR) -> DWORD; - pub fn OpenProcessToken(ProcessHandle: HANDLE, - DesiredAccess: DWORD, - TokenHandle: *mut HANDLE) -> BOOL; pub fn GetCurrentProcess() -> HANDLE; pub fn GetCurrentThread() -> HANDLE; pub fn GetStdHandle(which: DWORD) -> HANDLE; @@ -781,9 +786,6 @@ extern "system" { pub fn SwitchToThread() -> BOOL; pub fn Sleep(dwMilliseconds: DWORD); pub fn GetProcessId(handle: HANDLE) -> DWORD; - pub fn GetUserProfileDirectoryW(hToken: HANDLE, - lpProfileDir: LPWSTR, - lpcchSize: *mut DWORD) -> BOOL; pub fn CopyFileExW(lpExistingFileName: LPCWSTR, lpNewFileName: LPCWSTR, lpProgressRoutine: LPPROGRESS_ROUTINE, diff --git a/src/libstd/sys/windows/os.rs b/src/libstd/sys/windows/os.rs index 4e50b5521eb04..7c400dce686f3 100644 --- a/src/libstd/sys/windows/os.rs +++ b/src/libstd/sys/windows/os.rs @@ -13,7 +13,6 @@ use crate::path::{self, PathBuf}; use crate::ptr; use crate::slice; use crate::sys::{c, cvt}; -use crate::sys::handle::Handle; use super::to_u16s; @@ -284,10 +283,11 @@ pub fn temp_dir() -> PathBuf { }, super::os2path).unwrap() } -pub fn home_dir() -> Option { - crate::env::var_os("HOME").or_else(|| { - crate::env::var_os("USERPROFILE") - }).map(PathBuf::from).or_else(|| unsafe { +#[cfg(not(target_vendor = "uwp"))] +fn home_dir_crt() -> Option { + unsafe { + use crate::sys::handle::Handle; + let me = c::GetCurrentProcess(); let mut token = ptr::null_mut(); if c::OpenProcessToken(me, c::TOKEN_READ, &mut token) == 0 { @@ -301,7 +301,18 @@ pub fn home_dir() -> Option { _ => sz - 1, // sz includes the null terminator } }, super::os2path).ok() - }) + } +} + +#[cfg(target_vendor = "uwp")] +fn home_dir_crt() -> Option { + None +} + +pub fn home_dir() -> Option { + crate::env::var_os("HOME").or_else(|| { + crate::env::var_os("USERPROFILE") + }).map(PathBuf::from).or_else(|| home_dir_crt()) } pub fn exit(code: i32) -> ! { From 07d11aed3d31859c8dbf5539db64723262e09f8f Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Hugo=20Beauz=C3=A9e-Luyssen?= Date: Mon, 27 May 2019 17:13:04 +0200 Subject: [PATCH 10/16] std: win: Don't use GetFileInformationByHandle on UWP --- src/libstd/sys/windows/c.rs | 51 ++++++++++++++++++++++-------------- src/libstd/sys/windows/fs.rs | 44 +++++++++++++++++++++++++++++++ 2 files changed, 76 insertions(+), 19 deletions(-) diff --git a/src/libstd/sys/windows/c.rs b/src/libstd/sys/windows/c.rs index fe2226a754a0f..9c9d3cd878c82 100644 --- a/src/libstd/sys/windows/c.rs +++ b/src/libstd/sys/windows/c.rs @@ -38,7 +38,6 @@ pub type ULONG = c_ulong; pub type LPBOOL = *mut BOOL; pub type LPBYTE = *mut BYTE; -pub type LPBY_HANDLE_FILE_INFORMATION = *mut BY_HANDLE_FILE_INFORMATION; pub type LPCSTR = *const CHAR; pub type LPCVOID = *const c_void; pub type LPCWSTR = *const WCHAR; @@ -345,20 +344,6 @@ pub struct WIN32_FILE_ATTRIBUTE_DATA { pub nFileSizeLow: DWORD, } -#[repr(C)] -pub struct BY_HANDLE_FILE_INFORMATION { - pub dwFileAttributes: DWORD, - pub ftCreationTime: FILETIME, - pub ftLastAccessTime: FILETIME, - pub ftLastWriteTime: FILETIME, - pub dwVolumeSerialNumber: DWORD, - pub nFileSizeHigh: DWORD, - pub nFileSizeLow: DWORD, - pub nNumberOfLinks: DWORD, - pub nFileIndexHigh: DWORD, - pub nFileIndexLow: DWORD, -} - #[repr(C)] #[allow(dead_code)] // we only use some variants pub enum FILE_INFO_BY_HANDLE_CLASS { @@ -661,6 +646,22 @@ pub struct timeval { // Functions forbidden when targeting UWP #[cfg(not(target_vendor = "uwp"))] ifdef! { + #[repr(C)] + pub struct BY_HANDLE_FILE_INFORMATION { + pub dwFileAttributes: DWORD, + pub ftCreationTime: FILETIME, + pub ftLastAccessTime: FILETIME, + pub ftLastWriteTime: FILETIME, + pub dwVolumeSerialNumber: DWORD, + pub nFileSizeHigh: DWORD, + pub nFileSizeLow: DWORD, + pub nNumberOfLinks: DWORD, + pub nFileIndexHigh: DWORD, + pub nFileIndexLow: DWORD, + } + + pub type LPBY_HANDLE_FILE_INFORMATION = *mut BY_HANDLE_FILE_INFORMATION; + pub const HANDLE_FLAG_INHERIT: DWORD = 0x00000001; pub const TOKEN_READ: DWORD = 0x20008; @@ -676,6 +677,9 @@ ifdef! { pub fn GetUserProfileDirectoryW(hToken: HANDLE, lpProfileDir: LPWSTR, lpcchSize: *mut DWORD) -> BOOL; + pub fn GetFileInformationByHandle(hFile: HANDLE, + lpFileInformation: LPBY_HANDLE_FILE_INFORMATION) + -> BOOL; pub fn SetHandleInformation(hObject: HANDLE, dwMask: DWORD, dwFlags: DWORD) -> BOOL; @@ -691,7 +695,20 @@ ifdef! { ifdef! { pub const BCRYPT_USE_SYSTEM_PREFERRED_RNG: DWORD = 0x00000002; + #[repr(C)] + pub struct FILE_STANDARD_INFO { + pub AllocationSize: LARGE_INTEGER, + pub EndOfFile: LARGE_INTEGER, + pub NumberOfLink: DWORD, + pub DeletePending: BOOLEAN, + pub Directory: BOOLEAN, + } + extern "system" { + pub fn GetFileInformationByHandleEx(hFile: HANDLE, + fileInfoClass: FILE_INFO_BY_HANDLE_CLASS, + lpFileInformation: LPVOID, + dwBufferSize: DWORD) -> BOOL; pub fn BCryptGenRandom(hAlgorithm: LPVOID, pBuffer: *mut u8, cbBuffer: ULONG, dwFlags: ULONG) -> LONG; } @@ -754,10 +771,6 @@ extern "system" { pub fn RemoveDirectoryW(lpPathName: LPCWSTR) -> BOOL; pub fn SetFileAttributesW(lpFileName: LPCWSTR, dwFileAttributes: DWORD) -> BOOL; - pub fn GetFileInformationByHandle(hFile: HANDLE, - lpFileInformation: LPBY_HANDLE_FILE_INFORMATION) - -> BOOL; - pub fn SetLastError(dwErrCode: DWORD); pub fn GetCommandLineW() -> *mut LPCWSTR; pub fn GetTempPathW(nBufferLength: DWORD, diff --git a/src/libstd/sys/windows/fs.rs b/src/libstd/sys/windows/fs.rs index f6f64a008bbfe..2f158c014060b 100644 --- a/src/libstd/sys/windows/fs.rs +++ b/src/libstd/sys/windows/fs.rs @@ -287,6 +287,7 @@ impl File { Ok(()) } + #[cfg(not(target_vendor = "uwp"))] pub fn file_attr(&self) -> io::Result { unsafe { let mut info: c::BY_HANDLE_FILE_INFORMATION = mem::zeroed(); @@ -310,6 +311,49 @@ impl File { } } + #[cfg(target_vendor = "uwp")] + pub fn file_attr(&self) -> io::Result { + unsafe { + let mut info: c::FILE_BASIC_INFO = mem::zeroed(); + let size = mem::size_of_val(&info); + cvt(c::GetFileInformationByHandleEx(self.handle.raw(), + c::FileBasicInfo, + &mut info as *mut _ as *mut libc::c_void, + size as c::DWORD))?; + let mut attr = FileAttr { + attributes: info.FileAttributes, + creation_time: c::FILETIME { + dwLowDateTime: info.CreationTime as c::DWORD, + dwHighDateTime: (info.CreationTime >> 32) as c::DWORD, + }, + last_access_time: c::FILETIME { + dwLowDateTime: info.LastAccessTime as c::DWORD, + dwHighDateTime: (info.LastAccessTime >> 32) as c::DWORD, + }, + last_write_time: c::FILETIME { + dwLowDateTime: info.LastWriteTime as c::DWORD, + dwHighDateTime: (info.LastWriteTime >> 32) as c::DWORD, + }, + file_size: 0, + reparse_tag: 0, + }; + let mut info: c::FILE_STANDARD_INFO = mem::zeroed(); + let size = mem::size_of_val(&info); + cvt(c::GetFileInformationByHandleEx(self.handle.raw(), + c::FileStandardInfo, + &mut info as *mut _ as *mut libc::c_void, + size as c::DWORD))?; + attr.file_size = info.AllocationSize as u64; + if attr.is_reparse_point() { + let mut b = [0; c::MAXIMUM_REPARSE_DATA_BUFFER_SIZE]; + if let Ok((_, buf)) = self.reparse_point(&mut b) { + attr.reparse_tag = buf.ReparseTag; + } + } + Ok(attr) + } + } + pub fn read(&self, buf: &mut [u8]) -> io::Result { self.handle.read(buf) } From a7ad6992a22121579d129c178d28ec1ca290b49a Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Hugo=20Beauz=C3=A9e-Luyssen?= Date: Mon, 27 May 2019 17:15:27 +0200 Subject: [PATCH 11/16] std: win: Don't use console APIs on UWP --- src/libstd/sys/windows/c.rs | 51 ++++++++--------- src/libstd/sys/windows/mod.rs | 9 ++- src/libstd/sys/windows/stdio_uwp.rs | 85 +++++++++++++++++++++++++++++ 3 files changed, 119 insertions(+), 26 deletions(-) create mode 100644 src/libstd/sys/windows/stdio_uwp.rs diff --git a/src/libstd/sys/windows/c.rs b/src/libstd/sys/windows/c.rs index 9c9d3cd878c82..b3c5bd201ba91 100644 --- a/src/libstd/sys/windows/c.rs +++ b/src/libstd/sys/windows/c.rs @@ -39,7 +39,6 @@ pub type ULONG = c_ulong; pub type LPBOOL = *mut BOOL; pub type LPBYTE = *mut BYTE; pub type LPCSTR = *const CHAR; -pub type LPCVOID = *const c_void; pub type LPCWSTR = *const WCHAR; pub type LPDWORD = *mut DWORD; pub type LPHANDLE = *mut HANDLE; @@ -613,16 +612,6 @@ pub enum EXCEPTION_DISPOSITION { ExceptionCollidedUnwind } -#[repr(C)] -#[derive(Copy, Clone)] -pub struct CONSOLE_READCONSOLE_CONTROL { - pub nLength: ULONG, - pub nInitialChars: ULONG, - pub dwCtrlWakeupMask: ULONG, - pub dwControlKeyState: ULONG, -} -pub type PCONSOLE_READCONSOLE_CONTROL = *mut CONSOLE_READCONSOLE_CONTROL; - #[repr(C)] #[derive(Copy)] pub struct fd_set { @@ -646,6 +635,17 @@ pub struct timeval { // Functions forbidden when targeting UWP #[cfg(not(target_vendor = "uwp"))] ifdef! { + #[repr(C)] + #[derive(Copy, Clone)] + pub struct CONSOLE_READCONSOLE_CONTROL { + pub nLength: ULONG, + pub nInitialChars: ULONG, + pub dwCtrlWakeupMask: ULONG, + pub dwControlKeyState: ULONG, + } + + pub type PCONSOLE_READCONSOLE_CONTROL = *mut CONSOLE_READCONSOLE_CONTROL; + #[repr(C)] pub struct BY_HANDLE_FILE_INFORMATION { pub dwFileAttributes: DWORD, @@ -661,6 +661,7 @@ ifdef! { } pub type LPBY_HANDLE_FILE_INFORMATION = *mut BY_HANDLE_FILE_INFORMATION; + pub type LPCVOID = *const c_void; pub const HANDLE_FLAG_INHERIT: DWORD = 0x00000001; @@ -670,6 +671,20 @@ ifdef! { #[link_name = "SystemFunction036"] pub fn RtlGenRandom(RandomBuffer: *mut u8, RandomBufferLength: ULONG) -> BOOLEAN; + pub fn ReadConsoleW(hConsoleInput: HANDLE, + lpBuffer: LPVOID, + nNumberOfCharsToRead: DWORD, + lpNumberOfCharsRead: LPDWORD, + pInputControl: PCONSOLE_READCONSOLE_CONTROL) -> BOOL; + + pub fn WriteConsoleW(hConsoleOutput: HANDLE, + lpBuffer: LPCVOID, + nNumberOfCharsToWrite: DWORD, + lpNumberOfCharsWritten: LPDWORD, + lpReserved: LPVOID) -> BOOL; + + pub fn GetConsoleMode(hConsoleHandle: HANDLE, + lpMode: LPDWORD) -> BOOL; // Allowed but unused by UWP pub fn OpenProcessToken(ProcessHandle: HANDLE, DesiredAccess: DWORD, @@ -754,20 +769,6 @@ extern "system" { pub fn LeaveCriticalSection(CriticalSection: *mut CRITICAL_SECTION); pub fn DeleteCriticalSection(CriticalSection: *mut CRITICAL_SECTION); - pub fn ReadConsoleW(hConsoleInput: HANDLE, - lpBuffer: LPVOID, - nNumberOfCharsToRead: DWORD, - lpNumberOfCharsRead: LPDWORD, - pInputControl: PCONSOLE_READCONSOLE_CONTROL) -> BOOL; - - pub fn WriteConsoleW(hConsoleOutput: HANDLE, - lpBuffer: LPCVOID, - nNumberOfCharsToWrite: DWORD, - lpNumberOfCharsWritten: LPDWORD, - lpReserved: LPVOID) -> BOOL; - - pub fn GetConsoleMode(hConsoleHandle: HANDLE, - lpMode: LPDWORD) -> BOOL; pub fn RemoveDirectoryW(lpPathName: LPCWSTR) -> BOOL; pub fn SetFileAttributesW(lpFileName: LPCWSTR, dwFileAttributes: DWORD) -> BOOL; diff --git a/src/libstd/sys/windows/mod.rs b/src/libstd/sys/windows/mod.rs index 1cb5553912981..13f6775021fa3 100644 --- a/src/libstd/sys/windows/mod.rs +++ b/src/libstd/sys/windows/mod.rs @@ -37,7 +37,14 @@ pub mod stack_overflow; pub mod thread; pub mod thread_local; pub mod time; -pub mod stdio; +cfg_if! { + if #[cfg(not(target_vendor = "uwp"))] { + pub mod stdio; + } else { + pub mod stdio_uwp; + pub use self::stdio_uwp as stdio; + } +} #[cfg(not(test))] pub fn init() { diff --git a/src/libstd/sys/windows/stdio_uwp.rs b/src/libstd/sys/windows/stdio_uwp.rs new file mode 100644 index 0000000000000..489d3df28600b --- /dev/null +++ b/src/libstd/sys/windows/stdio_uwp.rs @@ -0,0 +1,85 @@ +#![unstable(issue = "0", feature = "windows_stdio")] + +use crate::io; +use crate::sys::c; +use crate::sys::handle::Handle; +use crate::mem::ManuallyDrop; + +pub struct Stdin { +} +pub struct Stdout; +pub struct Stderr; + +const MAX_BUFFER_SIZE: usize = 8192; +pub const STDIN_BUF_SIZE: usize = MAX_BUFFER_SIZE / 2 * 3; + +pub fn get_handle(handle_id: c::DWORD) -> io::Result { + let handle = unsafe { c::GetStdHandle(handle_id) }; + if handle == c::INVALID_HANDLE_VALUE { + Err(io::Error::last_os_error()) + } else if handle.is_null() { + Err(io::Error::from_raw_os_error(c::ERROR_INVALID_HANDLE as i32)) + } else { + Ok(handle) + } +} + +fn write(handle_id: c::DWORD, data: &[u8]) -> io::Result { + let handle = get_handle(handle_id)?; + let handle = Handle::new(handle); + ManuallyDrop::new(handle).write(data) +} + +impl Stdin { + pub fn new() -> io::Result { + Ok(Stdin { }) + } +} + +impl io::Read for Stdin { + fn read(&mut self, buf: &mut [u8]) -> io::Result { + let handle = get_handle(c::STD_INPUT_HANDLE)?; + let handle = Handle::new(handle); + ManuallyDrop::new(handle).read(buf) + } +} + +impl Stdout { + pub fn new() -> io::Result { + Ok(Stdout) + } +} + +impl io::Write for Stdout { + fn write(&mut self, buf: &[u8]) -> io::Result { + write(c::STD_OUTPUT_HANDLE, buf) + } + + fn flush(&mut self) -> io::Result<()> { + Ok(()) + } +} + +impl Stderr { + pub fn new() -> io::Result { + Ok(Stderr) + } +} + +impl io::Write for Stderr { + fn write(&mut self, buf: &[u8]) -> io::Result { + write(c::STD_ERROR_HANDLE, buf) + } + + fn flush(&mut self) -> io::Result<()> { + Ok(()) + } +} + +pub fn is_ebadf(err: &io::Error) -> bool { + err.raw_os_error() == Some(c::ERROR_INVALID_HANDLE as i32) +} + +pub fn panic_output() -> Option { + Stderr::new().ok() +} From 1a0a263a32d5c880121e6256ff7e87cb508f48f6 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Hugo=20Beauz=C3=A9e-Luyssen?= Date: Mon, 27 May 2019 17:16:20 +0200 Subject: [PATCH 12/16] std: win: Disable stack overflow handling on UWP The required functions are not available, so hope for the best --- src/libstd/sys/windows/c.rs | 57 ++++++++++---------- src/libstd/sys/windows/mod.rs | 4 +- src/libstd/sys/windows/stack_overflow_uwp.rs | 13 +++++ 3 files changed, 45 insertions(+), 29 deletions(-) create mode 100644 src/libstd/sys/windows/stack_overflow_uwp.rs diff --git a/src/libstd/sys/windows/c.rs b/src/libstd/sys/windows/c.rs index b3c5bd201ba91..33f82e47d9e41 100644 --- a/src/libstd/sys/windows/c.rs +++ b/src/libstd/sys/windows/c.rs @@ -260,10 +260,6 @@ pub const WAIT_OBJECT_0: DWORD = 0x00000000; pub const WAIT_TIMEOUT: DWORD = 258; pub const WAIT_FAILED: DWORD = 0xFFFFFFFF; -pub const EXCEPTION_CONTINUE_SEARCH: LONG = 0; -pub const EXCEPTION_STACK_OVERFLOW: DWORD = 0xc00000fd; -pub const EXCEPTION_MAXIMUM_PARAMETERS: usize = 15; - pub const PIPE_ACCESS_INBOUND: DWORD = 0x00000001; pub const PIPE_ACCESS_OUTBOUND: DWORD = 0x00000002; pub const FILE_FLAG_FIRST_PIPE_INSTANCE: DWORD = 0x00080000; @@ -448,25 +444,6 @@ pub struct REPARSE_MOUNTPOINT_DATA_BUFFER { pub ReparseTarget: WCHAR, } -#[repr(C)] -pub struct EXCEPTION_RECORD { - pub ExceptionCode: DWORD, - pub ExceptionFlags: DWORD, - pub ExceptionRecord: *mut EXCEPTION_RECORD, - pub ExceptionAddress: LPVOID, - pub NumberParameters: DWORD, - pub ExceptionInformation: [LPVOID; EXCEPTION_MAXIMUM_PARAMETERS] -} - -#[repr(C)] -pub struct EXCEPTION_POINTERS { - pub ExceptionRecord: *mut EXCEPTION_RECORD, - pub ContextRecord: *mut CONTEXT, -} - -pub type PVECTORED_EXCEPTION_HANDLER = extern "system" - fn(ExceptionInfo: *mut EXCEPTION_POINTERS) -> LONG; - #[repr(C)] pub struct GUID { pub Data1: DWORD, @@ -549,8 +526,6 @@ pub enum ADDRESS_MODE { AddrModeFlat, } -pub enum CONTEXT {} - #[repr(C)] pub struct SOCKADDR_STORAGE_LH { pub ss_family: ADDRESS_FAMILY, @@ -635,6 +610,31 @@ pub struct timeval { // Functions forbidden when targeting UWP #[cfg(not(target_vendor = "uwp"))] ifdef! { + pub const EXCEPTION_CONTINUE_SEARCH: LONG = 0; + pub const EXCEPTION_STACK_OVERFLOW: DWORD = 0xc00000fd; + pub const EXCEPTION_MAXIMUM_PARAMETERS: usize = 15; + + #[repr(C)] + pub struct EXCEPTION_RECORD { + pub ExceptionCode: DWORD, + pub ExceptionFlags: DWORD, + pub ExceptionRecord: *mut EXCEPTION_RECORD, + pub ExceptionAddress: LPVOID, + pub NumberParameters: DWORD, + pub ExceptionInformation: [LPVOID; EXCEPTION_MAXIMUM_PARAMETERS] + } + + pub enum CONTEXT {} + + #[repr(C)] + pub struct EXCEPTION_POINTERS { + pub ExceptionRecord: *mut EXCEPTION_RECORD, + pub ContextRecord: *mut CONTEXT, + } + + pub type PVECTORED_EXCEPTION_HANDLER = extern "system" + fn(ExceptionInfo: *mut EXCEPTION_POINTERS) -> LONG; + #[repr(C)] #[derive(Copy, Clone)] pub struct CONSOLE_READCONSOLE_CONTROL { @@ -698,6 +698,9 @@ ifdef! { pub fn SetHandleInformation(hObject: HANDLE, dwMask: DWORD, dwFlags: DWORD) -> BOOL; + pub fn AddVectoredExceptionHandler(FirstHandler: ULONG, + VectoredHandler: PVECTORED_EXCEPTION_HANDLER) + -> LPVOID; pub fn CreateHardLinkW(lpSymlinkFileName: LPCWSTR, lpTargetFileName: LPCWSTR, lpSecurityAttributes: LPSECURITY_ATTRIBUTES) @@ -806,9 +809,6 @@ extern "system" { lpData: LPVOID, pbCancel: LPBOOL, dwCopyFlags: DWORD) -> BOOL; - pub fn AddVectoredExceptionHandler(FirstHandler: ULONG, - VectoredHandler: PVECTORED_EXCEPTION_HANDLER) - -> LPVOID; pub fn FormatMessageW(flags: DWORD, lpSrc: LPVOID, msgId: DWORD, @@ -1017,6 +1017,7 @@ compat_fn! { _dwFlags: DWORD) -> DWORD { SetLastError(ERROR_CALL_NOT_IMPLEMENTED as DWORD); 0 } + #[cfg(not(target_vendor = "uwp"))] pub fn SetThreadStackGuarantee(_size: *mut c_ulong) -> BOOL { SetLastError(ERROR_CALL_NOT_IMPLEMENTED as DWORD); 0 } diff --git a/src/libstd/sys/windows/mod.rs b/src/libstd/sys/windows/mod.rs index 13f6775021fa3..63f4ab7ad1708 100644 --- a/src/libstd/sys/windows/mod.rs +++ b/src/libstd/sys/windows/mod.rs @@ -33,16 +33,18 @@ pub mod pipe; pub mod process; pub mod rand; pub mod rwlock; -pub mod stack_overflow; pub mod thread; pub mod thread_local; pub mod time; cfg_if! { if #[cfg(not(target_vendor = "uwp"))] { pub mod stdio; + pub mod stack_overflow; } else { pub mod stdio_uwp; + pub mod stack_overflow_uwp; pub use self::stdio_uwp as stdio; + pub use self::stack_overflow_uwp as stack_overflow; } } diff --git a/src/libstd/sys/windows/stack_overflow_uwp.rs b/src/libstd/sys/windows/stack_overflow_uwp.rs new file mode 100644 index 0000000000000..e7236cf359cd5 --- /dev/null +++ b/src/libstd/sys/windows/stack_overflow_uwp.rs @@ -0,0 +1,13 @@ +#![cfg_attr(test, allow(dead_code))] + +pub struct Handler; + +impl Handler { + pub fn new() -> Handler { + Handler + } +} + +pub unsafe fn init() {} + +pub unsafe fn cleanup() {} From 1726259075c80621c3ee3ec17d33b06e4014c98e Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Hugo=20Beauz=C3=A9e-Luyssen?= Date: Mon, 27 May 2019 17:18:14 +0200 Subject: [PATCH 13/16] Add UWP targets --- .../spec/i686_uwp_windows_gnu.rs | 27 ++++++++ src/librustc_target/spec/mod.rs | 3 + src/librustc_target/spec/windows_uwp_base.rs | 64 +++++++++++++++++++ .../spec/x86_64_uwp_windows_gnu.rs | 22 +++++++ 4 files changed, 116 insertions(+) create mode 100644 src/librustc_target/spec/i686_uwp_windows_gnu.rs create mode 100644 src/librustc_target/spec/windows_uwp_base.rs create mode 100644 src/librustc_target/spec/x86_64_uwp_windows_gnu.rs diff --git a/src/librustc_target/spec/i686_uwp_windows_gnu.rs b/src/librustc_target/spec/i686_uwp_windows_gnu.rs new file mode 100644 index 0000000000000..3ad77525eb37d --- /dev/null +++ b/src/librustc_target/spec/i686_uwp_windows_gnu.rs @@ -0,0 +1,27 @@ +use crate::spec::{LinkerFlavor, Target, TargetResult}; + +pub fn target() -> TargetResult { + let mut base = super::windows_uwp_base::opts(); + base.cpu = "pentium4".to_string(); + base.max_atomic_width = Some(64); + base.eliminate_frame_pointer = false; // Required for backtraces + + // Mark all dynamic libraries and executables as compatible with the larger 4GiB address + // space available to x86 Windows binaries on x86_64. + base.pre_link_args + .get_mut(&LinkerFlavor::Gcc).unwrap().push("-Wl,--large-address-aware".to_string()); + + Ok(Target { + llvm_target: "i686-pc-windows-gnu".to_string(), + target_endian: "little".to_string(), + target_pointer_width: "32".to_string(), + target_c_int_width: "32".to_string(), + data_layout: "e-m:x-p:32:32-i64:64-f80:32-n8:16:32-a:0:32-S32".to_string(), + arch: "x86".to_string(), + target_os: "windows".to_string(), + target_env: "gnu".to_string(), + target_vendor: "uwp".to_string(), + linker_flavor: LinkerFlavor::Gcc, + options: base, + }) +} diff --git a/src/librustc_target/spec/mod.rs b/src/librustc_target/spec/mod.rs index 75821aba4706e..a96dc81256a24 100644 --- a/src/librustc_target/spec/mod.rs +++ b/src/librustc_target/spec/mod.rs @@ -60,6 +60,7 @@ mod solaris_base; mod uefi_base; mod windows_base; mod windows_msvc_base; +mod windows_uwp_base; mod thumb_base; mod l4re_base; mod fuchsia_base; @@ -433,6 +434,8 @@ supported_targets! { ("x86_64-pc-windows-gnu", x86_64_pc_windows_gnu), ("i686-pc-windows-gnu", i686_pc_windows_gnu), + ("i686-uwp-windows-gnu", i686_uwp_windows_gnu), + ("x86_64-uwp-windows-gnu", x86_64_uwp_windows_gnu), ("aarch64-pc-windows-msvc", aarch64_pc_windows_msvc), ("x86_64-pc-windows-msvc", x86_64_pc_windows_msvc), diff --git a/src/librustc_target/spec/windows_uwp_base.rs b/src/librustc_target/spec/windows_uwp_base.rs new file mode 100644 index 0000000000000..108dbc417cbb3 --- /dev/null +++ b/src/librustc_target/spec/windows_uwp_base.rs @@ -0,0 +1,64 @@ +use crate::spec::{LinkArgs, LinkerFlavor, TargetOptions}; +use std::default::Default; + +pub fn opts() -> TargetOptions { + let mut pre_link_args = LinkArgs::new(); + pre_link_args.insert(LinkerFlavor::Gcc, vec![ + // Tell GCC to avoid linker plugins, because we are not bundling + // them with Windows installer, and Rust does its own LTO anyways. + "-fno-use-linker-plugin".to_string(), + + // Always enable DEP (NX bit) when it is available + "-Wl,--nxcompat".to_string(), + ]); + + let mut late_link_args = LinkArgs::new(); + late_link_args.insert(LinkerFlavor::Gcc, vec![ + //"-lwinstorecompat".to_string(), + //"-lmingwex".to_string(), + //"-lwinstorecompat".to_string(), + "-lwinstorecompat".to_string(), + "-lruntimeobject".to_string(), + "-lsynchronization".to_string(), + "-lvcruntime140_app".to_string(), + "-lucrt".to_string(), + "-lwindowsapp".to_string(), + "-lmingwex".to_string(), + "-lmingw32".to_string(), + ]); + + TargetOptions { + // FIXME(#13846) this should be enabled for windows + function_sections: false, + linker: Some("gcc".to_string()), + dynamic_linking: true, + executables: false, + dll_prefix: String::new(), + dll_suffix: ".dll".to_string(), + exe_suffix: ".exe".to_string(), + staticlib_prefix: "lib".to_string(), + staticlib_suffix: ".a".to_string(), + no_default_libraries: true, + target_family: Some("windows".to_string()), + is_like_windows: true, + allows_weak_linkage: false, + pre_link_args, + pre_link_objects_exe: vec![ + "rsbegin.o".to_string(), // Rust compiler runtime initialization, see rsbegin.rs + ], + pre_link_objects_dll: vec![ + "rsbegin.o".to_string(), + ], + late_link_args, + post_link_objects: vec![ + "rsend.o".to_string(), + ], + custom_unwind_resume: true, + abi_return_struct_as_int: true, + emit_debug_gdb_scripts: false, + requires_uwtable: true, + limit_rdylib_exports: false, + + .. Default::default() + } +} diff --git a/src/librustc_target/spec/x86_64_uwp_windows_gnu.rs b/src/librustc_target/spec/x86_64_uwp_windows_gnu.rs new file mode 100644 index 0000000000000..da0c324e48618 --- /dev/null +++ b/src/librustc_target/spec/x86_64_uwp_windows_gnu.rs @@ -0,0 +1,22 @@ +use crate::spec::{LinkerFlavor, Target, TargetResult}; + +pub fn target() -> TargetResult { + let mut base = super::windows_uwp_base::opts(); + base.cpu = "x86-64".to_string(); + base.pre_link_args.get_mut(&LinkerFlavor::Gcc).unwrap().push("-m64".to_string()); + base.max_atomic_width = Some(64); + + Ok(Target { + llvm_target: "x86_64-pc-windows-gnu".to_string(), + target_endian: "little".to_string(), + target_pointer_width: "64".to_string(), + target_c_int_width: "32".to_string(), + data_layout: "e-m:w-i64:64-f80:128-n8:16:32:64-S128".to_string(), + arch: "x86_64".to_string(), + target_os: "windows".to_string(), + target_env: "gnu".to_string(), + target_vendor: "uwp".to_string(), + linker_flavor: LinkerFlavor::Gcc, + options: base, + }) +} From 9d798b71988fd70e9f8147c48edd13a9d8555a32 Mon Sep 17 00:00:00 2001 From: Eric Huss Date: Tue, 25 Jun 2019 13:31:05 -0700 Subject: [PATCH 14/16] Adjust warning of -C extra-filename with -o. --- src/librustc_interface/util.rs | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/src/librustc_interface/util.rs b/src/librustc_interface/util.rs index a86d3cc43948d..6ae5e94b11af3 100644 --- a/src/librustc_interface/util.rs +++ b/src/librustc_interface/util.rs @@ -642,14 +642,14 @@ pub fn build_output_filenames( ); None } else { + if !sess.opts.cg.extra_filename.is_empty() { + sess.warn("ignoring -C extra-filename flag due to -o flag"); + } Some(out_file.clone()) }; if *odir != None { sess.warn("ignoring --out-dir flag due to -o flag"); } - if !sess.opts.cg.extra_filename.is_empty() { - sess.warn("ignoring -C extra-filename flag due to -o flag"); - } OutputFilenames { out_directory: out_file.parent().unwrap_or_else(|| Path::new("")).to_path_buf(), From 722cfc4797406e2cd98f61e95cf390103338c7c1 Mon Sep 17 00:00:00 2001 From: Alex Crichton Date: Wed, 26 Jun 2019 08:24:43 -0700 Subject: [PATCH 15/16] Update the `rust-installer` submodule This pulls in a commit which uses parallel xz encoding which should hopefully help shave some time off the dist builders which spend an inordinate amount of time compressing this data. --- Cargo.lock | 3 ++- src/tools/rust-installer | 2 +- 2 files changed, 3 insertions(+), 2 deletions(-) diff --git a/Cargo.lock b/Cargo.lock index eaec52a7a150c..f03a83f1c2ad7 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -1272,9 +1272,10 @@ name = "installer" version = "0.0.0" dependencies = [ "clap 2.32.0 (registry+https://github.com/rust-lang/crates.io-index)", - "error-chain 0.12.0 (registry+https://github.com/rust-lang/crates.io-index)", + "failure 0.1.5 (registry+https://github.com/rust-lang/crates.io-index)", "flate2 1.0.6 (registry+https://github.com/rust-lang/crates.io-index)", "lazy_static 1.3.0 (registry+https://github.com/rust-lang/crates.io-index)", + "num_cpus 1.8.0 (registry+https://github.com/rust-lang/crates.io-index)", "rayon 1.0.1 (registry+https://github.com/rust-lang/crates.io-index)", "tar 0.4.20 (registry+https://github.com/rust-lang/crates.io-index)", "walkdir 2.2.7 (registry+https://github.com/rust-lang/crates.io-index)", diff --git a/src/tools/rust-installer b/src/tools/rust-installer index ccdc47b657a76..4b07f7bc20910 160000 --- a/src/tools/rust-installer +++ b/src/tools/rust-installer @@ -1 +1 @@ -Subproject commit ccdc47b657a7600cbd0c2858eb52a8d712cfce18 +Subproject commit 4b07f7bc2091052c6f52b780971f44e07bd3c71d From e991abd00455b20bb96076bbeec63e56764fc822 Mon Sep 17 00:00:00 2001 From: Andy Russell Date: Wed, 26 Jun 2019 21:15:13 -0400 Subject: [PATCH 16/16] remove unused derives and variants --- src/librustdoc/clean/cfg.rs | 2 +- src/librustdoc/clean/mod.rs | 111 +++++++++++++++---------------- src/librustdoc/doctree.rs | 2 +- src/librustdoc/html/format.rs | 3 - src/librustdoc/html/item_type.rs | 1 - src/librustdoc/html/render.rs | 3 - src/librustdoc/lib.rs | 2 - 7 files changed, 56 insertions(+), 68 deletions(-) diff --git a/src/librustdoc/clean/cfg.rs b/src/librustdoc/clean/cfg.rs index 67113787915a3..ad211763a6c46 100644 --- a/src/librustdoc/clean/cfg.rs +++ b/src/librustdoc/clean/cfg.rs @@ -16,7 +16,7 @@ use syntax_pos::Span; use crate::html::escape::Escape; -#[derive(Clone, RustcEncodable, RustcDecodable, Debug, PartialEq, Eq, Hash)] +#[derive(Clone, Debug, PartialEq, Eq, Hash)] pub enum Cfg { /// Accepts all configurations. True, diff --git a/src/librustdoc/clean/mod.rs b/src/librustdoc/clean/mod.rs index 41a56756a1480..3fe048a6986bb 100644 --- a/src/librustdoc/clean/mod.rs +++ b/src/librustdoc/clean/mod.rs @@ -223,7 +223,7 @@ impl<'a, 'tcx> Clean for visit_ast::RustdocVisitor<'a, 'tcx> { } } -#[derive(Clone, RustcEncodable, RustcDecodable, Debug)] +#[derive(Clone, Debug)] pub struct ExternalCrate { pub name: String, pub src: FileName, @@ -355,7 +355,7 @@ impl Clean for CrateNum { /// Anything with a source location and set of attributes and, optionally, a /// name. That is, anything that can be documented. This doesn't correspond /// directly to the AST's concept of an item; it's a strict superset. -#[derive(Clone, RustcEncodable, RustcDecodable)] +#[derive(Clone)] pub struct Item { /// Stringified span pub source: Span, @@ -528,7 +528,7 @@ impl Item { } } -#[derive(Clone, RustcEncodable, RustcDecodable, Debug)] +#[derive(Clone, Debug)] pub enum ItemEnum { ExternCrateItem(String, Option), ImportItem(Import), @@ -594,7 +594,7 @@ impl ItemEnum { } } -#[derive(Clone, RustcEncodable, RustcDecodable, Debug)] +#[derive(Clone, Debug)] pub struct Module { pub items: Vec, pub is_crate: bool, @@ -731,7 +731,7 @@ impl> NestedAttributesExt for I { /// Included files are kept separate from inline doc comments so that proper line-number /// information can be given when a doctest fails. Sugared doc comments and "raw" doc comments are /// kept separate because of issue #42760. -#[derive(Clone, RustcEncodable, RustcDecodable, PartialEq, Eq, Debug, Hash)] +#[derive(Clone, PartialEq, Eq, Debug, Hash)] pub enum DocFragment { /// A doc fragment created from a `///` or `//!` doc comment. SugaredDoc(usize, syntax_pos::Span, String), @@ -781,7 +781,7 @@ impl<'a> FromIterator<&'a DocFragment> for String { } } -#[derive(Clone, RustcEncodable, RustcDecodable, Debug, Default)] +#[derive(Clone, Debug, Default)] pub struct Attributes { pub doc_strings: Vec, pub other_attrs: Vec, @@ -1048,7 +1048,7 @@ impl Clean for [ast::Attribute] { } } -#[derive(Clone, RustcEncodable, RustcDecodable, PartialEq, Eq, Debug, Hash)] +#[derive(Clone, PartialEq, Eq, Debug, Hash)] pub enum GenericBound { TraitBound(PolyTrait, hir::TraitBoundModifier), Outlives(Lifetime), @@ -1231,7 +1231,7 @@ impl<'tcx> Clean>> for InternalSubsts<'tcx> { } } -#[derive(Clone, RustcEncodable, RustcDecodable, PartialEq, Eq, Debug, Hash)] +#[derive(Clone, PartialEq, Eq, Debug, Hash)] pub struct Lifetime(String); impl Lifetime { @@ -1326,7 +1326,7 @@ impl Clean> for ty::RegionKind { } } -#[derive(Clone, RustcEncodable, RustcDecodable, PartialEq, Eq, Debug, Hash)] +#[derive(Clone, PartialEq, Eq, Debug, Hash)] pub enum WherePredicate { BoundPredicate { ty: Type, bounds: Vec }, RegionPredicate { lifetime: Lifetime, bounds: Vec }, @@ -1464,7 +1464,7 @@ impl<'tcx> Clean for ty::ProjectionTy<'tcx> { } } -#[derive(Clone, RustcEncodable, RustcDecodable, PartialEq, Eq, Debug, Hash)] +#[derive(Clone, PartialEq, Eq, Debug, Hash)] pub enum GenericParamDefKind { Lifetime, Type { @@ -1498,7 +1498,7 @@ impl GenericParamDefKind { } } -#[derive(Clone, RustcEncodable, RustcDecodable, PartialEq, Eq, Debug, Hash)] +#[derive(Clone, PartialEq, Eq, Debug, Hash)] pub struct GenericParamDef { pub name: String, @@ -1610,7 +1610,7 @@ impl Clean for hir::GenericParam { } // maybe use a Generic enum and use Vec? -#[derive(Clone, RustcEncodable, RustcDecodable, PartialEq, Eq, Debug, Default, Hash)] +#[derive(Clone, PartialEq, Eq, Debug, Default, Hash)] pub struct Generics { pub params: Vec, pub where_predicates: Vec, @@ -1874,7 +1874,7 @@ pub fn get_all_types( (all_types.into_iter().collect(), ret_types) } -#[derive(Clone, RustcEncodable, RustcDecodable, Debug)] +#[derive(Clone, Debug)] pub struct Method { pub generics: Generics, pub decl: FnDecl, @@ -1902,7 +1902,7 @@ impl<'a> Clean for (&'a hir::MethodSig, &'a hir::Generics, hir::BodyId, } } -#[derive(Clone, RustcEncodable, RustcDecodable, Debug)] +#[derive(Clone, Debug)] pub struct TyMethod { pub header: hir::FnHeader, pub decl: FnDecl, @@ -1911,7 +1911,7 @@ pub struct TyMethod { pub ret_types: Vec, } -#[derive(Clone, RustcEncodable, RustcDecodable, Debug)] +#[derive(Clone, Debug)] pub struct Function { pub decl: FnDecl, pub generics: Generics, @@ -1952,7 +1952,7 @@ impl Clean for doctree::Function<'_> { } } -#[derive(Clone, RustcEncodable, RustcDecodable, PartialEq, Eq, Debug, Hash)] +#[derive(Clone, PartialEq, Eq, Debug, Hash)] pub struct FnDecl { pub inputs: Arguments, pub output: FunctionRetTy, @@ -1989,7 +1989,7 @@ impl FnDecl { } } -#[derive(Clone, RustcEncodable, RustcDecodable, PartialEq, Eq, Debug, Hash)] +#[derive(Clone, PartialEq, Eq, Debug, Hash)] pub struct Arguments { pub values: Vec, } @@ -2063,13 +2063,13 @@ impl<'tcx> Clean for (DefId, ty::PolyFnSig<'tcx>) { } } -#[derive(Clone, RustcEncodable, RustcDecodable, PartialEq, Eq, Debug, Hash)] +#[derive(Clone, PartialEq, Eq, Debug, Hash)] pub struct Argument { pub type_: Type, pub name: String, } -#[derive(Clone, RustcEncodable, RustcDecodable, PartialEq, Debug)] +#[derive(Clone, PartialEq, Debug)] pub enum SelfTy { SelfValue, SelfBorrowed(Option, Mutability), @@ -2093,7 +2093,7 @@ impl Argument { } } -#[derive(Clone, RustcEncodable, RustcDecodable, PartialEq, Eq, Debug, Hash)] +#[derive(Clone, PartialEq, Eq, Debug, Hash)] pub enum FunctionRetTy { Return(Type), DefaultReturn, @@ -2117,7 +2117,7 @@ impl GetDefId for FunctionRetTy { } } -#[derive(Clone, RustcEncodable, RustcDecodable, Debug)] +#[derive(Clone, Debug)] pub struct Trait { pub auto: bool, pub unsafety: hir::Unsafety, @@ -2153,7 +2153,7 @@ impl Clean for doctree::Trait<'_> { } } -#[derive(Clone, RustcEncodable, RustcDecodable, Debug)] +#[derive(Clone, Debug)] pub struct TraitAlias { pub generics: Generics, pub bounds: Vec, @@ -2437,7 +2437,7 @@ impl Clean for ty::AssocItem { } /// A trait reference, which may have higher ranked lifetimes. -#[derive(Clone, RustcEncodable, RustcDecodable, PartialEq, Eq, Debug, Hash)] +#[derive(Clone, PartialEq, Eq, Debug, Hash)] pub struct PolyTrait { pub trait_: Type, pub generic_params: Vec, @@ -2446,7 +2446,7 @@ pub struct PolyTrait { /// A representation of a type suitable for hyperlinking purposes. Ideally, one can get the original /// type out of the AST/`TyCtxt` given one of these, if more information is needed. Most /// importantly, it does not preserve mutability or boxes. -#[derive(Clone, RustcEncodable, RustcDecodable, PartialEq, Eq, Debug, Hash)] +#[derive(Clone, PartialEq, Eq, Debug, Hash)] pub enum Type { /// Structs/enums/traits (most that would be an `hir::TyKind::Path`). ResolvedPath { @@ -2469,7 +2469,6 @@ pub enum Type { Array(Box, String), Never, CVarArgs, - Unique(Box), RawPointer(Mutability, Box), BorrowedRef { lifetime: Option, @@ -2491,7 +2490,7 @@ pub enum Type { ImplTrait(Vec), } -#[derive(Clone, RustcEncodable, RustcDecodable, PartialEq, Eq, Hash, Copy, Debug)] +#[derive(Clone, PartialEq, Eq, Hash, Copy, Debug)] pub enum PrimitiveType { Isize, I8, I16, I32, I64, I128, Usize, U8, U16, U32, U64, U128, @@ -2510,7 +2509,7 @@ pub enum PrimitiveType { CVarArgs, } -#[derive(Clone, RustcEncodable, RustcDecodable, Copy, Debug)] +#[derive(Clone, Copy, Debug)] pub enum TypeKind { Enum, Function, @@ -2520,7 +2519,6 @@ pub enum TypeKind { Struct, Union, Trait, - Variant, Typedef, Foreign, Macro, @@ -3190,7 +3188,7 @@ impl Clean for ty::FieldDef { } } -#[derive(Clone, PartialEq, Eq, RustcDecodable, RustcEncodable, Debug)] +#[derive(Clone, PartialEq, Eq, Debug)] pub enum Visibility { Public, Inherited, @@ -3219,7 +3217,7 @@ impl Clean> for ty::Visibility { } } -#[derive(Clone, RustcEncodable, RustcDecodable, Debug)] +#[derive(Clone, Debug)] pub struct Struct { pub struct_type: doctree::StructType, pub generics: Generics, @@ -3227,7 +3225,7 @@ pub struct Struct { pub fields_stripped: bool, } -#[derive(Clone, RustcEncodable, RustcDecodable, Debug)] +#[derive(Clone, Debug)] pub struct Union { pub struct_type: doctree::StructType, pub generics: Generics, @@ -3278,7 +3276,7 @@ impl Clean for doctree::Union<'_> { /// This is a more limited form of the standard Struct, different in that /// it lacks the things most items have (name, id, parameterization). Found /// only as a variant in an enum. -#[derive(Clone, RustcEncodable, RustcDecodable, Debug)] +#[derive(Clone, Debug)] pub struct VariantStruct { pub struct_type: doctree::StructType, pub fields: Vec, @@ -3295,7 +3293,7 @@ impl Clean for ::rustc::hir::VariantData { } } -#[derive(Clone, RustcEncodable, RustcDecodable, Debug)] +#[derive(Clone, Debug)] pub struct Enum { pub variants: IndexVec, pub generics: Generics, @@ -3321,7 +3319,7 @@ impl Clean for doctree::Enum<'_> { } } -#[derive(Clone, RustcEncodable, RustcDecodable, Debug)] +#[derive(Clone, Debug)] pub struct Variant { pub kind: VariantKind, } @@ -3384,7 +3382,7 @@ impl Clean for ty::VariantDef { } } -#[derive(Clone, RustcEncodable, RustcDecodable, Debug)] +#[derive(Clone, Debug)] pub enum VariantKind { CLike, Tuple(Vec), @@ -3402,7 +3400,7 @@ impl Clean for hir::VariantData { } } -#[derive(Clone, RustcEncodable, RustcDecodable, Debug)] +#[derive(Clone, Debug)] pub struct Span { pub filename: FileName, pub loline: usize, @@ -3448,7 +3446,7 @@ impl Clean for syntax_pos::Span { } } -#[derive(Clone, RustcEncodable, RustcDecodable, PartialEq, Eq, Debug, Hash)] +#[derive(Clone, PartialEq, Eq, Debug, Hash)] pub struct Path { pub global: bool, pub res: Res, @@ -3471,7 +3469,7 @@ impl Clean for hir::Path { } } -#[derive(Clone, RustcEncodable, RustcDecodable, PartialEq, Eq, Debug, Hash)] +#[derive(Clone, PartialEq, Eq, Debug, Hash)] pub enum GenericArg { Lifetime(Lifetime), Type(Type), @@ -3488,7 +3486,7 @@ impl fmt::Display for GenericArg { } } -#[derive(Clone, RustcEncodable, RustcDecodable, PartialEq, Eq, Debug, Hash)] +#[derive(Clone, PartialEq, Eq, Debug, Hash)] pub enum GenericArgs { AngleBracketed { args: Vec, @@ -3528,7 +3526,7 @@ impl Clean for hir::GenericArgs { } } -#[derive(Clone, RustcEncodable, RustcDecodable, PartialEq, Eq, Debug, Hash)] +#[derive(Clone, PartialEq, Eq, Debug, Hash)] pub struct PathSegment { pub name: String, pub args: GenericArgs, @@ -3553,7 +3551,6 @@ fn strip_type(ty: Type) -> Type { } Type::Slice(inner_ty) => Type::Slice(Box::new(strip_type(*inner_ty))), Type::Array(inner_ty, s) => Type::Array(Box::new(strip_type(*inner_ty)), s), - Type::Unique(inner_ty) => Type::Unique(Box::new(strip_type(*inner_ty))), Type::RawPointer(m, inner_ty) => Type::RawPointer(m, Box::new(strip_type(*inner_ty))), Type::BorrowedRef { lifetime, mutability, type_ } => { Type::BorrowedRef { lifetime, mutability, type_: Box::new(strip_type(*type_)) } @@ -3625,7 +3622,7 @@ impl Clean for InternedString { } } -#[derive(Clone, RustcEncodable, RustcDecodable, Debug)] +#[derive(Clone, Debug)] pub struct Typedef { pub type_: Type, pub generics: Generics, @@ -3649,7 +3646,7 @@ impl Clean for doctree::Typedef<'_> { } } -#[derive(Clone, RustcEncodable, RustcDecodable, Debug)] +#[derive(Clone, Debug)] pub struct Existential { pub bounds: Vec, pub generics: Generics, @@ -3673,7 +3670,7 @@ impl Clean for doctree::Existential<'_> { } } -#[derive(Clone, RustcEncodable, RustcDecodable, PartialEq, Eq, Debug, Hash)] +#[derive(Clone, PartialEq, Eq, Debug, Hash)] pub struct BareFunctionDecl { pub unsafety: hir::Unsafety, pub generic_params: Vec, @@ -3695,7 +3692,7 @@ impl Clean for hir::BareFnTy { } } -#[derive(Clone, RustcEncodable, RustcDecodable, Debug)] +#[derive(Clone, Debug)] pub struct Static { pub type_: Type, pub mutability: Mutability, @@ -3725,7 +3722,7 @@ impl Clean for doctree::Static<'_> { } } -#[derive(Clone, PartialEq, Eq, Hash, RustcEncodable, RustcDecodable, Debug)] +#[derive(Clone, PartialEq, Eq, Hash, Debug)] pub struct Constant { pub type_: Type, pub expr: String, @@ -3749,7 +3746,7 @@ impl Clean for doctree::Constant<'_> { } } -#[derive(Debug, Clone, RustcEncodable, RustcDecodable, PartialEq, Eq, Copy, Hash)] +#[derive(Debug, Clone, PartialEq, Eq, Copy, Hash)] pub enum Mutability { Mutable, Immutable, @@ -3764,7 +3761,7 @@ impl Clean for hir::Mutability { } } -#[derive(Clone, RustcEncodable, RustcDecodable, PartialEq, Eq, Copy, Debug, Hash)] +#[derive(Clone, PartialEq, Eq, Copy, Debug, Hash)] pub enum ImplPolarity { Positive, Negative, @@ -3779,7 +3776,7 @@ impl Clean for hir::ImplPolarity { } } -#[derive(Clone, RustcEncodable, RustcDecodable, Debug)] +#[derive(Clone, Debug)] pub struct Impl { pub unsafety: hir::Unsafety, pub generics: Generics, @@ -4003,7 +4000,7 @@ impl Clean> for doctree::Import<'_> { } } -#[derive(Clone, RustcEncodable, RustcDecodable, Debug)] +#[derive(Clone, Debug)] pub enum Import { // use source as str; Simple(String, ImportSource), @@ -4011,7 +4008,7 @@ pub enum Import { Glob(ImportSource) } -#[derive(Clone, RustcEncodable, RustcDecodable, Debug)] +#[derive(Clone, Debug)] pub struct ImportSource { pub path: Path, pub did: Option, @@ -4227,7 +4224,7 @@ fn resolve_use_source(cx: &DocContext<'_>, path: Path) -> ImportSource { } } -#[derive(Clone, RustcEncodable, RustcDecodable, Debug)] +#[derive(Clone, Debug)] pub struct Macro { pub source: String, pub imported_from: Option, @@ -4256,7 +4253,7 @@ impl Clean for doctree::Macro<'_> { } } -#[derive(Clone, RustcEncodable, RustcDecodable, Debug)] +#[derive(Clone, Debug)] pub struct ProcMacro { pub kind: MacroKind, pub helpers: Vec, @@ -4280,7 +4277,7 @@ impl Clean for doctree::ProcMacro<'_> { } } -#[derive(Clone, RustcEncodable, RustcDecodable, Debug)] +#[derive(Clone, Debug)] pub struct Stability { pub level: stability::StabilityLevel, pub feature: Option, @@ -4290,7 +4287,7 @@ pub struct Stability { pub issue: Option, } -#[derive(Clone, RustcEncodable, RustcDecodable, Debug)] +#[derive(Clone, Debug)] pub struct Deprecation { pub since: Option, pub note: Option, @@ -4340,13 +4337,13 @@ impl Clean for attr::Deprecation { /// An type binding on an associated type (e.g., `A = Bar` in `Foo` or /// `A: Send + Sync` in `Foo`). -#[derive(Clone, PartialEq, Eq, RustcDecodable, RustcEncodable, Debug, Hash)] +#[derive(Clone, PartialEq, Eq, Debug, Hash)] pub struct TypeBinding { pub name: String, pub kind: TypeBindingKind, } -#[derive(Clone, PartialEq, Eq, RustcDecodable, RustcEncodable, Debug, Hash)] +#[derive(Clone, PartialEq, Eq, Debug, Hash)] pub enum TypeBindingKind { Equality { ty: Type, diff --git a/src/librustdoc/doctree.rs b/src/librustdoc/doctree.rs index 51deb4e9b9747..2557b8d1627c0 100644 --- a/src/librustdoc/doctree.rs +++ b/src/librustdoc/doctree.rs @@ -78,7 +78,7 @@ impl Module<'hir> { } } -#[derive(Debug, Clone, RustcEncodable, RustcDecodable, Copy)] +#[derive(Debug, Clone, Copy)] pub enum StructType { /// A braced struct Plain, diff --git a/src/librustdoc/html/format.rs b/src/librustdoc/html/format.rs index fa3bc3f5f4f8b..9e5cc03b83123 100644 --- a/src/librustdoc/html/format.rs +++ b/src/librustdoc/html/format.rs @@ -737,9 +737,6 @@ fn fmt_type(t: &clean::Type, f: &mut fmt::Formatter<'_>, use_absolute: bool) -> } } } - clean::Unique(..) => { - panic!("should have been cleaned") - } } } diff --git a/src/librustdoc/html/item_type.rs b/src/librustdoc/html/item_type.rs index 3f3f4c85e81fc..5f1a1b31616c1 100644 --- a/src/librustdoc/html/item_type.rs +++ b/src/librustdoc/html/item_type.rs @@ -110,7 +110,6 @@ impl From for ItemType { clean::TypeKind::Module => ItemType::Module, clean::TypeKind::Static => ItemType::Static, clean::TypeKind::Const => ItemType::Constant, - clean::TypeKind::Variant => ItemType::Variant, clean::TypeKind::Typedef => ItemType::Typedef, clean::TypeKind::Foreign => ItemType::ForeignType, clean::TypeKind::Macro => ItemType::Macro, diff --git a/src/librustdoc/html/render.rs b/src/librustdoc/html/render.rs index f0aff961c6751..2080637ecb402 100644 --- a/src/librustdoc/html/render.rs +++ b/src/librustdoc/html/render.rs @@ -5188,9 +5188,6 @@ fn collect_paths_for_type(first_ty: clean::Type) -> Vec { clean::Type::Array(ty, _) => { work.push_back(*ty); }, - clean::Type::Unique(ty) => { - work.push_back(*ty); - }, clean::Type::RawPointer(_, ty) => { work.push_back(*ty); }, diff --git a/src/librustdoc/lib.rs b/src/librustdoc/lib.rs index 7a8b088020c53..ba423300e0277 100644 --- a/src/librustdoc/lib.rs +++ b/src/librustdoc/lib.rs @@ -42,8 +42,6 @@ extern crate test as testing; #[macro_use] extern crate log; extern crate rustc_errors as errors; -extern crate serialize as rustc_serialize; // used by deriving - use std::default::Default; use std::env; use std::panic;