mirror of
https://github.com/odin-lang/Odin.git
synced 2026-01-06 04:57:55 +00:00
Merge pull request #3108 from Kelimion/subsystem
Add WINDOWS_SUBSYSTEM constant
This commit is contained in:
@@ -56,6 +56,19 @@ enum TargetABIKind : u16 {
|
||||
TargetABI_COUNT,
|
||||
};
|
||||
|
||||
enum Windows_Subsystem : u8 {
|
||||
Windows_Subsystem_BOOT_APPLICATION,
|
||||
Windows_Subsystem_CONSOLE, // Default,
|
||||
Windows_Subsystem_EFI_APPLICATION,
|
||||
Windows_Subsystem_EFI_BOOT_SERVICE_DRIVER,
|
||||
Windows_Subsystem_EFI_ROM,
|
||||
Windows_Subsystem_EFI_RUNTIME_DRIVER,
|
||||
Windows_Subsystem_NATIVE,
|
||||
Windows_Subsystem_POSIX,
|
||||
Windows_Subsystem_WINDOWS,
|
||||
Windows_Subsystem_WINDOWSCE,
|
||||
Windows_Subsystem_COUNT,
|
||||
};
|
||||
|
||||
gb_global String target_os_names[TargetOs_COUNT] = {
|
||||
str_lit(""),
|
||||
@@ -120,6 +133,19 @@ gb_global TargetEndianKind target_endians[TargetArch_COUNT] = {
|
||||
TargetEndian_Little,
|
||||
};
|
||||
|
||||
gb_global String windows_subsystem_names[Windows_Subsystem_COUNT] = {
|
||||
str_lit("BOOT_APPLICATION"),
|
||||
str_lit("CONSOLE"), // Default
|
||||
str_lit("EFI_APPLICATION"),
|
||||
str_lit("EFI_BOOT_SERVICE_DRIVER"),
|
||||
str_lit("EFI_ROM"),
|
||||
str_lit("EFI_RUNTIME_DRIVER"),
|
||||
str_lit("NATIVE"),
|
||||
str_lit("POSIX"),
|
||||
str_lit("WINDOWS"),
|
||||
str_lit("WINDOWSCE"),
|
||||
};
|
||||
|
||||
#ifndef ODIN_VERSION_RAW
|
||||
#define ODIN_VERSION_RAW "dev-unknown-unknown"
|
||||
#endif
|
||||
@@ -287,14 +313,15 @@ enum SanitizerFlags : u32 {
|
||||
// This stores the information for the specify architecture of this build
|
||||
struct BuildContext {
|
||||
// Constants
|
||||
String ODIN_OS; // target operating system
|
||||
String ODIN_ARCH; // target architecture
|
||||
String ODIN_VENDOR; // compiler vendor
|
||||
String ODIN_VERSION; // compiler version
|
||||
String ODIN_ROOT; // Odin ROOT
|
||||
String ODIN_BUILD_PROJECT_NAME; // Odin main/initial package's directory name
|
||||
bool ODIN_DEBUG; // Odin in debug mode
|
||||
bool ODIN_DISABLE_ASSERT; // Whether the default 'assert' et al is disabled in code or not
|
||||
String ODIN_OS; // Target operating system
|
||||
String ODIN_ARCH; // Target architecture
|
||||
String ODIN_VENDOR; // Compiler vendor
|
||||
String ODIN_VERSION; // Compiler version
|
||||
String ODIN_ROOT; // Odin ROOT
|
||||
String ODIN_BUILD_PROJECT_NAME; // Odin main/initial package's directory name
|
||||
String ODIN_WINDOWS_SUBSYSTEM; // Empty string for non-Windows targets
|
||||
bool ODIN_DEBUG; // Odin in debug mode
|
||||
bool ODIN_DISABLE_ASSERT; // Whether the default 'assert' et al is disabled in code or not
|
||||
bool ODIN_DEFAULT_TO_NIL_ALLOCATOR; // Whether the default allocator is a "nil" allocator or not (i.e. it does nothing)
|
||||
bool ODIN_FOREIGN_ERROR_PROCEDURES;
|
||||
bool ODIN_VALGRIND_SUPPORT;
|
||||
@@ -367,7 +394,6 @@ struct BuildContext {
|
||||
bool ignore_lazy;
|
||||
bool ignore_llvm_build;
|
||||
|
||||
bool use_subsystem_windows;
|
||||
bool ignore_microsoft_magic;
|
||||
bool linker_map_file;
|
||||
|
||||
@@ -1282,8 +1308,6 @@ gb_internal void init_build_context(TargetMetrics *cross_target, Subtarget subta
|
||||
GB_ASSERT(metrics->int_size == 2*metrics->ptr_size);
|
||||
}
|
||||
|
||||
|
||||
|
||||
bc->metrics = *metrics;
|
||||
switch (subtarget) {
|
||||
case Subtarget_Default:
|
||||
@@ -1300,14 +1324,14 @@ gb_internal void init_build_context(TargetMetrics *cross_target, Subtarget subta
|
||||
break;
|
||||
}
|
||||
|
||||
bc->ODIN_OS = target_os_names[metrics->os];
|
||||
bc->ODIN_ARCH = target_arch_names[metrics->arch];
|
||||
bc->endian_kind = target_endians[metrics->arch];
|
||||
bc->ptr_size = metrics->ptr_size;
|
||||
bc->int_size = metrics->int_size;
|
||||
bc->max_align = metrics->max_align;
|
||||
bc->max_simd_align = metrics->max_simd_align;
|
||||
bc->link_flags = str_lit(" ");
|
||||
bc->ODIN_OS = target_os_names[metrics->os];
|
||||
bc->ODIN_ARCH = target_arch_names[metrics->arch];
|
||||
bc->endian_kind = target_endians[metrics->arch];
|
||||
bc->ptr_size = metrics->ptr_size;
|
||||
bc->int_size = metrics->int_size;
|
||||
bc->max_align = metrics->max_align;
|
||||
bc->max_simd_align = metrics->max_simd_align;
|
||||
bc->link_flags = str_lit(" ");
|
||||
|
||||
#if defined(DEFAULT_TO_THREADED_CHECKER)
|
||||
bc->threaded_checker = true;
|
||||
@@ -1329,6 +1353,11 @@ gb_internal void init_build_context(TargetMetrics *cross_target, Subtarget subta
|
||||
}
|
||||
}
|
||||
|
||||
// Default to subsystem:CONSOLE on Windows targets
|
||||
if (bc->ODIN_WINDOWS_SUBSYSTEM == "" && bc->metrics.os == TargetOs_windows) {
|
||||
bc->ODIN_WINDOWS_SUBSYSTEM = windows_subsystem_names[Windows_Subsystem_CONSOLE];
|
||||
}
|
||||
|
||||
// NOTE(zangent): The linker flags to set the build architecture are different
|
||||
// across OSs. It doesn't make sense to allocate extra data on the heap
|
||||
// here, so I just #defined the linker flags to keep things concise.
|
||||
|
||||
@@ -968,10 +968,11 @@ gb_internal void init_universal(void) {
|
||||
add_global_bool_constant("true", true);
|
||||
add_global_bool_constant("false", false);
|
||||
|
||||
add_global_string_constant("ODIN_VENDOR", bc->ODIN_VENDOR);
|
||||
add_global_string_constant("ODIN_VERSION", bc->ODIN_VERSION);
|
||||
add_global_string_constant("ODIN_ROOT", bc->ODIN_ROOT);
|
||||
add_global_string_constant("ODIN_VENDOR", bc->ODIN_VENDOR);
|
||||
add_global_string_constant("ODIN_VERSION", bc->ODIN_VERSION);
|
||||
add_global_string_constant("ODIN_ROOT", bc->ODIN_ROOT);
|
||||
add_global_string_constant("ODIN_BUILD_PROJECT_NAME", bc->ODIN_BUILD_PROJECT_NAME);
|
||||
add_global_string_constant("ODIN_WINDOWS_SUBSYSTEM", bc->ODIN_WINDOWS_SUBSYSTEM);
|
||||
|
||||
{
|
||||
GlobalEnumValue values[TargetOs_COUNT] = {
|
||||
|
||||
@@ -233,7 +233,6 @@ gb_internal i32 linker_stage(LinkerData *gen) {
|
||||
String windows_sdk_bin_path = path_to_string(heap_allocator(), build_context.build_paths[BuildPath_Win_SDK_Bin_Path]);
|
||||
defer (gb_free(heap_allocator(), windows_sdk_bin_path.text));
|
||||
|
||||
char const *subsystem_str = build_context.use_subsystem_windows ? "WINDOWS" : "CONSOLE";
|
||||
if (!build_context.use_lld) { // msvc
|
||||
String res_path = {};
|
||||
defer (gb_free(heap_allocator(), res_path.text));
|
||||
@@ -265,14 +264,14 @@ gb_internal i32 linker_stage(LinkerData *gen) {
|
||||
|
||||
result = system_exec_command_line_app("msvc-link",
|
||||
"\"%.*slink.exe\" %s %.*s -OUT:\"%.*s\" %s "
|
||||
"/nologo /incremental:no /opt:ref /subsystem:%s "
|
||||
"/nologo /incremental:no /opt:ref /subsystem:%.*s "
|
||||
"%.*s "
|
||||
"%.*s "
|
||||
"%s "
|
||||
"",
|
||||
LIT(vs_exe_path), object_files, LIT(res_path), LIT(output_filename),
|
||||
link_settings,
|
||||
subsystem_str,
|
||||
LIT(build_context.ODIN_WINDOWS_SUBSYSTEM),
|
||||
LIT(build_context.link_flags),
|
||||
LIT(build_context.extra_linker_flags),
|
||||
lib_str
|
||||
@@ -283,14 +282,14 @@ gb_internal i32 linker_stage(LinkerData *gen) {
|
||||
} else { // lld
|
||||
result = system_exec_command_line_app("msvc-lld-link",
|
||||
"\"%.*s\\bin\\lld-link\" %s -OUT:\"%.*s\" %s "
|
||||
"/nologo /incremental:no /opt:ref /subsystem:%s "
|
||||
"/nologo /incremental:no /opt:ref /subsystem:%.*s "
|
||||
"%.*s "
|
||||
"%.*s "
|
||||
"%s "
|
||||
"",
|
||||
LIT(build_context.ODIN_ROOT), object_files, LIT(output_filename),
|
||||
link_settings,
|
||||
subsystem_str,
|
||||
LIT(build_context.ODIN_WINDOWS_SUBSYSTEM),
|
||||
LIT(build_context.link_flags),
|
||||
LIT(build_context.extra_linker_flags),
|
||||
lib_str
|
||||
|
||||
43
src/main.cpp
43
src/main.cpp
@@ -1270,16 +1270,43 @@ gb_internal bool parse_build_flags(Array<String> args) {
|
||||
}
|
||||
|
||||
case BuildFlag_Subsystem: {
|
||||
// TODO(Jeroen): Parse optional "[,major[.minor]]"
|
||||
|
||||
GB_ASSERT(value.kind == ExactValue_String);
|
||||
String subsystem = value.value_string;
|
||||
if (str_eq_ignore_case(subsystem, str_lit("console"))) {
|
||||
build_context.use_subsystem_windows = false;
|
||||
} else if (str_eq_ignore_case(subsystem, str_lit("window"))) {
|
||||
build_context.use_subsystem_windows = true;
|
||||
} else if (str_eq_ignore_case(subsystem, str_lit("windows"))) {
|
||||
build_context.use_subsystem_windows = true;
|
||||
} else {
|
||||
gb_printf_err("Invalid -subsystem string, got %.*s, expected either 'console' or 'windows'\n", LIT(subsystem));
|
||||
bool subsystem_found = false;
|
||||
for (int i = 0; i < Windows_Subsystem_COUNT; i++) {
|
||||
if (str_eq_ignore_case(subsystem, windows_subsystem_names[i])) {
|
||||
build_context.ODIN_WINDOWS_SUBSYSTEM = windows_subsystem_names[i];
|
||||
subsystem_found = true;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
// WINDOW is a hidden alias for WINDOWS. Check it.
|
||||
String subsystem_windows_alias = str_lit("WINDOW");
|
||||
if (!subsystem_found && str_eq_ignore_case(subsystem, subsystem_windows_alias)) {
|
||||
build_context.ODIN_WINDOWS_SUBSYSTEM = windows_subsystem_names[Windows_Subsystem_WINDOWS];
|
||||
subsystem_found = true;
|
||||
break;
|
||||
}
|
||||
|
||||
if (!subsystem_found) {
|
||||
gb_printf_err("Invalid -subsystem string, got %.*s. Expected one of:\n", LIT(subsystem));
|
||||
gb_printf_err("\t");
|
||||
for (int i = 0; i < Windows_Subsystem_COUNT; i++) {
|
||||
if (i > 0) {
|
||||
gb_printf_err(", ");
|
||||
}
|
||||
gb_printf_err("%.*s", LIT(windows_subsystem_names[i]));
|
||||
if (i == Windows_Subsystem_CONSOLE) {
|
||||
gb_printf_err(" (default)");
|
||||
}
|
||||
if (i == Windows_Subsystem_WINDOWS) {
|
||||
gb_printf_err(" (or WINDOW)");
|
||||
}
|
||||
}
|
||||
gb_printf_err("\n");
|
||||
bad_flags = true;
|
||||
}
|
||||
break;
|
||||
|
||||
Reference in New Issue
Block a user