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

Upgrade x86_64-fortanix-unknown-sgx platform support to tier 2 #57130

Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Jump to
Jump to file
Failed to load files.
Diff view
Diff view
53 changes: 33 additions & 20 deletions src/bootstrap/compile.rs
Expand Up @@ -78,11 +78,8 @@ impl Step for Std {
builder.info(&format!("Uplifting stage1 std ({} -> {})", from.host, target));

// Even if we're not building std this stage, the new sysroot must
// still contain the musl startup objects.
if target.contains("musl") {
let libdir = builder.sysroot_libdir(compiler, target);
copy_musl_third_party_objects(builder, target, &libdir);
}
// still contain the third party objects needed by various targets.
copy_third_party_objects(builder, &compiler, target);

builder.ensure(StdLink {
compiler: from,
Expand All @@ -92,10 +89,7 @@ impl Step for Std {
return;
}

if target.contains("musl") {
let libdir = builder.sysroot_libdir(compiler, target);
copy_musl_third_party_objects(builder, target, &libdir);
}
copy_third_party_objects(builder, &compiler, target);

let mut cargo = builder.cargo(compiler, Mode::Std, target, "build");
std_cargo(builder, &compiler, target, &mut cargo);
Expand All @@ -116,17 +110,36 @@ impl Step for Std {
}
}

/// Copies the crt(1,i,n).o startup objects
///
/// Since musl supports fully static linking, we can cross link for it even
/// with a glibc-targeting toolchain, given we have the appropriate startup
/// files. As those shipped with glibc won't work, copy the ones provided by
/// musl so we have them on linux-gnu hosts.
fn copy_musl_third_party_objects(builder: &Builder,
target: Interned<String>,
into: &Path) {
for &obj in &["crt1.o", "crti.o", "crtn.o"] {
builder.copy(&builder.musl_root(target).unwrap().join("lib").join(obj), &into.join(obj));
/// Copies third pary objects needed by various targets.
fn copy_third_party_objects(builder: &Builder, compiler: &Compiler, target: Interned<String>) {
let libdir = builder.sysroot_libdir(*compiler, target);

// Copies the crt(1,i,n).o startup objects
//
// Since musl supports fully static linking, we can cross link for it even
// with a glibc-targeting toolchain, given we have the appropriate startup
// files. As those shipped with glibc won't work, copy the ones provided by
// musl so we have them on linux-gnu hosts.
if target.contains("musl") {
for &obj in &["crt1.o", "crti.o", "crtn.o"] {
builder.copy(
&builder.musl_root(target).unwrap().join("lib").join(obj),
&libdir.join(obj),
);
}
}

// Copies libunwind.a compiled to be linked wit x86_64-fortanix-unknown-sgx.
//
// This target needs to be linked to Fortanix's port of llvm's libunwind.
// libunwind requires support for rwlock and printing to stderr,
// which is provided by std for this target.
if target == "x86_64-fortanix-unknown-sgx" {
let src_path_env = "X86_FORTANIX_SGX_LIBS";
let obj = "libunwind.a";
let src = env::var(src_path_env).expect(&format!("{} not found in env", src_path_env));
let src = Path::new(&src).join(obj);
builder.copy(&src, &libdir.join(obj));
}
}

Expand Down
7 changes: 7 additions & 0 deletions src/ci/docker/dist-various-2/Dockerfile
Expand Up @@ -29,6 +29,10 @@ RUN /tmp/build-fuchsia-toolchain.sh
COPY dist-various-2/build-solaris-toolchain.sh /tmp/
RUN /tmp/build-solaris-toolchain.sh x86_64 amd64 solaris-i386
RUN /tmp/build-solaris-toolchain.sh sparcv9 sparcv9 solaris-sparc
COPY dist-various-2/build-x86_64-fortanix-unknown-sgx-toolchain.sh /tmp/
# We pass the commit id of the port of LLVM's libunwind to the build script.
# Any update to the commit id here, should cause the container image to be re-built from this point on.
RUN /tmp/build-x86_64-fortanix-unknown-sgx-toolchain.sh "bbe23902411be88d7388f381becefadd6e3ef819"

COPY scripts/sccache.sh /scripts/
RUN sh /scripts/sccache.sh
Expand Down Expand Up @@ -65,6 +69,9 @@ ENV TARGETS=$TARGETS,wasm32-unknown-unknown
ENV TARGETS=$TARGETS,x86_64-sun-solaris
ENV TARGETS=$TARGETS,x86_64-unknown-linux-gnux32
ENV TARGETS=$TARGETS,x86_64-unknown-cloudabi
ENV TARGETS=$TARGETS,x86_64-fortanix-unknown-sgx

ENV X86_FORTANIX_SGX_LIBS="/x86_64-fortanix-unknown-sgx/lib/"

ENV RUST_CONFIGURE_ARGS --enable-extended --enable-lld --disable-docs
ENV SCRIPT python2.7 ../x.py dist --target $TARGETS
@@ -0,0 +1,57 @@
#!/bin/bash

set -eu
source shared.sh

if [ -z "$1" ]; then
echo "Usage: ${0} <commit_id>"
exit -1
fi

target="x86_64-fortanix-unknown-sgx"
url="https://github.com/fortanix/llvm-project/archive/${1}.tar.gz"
repo_name="llvm-project"

install_prereq()
{
apt-get update
apt-get install -y --no-install-recommends \
build-essential \
ca-certificates \
cmake \
git
}

# Clone Fortanix's port of llvm-project to build libunwind that would link with this target.
# The below method to download a single commit from llvm-project is based on fetch_submodule
# from init_repo.sh
fetch_llvm_commit()
{
cached="download-${repo_name}.tar.gz"
curl -f -sSL -o ${cached} ${url}
tar -xvzf ${cached}
mkdir "./${repo_name}" && tar -xf ${cached} -C ${repo_name} --strip-components 1
}

build_unwind()
{
dir_name="${target}_temp"
rm -rf "./${dir_name}"
mkdir -p ${dir_name}
cd ${dir_name}

retry fetch_llvm_commit
cd "${repo_name}/libunwind"

# Build libunwind
mkdir -p build
cd build
cmake -DCMAKE_BUILD_TYPE="RELEASE" -DRUST_SGX=1 -G "Unix Makefiles" -DLLVM_PATH=../../llvm/ ../
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

To be clear, this doesn't build LLVM, correct?

Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Correct. It does not build llvm. In fact, it needs only llvm/cmake.

make unwind_static
install -D "lib/libunwind.a" "/${target}/lib/libunwind.a"
rm -rf ${dir_name}
}

set -x
hide_output install_prereq
hide_output build_unwind
18 changes: 18 additions & 0 deletions src/ci/docker/dist-various-2/shared.sh
Expand Up @@ -13,3 +13,21 @@ exit 1
kill $PING_LOOP_PID
set -x
}

function retry {
echo "Attempting with retry:" "$@"
local n=1
local max=5
while true; do
"$@" && break || {
if [[ $n -lt $max ]]; then
sleep $n # don't retry immediately
((n++))
echo "Command failed. Attempt $n/$max:"
else
echo "The command has failed after $n attempts."
return 1
fi
}
done
}
10 changes: 10 additions & 0 deletions src/libstd/sys/sgx/abi/entry.S
Expand Up @@ -4,6 +4,16 @@
.global IMAGE_BASE
IMAGE_BASE:

.section ".note.x86_64-fortanix-unknown-sgx", "", @note
.align 4
.long 1f - 0f /* name length (not including padding) */
.long 3f - 2f /* desc length (not including padding) */
.long 1 /* type = NT_VERSION */
0: .asciz "toolchain-version" /* name */
1: .align 4
2: .long 0 /* desc - toolchain version number, 32-bit LE */
3: .align 4

.section .rodata
/* The XSAVE area needs to be a large chunk of readable memory, but since we are */
/* going to restore everything to its initial state (XSTATE_BV=0), only certain */
Expand Down
8 changes: 8 additions & 0 deletions src/libstd/sys/sgx/time.rs
Expand Up @@ -25,6 +25,14 @@ impl Instant {
pub fn checked_sub_duration(&self, other: &Duration) -> Option<Instant> {
Some(Instant(self.0.checked_sub(*other)?))
}

pub fn actually_monotonic() -> bool {
false
}

pub const fn zero() -> Instant {
Instant(Duration::from_secs(0))
}
}

impl SystemTime {
Expand Down
1 change: 1 addition & 0 deletions src/libstd/sys/sgx/waitqueue.rs
Expand Up @@ -456,6 +456,7 @@ mod spin_mutex {
}
}

/// Lock the Mutex or return false.
pub macro try_lock_or_false {
($e:expr) => {
if let Some(v) = $e.try_lock() {
Expand Down