Change:
<ins> #!/bin/bash # Copyright 2016-2017 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 <LICENSE-APACHE or # http://www.apache.org/licenses/LICENSE-2.0> or the MIT license # <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your # option. This file may not be copied, modified, or distributed # except according to those terms. set -eux arch=$1 binutils_version=2.25.1 freebsd_version=10.3 triple=$arch-unknown-freebsd10 sysroot=/usr/local/$triple hide_output() { set +x local on_err=" echo ERROR: An error was encountered with the build. cat /tmp/build.log exit 1 " trap "$on_err" ERR bash -c "while true; do sleep 30; echo $(date) - building ...; done" & local ping_loop_pid=$! $@ &> /tmp/build.log trap - ERR kill $ping_loop_pid set -x } # First up, build binutils mkdir binutils cd binutils curl https://ftp.gnu.org/gnu/binutils/binutils-${binutils_version}.tar.bz2 | tar xjf - mkdir binutils-build cd binutils-build hide_output ../binutils-${binutils_version}/configure  --target="$triple" --with-sysroot="$sysroot" hide_output make -j"$(getconf _NPROCESSORS_ONLN)" hide_output make install cd ../.. rm -rf binutils # Next, download the FreeBSD libraries and header files mkdir -p "$sysroot" case $arch in (x86_64) freebsd_arch=amd64 ;; (i686) freebsd_arch=i386 ;; esac files_to_extract=( "./usr/include" "./usr/lib/*crt*.o" ) # Try to unpack only the libraries the build needs, to save space. for lib in c cxxrt gcc_s m thr util; do files_to_extract=("${files_to_extract[@]}" "./lib/lib${lib}.*" "./usr/lib/lib${lib}.*") done for lib in c++ c_nonshared compiler_rt execinfo gcc pthread rt ssp_nonshared; do files_to_extract=("${files_to_extract[@]}" "./usr/lib/lib${lib}.*") done URL=https://download.freebsd.org/ftp/releases/${freebsd_arch}/${freebsd_version}-RELEASE/base.txz curl "$URL" | tar xJf - -C "$sysroot" --wildcards "${files_to_extract[@]}" # Fix up absolute symlinks from the system image.  This can be removed # for FreeBSD 11.  (If there's an easy way to make them relative # symlinks instead, feel free to change this.) set +x find "$sysroot" -type l | while read symlink_path; do symlink_target=$(readlink "$symlink_path") case $symlink_target in (/*) echo "Fixing symlink ${symlink_path} -> ${sysroot}${symlink_target}" >&2 ln -nfs "${sysroot}${symlink_target}" "${symlink_path}" ;; esac done set -x # Clang can do cross-builds out of the box, if we give it the right # flags.  (The local binutils seem to work, but they set the ELF # header "OS/ABI" (EI_OSABI) field to SysV rather than FreeBSD, so # there might be other problems.) # # The --target option is last because the cross-build of LLVM uses # --target without an OS version ("-freebsd" vs. "-freebsd10").  This # makes Clang default to libstdc++ (which no longer exists), and also # controls other features, like GNU-style symbol table hashing and # anything predicated on the version number in the __FreeBSD__ # preprocessor macro. for tool in clang clang++; do tool_path=/usr/local/bin/${triple}-${tool} cat > "$tool_path" <<EOF #!/bin/sh exec $tool --sysroot=$sysroot --prefix=${sysroot}/bin "$@" --target=$triple EOF chmod +x "$tool_path" done </ins>

Discussion:
Steps to reproduce, on my FreeBSD/amd64 11.0 system: , where is: It's not 100%, but it usually happens after a few tries at most. I'll skip all the debugging and source-diving and just say that it's the same basic problem as : threads A and B are both in , thread A gets to first and s a lambda, then thread B enters and blocks in with the global mutex held, then thread A calls reentrantly on a different and deadlocks. But there might be a nicer solution than for , because has this patch: , on all platforms where they use Clang (apparently x86, little-endian ARM, and PPC), and 10.x is now the . appears to have a self-contained that doesn't use , and emprically the Rust 1.18.0 package available via doesn't deadlock. So, it might be enough to upstream that patch and update the build environment to 10.x if it isn't already.
Looks like we're using 10.2 on ci:
Thanks for the pointer. I took a (much) closer look at this, and I've gotten the build more or less working using Ubuntu's regular Clang package, which can cross-compile out of the box. I'll send a PR once I've gotten things cleaned up and tested a bit more.
So I'm kind of stuck because, when I try to test locally, I run into unless I remove , which isn't maximally useful because I don't have Cargo and therefore can't build Cargo. This happens even without my changes, but the same container running on Travis CI seems to work, and I'm at a loss as to what differences there could be that would affect (apparently?) the type checker. I suppose I could just test what I can and send a PR and hope for the best, but if possible I'd prefer to understand what my local setup is doing wrong.
Noticed this on 12-CURRENT, compilers from rustup always lock up when compiling , but it usually succeeds after a couple tries. It's nearly always !
Hmm, the rust from ports (that doesn't have this problem IIRC??) is built with bundled llvm by default…