From 4ffc2bbb5ec6993802a59f358c4316375615a27c Mon Sep 17 00:00:00 2001 From: kcbanner Date: Tue, 1 Nov 2022 23:11:52 -0400 Subject: [PATCH 01/17] cmake: handle llvm system libraries separately from the llvm libraries themselves, to fix path issues on windows --- build.zig | 24 ++++++++++++++++++++++++ cmake/Findllvm.cmake | 11 ++++++++--- stage1/config.h.in | 1 + 3 files changed, 33 insertions(+), 3 deletions(-) diff --git a/build.zig b/build.zig index c11329dbf3..61b2a08b09 100644 --- a/build.zig +++ b/build.zig @@ -552,6 +552,7 @@ fn addCmakeCfgOptionsToExe( addCMakeLibraryList(exe, cfg.clang_libraries); addCMakeLibraryList(exe, cfg.lld_libraries); addCMakeLibraryList(exe, cfg.llvm_libraries); + addCMakeSystemLibraryList(exe, cfg.llvm_system_libraries); if (use_zig_libcxx) { exe.linkLibCpp(); @@ -679,6 +680,23 @@ fn addCMakeLibraryList(exe: *std.build.LibExeObjStep, list: []const u8) void { } } +fn addCMakeSystemLibraryList(exe: *std.build.LibExeObjStep, list: []const u8) void { + var it = mem.tokenize(u8, list, ";"); + while (it.next()) |lib| { + var start_offset: usize = 0; + var end_offset: usize = 0; + if (mem.startsWith(u8, lib, "-l")) { + start_offset = "-l".len; + } + + if (exe.target.isWindows() and mem.endsWith(u8, lib, ".lib")) { + end_offset = ".lib".len; + } + + exe.linkSystemLibrary(lib[start_offset..lib.len - end_offset]); + } +} + const CMakeConfig = struct { llvm_linkage: std.build.LibExeObjStep.Linkage, cmake_binary_dir: []const u8, @@ -692,6 +710,7 @@ const CMakeConfig = struct { llvm_lib_dir: []const u8, llvm_include_dir: []const u8, llvm_libraries: []const u8, + llvm_system_libraries: []const u8, dia_guids_lib: []const u8, }; @@ -757,6 +776,7 @@ fn parseConfigH(b: *Builder, config_h_text: []const u8) ?CMakeConfig { .llvm_lib_dir = undefined, .llvm_include_dir = undefined, .llvm_libraries = undefined, + .llvm_system_libraries = undefined, .dia_guids_lib = undefined, }; @@ -797,6 +817,10 @@ fn parseConfigH(b: *Builder, config_h_text: []const u8) ?CMakeConfig { .prefix = "#define ZIG_LLVM_LIBRARIES ", .field = "llvm_libraries", }, + .{ + .prefix = "#define ZIG_LLVM_SYSTEM_LIBRARIES ", + .field = "llvm_system_libraries", + }, .{ .prefix = "#define ZIG_DIA_GUIDS_LIB ", .field = "dia_guids_lib", diff --git a/cmake/Findllvm.cmake b/cmake/Findllvm.cmake index 60a52056d8..87059f9f1d 100644 --- a/cmake/Findllvm.cmake +++ b/cmake/Findllvm.cmake @@ -5,6 +5,7 @@ # LLVM_FOUND # LLVM_INCLUDE_DIRS # LLVM_LIBRARIES +# LLVM_SYSTEM_LIBRARIES # LLVM_LIBDIRS # LLVM_LINK_MODE @@ -172,9 +173,9 @@ if(ZIG_USE_LLVM_CONFIG) OUTPUT_STRIP_TRAILING_WHITESPACE) string(REPLACE " " ";" LLVM_STATIC_SYSTEM_LIBS "${LLVM_STATIC_SYSTEM_LIBS_SPACES}") - set(LLVM_LIBRARIES ${LLVM_LIBRARIES} ${LLVM_SYSTEM_LIBS} ${LLVM_STATIC_SYSTEM_LIBS}) + set(LLVM_SYSTEM_LIBRARIES ${LLVM_SYSTEM_LIBS} ${LLVM_STATIC_SYSTEM_LIBS}) else() - set(LLVM_LIBRARIES ${LLVM_LIBRARIES} ${LLVM_SYSTEM_LIBS}) + set(LLVM_SYSTEM_LIBRARIES ${LLVM_SYSTEM_LIBS}) endif() execute_process( @@ -369,7 +370,11 @@ else() find_path(LLVM_INCLUDE_DIRS NAMES llvm/IR/IRBuilder.h) endif() +if(NOT LLVM_SYSTEM_LIBRARIES) + set(LLVM_SYSTEM_LIBRARIES "") +endif() + include(FindPackageHandleStandardArgs) find_package_handle_standard_args(llvm DEFAULT_MSG LLVM_LIBRARIES LLVM_INCLUDE_DIRS) -mark_as_advanced(LLVM_INCLUDE_DIRS LLVM_LIBRARIES LLVM_LIBDIRS) +mark_as_advanced(LLVM_INCLUDE_DIRS LLVM_LIBRARIES LLVM_SYSTEM_LIBRARIES LLVM_LIBDIRS) diff --git a/stage1/config.h.in b/stage1/config.h.in index 0f1d902ef9..4ec1aa1fa6 100644 --- a/stage1/config.h.in +++ b/stage1/config.h.in @@ -28,5 +28,6 @@ #define ZIG_LLVM_LIBRARIES "@LLVM_LIBRARIES@" #define ZIG_LLVM_LIB_PATH "@LLVM_LIBDIRS@" #define ZIG_LLVM_LINK_MODE "@LLVM_LINK_MODE@" +#define ZIG_LLVM_SYSTEM_LIBRARIES "@LLVM_SYSTEM_LIBRARIES@" #endif From c3945d9edeb304ccd9f3d44e9ab0bf94f5420694 Mon Sep 17 00:00:00 2001 From: kcbanner Date: Wed, 2 Nov 2022 10:12:22 -0400 Subject: [PATCH 02/17] cmake: output binaries to the build directory (ie. instead of Release/Debug subfolders) --- CMakeLists.txt | 1 + 1 file changed, 1 insertion(+) diff --git a/CMakeLists.txt b/CMakeLists.txt index ece221632f..89620a4977 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -168,6 +168,7 @@ foreach(CONFIG_TYPE ${CMAKE_CONFIGURATION_TYPES}) string(TOUPPER ${CONFIG_TYPE} CONFIG_TYPE) set(CMAKE_ARCHIVE_OUTPUT_DIRECTORY_${CONFIG_TYPE} ${ZIG_CPP_LIB_DIR}) set(CMAKE_LIBRARY_OUTPUT_DIRECTORY_${CONFIG_TYPE} ${ZIG_CPP_LIB_DIR}) + set(CMAKE_RUNTIME_OUTPUT_DIRECTORY_${CONFIG_TYPE} ${CMAKE_BINARY_DIR}) endforeach(CONFIG_TYPE CMAKE_CONFIGURATION_TYPES) include_directories(${LLVM_INCLUDE_DIRS}) From 0471eea0e2cac49946449efe4698d5ac18c0dc0d Mon Sep 17 00:00:00 2001 From: kcbanner Date: Tue, 8 Nov 2022 02:14:39 -0500 Subject: [PATCH 03/17] build: first pass on geting stage3 building under x64_64-windows-msvc --- CMakeLists.txt | 17 ++++++++++++----- build.zig | 23 ++++++++++++++++++++--- cmake/Findclang.cmake | 5 +++++ src/Compilation.zig | 4 ++-- src/link/Coff/lld.zig | 6 ++++++ stage1/config.h.in | 1 + 6 files changed, 46 insertions(+), 10 deletions(-) diff --git a/CMakeLists.txt b/CMakeLists.txt index 89620a4977..7340572bdc 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -91,6 +91,7 @@ set(ZIG_STATIC off CACHE BOOL "Attempt to build a static zig executable (not com set(ZIG_SHARED_LLVM off CACHE BOOL "Prefer linking against shared LLVM libraries") set(ZIG_STATIC_LLVM off CACHE BOOL "Prefer linking against static LLVM libraries") set(ZIG_STATIC_ZLIB off CACHE BOOL "Prefer linking against static zlib") +set(ZIG_ENABLE_ZSTD on CACHE BOOL "Enable linking zstd") set(ZIG_STATIC_ZSTD off CACHE BOOL "Prefer linking against static zstd") set(ZIG_USE_CCACHE off CACHE BOOL "Use ccache") @@ -138,19 +139,24 @@ find_package(clang 15) find_package(lld 15) if(ZIG_STATIC_ZLIB) - list(REMOVE_ITEM LLVM_LIBRARIES "-lz") + if (MSVC) + list(REMOVE_ITEM LLVM_SYSTEM_LIBRARIES "z.lib") + else() + list(REMOVE_ITEM LLVM_SYSTEM_LIBRARIES "-lz") + endif() + find_library(ZLIB NAMES libz.a libzlibstatic.a z zlib libz NAMES_PER_DIR) list(APPEND LLVM_LIBRARIES "${ZLIB}") endif() -if(ZIG_STATIC_ZSTD) - list(REMOVE_ITEM LLVM_LIBRARIES "-lzstd") +if(ZIG_STATIC_ZSTD AND ZIG_ENABLE_ZSTD) + list(REMOVE_ITEM LLVM_SYSTEM_LIBRARIES "-lzstd") find_library(ZSTD NAMES libzstd.a libzstdstatic.a zstd NAMES_PER_DIR) list(APPEND LLVM_LIBRARIES "${ZSTD}") endif() if(APPLE AND ZIG_STATIC) - list(REMOVE_ITEM LLVM_LIBRARIES "-lcurses") + list(REMOVE_ITEM LLVM_SYSTEM_LIBRARIES "-lcurses") find_library(CURSES NAMES libcurses.a libncurses.a NAMES_PER_DIR PATHS /usr/local/opt/ncurses/lib @@ -706,6 +712,7 @@ target_link_libraries(zigcpp LINK_PUBLIC ${CLANG_LIBRARIES} ${LLD_LIBRARIES} ${LLVM_LIBRARIES} + ${LLVM_SYSTEM_LIBRARIES} ${CMAKE_THREAD_LIBS_INIT} ) @@ -839,7 +846,7 @@ if(ZIG_SINGLE_THREADED) else() set(ZIG_SINGLE_THREADED_ARG "") endif() -if(ZIG_STATIC) +if(ZIG_STATIC AND NOT MSVC) set(ZIG_STATIC_ARG "-Duse-zig-libcxx") else() set(ZIG_STATIC_ARG "") diff --git a/build.zig b/build.zig index 61b2a08b09..b33596ae52 100644 --- a/build.zig +++ b/build.zig @@ -552,6 +552,7 @@ fn addCmakeCfgOptionsToExe( addCMakeLibraryList(exe, cfg.clang_libraries); addCMakeLibraryList(exe, cfg.lld_libraries); addCMakeLibraryList(exe, cfg.llvm_libraries); + addCMakeSystemLibraryList(exe, cfg.clang_system_libraries); addCMakeSystemLibraryList(exe, cfg.llvm_system_libraries); if (use_zig_libcxx) { @@ -627,10 +628,20 @@ fn addStaticLlvmOptionsToExe(exe: *std.build.LibExeObjStep) !void { } exe.linkSystemLibrary("z"); - exe.linkSystemLibrary("zstd"); - // This means we rely on clang-or-zig-built LLVM, Clang, LLD libraries. - exe.linkSystemLibrary("c++"); + if (exe.target.getOs().tag != .windows and exe.target.getAbi() != .msvc) { + // TODO: Support this on msvc + exe.linkSystemLibrary("zstd"); + + // This means we rely on clang-or-zig-built LLVM, Clang, LLD libraries. + exe.linkSystemLibrary("c++"); + } + + if (exe.target.getOs().tag == .windows) { + exe.linkSystemLibrary("version"); + exe.linkSystemLibrary("uuid"); + exe.linkSystemLibrary("ole32"); + } } fn addCxxKnownPath( @@ -707,6 +718,7 @@ const CMakeConfig = struct { lld_include_dir: []const u8, lld_libraries: []const u8, clang_libraries: []const u8, + clang_system_libraries: []const u8, llvm_lib_dir: []const u8, llvm_include_dir: []const u8, llvm_libraries: []const u8, @@ -773,6 +785,7 @@ fn parseConfigH(b: *Builder, config_h_text: []const u8) ?CMakeConfig { .lld_include_dir = undefined, .lld_libraries = undefined, .clang_libraries = undefined, + .clang_system_libraries = undefined, .llvm_lib_dir = undefined, .llvm_include_dir = undefined, .llvm_libraries = undefined, @@ -813,6 +826,10 @@ fn parseConfigH(b: *Builder, config_h_text: []const u8) ?CMakeConfig { .prefix = "#define ZIG_CLANG_LIBRARIES ", .field = "clang_libraries", }, + .{ + .prefix = "#define ZIG_CLANG_SYSTEM_LIBRARIES ", + .field = "clang_system_libraries", + }, .{ .prefix = "#define ZIG_LLVM_LIBRARIES ", .field = "llvm_libraries", diff --git a/cmake/Findclang.cmake b/cmake/Findclang.cmake index 0949552cac..ba1abbcb64 100644 --- a/cmake/Findclang.cmake +++ b/cmake/Findclang.cmake @@ -5,6 +5,7 @@ # CLANG_FOUND # CLANG_INCLUDE_DIRS # CLANG_LIBRARIES +# CLANG_SYSTEM_LIBRARIES # CLANG_LIBDIRS find_path(CLANG_INCLUDE_DIRS NAMES clang/Frontend/ASTUnit.h @@ -68,6 +69,10 @@ else() FIND_AND_ADD_CLANG_LIB(clangSupport) endif() +if (MSVC) + set(CLANG_SYSTEM_LIBRARIES "version.lib") +endif() + include(FindPackageHandleStandardArgs) find_package_handle_standard_args(clang DEFAULT_MSG CLANG_LIBRARIES CLANG_INCLUDE_DIRS) diff --git a/src/Compilation.zig b/src/Compilation.zig index e365d1dab2..eeecf58751 100644 --- a/src/Compilation.zig +++ b/src/Compilation.zig @@ -3297,8 +3297,8 @@ fn processOneJob(comp: *Compilation, job: Job) !void { // TODO Surface more error details. comp.lockAndSetMiscFailure( .windows_import_lib, - "unable to generate DLL import .lib file: {s}", - .{@errorName(err)}, + "unable to generate DLL import .lib file for {s}: {s}", + .{link_lib, @errorName(err)}, ); }; }, diff --git a/src/link/Coff/lld.zig b/src/link/Coff/lld.zig index 46b0130542..dfa56527bf 100644 --- a/src/link/Coff/lld.zig +++ b/src/link/Coff/lld.zig @@ -486,6 +486,12 @@ pub fn linkWithLLD(self: *Coff, comp: *Compilation, prog_node: *std.Progress.Nod continue; } } + if (target.abi == .msvc) { // TODO: Do this at the top, if we detect we're using the native libc? + log.warn("adding system lib {s}", .{ lib_basename }); + argv.appendAssumeCapacity(lib_basename); + continue; + } + log.err("DLL import library for -l{s} not found", .{key}); return error.DllImportLibraryNotFound; } diff --git a/stage1/config.h.in b/stage1/config.h.in index 4ec1aa1fa6..2f4ed02fdc 100644 --- a/stage1/config.h.in +++ b/stage1/config.h.in @@ -16,6 +16,7 @@ // Used by build.zig for communicating build information to self hosted build. #define ZIG_CLANG_LIBRARIES "@CLANG_LIBRARIES@" +#define ZIG_CLANG_SYSTEM_LIBRARIES "@CLANG_SYSTEM_LIBRARIES@" #define ZIG_CMAKE_BINARY_DIR "@CMAKE_BINARY_DIR@" #define ZIG_CMAKE_PREFIX_PATH "@ZIG_CMAKE_PREFIX_PATH@" #define ZIG_CMAKE_STATIC_LIBRARY_PREFIX "@CMAKE_STATIC_LIBRARY_PREFIX@" From b97a68c529b5db15705f4d542d8ead616d27c880 Mon Sep 17 00:00:00 2001 From: kcbanner Date: Wed, 9 Nov 2022 00:50:29 -0500 Subject: [PATCH 04/17] windows: supporting changes for boostrapping via msvc - add support for passing through .def files to the linker, required for building libLTO.dll in LLVM - fixup libcpp linking conditionals - add option to skip linking zstd for use in bootstrapping (when building against an LLVM with LLVM_ENABLE_ZSTD=OFF) --- build.zig | 14 ++++++++------ src/Compilation.zig | 8 +++++++- src/link.zig | 7 +++++++ src/link/Coff/lld.zig | 4 ++++ src/main.zig | 7 ++++++- 5 files changed, 32 insertions(+), 8 deletions(-) diff --git a/build.zig b/build.zig index b33596ae52..1c814e203a 100644 --- a/build.zig +++ b/build.zig @@ -99,6 +99,7 @@ pub fn build(b: *Builder) !void { const enable_macos_sdk = b.option(bool, "enable-macos-sdk", "Run tests requiring presence of macOS SDK and frameworks") orelse false; const enable_symlinks_windows = b.option(bool, "enable-symlinks-windows", "Run tests requiring presence of symlinks on Windows") orelse false; const config_h_path_option = b.option([]const u8, "config_h", "Path to the generated config.h"); + const disable_zstd = b.option(bool, "disable-zstd", "Skip linking zstd") orelse false; if (!skip_install_lib_files) { b.installDirectory(InstallDirectoryOptions{ @@ -277,8 +278,8 @@ pub fn build(b: *Builder) !void { try addCmakeCfgOptionsToExe(b, cfg, test_cases, use_zig_libcxx); } else { // Here we are -Denable-llvm but no cmake integration. - try addStaticLlvmOptionsToExe(exe); - try addStaticLlvmOptionsToExe(test_cases); + try addStaticLlvmOptionsToExe(exe, !disable_zstd); + try addStaticLlvmOptionsToExe(test_cases, !disable_zstd); } if (target.isWindows()) { inline for (.{ exe, test_cases }) |artifact| { @@ -606,7 +607,7 @@ fn addCmakeCfgOptionsToExe( } } -fn addStaticLlvmOptionsToExe(exe: *std.build.LibExeObjStep) !void { +fn addStaticLlvmOptionsToExe(exe: *std.build.LibExeObjStep, link_zstd: bool) !void { // Adds the Zig C++ sources which both stage1 and stage2 need. // // We need this because otherwise zig_clang_cc1_main.cpp ends up pulling @@ -629,10 +630,11 @@ fn addStaticLlvmOptionsToExe(exe: *std.build.LibExeObjStep) !void { exe.linkSystemLibrary("z"); - if (exe.target.getOs().tag != .windows and exe.target.getAbi() != .msvc) { - // TODO: Support this on msvc + if (link_zstd) { exe.linkSystemLibrary("zstd"); + } + if (exe.target.getOs().tag != .windows or exe.target.getAbi() != .msvc) { // This means we rely on clang-or-zig-built LLVM, Clang, LLD libraries. exe.linkSystemLibrary("c++"); } @@ -704,7 +706,7 @@ fn addCMakeSystemLibraryList(exe: *std.build.LibExeObjStep, list: []const u8) vo end_offset = ".lib".len; } - exe.linkSystemLibrary(lib[start_offset..lib.len - end_offset]); + exe.linkSystemLibrary(lib[start_offset .. lib.len - end_offset]); } } diff --git a/src/Compilation.zig b/src/Compilation.zig index eeecf58751..98eb15c437 100644 --- a/src/Compilation.zig +++ b/src/Compilation.zig @@ -984,6 +984,7 @@ pub const InitOptions = struct { linker_dynamicbase: bool = false, linker_optimization: ?u8 = null, linker_compress_debug_sections: ?link.CompressDebugSections = null, + linker_module_definition_file: ?[]const u8 = null, major_subsystem_version: ?u32 = null, minor_subsystem_version: ?u32 = null, clang_passthrough_mode: bool = false, @@ -1815,6 +1816,7 @@ pub fn create(gpa: Allocator, options: InitOptions) !*Compilation { .allow_shlib_undefined = options.linker_allow_shlib_undefined, .bind_global_refs_locally = options.linker_bind_global_refs_locally orelse false, .compress_debug_sections = options.linker_compress_debug_sections orelse .none, + .module_definition_file = options.linker_module_definition_file, .import_memory = options.linker_import_memory orelse false, .import_symbols = options.linker_import_symbols, .import_table = options.linker_import_table, @@ -4379,7 +4381,7 @@ pub fn addCCArgs( try argv.append("-fno-unwind-tables"); } }, - .shared_library, .ll, .bc, .unknown, .static_library, .object, .zig => {}, + .shared_library, .ll, .bc, .unknown, .static_library, .object, .def, .zig => {}, .assembly => { // The Clang assembler does not accept the list of CPU features like the // compiler frontend does. Therefore we must hard-code the -m flags for @@ -4524,6 +4526,7 @@ pub const FileExt = enum { object, static_library, zig, + def, unknown, pub fn clangSupportsDepFile(ext: FileExt) bool { @@ -4537,6 +4540,7 @@ pub const FileExt = enum { .object, .static_library, .zig, + .def, .unknown, => false, }; @@ -4629,6 +4633,8 @@ pub fn classifyFileExt(filename: []const u8) FileExt { return .object; } else if (mem.endsWith(u8, filename, ".cu")) { return .cu; + } else if (mem.endsWith(u8, filename, ".def")) { + return .def; } else { return .unknown; } diff --git a/src/link.zig b/src/link.zig index 0a526db0de..410d1232af 100644 --- a/src/link.zig +++ b/src/link.zig @@ -219,6 +219,13 @@ pub const Options = struct { /// (Darwin) remove dylibs that are unreachable by the entry point or exported symbols dead_strip_dylibs: bool = false, + /// (Windows) PDB source path prefix to instruct the linker how to resolve relative + /// paths when consolidating CodeView streams into a single PDB file. + pdb_source_path: ?[]const u8 = null, + + /// (Windows) .def file to specify when linking + module_definition_file: ?[] const u8 = null, + pub fn effectiveOutputMode(options: Options) std.builtin.OutputMode { return if (options.use_lld) .Obj else options.output_mode; } diff --git a/src/link/Coff/lld.zig b/src/link/Coff/lld.zig index dfa56527bf..367dde3e88 100644 --- a/src/link/Coff/lld.zig +++ b/src/link/Coff/lld.zig @@ -260,6 +260,10 @@ pub fn linkWithLLD(self: *Coff, comp: *Compilation, prog_node: *std.Progress.Nod try argv.append(p); } + if (self.base.options.module_definition_file) |def| { + try argv.append(try allocPrint(arena, "-DEF:{s}", .{ def })); + } + const resolved_subsystem: ?std.Target.SubSystem = blk: { if (self.base.options.subsystem) |explicit| break :blk explicit; switch (target.os.tag) { diff --git a/src/main.zig b/src/main.zig index 421164de1c..d718f299c7 100644 --- a/src/main.zig +++ b/src/main.zig @@ -742,6 +742,7 @@ fn buildOutputType( var linker_nxcompat = false; var linker_dynamicbase = false; var linker_optimization: ?u8 = null; + var linker_module_definition_file: ?[]const u8 = null; var test_evented_io = false; var test_no_exec = false; var entry: ?[]const u8 = null; @@ -1404,7 +1405,7 @@ fn buildOutputType( root_src_file = arg; } }, - .unknown => { + .def, .unknown => { fatal("unrecognized file extension of parameter '{s}'", .{arg}); }, } @@ -1478,6 +1479,9 @@ fn buildOutputType( .must_link = must_link, }); }, + .def => { + linker_module_definition_file = it.only_arg; + }, .zig => { if (root_src_file) |other| { fatal("found another zig file '{s}' after root source file '{s}'", .{ it.only_arg, other }); @@ -3015,6 +3019,7 @@ fn buildOutputType( .linker_dynamicbase = linker_dynamicbase, .linker_optimization = linker_optimization, .linker_compress_debug_sections = linker_compress_debug_sections, + .linker_module_definition_file = linker_module_definition_file, .major_subsystem_version = major_subsystem_version, .minor_subsystem_version = minor_subsystem_version, .link_eh_frame_hdr = link_eh_frame_hdr, From 2d0fd76766eb231ce3021d023ad8fca05cbb81c0 Mon Sep 17 00:00:00 2001 From: kcbanner Date: Fri, 11 Nov 2022 01:38:39 -0500 Subject: [PATCH 05/17] fixup: remove leftover log --- src/link/Coff/lld.zig | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/src/link/Coff/lld.zig b/src/link/Coff/lld.zig index 367dde3e88..cc89c8d344 100644 --- a/src/link/Coff/lld.zig +++ b/src/link/Coff/lld.zig @@ -490,8 +490,7 @@ pub fn linkWithLLD(self: *Coff, comp: *Compilation, prog_node: *std.Progress.Nod continue; } } - if (target.abi == .msvc) { // TODO: Do this at the top, if we detect we're using the native libc? - log.warn("adding system lib {s}", .{ lib_basename }); + if (target.abi == .msvc) { argv.appendAssumeCapacity(lib_basename); continue; } From a03c8ef4bf526888518d13de1794c28375900cc2 Mon Sep 17 00:00:00 2001 From: kcbanner Date: Fri, 11 Nov 2022 13:31:10 -0500 Subject: [PATCH 06/17] fixup formatting --- src/Compilation.zig | 2 +- src/link.zig | 2 +- src/link/Coff/lld.zig | 2 +- 3 files changed, 3 insertions(+), 3 deletions(-) diff --git a/src/Compilation.zig b/src/Compilation.zig index 98eb15c437..aa352fb9ab 100644 --- a/src/Compilation.zig +++ b/src/Compilation.zig @@ -3300,7 +3300,7 @@ fn processOneJob(comp: *Compilation, job: Job) !void { comp.lockAndSetMiscFailure( .windows_import_lib, "unable to generate DLL import .lib file for {s}: {s}", - .{link_lib, @errorName(err)}, + .{ link_lib, @errorName(err) }, ); }; }, diff --git a/src/link.zig b/src/link.zig index 410d1232af..ee9efd83ed 100644 --- a/src/link.zig +++ b/src/link.zig @@ -224,7 +224,7 @@ pub const Options = struct { pdb_source_path: ?[]const u8 = null, /// (Windows) .def file to specify when linking - module_definition_file: ?[] const u8 = null, + module_definition_file: ?[]const u8 = null, pub fn effectiveOutputMode(options: Options) std.builtin.OutputMode { return if (options.use_lld) .Obj else options.output_mode; diff --git a/src/link/Coff/lld.zig b/src/link/Coff/lld.zig index cc89c8d344..be6c90d11d 100644 --- a/src/link/Coff/lld.zig +++ b/src/link/Coff/lld.zig @@ -261,7 +261,7 @@ pub fn linkWithLLD(self: *Coff, comp: *Compilation, prog_node: *std.Progress.Nod } if (self.base.options.module_definition_file) |def| { - try argv.append(try allocPrint(arena, "-DEF:{s}", .{ def })); + try argv.append(try allocPrint(arena, "-DEF:{s}", .{def})); } const resolved_subsystem: ?std.Target.SubSystem = blk: { From b42442f5b4913938b04f580b1d13a1fd7318514d Mon Sep 17 00:00:00 2001 From: kcbanner Date: Sun, 13 Nov 2022 03:42:51 -0500 Subject: [PATCH 07/17] windows: fixes to support using zig cc/c++ with CMake on Windows Using zig cc with CMake on Windows was failing during compiler detection. -nostdinc was causing the crt not to be linked, and Coff/lld.zig assumed that wWinMainCRTStartup would be present in this case. -nostdlib did not prevent the default behaviour of linking libc++ when zig c++ was used. This caused libc++ to be built when CMake ran ABI detection using zig c++, which fails as libcxxabi cannot compile under MSVC. - Change the behaviour of COFF -nostdinc to set /entry to the function that the default CRT method for the specified subsystem would have called. - Fix -ENTRY being passed twice if it was specified explicitly and -nostdlib was present. - Add support for /pdb, /version, /implib, and /subsystem as linker args (passed by CMake) - Remove -Ddisable-zstd, no longer needed - Add -Ddisable-libcpp for use when bootstrapping on msvc --- CMakeLists.txt | 1 + build.zig | 13 +++++-------- src/Compilation.zig | 7 +++++++ src/link.zig | 3 +++ src/link/Coff/lld.zig | 35 ++++++++++++++++++++++++++++++++--- src/main.zig | 25 ++++++++++++++++++++++++- 6 files changed, 72 insertions(+), 12 deletions(-) diff --git a/CMakeLists.txt b/CMakeLists.txt index 7340572bdc..a92878781b 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -92,6 +92,7 @@ set(ZIG_SHARED_LLVM off CACHE BOOL "Prefer linking against shared LLVM libraries set(ZIG_STATIC_LLVM off CACHE BOOL "Prefer linking against static LLVM libraries") set(ZIG_STATIC_ZLIB off CACHE BOOL "Prefer linking against static zlib") set(ZIG_ENABLE_ZSTD on CACHE BOOL "Enable linking zstd") +set(ZIG_ENABLE_LIBCPP on CACHE BOOL "Enable linking libcpp") set(ZIG_STATIC_ZSTD off CACHE BOOL "Prefer linking against static zstd") set(ZIG_USE_CCACHE off CACHE BOOL "Use ccache") diff --git a/build.zig b/build.zig index 1c814e203a..6eba66db42 100644 --- a/build.zig +++ b/build.zig @@ -99,7 +99,7 @@ pub fn build(b: *Builder) !void { const enable_macos_sdk = b.option(bool, "enable-macos-sdk", "Run tests requiring presence of macOS SDK and frameworks") orelse false; const enable_symlinks_windows = b.option(bool, "enable-symlinks-windows", "Run tests requiring presence of symlinks on Windows") orelse false; const config_h_path_option = b.option([]const u8, "config_h", "Path to the generated config.h"); - const disable_zstd = b.option(bool, "disable-zstd", "Skip linking zstd") orelse false; + const disable_libcpp = b.option(bool, "disable-libcpp", "Skip building/linking libcpp") orelse false; if (!skip_install_lib_files) { b.installDirectory(InstallDirectoryOptions{ @@ -278,8 +278,8 @@ pub fn build(b: *Builder) !void { try addCmakeCfgOptionsToExe(b, cfg, test_cases, use_zig_libcxx); } else { // Here we are -Denable-llvm but no cmake integration. - try addStaticLlvmOptionsToExe(exe, !disable_zstd); - try addStaticLlvmOptionsToExe(test_cases, !disable_zstd); + try addStaticLlvmOptionsToExe(exe); + try addStaticLlvmOptionsToExe(test_cases); } if (target.isWindows()) { inline for (.{ exe, test_cases }) |artifact| { @@ -607,7 +607,7 @@ fn addCmakeCfgOptionsToExe( } } -fn addStaticLlvmOptionsToExe(exe: *std.build.LibExeObjStep, link_zstd: bool) !void { +fn addStaticLlvmOptionsToExe(exe: *std.build.LibExeObjStep) !void { // Adds the Zig C++ sources which both stage1 and stage2 need. // // We need this because otherwise zig_clang_cc1_main.cpp ends up pulling @@ -629,10 +629,7 @@ fn addStaticLlvmOptionsToExe(exe: *std.build.LibExeObjStep, link_zstd: bool) !vo } exe.linkSystemLibrary("z"); - - if (link_zstd) { - exe.linkSystemLibrary("zstd"); - } + exe.linkSystemLibrary("zstd"); if (exe.target.getOs().tag != .windows or exe.target.getAbi() != .msvc) { // This means we rely on clang-or-zig-built LLVM, Clang, LLD libraries. diff --git a/src/Compilation.zig b/src/Compilation.zig index aa352fb9ab..5d0a9308af 100644 --- a/src/Compilation.zig +++ b/src/Compilation.zig @@ -1042,6 +1042,11 @@ pub const InitOptions = struct { /// (Darwin) remove dylibs that are unreachable by the entry point or exported symbols dead_strip_dylibs: bool = false, libcxx_abi_version: libcxx.AbiVersion = libcxx.AbiVersion.default, + /// (Windows) PDB source path prefix to instruct the linker how to resolve relative + /// paths when consolidating CodeView streams into a single PDB file. + pdb_source_path: ?[]const u8 = null, + /// (Windows) PDB output path + pdb_out_path: ?[]const u8 = null, }; fn addPackageTableToCacheHash( @@ -1892,6 +1897,8 @@ pub fn create(gpa: Allocator, options: InitOptions) !*Compilation { .headerpad_max_install_names = options.headerpad_max_install_names, .dead_strip_dylibs = options.dead_strip_dylibs, .force_undefined_symbols = .{}, + .pdb_source_path = pdb_source_path, + .pdb_out_path = options.pdb_out_path, }); errdefer bin_file.destroy(); comp.* = .{ diff --git a/src/link.zig b/src/link.zig index ee9efd83ed..222c0e4918 100644 --- a/src/link.zig +++ b/src/link.zig @@ -223,6 +223,9 @@ pub const Options = struct { /// paths when consolidating CodeView streams into a single PDB file. pdb_source_path: ?[]const u8 = null, + /// (Windows) PDB output path + pdb_out_path: ?[]const u8 = null, + /// (Windows) .def file to specify when linking module_definition_file: ?[]const u8 = null, diff --git a/src/link/Coff/lld.zig b/src/link/Coff/lld.zig index be6c90d11d..4f1124115e 100644 --- a/src/link/Coff/lld.zig +++ b/src/link/Coff/lld.zig @@ -166,12 +166,16 @@ pub fn linkWithLLD(self: *Coff, comp: *Compilation, prog_node: *std.Progress.Nod try argv.append("-DEBUG"); const out_ext = std.fs.path.extension(full_out_path); - const out_pdb = try allocPrint(arena, "{s}.pdb", .{ + const out_pdb = self.base.options.pdb_out_path orelse try allocPrint(arena, "{s}.pdb", .{ full_out_path[0 .. full_out_path.len - out_ext.len], }); + try argv.append(try allocPrint(arena, "-PDB:{s}", .{out_pdb})); try argv.append(try allocPrint(arena, "-PDBALTPATH:{s}", .{out_pdb})); } + if (self.base.options.version) |version| { + try argv.append(try allocPrint(arena, "-VERSION:{}.{}", .{ version.major, version.minor })); + } if (self.base.options.lto) { switch (self.base.options.optimize_mode) { .Debug => {}, @@ -427,7 +431,7 @@ pub fn linkWithLLD(self: *Coff, comp: *Compilation, prog_node: *std.Progress.Nod } } else { try argv.append("-NODEFAULTLIB"); - if (!is_lib) { + if (!is_lib and self.base.options.entry == null) { if (self.base.options.module) |module| { if (module.stage1_flags.have_winmain_crt_startup) { try argv.append("-ENTRY:WinMainCRTStartup"); @@ -435,7 +439,32 @@ pub fn linkWithLLD(self: *Coff, comp: *Compilation, prog_node: *std.Progress.Nod try argv.append("-ENTRY:wWinMainCRTStartup"); } } else { - try argv.append("-ENTRY:wWinMainCRTStartup"); + // If the crt isn't being linked, it won't provide the CRT startup methods that + // call through to the user-provided entrypoint. Instead, choose the entry point + // that the CRT methods would have called. Note that this differs from the behaviour + // of link.exe (which still tries to use the CRT methods in this case), but this + // fixes CMake compiler checks when using zig cc on Windows, as Windows-Clang.cmake + // does not specify /entry:main + + // TODO: I think the correct thing to do in this case would be to inspect the object + // being linked (like link.exe / lld-link does) and detect which symbols are available. + // This would allow detection of the w variants, as well as the crt methods. + if (resolved_subsystem) |subsystem| { + switch (subsystem) { + .Console => { + // The default is to call mainCRTStartup/wmainCRTStartup, which calls main/wmain + try argv.append("-ENTRY:main"); + }, + .Windows => { + // The default is to call WinMainCRTStartup/wWinMainCRTStartup, which calls WinMain/wWinMain + try argv.append("-ENTRY:WinMain"); + }, + else => {} + } + } + + // when no /entry is specified, lld-link will infer it based on which functions + // are present in the object being linked - see lld/COFF/Driver.cpp#LinkerDriver::findDefaultEntry } } } diff --git a/src/main.zig b/src/main.zig index d718f299c7..5e2377637c 100644 --- a/src/main.zig +++ b/src/main.zig @@ -782,6 +782,7 @@ fn buildOutputType( var headerpad_max_install_names: bool = false; var dead_strip_dylibs: bool = false; var reference_trace: ?u32 = null; + var pdb_out_path: ?[]const u8 = null; // e.g. -m3dnow or -mno-outline-atomics. They correspond to std.Target llvm cpu feature names. // This array is populated by zig cc frontend and then has to be converted to zig-style @@ -1541,7 +1542,10 @@ fn buildOutputType( .no_stack_protector => want_stack_protector = 0, .unwind_tables => want_unwind_tables = true, .no_unwind_tables => want_unwind_tables = false, - .nostdlib => ensure_libc_on_non_freestanding = false, + .nostdlib => { + ensure_libc_on_non_freestanding = false; + ensure_libcpp_on_non_freestanding = false; + }, .nostdlib_cpp => ensure_libcpp_on_non_freestanding = false, .shared => { link_mode = .Dynamic; @@ -2120,6 +2124,24 @@ fn buildOutputType( next_arg, }); }; + } else if (mem.startsWith(u8, arg, "/subsystem:")) { + var split_it = mem.splitBackwards(u8, arg, ":"); + subsystem = try parseSubSystem(split_it.first()); + } else if (mem.startsWith(u8, arg, "/implib:")) { + var split_it = mem.splitBackwards(u8, arg, ":"); + emit_implib = .{ .yes = split_it.first() }; + emit_implib_arg_provided = true; + } else if (mem.startsWith(u8, arg, "/pdb:")) { + var split_it = mem.splitBackwards(u8, arg, ":"); + pdb_out_path = split_it.first(); + } else if (mem.startsWith(u8, arg, "/version:")) { + var split_it = mem.splitBackwards(u8, arg, ":"); + const version_arg = split_it.first(); + version = std.builtin.Version.parse(version_arg) catch |err| { + fatal("unable to parse /version '{s}': {s}", .{ arg, @errorName(err) }); + }; + + have_version = true; } else { warn("unsupported linker arg: {s}", .{arg}); } @@ -3069,6 +3091,7 @@ fn buildOutputType( .headerpad_max_install_names = headerpad_max_install_names, .dead_strip_dylibs = dead_strip_dylibs, .reference_trace = reference_trace, + .pdb_out_path = pdb_out_path, }) catch |err| switch (err) { error.LibCUnavailable => { const target = target_info.target; From cd430b5b081f45ad481a18d15741a96e0ad94167 Mon Sep 17 00:00:00 2001 From: kcbanner Date: Mon, 14 Nov 2022 13:57:33 -0500 Subject: [PATCH 08/17] windows: revert changes made to lld.zig to support the way CMake calls zig cc on Windows-Clang --- src/link/Coff/lld.zig | 27 +-------------------------- 1 file changed, 1 insertion(+), 26 deletions(-) diff --git a/src/link/Coff/lld.zig b/src/link/Coff/lld.zig index 4f1124115e..da09505e90 100644 --- a/src/link/Coff/lld.zig +++ b/src/link/Coff/lld.zig @@ -439,32 +439,7 @@ pub fn linkWithLLD(self: *Coff, comp: *Compilation, prog_node: *std.Progress.Nod try argv.append("-ENTRY:wWinMainCRTStartup"); } } else { - // If the crt isn't being linked, it won't provide the CRT startup methods that - // call through to the user-provided entrypoint. Instead, choose the entry point - // that the CRT methods would have called. Note that this differs from the behaviour - // of link.exe (which still tries to use the CRT methods in this case), but this - // fixes CMake compiler checks when using zig cc on Windows, as Windows-Clang.cmake - // does not specify /entry:main - - // TODO: I think the correct thing to do in this case would be to inspect the object - // being linked (like link.exe / lld-link does) and detect which symbols are available. - // This would allow detection of the w variants, as well as the crt methods. - if (resolved_subsystem) |subsystem| { - switch (subsystem) { - .Console => { - // The default is to call mainCRTStartup/wmainCRTStartup, which calls main/wmain - try argv.append("-ENTRY:main"); - }, - .Windows => { - // The default is to call WinMainCRTStartup/wWinMainCRTStartup, which calls WinMain/wWinMain - try argv.append("-ENTRY:WinMain"); - }, - else => {} - } - } - - // when no /entry is specified, lld-link will infer it based on which functions - // are present in the object being linked - see lld/COFF/Driver.cpp#LinkerDriver::findDefaultEntry + try argv.append("-ENTRY:wWinMainCRTStartup"); } } } From 2c73bb9a057173ef1b6b599a8769a536a6070a36 Mon Sep 17 00:00:00 2001 From: kcbanner Date: Thu, 8 Dec 2022 19:42:00 -0500 Subject: [PATCH 09/17] fixup from rebase --- build.zig | 1 - 1 file changed, 1 deletion(-) diff --git a/build.zig b/build.zig index 6eba66db42..eb1d4ab34a 100644 --- a/build.zig +++ b/build.zig @@ -99,7 +99,6 @@ pub fn build(b: *Builder) !void { const enable_macos_sdk = b.option(bool, "enable-macos-sdk", "Run tests requiring presence of macOS SDK and frameworks") orelse false; const enable_symlinks_windows = b.option(bool, "enable-symlinks-windows", "Run tests requiring presence of symlinks on Windows") orelse false; const config_h_path_option = b.option([]const u8, "config_h", "Path to the generated config.h"); - const disable_libcpp = b.option(bool, "disable-libcpp", "Skip building/linking libcpp") orelse false; if (!skip_install_lib_files) { b.installDirectory(InstallDirectoryOptions{ From 701996083a8e4ac6209d953a38df8dfb7d18a184 Mon Sep 17 00:00:00 2001 From: kcbanner Date: Tue, 13 Dec 2022 01:30:03 -0500 Subject: [PATCH 10/17] cmake: /std:c99 isn't a valid cl option --- CMakeLists.txt | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/CMakeLists.txt b/CMakeLists.txt index a92878781b..0b9ad284ab 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -731,8 +731,8 @@ set(HOST_TARGET_TRIPLE "${HOST_TARGET_ARCH}-${HOST_TARGET_OS}") if(MSVC) set(ZIG_WASM2C_COMPILE_FLAGS "") - set(ZIG1_COMPILE_FLAGS "/std:c99 /Os") - set(ZIG2_COMPILE_FLAGS "/std:c99 /O0") + set(ZIG1_COMPILE_FLAGS "/Os") + set(ZIG2_COMPILE_FLAGS "/O0") set(ZIG2_LINK_FLAGS "/STACK:16777216") else() set(ZIG_WASM2C_COMPILE_FLAGS "-std=c99 -O2") From 9c0a41f88afadc29fa46565da5df8cdda177b497 Mon Sep 17 00:00:00 2001 From: kcbanner Date: Tue, 13 Dec 2022 01:34:13 -0500 Subject: [PATCH 11/17] rebase fixup --- src/Compilation.zig | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/Compilation.zig b/src/Compilation.zig index 5d0a9308af..f90b8f28d1 100644 --- a/src/Compilation.zig +++ b/src/Compilation.zig @@ -1897,7 +1897,7 @@ pub fn create(gpa: Allocator, options: InitOptions) !*Compilation { .headerpad_max_install_names = options.headerpad_max_install_names, .dead_strip_dylibs = options.dead_strip_dylibs, .force_undefined_symbols = .{}, - .pdb_source_path = pdb_source_path, + .pdb_source_path = options.pdb_source_path, .pdb_out_path = options.pdb_out_path, }); errdefer bin_file.destroy(); From bd252c58bcb155bfda4d9fab46a1e0a0a5f806fd Mon Sep 17 00:00:00 2001 From: kcbanner Date: Sat, 17 Dec 2022 17:55:56 -0500 Subject: [PATCH 12/17] cmake: /O0 -> /Od --- CMakeLists.txt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/CMakeLists.txt b/CMakeLists.txt index 0b9ad284ab..2fc9be5e3e 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -732,7 +732,7 @@ set(HOST_TARGET_TRIPLE "${HOST_TARGET_ARCH}-${HOST_TARGET_OS}") if(MSVC) set(ZIG_WASM2C_COMPILE_FLAGS "") set(ZIG1_COMPILE_FLAGS "/Os") - set(ZIG2_COMPILE_FLAGS "/O0") + set(ZIG2_COMPILE_FLAGS "/Od") set(ZIG2_LINK_FLAGS "/STACK:16777216") else() set(ZIG_WASM2C_COMPILE_FLAGS "-std=c99 -O2") From 88e442253b5cd0087b3f8da63e1653b9356dc6ab Mon Sep 17 00:00:00 2001 From: kcbanner Date: Wed, 28 Dec 2022 02:11:12 -0500 Subject: [PATCH 13/17] cmake: add /FORCE:MULTIPLE to handle fabsl being defined in compiler_rt as well as libcmpt --- CMakeLists.txt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/CMakeLists.txt b/CMakeLists.txt index 2fc9be5e3e..310f90a9ca 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -733,7 +733,7 @@ if(MSVC) set(ZIG_WASM2C_COMPILE_FLAGS "") set(ZIG1_COMPILE_FLAGS "/Os") set(ZIG2_COMPILE_FLAGS "/Od") - set(ZIG2_LINK_FLAGS "/STACK:16777216") + set(ZIG2_LINK_FLAGS "/STACK:16777216 /FORCE:MULTIPLE") else() set(ZIG_WASM2C_COMPILE_FLAGS "-std=c99 -O2") set(ZIG1_COMPILE_FLAGS "-std=c99 -Os") From f5135f8e3b0d7a23d44944c720b6a6f3410a2b3a Mon Sep 17 00:00:00 2001 From: kcbanner Date: Tue, 3 Jan 2023 02:51:22 -0500 Subject: [PATCH 14/17] cmake: fix handling of transitive zstd dependency - Remove ZIG_ENABLE_ZSTD in favour of allowing ZIG_STATIC_ZSTD to be toggled off explicitly when ZIG_STATIC is on - Remove ZIG_ENABLE_LIBCPP (now unused) --- CMakeLists.txt | 23 ++++++++++------------- 1 file changed, 10 insertions(+), 13 deletions(-) diff --git a/CMakeLists.txt b/CMakeLists.txt index 310f90a9ca..69b818259a 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -89,11 +89,9 @@ endif() set(ZIG_STATIC off CACHE BOOL "Attempt to build a static zig executable (not compatible with glibc)") set(ZIG_SHARED_LLVM off CACHE BOOL "Prefer linking against shared LLVM libraries") -set(ZIG_STATIC_LLVM off CACHE BOOL "Prefer linking against static LLVM libraries") -set(ZIG_STATIC_ZLIB off CACHE BOOL "Prefer linking against static zlib") -set(ZIG_ENABLE_ZSTD on CACHE BOOL "Enable linking zstd") -set(ZIG_ENABLE_LIBCPP on CACHE BOOL "Enable linking libcpp") -set(ZIG_STATIC_ZSTD off CACHE BOOL "Prefer linking against static zstd") +set(ZIG_STATIC_LLVM ${ZIG_STATIC} CACHE BOOL "Prefer linking against static LLVM libraries") +set(ZIG_STATIC_ZLIB ${ZIG_STATIC} CACHE BOOL "Prefer linking against static zlib") +set(ZIG_STATIC_ZSTD ${ZIG_STATIC} CACHE BOOL "Prefer linking against static zstd") set(ZIG_USE_CCACHE off CACHE BOOL "Use ccache") if(ZIG_USE_CCACHE) @@ -105,12 +103,6 @@ if(ZIG_USE_CCACHE) endif() endif() -if(ZIG_STATIC) - set(ZIG_STATIC_LLVM ON) - set(ZIG_STATIC_ZLIB ON) - set(ZIG_STATIC_ZSTD ON) -endif() - if (ZIG_SHARED_LLVM AND ZIG_STATIC_LLVM) message(SEND_ERROR "-DZIG_SHARED_LLVM and -DZIG_STATIC_LLVM cannot both be enabled simultaneously") endif() @@ -150,8 +142,13 @@ if(ZIG_STATIC_ZLIB) list(APPEND LLVM_LIBRARIES "${ZLIB}") endif() -if(ZIG_STATIC_ZSTD AND ZIG_ENABLE_ZSTD) - list(REMOVE_ITEM LLVM_SYSTEM_LIBRARIES "-lzstd") +if(ZIG_STATIC_ZSTD) + if (MSVC) + list(REMOVE_ITEM LLVM_SYSTEM_LIBRARIES "zstd.lib") + else() + list(REMOVE_ITEM LLVM_SYSTEM_LIBRARIES "-lzstd") + endif() + find_library(ZSTD NAMES libzstd.a libzstdstatic.a zstd NAMES_PER_DIR) list(APPEND LLVM_LIBRARIES "${ZSTD}") endif() From 3cacbea95b2052f0dffd0a412f5e99ff61397826 Mon Sep 17 00:00:00 2001 From: kcbanner Date: Wed, 4 Jan 2023 02:18:51 -0500 Subject: [PATCH 15/17] build: simplify llvm-config provided system library parsing - Revert the addition of CLANG_SYSTEM_LIBARIES and LLVM_SYSTEM_LIBRARIES - Change addCMakeLibraryList to parse non-absolute path .lib dependencies as system libraries --- CMakeLists.txt | 11 +++++------ build.zig | 33 ++------------------------------- cmake/Findclang.cmake | 3 +-- cmake/Findllvm.cmake | 11 +++-------- stage1/config.h.in | 2 -- 5 files changed, 11 insertions(+), 49 deletions(-) diff --git a/CMakeLists.txt b/CMakeLists.txt index 69b818259a..dd3e016edb 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -133,9 +133,9 @@ find_package(lld 15) if(ZIG_STATIC_ZLIB) if (MSVC) - list(REMOVE_ITEM LLVM_SYSTEM_LIBRARIES "z.lib") + list(REMOVE_ITEM LLVM_LIBRARIES "z.lib") else() - list(REMOVE_ITEM LLVM_SYSTEM_LIBRARIES "-lz") + list(REMOVE_ITEM LLVM_LIBRARIES "-lz") endif() find_library(ZLIB NAMES libz.a libzlibstatic.a z zlib libz NAMES_PER_DIR) @@ -144,9 +144,9 @@ endif() if(ZIG_STATIC_ZSTD) if (MSVC) - list(REMOVE_ITEM LLVM_SYSTEM_LIBRARIES "zstd.lib") + list(REMOVE_ITEM LLVM_LIBRARIES "zstd.lib") else() - list(REMOVE_ITEM LLVM_SYSTEM_LIBRARIES "-lzstd") + list(REMOVE_ITEM LLVM_LIBRARIES "-lzstd") endif() find_library(ZSTD NAMES libzstd.a libzstdstatic.a zstd NAMES_PER_DIR) @@ -154,7 +154,7 @@ if(ZIG_STATIC_ZSTD) endif() if(APPLE AND ZIG_STATIC) - list(REMOVE_ITEM LLVM_SYSTEM_LIBRARIES "-lcurses") + list(REMOVE_ITEM LLVM_LIBRARIES "-lcurses") find_library(CURSES NAMES libcurses.a libncurses.a NAMES_PER_DIR PATHS /usr/local/opt/ncurses/lib @@ -710,7 +710,6 @@ target_link_libraries(zigcpp LINK_PUBLIC ${CLANG_LIBRARIES} ${LLD_LIBRARIES} ${LLVM_LIBRARIES} - ${LLVM_SYSTEM_LIBRARIES} ${CMAKE_THREAD_LIBS_INIT} ) diff --git a/build.zig b/build.zig index eb1d4ab34a..999ebad08e 100644 --- a/build.zig +++ b/build.zig @@ -552,8 +552,6 @@ fn addCmakeCfgOptionsToExe( addCMakeLibraryList(exe, cfg.clang_libraries); addCMakeLibraryList(exe, cfg.lld_libraries); addCMakeLibraryList(exe, cfg.llvm_libraries); - addCMakeSystemLibraryList(exe, cfg.clang_system_libraries); - addCMakeSystemLibraryList(exe, cfg.llvm_system_libraries); if (use_zig_libcxx) { exe.linkLibCpp(); @@ -683,29 +681,14 @@ fn addCMakeLibraryList(exe: *std.build.LibExeObjStep, list: []const u8) void { while (it.next()) |lib| { if (mem.startsWith(u8, lib, "-l")) { exe.linkSystemLibrary(lib["-l".len..]); + } else if (exe.target.isWindows() and mem.endsWith(u8, lib, ".lib") and !fs.path.isAbsolute(lib)) { + exe.linkSystemLibrary(lib[0 .. lib.len - ".lib".len]); } else { exe.addObjectFile(lib); } } } -fn addCMakeSystemLibraryList(exe: *std.build.LibExeObjStep, list: []const u8) void { - var it = mem.tokenize(u8, list, ";"); - while (it.next()) |lib| { - var start_offset: usize = 0; - var end_offset: usize = 0; - if (mem.startsWith(u8, lib, "-l")) { - start_offset = "-l".len; - } - - if (exe.target.isWindows() and mem.endsWith(u8, lib, ".lib")) { - end_offset = ".lib".len; - } - - exe.linkSystemLibrary(lib[start_offset .. lib.len - end_offset]); - } -} - const CMakeConfig = struct { llvm_linkage: std.build.LibExeObjStep.Linkage, cmake_binary_dir: []const u8, @@ -716,11 +699,9 @@ const CMakeConfig = struct { lld_include_dir: []const u8, lld_libraries: []const u8, clang_libraries: []const u8, - clang_system_libraries: []const u8, llvm_lib_dir: []const u8, llvm_include_dir: []const u8, llvm_libraries: []const u8, - llvm_system_libraries: []const u8, dia_guids_lib: []const u8, }; @@ -783,11 +764,9 @@ fn parseConfigH(b: *Builder, config_h_text: []const u8) ?CMakeConfig { .lld_include_dir = undefined, .lld_libraries = undefined, .clang_libraries = undefined, - .clang_system_libraries = undefined, .llvm_lib_dir = undefined, .llvm_include_dir = undefined, .llvm_libraries = undefined, - .llvm_system_libraries = undefined, .dia_guids_lib = undefined, }; @@ -824,18 +803,10 @@ fn parseConfigH(b: *Builder, config_h_text: []const u8) ?CMakeConfig { .prefix = "#define ZIG_CLANG_LIBRARIES ", .field = "clang_libraries", }, - .{ - .prefix = "#define ZIG_CLANG_SYSTEM_LIBRARIES ", - .field = "clang_system_libraries", - }, .{ .prefix = "#define ZIG_LLVM_LIBRARIES ", .field = "llvm_libraries", }, - .{ - .prefix = "#define ZIG_LLVM_SYSTEM_LIBRARIES ", - .field = "llvm_system_libraries", - }, .{ .prefix = "#define ZIG_DIA_GUIDS_LIB ", .field = "dia_guids_lib", diff --git a/cmake/Findclang.cmake b/cmake/Findclang.cmake index ba1abbcb64..4441664447 100644 --- a/cmake/Findclang.cmake +++ b/cmake/Findclang.cmake @@ -5,7 +5,6 @@ # CLANG_FOUND # CLANG_INCLUDE_DIRS # CLANG_LIBRARIES -# CLANG_SYSTEM_LIBRARIES # CLANG_LIBDIRS find_path(CLANG_INCLUDE_DIRS NAMES clang/Frontend/ASTUnit.h @@ -70,7 +69,7 @@ else() endif() if (MSVC) - set(CLANG_SYSTEM_LIBRARIES "version.lib") + set(CLANG_LIBRARIES ${CLANG_LIBRARIES} "version.lib") endif() include(FindPackageHandleStandardArgs) diff --git a/cmake/Findllvm.cmake b/cmake/Findllvm.cmake index 87059f9f1d..60a52056d8 100644 --- a/cmake/Findllvm.cmake +++ b/cmake/Findllvm.cmake @@ -5,7 +5,6 @@ # LLVM_FOUND # LLVM_INCLUDE_DIRS # LLVM_LIBRARIES -# LLVM_SYSTEM_LIBRARIES # LLVM_LIBDIRS # LLVM_LINK_MODE @@ -173,9 +172,9 @@ if(ZIG_USE_LLVM_CONFIG) OUTPUT_STRIP_TRAILING_WHITESPACE) string(REPLACE " " ";" LLVM_STATIC_SYSTEM_LIBS "${LLVM_STATIC_SYSTEM_LIBS_SPACES}") - set(LLVM_SYSTEM_LIBRARIES ${LLVM_SYSTEM_LIBS} ${LLVM_STATIC_SYSTEM_LIBS}) + set(LLVM_LIBRARIES ${LLVM_LIBRARIES} ${LLVM_SYSTEM_LIBS} ${LLVM_STATIC_SYSTEM_LIBS}) else() - set(LLVM_SYSTEM_LIBRARIES ${LLVM_SYSTEM_LIBS}) + set(LLVM_LIBRARIES ${LLVM_LIBRARIES} ${LLVM_SYSTEM_LIBS}) endif() execute_process( @@ -370,11 +369,7 @@ else() find_path(LLVM_INCLUDE_DIRS NAMES llvm/IR/IRBuilder.h) endif() -if(NOT LLVM_SYSTEM_LIBRARIES) - set(LLVM_SYSTEM_LIBRARIES "") -endif() - include(FindPackageHandleStandardArgs) find_package_handle_standard_args(llvm DEFAULT_MSG LLVM_LIBRARIES LLVM_INCLUDE_DIRS) -mark_as_advanced(LLVM_INCLUDE_DIRS LLVM_LIBRARIES LLVM_SYSTEM_LIBRARIES LLVM_LIBDIRS) +mark_as_advanced(LLVM_INCLUDE_DIRS LLVM_LIBRARIES LLVM_LIBDIRS) diff --git a/stage1/config.h.in b/stage1/config.h.in index 2f4ed02fdc..0f1d902ef9 100644 --- a/stage1/config.h.in +++ b/stage1/config.h.in @@ -16,7 +16,6 @@ // Used by build.zig for communicating build information to self hosted build. #define ZIG_CLANG_LIBRARIES "@CLANG_LIBRARIES@" -#define ZIG_CLANG_SYSTEM_LIBRARIES "@CLANG_SYSTEM_LIBRARIES@" #define ZIG_CMAKE_BINARY_DIR "@CMAKE_BINARY_DIR@" #define ZIG_CMAKE_PREFIX_PATH "@ZIG_CMAKE_PREFIX_PATH@" #define ZIG_CMAKE_STATIC_LIBRARY_PREFIX "@CMAKE_STATIC_LIBRARY_PREFIX@" @@ -29,6 +28,5 @@ #define ZIG_LLVM_LIBRARIES "@LLVM_LIBRARIES@" #define ZIG_LLVM_LIB_PATH "@LLVM_LIBDIRS@" #define ZIG_LLVM_LINK_MODE "@LLVM_LINK_MODE@" -#define ZIG_LLVM_SYSTEM_LIBRARIES "@LLVM_SYSTEM_LIBRARIES@" #endif From 7fe62475181489c200d9248b43b983ae41acf985 Mon Sep 17 00:00:00 2001 From: kcbanner Date: Wed, 4 Jan 2023 21:45:00 -0500 Subject: [PATCH 16/17] coff: include version and module_definition_file in the hash --- src/link/Coff/lld.zig | 2 ++ 1 file changed, 2 insertions(+) diff --git a/src/link/Coff/lld.zig b/src/link/Coff/lld.zig index da09505e90..7702062eae 100644 --- a/src/link/Coff/lld.zig +++ b/src/link/Coff/lld.zig @@ -98,6 +98,8 @@ pub fn linkWithLLD(self: *Coff, comp: *Compilation, prog_node: *std.Progress.Nod // strip does not need to go into the linker hash because it is part of the hash namespace man.hash.addOptional(self.base.options.major_subsystem_version); man.hash.addOptional(self.base.options.minor_subsystem_version); + man.hash.addOptional(self.base.options.version); + man.hash.addOptionalBytes(self.base.options.module_definition_file); // We don't actually care whether it's a cache hit or miss; we just need the digest and the lock. _ = try man.hit(); From 25e6187d28813c0f5227095b927374d901c6004b Mon Sep 17 00:00:00 2001 From: kcbanner Date: Thu, 5 Jan 2023 13:41:53 -0500 Subject: [PATCH 17/17] coff: fixup module_definition_file hashing --- src/link/Coff/lld.zig | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/link/Coff/lld.zig b/src/link/Coff/lld.zig index 7702062eae..d705f62f5c 100644 --- a/src/link/Coff/lld.zig +++ b/src/link/Coff/lld.zig @@ -99,7 +99,7 @@ pub fn linkWithLLD(self: *Coff, comp: *Compilation, prog_node: *std.Progress.Nod man.hash.addOptional(self.base.options.major_subsystem_version); man.hash.addOptional(self.base.options.minor_subsystem_version); man.hash.addOptional(self.base.options.version); - man.hash.addOptionalBytes(self.base.options.module_definition_file); + try man.addOptionalFile(self.base.options.module_definition_file); // We don't actually care whether it's a cache hit or miss; we just need the digest and the lock. _ = try man.hit();