diff --git a/compiler/rustc_llvm/build.rs b/compiler/rustc_llvm/build.rs index 6692ea735401a..a662694ac38f2 100644 --- a/compiler/rustc_llvm/build.rs +++ b/compiler/rustc_llvm/build.rs @@ -255,6 +255,7 @@ fn main() { } else if target.contains("haiku") || target.contains("darwin") || (is_crossed && (target.contains("dragonfly") || target.contains("solaris"))) + || target.contains("cygwin") { println!("cargo:rustc-link-lib=z"); } else if target.contains("netbsd") { diff --git a/compiler/rustc_session/src/filesearch.rs b/compiler/rustc_session/src/filesearch.rs index bdeca91eb64a4..2a85f44278a03 100644 --- a/compiler/rustc_session/src/filesearch.rs +++ b/compiler/rustc_session/src/filesearch.rs @@ -58,7 +58,7 @@ pub fn make_target_bin_path(sysroot: &Path, target_triple: &str) -> PathBuf { sysroot.join(rustlib_path).join("bin") } -#[cfg(unix)] +#[cfg(all(unix, not(target_os = "cygwin")))] fn current_dll_path() -> Result { use std::sync::OnceLock; @@ -132,6 +132,23 @@ fn current_dll_path() -> Result { .clone() } +#[cfg(target_os = "cygwin")] +fn current_dll_path() -> Result { + use std::ffi::{CStr, OsStr}; + use std::os::unix::prelude::*; + + unsafe { + let addr = current_dll_path as usize as *mut _; + let mut info = std::mem::zeroed(); + if libc::dladdr(addr, &mut info) == 0 { + return Err("dladdr failed".into()); + } + let bytes = CStr::from_ptr(info.dli_fname.as_ptr()).to_bytes(); + let os = OsStr::from_bytes(bytes); + Ok(PathBuf::from(os)) + } +} + #[cfg(windows)] fn current_dll_path() -> Result { use std::ffi::OsString; diff --git a/src/bootstrap/src/core/builder/mod.rs b/src/bootstrap/src/core/builder/mod.rs index 75cc5d3986b88..34eaf7212aa3b 100644 --- a/src/bootstrap/src/core/builder/mod.rs +++ b/src/bootstrap/src/core/builder/mod.rs @@ -1389,7 +1389,7 @@ impl<'a> Builder<'a> { // Windows doesn't need dylib path munging because the dlls for the // compiler live next to the compiler and the system will find them // automatically. - if cfg!(windows) { + if cfg!(any(windows, target_os = "cygwin")) { return; } diff --git a/src/bootstrap/src/utils/helpers.rs b/src/bootstrap/src/utils/helpers.rs index b31b2757767c3..77e0ef79bcbc2 100644 --- a/src/bootstrap/src/utils/helpers.rs +++ b/src/bootstrap/src/utils/helpers.rs @@ -130,7 +130,7 @@ pub fn is_debug_info(name: &str) -> bool { /// Returns the corresponding relative library directory that the compiler's /// dylibs will be found in. pub fn libdir(target: TargetSelection) -> &'static str { - if target.is_windows() { "bin" } else { "lib" } + if target.is_windows() || target.contains("cygwin") { "bin" } else { "lib" } } /// Adds a list of lookup paths to `cmd`'s dynamic library lookup path. diff --git a/src/bootstrap/src/utils/shared_helpers.rs b/src/bootstrap/src/utils/shared_helpers.rs index 7b206c3ffe826..3c58214bdece9 100644 --- a/src/bootstrap/src/utils/shared_helpers.rs +++ b/src/bootstrap/src/utils/shared_helpers.rs @@ -20,7 +20,7 @@ use std::str::FromStr; /// Returns the environment variable which the dynamic library lookup path /// resides in for this platform. pub fn dylib_path_var() -> &'static str { - if cfg!(target_os = "windows") { + if cfg!(any(target_os = "windows", target_os = "cygwin")) { "PATH" } else if cfg!(target_vendor = "apple") { "DYLD_LIBRARY_PATH"