about summary refs log tree commit diff
path: root/library/stdarch/crates/intrinsic-test/src/common/gen_rust.rs
diff options
context:
space:
mode:
Diffstat (limited to 'library/stdarch/crates/intrinsic-test/src/common/gen_rust.rs')
-rw-r--r--library/stdarch/crates/intrinsic-test/src/common/gen_rust.rs134
1 files changed, 134 insertions, 0 deletions
diff --git a/library/stdarch/crates/intrinsic-test/src/common/gen_rust.rs b/library/stdarch/crates/intrinsic-test/src/common/gen_rust.rs
new file mode 100644
index 00000000000..e405ab4e640
--- /dev/null
+++ b/library/stdarch/crates/intrinsic-test/src/common/gen_rust.rs
@@ -0,0 +1,134 @@
+use itertools::Itertools;
+use rayon::prelude::*;
+use std::collections::BTreeMap;
+use std::fs::File;
+use std::io::Write;
+use std::process::Command;
+
+pub fn generate_rust_program(
+    notices: &str,
+    configurations: &str,
+    arch_definition: &str,
+    arglists: &str,
+    passes: &str,
+) -> String {
+    format!(
+        r#"{notices}#![feature(simd_ffi)]
+#![feature(link_llvm_intrinsics)]
+#![feature(f16)]
+{configurations}
+#![allow(non_upper_case_globals)]
+use core_arch::arch::{arch_definition}::*;
+
+fn main() {{
+{arglists}
+{passes}
+}}
+"#,
+    )
+}
+
+pub fn compile_rust(
+    binaries: &[&str],
+    toolchain: Option<&str>,
+    target: &str,
+    linker: Option<&str>,
+) -> bool {
+    let mut cargo = File::create("rust_programs/Cargo.toml").unwrap();
+    cargo
+        .write_all(
+            format!(
+                r#"[package]
+name = "intrinsic-test-programs"
+version = "{version}"
+authors = [{authors}]
+license = "{license}"
+edition = "2018"
+[workspace]
+[dependencies]
+core_arch = {{ path = "../crates/core_arch" }}
+{binaries}"#,
+                version = env!("CARGO_PKG_VERSION"),
+                authors = env!("CARGO_PKG_AUTHORS")
+                    .split(":")
+                    .format_with(", ", |author, fmt| fmt(&format_args!("\"{author}\""))),
+                license = env!("CARGO_PKG_LICENSE"),
+                binaries = binaries
+                    .iter()
+                    .map(|binary| {
+                        format!(
+                            r#"[[bin]]
+name = "{binary}"
+path = "{binary}/main.rs""#,
+                        )
+                    })
+                    .collect::<Vec<_>>()
+                    .join("\n")
+            )
+            .into_bytes()
+            .as_slice(),
+        )
+        .unwrap();
+
+    let toolchain = match toolchain {
+        None => return true,
+        Some(t) => t,
+    };
+
+    /* If there has been a linker explicitly set from the command line then
+     * we want to set it via setting it in the RUSTFLAGS*/
+
+    let cargo_command = format!(
+        "cargo {toolchain} build --target {target} --release",
+        toolchain = toolchain,
+        target = target
+    );
+
+    let mut command = Command::new("sh");
+    command
+        .current_dir("rust_programs")
+        .arg("-c")
+        .arg(cargo_command);
+
+    let mut rust_flags = "-Cdebuginfo=0".to_string();
+    if let Some(linker) = linker {
+        rust_flags.push_str(" -C linker=");
+        rust_flags.push_str(linker);
+        rust_flags.push_str(" -C link-args=-static");
+
+        command.env("CPPFLAGS", "-fuse-ld=lld");
+    }
+
+    command.env("RUSTFLAGS", rust_flags);
+    let output = command.output();
+
+    if let Ok(output) = output {
+        if output.status.success() {
+            true
+        } else {
+            error!(
+                "Failed to compile code for rust intrinsics\n\nstdout:\n{}\n\nstderr:\n{}",
+                std::str::from_utf8(&output.stdout).unwrap_or(""),
+                std::str::from_utf8(&output.stderr).unwrap_or("")
+            );
+            false
+        }
+    } else {
+        error!("Command failed: {:#?}", output);
+        false
+    }
+}
+
+pub fn create_rust_files(identifiers: &Vec<String>) -> BTreeMap<&String, File> {
+    identifiers
+        .par_iter()
+        .map(|identifier| {
+            let rust_dir = format!(r#"rust_programs/{}"#, identifier);
+            let _ = std::fs::create_dir_all(&rust_dir);
+            let rust_filename = format!(r#"{rust_dir}/main.rs"#);
+            let file = File::create(&rust_filename).unwrap();
+
+            (identifier, file)
+        })
+        .collect::<BTreeMap<&String, File>>()
+}