From 8e86640bd7af9cb961e3e67af144055e539fe125 Mon Sep 17 00:00:00 2001 From: Brendan Hansknecht Date: Sun, 5 Nov 2023 12:22:39 -0800 Subject: [PATCH 1/3] add preprocess host cli option --- crates/cli/src/lib.rs | 18 ++++++++++++++++++ crates/cli/src/main.rs | 35 +++++++++++++++++++++++++++++++---- crates/linker/src/lib.rs | 6 +++--- 3 files changed, 52 insertions(+), 7 deletions(-) diff --git a/crates/cli/src/lib.rs b/crates/cli/src/lib.rs index 1e42baeb5b2..d5c91b912ca 100644 --- a/crates/cli/src/lib.rs +++ b/crates/cli/src/lib.rs @@ -48,6 +48,7 @@ pub const CMD_FORMAT: &str = "format"; pub const CMD_TEST: &str = "test"; pub const CMD_GLUE: &str = "glue"; pub const CMD_GEN_STUB_LIB: &str = "gen-stub-lib"; +pub const CMD_PREPROCESS_HOST: &str = "preprocess-host"; pub const FLAG_DEBUG: &str = "debug"; pub const FLAG_BUNDLE: &str = "bundle"; @@ -345,6 +346,23 @@ pub fn build_app() -> Command { .value_parser(value_parser!(PathBuf)) .required(true) ) + .arg( + Arg::new(FLAG_TARGET) + .long(FLAG_TARGET) + .help("Choose a different target") + .default_value(Into::<&'static str>::into(Target::default())) + .value_parser(build_target_values_parser.clone()) + .required(false), + ) + ) + .subcommand(Command::new(CMD_PREPROCESS_HOST) + .about("Runs the surgical linker preprocessor to generate `.rh` and `.rm` files.") + .arg( + Arg::new(ROC_FILE) + .help("The .roc file for an app using the platform") + .value_parser(value_parser!(PathBuf)) + .required(true) + ) .arg( Arg::new(FLAG_TARGET) .long(FLAG_TARGET) diff --git a/crates/cli/src/main.rs b/crates/cli/src/main.rs index 2d679ce917a..9d1f7bef8c1 100644 --- a/crates/cli/src/main.rs +++ b/crates/cli/src/main.rs @@ -4,9 +4,10 @@ use roc_build::link::LinkType; use roc_build::program::{check_file, CodeGenBackend}; use roc_cli::{ build_app, format_files, format_src, test, BuildConfig, FormatMode, CMD_BUILD, CMD_CHECK, - CMD_DEV, CMD_DOCS, CMD_FORMAT, CMD_GEN_STUB_LIB, CMD_GLUE, CMD_REPL, CMD_RUN, CMD_TEST, - CMD_VERSION, DIRECTORY_OR_FILES, FLAG_CHECK, FLAG_DEV, FLAG_LIB, FLAG_NO_LINK, FLAG_OUTPUT, - FLAG_STDIN, FLAG_STDOUT, FLAG_TARGET, FLAG_TIME, GLUE_DIR, GLUE_SPEC, ROC_FILE, + CMD_DEV, CMD_DOCS, CMD_FORMAT, CMD_GEN_STUB_LIB, CMD_GLUE, CMD_PREPROCESS_HOST, CMD_REPL, + CMD_RUN, CMD_TEST, CMD_VERSION, DIRECTORY_OR_FILES, FLAG_CHECK, FLAG_DEV, FLAG_LIB, + FLAG_NO_LINK, FLAG_OUTPUT, FLAG_STDIN, FLAG_STDOUT, FLAG_TARGET, FLAG_TIME, GLUE_DIR, + GLUE_SPEC, ROC_FILE, }; use roc_docs::generate_docs_html; use roc_error_macros::user_error; @@ -131,7 +132,33 @@ fn main() -> io::Result<()> { RocCacheDir::Persistent(cache::roc_cache_dir().as_path()), &target.to_triple(), function_kind, - ) + ); + Ok(0) + } + Some((CMD_PREPROCESS_HOST, matches)) => { + let input_path = matches.get_one::(ROC_FILE).unwrap(); + let target = matches + .get_one::(FLAG_TARGET) + .and_then(|s| Target::from_str(s).ok()) + .unwrap_or_default(); + + let triple = target.to_triple(); + let function_kind = FunctionKind::LambdaSet; + let (platform_path, stub_lib, stub_dll_symbols) = roc_linker::generate_stub_lib( + &input_path, + RocCacheDir::Persistent(cache::roc_cache_dir().as_path()), + &triple, + function_kind, + ); + + roc_linker::preprocess_host( + &triple, + &platform_path.with_file_name("main.roc"), + &platform_path.with_file_name("linux-x64.rh"), + &stub_lib, + &stub_dll_symbols, + ); + Ok(0) } Some((CMD_BUILD, matches)) => { let target = matches diff --git a/crates/linker/src/lib.rs b/crates/linker/src/lib.rs index bec65cbfa24..1f1408bd0bc 100644 --- a/crates/linker/src/lib.rs +++ b/crates/linker/src/lib.rs @@ -90,7 +90,7 @@ pub fn generate_stub_lib( roc_cache_dir: RocCacheDir<'_>, triple: &Triple, function_kind: FunctionKind, -) -> std::io::Result { +) -> (PathBuf, PathBuf, Vec) { // Note: this should theoretically just be able to load the host, I think. // Instead, I am loading an entire app because that was simpler and had example code. // If this was expected to stay around for the the long term, we should change it. @@ -146,10 +146,10 @@ pub fn generate_stub_lib( let stub_dll_symbols = exposed_symbols.stub_dll_symbols(); generate_dynamic_lib(triple, &stub_dll_symbols, &stub_lib); + (platform_path.into(), stub_lib, stub_dll_symbols) } else { unreachable!(); - }; - Ok(0) + } } pub fn generate_stub_lib_from_loaded( From 6006891889f58a04b5f662f39972e83ce268e454 Mon Sep 17 00:00:00 2001 From: Brendan Hansknecht Date: Sun, 5 Nov 2023 12:42:59 -0800 Subject: [PATCH 2/3] correct path and add TODO --- crates/cli/src/main.rs | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/crates/cli/src/main.rs b/crates/cli/src/main.rs index 9d1f7bef8c1..eea6a9c89ae 100644 --- a/crates/cli/src/main.rs +++ b/crates/cli/src/main.rs @@ -151,10 +151,12 @@ fn main() -> io::Result<()> { function_kind, ); + // TODO: pipeline the executable location through here. + // Currently it is essentally hardcoded as platform_path/dynhost. roc_linker::preprocess_host( &triple, &platform_path.with_file_name("main.roc"), - &platform_path.with_file_name("linux-x64.rh"), + &platform_path.with_file_name(format!("{}.rh", target)), &stub_lib, &stub_dll_symbols, ); From 2a385839fe4d37b225e60ff07358d2a7eba90cae Mon Sep 17 00:00:00 2001 From: Brendan Hansknecht Date: Sun, 5 Nov 2023 13:15:22 -0800 Subject: [PATCH 3/3] deal with system target --- crates/cli/src/main.rs | 7 +++++-- 1 file changed, 5 insertions(+), 2 deletions(-) diff --git a/crates/cli/src/main.rs b/crates/cli/src/main.rs index eea6a9c89ae..8cb445379db 100644 --- a/crates/cli/src/main.rs +++ b/crates/cli/src/main.rs @@ -15,7 +15,7 @@ use roc_gen_dev::AssemblyBackendMode; use roc_gen_llvm::llvm::build::LlvmBackendMode; use roc_load::{FunctionKind, LoadingProblem, Threading}; use roc_packaging::cache::{self, RocCacheDir}; -use roc_target::Target; +use roc_target::{get_target_triple_str, Target}; use std::fs::{self, FileType}; use std::io::{self, Read, Write}; use std::path::{Path, PathBuf}; @@ -156,7 +156,10 @@ fn main() -> io::Result<()> { roc_linker::preprocess_host( &triple, &platform_path.with_file_name("main.roc"), - &platform_path.with_file_name(format!("{}.rh", target)), + // The target triple string must be derived from the triple to convert from the generic + // `system` target to the exact specific target. + &platform_path + .with_file_name(format!("{}.rh", get_target_triple_str(&triple).unwrap())), &stub_lib, &stub_dll_symbols, );