From b542ef273dd4044692fecc02934f117c278d1891 Mon Sep 17 00:00:00 2001 From: gingerBill Date: Sat, 18 Jan 2020 14:44:53 +0000 Subject: [PATCH] Begin work on `-target:windows_386` --- core/runtime/procs_windows_386.odin | 59 +++++++++++++++++++ src/main.cpp | 91 +++++++++++++++-------------- src/microsoft_craziness.h | 34 +++++++---- 3 files changed, 127 insertions(+), 57 deletions(-) create mode 100644 core/runtime/procs_windows_386.odin diff --git a/core/runtime/procs_windows_386.odin b/core/runtime/procs_windows_386.odin new file mode 100644 index 000000000..b2597ad67 --- /dev/null +++ b/core/runtime/procs_windows_386.odin @@ -0,0 +1,59 @@ +package runtime + +foreign import kernel32 "system:Kernel32.lib" + +@private +@(link_name="_tls_index") +_tls_index: u32; + +@private +@(link_name="_fltused") +_fltused: i32 = 0x9875; + +@(link_name="memcpy") +memcpy :: proc "c" (dst, src: rawptr, len: int) -> rawptr { + foreign kernel32 { + RtlCopyMemory :: proc "c" (dst, src: rawptr, len: int) --- + } + RtlCopyMemory(dst, src, len); + return dst; +} + +@(link_name="memmove") +memmove :: proc "c" (dst, src: rawptr, len: int) -> rawptr { + foreign kernel32 { + RtlMoveMemory :: proc "c" (dst, src: rawptr, len: int) --- + } + RtlMoveMemory(dst, src, len); + return dst; +} + +@(link_name="memset") +memset :: proc "c" (ptr: rawptr, val: i32, len: int) -> rawptr { + d := uintptr(ptr); + b := byte(val); + for i in 0.. i32 { +// if dst == nil || src == nil { +// return 0; +// } +// if dst == src { +// return 0; +// } +// d, s := uintptr(dst), uintptr(src); +// n := uintptr(len); + +// for i := uintptr(0); i < n; i += 1 { +// x, y := (^byte)(d+i)^, (^byte)(s+i)^; +// if x != y { +// return x < y ? -1 : +1; +// } +// } +// return 0; +// } diff --git a/src/main.cpp b/src/main.cpp index 95340f1fb..bee298738 100644 --- a/src/main.cpp +++ b/src/main.cpp @@ -50,7 +50,7 @@ i32 system_exec_command_line_app(char const *name, char const *fmt, ...) { cmd_len = gb_snprintf_va(cmd_line, gb_size_of(cmd_line), fmt, va); va_end(va); - // gb_printf_err("%.*s\n", cast(int)cmd_len, cmd_line); + gb_printf_err("%.*s\n", cast(int)cmd_len, cmd_line); tmp = gb_temp_arena_memory_begin(&string_buffer_arena); defer (gb_temp_arena_memory_end(tmp)); @@ -625,6 +625,7 @@ bool parse_build_flags(Array args) { } case BuildFlag_Target: { + GB_ASSERT(value.kind == ExactValue_String); String str = value.value_string; bool found = false; @@ -1201,7 +1202,7 @@ int main(int arg_count, char const **arg_ptr) { init_build_context(selected_target_metrics ? selected_target_metrics->metrics : nullptr); if (build_context.word_size == 4) { - print_usage_line(0, "%s 32-bit is not yet supported", args[0]); + print_usage_line(0, "%.*s 32-bit is not yet supported", LIT(args[0])); return 1; } @@ -1294,16 +1295,13 @@ int main(int arg_count, char const **arg_ptr) { return exit_code; } - if (build_context.cross_compiling) { - if (0) { + if (build_context.cross_compiling && selected_target_metrics->metrics == &target_essence_amd64) { #ifdef GB_SYSTEM_UNIX - } else if (selected_target_metrics->metrics == &target_essence_amd64) { - system_exec_command_line_app("linker", "x86_64-essence-gcc \"%.*s.o\" -o \"%.*s\" %.*s", - LIT(output_base), LIT(output_base), LIT(build_context.link_flags)); + system_exec_command_line_app("linker", "x86_64-essence-gcc \"%.*s.o\" -o \"%.*s\" %.*s", + LIT(output_base), LIT(output_base), LIT(build_context.link_flags)); +#else + gb_printf_err("Don't know how to cross compile to selected target.\n"); #endif - } else { - gb_printf_err("Don't know how to cross compile to selected target.\n"); - } } else { #if defined(GB_SYSTEM_WINDOWS) timings_start_section(timings, str_lit("msvc-link")); @@ -1312,42 +1310,13 @@ int main(int arg_count, char const **arg_ptr) { defer (gb_string_free(lib_str)); char lib_str_buf[1024] = {0}; - for_array(i, ir_gen.module.foreign_library_paths) { - String lib = ir_gen.module.foreign_library_paths[i]; - GB_ASSERT(lib.len < gb_count_of(lib_str_buf)-1); - isize len = gb_snprintf(lib_str_buf, gb_size_of(lib_str_buf), - " \"%.*s\"", LIT(lib)); - lib_str = gb_string_appendc(lib_str, lib_str_buf); - } - char const *output_ext = "exe"; gbString link_settings = gb_string_make_reserve(heap_allocator(), 256); defer (gb_string_free(link_settings)); - if (build_context.is_dll) { - output_ext = "dll"; - link_settings = gb_string_append_fmt(link_settings, "/DLL"); - } else { - link_settings = gb_string_append_fmt(link_settings, "/ENTRY:mainCRTStartup"); - } - - if (build_context.pdb_filepath != "") { - link_settings = gb_string_append_fmt(link_settings, " /PDB:%.*s", LIT(build_context.pdb_filepath)); - } - - if (build_context.no_crt) { - link_settings = gb_string_append_fmt(link_settings, " /nodefaultlib"); - } else { - link_settings = gb_string_append_fmt(link_settings, " /defaultlib:libcmt"); - } - - if (ir_gen.module.generate_debug_info) { - link_settings = gb_string_append_fmt(link_settings, " /DEBUG"); - } // NOTE(ic): It would be nice to extend this so that we could specify the Visual Studio version that we want instead of defaulting to the latest. Find_Result_Utf8 find_result = find_visual_studio_and_windows_sdk_utf8(); - // defer(free_"resource"s(&find_result)); if (find_result.windows_sdk_version == 0) { gb_printf_err("Windows SDK not found.\n"); @@ -1371,6 +1340,38 @@ int main(int arg_count, char const **arg_ptr) { add_path(find_result.vs_library_path); } + for_array(i, ir_gen.module.foreign_library_paths) { + String lib = ir_gen.module.foreign_library_paths[i]; + GB_ASSERT(lib.len < gb_count_of(lib_str_buf)-1); + isize len = gb_snprintf(lib_str_buf, gb_size_of(lib_str_buf), + " \"%.*s\"", LIT(lib)); + lib_str = gb_string_appendc(lib_str, lib_str_buf); + } + + + + if (build_context.is_dll) { + output_ext = "dll"; + link_settings = gb_string_append_fmt(link_settings, "/DLL"); + } else { + link_settings = gb_string_append_fmt(link_settings, "/ENTRY:mainCRTStartup"); + } + + if (build_context.pdb_filepath != "") { + link_settings = gb_string_append_fmt(link_settings, " /PDB:%.*s", LIT(build_context.pdb_filepath)); + } + + if (build_context.no_crt) { + link_settings = gb_string_append_fmt(link_settings, " /nodefaultlib"); + } else { + link_settings = gb_string_append_fmt(link_settings, " /defaultlib:libcmt"); + } + + if (ir_gen.module.generate_debug_info) { + link_settings = gb_string_append_fmt(link_settings, " /DEBUG"); + } + + if (!build_context.use_lld) { // msvc if (build_context.has_resource) { @@ -1392,8 +1393,8 @@ int main(int arg_count, char const **arg_ptr) { " %s " "", LIT(find_result.vs_exe_path), LIT(output_base), LIT(output_base), LIT(output_base), output_ext, - lib_str, LIT(build_context.link_flags), - link_settings + link_settings, LIT(build_context.link_flags), + lib_str ); } else { exit_code = system_exec_command_line_app("msvc-link", @@ -1403,8 +1404,8 @@ int main(int arg_count, char const **arg_ptr) { " %s " "", LIT(find_result.vs_exe_path), LIT(output_base), LIT(output_base), output_ext, - lib_str, LIT(build_context.link_flags), - link_settings + link_settings, LIT(build_context.link_flags), + lib_str ); } } else { // lld @@ -1416,8 +1417,8 @@ int main(int arg_count, char const **arg_ptr) { "", LIT(build_context.ODIN_ROOT), LIT(output_base), LIT(output_base), output_ext, - lib_str, LIT(build_context.link_flags), - link_settings + link_settings, LIT(build_context.link_flags), + lib_str ); } diff --git a/src/microsoft_craziness.h b/src/microsoft_craziness.h index cfb0438df..1a94aff3f 100644 --- a/src/microsoft_craziness.h +++ b/src/microsoft_craziness.h @@ -202,7 +202,7 @@ wchar_t *concat(wchar_t *a, wchar_t *b, wchar_t *c = nullptr, wchar_t *d = nullp isize len_c = string16_len(c); isize len_d = string16_len(d); - wchar_t *result = (wchar_t *)malloc((len_a + len_b + len_c + len_d + 1) * 2); + wchar_t *result = (wchar_t *)calloc(2, (len_a + len_b + len_c + len_d + 1)); gb_memmove(result, a, len_a*2); gb_memmove(result + len_a, b, len_b*2); @@ -256,7 +256,7 @@ wchar_t *find_windows_kit_root(HKEY key, wchar_t *version) { if (rc != 0) return NULL; DWORD length = required_length + 2; // The +2 is for the maybe optional zero later on. Probably we are over-allocating. - wchar_t *value = (wchar_t *)malloc(length); + wchar_t *value = (wchar_t *)calloc(1, length); if (!value) return NULL; rc = RegQueryValueExW(key, version, NULL, NULL, (LPBYTE)value, &length); // We know that version is zero-terminated... @@ -448,7 +448,7 @@ bool find_visual_studio_by_fighting_through_microsoft_craziness(Find_Result *res auto version_bytes = (tools_file_size.QuadPart + 1) * 2; // Warning: This multiplication by 2 presumes there is no variable-length encoding in the wchars (wacky characters in the file could betray this expectation). if (version_bytes > 0x7FFFFFFF) continue; // Avoid overflow. - wchar_t *version = (wchar_t *)malloc(version_bytes); + wchar_t *version = (wchar_t *)calloc(1, version_bytes); defer (free(version)); auto read_result = fgetws(version, (int)version_bytes, f); @@ -516,7 +516,7 @@ bool find_visual_studio_by_fighting_through_microsoft_craziness(Find_Result *res continue; } - auto buffer = (wchar_t *)malloc(cb_data); + auto buffer = (wchar_t *)calloc(1, cb_data); if (!buffer) return false; defer (free(buffer)); @@ -530,7 +530,7 @@ bool find_visual_studio_by_fighting_through_microsoft_craziness(Find_Result *res if (build_context.metrics.arch == TargetArch_amd64) { lib_path = concat(buffer, L"VC\\Lib\\amd64\\"); } else if (build_context.metrics.arch == TargetArch_386) { - lib_path = concat(buffer, L"VC\\Lib\\386\\"); + lib_path = concat(buffer, L"VC\\Lib\\"); } else { continue; } @@ -540,7 +540,15 @@ bool find_visual_studio_by_fighting_through_microsoft_craziness(Find_Result *res defer (free(vcruntime_filename)); if (os_file_exists(vcruntime_filename)) { - result->vs_exe_path = concat(buffer, L"VC\\bin\\"); + if (build_context.metrics.arch == TargetArch_amd64) { + result->vs_exe_path = concat(buffer, L"VC\\bin\\"); + } else if (build_context.metrics.arch == TargetArch_386) { + // result->vs_exe_path = concat(buffer, L"VC\\bin\\amd64_x86\\"); + result->vs_exe_path = concat(buffer, L"VC\\bin\\x86_amd64\\"); + } else { + continue; + } + result->vs_library_path = lib_path; return true; } @@ -599,13 +607,15 @@ Find_Result_Utf8 find_visual_studio_and_windows_sdk_utf8() { r.vs_exe_path = mc_wstring_to_string(result.vs_exe_path); r.vs_library_path = mc_wstring_to_string(result.vs_library_path); - // printf("windows_sdk_root: %.*s\n", LIT(r.windows_sdk_root)); - // printf("windows_sdk_um_library_path: %.*s\n", LIT(r.windows_sdk_um_library_path)); - // printf("windows_sdk_ucrt_library_path: %.*s\n", LIT(r.windows_sdk_ucrt_library_path)); - // printf("vs_exe_path: %.*s\n", LIT(r.vs_exe_path)); - // printf("vs_library_path: %.*s\n", LIT(r.vs_library_path)); +#if 0 + printf("windows_sdk_root: %.*s\n", LIT(r.windows_sdk_root)); + printf("windows_sdk_um_library_path: %.*s\n", LIT(r.windows_sdk_um_library_path)); + printf("windows_sdk_ucrt_library_path: %.*s\n", LIT(r.windows_sdk_ucrt_library_path)); + printf("vs_exe_path: %.*s\n", LIT(r.vs_exe_path)); + printf("vs_library_path: %.*s\n", LIT(r.vs_library_path)); - // gb_exit(1); + gb_exit(1); +#endif return r; }