From bc087759c80791cb3d76744486c2140467f6c7d4 Mon Sep 17 00:00:00 2001 From: Christoffer Lerno Date: Mon, 16 Aug 2021 00:00:05 +0200 Subject: [PATCH] Add soft-float, no-sse, no-avx, no-mmx for x64 targets. --- src/build/build_options.h | 3 +++ src/build/project.c | 3 +++ src/compiler/target.c | 18 +++++++++++++++--- src/compiler/target.h | 3 +++ 4 files changed, 24 insertions(+), 3 deletions(-) diff --git a/src/build/build_options.h b/src/build/build_options.h index d4b1fba0a..19d8a1c09 100644 --- a/src/build/build_options.h +++ b/src/build/build_options.h @@ -237,6 +237,9 @@ typedef struct bool no_memcpy_pass : 1; bool trap_on_wrap : 1; bool safe_mode : 1; + bool no_sse : 1; + bool no_mmx : 1; + bool no_avx : 1; } feature; } BuildTarget; diff --git a/src/build/project.c b/src/build/project.c index 21d756d2d..ba45035e7 100644 --- a/src/build/project.c +++ b/src/build/project.c @@ -197,6 +197,9 @@ void project_add_target(Project *project, TomlValue *wrapped_table, const char * // Use the fact that they correspond to 0, 1, -1 target->feature.struct_return = get_valid_bool(table, "stack-struct-return", type, STRUCT_RETURN_DEFAULT); target->feature.soft_float = get_valid_bool(table, "soft-float", type, SOFT_FLOAT_DEFAULT); + target->feature.no_avx = get_valid_bool(table, "no-avx", type, false); + target->feature.no_sse = get_valid_bool(table, "no-sse", type, false); + target->feature.no_mmx = get_valid_bool(table, "no-mmx", type, false); } static void project_add_targets(Project *project, TomlTable *table, const char *type, const char *type_key, TargetType target_type) diff --git a/src/compiler/target.c b/src/compiler/target.c index 436444a00..aa96b408e 100644 --- a/src/compiler/target.c +++ b/src/compiler/target.c @@ -381,11 +381,15 @@ static inline void target_setup_x86_abi(BuildTarget *target) } -static inline void target_setup_x64_abi(void) +static inline void target_setup_x64_abi(BuildTarget *target) { platform_target.abi = ABI_X64; platform_target.x64.avx_level = AVX; platform_target.x64.is_win64 = platform_target.os == OS_TYPE_WIN32; + if (target->feature.no_avx) platform_target.x64.avx_level = AVX_NONE; + if (target->feature.no_mmx) platform_target.x64.no_mmx = true; + if (target->feature.no_sse) platform_target.x64.no_sse = true; + if (target->feature.soft_float) platform_target.x64.soft_float = true; if (platform_target.environment_type == ENV_TYPE_GNU) { platform_target.x64.is_mingw64 = platform_target.x64.is_win64; @@ -1110,8 +1114,16 @@ void *llvm_target_machine_create(void) reloc_mode = LLVMRelocDynamicNoPic; } + scratch_buffer_clear(); + if (platform_target.arch == ARCH_TYPE_X86_64) + { + if (platform_target.x64.avx_level == AVX_NONE) scratch_buffer_append("-avx,"); + if (platform_target.x64.no_sse) scratch_buffer_append("-sse,"); + if (platform_target.x64.soft_float) scratch_buffer_append("+soft-float,"); + if (platform_target.x64.no_mmx) scratch_buffer_append("-mmx,"); + } void *result = LLVMCreateTargetMachine(target, platform_target.target_triple, - platform_target.cpu ?: "", platform_target.features ?: "", + platform_target.cpu ?: "", scratch_buffer_to_string(), (LLVMCodeGenOptLevel)platform_target.llvm_opt_level, reloc_mode, LLVMCodeModelDefault); if (!result) error_exit("Failed to create target machine."); @@ -1301,7 +1313,7 @@ void target_setup(BuildTarget *target) target_setup_x86_abi(target); break; case ARCH_TYPE_X86_64: - target_setup_x64_abi(); + target_setup_x64_abi(target); platform_target.x64.avx_level = 0; /* TODO */ if (platform_target.os == OS_TYPE_WIN32) { diff --git a/src/compiler/target.h b/src/compiler/target.h index 5646729e1..dd3de8850 100644 --- a/src/compiler/target.h +++ b/src/compiler/target.h @@ -266,6 +266,9 @@ typedef struct struct { AVXLevel avx_level : 3; + bool no_mmx : 1; + bool no_sse : 1; + bool soft_float : 1; bool is_win64 : 1; bool is_mingw64 : 1; bool pass_int128_vector_in_mem : 1;