about summary refs log tree commit diff
path: root/src
diff options
context:
space:
mode:
authorHarald Hoyer <harald@redhat.com>2020-06-15 13:23:38 +0200
committerHarald Hoyer <harald@redhat.com>2020-06-15 14:04:48 +0200
commitd3ca6fd71ed3003e58c6b58d7beb0505d0c8adc3 (patch)
treec3bcd8ee33b2910e161f20abb2ebc95966118303 /src
parent4fb54ed484e2239a3e9eff3be17df00d2a162be3 (diff)
downloadrust-d3ca6fd71ed3003e58c6b58d7beb0505d0c8adc3.tar.gz
rust-d3ca6fd71ed3003e58c6b58d7beb0505d0c8adc3.zip
Enable static-pie for the x86_64-unknown-linux-musl target
Fixes: https://github.com/rust-lang/rust/issues/70693
Diffstat (limited to 'src')
-rw-r--r--src/librustc_target/spec/x86_64_unknown_linux_musl.rs1
-rw-r--r--src/test/run-make/static-pie/Makefile15
-rw-r--r--src/test/run-make/static-pie/test-aslr.rs43
3 files changed, 59 insertions, 0 deletions
diff --git a/src/librustc_target/spec/x86_64_unknown_linux_musl.rs b/src/librustc_target/spec/x86_64_unknown_linux_musl.rs
index 34c628e8f67..3a22290da68 100644
--- a/src/librustc_target/spec/x86_64_unknown_linux_musl.rs
+++ b/src/librustc_target/spec/x86_64_unknown_linux_musl.rs
@@ -6,6 +6,7 @@ pub fn target() -> TargetResult {
     base.max_atomic_width = Some(64);
     base.pre_link_args.get_mut(&LinkerFlavor::Gcc).unwrap().push("-m64".to_string());
     base.stack_probes = true;
+    base.static_position_independent_executables = true;
 
     Ok(Target {
         llvm_target: "x86_64-unknown-linux-musl".to_string(),
diff --git a/src/test/run-make/static-pie/Makefile b/src/test/run-make/static-pie/Makefile
new file mode 100644
index 00000000000..1d3cc821389
--- /dev/null
+++ b/src/test/run-make/static-pie/Makefile
@@ -0,0 +1,15 @@
+-include ../../run-make-fulldeps/tools.mk
+
+# only-x86_64-unknown-linux-musl
+
+# How to manually run this
+# $ ./x.py test --target x86_64-unknown-linux-musl src/test/run-make/static-pie
+
+all:
+	$(RUSTC) --target $(TARGET) -C target-feature=+crt-static test-aslr.rs
+	# Check that no dynamic interpreter is set
+	! readelf -l $(call RUN_BINFILE,test-aslr) | $(CGREP) INTERP
+	# Check that we have a dynamic executable
+	readelf -l $(call RUN_BINFILE,test-aslr) | $(CGREP) DYNAMIC
+	# Check for address space layout randomization
+	$(call RUN,test-aslr) --test-aslr
diff --git a/src/test/run-make/static-pie/test-aslr.rs b/src/test/run-make/static-pie/test-aslr.rs
new file mode 100644
index 00000000000..f28e00f7f4c
--- /dev/null
+++ b/src/test/run-make/static-pie/test-aslr.rs
@@ -0,0 +1,43 @@
+const NUM_RUNS: usize = 10;
+
+fn run_self(exe: &str) -> usize {
+    use std::process::Command;
+    let mut set = std::collections::HashSet::new();
+
+    let mut cmd = Command::new(exe);
+    cmd.arg("--report");
+    (0..NUM_RUNS).for_each(|_| {
+        set.insert(cmd.output().expect("failed to execute process").stdout);
+    });
+    set.len()
+}
+
+fn main() {
+    let mut args = std::env::args();
+    let arg0 = args.next().unwrap();
+    match args.next() {
+        Some(s) if s.eq("--report") => {
+            println!("main = {:#?}", &main as *const _);
+        }
+        Some(s) if s.eq("--test-no-aslr") => {
+            let cnt = run_self(&arg0);
+            if cnt != 1 {
+                eprintln!("FAIL: {} most likely ASLR", arg0);
+                std::process::exit(1);
+            }
+            println!("PASS: {} does no ASLR", arg0);
+        }
+        Some(s) if s.eq("--test-aslr") => {
+            let cnt = run_self(&arg0);
+            if cnt != NUM_RUNS {
+                eprintln!("FAIL: {} most likely no ASLR", arg0);
+                std::process::exit(1);
+            }
+            println!("PASS: {} does ASLR", arg0);
+        }
+        Some(_) | None => {
+            println!("Usage: {} --test-no-aslr | --test-aslr", arg0);
+            std::process::exit(1);
+        }
+    }
+}