Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Use a search list to find a compatible toolchain #521

Merged
merged 2 commits into from
Jun 29, 2020
Merged
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
62 changes: 57 additions & 5 deletions src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -2291,11 +2291,31 @@ impl Build {
"powerpc-unknown-netbsd" => Some("powerpc--netbsd"),
"powerpc64-unknown-linux-gnu" => Some("powerpc-linux-gnu"),
"powerpc64le-unknown-linux-gnu" => Some("powerpc64le-linux-gnu"),
"riscv32i-unknown-none-elf" => Some("riscv32-unknown-elf"),
"riscv32imac-unknown-none-elf" => Some("riscv32-unknown-elf"),
"riscv32imc-unknown-none-elf" => Some("riscv32-unknown-elf"),
"riscv64gc-unknown-none-elf" => Some("riscv64-unknown-elf"),
"riscv64imac-unknown-none-elf" => Some("riscv64-unknown-elf"),
"riscv32i-unknown-none-elf" => self.find_working_gnu_prefix(&[
"riscv32-unknown-elf",
"riscv64-unknown-elf",
alexcrichton marked this conversation as resolved.
Show resolved Hide resolved
"riscv-none-embed",
]),
"riscv32imac-unknown-none-elf" => self.find_working_gnu_prefix(&[
"riscv32-unknown-elf",
"riscv64-unknown-elf",
"riscv-none-embed",
]),
"riscv32imc-unknown-none-elf" => self.find_working_gnu_prefix(&[
"riscv32-unknown-elf",
"riscv64-unknown-elf",
"riscv-none-embed",
]),
"riscv64gc-unknown-none-elf" => self.find_working_gnu_prefix(&[
"riscv64-unknown-elf",
"riscv32-unknown-elf",
"riscv-none-embed",
]),
"riscv64imac-unknown-none-elf" => self.find_working_gnu_prefix(&[
"riscv64-unknown-elf",
"riscv32-unknown-elf",
"riscv-none-embed",
]),
"riscv64gc-unknown-linux-gnu" => Some("riscv64-linux-gnu"),
"s390x-unknown-linux-gnu" => Some("s390x-linux-gnu"),
"sparc-unknown-linux-gnu" => Some("sparc-linux-gnu"),
Expand Down Expand Up @@ -2325,6 +2345,38 @@ impl Build {
.map(|x| x.to_owned()))
}

/// Some platforms have multiple, compatible, canonical prefixes. Look through
/// each possible prefix for a compiler that exists and return it. The prefixes
/// should be ordered from most-likely to least-likely.
fn find_working_gnu_prefix(&self, prefixes: &[&'static str]) -> Option<&'static str> {
let suffix = if self.cpp { "-g++" } else { "-gcc" };
let extension = std::env::consts::EXE_SUFFIX;

// Loop through PATH entries searching for each toolchain. This ensures that we
// are more likely to discover the toolchain early on, because chances are good
// that the desired toolchain is in one of the higher-priority paths.
env::var_os("PATH")
.as_ref()
.and_then(|path_entries| {
env::split_paths(path_entries).find_map(|path_entry| {
for prefix in prefixes {
let target_compiler = format!("{}{}{}", prefix, suffix, extension);
if path_entry.join(&target_compiler).exists() {
return Some(prefix);
}
}
None
})
})
.map(|prefix| *prefix)
.or_else(||
// If no toolchain was found, provide the first toolchain that was passed in.
// This toolchain has been shown not to exist, however it will appear in the
// error that is shown to the user which should make it easier to search for
// where it should be obtained.
prefixes.first().map(|prefix| *prefix))
}

fn get_target(&self) -> Result<String, Error> {
match self.target.clone() {
Some(t) => Ok(t),
Expand Down