diff --git a/BRANCH_TODO b/BRANCH_TODO index 1934cfd02d..56f4661259 100644 --- a/BRANCH_TODO +++ b/BRANCH_TODO @@ -1,3 +1,21 @@ + * `zig builtin` + * `zig translate-c` + * `zig test` + * `zig run` + * `zig init-lib` + * `zig init-exe` + * `zig build` + * `-ftime-report` + * -fstack-report print stack size diagnostics\n" + * -fdump-analysis write analysis.json file with type information\n" + * -femit-docs create a docs/ dir with html documentation\n" + * -fno-emit-docs do not produce docs/ dir with html documentation\n" + * -femit-asm output .s (assembly code)\n" + * -fno-emit-asm (default) do not output .s (assembly code)\n" + * -femit-llvm-ir produce a .ll file with LLVM IR\n" + * -fno-emit-llvm-ir (default) do not produce a .ll file with LLVM IR\n" + * --cache-dir [path] override the local cache directory\n" + * move main.cpp to stage2 * make sure zig cc works - using it as a preprocessor (-E) - try building some software @@ -6,26 +24,24 @@ - stage1 C++ code integration * build & link againstn freestanding libc * add CLI support for a way to pass extra flags to c source files - * implement the workaround for using LLVM to detect native CPU features - * self-host main.cpp * capture lld stdout/stderr better * musl * mingw-w64 * use global zig-cache dir for crt files - * `zig translate-c` * MachO LLD linking * COFF LLD linking * WASM LLD linking * implement proper parsing of LLD stderr/stdout and exposing compile errors * implement proper parsing of clang stderr/stdout and exposing compile errors * implement proper compile errors for failing to build glibc crt files and shared libs - * self-host link.cpp and building libcs (#4313 and #4314). using the `zig cc` command will set a flag indicating a preference for the llvm backend, which will include linking with LLD. At least for now. If zig's self-hosted linker ever gets on par with the likes of ld and lld, we can make it always be used even for zig cc. * improve the stage2 tests to support testing with LLVM extensions enabled * multi-thread building C objects * support cross compiling stage2 with `zig build` * implement emit-h in stage2 * implement -fno-emit-bin * audit the base cache hash + * audit the CLI options for stage2 + * implement serialization/deserialization of incremental compilation metadata * incremental compilation - implement detection of which source files changed * improve the cache hash logic for c objects with respect to extra flags and file parameters diff --git a/CMakeLists.txt b/CMakeLists.txt index ceaecf5552..c8746338d4 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -51,7 +51,6 @@ message("Configuring zig version ${ZIG_VERSION}") set(ZIG_STATIC off CACHE BOOL "Attempt to build a static zig executable (not compatible with glibc)") set(ZIG_STATIC_LLVM off CACHE BOOL "Prefer linking against static LLVM libraries") -set(ZIG_ENABLE_MEM_PROFILE off CACHE BOOL "Activate memory usage instrumentation") set(ZIG_PREFER_CLANG_CPP_DYLIB off CACHE BOOL "Try to link against -lclang-cpp") set(ZIG_WORKAROUND_4799 off CACHE BOOL "workaround for https://github.com/ziglang/zig/issues/4799") set(ZIG_WORKAROUND_POLLY_SO off CACHE STRING "workaround for https://github.com/ziglang/zig/issues/4799") @@ -71,11 +70,6 @@ string(REGEX REPLACE "\\\\" "\\\\\\\\" ZIG_LIBC_INCLUDE_DIR_ESCAPED "${ZIG_LIBC_ option(ZIG_TEST_COVERAGE "Build Zig with test coverage instrumentation" OFF) -# Zig no longer has embedded LLD. This option is kept for package maintainers -# so that they don't have to update their scripts in case we ever re-introduce -# LLD to the tree. This option does nothing. -option(ZIG_FORCE_EXTERNAL_LLD "does nothing" OFF) - set(ZIG_TARGET_TRIPLE "native" CACHE STRING "arch-os-abi to output binaries for") set(ZIG_TARGET_MCPU "baseline" CACHE STRING "-mcpu parameter to output binaries for") set(ZIG_EXECUTABLE "" CACHE STRING "(when cross compiling) path to already-built zig binary") @@ -261,15 +255,11 @@ include_directories("${CMAKE_SOURCE_DIR}/deps/dbg-macro") find_package(Threads) -# CMake doesn't let us create an empty executable, so we hang on to this one separately. -set(ZIG_MAIN_SRC "${CMAKE_SOURCE_DIR}/src/main.cpp") - -# This is our shim which will be replaced by libstage2 written in Zig. -set(ZIG0_SHIM_SRC "${CMAKE_SOURCE_DIR}/src/stage2.cpp") - -if(ZIG_ENABLE_MEM_PROFILE) - set(ZIG_SOURCES_MEM_PROFILE "${CMAKE_SOURCE_DIR}/src/mem_profile.cpp") -endif() +# This is our shim which will be replaced by stage1.zig. +set(ZIG0_SOURCES + "${CMAKE_SOURCE_DIR}/src/zig0.cpp" + "${CMAKE_SOURCE_DIR}/src/stage2.cpp" +) set(ZIG_SOURCES "${CMAKE_SOURCE_DIR}/src/analyze.cpp" @@ -277,37 +267,34 @@ set(ZIG_SOURCES "${CMAKE_SOURCE_DIR}/src/bigfloat.cpp" "${CMAKE_SOURCE_DIR}/src/bigint.cpp" "${CMAKE_SOURCE_DIR}/src/buffer.cpp" - "${CMAKE_SOURCE_DIR}/src/cache_hash.cpp" "${CMAKE_SOURCE_DIR}/src/codegen.cpp" - "${CMAKE_SOURCE_DIR}/src/compiler.cpp" "${CMAKE_SOURCE_DIR}/src/dump_analysis.cpp" "${CMAKE_SOURCE_DIR}/src/errmsg.cpp" "${CMAKE_SOURCE_DIR}/src/error.cpp" - "${CMAKE_SOURCE_DIR}/src/glibc.cpp" "${CMAKE_SOURCE_DIR}/src/heap.cpp" "${CMAKE_SOURCE_DIR}/src/ir.cpp" "${CMAKE_SOURCE_DIR}/src/ir_print.cpp" - "${CMAKE_SOURCE_DIR}/src/link.cpp" "${CMAKE_SOURCE_DIR}/src/mem.cpp" "${CMAKE_SOURCE_DIR}/src/os.cpp" "${CMAKE_SOURCE_DIR}/src/parser.cpp" "${CMAKE_SOURCE_DIR}/src/range_set.cpp" + "${CMAKE_SOURCE_DIR}/src/stage1.cpp" "${CMAKE_SOURCE_DIR}/src/target.cpp" "${CMAKE_SOURCE_DIR}/src/tokenizer.cpp" "${CMAKE_SOURCE_DIR}/src/util.cpp" "${CMAKE_SOURCE_DIR}/src/softfloat_ext.cpp" - "${ZIG_SOURCES_MEM_PROFILE}" ) set(OPTIMIZED_C_SOURCES - "${CMAKE_SOURCE_DIR}/src/blake2b.c" "${CMAKE_SOURCE_DIR}/src/parse_f128.c" ) set(ZIG_CPP_SOURCES + # These are planned to stay even when we are self-hosted. "${CMAKE_SOURCE_DIR}/src/zig_llvm.cpp" "${CMAKE_SOURCE_DIR}/src/zig_clang.cpp" "${CMAKE_SOURCE_DIR}/src/zig_clang_driver.cpp" "${CMAKE_SOURCE_DIR}/src/zig_clang_cc1_main.cpp" "${CMAKE_SOURCE_DIR}/src/zig_clang_cc1as_main.cpp" + # https://github.com/ziglang/zig/issues/6363 "${CMAKE_SOURCE_DIR}/src/windows_sdk.cpp" ) @@ -447,7 +434,7 @@ if(MSVC OR MINGW) target_link_libraries(zigcompiler LINK_PUBLIC version) endif() -add_executable(zig0 "${ZIG_MAIN_SRC}" "${ZIG0_SHIM_SRC}") +add_executable(zig0 ${ZIG0_SOURCES}) set_target_properties(zig0 PROPERTIES COMPILE_FLAGS ${EXE_CFLAGS} LINK_FLAGS ${EXE_LDFLAGS} @@ -455,37 +442,36 @@ set_target_properties(zig0 PROPERTIES target_link_libraries(zig0 zigcompiler) if(MSVC) - set(LIBSTAGE2 "${CMAKE_BINARY_DIR}/zigstage2.lib") + set(ZIG1_OBJECT "${CMAKE_BINARY_DIR}/zig1.obj") else() - set(LIBSTAGE2 "${CMAKE_BINARY_DIR}/libzigstage2.a") + set(ZIG1_OBJECT "${CMAKE_BINARY_DIR}/zig1.o") endif() if("${CMAKE_BUILD_TYPE}" STREQUAL "Debug") - set(LIBSTAGE2_RELEASE_ARG "") + set(ZIG1_RELEASE_ARG "") else() - set(LIBSTAGE2_RELEASE_ARG --release-fast --strip) + set(ZIG1_RELEASE_ARG --release-fast --strip) endif() -set(BUILD_LIBSTAGE2_ARGS "build-lib" - "src-self-hosted/stage2.zig" +set(BUILD_ZIG1_ARGS + "src-self-hosted/stage1.zig" -target "${ZIG_TARGET_TRIPLE}" "-mcpu=${ZIG_TARGET_MCPU}" - --name zigstage2 + --name zig1 --override-lib-dir "${CMAKE_SOURCE_DIR}/lib" - --cache on --output-dir "${CMAKE_BINARY_DIR}" - ${LIBSTAGE2_RELEASE_ARG} - --bundle-compiler-rt - -fPIC + ${ZIG1_RELEASE_ARG} -lc --pkg-begin build_options "${ZIG_CONFIG_ZIG_OUT}" --pkg-end + --pkg-begin compiler_rt "${CMAKE_SOURCE_DIR}/lib/std/special/compiler_rt.zig" + --pkg-end ) if("${ZIG_TARGET_TRIPLE}" STREQUAL "native") - add_custom_target(zig_build_libstage2 ALL - COMMAND zig0 ${BUILD_LIBSTAGE2_ARGS} + add_custom_target(zig_build_zig1 ALL + COMMAND zig0 ${BUILD_ZIG1_ARGS} DEPENDS zig0 - BYPRODUCTS "${LIBSTAGE2}" + BYPRODUCTS "${ZIG1_OBJECT}" WORKING_DIRECTORY "${CMAKE_SOURCE_DIR}" ) set(ZIG_EXECUTABLE "${zig_BINARY_DIR}/zig") @@ -493,26 +479,27 @@ if("${ZIG_TARGET_TRIPLE}" STREQUAL "native") set(ZIG_EXECUTABLE "${ZIG_EXECUTABLE}.exe") endif() else() - add_custom_target(zig_build_libstage2 ALL - COMMAND "${ZIG_EXECUTABLE}" ${BUILD_LIBSTAGE2_ARGS} - BYPRODUCTS "${LIBSTAGE2}" + add_custom_target(zig_build_zig1 ALL + COMMAND "${ZIG_EXECUTABLE}" ${BUILD_ZIG1_ARGS} + BYPRODUCTS "${ZIG1_OBJECT}" WORKING_DIRECTORY "${CMAKE_SOURCE_DIR}" ) endif() -add_executable(zig "${ZIG_MAIN_SRC}") +# cmake won't let us configure an executable without C sources. +add_executable(zig "${CMAKE_SOURCE_DIR}/src/empty.cpp") set_target_properties(zig PROPERTIES COMPILE_FLAGS ${EXE_CFLAGS} LINK_FLAGS ${EXE_LDFLAGS} ) -target_link_libraries(zig zigcompiler "${LIBSTAGE2}") +target_link_libraries(zig zigcompiler "${ZIG1_OBJECT}") if(MSVC) target_link_libraries(zig ntdll.lib) elseif(MINGW) target_link_libraries(zig ntdll) endif() -add_dependencies(zig zig_build_libstage2) +add_dependencies(zig zig_build_zig1) install(TARGETS zig DESTINATION bin) diff --git a/README.md b/README.md index 8031aa790e..242f78d59e 100644 --- a/README.md +++ b/README.md @@ -22,6 +22,8 @@ Note that you can ### Stage 1: Build Zig from C++ Source Code +This step must be repeated when you make changes to any of the C++ source code. + #### Dependencies ##### POSIX @@ -77,6 +79,41 @@ Hopefully this will be fixed upstream with LLVM 10.0.1. See https://github.com/ziglang/zig/wiki/Building-Zig-on-Windows +### Stage 2: Build Self-Hosted Zig from Zig Source Code + +Now we use the stage1 binary: + +``` +zig build --prefix $(pwd)/stage2 -Denable-llvm +``` + +This produces `stage2/bin/zig` which can be used for testing and development. +Once it is feature complete, it will be used to build stage 3 - the final compiler +binary. + +### Stage 3: Rebuild Self-Hosted Zig Using the Self-Hosted Compiler + +*Note: Stage 2 compiler is not yet able to build Stage 3. Building Stage 3 is +not yet supported.* + +Once the self-hosted compiler can build itself, this will be the actual +compiler binary that we will install to the system. Until then, users should +use stage 1. + +#### Debug / Development Build + +``` +stage2/bin/zig build +``` + +This produces `zig-cache/bin/zig`. + +#### Release / Install Build + +``` +stage2/bin/zig build install -Drelease +``` + ## License The ultimate goal of the Zig project is to serve users. As a first-order diff --git a/build.zig b/build.zig index 17ee040e8f..9e5f2425c2 100644 --- a/build.zig +++ b/build.zig @@ -145,6 +145,7 @@ pub fn build(b: *Builder) !void { exe.addBuildOption([]const []const u8, "log_scopes", log_scopes); exe.addBuildOption([]const []const u8, "zir_dumps", zir_dumps); exe.addBuildOption(bool, "enable_tracy", tracy != null); + exe.addBuildOption(bool, "is_stage1", false); if (tracy) |tracy_path| { const client_cpp = fs.path.join( b.allocator, @@ -165,6 +166,7 @@ pub fn build(b: *Builder) !void { const is_wasmtime_enabled = b.option(bool, "enable-wasmtime", "Use Wasmtime to enable and run WASI libstd tests") orelse false; const glibc_multi_dir = b.option([]const u8, "enable-foreign-glibc", "Provide directory with glibc installations to run cross compiled tests that link glibc"); + test_stage2.addBuildOption(bool, "is_stage1", false); test_stage2.addBuildOption(bool, "have_llvm", enable_llvm); test_stage2.addBuildOption(bool, "enable_qemu", is_qemu_enabled); test_stage2.addBuildOption(bool, "enable_wine", is_wine_enabled); diff --git a/src-self-hosted/Compilation.zig b/src-self-hosted/Compilation.zig index 8e18e7fffc..05f76f08f3 100644 --- a/src-self-hosted/Compilation.zig +++ b/src-self-hosted/Compilation.zig @@ -244,6 +244,7 @@ pub const InitOptions = struct { /// `null` means to not emit a C header file. emit_h: ?EmitLoc = null, link_mode: ?std.builtin.LinkMode = null, + dll_export_fns: ?bool = false, object_format: ?std.builtin.ObjectFormat = null, optimize_mode: std.builtin.Mode = .Debug, keep_source_files_loaded: bool = false, @@ -340,9 +341,13 @@ pub fn create(gpa: *Allocator, options: InitOptions) !*Compilation { return error.MachineCodeModelNotSupported; } + const is_dyn_lib = switch (options.output_mode) { + .Obj, .Exe => false, + .Lib => (options.link_mode orelse .Static) == .Dynamic, + }; const is_exe_or_dyn_lib = switch (options.output_mode) { .Obj => false, - .Lib => (options.link_mode orelse .Static) == .Dynamic, + .Lib => is_dyn_lib, .Exe => true, }; const must_dynamic_link = dl: { @@ -365,6 +370,8 @@ pub fn create(gpa: *Allocator, options: InitOptions) !*Compilation { break :blk lm; } else default_link_mode; + const dll_export_fns = if (options.dll_export_fns) |explicit| explicit else is_dyn_lib; + const libc_dirs = try detectLibCIncludeDirs( arena, options.zig_lib_directory.path.?, @@ -379,7 +386,12 @@ pub fn create(gpa: *Allocator, options: InitOptions) !*Compilation { break :b true; break :b link_mode == .Dynamic; }; - const pic = options.want_pic orelse must_pic; + const pic = if (options.want_pic) |explicit| pic: { + if (!explicit and must_pic) { + return error.TargetRequiresPIC; + } + break :pic explicit; + } else must_pic; if (options.emit_h != null) fatal("-femit-h not supported yet", .{}); // TODO @@ -464,6 +476,7 @@ pub fn create(gpa: *Allocator, options: InitOptions) !*Compilation { hash.add(valgrind); hash.add(single_threaded); hash.add(options.target.os.getVersionRange()); + hash.add(dll_export_fns); const digest = hash.final(); const artifact_sub_dir = try std.fs.path.join(arena, &[_][]const u8{ "o", &digest }); @@ -601,6 +614,7 @@ pub fn create(gpa: *Allocator, options: InitOptions) !*Compilation { .single_threaded = single_threaded, .debug_link = options.debug_link, .machine_code_model = options.machine_code_model, + .dll_export_fns = dll_export_fns, }); errdefer bin_file.destroy(); diff --git a/src-self-hosted/libcxx.zig b/src-self-hosted/libcxx.zig new file mode 100644 index 0000000000..c7dc24ae9f --- /dev/null +++ b/src-self-hosted/libcxx.zig @@ -0,0 +1,66 @@ +//! TODO build libcxx and libcxxabi from source + +pub const libcxxabi_files = [_][]const u8{ + "src/abort_message.cpp", + "src/cxa_aux_runtime.cpp", + "src/cxa_default_handlers.cpp", + "src/cxa_demangle.cpp", + "src/cxa_exception.cpp", + "src/cxa_exception_storage.cpp", + "src/cxa_guard.cpp", + "src/cxa_handlers.cpp", + "src/cxa_noexception.cpp", + "src/cxa_personality.cpp", + "src/cxa_thread_atexit.cpp", + "src/cxa_unexpected.cpp", + "src/cxa_vector.cpp", + "src/cxa_virtual.cpp", + "src/fallback_malloc.cpp", + "src/private_typeinfo.cpp", + "src/stdlib_exception.cpp", + "src/stdlib_stdexcept.cpp", + "src/stdlib_typeinfo.cpp", +}; + +pub const libcxx_files = [_][]const u8{ + "src/algorithm.cpp", + "src/any.cpp", + "src/bind.cpp", + "src/charconv.cpp", + "src/chrono.cpp", + "src/condition_variable.cpp", + "src/condition_variable_destructor.cpp", + "src/debug.cpp", + "src/exception.cpp", + "src/experimental/memory_resource.cpp", + "src/filesystem/directory_iterator.cpp", + "src/filesystem/operations.cpp", + "src/functional.cpp", + "src/future.cpp", + "src/hash.cpp", + "src/ios.cpp", + "src/iostream.cpp", + "src/locale.cpp", + "src/memory.cpp", + "src/mutex.cpp", + "src/mutex_destructor.cpp", + "src/new.cpp", + "src/optional.cpp", + "src/random.cpp", + "src/regex.cpp", + "src/shared_mutex.cpp", + "src/stdexcept.cpp", + "src/string.cpp", + "src/strstream.cpp", + "src/support/solaris/xlocale.cpp", + "src/support/win32/locale_win32.cpp", + "src/support/win32/support.cpp", + "src/support/win32/thread_win32.cpp", + "src/system_error.cpp", + "src/thread.cpp", + "src/typeinfo.cpp", + "src/utility.cpp", + "src/valarray.cpp", + "src/variant.cpp", + "src/vector.cpp", +}; diff --git a/src-self-hosted/link.zig b/src-self-hosted/link.zig index cdeb2b5e5c..069a90872e 100644 --- a/src-self-hosted/link.zig +++ b/src-self-hosted/link.zig @@ -62,6 +62,7 @@ pub const Options = struct { stack_check: bool, single_threaded: bool, debug_link: bool = false, + dll_export_fns: bool, gc_sections: ?bool = null, allow_shlib_undefined: ?bool = null, linker_script: ?[]const u8 = null, diff --git a/src-self-hosted/main.zig b/src-self-hosted/main.zig index c9b872cc7e..db68c867b2 100644 --- a/src-self-hosted/main.zig +++ b/src-self-hosted/main.zig @@ -92,7 +92,7 @@ pub fn log( var general_purpose_allocator = std.heap.GeneralPurposeAllocator(.{}){}; -pub fn main() !void { +pub fn main() anyerror!void { const gpa = if (std.builtin.link_libc) std.heap.c_allocator else &general_purpose_allocator.allocator; defer if (!std.builtin.link_libc) { _ = general_purpose_allocator.deinit(); @@ -102,7 +102,10 @@ pub fn main() !void { const arena = &arena_instance.allocator; const args = try process.argsAlloc(arena); + return mainArgs(gpa, arena, args); +} +pub fn mainArgs(gpa: *Allocator, arena: *Allocator, args: []const []const u8) !void { if (args.len <= 1) { std.log.info("{}", .{usage}); fatal("expected command argument", .{}); @@ -131,7 +134,7 @@ pub fn main() !void { } else if (mem.eql(u8, cmd, "libc")) { return cmdLibC(gpa, cmd_args); } else if (mem.eql(u8, cmd, "targets")) { - const info = try std.zig.system.NativeTargetInfo.detect(arena, .{}); + const info = try detectNativeTargetInfo(arena, .{}); const stdout = io.getStdOut().outStream(); return @import("print_targets.zig").cmdTargets(arena, cmd_args, stdout, info.target); } else if (mem.eql(u8, cmd, "version")) { @@ -183,7 +186,7 @@ const usage_build_generic = \\ -mcmodel=[default|tiny| Limit range of code and data virtual addresses \\ small|kernel| \\ medium|large] - \\ --name [name] Override output name + \\ --name [name] Override root name (not a file path) \\ --mode [mode] Set the build mode \\ Debug (default) optimizations off, safety on \\ ReleaseFast Optimizations on, safety off @@ -197,7 +200,9 @@ const usage_build_generic = \\ -fno-sanitize-c Disable C undefined behavior detection in safe builds \\ -fvalgrind Include valgrind client requests in release builds \\ -fno-valgrind Omit valgrind client requests in debug builds - \\ --strip Exclude debug symbols + \\ -fdll-export-fns Mark exported functions as DLL exports (Windows) + \\ -fno-dll-export-fns Force-disable marking exported functions as DLL exports + \\ --strip Omit debug symbols \\ --single-threaded Code assumes it is only used single-threaded \\ -ofmt=[mode] Override target object format \\ elf Executable and Linking Format @@ -262,6 +267,7 @@ pub fn buildOutputType( var build_mode: std.builtin.Mode = .Debug; var provided_name: ?[]const u8 = null; var link_mode: ?std.builtin.LinkMode = null; + var dll_export_fns: ?bool = null; var root_src_file: ?[]const u8 = null; var version: std.builtin.Version = .{ .major = 0, .minor = 0, .patch = 0 }; var have_version = false; @@ -521,6 +527,10 @@ pub fn buildOutputType( link_mode = .Dynamic; } else if (mem.eql(u8, arg, "-static")) { link_mode = .Static; + } else if (mem.eql(u8, arg, "-fdll-export-fns")) { + dll_export_fns = true; + } else if (mem.eql(u8, arg, "-fno-dll-export-fns")) { + dll_export_fns = false; } else if (mem.eql(u8, arg, "--strip")) { strip = true; } else if (mem.eql(u8, arg, "--single-threaded")) { @@ -902,14 +912,7 @@ pub fn buildOutputType( else => |e| return e, }; - const target_info = try std.zig.system.NativeTargetInfo.detect(gpa, cross_target); - if (target_info.cpu_detection_unimplemented) { - // TODO We want to just use detected_info.target but implementing - // CPU model & feature detection is todo so here we rely on LLVM. - // TODO The workaround to use LLVM to detect features needs to be used for - // `zig targets` as well. - fatal("CPU features detection is not yet available for this system without LLVM extensions", .{}); - } + const target_info = try detectNativeTargetInfo(gpa, cross_target); if (target_info.target.os.tag != .freestanding) { if (ensure_libc_on_non_freestanding) @@ -1116,6 +1119,7 @@ pub fn buildOutputType( .emit_bin = emit_bin_loc, .emit_h = emit_h_loc, .link_mode = link_mode, + .dll_export_fns = dll_export_fns, .object_format = object_format, .optimize_mode = build_mode, .keep_source_files_loaded = zir_out_path != null, @@ -1974,3 +1978,87 @@ fn gimmeMoreOfThoseSweetSweetFileDescriptors() void { test "fds" { gimmeMoreOfThoseSweetSweetFileDescriptors(); } + +fn detectNativeCpuWithLLVM( + arch: std.Target.Cpu.Arch, + llvm_cpu_name_z: ?[*:0]const u8, + llvm_cpu_features_opt: ?[*:0]const u8, +) !std.Target.Cpu { + var result = std.Target.Cpu.baseline(arch); + + if (llvm_cpu_name_z) |cpu_name_z| { + const llvm_cpu_name = mem.spanZ(cpu_name_z); + + for (arch.allCpuModels()) |model| { + const this_llvm_name = model.llvm_name orelse continue; + if (mem.eql(u8, this_llvm_name, llvm_cpu_name)) { + // Here we use the non-dependencies-populated set, + // so that subtracting features later in this function + // affect the prepopulated set. + result = std.Target.Cpu{ + .arch = arch, + .model = model, + .features = model.features, + }; + break; + } + } + } + + const all_features = arch.allFeaturesList(); + + if (llvm_cpu_features_opt) |llvm_cpu_features| { + var it = mem.tokenize(mem.spanZ(llvm_cpu_features), ","); + while (it.next()) |decorated_llvm_feat| { + var op: enum { + add, + sub, + } = undefined; + var llvm_feat: []const u8 = undefined; + if (mem.startsWith(u8, decorated_llvm_feat, "+")) { + op = .add; + llvm_feat = decorated_llvm_feat[1..]; + } else if (mem.startsWith(u8, decorated_llvm_feat, "-")) { + op = .sub; + llvm_feat = decorated_llvm_feat[1..]; + } else { + return error.InvalidLlvmCpuFeaturesFormat; + } + for (all_features) |feature, index_usize| { + const this_llvm_name = feature.llvm_name orelse continue; + if (mem.eql(u8, llvm_feat, this_llvm_name)) { + const index = @intCast(std.Target.Cpu.Feature.Set.Index, index_usize); + switch (op) { + .add => result.features.addFeature(index), + .sub => result.features.removeFeature(index), + } + break; + } + } + } + } + + result.features.populateDependencies(all_features); + return result; +} + +fn detectNativeTargetInfo(gpa: *Allocator, cross_target: std.zig.CrossTarget) !std.zig.system.NativeTargetInfo { + var info = try std.zig.system.NativeTargetInfo.detect(gpa, cross_target); + if (info.cpu_detection_unimplemented) { + const arch = std.Target.current.cpu.arch; + + // We want to just use detected_info.target but implementing + // CPU model & feature detection is todo so here we rely on LLVM. + // https://github.com/ziglang/zig/issues/4591 + if (!build_options.have_llvm) + fatal("CPU features detection is not yet available for {} without LLVM extensions", .{@tagName(arch)}); + + const llvm = @import("llvm.zig"); + const llvm_cpu_name = llvm.GetHostCPUName(); + const llvm_cpu_features = llvm.GetNativeFeatures(); + info.target.cpu = try detectNativeCpuWithLLVM(arch, llvm_cpu_name, llvm_cpu_features); + cross_target.updateCpuFeatures(&info.target.cpu.features); + info.target.cpu.arch = cross_target.getCpuArch(); + } + return info; +} diff --git a/src-self-hosted/musl.zig b/src-self-hosted/musl.zig new file mode 100644 index 0000000000..88536b90fd --- /dev/null +++ b/src-self-hosted/musl.zig @@ -0,0 +1,1843 @@ +//! TODO build musl libc from source + +pub const src_files = [_][]const u8{ + "musl/src/aio/aio.c", + "musl/src/aio/aio_suspend.c", + "musl/src/aio/lio_listio.c", + "musl/src/complex/__cexp.c", + "musl/src/complex/__cexpf.c", + "musl/src/complex/cabs.c", + "musl/src/complex/cabsf.c", + "musl/src/complex/cabsl.c", + "musl/src/complex/cacos.c", + "musl/src/complex/cacosf.c", + "musl/src/complex/cacosh.c", + "musl/src/complex/cacoshf.c", + "musl/src/complex/cacoshl.c", + "musl/src/complex/cacosl.c", + "musl/src/complex/carg.c", + "musl/src/complex/cargf.c", + "musl/src/complex/cargl.c", + "musl/src/complex/casin.c", + "musl/src/complex/casinf.c", + "musl/src/complex/casinh.c", + "musl/src/complex/casinhf.c", + "musl/src/complex/casinhl.c", + "musl/src/complex/casinl.c", + "musl/src/complex/catan.c", + "musl/src/complex/catanf.c", + "musl/src/complex/catanh.c", + "musl/src/complex/catanhf.c", + "musl/src/complex/catanhl.c", + "musl/src/complex/catanl.c", + "musl/src/complex/ccos.c", + "musl/src/complex/ccosf.c", + "musl/src/complex/ccosh.c", + "musl/src/complex/ccoshf.c", + "musl/src/complex/ccoshl.c", + "musl/src/complex/ccosl.c", + "musl/src/complex/cexp.c", + "musl/src/complex/cexpf.c", + "musl/src/complex/cexpl.c", + "musl/src/complex/cimag.c", + "musl/src/complex/cimagf.c", + "musl/src/complex/cimagl.c", + "musl/src/complex/clog.c", + "musl/src/complex/clogf.c", + "musl/src/complex/clogl.c", + "musl/src/complex/conj.c", + "musl/src/complex/conjf.c", + "musl/src/complex/conjl.c", + "musl/src/complex/cpow.c", + "musl/src/complex/cpowf.c", + "musl/src/complex/cpowl.c", + "musl/src/complex/cproj.c", + "musl/src/complex/cprojf.c", + "musl/src/complex/cprojl.c", + "musl/src/complex/creal.c", + "musl/src/complex/crealf.c", + "musl/src/complex/creall.c", + "musl/src/complex/csin.c", + "musl/src/complex/csinf.c", + "musl/src/complex/csinh.c", + "musl/src/complex/csinhf.c", + "musl/src/complex/csinhl.c", + "musl/src/complex/csinl.c", + "musl/src/complex/csqrt.c", + "musl/src/complex/csqrtf.c", + "musl/src/complex/csqrtl.c", + "musl/src/complex/ctan.c", + "musl/src/complex/ctanf.c", + "musl/src/complex/ctanh.c", + "musl/src/complex/ctanhf.c", + "musl/src/complex/ctanhl.c", + "musl/src/complex/ctanl.c", + "musl/src/conf/confstr.c", + "musl/src/conf/fpathconf.c", + "musl/src/conf/legacy.c", + "musl/src/conf/pathconf.c", + "musl/src/conf/sysconf.c", + "musl/src/crypt/crypt.c", + "musl/src/crypt/crypt_blowfish.c", + "musl/src/crypt/crypt_des.c", + "musl/src/crypt/crypt_md5.c", + "musl/src/crypt/crypt_r.c", + "musl/src/crypt/crypt_sha256.c", + "musl/src/crypt/crypt_sha512.c", + "musl/src/crypt/encrypt.c", + "musl/src/ctype/__ctype_b_loc.c", + "musl/src/ctype/__ctype_get_mb_cur_max.c", + "musl/src/ctype/__ctype_tolower_loc.c", + "musl/src/ctype/__ctype_toupper_loc.c", + "musl/src/ctype/isalnum.c", + "musl/src/ctype/isalpha.c", + "musl/src/ctype/isascii.c", + "musl/src/ctype/isblank.c", + "musl/src/ctype/iscntrl.c", + "musl/src/ctype/isdigit.c", + "musl/src/ctype/isgraph.c", + "musl/src/ctype/islower.c", + "musl/src/ctype/isprint.c", + "musl/src/ctype/ispunct.c", + "musl/src/ctype/isspace.c", + "musl/src/ctype/isupper.c", + "musl/src/ctype/iswalnum.c", + "musl/src/ctype/iswalpha.c", + "musl/src/ctype/iswblank.c", + "musl/src/ctype/iswcntrl.c", + "musl/src/ctype/iswctype.c", + "musl/src/ctype/iswdigit.c", + "musl/src/ctype/iswgraph.c", + "musl/src/ctype/iswlower.c", + "musl/src/ctype/iswprint.c", + "musl/src/ctype/iswpunct.c", + "musl/src/ctype/iswspace.c", + "musl/src/ctype/iswupper.c", + "musl/src/ctype/iswxdigit.c", + "musl/src/ctype/isxdigit.c", + "musl/src/ctype/toascii.c", + "musl/src/ctype/tolower.c", + "musl/src/ctype/toupper.c", + "musl/src/ctype/towctrans.c", + "musl/src/ctype/wcswidth.c", + "musl/src/ctype/wctrans.c", + "musl/src/ctype/wcwidth.c", + "musl/src/dirent/alphasort.c", + "musl/src/dirent/closedir.c", + "musl/src/dirent/dirfd.c", + "musl/src/dirent/fdopendir.c", + "musl/src/dirent/opendir.c", + "musl/src/dirent/readdir.c", + "musl/src/dirent/readdir_r.c", + "musl/src/dirent/rewinddir.c", + "musl/src/dirent/scandir.c", + "musl/src/dirent/seekdir.c", + "musl/src/dirent/telldir.c", + "musl/src/dirent/versionsort.c", + "musl/src/env/__environ.c", + "musl/src/env/__init_tls.c", + "musl/src/env/__libc_start_main.c", + "musl/src/env/__reset_tls.c", + "musl/src/env/__stack_chk_fail.c", + "musl/src/env/clearenv.c", + "musl/src/env/getenv.c", + "musl/src/env/putenv.c", + "musl/src/env/secure_getenv.c", + "musl/src/env/setenv.c", + "musl/src/env/unsetenv.c", + "musl/src/errno/__errno_location.c", + "musl/src/errno/strerror.c", + "musl/src/exit/_Exit.c", + "musl/src/exit/abort.c", + "musl/src/exit/arm/__aeabi_atexit.c", + "musl/src/exit/assert.c", + "musl/src/exit/at_quick_exit.c", + "musl/src/exit/atexit.c", + "musl/src/exit/exit.c", + "musl/src/exit/quick_exit.c", + "musl/src/fcntl/creat.c", + "musl/src/fcntl/fcntl.c", + "musl/src/fcntl/open.c", + "musl/src/fcntl/openat.c", + "musl/src/fcntl/posix_fadvise.c", + "musl/src/fcntl/posix_fallocate.c", + "musl/src/fenv/__flt_rounds.c", + "musl/src/fenv/aarch64/fenv.s", + "musl/src/fenv/arm/fenv-hf.S", + "musl/src/fenv/arm/fenv.c", + "musl/src/fenv/fegetexceptflag.c", + "musl/src/fenv/feholdexcept.c", + "musl/src/fenv/fenv.c", + "musl/src/fenv/fesetexceptflag.c", + "musl/src/fenv/fesetround.c", + "musl/src/fenv/feupdateenv.c", + "musl/src/fenv/i386/fenv.s", + "musl/src/fenv/m68k/fenv.c", + "musl/src/fenv/mips/fenv-sf.c", + "musl/src/fenv/mips/fenv.S", + "musl/src/fenv/mips64/fenv-sf.c", + "musl/src/fenv/mips64/fenv.S", + "musl/src/fenv/mipsn32/fenv-sf.c", + "musl/src/fenv/mipsn32/fenv.S", + "musl/src/fenv/powerpc/fenv-sf.c", + "musl/src/fenv/powerpc/fenv.S", + "musl/src/fenv/powerpc64/fenv.c", + "musl/src/fenv/riscv64/fenv-sf.c", + "musl/src/fenv/riscv64/fenv.S", + "musl/src/fenv/s390x/fenv.c", + "musl/src/fenv/sh/fenv-nofpu.c", + "musl/src/fenv/sh/fenv.S", + "musl/src/fenv/x32/fenv.s", + "musl/src/fenv/x86_64/fenv.s", + "musl/src/internal/defsysinfo.c", + "musl/src/internal/floatscan.c", + "musl/src/internal/i386/defsysinfo.s", + "musl/src/internal/intscan.c", + "musl/src/internal/libc.c", + "musl/src/internal/procfdname.c", + "musl/src/internal/sh/__shcall.c", + "musl/src/internal/shgetc.c", + "musl/src/internal/syscall_ret.c", + "musl/src/internal/vdso.c", + "musl/src/internal/version.c", + "musl/src/ipc/ftok.c", + "musl/src/ipc/msgctl.c", + "musl/src/ipc/msgget.c", + "musl/src/ipc/msgrcv.c", + "musl/src/ipc/msgsnd.c", + "musl/src/ipc/semctl.c", + "musl/src/ipc/semget.c", + "musl/src/ipc/semop.c", + "musl/src/ipc/semtimedop.c", + "musl/src/ipc/shmat.c", + "musl/src/ipc/shmctl.c", + "musl/src/ipc/shmdt.c", + "musl/src/ipc/shmget.c", + "musl/src/ldso/__dlsym.c", + "musl/src/ldso/aarch64/dlsym.s", + "musl/src/ldso/aarch64/tlsdesc.s", + "musl/src/ldso/arm/dlsym.s", + "musl/src/ldso/arm/dlsym_time64.S", + "musl/src/ldso/arm/find_exidx.c", + "musl/src/ldso/arm/tlsdesc.S", + "musl/src/ldso/dl_iterate_phdr.c", + "musl/src/ldso/dladdr.c", + "musl/src/ldso/dlclose.c", + "musl/src/ldso/dlerror.c", + "musl/src/ldso/dlinfo.c", + "musl/src/ldso/dlopen.c", + "musl/src/ldso/dlsym.c", + "musl/src/ldso/i386/dlsym.s", + "musl/src/ldso/i386/dlsym_time64.S", + "musl/src/ldso/i386/tlsdesc.s", + "musl/src/ldso/m68k/dlsym.s", + "musl/src/ldso/m68k/dlsym_time64.S", + "musl/src/ldso/microblaze/dlsym.s", + "musl/src/ldso/microblaze/dlsym_time64.S", + "musl/src/ldso/mips/dlsym.s", + "musl/src/ldso/mips/dlsym_time64.S", + "musl/src/ldso/mips64/dlsym.s", + "musl/src/ldso/mipsn32/dlsym.s", + "musl/src/ldso/mipsn32/dlsym_time64.S", + "musl/src/ldso/or1k/dlsym.s", + "musl/src/ldso/or1k/dlsym_time64.S", + "musl/src/ldso/powerpc/dlsym.s", + "musl/src/ldso/powerpc/dlsym_time64.S", + "musl/src/ldso/powerpc64/dlsym.s", + "musl/src/ldso/riscv64/dlsym.s", + "musl/src/ldso/s390x/dlsym.s", + "musl/src/ldso/sh/dlsym.s", + "musl/src/ldso/sh/dlsym_time64.S", + "musl/src/ldso/tlsdesc.c", + "musl/src/ldso/x32/dlsym.s", + "musl/src/ldso/x86_64/dlsym.s", + "musl/src/ldso/x86_64/tlsdesc.s", + "musl/src/legacy/cuserid.c", + "musl/src/legacy/daemon.c", + "musl/src/legacy/err.c", + "musl/src/legacy/euidaccess.c", + "musl/src/legacy/ftw.c", + "musl/src/legacy/futimes.c", + "musl/src/legacy/getdtablesize.c", + "musl/src/legacy/getloadavg.c", + "musl/src/legacy/getpagesize.c", + "musl/src/legacy/getpass.c", + "musl/src/legacy/getusershell.c", + "musl/src/legacy/isastream.c", + "musl/src/legacy/lutimes.c", + "musl/src/legacy/ulimit.c", + "musl/src/legacy/utmpx.c", + "musl/src/legacy/valloc.c", + "musl/src/linux/adjtime.c", + "musl/src/linux/adjtimex.c", + "musl/src/linux/arch_prctl.c", + "musl/src/linux/brk.c", + "musl/src/linux/cache.c", + "musl/src/linux/cap.c", + "musl/src/linux/chroot.c", + "musl/src/linux/clock_adjtime.c", + "musl/src/linux/clone.c", + "musl/src/linux/copy_file_range.c", + "musl/src/linux/epoll.c", + "musl/src/linux/eventfd.c", + "musl/src/linux/fallocate.c", + "musl/src/linux/fanotify.c", + "musl/src/linux/flock.c", + "musl/src/linux/getdents.c", + "musl/src/linux/getrandom.c", + "musl/src/linux/inotify.c", + "musl/src/linux/ioperm.c", + "musl/src/linux/iopl.c", + "musl/src/linux/klogctl.c", + "musl/src/linux/membarrier.c", + "musl/src/linux/memfd_create.c", + "musl/src/linux/mlock2.c", + "musl/src/linux/module.c", + "musl/src/linux/mount.c", + "musl/src/linux/name_to_handle_at.c", + "musl/src/linux/open_by_handle_at.c", + "musl/src/linux/personality.c", + "musl/src/linux/pivot_root.c", + "musl/src/linux/ppoll.c", + "musl/src/linux/prctl.c", + "musl/src/linux/prlimit.c", + "musl/src/linux/process_vm.c", + "musl/src/linux/ptrace.c", + "musl/src/linux/quotactl.c", + "musl/src/linux/readahead.c", + "musl/src/linux/reboot.c", + "musl/src/linux/remap_file_pages.c", + "musl/src/linux/sbrk.c", + "musl/src/linux/sendfile.c", + "musl/src/linux/setfsgid.c", + "musl/src/linux/setfsuid.c", + "musl/src/linux/setgroups.c", + "musl/src/linux/sethostname.c", + "musl/src/linux/setns.c", + "musl/src/linux/settimeofday.c", + "musl/src/linux/signalfd.c", + "musl/src/linux/splice.c", + "musl/src/linux/stime.c", + "musl/src/linux/swap.c", + "musl/src/linux/sync_file_range.c", + "musl/src/linux/syncfs.c", + "musl/src/linux/sysinfo.c", + "musl/src/linux/tee.c", + "musl/src/linux/timerfd.c", + "musl/src/linux/unshare.c", + "musl/src/linux/utimes.c", + "musl/src/linux/vhangup.c", + "musl/src/linux/vmsplice.c", + "musl/src/linux/wait3.c", + "musl/src/linux/wait4.c", + "musl/src/linux/x32/sysinfo.c", + "musl/src/linux/xattr.c", + "musl/src/locale/__lctrans.c", + "musl/src/locale/__mo_lookup.c", + "musl/src/locale/bind_textdomain_codeset.c", + "musl/src/locale/c_locale.c", + "musl/src/locale/catclose.c", + "musl/src/locale/catgets.c", + "musl/src/locale/catopen.c", + "musl/src/locale/dcngettext.c", + "musl/src/locale/duplocale.c", + "musl/src/locale/freelocale.c", + "musl/src/locale/iconv.c", + "musl/src/locale/iconv_close.c", + "musl/src/locale/langinfo.c", + "musl/src/locale/locale_map.c", + "musl/src/locale/localeconv.c", + "musl/src/locale/newlocale.c", + "musl/src/locale/pleval.c", + "musl/src/locale/setlocale.c", + "musl/src/locale/strcoll.c", + "musl/src/locale/strfmon.c", + "musl/src/locale/strxfrm.c", + "musl/src/locale/textdomain.c", + "musl/src/locale/uselocale.c", + "musl/src/locale/wcscoll.c", + "musl/src/locale/wcsxfrm.c", + "musl/src/malloc/aligned_alloc.c", + "musl/src/malloc/expand_heap.c", + "musl/src/malloc/lite_malloc.c", + "musl/src/malloc/malloc.c", + "musl/src/malloc/malloc_usable_size.c", + "musl/src/malloc/memalign.c", + "musl/src/malloc/posix_memalign.c", + "musl/src/math/__cos.c", + "musl/src/math/__cosdf.c", + "musl/src/math/__cosl.c", + "musl/src/math/__expo2.c", + "musl/src/math/__expo2f.c", + "musl/src/math/__fpclassify.c", + "musl/src/math/__fpclassifyf.c", + "musl/src/math/__fpclassifyl.c", + "musl/src/math/__invtrigl.c", + "musl/src/math/__math_divzero.c", + "musl/src/math/__math_divzerof.c", + "musl/src/math/__math_invalid.c", + "musl/src/math/__math_invalidf.c", + "musl/src/math/__math_oflow.c", + "musl/src/math/__math_oflowf.c", + "musl/src/math/__math_uflow.c", + "musl/src/math/__math_uflowf.c", + "musl/src/math/__math_xflow.c", + "musl/src/math/__math_xflowf.c", + "musl/src/math/__polevll.c", + "musl/src/math/__rem_pio2.c", + "musl/src/math/__rem_pio2_large.c", + "musl/src/math/__rem_pio2f.c", + "musl/src/math/__rem_pio2l.c", + "musl/src/math/__signbit.c", + "musl/src/math/__signbitf.c", + "musl/src/math/__signbitl.c", + "musl/src/math/__sin.c", + "musl/src/math/__sindf.c", + "musl/src/math/__sinl.c", + "musl/src/math/__tan.c", + "musl/src/math/__tandf.c", + "musl/src/math/__tanl.c", + "musl/src/math/aarch64/ceil.c", + "musl/src/math/aarch64/ceilf.c", + "musl/src/math/aarch64/fabs.c", + "musl/src/math/aarch64/fabsf.c", + "musl/src/math/aarch64/floor.c", + "musl/src/math/aarch64/floorf.c", + "musl/src/math/aarch64/fma.c", + "musl/src/math/aarch64/fmaf.c", + "musl/src/math/aarch64/fmax.c", + "musl/src/math/aarch64/fmaxf.c", + "musl/src/math/aarch64/fmin.c", + "musl/src/math/aarch64/fminf.c", + "musl/src/math/aarch64/llrint.c", + "musl/src/math/aarch64/llrintf.c", + "musl/src/math/aarch64/llround.c", + "musl/src/math/aarch64/llroundf.c", + "musl/src/math/aarch64/lrint.c", + "musl/src/math/aarch64/lrintf.c", + "musl/src/math/aarch64/lround.c", + "musl/src/math/aarch64/lroundf.c", + "musl/src/math/aarch64/nearbyint.c", + "musl/src/math/aarch64/nearbyintf.c", + "musl/src/math/aarch64/rint.c", + "musl/src/math/aarch64/rintf.c", + "musl/src/math/aarch64/round.c", + "musl/src/math/aarch64/roundf.c", + "musl/src/math/aarch64/sqrt.c", + "musl/src/math/aarch64/sqrtf.c", + "musl/src/math/aarch64/trunc.c", + "musl/src/math/aarch64/truncf.c", + "musl/src/math/acos.c", + "musl/src/math/acosf.c", + "musl/src/math/acosh.c", + "musl/src/math/acoshf.c", + "musl/src/math/acoshl.c", + "musl/src/math/acosl.c", + "musl/src/math/arm/fabs.c", + "musl/src/math/arm/fabsf.c", + "musl/src/math/arm/fma.c", + "musl/src/math/arm/fmaf.c", + "musl/src/math/arm/sqrt.c", + "musl/src/math/arm/sqrtf.c", + "musl/src/math/asin.c", + "musl/src/math/asinf.c", + "musl/src/math/asinh.c", + "musl/src/math/asinhf.c", + "musl/src/math/asinhl.c", + "musl/src/math/asinl.c", + "musl/src/math/atan.c", + "musl/src/math/atan2.c", + "musl/src/math/atan2f.c", + "musl/src/math/atan2l.c", + "musl/src/math/atanf.c", + "musl/src/math/atanh.c", + "musl/src/math/atanhf.c", + "musl/src/math/atanhl.c", + "musl/src/math/atanl.c", + "musl/src/math/cbrt.c", + "musl/src/math/cbrtf.c", + "musl/src/math/cbrtl.c", + "musl/src/math/ceil.c", + "musl/src/math/ceilf.c", + "musl/src/math/ceill.c", + "musl/src/math/copysign.c", + "musl/src/math/copysignf.c", + "musl/src/math/copysignl.c", + "musl/src/math/cos.c", + "musl/src/math/cosf.c", + "musl/src/math/cosh.c", + "musl/src/math/coshf.c", + "musl/src/math/coshl.c", + "musl/src/math/cosl.c", + "musl/src/math/erf.c", + "musl/src/math/erff.c", + "musl/src/math/erfl.c", + "musl/src/math/exp.c", + "musl/src/math/exp10.c", + "musl/src/math/exp10f.c", + "musl/src/math/exp10l.c", + "musl/src/math/exp2.c", + "musl/src/math/exp2f.c", + "musl/src/math/exp2f_data.c", + "musl/src/math/exp2l.c", + "musl/src/math/exp_data.c", + "musl/src/math/expf.c", + "musl/src/math/expl.c", + "musl/src/math/expm1.c", + "musl/src/math/expm1f.c", + "musl/src/math/expm1l.c", + "musl/src/math/fabs.c", + "musl/src/math/fabsf.c", + "musl/src/math/fabsl.c", + "musl/src/math/fdim.c", + "musl/src/math/fdimf.c", + "musl/src/math/fdiml.c", + "musl/src/math/finite.c", + "musl/src/math/finitef.c", + "musl/src/math/floor.c", + "musl/src/math/floorf.c", + "musl/src/math/floorl.c", + "musl/src/math/fma.c", + "musl/src/math/fmaf.c", + "musl/src/math/fmal.c", + "musl/src/math/fmax.c", + "musl/src/math/fmaxf.c", + "musl/src/math/fmaxl.c", + "musl/src/math/fmin.c", + "musl/src/math/fminf.c", + "musl/src/math/fminl.c", + "musl/src/math/fmod.c", + "musl/src/math/fmodf.c", + "musl/src/math/fmodl.c", + "musl/src/math/frexp.c", + "musl/src/math/frexpf.c", + "musl/src/math/frexpl.c", + "musl/src/math/hypot.c", + "musl/src/math/hypotf.c", + "musl/src/math/hypotl.c", + "musl/src/math/i386/__invtrigl.s", + "musl/src/math/i386/acos.s", + "musl/src/math/i386/acosf.s", + "musl/src/math/i386/acosl.s", + "musl/src/math/i386/asin.s", + "musl/src/math/i386/asinf.s", + "musl/src/math/i386/asinl.s", + "musl/src/math/i386/atan.s", + "musl/src/math/i386/atan2.s", + "musl/src/math/i386/atan2f.s", + "musl/src/math/i386/atan2l.s", + "musl/src/math/i386/atanf.s", + "musl/src/math/i386/atanl.s", + "musl/src/math/i386/ceil.s", + "musl/src/math/i386/ceilf.s", + "musl/src/math/i386/ceill.s", + "musl/src/math/i386/exp2l.s", + "musl/src/math/i386/exp_ld.s", + "musl/src/math/i386/expl.s", + "musl/src/math/i386/expm1l.s", + "musl/src/math/i386/fabs.s", + "musl/src/math/i386/fabsf.s", + "musl/src/math/i386/fabsl.s", + "musl/src/math/i386/floor.s", + "musl/src/math/i386/floorf.s", + "musl/src/math/i386/floorl.s", + "musl/src/math/i386/fmod.s", + "musl/src/math/i386/fmodf.s", + "musl/src/math/i386/fmodl.s", + "musl/src/math/i386/hypot.s", + "musl/src/math/i386/hypotf.s", + "musl/src/math/i386/ldexp.s", + "musl/src/math/i386/ldexpf.s", + "musl/src/math/i386/ldexpl.s", + "musl/src/math/i386/llrint.s", + "musl/src/math/i386/llrintf.s", + "musl/src/math/i386/llrintl.s", + "musl/src/math/i386/log.s", + "musl/src/math/i386/log10.s", + "musl/src/math/i386/log10f.s", + "musl/src/math/i386/log10l.s", + "musl/src/math/i386/log1p.s", + "musl/src/math/i386/log1pf.s", + "musl/src/math/i386/log1pl.s", + "musl/src/math/i386/log2.s", + "musl/src/math/i386/log2f.s", + "musl/src/math/i386/log2l.s", + "musl/src/math/i386/logf.s", + "musl/src/math/i386/logl.s", + "musl/src/math/i386/lrint.s", + "musl/src/math/i386/lrintf.s", + "musl/src/math/i386/lrintl.s", + "musl/src/math/i386/remainder.s", + "musl/src/math/i386/remainderf.s", + "musl/src/math/i386/remainderl.s", + "musl/src/math/i386/remquo.s", + "musl/src/math/i386/remquof.s", + "musl/src/math/i386/remquol.s", + "musl/src/math/i386/rint.s", + "musl/src/math/i386/rintf.s", + "musl/src/math/i386/rintl.s", + "musl/src/math/i386/scalbln.s", + "musl/src/math/i386/scalblnf.s", + "musl/src/math/i386/scalblnl.s", + "musl/src/math/i386/scalbn.s", + "musl/src/math/i386/scalbnf.s", + "musl/src/math/i386/scalbnl.s", + "musl/src/math/i386/sqrt.s", + "musl/src/math/i386/sqrtf.s", + "musl/src/math/i386/sqrtl.s", + "musl/src/math/i386/trunc.s", + "musl/src/math/i386/truncf.s", + "musl/src/math/i386/truncl.s", + "musl/src/math/ilogb.c", + "musl/src/math/ilogbf.c", + "musl/src/math/ilogbl.c", + "musl/src/math/j0.c", + "musl/src/math/j0f.c", + "musl/src/math/j1.c", + "musl/src/math/j1f.c", + "musl/src/math/jn.c", + "musl/src/math/jnf.c", + "musl/src/math/ldexp.c", + "musl/src/math/ldexpf.c", + "musl/src/math/ldexpl.c", + "musl/src/math/lgamma.c", + "musl/src/math/lgamma_r.c", + "musl/src/math/lgammaf.c", + "musl/src/math/lgammaf_r.c", + "musl/src/math/lgammal.c", + "musl/src/math/llrint.c", + "musl/src/math/llrintf.c", + "musl/src/math/llrintl.c", + "musl/src/math/llround.c", + "musl/src/math/llroundf.c", + "musl/src/math/llroundl.c", + "musl/src/math/log.c", + "musl/src/math/log10.c", + "musl/src/math/log10f.c", + "musl/src/math/log10l.c", + "musl/src/math/log1p.c", + "musl/src/math/log1pf.c", + "musl/src/math/log1pl.c", + "musl/src/math/log2.c", + "musl/src/math/log2_data.c", + "musl/src/math/log2f.c", + "musl/src/math/log2f_data.c", + "musl/src/math/log2l.c", + "musl/src/math/log_data.c", + "musl/src/math/logb.c", + "musl/src/math/logbf.c", + "musl/src/math/logbl.c", + "musl/src/math/logf.c", + "musl/src/math/logf_data.c", + "musl/src/math/logl.c", + "musl/src/math/lrint.c", + "musl/src/math/lrintf.c", + "musl/src/math/lrintl.c", + "musl/src/math/lround.c", + "musl/src/math/lroundf.c", + "musl/src/math/lroundl.c", + "musl/src/math/mips/fabs.c", + "musl/src/math/mips/fabsf.c", + "musl/src/math/mips/sqrt.c", + "musl/src/math/mips/sqrtf.c", + "musl/src/math/modf.c", + "musl/src/math/modff.c", + "musl/src/math/modfl.c", + "musl/src/math/nan.c", + "musl/src/math/nanf.c", + "musl/src/math/nanl.c", + "musl/src/math/nearbyint.c", + "musl/src/math/nearbyintf.c", + "musl/src/math/nearbyintl.c", + "musl/src/math/nextafter.c", + "musl/src/math/nextafterf.c", + "musl/src/math/nextafterl.c", + "musl/src/math/nexttoward.c", + "musl/src/math/nexttowardf.c", + "musl/src/math/nexttowardl.c", + "musl/src/math/pow.c", + "musl/src/math/pow_data.c", + "musl/src/math/powerpc/fabs.c", + "musl/src/math/powerpc/fabsf.c", + "musl/src/math/powerpc/fma.c", + "musl/src/math/powerpc/fmaf.c", + "musl/src/math/powerpc/sqrt.c", + "musl/src/math/powerpc/sqrtf.c", + "musl/src/math/powerpc64/ceil.c", + "musl/src/math/powerpc64/ceilf.c", + "musl/src/math/powerpc64/fabs.c", + "musl/src/math/powerpc64/fabsf.c", + "musl/src/math/powerpc64/floor.c", + "musl/src/math/powerpc64/floorf.c", + "musl/src/math/powerpc64/fma.c", + "musl/src/math/powerpc64/fmaf.c", + "musl/src/math/powerpc64/fmax.c", + "musl/src/math/powerpc64/fmaxf.c", + "musl/src/math/powerpc64/fmin.c", + "musl/src/math/powerpc64/fminf.c", + "musl/src/math/powerpc64/lrint.c", + "musl/src/math/powerpc64/lrintf.c", + "musl/src/math/powerpc64/lround.c", + "musl/src/math/powerpc64/lroundf.c", + "musl/src/math/powerpc64/round.c", + "musl/src/math/powerpc64/roundf.c", + "musl/src/math/powerpc64/sqrt.c", + "musl/src/math/powerpc64/sqrtf.c", + "musl/src/math/powerpc64/trunc.c", + "musl/src/math/powerpc64/truncf.c", + "musl/src/math/powf.c", + "musl/src/math/powf_data.c", + "musl/src/math/powl.c", + "musl/src/math/remainder.c", + "musl/src/math/remainderf.c", + "musl/src/math/remainderl.c", + "musl/src/math/remquo.c", + "musl/src/math/remquof.c", + "musl/src/math/remquol.c", + "musl/src/math/rint.c", + "musl/src/math/rintf.c", + "musl/src/math/rintl.c", + "musl/src/math/riscv64/copysign.c", + "musl/src/math/riscv64/copysignf.c", + "musl/src/math/riscv64/fabs.c", + "musl/src/math/riscv64/fabsf.c", + "musl/src/math/riscv64/fma.c", + "musl/src/math/riscv64/fmaf.c", + "musl/src/math/riscv64/fmax.c", + "musl/src/math/riscv64/fmaxf.c", + "musl/src/math/riscv64/fmin.c", + "musl/src/math/riscv64/fminf.c", + "musl/src/math/riscv64/sqrt.c", + "musl/src/math/riscv64/sqrtf.c", + "musl/src/math/round.c", + "musl/src/math/roundf.c", + "musl/src/math/roundl.c", + "musl/src/math/s390x/ceil.c", + "musl/src/math/s390x/ceilf.c", + "musl/src/math/s390x/ceill.c", + "musl/src/math/s390x/fabs.c", + "musl/src/math/s390x/fabsf.c", + "musl/src/math/s390x/fabsl.c", + "musl/src/math/s390x/floor.c", + "musl/src/math/s390x/floorf.c", + "musl/src/math/s390x/floorl.c", + "musl/src/math/s390x/fma.c", + "musl/src/math/s390x/fmaf.c", + "musl/src/math/s390x/nearbyint.c", + "musl/src/math/s390x/nearbyintf.c", + "musl/src/math/s390x/nearbyintl.c", + "musl/src/math/s390x/rint.c", + "musl/src/math/s390x/rintf.c", + "musl/src/math/s390x/rintl.c", + "musl/src/math/s390x/round.c", + "musl/src/math/s390x/roundf.c", + "musl/src/math/s390x/roundl.c", + "musl/src/math/s390x/sqrt.c", + "musl/src/math/s390x/sqrtf.c", + "musl/src/math/s390x/sqrtl.c", + "musl/src/math/s390x/trunc.c", + "musl/src/math/s390x/truncf.c", + "musl/src/math/s390x/truncl.c", + "musl/src/math/scalb.c", + "musl/src/math/scalbf.c", + "musl/src/math/scalbln.c", + "musl/src/math/scalblnf.c", + "musl/src/math/scalblnl.c", + "musl/src/math/scalbn.c", + "musl/src/math/scalbnf.c", + "musl/src/math/scalbnl.c", + "musl/src/math/signgam.c", + "musl/src/math/significand.c", + "musl/src/math/significandf.c", + "musl/src/math/sin.c", + "musl/src/math/sincos.c", + "musl/src/math/sincosf.c", + "musl/src/math/sincosl.c", + "musl/src/math/sinf.c", + "musl/src/math/sinh.c", + "musl/src/math/sinhf.c", + "musl/src/math/sinhl.c", + "musl/src/math/sinl.c", + "musl/src/math/sqrt.c", + "musl/src/math/sqrtf.c", + "musl/src/math/sqrtl.c", + "musl/src/math/tan.c", + "musl/src/math/tanf.c", + "musl/src/math/tanh.c", + "musl/src/math/tanhf.c", + "musl/src/math/tanhl.c", + "musl/src/math/tanl.c", + "musl/src/math/tgamma.c", + "musl/src/math/tgammaf.c", + "musl/src/math/tgammal.c", + "musl/src/math/trunc.c", + "musl/src/math/truncf.c", + "musl/src/math/truncl.c", + "musl/src/math/x32/__invtrigl.s", + "musl/src/math/x32/acosl.s", + "musl/src/math/x32/asinl.s", + "musl/src/math/x32/atan2l.s", + "musl/src/math/x32/atanl.s", + "musl/src/math/x32/ceill.s", + "musl/src/math/x32/exp2l.s", + "musl/src/math/x32/expl.s", + "musl/src/math/x32/expm1l.s", + "musl/src/math/x32/fabs.s", + "musl/src/math/x32/fabsf.s", + "musl/src/math/x32/fabsl.s", + "musl/src/math/x32/floorl.s", + "musl/src/math/x32/fma.c", + "musl/src/math/x32/fmaf.c", + "musl/src/math/x32/fmodl.s", + "musl/src/math/x32/llrint.s", + "musl/src/math/x32/llrintf.s", + "musl/src/math/x32/llrintl.s", + "musl/src/math/x32/log10l.s", + "musl/src/math/x32/log1pl.s", + "musl/src/math/x32/log2l.s", + "musl/src/math/x32/logl.s", + "musl/src/math/x32/lrint.s", + "musl/src/math/x32/lrintf.s", + "musl/src/math/x32/lrintl.s", + "musl/src/math/x32/remainderl.s", + "musl/src/math/x32/rintl.s", + "musl/src/math/x32/sqrt.s", + "musl/src/math/x32/sqrtf.s", + "musl/src/math/x32/sqrtl.s", + "musl/src/math/x32/truncl.s", + "musl/src/math/x86_64/__invtrigl.s", + "musl/src/math/x86_64/acosl.s", + "musl/src/math/x86_64/asinl.s", + "musl/src/math/x86_64/atan2l.s", + "musl/src/math/x86_64/atanl.s", + "musl/src/math/x86_64/ceill.s", + "musl/src/math/x86_64/exp2l.s", + "musl/src/math/x86_64/expl.s", + "musl/src/math/x86_64/expm1l.s", + "musl/src/math/x86_64/fabs.s", + "musl/src/math/x86_64/fabsf.s", + "musl/src/math/x86_64/fabsl.s", + "musl/src/math/x86_64/floorl.s", + "musl/src/math/x86_64/fma.c", + "musl/src/math/x86_64/fmaf.c", + "musl/src/math/x86_64/fmodl.s", + "musl/src/math/x86_64/llrint.s", + "musl/src/math/x86_64/llrintf.s", + "musl/src/math/x86_64/llrintl.s", + "musl/src/math/x86_64/log10l.s", + "musl/src/math/x86_64/log1pl.s", + "musl/src/math/x86_64/log2l.s", + "musl/src/math/x86_64/logl.s", + "musl/src/math/x86_64/lrint.s", + "musl/src/math/x86_64/lrintf.s", + "musl/src/math/x86_64/lrintl.s", + "musl/src/math/x86_64/remainderl.s", + "musl/src/math/x86_64/rintl.s", + "musl/src/math/x86_64/sqrt.s", + "musl/src/math/x86_64/sqrtf.s", + "musl/src/math/x86_64/sqrtl.s", + "musl/src/math/x86_64/truncl.s", + "musl/src/misc/a64l.c", + "musl/src/misc/basename.c", + "musl/src/misc/dirname.c", + "musl/src/misc/ffs.c", + "musl/src/misc/ffsl.c", + "musl/src/misc/ffsll.c", + "musl/src/misc/fmtmsg.c", + "musl/src/misc/forkpty.c", + "musl/src/misc/get_current_dir_name.c", + "musl/src/misc/getauxval.c", + "musl/src/misc/getdomainname.c", + "musl/src/misc/getentropy.c", + "musl/src/misc/gethostid.c", + "musl/src/misc/getopt.c", + "musl/src/misc/getopt_long.c", + "musl/src/misc/getpriority.c", + "musl/src/misc/getresgid.c", + "musl/src/misc/getresuid.c", + "musl/src/misc/getrlimit.c", + "musl/src/misc/getrusage.c", + "musl/src/misc/getsubopt.c", + "musl/src/misc/initgroups.c", + "musl/src/misc/ioctl.c", + "musl/src/misc/issetugid.c", + "musl/src/misc/lockf.c", + "musl/src/misc/login_tty.c", + "musl/src/misc/mntent.c", + "musl/src/misc/nftw.c", + "musl/src/misc/openpty.c", + "musl/src/misc/ptsname.c", + "musl/src/misc/pty.c", + "musl/src/misc/realpath.c", + "musl/src/misc/setdomainname.c", + "musl/src/misc/setpriority.c", + "musl/src/misc/setrlimit.c", + "musl/src/misc/syscall.c", + "musl/src/misc/syslog.c", + "musl/src/misc/uname.c", + "musl/src/misc/wordexp.c", + "musl/src/mman/madvise.c", + "musl/src/mman/mincore.c", + "musl/src/mman/mlock.c", + "musl/src/mman/mlockall.c", + "musl/src/mman/mmap.c", + "musl/src/mman/mprotect.c", + "musl/src/mman/mremap.c", + "musl/src/mman/msync.c", + "musl/src/mman/munlock.c", + "musl/src/mman/munlockall.c", + "musl/src/mman/munmap.c", + "musl/src/mman/posix_madvise.c", + "musl/src/mman/shm_open.c", + "musl/src/mq/mq_close.c", + "musl/src/mq/mq_getattr.c", + "musl/src/mq/mq_notify.c", + "musl/src/mq/mq_open.c", + "musl/src/mq/mq_receive.c", + "musl/src/mq/mq_send.c", + "musl/src/mq/mq_setattr.c", + "musl/src/mq/mq_timedreceive.c", + "musl/src/mq/mq_timedsend.c", + "musl/src/mq/mq_unlink.c", + "musl/src/multibyte/btowc.c", + "musl/src/multibyte/c16rtomb.c", + "musl/src/multibyte/c32rtomb.c", + "musl/src/multibyte/internal.c", + "musl/src/multibyte/mblen.c", + "musl/src/multibyte/mbrlen.c", + "musl/src/multibyte/mbrtoc16.c", + "musl/src/multibyte/mbrtoc32.c", + "musl/src/multibyte/mbrtowc.c", + "musl/src/multibyte/mbsinit.c", + "musl/src/multibyte/mbsnrtowcs.c", + "musl/src/multibyte/mbsrtowcs.c", + "musl/src/multibyte/mbstowcs.c", + "musl/src/multibyte/mbtowc.c", + "musl/src/multibyte/wcrtomb.c", + "musl/src/multibyte/wcsnrtombs.c", + "musl/src/multibyte/wcsrtombs.c", + "musl/src/multibyte/wcstombs.c", + "musl/src/multibyte/wctob.c", + "musl/src/multibyte/wctomb.c", + "musl/src/network/accept.c", + "musl/src/network/accept4.c", + "musl/src/network/bind.c", + "musl/src/network/connect.c", + "musl/src/network/dn_comp.c", + "musl/src/network/dn_expand.c", + "musl/src/network/dn_skipname.c", + "musl/src/network/dns_parse.c", + "musl/src/network/ent.c", + "musl/src/network/ether.c", + "musl/src/network/freeaddrinfo.c", + "musl/src/network/gai_strerror.c", + "musl/src/network/getaddrinfo.c", + "musl/src/network/gethostbyaddr.c", + "musl/src/network/gethostbyaddr_r.c", + "musl/src/network/gethostbyname.c", + "musl/src/network/gethostbyname2.c", + "musl/src/network/gethostbyname2_r.c", + "musl/src/network/gethostbyname_r.c", + "musl/src/network/getifaddrs.c", + "musl/src/network/getnameinfo.c", + "musl/src/network/getpeername.c", + "musl/src/network/getservbyname.c", + "musl/src/network/getservbyname_r.c", + "musl/src/network/getservbyport.c", + "musl/src/network/getservbyport_r.c", + "musl/src/network/getsockname.c", + "musl/src/network/getsockopt.c", + "musl/src/network/h_errno.c", + "musl/src/network/herror.c", + "musl/src/network/hstrerror.c", + "musl/src/network/htonl.c", + "musl/src/network/htons.c", + "musl/src/network/if_freenameindex.c", + "musl/src/network/if_indextoname.c", + "musl/src/network/if_nameindex.c", + "musl/src/network/if_nametoindex.c", + "musl/src/network/in6addr_any.c", + "musl/src/network/in6addr_loopback.c", + "musl/src/network/inet_addr.c", + "musl/src/network/inet_aton.c", + "musl/src/network/inet_legacy.c", + "musl/src/network/inet_ntoa.c", + "musl/src/network/inet_ntop.c", + "musl/src/network/inet_pton.c", + "musl/src/network/listen.c", + "musl/src/network/lookup_ipliteral.c", + "musl/src/network/lookup_name.c", + "musl/src/network/lookup_serv.c", + "musl/src/network/netlink.c", + "musl/src/network/netname.c", + "musl/src/network/ns_parse.c", + "musl/src/network/ntohl.c", + "musl/src/network/ntohs.c", + "musl/src/network/proto.c", + "musl/src/network/recv.c", + "musl/src/network/recvfrom.c", + "musl/src/network/recvmmsg.c", + "musl/src/network/recvmsg.c", + "musl/src/network/res_init.c", + "musl/src/network/res_mkquery.c", + "musl/src/network/res_msend.c", + "musl/src/network/res_query.c", + "musl/src/network/res_querydomain.c", + "musl/src/network/res_send.c", + "musl/src/network/res_state.c", + "musl/src/network/resolvconf.c", + "musl/src/network/send.c", + "musl/src/network/sendmmsg.c", + "musl/src/network/sendmsg.c", + "musl/src/network/sendto.c", + "musl/src/network/serv.c", + "musl/src/network/setsockopt.c", + "musl/src/network/shutdown.c", + "musl/src/network/sockatmark.c", + "musl/src/network/socket.c", + "musl/src/network/socketpair.c", + "musl/src/passwd/fgetgrent.c", + "musl/src/passwd/fgetpwent.c", + "musl/src/passwd/fgetspent.c", + "musl/src/passwd/getgr_a.c", + "musl/src/passwd/getgr_r.c", + "musl/src/passwd/getgrent.c", + "musl/src/passwd/getgrent_a.c", + "musl/src/passwd/getgrouplist.c", + "musl/src/passwd/getpw_a.c", + "musl/src/passwd/getpw_r.c", + "musl/src/passwd/getpwent.c", + "musl/src/passwd/getpwent_a.c", + "musl/src/passwd/getspent.c", + "musl/src/passwd/getspnam.c", + "musl/src/passwd/getspnam_r.c", + "musl/src/passwd/lckpwdf.c", + "musl/src/passwd/nscd_query.c", + "musl/src/passwd/putgrent.c", + "musl/src/passwd/putpwent.c", + "musl/src/passwd/putspent.c", + "musl/src/prng/__rand48_step.c", + "musl/src/prng/__seed48.c", + "musl/src/prng/drand48.c", + "musl/src/prng/lcong48.c", + "musl/src/prng/lrand48.c", + "musl/src/prng/mrand48.c", + "musl/src/prng/rand.c", + "musl/src/prng/rand_r.c", + "musl/src/prng/random.c", + "musl/src/prng/seed48.c", + "musl/src/prng/srand48.c", + "musl/src/process/arm/vfork.s", + "musl/src/process/execl.c", + "musl/src/process/execle.c", + "musl/src/process/execlp.c", + "musl/src/process/execv.c", + "musl/src/process/execve.c", + "musl/src/process/execvp.c", + "musl/src/process/fexecve.c", + "musl/src/process/fork.c", + "musl/src/process/i386/vfork.s", + "musl/src/process/posix_spawn.c", + "musl/src/process/posix_spawn_file_actions_addchdir.c", + "musl/src/process/posix_spawn_file_actions_addclose.c", + "musl/src/process/posix_spawn_file_actions_adddup2.c", + "musl/src/process/posix_spawn_file_actions_addfchdir.c", + "musl/src/process/posix_spawn_file_actions_addopen.c", + "musl/src/process/posix_spawn_file_actions_destroy.c", + "musl/src/process/posix_spawn_file_actions_init.c", + "musl/src/process/posix_spawnattr_destroy.c", + "musl/src/process/posix_spawnattr_getflags.c", + "musl/src/process/posix_spawnattr_getpgroup.c", + "musl/src/process/posix_spawnattr_getsigdefault.c", + "musl/src/process/posix_spawnattr_getsigmask.c", + "musl/src/process/posix_spawnattr_init.c", + "musl/src/process/posix_spawnattr_sched.c", + "musl/src/process/posix_spawnattr_setflags.c", + "musl/src/process/posix_spawnattr_setpgroup.c", + "musl/src/process/posix_spawnattr_setsigdefault.c", + "musl/src/process/posix_spawnattr_setsigmask.c", + "musl/src/process/posix_spawnp.c", + "musl/src/process/s390x/vfork.s", + "musl/src/process/sh/vfork.s", + "musl/src/process/system.c", + "musl/src/process/vfork.c", + "musl/src/process/wait.c", + "musl/src/process/waitid.c", + "musl/src/process/waitpid.c", + "musl/src/process/x32/vfork.s", + "musl/src/process/x86_64/vfork.s", + "musl/src/regex/fnmatch.c", + "musl/src/regex/glob.c", + "musl/src/regex/regcomp.c", + "musl/src/regex/regerror.c", + "musl/src/regex/regexec.c", + "musl/src/regex/tre-mem.c", + "musl/src/sched/affinity.c", + "musl/src/sched/sched_cpucount.c", + "musl/src/sched/sched_get_priority_max.c", + "musl/src/sched/sched_getcpu.c", + "musl/src/sched/sched_getparam.c", + "musl/src/sched/sched_getscheduler.c", + "musl/src/sched/sched_rr_get_interval.c", + "musl/src/sched/sched_setparam.c", + "musl/src/sched/sched_setscheduler.c", + "musl/src/sched/sched_yield.c", + "musl/src/search/hsearch.c", + "musl/src/search/insque.c", + "musl/src/search/lsearch.c", + "musl/src/search/tdelete.c", + "musl/src/search/tdestroy.c", + "musl/src/search/tfind.c", + "musl/src/search/tsearch.c", + "musl/src/search/twalk.c", + "musl/src/select/poll.c", + "musl/src/select/pselect.c", + "musl/src/select/select.c", + "musl/src/setjmp/aarch64/longjmp.s", + "musl/src/setjmp/aarch64/setjmp.s", + "musl/src/setjmp/arm/longjmp.S", + "musl/src/setjmp/arm/setjmp.S", + "musl/src/setjmp/i386/longjmp.s", + "musl/src/setjmp/i386/setjmp.s", + "musl/src/setjmp/longjmp.c", + "musl/src/setjmp/m68k/longjmp.s", + "musl/src/setjmp/m68k/setjmp.s", + "musl/src/setjmp/microblaze/longjmp.s", + "musl/src/setjmp/microblaze/setjmp.s", + "musl/src/setjmp/mips/longjmp.S", + "musl/src/setjmp/mips/setjmp.S", + "musl/src/setjmp/mips64/longjmp.S", + "musl/src/setjmp/mips64/setjmp.S", + "musl/src/setjmp/mipsn32/longjmp.S", + "musl/src/setjmp/mipsn32/setjmp.S", + "musl/src/setjmp/or1k/longjmp.s", + "musl/src/setjmp/or1k/setjmp.s", + "musl/src/setjmp/powerpc/longjmp.S", + "musl/src/setjmp/powerpc/setjmp.S", + "musl/src/setjmp/powerpc64/longjmp.s", + "musl/src/setjmp/powerpc64/setjmp.s", + "musl/src/setjmp/riscv64/longjmp.S", + "musl/src/setjmp/riscv64/setjmp.S", + "musl/src/setjmp/s390x/longjmp.s", + "musl/src/setjmp/s390x/setjmp.s", + "musl/src/setjmp/setjmp.c", + "musl/src/setjmp/sh/longjmp.S", + "musl/src/setjmp/sh/setjmp.S", + "musl/src/setjmp/x32/longjmp.s", + "musl/src/setjmp/x32/setjmp.s", + "musl/src/setjmp/x86_64/longjmp.s", + "musl/src/setjmp/x86_64/setjmp.s", + "musl/src/signal/aarch64/restore.s", + "musl/src/signal/aarch64/sigsetjmp.s", + "musl/src/signal/arm/restore.s", + "musl/src/signal/arm/sigsetjmp.s", + "musl/src/signal/block.c", + "musl/src/signal/getitimer.c", + "musl/src/signal/i386/restore.s", + "musl/src/signal/i386/sigsetjmp.s", + "musl/src/signal/kill.c", + "musl/src/signal/killpg.c", + "musl/src/signal/m68k/sigsetjmp.s", + "musl/src/signal/microblaze/restore.s", + "musl/src/signal/microblaze/sigsetjmp.s", + "musl/src/signal/mips/restore.s", + "musl/src/signal/mips/sigsetjmp.s", + "musl/src/signal/mips64/restore.s", + "musl/src/signal/mips64/sigsetjmp.s", + "musl/src/signal/mipsn32/restore.s", + "musl/src/signal/mipsn32/sigsetjmp.s", + "musl/src/signal/or1k/sigsetjmp.s", + "musl/src/signal/powerpc/restore.s", + "musl/src/signal/powerpc/sigsetjmp.s", + "musl/src/signal/powerpc64/restore.s", + "musl/src/signal/powerpc64/sigsetjmp.s", + "musl/src/signal/psiginfo.c", + "musl/src/signal/psignal.c", + "musl/src/signal/raise.c", + "musl/src/signal/restore.c", + "musl/src/signal/riscv64/restore.s", + "musl/src/signal/riscv64/sigsetjmp.s", + "musl/src/signal/s390x/restore.s", + "musl/src/signal/s390x/sigsetjmp.s", + "musl/src/signal/setitimer.c", + "musl/src/signal/sh/restore.s", + "musl/src/signal/sh/sigsetjmp.s", + "musl/src/signal/sigaction.c", + "musl/src/signal/sigaddset.c", + "musl/src/signal/sigaltstack.c", + "musl/src/signal/sigandset.c", + "musl/src/signal/sigdelset.c", + "musl/src/signal/sigemptyset.c", + "musl/src/signal/sigfillset.c", + "musl/src/signal/sighold.c", + "musl/src/signal/sigignore.c", + "musl/src/signal/siginterrupt.c", + "musl/src/signal/sigisemptyset.c", + "musl/src/signal/sigismember.c", + "musl/src/signal/siglongjmp.c", + "musl/src/signal/signal.c", + "musl/src/signal/sigorset.c", + "musl/src/signal/sigpause.c", + "musl/src/signal/sigpending.c", + "musl/src/signal/sigprocmask.c", + "musl/src/signal/sigqueue.c", + "musl/src/signal/sigrelse.c", + "musl/src/signal/sigrtmax.c", + "musl/src/signal/sigrtmin.c", + "musl/src/signal/sigset.c", + "musl/src/signal/sigsetjmp.c", + "musl/src/signal/sigsetjmp_tail.c", + "musl/src/signal/sigsuspend.c", + "musl/src/signal/sigtimedwait.c", + "musl/src/signal/sigwait.c", + "musl/src/signal/sigwaitinfo.c", + "musl/src/signal/x32/getitimer.c", + "musl/src/signal/x32/restore.s", + "musl/src/signal/x32/setitimer.c", + "musl/src/signal/x32/sigsetjmp.s", + "musl/src/signal/x86_64/restore.s", + "musl/src/signal/x86_64/sigsetjmp.s", + "musl/src/stat/__xstat.c", + "musl/src/stat/chmod.c", + "musl/src/stat/fchmod.c", + "musl/src/stat/fchmodat.c", + "musl/src/stat/fstat.c", + "musl/src/stat/fstatat.c", + "musl/src/stat/futimens.c", + "musl/src/stat/futimesat.c", + "musl/src/stat/lchmod.c", + "musl/src/stat/lstat.c", + "musl/src/stat/mkdir.c", + "musl/src/stat/mkdirat.c", + "musl/src/stat/mkfifo.c", + "musl/src/stat/mkfifoat.c", + "musl/src/stat/mknod.c", + "musl/src/stat/mknodat.c", + "musl/src/stat/stat.c", + "musl/src/stat/statvfs.c", + "musl/src/stat/umask.c", + "musl/src/stat/utimensat.c", + "musl/src/stdio/__fclose_ca.c", + "musl/src/stdio/__fdopen.c", + "musl/src/stdio/__fmodeflags.c", + "musl/src/stdio/__fopen_rb_ca.c", + "musl/src/stdio/__lockfile.c", + "musl/src/stdio/__overflow.c", + "musl/src/stdio/__stdio_close.c", + "musl/src/stdio/__stdio_exit.c", + "musl/src/stdio/__stdio_read.c", + "musl/src/stdio/__stdio_seek.c", + "musl/src/stdio/__stdio_write.c", + "musl/src/stdio/__stdout_write.c", + "musl/src/stdio/__string_read.c", + "musl/src/stdio/__toread.c", + "musl/src/stdio/__towrite.c", + "musl/src/stdio/__uflow.c", + "musl/src/stdio/asprintf.c", + "musl/src/stdio/clearerr.c", + "musl/src/stdio/dprintf.c", + "musl/src/stdio/ext.c", + "musl/src/stdio/ext2.c", + "musl/src/stdio/fclose.c", + "musl/src/stdio/feof.c", + "musl/src/stdio/ferror.c", + "musl/src/stdio/fflush.c", + "musl/src/stdio/fgetc.c", + "musl/src/stdio/fgetln.c", + "musl/src/stdio/fgetpos.c", + "musl/src/stdio/fgets.c", + "musl/src/stdio/fgetwc.c", + "musl/src/stdio/fgetws.c", + "musl/src/stdio/fileno.c", + "musl/src/stdio/flockfile.c", + "musl/src/stdio/fmemopen.c", + "musl/src/stdio/fopen.c", + "musl/src/stdio/fopencookie.c", + "musl/src/stdio/fprintf.c", + "musl/src/stdio/fputc.c", + "musl/src/stdio/fputs.c", + "musl/src/stdio/fputwc.c", + "musl/src/stdio/fputws.c", + "musl/src/stdio/fread.c", + "musl/src/stdio/freopen.c", + "musl/src/stdio/fscanf.c", + "musl/src/stdio/fseek.c", + "musl/src/stdio/fsetpos.c", + "musl/src/stdio/ftell.c", + "musl/src/stdio/ftrylockfile.c", + "musl/src/stdio/funlockfile.c", + "musl/src/stdio/fwide.c", + "musl/src/stdio/fwprintf.c", + "musl/src/stdio/fwrite.c", + "musl/src/stdio/fwscanf.c", + "musl/src/stdio/getc.c", + "musl/src/stdio/getc_unlocked.c", + "musl/src/stdio/getchar.c", + "musl/src/stdio/getchar_unlocked.c", + "musl/src/stdio/getdelim.c", + "musl/src/stdio/getline.c", + "musl/src/stdio/gets.c", + "musl/src/stdio/getw.c", + "musl/src/stdio/getwc.c", + "musl/src/stdio/getwchar.c", + "musl/src/stdio/ofl.c", + "musl/src/stdio/ofl_add.c", + "musl/src/stdio/open_memstream.c", + "musl/src/stdio/open_wmemstream.c", + "musl/src/stdio/pclose.c", + "musl/src/stdio/perror.c", + "musl/src/stdio/popen.c", + "musl/src/stdio/printf.c", + "musl/src/stdio/putc.c", + "musl/src/stdio/putc_unlocked.c", + "musl/src/stdio/putchar.c", + "musl/src/stdio/putchar_unlocked.c", + "musl/src/stdio/puts.c", + "musl/src/stdio/putw.c", + "musl/src/stdio/putwc.c", + "musl/src/stdio/putwchar.c", + "musl/src/stdio/remove.c", + "musl/src/stdio/rename.c", + "musl/src/stdio/rewind.c", + "musl/src/stdio/scanf.c", + "musl/src/stdio/setbuf.c", + "musl/src/stdio/setbuffer.c", + "musl/src/stdio/setlinebuf.c", + "musl/src/stdio/setvbuf.c", + "musl/src/stdio/snprintf.c", + "musl/src/stdio/sprintf.c", + "musl/src/stdio/sscanf.c", + "musl/src/stdio/stderr.c", + "musl/src/stdio/stdin.c", + "musl/src/stdio/stdout.c", + "musl/src/stdio/swprintf.c", + "musl/src/stdio/swscanf.c", + "musl/src/stdio/tempnam.c", + "musl/src/stdio/tmpfile.c", + "musl/src/stdio/tmpnam.c", + "musl/src/stdio/ungetc.c", + "musl/src/stdio/ungetwc.c", + "musl/src/stdio/vasprintf.c", + "musl/src/stdio/vdprintf.c", + "musl/src/stdio/vfprintf.c", + "musl/src/stdio/vfscanf.c", + "musl/src/stdio/vfwprintf.c", + "musl/src/stdio/vfwscanf.c", + "musl/src/stdio/vprintf.c", + "musl/src/stdio/vscanf.c", + "musl/src/stdio/vsnprintf.c", + "musl/src/stdio/vsprintf.c", + "musl/src/stdio/vsscanf.c", + "musl/src/stdio/vswprintf.c", + "musl/src/stdio/vswscanf.c", + "musl/src/stdio/vwprintf.c", + "musl/src/stdio/vwscanf.c", + "musl/src/stdio/wprintf.c", + "musl/src/stdio/wscanf.c", + "musl/src/stdlib/abs.c", + "musl/src/stdlib/atof.c", + "musl/src/stdlib/atoi.c", + "musl/src/stdlib/atol.c", + "musl/src/stdlib/atoll.c", + "musl/src/stdlib/bsearch.c", + "musl/src/stdlib/div.c", + "musl/src/stdlib/ecvt.c", + "musl/src/stdlib/fcvt.c", + "musl/src/stdlib/gcvt.c", + "musl/src/stdlib/imaxabs.c", + "musl/src/stdlib/imaxdiv.c", + "musl/src/stdlib/labs.c", + "musl/src/stdlib/ldiv.c", + "musl/src/stdlib/llabs.c", + "musl/src/stdlib/lldiv.c", + "musl/src/stdlib/qsort.c", + "musl/src/stdlib/strtod.c", + "musl/src/stdlib/strtol.c", + "musl/src/stdlib/wcstod.c", + "musl/src/stdlib/wcstol.c", + "musl/src/string/arm/__aeabi_memcpy.s", + "musl/src/string/arm/__aeabi_memset.s", + "musl/src/string/arm/memcpy.c", + "musl/src/string/arm/memcpy_le.S", + "musl/src/string/bcmp.c", + "musl/src/string/bcopy.c", + "musl/src/string/bzero.c", + "musl/src/string/explicit_bzero.c", + "musl/src/string/i386/memcpy.s", + "musl/src/string/i386/memmove.s", + "musl/src/string/i386/memset.s", + "musl/src/string/index.c", + "musl/src/string/memccpy.c", + "musl/src/string/memchr.c", + "musl/src/string/memcmp.c", + "musl/src/string/memcpy.c", + "musl/src/string/memmem.c", + "musl/src/string/memmove.c", + "musl/src/string/mempcpy.c", + "musl/src/string/memrchr.c", + "musl/src/string/memset.c", + "musl/src/string/rindex.c", + "musl/src/string/stpcpy.c", + "musl/src/string/stpncpy.c", + "musl/src/string/strcasecmp.c", + "musl/src/string/strcasestr.c", + "musl/src/string/strcat.c", + "musl/src/string/strchr.c", + "musl/src/string/strchrnul.c", + "musl/src/string/strcmp.c", + "musl/src/string/strcpy.c", + "musl/src/string/strcspn.c", + "musl/src/string/strdup.c", + "musl/src/string/strerror_r.c", + "musl/src/string/strlcat.c", + "musl/src/string/strlcpy.c", + "musl/src/string/strlen.c", + "musl/src/string/strncasecmp.c", + "musl/src/string/strncat.c", + "musl/src/string/strncmp.c", + "musl/src/string/strncpy.c", + "musl/src/string/strndup.c", + "musl/src/string/strnlen.c", + "musl/src/string/strpbrk.c", + "musl/src/string/strrchr.c", + "musl/src/string/strsep.c", + "musl/src/string/strsignal.c", + "musl/src/string/strspn.c", + "musl/src/string/strstr.c", + "musl/src/string/strtok.c", + "musl/src/string/strtok_r.c", + "musl/src/string/strverscmp.c", + "musl/src/string/swab.c", + "musl/src/string/wcpcpy.c", + "musl/src/string/wcpncpy.c", + "musl/src/string/wcscasecmp.c", + "musl/src/string/wcscasecmp_l.c", + "musl/src/string/wcscat.c", + "musl/src/string/wcschr.c", + "musl/src/string/wcscmp.c", + "musl/src/string/wcscpy.c", + "musl/src/string/wcscspn.c", + "musl/src/string/wcsdup.c", + "musl/src/string/wcslen.c", + "musl/src/string/wcsncasecmp.c", + "musl/src/string/wcsncasecmp_l.c", + "musl/src/string/wcsncat.c", + "musl/src/string/wcsncmp.c", + "musl/src/string/wcsncpy.c", + "musl/src/string/wcsnlen.c", + "musl/src/string/wcspbrk.c", + "musl/src/string/wcsrchr.c", + "musl/src/string/wcsspn.c", + "musl/src/string/wcsstr.c", + "musl/src/string/wcstok.c", + "musl/src/string/wcswcs.c", + "musl/src/string/wmemchr.c", + "musl/src/string/wmemcmp.c", + "musl/src/string/wmemcpy.c", + "musl/src/string/wmemmove.c", + "musl/src/string/wmemset.c", + "musl/src/string/x86_64/memcpy.s", + "musl/src/string/x86_64/memmove.s", + "musl/src/string/x86_64/memset.s", + "musl/src/temp/__randname.c", + "musl/src/temp/mkdtemp.c", + "musl/src/temp/mkostemp.c", + "musl/src/temp/mkostemps.c", + "musl/src/temp/mkstemp.c", + "musl/src/temp/mkstemps.c", + "musl/src/temp/mktemp.c", + "musl/src/termios/cfgetospeed.c", + "musl/src/termios/cfmakeraw.c", + "musl/src/termios/cfsetospeed.c", + "musl/src/termios/tcdrain.c", + "musl/src/termios/tcflow.c", + "musl/src/termios/tcflush.c", + "musl/src/termios/tcgetattr.c", + "musl/src/termios/tcgetsid.c", + "musl/src/termios/tcsendbreak.c", + "musl/src/termios/tcsetattr.c", + "musl/src/thread/__lock.c", + "musl/src/thread/__set_thread_area.c", + "musl/src/thread/__syscall_cp.c", + "musl/src/thread/__timedwait.c", + "musl/src/thread/__tls_get_addr.c", + "musl/src/thread/__unmapself.c", + "musl/src/thread/__wait.c", + "musl/src/thread/aarch64/__set_thread_area.s", + "musl/src/thread/aarch64/__unmapself.s", + "musl/src/thread/aarch64/clone.s", + "musl/src/thread/aarch64/syscall_cp.s", + "musl/src/thread/arm/__aeabi_read_tp.s", + "musl/src/thread/arm/__set_thread_area.c", + "musl/src/thread/arm/__unmapself.s", + "musl/src/thread/arm/atomics.s", + "musl/src/thread/arm/clone.s", + "musl/src/thread/arm/syscall_cp.s", + "musl/src/thread/call_once.c", + "musl/src/thread/clone.c", + "musl/src/thread/cnd_broadcast.c", + "musl/src/thread/cnd_destroy.c", + "musl/src/thread/cnd_init.c", + "musl/src/thread/cnd_signal.c", + "musl/src/thread/cnd_timedwait.c", + "musl/src/thread/cnd_wait.c", + "musl/src/thread/default_attr.c", + "musl/src/thread/i386/__set_thread_area.s", + "musl/src/thread/i386/__unmapself.s", + "musl/src/thread/i386/clone.s", + "musl/src/thread/i386/syscall_cp.s", + "musl/src/thread/i386/tls.s", + "musl/src/thread/lock_ptc.c", + "musl/src/thread/m68k/__m68k_read_tp.s", + "musl/src/thread/m68k/clone.s", + "musl/src/thread/m68k/syscall_cp.s", + "musl/src/thread/microblaze/__set_thread_area.s", + "musl/src/thread/microblaze/__unmapself.s", + "musl/src/thread/microblaze/clone.s", + "musl/src/thread/microblaze/syscall_cp.s", + "musl/src/thread/mips/__unmapself.s", + "musl/src/thread/mips/clone.s", + "musl/src/thread/mips/syscall_cp.s", + "musl/src/thread/mips64/__unmapself.s", + "musl/src/thread/mips64/clone.s", + "musl/src/thread/mips64/syscall_cp.s", + "musl/src/thread/mipsn32/__unmapself.s", + "musl/src/thread/mipsn32/clone.s", + "musl/src/thread/mipsn32/syscall_cp.s", + "musl/src/thread/mtx_destroy.c", + "musl/src/thread/mtx_init.c", + "musl/src/thread/mtx_lock.c", + "musl/src/thread/mtx_timedlock.c", + "musl/src/thread/mtx_trylock.c", + "musl/src/thread/mtx_unlock.c", + "musl/src/thread/or1k/__set_thread_area.s", + "musl/src/thread/or1k/__unmapself.s", + "musl/src/thread/or1k/clone.s", + "musl/src/thread/or1k/syscall_cp.s", + "musl/src/thread/powerpc/__set_thread_area.s", + "musl/src/thread/powerpc/__unmapself.s", + "musl/src/thread/powerpc/clone.s", + "musl/src/thread/powerpc/syscall_cp.s", + "musl/src/thread/powerpc64/__set_thread_area.s", + "musl/src/thread/powerpc64/__unmapself.s", + "musl/src/thread/powerpc64/clone.s", + "musl/src/thread/powerpc64/syscall_cp.s", + "musl/src/thread/pthread_atfork.c", + "musl/src/thread/pthread_attr_destroy.c", + "musl/src/thread/pthread_attr_get.c", + "musl/src/thread/pthread_attr_init.c", + "musl/src/thread/pthread_attr_setdetachstate.c", + "musl/src/thread/pthread_attr_setguardsize.c", + "musl/src/thread/pthread_attr_setinheritsched.c", + "musl/src/thread/pthread_attr_setschedparam.c", + "musl/src/thread/pthread_attr_setschedpolicy.c", + "musl/src/thread/pthread_attr_setscope.c", + "musl/src/thread/pthread_attr_setstack.c", + "musl/src/thread/pthread_attr_setstacksize.c", + "musl/src/thread/pthread_barrier_destroy.c", + "musl/src/thread/pthread_barrier_init.c", + "musl/src/thread/pthread_barrier_wait.c", + "musl/src/thread/pthread_barrierattr_destroy.c", + "musl/src/thread/pthread_barrierattr_init.c", + "musl/src/thread/pthread_barrierattr_setpshared.c", + "musl/src/thread/pthread_cancel.c", + "musl/src/thread/pthread_cleanup_push.c", + "musl/src/thread/pthread_cond_broadcast.c", + "musl/src/thread/pthread_cond_destroy.c", + "musl/src/thread/pthread_cond_init.c", + "musl/src/thread/pthread_cond_signal.c", + "musl/src/thread/pthread_cond_timedwait.c", + "musl/src/thread/pthread_cond_wait.c", + "musl/src/thread/pthread_condattr_destroy.c", + "musl/src/thread/pthread_condattr_init.c", + "musl/src/thread/pthread_condattr_setclock.c", + "musl/src/thread/pthread_condattr_setpshared.c", + "musl/src/thread/pthread_create.c", + "musl/src/thread/pthread_detach.c", + "musl/src/thread/pthread_equal.c", + "musl/src/thread/pthread_getattr_np.c", + "musl/src/thread/pthread_getconcurrency.c", + "musl/src/thread/pthread_getcpuclockid.c", + "musl/src/thread/pthread_getschedparam.c", + "musl/src/thread/pthread_getspecific.c", + "musl/src/thread/pthread_join.c", + "musl/src/thread/pthread_key_create.c", + "musl/src/thread/pthread_kill.c", + "musl/src/thread/pthread_mutex_consistent.c", + "musl/src/thread/pthread_mutex_destroy.c", + "musl/src/thread/pthread_mutex_getprioceiling.c", + "musl/src/thread/pthread_mutex_init.c", + "musl/src/thread/pthread_mutex_lock.c", + "musl/src/thread/pthread_mutex_setprioceiling.c", + "musl/src/thread/pthread_mutex_timedlock.c", + "musl/src/thread/pthread_mutex_trylock.c", + "musl/src/thread/pthread_mutex_unlock.c", + "musl/src/thread/pthread_mutexattr_destroy.c", + "musl/src/thread/pthread_mutexattr_init.c", + "musl/src/thread/pthread_mutexattr_setprotocol.c", + "musl/src/thread/pthread_mutexattr_setpshared.c", + "musl/src/thread/pthread_mutexattr_setrobust.c", + "musl/src/thread/pthread_mutexattr_settype.c", + "musl/src/thread/pthread_once.c", + "musl/src/thread/pthread_rwlock_destroy.c", + "musl/src/thread/pthread_rwlock_init.c", + "musl/src/thread/pthread_rwlock_rdlock.c", + "musl/src/thread/pthread_rwlock_timedrdlock.c", + "musl/src/thread/pthread_rwlock_timedwrlock.c", + "musl/src/thread/pthread_rwlock_tryrdlock.c", + "musl/src/thread/pthread_rwlock_trywrlock.c", + "musl/src/thread/pthread_rwlock_unlock.c", + "musl/src/thread/pthread_rwlock_wrlock.c", + "musl/src/thread/pthread_rwlockattr_destroy.c", + "musl/src/thread/pthread_rwlockattr_init.c", + "musl/src/thread/pthread_rwlockattr_setpshared.c", + "musl/src/thread/pthread_self.c", + "musl/src/thread/pthread_setattr_default_np.c", + "musl/src/thread/pthread_setcancelstate.c", + "musl/src/thread/pthread_setcanceltype.c", + "musl/src/thread/pthread_setconcurrency.c", + "musl/src/thread/pthread_setname_np.c", + "musl/src/thread/pthread_setschedparam.c", + "musl/src/thread/pthread_setschedprio.c", + "musl/src/thread/pthread_setspecific.c", + "musl/src/thread/pthread_sigmask.c", + "musl/src/thread/pthread_spin_destroy.c", + "musl/src/thread/pthread_spin_init.c", + "musl/src/thread/pthread_spin_lock.c", + "musl/src/thread/pthread_spin_trylock.c", + "musl/src/thread/pthread_spin_unlock.c", + "musl/src/thread/pthread_testcancel.c", + "musl/src/thread/riscv64/__set_thread_area.s", + "musl/src/thread/riscv64/__unmapself.s", + "musl/src/thread/riscv64/clone.s", + "musl/src/thread/riscv64/syscall_cp.s", + "musl/src/thread/s390x/__set_thread_area.s", + "musl/src/thread/s390x/__tls_get_offset.s", + "musl/src/thread/s390x/__unmapself.s", + "musl/src/thread/s390x/clone.s", + "musl/src/thread/s390x/syscall_cp.s", + "musl/src/thread/sem_destroy.c", + "musl/src/thread/sem_getvalue.c", + "musl/src/thread/sem_init.c", + "musl/src/thread/sem_open.c", + "musl/src/thread/sem_post.c", + "musl/src/thread/sem_timedwait.c", + "musl/src/thread/sem_trywait.c", + "musl/src/thread/sem_unlink.c", + "musl/src/thread/sem_wait.c", + "musl/src/thread/sh/__set_thread_area.c", + "musl/src/thread/sh/__unmapself.c", + "musl/src/thread/sh/__unmapself_mmu.s", + "musl/src/thread/sh/atomics.s", + "musl/src/thread/sh/clone.s", + "musl/src/thread/sh/syscall_cp.s", + "musl/src/thread/synccall.c", + "musl/src/thread/syscall_cp.c", + "musl/src/thread/thrd_create.c", + "musl/src/thread/thrd_exit.c", + "musl/src/thread/thrd_join.c", + "musl/src/thread/thrd_sleep.c", + "musl/src/thread/thrd_yield.c", + "musl/src/thread/tls.c", + "musl/src/thread/tss_create.c", + "musl/src/thread/tss_delete.c", + "musl/src/thread/tss_set.c", + "musl/src/thread/vmlock.c", + "musl/src/thread/x32/__set_thread_area.s", + "musl/src/thread/x32/__unmapself.s", + "musl/src/thread/x32/clone.s", + "musl/src/thread/x32/syscall_cp.s", + "musl/src/thread/x86_64/__set_thread_area.s", + "musl/src/thread/x86_64/__unmapself.s", + "musl/src/thread/x86_64/clone.s", + "musl/src/thread/x86_64/syscall_cp.s", + "musl/src/time/__map_file.c", + "musl/src/time/__month_to_secs.c", + "musl/src/time/__secs_to_tm.c", + "musl/src/time/__tm_to_secs.c", + "musl/src/time/__tz.c", + "musl/src/time/__year_to_secs.c", + "musl/src/time/asctime.c", + "musl/src/time/asctime_r.c", + "musl/src/time/clock.c", + "musl/src/time/clock_getcpuclockid.c", + "musl/src/time/clock_getres.c", + "musl/src/time/clock_gettime.c", + "musl/src/time/clock_nanosleep.c", + "musl/src/time/clock_settime.c", + "musl/src/time/ctime.c", + "musl/src/time/ctime_r.c", + "musl/src/time/difftime.c", + "musl/src/time/ftime.c", + "musl/src/time/getdate.c", + "musl/src/time/gettimeofday.c", + "musl/src/time/gmtime.c", + "musl/src/time/gmtime_r.c", + "musl/src/time/localtime.c", + "musl/src/time/localtime_r.c", + "musl/src/time/mktime.c", + "musl/src/time/nanosleep.c", + "musl/src/time/strftime.c", + "musl/src/time/strptime.c", + "musl/src/time/time.c", + "musl/src/time/timegm.c", + "musl/src/time/timer_create.c", + "musl/src/time/timer_delete.c", + "musl/src/time/timer_getoverrun.c", + "musl/src/time/timer_gettime.c", + "musl/src/time/timer_settime.c", + "musl/src/time/times.c", + "musl/src/time/timespec_get.c", + "musl/src/time/utime.c", + "musl/src/time/wcsftime.c", + "musl/src/unistd/_exit.c", + "musl/src/unistd/access.c", + "musl/src/unistd/acct.c", + "musl/src/unistd/alarm.c", + "musl/src/unistd/chdir.c", + "musl/src/unistd/chown.c", + "musl/src/unistd/close.c", + "musl/src/unistd/ctermid.c", + "musl/src/unistd/dup.c", + "musl/src/unistd/dup2.c", + "musl/src/unistd/dup3.c", + "musl/src/unistd/faccessat.c", + "musl/src/unistd/fchdir.c", + "musl/src/unistd/fchown.c", + "musl/src/unistd/fchownat.c", + "musl/src/unistd/fdatasync.c", + "musl/src/unistd/fsync.c", + "musl/src/unistd/ftruncate.c", + "musl/src/unistd/getcwd.c", + "musl/src/unistd/getegid.c", + "musl/src/unistd/geteuid.c", + "musl/src/unistd/getgid.c", + "musl/src/unistd/getgroups.c", + "musl/src/unistd/gethostname.c", + "musl/src/unistd/getlogin.c", + "musl/src/unistd/getlogin_r.c", + "musl/src/unistd/getpgid.c", + "musl/src/unistd/getpgrp.c", + "musl/src/unistd/getpid.c", + "musl/src/unistd/getppid.c", + "musl/src/unistd/getsid.c", + "musl/src/unistd/getuid.c", + "musl/src/unistd/isatty.c", + "musl/src/unistd/lchown.c", + "musl/src/unistd/link.c", + "musl/src/unistd/linkat.c", + "musl/src/unistd/lseek.c", + "musl/src/unistd/mips/pipe.s", + "musl/src/unistd/mips64/pipe.s", + "musl/src/unistd/mipsn32/lseek.c", + "musl/src/unistd/mipsn32/pipe.s", + "musl/src/unistd/nice.c", + "musl/src/unistd/pause.c", + "musl/src/unistd/pipe.c", + "musl/src/unistd/pipe2.c", + "musl/src/unistd/posix_close.c", + "musl/src/unistd/pread.c", + "musl/src/unistd/preadv.c", + "musl/src/unistd/pwrite.c", + "musl/src/unistd/pwritev.c", + "musl/src/unistd/read.c", + "musl/src/unistd/readlink.c", + "musl/src/unistd/readlinkat.c", + "musl/src/unistd/readv.c", + "musl/src/unistd/renameat.c", + "musl/src/unistd/rmdir.c", + "musl/src/unistd/setegid.c", + "musl/src/unistd/seteuid.c", + "musl/src/unistd/setgid.c", + "musl/src/unistd/setpgid.c", + "musl/src/unistd/setpgrp.c", + "musl/src/unistd/setregid.c", + "musl/src/unistd/setresgid.c", + "musl/src/unistd/setresuid.c", + "musl/src/unistd/setreuid.c", + "musl/src/unistd/setsid.c", + "musl/src/unistd/setuid.c", + "musl/src/unistd/setxid.c", + "musl/src/unistd/sh/pipe.s", + "musl/src/unistd/sleep.c", + "musl/src/unistd/symlink.c", + "musl/src/unistd/symlinkat.c", + "musl/src/unistd/sync.c", + "musl/src/unistd/tcgetpgrp.c", + "musl/src/unistd/tcsetpgrp.c", + "musl/src/unistd/truncate.c", + "musl/src/unistd/ttyname.c", + "musl/src/unistd/ttyname_r.c", + "musl/src/unistd/ualarm.c", + "musl/src/unistd/unlink.c", + "musl/src/unistd/unlinkat.c", + "musl/src/unistd/usleep.c", + "musl/src/unistd/write.c", + "musl/src/unistd/writev.c", + "musl/src/unistd/x32/lseek.c", +}; +pub const compat_time32_files = [_][]const u8{ + "musl/compat/time32/__xstat.c", + "musl/compat/time32/adjtime32.c", + "musl/compat/time32/adjtimex_time32.c", + "musl/compat/time32/aio_suspend_time32.c", + "musl/compat/time32/clock_adjtime32.c", + "musl/compat/time32/clock_getres_time32.c", + "musl/compat/time32/clock_gettime32.c", + "musl/compat/time32/clock_nanosleep_time32.c", + "musl/compat/time32/clock_settime32.c", + "musl/compat/time32/cnd_timedwait_time32.c", + "musl/compat/time32/ctime32.c", + "musl/compat/time32/ctime32_r.c", + "musl/compat/time32/difftime32.c", + "musl/compat/time32/fstat_time32.c", + "musl/compat/time32/fstatat_time32.c", + "musl/compat/time32/ftime32.c", + "musl/compat/time32/futimens_time32.c", + "musl/compat/time32/futimes_time32.c", + "musl/compat/time32/futimesat_time32.c", + "musl/compat/time32/getitimer_time32.c", + "musl/compat/time32/getrusage_time32.c", + "musl/compat/time32/gettimeofday_time32.c", + "musl/compat/time32/gmtime32.c", + "musl/compat/time32/gmtime32_r.c", + "musl/compat/time32/localtime32.c", + "musl/compat/time32/localtime32_r.c", + "musl/compat/time32/lstat_time32.c", + "musl/compat/time32/lutimes_time32.c", + "musl/compat/time32/mktime32.c", + "musl/compat/time32/mq_timedreceive_time32.c", + "musl/compat/time32/mq_timedsend_time32.c", + "musl/compat/time32/mtx_timedlock_time32.c", + "musl/compat/time32/nanosleep_time32.c", + "musl/compat/time32/ppoll_time32.c", + "musl/compat/time32/pselect_time32.c", + "musl/compat/time32/pthread_cond_timedwait_time32.c", + "musl/compat/time32/pthread_mutex_timedlock_time32.c", + "musl/compat/time32/pthread_rwlock_timedrdlock_time32.c", + "musl/compat/time32/pthread_rwlock_timedwrlock_time32.c", + "musl/compat/time32/pthread_timedjoin_np_time32.c", + "musl/compat/time32/recvmmsg_time32.c", + "musl/compat/time32/sched_rr_get_interval_time32.c", + "musl/compat/time32/select_time32.c", + "musl/compat/time32/sem_timedwait_time32.c", + "musl/compat/time32/semtimedop_time32.c", + "musl/compat/time32/setitimer_time32.c", + "musl/compat/time32/settimeofday_time32.c", + "musl/compat/time32/sigtimedwait_time32.c", + "musl/compat/time32/stat_time32.c", + "musl/compat/time32/stime32.c", + "musl/compat/time32/thrd_sleep_time32.c", + "musl/compat/time32/time32.c", + "musl/compat/time32/time32gm.c", + "musl/compat/time32/timer_gettime32.c", + "musl/compat/time32/timer_settime32.c", + "musl/compat/time32/timerfd_gettime32.c", + "musl/compat/time32/timerfd_settime32.c", + "musl/compat/time32/timespec_get_time32.c", + "musl/compat/time32/utime_time32.c", + "musl/compat/time32/utimensat_time32.c", + "musl/compat/time32/utimes_time32.c", + "musl/compat/time32/wait3_time32.c", + "musl/compat/time32/wait4_time32.c", +}; diff --git a/src-self-hosted/stage1.zig b/src-self-hosted/stage1.zig new file mode 100644 index 0000000000..c2ce99db22 --- /dev/null +++ b/src-self-hosted/stage1.zig @@ -0,0 +1,495 @@ +//! This is the main entry point for the Zig/C++ hybrid compiler (stage1). +//! It has the functions exported from Zig, called in C++, and bindings for +//! the functions exported from C++, called from Zig. + +const std = @import("std"); +const assert = std.debug.assert; +const mem = std.mem; +const build_options = @import("build_options"); +const stage2 = @import("main.zig"); +const fatal = stage2.fatal; +const CrossTarget = std.zig.CrossTarget; +const Target = std.Target; + +comptime { + assert(std.builtin.link_libc); + assert(build_options.is_stage1); + _ = @import("compiler_rt"); +} + +pub const log = stage2.log; +pub const log_level = stage2.log_level; + +pub export fn main(argc: c_int, argv: [*]const [*:0]const u8) c_int { + std.debug.maybeEnableSegfaultHandler(); + + const gpa = std.heap.c_allocator; + var arena_instance = std.heap.ArenaAllocator.init(gpa); + defer arena_instance.deinit(); + const arena = &arena_instance.allocator; + + const args = arena.alloc([]const u8, @intCast(usize, argc)) catch fatal("out of memory", .{}); + for (args) |*arg, i| { + arg.* = mem.spanZ(argv[i]); + } + stage2.mainArgs(gpa, arena, args) catch |err| fatal("{}", .{err}); + return 0; +} + +// ABI warning +export fn stage2_panic(ptr: [*]const u8, len: usize) void { + @panic(ptr[0..len]); +} + +// ABI warning +const Error = extern enum { + None, + OutOfMemory, + InvalidFormat, + SemanticAnalyzeFail, + AccessDenied, + Interrupted, + SystemResources, + FileNotFound, + FileSystem, + FileTooBig, + DivByZero, + Overflow, + PathAlreadyExists, + Unexpected, + ExactDivRemainder, + NegativeDenominator, + ShiftedOutOneBits, + CCompileErrors, + EndOfFile, + IsDir, + NotDir, + UnsupportedOperatingSystem, + SharingViolation, + PipeBusy, + PrimitiveTypeNotFound, + CacheUnavailable, + PathTooLong, + CCompilerCannotFindFile, + NoCCompilerInstalled, + ReadingDepFile, + InvalidDepFile, + MissingArchitecture, + MissingOperatingSystem, + UnknownArchitecture, + UnknownOperatingSystem, + UnknownABI, + InvalidFilename, + DiskQuota, + DiskSpace, + UnexpectedWriteFailure, + UnexpectedSeekFailure, + UnexpectedFileTruncationFailure, + Unimplemented, + OperationAborted, + BrokenPipe, + NoSpaceLeft, + NotLazy, + IsAsync, + ImportOutsidePkgPath, + UnknownCpuModel, + UnknownCpuFeature, + InvalidCpuFeatures, + InvalidLlvmCpuFeaturesFormat, + UnknownApplicationBinaryInterface, + ASTUnitFailure, + BadPathName, + SymLinkLoop, + ProcessFdQuotaExceeded, + SystemFdQuotaExceeded, + NoDevice, + DeviceBusy, + UnableToSpawnCCompiler, + CCompilerExitCode, + CCompilerCrashed, + CCompilerCannotFindHeaders, + LibCRuntimeNotFound, + LibCStdLibHeaderNotFound, + LibCKernel32LibNotFound, + UnsupportedArchitecture, + WindowsSdkNotFound, + UnknownDynamicLinkerPath, + TargetHasNoDynamicLinker, + InvalidAbiVersion, + InvalidOperatingSystemVersion, + UnknownClangOption, + NestedResponseFile, + ZigIsTheCCompiler, + FileBusy, + Locked, +}; + +// ABI warning +export fn stage2_attach_segfault_handler() void { + if (std.debug.runtime_safety and std.debug.have_segfault_handling_support) { + std.debug.attachSegfaultHandler(); + } +} + +// ABI warning +export fn stage2_progress_create() *std.Progress { + const ptr = std.heap.c_allocator.create(std.Progress) catch @panic("out of memory"); + ptr.* = std.Progress{}; + return ptr; +} + +// ABI warning +export fn stage2_progress_destroy(progress: *std.Progress) void { + std.heap.c_allocator.destroy(progress); +} + +// ABI warning +export fn stage2_progress_start_root( + progress: *std.Progress, + name_ptr: [*]const u8, + name_len: usize, + estimated_total_items: usize, +) *std.Progress.Node { + return progress.start( + name_ptr[0..name_len], + if (estimated_total_items == 0) null else estimated_total_items, + ) catch @panic("timer unsupported"); +} + +// ABI warning +export fn stage2_progress_disable_tty(progress: *std.Progress) void { + progress.terminal = null; +} + +// ABI warning +export fn stage2_progress_start( + node: *std.Progress.Node, + name_ptr: [*]const u8, + name_len: usize, + estimated_total_items: usize, +) *std.Progress.Node { + const child_node = std.heap.c_allocator.create(std.Progress.Node) catch @panic("out of memory"); + child_node.* = node.start( + name_ptr[0..name_len], + if (estimated_total_items == 0) null else estimated_total_items, + ); + child_node.activate(); + return child_node; +} + +// ABI warning +export fn stage2_progress_end(node: *std.Progress.Node) void { + node.end(); + if (&node.context.root != node) { + std.heap.c_allocator.destroy(node); + } +} + +// ABI warning +export fn stage2_progress_complete_one(node: *std.Progress.Node) void { + node.completeOne(); +} + +// ABI warning +export fn stage2_progress_update_node(node: *std.Progress.Node, done_count: usize, total_count: usize) void { + node.completed_items = done_count; + node.estimated_total_items = total_count; + node.activate(); + node.context.maybeRefresh(); +} + +// ABI warning +const Stage2Target = extern struct { + arch: c_int, + vendor: c_int, + + abi: c_int, + os: c_int, + + is_native_os: bool, + is_native_cpu: bool, + + llvm_cpu_name: ?[*:0]const u8, + llvm_cpu_features: ?[*:0]const u8, + cpu_builtin_str: ?[*:0]const u8, + os_builtin_str: ?[*:0]const u8, + + dynamic_linker: ?[*:0]const u8, + + llvm_cpu_features_asm_ptr: [*]const [*:0]const u8, + llvm_cpu_features_asm_len: usize, + + fn fromTarget(self: *Stage2Target, cross_target: CrossTarget) !void { + const allocator = std.heap.c_allocator; + + var dynamic_linker: ?[*:0]u8 = null; + const target = try crossTargetToTarget(cross_target, &dynamic_linker); + + const generic_arch_name = target.cpu.arch.genericName(); + var cpu_builtin_str_buffer = try std.ArrayListSentineled(u8, 0).allocPrint(allocator, + \\Cpu{{ + \\ .arch = .{}, + \\ .model = &Target.{}.cpu.{}, + \\ .features = Target.{}.featureSet(&[_]Target.{}.Feature{{ + \\ + , .{ + @tagName(target.cpu.arch), + generic_arch_name, + target.cpu.model.name, + generic_arch_name, + generic_arch_name, + }); + defer cpu_builtin_str_buffer.deinit(); + + var llvm_features_buffer = try std.ArrayListSentineled(u8, 0).initSize(allocator, 0); + defer llvm_features_buffer.deinit(); + + // Unfortunately we have to do the work twice, because Clang does not support + // the same command line parameters for CPU features when assembling code as it does + // when compiling C code. + var asm_features_list = std.ArrayList([*:0]const u8).init(allocator); + defer asm_features_list.deinit(); + + for (target.cpu.arch.allFeaturesList()) |feature, index_usize| { + const index = @intCast(Target.Cpu.Feature.Set.Index, index_usize); + const is_enabled = target.cpu.features.isEnabled(index); + + if (feature.llvm_name) |llvm_name| { + const plus_or_minus = "-+"[@boolToInt(is_enabled)]; + try llvm_features_buffer.append(plus_or_minus); + try llvm_features_buffer.appendSlice(llvm_name); + try llvm_features_buffer.appendSlice(","); + } + + if (is_enabled) { + // TODO some kind of "zig identifier escape" function rather than + // unconditionally using @"" syntax + try cpu_builtin_str_buffer.appendSlice(" .@\""); + try cpu_builtin_str_buffer.appendSlice(feature.name); + try cpu_builtin_str_buffer.appendSlice("\",\n"); + } + } + + switch (target.cpu.arch) { + .riscv32, .riscv64 => { + if (Target.riscv.featureSetHas(target.cpu.features, .relax)) { + try asm_features_list.append("-mrelax"); + } else { + try asm_features_list.append("-mno-relax"); + } + }, + else => { + // TODO + // Argh, why doesn't the assembler accept the list of CPU features?! + // I don't see a way to do this other than hard coding everything. + }, + } + + try cpu_builtin_str_buffer.appendSlice( + \\ }), + \\}; + \\ + ); + + assert(mem.endsWith(u8, llvm_features_buffer.span(), ",")); + llvm_features_buffer.shrink(llvm_features_buffer.len() - 1); + + var os_builtin_str_buffer = try std.ArrayListSentineled(u8, 0).allocPrint(allocator, + \\Os{{ + \\ .tag = .{}, + \\ .version_range = .{{ + , .{@tagName(target.os.tag)}); + defer os_builtin_str_buffer.deinit(); + + // We'll re-use the OS version range builtin string for the cache hash. + const os_builtin_str_ver_start_index = os_builtin_str_buffer.len(); + + @setEvalBranchQuota(2000); + switch (target.os.tag) { + .freestanding, + .ananas, + .cloudabi, + .dragonfly, + .fuchsia, + .ios, + .kfreebsd, + .lv2, + .solaris, + .haiku, + .minix, + .rtems, + .nacl, + .cnk, + .aix, + .cuda, + .nvcl, + .amdhsa, + .ps4, + .elfiamcu, + .tvos, + .watchos, + .mesa3d, + .contiki, + .amdpal, + .hermit, + .hurd, + .wasi, + .emscripten, + .uefi, + .other, + => try os_builtin_str_buffer.appendSlice(" .none = {} }\n"), + + .freebsd, + .macosx, + .netbsd, + .openbsd, + => try os_builtin_str_buffer.outStream().print( + \\ .semver = .{{ + \\ .min = .{{ + \\ .major = {}, + \\ .minor = {}, + \\ .patch = {}, + \\ }}, + \\ .max = .{{ + \\ .major = {}, + \\ .minor = {}, + \\ .patch = {}, + \\ }}, + \\ }}}}, + \\ + , .{ + target.os.version_range.semver.min.major, + target.os.version_range.semver.min.minor, + target.os.version_range.semver.min.patch, + + target.os.version_range.semver.max.major, + target.os.version_range.semver.max.minor, + target.os.version_range.semver.max.patch, + }), + + .linux => try os_builtin_str_buffer.outStream().print( + \\ .linux = .{{ + \\ .range = .{{ + \\ .min = .{{ + \\ .major = {}, + \\ .minor = {}, + \\ .patch = {}, + \\ }}, + \\ .max = .{{ + \\ .major = {}, + \\ .minor = {}, + \\ .patch = {}, + \\ }}, + \\ }}, + \\ .glibc = .{{ + \\ .major = {}, + \\ .minor = {}, + \\ .patch = {}, + \\ }}, + \\ }}}}, + \\ + , .{ + target.os.version_range.linux.range.min.major, + target.os.version_range.linux.range.min.minor, + target.os.version_range.linux.range.min.patch, + + target.os.version_range.linux.range.max.major, + target.os.version_range.linux.range.max.minor, + target.os.version_range.linux.range.max.patch, + + target.os.version_range.linux.glibc.major, + target.os.version_range.linux.glibc.minor, + target.os.version_range.linux.glibc.patch, + }), + + .windows => try os_builtin_str_buffer.outStream().print( + \\ .windows = .{{ + \\ .min = {s}, + \\ .max = {s}, + \\ }}}}, + \\ + , .{ + target.os.version_range.windows.min, + target.os.version_range.windows.max, + }), + } + try os_builtin_str_buffer.appendSlice("};\n"); + + const glibc_or_darwin_version = blk: { + if (target.isGnuLibC()) { + const stage1_glibc = try std.heap.c_allocator.create(Stage2SemVer); + const stage2_glibc = target.os.version_range.linux.glibc; + stage1_glibc.* = .{ + .major = stage2_glibc.major, + .minor = stage2_glibc.minor, + .patch = stage2_glibc.patch, + }; + break :blk stage1_glibc; + } else if (target.isDarwin()) { + const stage1_semver = try std.heap.c_allocator.create(Stage2SemVer); + const stage2_semver = target.os.version_range.semver.min; + stage1_semver.* = .{ + .major = stage2_semver.major, + .minor = stage2_semver.minor, + .patch = stage2_semver.patch, + }; + break :blk stage1_semver; + } else { + break :blk null; + } + }; + + const std_dl = target.standardDynamicLinkerPath(); + const std_dl_z = if (std_dl.get()) |dl| + (try mem.dupeZ(std.heap.c_allocator, u8, dl)).ptr + else + null; + + const asm_features = asm_features_list.toOwnedSlice(); + self.* = .{ + .arch = @enumToInt(target.cpu.arch) + 1, // skip over ZigLLVM_UnknownArch + .vendor = 0, + .os = @enumToInt(target.os.tag), + .abi = @enumToInt(target.abi), + .llvm_cpu_name = if (target.cpu.model.llvm_name) |s| s.ptr else null, + .llvm_cpu_features = llvm_features_buffer.toOwnedSlice().ptr, + .llvm_cpu_features_asm_ptr = asm_features.ptr, + .llvm_cpu_features_asm_len = asm_features.len, + .cpu_builtin_str = cpu_builtin_str_buffer.toOwnedSlice().ptr, + .os_builtin_str = os_builtin_str_buffer.toOwnedSlice().ptr, + .is_native_os = cross_target.isNativeOs(), + .is_native_cpu = cross_target.isNativeCpu(), + .glibc_or_darwin_version = glibc_or_darwin_version, + .dynamic_linker = dynamic_linker, + .standard_dynamic_linker_path = std_dl_z, + }; + } +}; + +fn crossTargetToTarget(cross_target: CrossTarget, dynamic_linker_ptr: *?[*:0]u8) !Target { + var info = try std.zig.system.NativeTargetInfo.detect(std.heap.c_allocator, cross_target); + if (info.cpu_detection_unimplemented) { + // TODO We want to just use detected_info.target but implementing + // CPU model & feature detection is todo so here we rely on LLVM. + const llvm = @import("llvm.zig"); + const llvm_cpu_name = llvm.GetHostCPUName(); + const llvm_cpu_features = llvm.GetNativeFeatures(); + const arch = Target.current.cpu.arch; + info.target.cpu = try detectNativeCpuWithLLVM(arch, llvm_cpu_name, llvm_cpu_features); + cross_target.updateCpuFeatures(&info.target.cpu.features); + info.target.cpu.arch = cross_target.getCpuArch(); + } + if (info.dynamic_linker.get()) |dl| { + dynamic_linker_ptr.* = try mem.dupeZ(std.heap.c_allocator, u8, dl); + } else { + dynamic_linker_ptr.* = null; + } + return info.target; +} + +// ABI warning +const Stage2SemVer = extern struct { + major: u32, + minor: u32, + patch: u32, +}; diff --git a/src-self-hosted/stage2.zig b/src-self-hosted/stage2.zig deleted file mode 100644 index bfa37b603e..0000000000 --- a/src-self-hosted/stage2.zig +++ /dev/null @@ -1,1054 +0,0 @@ -// This is Zig code that is used by both stage1 and stage2. -// The prototypes in src/userland.h must match these definitions. - -const std = @import("std"); -const io = std.io; -const mem = std.mem; -const fs = std.fs; -const process = std.process; -const Allocator = mem.Allocator; -const ArrayList = std.ArrayList; -const ArrayListSentineled = std.ArrayListSentineled; -const Target = std.Target; -const CrossTarget = std.zig.CrossTarget; -const self_hosted_main = @import("main.zig"); -const DepTokenizer = @import("DepTokenizer.zig"); -const assert = std.debug.assert; -const LibCInstallation = @import("libc_installation.zig").LibCInstallation; - -var stderr_file: fs.File = undefined; -var stderr: fs.File.OutStream = undefined; -var stdout: fs.File.OutStream = undefined; - -comptime { - _ = @import("DepTokenizer.zig"); -} - -// ABI warning -export fn stage2_zen(ptr: *[*]const u8, len: *usize) void { - const info_zen = @import("main.zig").info_zen; - ptr.* = info_zen; - len.* = info_zen.len; -} - -// ABI warning -export fn stage2_panic(ptr: [*]const u8, len: usize) void { - @panic(ptr[0..len]); -} - -// ABI warning -const Error = extern enum { - None, - OutOfMemory, - InvalidFormat, - SemanticAnalyzeFail, - AccessDenied, - Interrupted, - SystemResources, - FileNotFound, - FileSystem, - FileTooBig, - DivByZero, - Overflow, - PathAlreadyExists, - Unexpected, - ExactDivRemainder, - NegativeDenominator, - ShiftedOutOneBits, - CCompileErrors, - EndOfFile, - IsDir, - NotDir, - UnsupportedOperatingSystem, - SharingViolation, - PipeBusy, - PrimitiveTypeNotFound, - CacheUnavailable, - PathTooLong, - CCompilerCannotFindFile, - NoCCompilerInstalled, - ReadingDepFile, - InvalidDepFile, - MissingArchitecture, - MissingOperatingSystem, - UnknownArchitecture, - UnknownOperatingSystem, - UnknownABI, - InvalidFilename, - DiskQuota, - DiskSpace, - UnexpectedWriteFailure, - UnexpectedSeekFailure, - UnexpectedFileTruncationFailure, - Unimplemented, - OperationAborted, - BrokenPipe, - NoSpaceLeft, - NotLazy, - IsAsync, - ImportOutsidePkgPath, - UnknownCpuModel, - UnknownCpuFeature, - InvalidCpuFeatures, - InvalidLlvmCpuFeaturesFormat, - UnknownApplicationBinaryInterface, - ASTUnitFailure, - BadPathName, - SymLinkLoop, - ProcessFdQuotaExceeded, - SystemFdQuotaExceeded, - NoDevice, - DeviceBusy, - UnableToSpawnCCompiler, - CCompilerExitCode, - CCompilerCrashed, - CCompilerCannotFindHeaders, - LibCRuntimeNotFound, - LibCStdLibHeaderNotFound, - LibCKernel32LibNotFound, - UnsupportedArchitecture, - WindowsSdkNotFound, - UnknownDynamicLinkerPath, - TargetHasNoDynamicLinker, - InvalidAbiVersion, - InvalidOperatingSystemVersion, - UnknownClangOption, - NestedResponseFile, - ZigIsTheCCompiler, - FileBusy, - Locked, -}; - -const FILE = std.c.FILE; -const ast = std.zig.ast; -const translate_c = @import("translate_c.zig"); - -/// Args should have a null terminating last arg. -export fn stage2_translate_c( - out_ast: **ast.Tree, - out_errors_ptr: *[*]translate_c.ClangErrMsg, - out_errors_len: *usize, - args_begin: [*]?[*]const u8, - args_end: [*]?[*]const u8, - resources_path: [*:0]const u8, -) Error { - var errors: []translate_c.ClangErrMsg = &[0]translate_c.ClangErrMsg{}; - out_ast.* = translate_c.translate(std.heap.c_allocator, args_begin, args_end, &errors, resources_path) catch |err| switch (err) { - error.SemanticAnalyzeFail => { - out_errors_ptr.* = errors.ptr; - out_errors_len.* = errors.len; - return .CCompileErrors; - }, - error.ASTUnitFailure => return .ASTUnitFailure, - error.OutOfMemory => return .OutOfMemory, - }; - return .None; -} - -export fn stage2_free_clang_errors(errors_ptr: [*]translate_c.ClangErrMsg, errors_len: usize) void { - translate_c.freeErrors(errors_ptr[0..errors_len]); -} - -export fn stage2_render_ast(tree: *ast.Tree, output_file: *FILE) Error { - const c_out_stream = std.io.cOutStream(output_file); - _ = std.zig.render(std.heap.c_allocator, c_out_stream, tree) catch |e| switch (e) { - error.WouldBlock => unreachable, // stage1 opens stuff in exclusively blocking mode - error.NotOpenForWriting => unreachable, - error.SystemResources => return .SystemResources, - error.OperationAborted => return .OperationAborted, - error.BrokenPipe => return .BrokenPipe, - error.DiskQuota => return .DiskQuota, - error.FileTooBig => return .FileTooBig, - error.NoSpaceLeft => return .NoSpaceLeft, - error.AccessDenied => return .AccessDenied, - error.OutOfMemory => return .OutOfMemory, - error.Unexpected => return .Unexpected, - error.InputOutput => return .FileSystem, - }; - return .None; -} - -export fn stage2_fmt(argc: c_int, argv: [*]const [*:0]const u8) c_int { - if (std.debug.runtime_safety) { - fmtMain(argc, argv) catch unreachable; - } else { - fmtMain(argc, argv) catch |e| { - std.debug.warn("{}\n", .{@errorName(e)}); - return -1; - }; - } - return 0; -} - -fn argvToArrayList(allocator: *Allocator, argc: c_int, argv: [*]const [*:0]const u8) !ArrayList([]const u8) { - var args_list = std.ArrayList([]const u8).init(allocator); - const argc_usize = @intCast(usize, argc); - var arg_i: usize = 0; - while (arg_i < argc_usize) : (arg_i += 1) { - try args_list.append(mem.spanZ(argv[arg_i])); - } - - return args_list; -} - -fn fmtMain(argc: c_int, argv: [*]const [*:0]const u8) !void { - const allocator = std.heap.c_allocator; - - var args_list = try argvToArrayList(allocator, argc, argv); - defer args_list.deinit(); - - const args = args_list.span()[2..]; - return self_hosted_main.cmdFmt(allocator, args); -} - -export fn stage2_DepTokenizer_init(input: [*]const u8, len: usize) stage2_DepTokenizer { - const t = std.heap.c_allocator.create(DepTokenizer) catch @panic("failed to create .d tokenizer"); - t.* = DepTokenizer.init(std.heap.c_allocator, input[0..len]); - return stage2_DepTokenizer{ - .handle = t, - }; -} - -export fn stage2_DepTokenizer_deinit(self: *stage2_DepTokenizer) void { - self.handle.deinit(); -} - -export fn stage2_DepTokenizer_next(self: *stage2_DepTokenizer) stage2_DepNextResult { - const otoken = self.handle.next() catch { - const textz = std.ArrayListSentineled(u8, 0).init(&self.handle.arena.allocator, self.handle.error_text) catch @panic("failed to create .d tokenizer error text"); - return stage2_DepNextResult{ - .type_id = .error_, - .textz = textz.span().ptr, - }; - }; - const token = otoken orelse { - return stage2_DepNextResult{ - .type_id = .null_, - .textz = undefined, - }; - }; - const textz = std.ArrayListSentineled(u8, 0).init(&self.handle.arena.allocator, token.bytes) catch @panic("failed to create .d tokenizer token text"); - return stage2_DepNextResult{ - .type_id = switch (token.id) { - .target => .target, - .prereq => .prereq, - }, - .textz = textz.span().ptr, - }; -} - -const stage2_DepTokenizer = extern struct { - handle: *DepTokenizer, -}; - -const stage2_DepNextResult = extern struct { - type_id: TypeId, - - // when type_id == error --> error text - // when type_id == null --> undefined - // when type_id == target --> target pathname - // when type_id == prereq --> prereq pathname - textz: [*]const u8, - - const TypeId = extern enum { - error_, - null_, - target, - prereq, - }; -}; - -// ABI warning -export fn stage2_attach_segfault_handler() void { - if (std.debug.runtime_safety and std.debug.have_segfault_handling_support) { - std.debug.attachSegfaultHandler(); - } -} - -// ABI warning -export fn stage2_progress_create() *std.Progress { - const ptr = std.heap.c_allocator.create(std.Progress) catch @panic("out of memory"); - ptr.* = std.Progress{}; - return ptr; -} - -// ABI warning -export fn stage2_progress_destroy(progress: *std.Progress) void { - std.heap.c_allocator.destroy(progress); -} - -// ABI warning -export fn stage2_progress_start_root( - progress: *std.Progress, - name_ptr: [*]const u8, - name_len: usize, - estimated_total_items: usize, -) *std.Progress.Node { - return progress.start( - name_ptr[0..name_len], - if (estimated_total_items == 0) null else estimated_total_items, - ) catch @panic("timer unsupported"); -} - -// ABI warning -export fn stage2_progress_disable_tty(progress: *std.Progress) void { - progress.terminal = null; -} - -// ABI warning -export fn stage2_progress_start( - node: *std.Progress.Node, - name_ptr: [*]const u8, - name_len: usize, - estimated_total_items: usize, -) *std.Progress.Node { - const child_node = std.heap.c_allocator.create(std.Progress.Node) catch @panic("out of memory"); - child_node.* = node.start( - name_ptr[0..name_len], - if (estimated_total_items == 0) null else estimated_total_items, - ); - child_node.activate(); - return child_node; -} - -// ABI warning -export fn stage2_progress_end(node: *std.Progress.Node) void { - node.end(); - if (&node.context.root != node) { - std.heap.c_allocator.destroy(node); - } -} - -// ABI warning -export fn stage2_progress_complete_one(node: *std.Progress.Node) void { - node.completeOne(); -} - -// ABI warning -export fn stage2_progress_update_node(node: *std.Progress.Node, done_count: usize, total_count: usize) void { - node.completed_items = done_count; - node.estimated_total_items = total_count; - node.activate(); - node.context.maybeRefresh(); -} - -fn detectNativeCpuWithLLVM( - arch: Target.Cpu.Arch, - llvm_cpu_name_z: ?[*:0]const u8, - llvm_cpu_features_opt: ?[*:0]const u8, -) !Target.Cpu { - var result = Target.Cpu.baseline(arch); - - if (llvm_cpu_name_z) |cpu_name_z| { - const llvm_cpu_name = mem.spanZ(cpu_name_z); - - for (arch.allCpuModels()) |model| { - const this_llvm_name = model.llvm_name orelse continue; - if (mem.eql(u8, this_llvm_name, llvm_cpu_name)) { - // Here we use the non-dependencies-populated set, - // so that subtracting features later in this function - // affect the prepopulated set. - result = Target.Cpu{ - .arch = arch, - .model = model, - .features = model.features, - }; - break; - } - } - } - - const all_features = arch.allFeaturesList(); - - if (llvm_cpu_features_opt) |llvm_cpu_features| { - var it = mem.tokenize(mem.spanZ(llvm_cpu_features), ","); - while (it.next()) |decorated_llvm_feat| { - var op: enum { - add, - sub, - } = undefined; - var llvm_feat: []const u8 = undefined; - if (mem.startsWith(u8, decorated_llvm_feat, "+")) { - op = .add; - llvm_feat = decorated_llvm_feat[1..]; - } else if (mem.startsWith(u8, decorated_llvm_feat, "-")) { - op = .sub; - llvm_feat = decorated_llvm_feat[1..]; - } else { - return error.InvalidLlvmCpuFeaturesFormat; - } - for (all_features) |feature, index_usize| { - const this_llvm_name = feature.llvm_name orelse continue; - if (mem.eql(u8, llvm_feat, this_llvm_name)) { - const index = @intCast(Target.Cpu.Feature.Set.Index, index_usize); - switch (op) { - .add => result.features.addFeature(index), - .sub => result.features.removeFeature(index), - } - break; - } - } - } - } - - result.features.populateDependencies(all_features); - return result; -} - -export fn stage2_env(argc: c_int, argv: [*]const [*:0]const u8) c_int { - const allocator = std.heap.c_allocator; - - var args_list = argvToArrayList(allocator, argc, argv) catch |err| { - std.debug.print("unable to parse arguments: {}\n", .{@errorName(err)}); - return -1; - }; - defer args_list.deinit(); - - const args = args_list.span()[2..]; - - @import("print_env.zig").cmdEnv(allocator, args, std.io.getStdOut().outStream()) catch |err| { - std.debug.print("unable to print info: {}\n", .{@errorName(err)}); - return -1; - }; - - return 0; -} - -export fn stage2_cc(argc: c_int, argv: [*]const [*:0]const u8, is_cpp: bool) c_int { - const allocator = std.heap.c_allocator; - - var args_list = argvToArrayList(allocator, argc, argv) catch |err| { - std.debug.print("unable to parse arguments: {}\n", .{@errorName(err)}); - return -1; - }; - defer args_list.deinit(); - - self_hosted_main.buildOutputType(allocator, allocator, args_list.items, if (is_cpp) .cpp else .cc) catch |err| { - std.debug.print("zig cc failure: {}\n", .{@errorName(err)}); - return -1; - }; - - return 0; -} - -// ABI warning -export fn stage2_cmd_targets( - zig_triple: ?[*:0]const u8, - mcpu: ?[*:0]const u8, - dynamic_linker: ?[*:0]const u8, -) c_int { - cmdTargets(zig_triple, mcpu, dynamic_linker) catch |err| { - std.debug.warn("unable to list targets: {}\n", .{@errorName(err)}); - return -1; - }; - return 0; -} - -fn cmdTargets( - zig_triple_oz: ?[*:0]const u8, - mcpu_oz: ?[*:0]const u8, - dynamic_linker_oz: ?[*:0]const u8, -) !void { - const cross_target = try stage2CrossTarget(zig_triple_oz, mcpu_oz, dynamic_linker_oz); - var dynamic_linker: ?[*:0]u8 = null; - const target = try crossTargetToTarget(cross_target, &dynamic_linker); - return @import("print_targets.zig").cmdTargets( - std.heap.c_allocator, - &[0][]u8{}, - std.io.getStdOut().outStream(), - target, - ); -} - -// ABI warning -export fn stage2_target_parse( - target: *Stage2Target, - zig_triple: ?[*:0]const u8, - mcpu: ?[*:0]const u8, - dynamic_linker: ?[*:0]const u8, -) Error { - stage2TargetParse(target, zig_triple, mcpu, dynamic_linker) catch |err| switch (err) { - error.OutOfMemory => return .OutOfMemory, - error.UnknownArchitecture => return .UnknownArchitecture, - error.UnknownOperatingSystem => return .UnknownOperatingSystem, - error.UnknownApplicationBinaryInterface => return .UnknownApplicationBinaryInterface, - error.MissingOperatingSystem => return .MissingOperatingSystem, - error.InvalidLlvmCpuFeaturesFormat => return .InvalidLlvmCpuFeaturesFormat, - error.UnexpectedExtraField => return .SemanticAnalyzeFail, - error.InvalidAbiVersion => return .InvalidAbiVersion, - error.InvalidOperatingSystemVersion => return .InvalidOperatingSystemVersion, - error.FileSystem => return .FileSystem, - error.SymLinkLoop => return .SymLinkLoop, - error.SystemResources => return .SystemResources, - error.ProcessFdQuotaExceeded => return .ProcessFdQuotaExceeded, - error.SystemFdQuotaExceeded => return .SystemFdQuotaExceeded, - error.DeviceBusy => return .DeviceBusy, - }; - return .None; -} - -fn stage2CrossTarget( - zig_triple_oz: ?[*:0]const u8, - mcpu_oz: ?[*:0]const u8, - dynamic_linker_oz: ?[*:0]const u8, -) !CrossTarget { - const mcpu = mem.spanZ(mcpu_oz); - const dynamic_linker = mem.spanZ(dynamic_linker_oz); - var diags: CrossTarget.ParseOptions.Diagnostics = .{}; - const target: CrossTarget = CrossTarget.parse(.{ - .arch_os_abi = mem.spanZ(zig_triple_oz) orelse "native", - .cpu_features = mcpu, - .dynamic_linker = dynamic_linker, - .diagnostics = &diags, - }) catch |err| switch (err) { - error.UnknownCpuModel => { - std.debug.warn("Unknown CPU: '{}'\nAvailable CPUs for architecture '{}':\n", .{ - diags.cpu_name.?, - @tagName(diags.arch.?), - }); - for (diags.arch.?.allCpuModels()) |cpu| { - std.debug.warn(" {}\n", .{cpu.name}); - } - process.exit(1); - }, - error.UnknownCpuFeature => { - std.debug.warn( - \\Unknown CPU feature: '{}' - \\Available CPU features for architecture '{}': - \\ - , .{ - diags.unknown_feature_name, - @tagName(diags.arch.?), - }); - for (diags.arch.?.allFeaturesList()) |feature| { - std.debug.warn(" {}: {}\n", .{ feature.name, feature.description }); - } - process.exit(1); - }, - else => |e| return e, - }; - - return target; -} - -fn stage2TargetParse( - stage1_target: *Stage2Target, - zig_triple_oz: ?[*:0]const u8, - mcpu_oz: ?[*:0]const u8, - dynamic_linker_oz: ?[*:0]const u8, -) !void { - const target = try stage2CrossTarget(zig_triple_oz, mcpu_oz, dynamic_linker_oz); - try stage1_target.fromTarget(target); -} - -// ABI warning -const Stage2LibCInstallation = extern struct { - include_dir: [*]const u8, - include_dir_len: usize, - sys_include_dir: [*]const u8, - sys_include_dir_len: usize, - crt_dir: [*]const u8, - crt_dir_len: usize, - msvc_lib_dir: [*]const u8, - msvc_lib_dir_len: usize, - kernel32_lib_dir: [*]const u8, - kernel32_lib_dir_len: usize, - - fn initFromStage2(self: *Stage2LibCInstallation, libc: LibCInstallation) void { - if (libc.include_dir) |s| { - self.include_dir = s.ptr; - self.include_dir_len = s.len; - } else { - self.include_dir = ""; - self.include_dir_len = 0; - } - if (libc.sys_include_dir) |s| { - self.sys_include_dir = s.ptr; - self.sys_include_dir_len = s.len; - } else { - self.sys_include_dir = ""; - self.sys_include_dir_len = 0; - } - if (libc.crt_dir) |s| { - self.crt_dir = s.ptr; - self.crt_dir_len = s.len; - } else { - self.crt_dir = ""; - self.crt_dir_len = 0; - } - if (libc.msvc_lib_dir) |s| { - self.msvc_lib_dir = s.ptr; - self.msvc_lib_dir_len = s.len; - } else { - self.msvc_lib_dir = ""; - self.msvc_lib_dir_len = 0; - } - if (libc.kernel32_lib_dir) |s| { - self.kernel32_lib_dir = s.ptr; - self.kernel32_lib_dir_len = s.len; - } else { - self.kernel32_lib_dir = ""; - self.kernel32_lib_dir_len = 0; - } - } - - fn toStage2(self: Stage2LibCInstallation) LibCInstallation { - var libc: LibCInstallation = .{}; - if (self.include_dir_len != 0) { - libc.include_dir = self.include_dir[0..self.include_dir_len]; - } - if (self.sys_include_dir_len != 0) { - libc.sys_include_dir = self.sys_include_dir[0..self.sys_include_dir_len]; - } - if (self.crt_dir_len != 0) { - libc.crt_dir = self.crt_dir[0..self.crt_dir_len]; - } - if (self.msvc_lib_dir_len != 0) { - libc.msvc_lib_dir = self.msvc_lib_dir[0..self.msvc_lib_dir_len]; - } - if (self.kernel32_lib_dir_len != 0) { - libc.kernel32_lib_dir = self.kernel32_lib_dir[0..self.kernel32_lib_dir_len]; - } - return libc; - } -}; - -// ABI warning -export fn stage2_libc_parse(stage1_libc: *Stage2LibCInstallation, libc_file_z: [*:0]const u8) Error { - const libc_file = mem.spanZ(libc_file_z); - var libc = LibCInstallation.parse(std.heap.c_allocator, libc_file) catch |err| switch (err) { - error.ParseError => return .SemanticAnalyzeFail, - error.FileTooBig => return .FileTooBig, - error.InputOutput => return .FileSystem, - error.NoSpaceLeft => return .NoSpaceLeft, - error.AccessDenied => return .AccessDenied, - error.BrokenPipe => return .BrokenPipe, - error.SystemResources => return .SystemResources, - error.OperationAborted => return .OperationAborted, - error.WouldBlock => unreachable, - error.NotOpenForReading => unreachable, - error.Unexpected => return .Unexpected, - error.IsDir => return .IsDir, - error.ConnectionResetByPeer => unreachable, - error.ConnectionTimedOut => unreachable, - error.OutOfMemory => return .OutOfMemory, - error.Unseekable => unreachable, - error.SharingViolation => return .SharingViolation, - error.PathAlreadyExists => unreachable, - error.FileNotFound => return .FileNotFound, - error.PipeBusy => return .PipeBusy, - error.NameTooLong => return .PathTooLong, - error.InvalidUtf8 => return .BadPathName, - error.BadPathName => return .BadPathName, - error.SymLinkLoop => return .SymLinkLoop, - error.ProcessFdQuotaExceeded => return .ProcessFdQuotaExceeded, - error.SystemFdQuotaExceeded => return .SystemFdQuotaExceeded, - error.NoDevice => return .NoDevice, - error.NotDir => return .NotDir, - error.DeviceBusy => return .DeviceBusy, - error.FileLocksNotSupported => unreachable, - }; - stage1_libc.initFromStage2(libc); - return .None; -} - -// ABI warning -export fn stage2_libc_find_native(stage1_libc: *Stage2LibCInstallation) Error { - var libc = LibCInstallation.findNative(.{ - .allocator = std.heap.c_allocator, - .verbose = true, - }) catch |err| switch (err) { - error.OutOfMemory => return .OutOfMemory, - error.FileSystem => return .FileSystem, - error.UnableToSpawnCCompiler => return .UnableToSpawnCCompiler, - error.CCompilerExitCode => return .CCompilerExitCode, - error.CCompilerCrashed => return .CCompilerCrashed, - error.CCompilerCannotFindHeaders => return .CCompilerCannotFindHeaders, - error.LibCRuntimeNotFound => return .LibCRuntimeNotFound, - error.LibCStdLibHeaderNotFound => return .LibCStdLibHeaderNotFound, - error.LibCKernel32LibNotFound => return .LibCKernel32LibNotFound, - error.UnsupportedArchitecture => return .UnsupportedArchitecture, - error.WindowsSdkNotFound => return .WindowsSdkNotFound, - error.ZigIsTheCCompiler => return .ZigIsTheCCompiler, - }; - stage1_libc.initFromStage2(libc); - return .None; -} - -// ABI warning -export fn stage2_libc_render(stage1_libc: *Stage2LibCInstallation, output_file: *FILE) Error { - var libc = stage1_libc.toStage2(); - const c_out_stream = std.io.cOutStream(output_file); - libc.render(c_out_stream) catch |err| switch (err) { - error.WouldBlock => unreachable, // stage1 opens stuff in exclusively blocking mode - error.NotOpenForWriting => unreachable, - error.SystemResources => return .SystemResources, - error.OperationAborted => return .OperationAborted, - error.BrokenPipe => return .BrokenPipe, - error.DiskQuota => return .DiskQuota, - error.FileTooBig => return .FileTooBig, - error.NoSpaceLeft => return .NoSpaceLeft, - error.AccessDenied => return .AccessDenied, - error.Unexpected => return .Unexpected, - error.InputOutput => return .FileSystem, - }; - return .None; -} - -// ABI warning -const Stage2Target = extern struct { - arch: c_int, - vendor: c_int, - - abi: c_int, - os: c_int, - - is_native_os: bool, - is_native_cpu: bool, - - glibc_or_darwin_version: ?*Stage2SemVer, - - llvm_cpu_name: ?[*:0]const u8, - llvm_cpu_features: ?[*:0]const u8, - cpu_builtin_str: ?[*:0]const u8, - cache_hash: ?[*:0]const u8, - cache_hash_len: usize, - os_builtin_str: ?[*:0]const u8, - - dynamic_linker: ?[*:0]const u8, - standard_dynamic_linker_path: ?[*:0]const u8, - - llvm_cpu_features_asm_ptr: [*]const [*:0]const u8, - llvm_cpu_features_asm_len: usize, - - fn fromTarget(self: *Stage2Target, cross_target: CrossTarget) !void { - const allocator = std.heap.c_allocator; - - var dynamic_linker: ?[*:0]u8 = null; - const target = try crossTargetToTarget(cross_target, &dynamic_linker); - - var cache_hash = try std.ArrayListSentineled(u8, 0).allocPrint(allocator, "{}\n{}\n", .{ - target.cpu.model.name, - target.cpu.features.asBytes(), - }); - defer cache_hash.deinit(); - - const generic_arch_name = target.cpu.arch.genericName(); - var cpu_builtin_str_buffer = try std.ArrayListSentineled(u8, 0).allocPrint(allocator, - \\Cpu{{ - \\ .arch = .{}, - \\ .model = &Target.{}.cpu.{}, - \\ .features = Target.{}.featureSet(&[_]Target.{}.Feature{{ - \\ - , .{ - @tagName(target.cpu.arch), - generic_arch_name, - target.cpu.model.name, - generic_arch_name, - generic_arch_name, - }); - defer cpu_builtin_str_buffer.deinit(); - - var llvm_features_buffer = try std.ArrayListSentineled(u8, 0).initSize(allocator, 0); - defer llvm_features_buffer.deinit(); - - // Unfortunately we have to do the work twice, because Clang does not support - // the same command line parameters for CPU features when assembling code as it does - // when compiling C code. - var asm_features_list = std.ArrayList([*:0]const u8).init(allocator); - defer asm_features_list.deinit(); - - for (target.cpu.arch.allFeaturesList()) |feature, index_usize| { - const index = @intCast(Target.Cpu.Feature.Set.Index, index_usize); - const is_enabled = target.cpu.features.isEnabled(index); - - if (feature.llvm_name) |llvm_name| { - const plus_or_minus = "-+"[@boolToInt(is_enabled)]; - try llvm_features_buffer.append(plus_or_minus); - try llvm_features_buffer.appendSlice(llvm_name); - try llvm_features_buffer.appendSlice(","); - } - - if (is_enabled) { - // TODO some kind of "zig identifier escape" function rather than - // unconditionally using @"" syntax - try cpu_builtin_str_buffer.appendSlice(" .@\""); - try cpu_builtin_str_buffer.appendSlice(feature.name); - try cpu_builtin_str_buffer.appendSlice("\",\n"); - } - } - - switch (target.cpu.arch) { - .riscv32, .riscv64 => { - if (std.Target.riscv.featureSetHas(target.cpu.features, .relax)) { - try asm_features_list.append("-mrelax"); - } else { - try asm_features_list.append("-mno-relax"); - } - }, - else => { - // TODO - // Argh, why doesn't the assembler accept the list of CPU features?! - // I don't see a way to do this other than hard coding everything. - }, - } - - try cpu_builtin_str_buffer.appendSlice( - \\ }), - \\}; - \\ - ); - - assert(mem.endsWith(u8, llvm_features_buffer.span(), ",")); - llvm_features_buffer.shrink(llvm_features_buffer.len() - 1); - - var os_builtin_str_buffer = try std.ArrayListSentineled(u8, 0).allocPrint(allocator, - \\Os{{ - \\ .tag = .{}, - \\ .version_range = .{{ - , .{@tagName(target.os.tag)}); - defer os_builtin_str_buffer.deinit(); - - // We'll re-use the OS version range builtin string for the cache hash. - const os_builtin_str_ver_start_index = os_builtin_str_buffer.len(); - - @setEvalBranchQuota(2000); - switch (target.os.tag) { - .freestanding, - .ananas, - .cloudabi, - .dragonfly, - .fuchsia, - .ios, - .kfreebsd, - .lv2, - .solaris, - .haiku, - .minix, - .rtems, - .nacl, - .cnk, - .aix, - .cuda, - .nvcl, - .amdhsa, - .ps4, - .elfiamcu, - .tvos, - .watchos, - .mesa3d, - .contiki, - .amdpal, - .hermit, - .hurd, - .wasi, - .emscripten, - .uefi, - .other, - => try os_builtin_str_buffer.appendSlice(" .none = {} }\n"), - - .freebsd, - .macosx, - .netbsd, - .openbsd, - => try os_builtin_str_buffer.outStream().print( - \\ .semver = .{{ - \\ .min = .{{ - \\ .major = {}, - \\ .minor = {}, - \\ .patch = {}, - \\ }}, - \\ .max = .{{ - \\ .major = {}, - \\ .minor = {}, - \\ .patch = {}, - \\ }}, - \\ }}}}, - \\ - , .{ - target.os.version_range.semver.min.major, - target.os.version_range.semver.min.minor, - target.os.version_range.semver.min.patch, - - target.os.version_range.semver.max.major, - target.os.version_range.semver.max.minor, - target.os.version_range.semver.max.patch, - }), - - .linux => try os_builtin_str_buffer.outStream().print( - \\ .linux = .{{ - \\ .range = .{{ - \\ .min = .{{ - \\ .major = {}, - \\ .minor = {}, - \\ .patch = {}, - \\ }}, - \\ .max = .{{ - \\ .major = {}, - \\ .minor = {}, - \\ .patch = {}, - \\ }}, - \\ }}, - \\ .glibc = .{{ - \\ .major = {}, - \\ .minor = {}, - \\ .patch = {}, - \\ }}, - \\ }}}}, - \\ - , .{ - target.os.version_range.linux.range.min.major, - target.os.version_range.linux.range.min.minor, - target.os.version_range.linux.range.min.patch, - - target.os.version_range.linux.range.max.major, - target.os.version_range.linux.range.max.minor, - target.os.version_range.linux.range.max.patch, - - target.os.version_range.linux.glibc.major, - target.os.version_range.linux.glibc.minor, - target.os.version_range.linux.glibc.patch, - }), - - .windows => try os_builtin_str_buffer.outStream().print( - \\ .windows = .{{ - \\ .min = {s}, - \\ .max = {s}, - \\ }}}}, - \\ - , .{ - target.os.version_range.windows.min, - target.os.version_range.windows.max, - }), - } - try os_builtin_str_buffer.appendSlice("};\n"); - - try cache_hash.appendSlice( - os_builtin_str_buffer.span()[os_builtin_str_ver_start_index..os_builtin_str_buffer.len()], - ); - - const glibc_or_darwin_version = blk: { - if (target.isGnuLibC()) { - const stage1_glibc = try std.heap.c_allocator.create(Stage2SemVer); - const stage2_glibc = target.os.version_range.linux.glibc; - stage1_glibc.* = .{ - .major = stage2_glibc.major, - .minor = stage2_glibc.minor, - .patch = stage2_glibc.patch, - }; - break :blk stage1_glibc; - } else if (target.isDarwin()) { - const stage1_semver = try std.heap.c_allocator.create(Stage2SemVer); - const stage2_semver = target.os.version_range.semver.min; - stage1_semver.* = .{ - .major = stage2_semver.major, - .minor = stage2_semver.minor, - .patch = stage2_semver.patch, - }; - break :blk stage1_semver; - } else { - break :blk null; - } - }; - - const std_dl = target.standardDynamicLinkerPath(); - const std_dl_z = if (std_dl.get()) |dl| - (try mem.dupeZ(std.heap.c_allocator, u8, dl)).ptr - else - null; - - const cache_hash_slice = cache_hash.toOwnedSlice(); - const asm_features = asm_features_list.toOwnedSlice(); - self.* = .{ - .arch = @enumToInt(target.cpu.arch) + 1, // skip over ZigLLVM_UnknownArch - .vendor = 0, - .os = @enumToInt(target.os.tag), - .abi = @enumToInt(target.abi), - .llvm_cpu_name = if (target.cpu.model.llvm_name) |s| s.ptr else null, - .llvm_cpu_features = llvm_features_buffer.toOwnedSlice().ptr, - .llvm_cpu_features_asm_ptr = asm_features.ptr, - .llvm_cpu_features_asm_len = asm_features.len, - .cpu_builtin_str = cpu_builtin_str_buffer.toOwnedSlice().ptr, - .os_builtin_str = os_builtin_str_buffer.toOwnedSlice().ptr, - .cache_hash = cache_hash_slice.ptr, - .cache_hash_len = cache_hash_slice.len, - .is_native_os = cross_target.isNativeOs(), - .is_native_cpu = cross_target.isNativeCpu(), - .glibc_or_darwin_version = glibc_or_darwin_version, - .dynamic_linker = dynamic_linker, - .standard_dynamic_linker_path = std_dl_z, - }; - } -}; - -fn enumInt(comptime Enum: type, int: c_int) Enum { - return @intToEnum(Enum, @intCast(@TagType(Enum), int)); -} - -fn crossTargetToTarget(cross_target: CrossTarget, dynamic_linker_ptr: *?[*:0]u8) !Target { - var info = try std.zig.system.NativeTargetInfo.detect(std.heap.c_allocator, cross_target); - if (info.cpu_detection_unimplemented) { - // TODO We want to just use detected_info.target but implementing - // CPU model & feature detection is todo so here we rely on LLVM. - const llvm = @import("llvm.zig"); - const llvm_cpu_name = llvm.GetHostCPUName(); - const llvm_cpu_features = llvm.GetNativeFeatures(); - const arch = std.Target.current.cpu.arch; - info.target.cpu = try detectNativeCpuWithLLVM(arch, llvm_cpu_name, llvm_cpu_features); - cross_target.updateCpuFeatures(&info.target.cpu.features); - info.target.cpu.arch = cross_target.getCpuArch(); - } - if (info.dynamic_linker.get()) |dl| { - dynamic_linker_ptr.* = try mem.dupeZ(std.heap.c_allocator, u8, dl); - } else { - dynamic_linker_ptr.* = null; - } - return info.target; -} - -// ABI warning -const Stage2SemVer = extern struct { - major: u32, - minor: u32, - patch: u32, -}; - -// ABI warning -const Stage2NativePaths = extern struct { - include_dirs_ptr: [*][*:0]u8, - include_dirs_len: usize, - lib_dirs_ptr: [*][*:0]u8, - lib_dirs_len: usize, - rpaths_ptr: [*][*:0]u8, - rpaths_len: usize, - warnings_ptr: [*][*:0]u8, - warnings_len: usize, -}; -// ABI warning -export fn stage2_detect_native_paths(stage1_paths: *Stage2NativePaths) Error { - stage2DetectNativePaths(stage1_paths) catch |err| switch (err) { - error.OutOfMemory => return .OutOfMemory, - }; - return .None; -} - -fn stage2DetectNativePaths(stage1_paths: *Stage2NativePaths) !void { - var paths = try std.zig.system.NativePaths.detect(std.heap.c_allocator); - errdefer paths.deinit(); - - try convertSlice(paths.include_dirs.span(), &stage1_paths.include_dirs_ptr, &stage1_paths.include_dirs_len); - try convertSlice(paths.lib_dirs.span(), &stage1_paths.lib_dirs_ptr, &stage1_paths.lib_dirs_len); - try convertSlice(paths.rpaths.span(), &stage1_paths.rpaths_ptr, &stage1_paths.rpaths_len); - try convertSlice(paths.warnings.span(), &stage1_paths.warnings_ptr, &stage1_paths.warnings_len); -} - -fn convertSlice(slice: [][:0]u8, ptr: *[*][*:0]u8, len: *usize) !void { - len.* = slice.len; - const new_slice = try std.heap.c_allocator.alloc([*:0]u8, slice.len); - for (slice) |item, i| { - new_slice[i] = item.ptr; - } - ptr.* = new_slice.ptr; -} - -export const stage2_is_zig0 = false; diff --git a/src/all_types.hpp b/src/all_types.hpp index 1fa04f2b79..7b8ad57483 100644 --- a/src/all_types.hpp +++ b/src/all_types.hpp @@ -10,7 +10,6 @@ #include "list.hpp" #include "buffer.hpp" -#include "cache_hash.hpp" #include "zig_llvm.h" #include "hash_map.hpp" #include "errmsg.hpp" @@ -1639,8 +1638,6 @@ struct ZigType { size_t abi_size; // Number of bits of information in this type. Known after ResolveStatusSizeKnown. size_t size_in_bits; - - bool gen_h_loop_flag; }; enum FnAnalState { @@ -1976,67 +1973,16 @@ struct TimeEvent { const char *name; }; -enum BuildMode { - BuildModeDebug, - BuildModeFastRelease, - BuildModeSafeRelease, - BuildModeSmallRelease, -}; - -enum CodeModel { - CodeModelDefault, - CodeModelTiny, - CodeModelSmall, - CodeModelKernel, - CodeModelMedium, - CodeModelLarge, -}; - -struct LinkLib { - Buf *name; - Buf *path; - ZigList symbols; // the list of symbols that we depend on from this lib - bool provided_explicitly; -}; - -enum ValgrindSupport { - ValgrindSupportAuto, - ValgrindSupportDisabled, - ValgrindSupportEnabled, -}; - -enum WantPIC { - WantPICAuto, - WantPICDisabled, - WantPICEnabled, -}; - -enum WantStackCheck { - WantStackCheckAuto, - WantStackCheckDisabled, - WantStackCheckEnabled, -}; - -enum WantCSanitize { - WantCSanitizeAuto, - WantCSanitizeDisabled, - WantCSanitizeEnabled, -}; - -enum OptionalBool { - OptionalBoolNull, - OptionalBoolFalse, - OptionalBoolTrue, -}; - struct CFile { ZigList args; const char *source_path; const char *preprocessor_only_basename; }; -// When adding fields, check if they should be added to the hash computation in build_with_cache struct CodeGen { + // Other code depends on this being first. + ZigStage1 stage1; + // arena allocator destroyed just prior to codegen emit heap::ArenaAllocator *pass1_arena; @@ -2048,8 +1994,6 @@ struct CodeGen { ZigLLVMDIBuilder *dbuilder; ZigLLVMDICompileUnit *compile_unit; ZigLLVMDIFile *compile_unit_file; - LinkLib *libc_link_lib; - LinkLib *libcpp_link_lib; LLVMTargetDataRef target_data_ref; LLVMTargetMachineRef target_machine; ZigLLVMDIFile *dummy_di_file; @@ -2104,7 +2048,6 @@ struct CodeGen { ZigList inline_fns; ZigList test_fns; ZigList errors_by_index; - ZigList caches_to_release; size_t largest_err_name_len; ZigList type_resolve_stack; @@ -2173,7 +2116,6 @@ struct CodeGen { Buf llvm_triple_str; Buf global_asm; Buf o_file_output_path; - Buf bin_file_output_path; Buf asm_file_output_path; Buf llvm_ir_file_output_path; Buf *cache_dir; @@ -2184,7 +2126,7 @@ struct CodeGen { const char **libc_include_dir_list; size_t libc_include_dir_len; - Buf *zig_c_headers_dir; // Cannot be overridden; derived from zig_lib_dir. + Buf *builtin_zig_path; Buf *zig_std_special_dir; // Cannot be overridden; derived from zig_lib_dir. IrInstSrc *invalid_inst_src; @@ -2206,18 +2148,9 @@ struct CodeGen { Stage2ProgressNode *main_progress_node; Stage2ProgressNode *sub_progress_node; - WantPIC want_pic; - WantStackCheck want_stack_check; - WantCSanitize want_sanitize_c; - CacheHash cache_hash; ErrColor err_color; uint32_t next_unresolved_index; unsigned pointer_size_bytes; - uint32_t target_os_index; - uint32_t target_arch_index; - uint32_t target_sub_arch_index; - uint32_t target_abi_index; - uint32_t target_oformat_index; bool is_big_endian; bool have_c_main; bool have_winmain; @@ -2226,9 +2159,6 @@ struct CodeGen { bool have_wwinmain_crt_startup; bool have_dllmain_crt_startup; bool have_err_ret_tracing; - bool link_eh_frame_hdr; - bool c_want_stdint; - bool c_want_stdbool; bool verbose_tokenize; bool verbose_ast; bool verbose_link; @@ -2239,61 +2169,24 @@ struct CodeGen { bool verbose_llvm_cpu_features; bool error_during_imports; bool generate_error_name_table; - bool enable_cache; // mutually exclusive with output_dir bool enable_time_report; bool enable_stack_report; - bool system_linker_hack; bool reported_bad_link_libc_error; - bool is_dynamic; // shared library rather than static library. dynamic musl rather than static musl. bool need_frame_size_prefix_data; - bool disable_c_depfile; - - //////////////////////////// Participates in Input Parameter Cache Hash - /////// Note: there is a separate cache hash for builtin.zig, when adding fields, - /////// consider if they need to go into both. - ZigList link_libs_list; - // add -framework [name] args to linker - ZigList darwin_frameworks; - // add -rpath [name] args to linker - ZigList rpath_list; - ZigList forbidden_libs; - ZigList link_objects; - ZigList assembly_files; - ZigList c_source_files; - ZigList lib_dirs; - ZigList framework_dirs; - - Stage2LibCInstallation *libc; - - bool is_versioned; - size_t version_major; - size_t version_minor; - size_t version_patch; - const char *linker_script; - size_t stack_size_override; + bool link_libc; + bool link_libcpp; BuildMode build_mode; - OutType out_type; const ZigTarget *zig_target; TargetSubsystem subsystem; // careful using this directly; see detect_subsystem - ValgrindSupport valgrind_support; CodeModel code_model; - OptionalBool linker_gc_sections; - OptionalBool linker_allow_shlib_undefined; - OptionalBool linker_bind_global_refs_locally; bool strip_debug_symbols; bool is_test_build; bool is_single_threaded; - bool want_single_threaded; - bool linker_rdynamic; - bool each_lib_rpath; - bool is_dummy_so; - bool disable_gen_h; - bool bundle_compiler_rt; bool have_pic; - bool have_dynamic_link; // this is whether the final thing will be dynamically linked. see also is_dynamic + bool link_mode_dynamic; + bool dll_export_fns; bool have_stack_probing; - bool have_sanitize_c; bool function_sections; bool enable_dump_analysis; bool enable_doc_generation; @@ -2301,23 +2194,13 @@ struct CodeGen { bool emit_asm; bool emit_llvm_ir; bool test_is_evented; - bool linker_z_nodelete; - bool linker_z_defs; + bool valgrind_enabled; Buf *root_out_name; Buf *test_filter; Buf *test_name_prefix; Buf *zig_lib_dir; Buf *zig_std_dir; - Buf *version_script_path; - Buf *override_soname; - Buf *linker_optimization; - - const char **llvm_argv; - size_t llvm_argv_len; - - const char **clang_argv; - size_t clang_argv_len; }; struct ZigVar { diff --git a/src/analyze.cpp b/src/analyze.cpp index b97423da73..ea19d81995 100644 --- a/src/analyze.cpp +++ b/src/analyze.cpp @@ -3496,7 +3496,7 @@ void add_var_export(CodeGen *g, ZigVar *var, const char *symbol_name, GlobalLink } void add_fn_export(CodeGen *g, ZigFn *fn_table_entry, const char *symbol_name, GlobalLinkageId linkage, CallingConvention cc) { - if (cc == CallingConventionC && strcmp(symbol_name, "main") == 0 && g->libc_link_lib != nullptr) { + if (cc == CallingConventionC && strcmp(symbol_name, "main") == 0 && g->link_libc) { g->have_c_main = true; } else if (cc == CallingConventionStdcall && g->zig_target->os == OsWindows) { if (strcmp(symbol_name, "WinMain") == 0) { @@ -7863,40 +7863,6 @@ const char *type_id_name(ZigTypeId id) { zig_unreachable(); } -LinkLib *create_link_lib(Buf *name) { - LinkLib *link_lib = heap::c_allocator.create(); - link_lib->name = name; - return link_lib; -} - -LinkLib *add_link_lib(CodeGen *g, Buf *name) { - bool is_libc = buf_eql_str(name, "c"); - bool is_libcpp = buf_eql_str(name, "c++") || buf_eql_str(name, "c++abi"); - - if (is_libc && g->libc_link_lib != nullptr) - return g->libc_link_lib; - - if (is_libcpp && g->libcpp_link_lib != nullptr) - return g->libcpp_link_lib; - - for (size_t i = 0; i < g->link_libs_list.length; i += 1) { - LinkLib *existing_lib = g->link_libs_list.at(i); - if (buf_eql_buf(existing_lib->name, name)) { - return existing_lib; - } - } - - LinkLib *link_lib = create_link_lib(name); - g->link_libs_list.append(link_lib); - - if (is_libc) - g->libc_link_lib = link_lib; - if (is_libcpp) - g->libcpp_link_lib = link_lib; - - return link_lib; -} - ZigType *get_align_amt_type(CodeGen *g) { if (g->align_amt_type == nullptr) { // according to LLVM the maximum alignment is 1 << 29. @@ -8017,12 +7983,13 @@ not_integer: return ErrorNone; } -Error file_fetch(CodeGen *g, Buf *resolved_path, Buf *contents) { - if (g->enable_cache) { - return cache_add_file_fetch(&g->cache_hash, resolved_path, contents); - } else { - return os_fetch_file_path(resolved_path, contents); - } +Error file_fetch(CodeGen *g, Buf *resolved_path, Buf *contents_buf) { + size_t len; + const char *contents = stage2_fetch_file(&g->stage1, buf_ptr(resolved_path), buf_len(resolved_path), &len); + if (contents == nullptr) + return ErrorNoMem; + buf_init_from_mem(contents_buf, contents, len); + return ErrorNone; } static X64CABIClass type_windows_abi_x86_64_class(CodeGen *g, ZigType *ty, size_t ty_size) { diff --git a/src/analyze.hpp b/src/analyze.hpp index 0df1a4ba91..07601e6dea 100644 --- a/src/analyze.hpp +++ b/src/analyze.hpp @@ -200,8 +200,6 @@ ZigTypeId type_id_at_index(size_t index); size_t type_id_len(); size_t type_id_index(ZigType *entry); ZigType *get_generic_fn_type(CodeGen *g, FnTypeId *fn_type_id); -LinkLib *create_link_lib(Buf *name); -LinkLib *add_link_lib(CodeGen *codegen, Buf *lib); bool optional_value_is_null(ZigValue *val); uint32_t get_abi_alignment(CodeGen *g, ZigType *type_entry); @@ -256,7 +254,6 @@ Error ensure_const_val_repr(IrAnalyze *ira, CodeGen *codegen, AstNode *source_no void typecheck_panic_fn(CodeGen *g, TldFn *tld_fn, ZigFn *panic_fn); Buf *type_bare_name(ZigType *t); Buf *type_h_name(ZigType *t); -Error create_c_object_cache(CodeGen *g, CacheHash **out_cache_hash, bool verbose); LLVMTypeRef get_llvm_type(CodeGen *g, ZigType *type); ZigLLVMDIType *get_llvm_di_type(CodeGen *g, ZigType *type); diff --git a/src/blake2.h b/src/blake2.h deleted file mode 100644 index 6420c5367a..0000000000 --- a/src/blake2.h +++ /dev/null @@ -1,196 +0,0 @@ -/* - BLAKE2 reference source code package - reference C implementations - - Copyright 2012, Samuel Neves . You may use this under the - terms of the CC0, the OpenSSL Licence, or the Apache Public License 2.0, at - your option. The terms of these licenses can be found at: - - - CC0 1.0 Universal : http://creativecommons.org/publicdomain/zero/1.0 - - OpenSSL license : https://www.openssl.org/source/license.html - - Apache 2.0 : http://www.apache.org/licenses/LICENSE-2.0 - - More information about the BLAKE2 hash function can be found at - https://blake2.net. -*/ -#ifndef BLAKE2_H -#define BLAKE2_H - -#include -#include - -#if defined(_MSC_VER) -#define BLAKE2_PACKED(x) __pragma(pack(push, 1)) x __pragma(pack(pop)) -#else -#define BLAKE2_PACKED(x) x __attribute__((packed)) -#endif - -#if defined(__cplusplus) -extern "C" { -#endif - - enum blake2s_constant - { - BLAKE2S_BLOCKBYTES = 64, - BLAKE2S_OUTBYTES = 32, - BLAKE2S_KEYBYTES = 32, - BLAKE2S_SALTBYTES = 8, - BLAKE2S_PERSONALBYTES = 8 - }; - - enum blake2b_constant - { - BLAKE2B_BLOCKBYTES = 128, - BLAKE2B_OUTBYTES = 64, - BLAKE2B_KEYBYTES = 64, - BLAKE2B_SALTBYTES = 16, - BLAKE2B_PERSONALBYTES = 16 - }; - - typedef struct blake2s_state__ - { - uint32_t h[8]; - uint32_t t[2]; - uint32_t f[2]; - uint8_t buf[BLAKE2S_BLOCKBYTES]; - size_t buflen; - size_t outlen; - uint8_t last_node; - } blake2s_state; - - typedef struct blake2b_state__ - { - uint64_t h[8]; - uint64_t t[2]; - uint64_t f[2]; - uint8_t buf[BLAKE2B_BLOCKBYTES]; - size_t buflen; - size_t outlen; - uint8_t last_node; - } blake2b_state; - - typedef struct blake2sp_state__ - { - blake2s_state S[8][1]; - blake2s_state R[1]; - uint8_t buf[8 * BLAKE2S_BLOCKBYTES]; - size_t buflen; - size_t outlen; - } blake2sp_state; - - typedef struct blake2bp_state__ - { - blake2b_state S[4][1]; - blake2b_state R[1]; - uint8_t buf[4 * BLAKE2B_BLOCKBYTES]; - size_t buflen; - size_t outlen; - } blake2bp_state; - - - BLAKE2_PACKED(struct blake2s_param__ - { - uint8_t digest_length; /* 1 */ - uint8_t key_length; /* 2 */ - uint8_t fanout; /* 3 */ - uint8_t depth; /* 4 */ - uint32_t leaf_length; /* 8 */ - uint32_t node_offset; /* 12 */ - uint16_t xof_length; /* 14 */ - uint8_t node_depth; /* 15 */ - uint8_t inner_length; /* 16 */ - /* uint8_t reserved[0]; */ - uint8_t salt[BLAKE2S_SALTBYTES]; /* 24 */ - uint8_t personal[BLAKE2S_PERSONALBYTES]; /* 32 */ - }); - - typedef struct blake2s_param__ blake2s_param; - - BLAKE2_PACKED(struct blake2b_param__ - { - uint8_t digest_length; /* 1 */ - uint8_t key_length; /* 2 */ - uint8_t fanout; /* 3 */ - uint8_t depth; /* 4 */ - uint32_t leaf_length; /* 8 */ - uint32_t node_offset; /* 12 */ - uint32_t xof_length; /* 16 */ - uint8_t node_depth; /* 17 */ - uint8_t inner_length; /* 18 */ - uint8_t reserved[14]; /* 32 */ - uint8_t salt[BLAKE2B_SALTBYTES]; /* 48 */ - uint8_t personal[BLAKE2B_PERSONALBYTES]; /* 64 */ - }); - - typedef struct blake2b_param__ blake2b_param; - - typedef struct blake2xs_state__ - { - blake2s_state S[1]; - blake2s_param P[1]; - } blake2xs_state; - - typedef struct blake2xb_state__ - { - blake2b_state S[1]; - blake2b_param P[1]; - } blake2xb_state; - - /* Padded structs result in a compile-time error */ - enum { - BLAKE2_DUMMY_1 = 1/(sizeof(blake2s_param) == BLAKE2S_OUTBYTES), - BLAKE2_DUMMY_2 = 1/(sizeof(blake2b_param) == BLAKE2B_OUTBYTES) - }; - - /* Streaming API */ - int blake2s_init( blake2s_state *S, size_t outlen ); - int blake2s_init_key( blake2s_state *S, size_t outlen, const void *key, size_t keylen ); - int blake2s_init_param( blake2s_state *S, const blake2s_param *P ); - int blake2s_update( blake2s_state *S, const void *in, size_t inlen ); - int blake2s_final( blake2s_state *S, void *out, size_t outlen ); - - int blake2b_init( blake2b_state *S, size_t outlen ); - int blake2b_init_key( blake2b_state *S, size_t outlen, const void *key, size_t keylen ); - int blake2b_init_param( blake2b_state *S, const blake2b_param *P ); - int blake2b_update( blake2b_state *S, const void *in, size_t inlen ); - int blake2b_final( blake2b_state *S, void *out, size_t outlen ); - - int blake2sp_init( blake2sp_state *S, size_t outlen ); - int blake2sp_init_key( blake2sp_state *S, size_t outlen, const void *key, size_t keylen ); - int blake2sp_update( blake2sp_state *S, const void *in, size_t inlen ); - int blake2sp_final( blake2sp_state *S, void *out, size_t outlen ); - - int blake2bp_init( blake2bp_state *S, size_t outlen ); - int blake2bp_init_key( blake2bp_state *S, size_t outlen, const void *key, size_t keylen ); - int blake2bp_update( blake2bp_state *S, const void *in, size_t inlen ); - int blake2bp_final( blake2bp_state *S, void *out, size_t outlen ); - - /* Variable output length API */ - int blake2xs_init( blake2xs_state *S, const size_t outlen ); - int blake2xs_init_key( blake2xs_state *S, const size_t outlen, const void *key, size_t keylen ); - int blake2xs_update( blake2xs_state *S, const void *in, size_t inlen ); - int blake2xs_final(blake2xs_state *S, void *out, size_t outlen); - - int blake2xb_init( blake2xb_state *S, const size_t outlen ); - int blake2xb_init_key( blake2xb_state *S, const size_t outlen, const void *key, size_t keylen ); - int blake2xb_update( blake2xb_state *S, const void *in, size_t inlen ); - int blake2xb_final(blake2xb_state *S, void *out, size_t outlen); - - /* Simple API */ - int blake2s( void *out, size_t outlen, const void *in, size_t inlen, const void *key, size_t keylen ); - int blake2b( void *out, size_t outlen, const void *in, size_t inlen, const void *key, size_t keylen ); - - int blake2sp( void *out, size_t outlen, const void *in, size_t inlen, const void *key, size_t keylen ); - int blake2bp( void *out, size_t outlen, const void *in, size_t inlen, const void *key, size_t keylen ); - - int blake2xs( void *out, size_t outlen, const void *in, size_t inlen, const void *key, size_t keylen ); - int blake2xb( void *out, size_t outlen, const void *in, size_t inlen, const void *key, size_t keylen ); - - /* This is simply an alias for blake2b */ - int blake2( void *out, size_t outlen, const void *in, size_t inlen, const void *key, size_t keylen ); - -#if defined(__cplusplus) -} -#endif - -#endif - diff --git a/src/blake2b.c b/src/blake2b.c deleted file mode 100644 index 600f951b9b..0000000000 --- a/src/blake2b.c +++ /dev/null @@ -1,539 +0,0 @@ -/* - BLAKE2 reference source code package - reference C implementations - - Copyright 2012, Samuel Neves . You may use this under the - terms of the CC0, the OpenSSL Licence, or the Apache Public License 2.0, at - your option. The terms of these licenses can be found at: - - - CC0 1.0 Universal : http://creativecommons.org/publicdomain/zero/1.0 - - OpenSSL license : https://www.openssl.org/source/license.html - - Apache 2.0 : http://www.apache.org/licenses/LICENSE-2.0 - - More information about the BLAKE2 hash function can be found at - https://blake2.net. -*/ - -#include -#include -#include - -#include "blake2.h" -/* - BLAKE2 reference source code package - reference C implementations - - Copyright 2012, Samuel Neves . You may use this under the - terms of the CC0, the OpenSSL Licence, or the Apache Public License 2.0, at - your option. The terms of these licenses can be found at: - - - CC0 1.0 Universal : http://creativecommons.org/publicdomain/zero/1.0 - - OpenSSL license : https://www.openssl.org/source/license.html - - Apache 2.0 : http://www.apache.org/licenses/LICENSE-2.0 - - More information about the BLAKE2 hash function can be found at - https://blake2.net. -*/ -#ifndef BLAKE2_IMPL_H -#define BLAKE2_IMPL_H - -#include -#include - -#if !defined(__cplusplus) && (!defined(__STDC_VERSION__) || __STDC_VERSION__ < 199901L) - #if defined(_MSC_VER) - #define BLAKE2_INLINE __inline - #elif defined(__GNUC__) - #define BLAKE2_INLINE __inline__ - #else - #define BLAKE2_INLINE - #endif -#else - #define BLAKE2_INLINE inline -#endif - -static BLAKE2_INLINE uint32_t load32( const void *src ) -{ -#if defined(NATIVE_LITTLE_ENDIAN) - uint32_t w; - memcpy(&w, src, sizeof w); - return w; -#else - const uint8_t *p = ( const uint8_t * )src; - return (( uint32_t )( p[0] ) << 0) | - (( uint32_t )( p[1] ) << 8) | - (( uint32_t )( p[2] ) << 16) | - (( uint32_t )( p[3] ) << 24) ; -#endif -} - -static BLAKE2_INLINE uint64_t load64( const void *src ) -{ -#if defined(NATIVE_LITTLE_ENDIAN) - uint64_t w; - memcpy(&w, src, sizeof w); - return w; -#else - const uint8_t *p = ( const uint8_t * )src; - return (( uint64_t )( p[0] ) << 0) | - (( uint64_t )( p[1] ) << 8) | - (( uint64_t )( p[2] ) << 16) | - (( uint64_t )( p[3] ) << 24) | - (( uint64_t )( p[4] ) << 32) | - (( uint64_t )( p[5] ) << 40) | - (( uint64_t )( p[6] ) << 48) | - (( uint64_t )( p[7] ) << 56) ; -#endif -} - -static BLAKE2_INLINE uint16_t load16( const void *src ) -{ -#if defined(NATIVE_LITTLE_ENDIAN) - uint16_t w; - memcpy(&w, src, sizeof w); - return w; -#else - const uint8_t *p = ( const uint8_t * )src; - return ( uint16_t )((( uint32_t )( p[0] ) << 0) | - (( uint32_t )( p[1] ) << 8)); -#endif -} - -static BLAKE2_INLINE void store16( void *dst, uint16_t w ) -{ -#if defined(NATIVE_LITTLE_ENDIAN) - memcpy(dst, &w, sizeof w); -#else - uint8_t *p = ( uint8_t * )dst; - *p++ = ( uint8_t )w; w >>= 8; - *p++ = ( uint8_t )w; -#endif -} - -static BLAKE2_INLINE void store32( void *dst, uint32_t w ) -{ -#if defined(NATIVE_LITTLE_ENDIAN) - memcpy(dst, &w, sizeof w); -#else - uint8_t *p = ( uint8_t * )dst; - p[0] = (uint8_t)(w >> 0); - p[1] = (uint8_t)(w >> 8); - p[2] = (uint8_t)(w >> 16); - p[3] = (uint8_t)(w >> 24); -#endif -} - -static BLAKE2_INLINE void store64( void *dst, uint64_t w ) -{ -#if defined(NATIVE_LITTLE_ENDIAN) - memcpy(dst, &w, sizeof w); -#else - uint8_t *p = ( uint8_t * )dst; - p[0] = (uint8_t)(w >> 0); - p[1] = (uint8_t)(w >> 8); - p[2] = (uint8_t)(w >> 16); - p[3] = (uint8_t)(w >> 24); - p[4] = (uint8_t)(w >> 32); - p[5] = (uint8_t)(w >> 40); - p[6] = (uint8_t)(w >> 48); - p[7] = (uint8_t)(w >> 56); -#endif -} - -static BLAKE2_INLINE uint64_t load48( const void *src ) -{ - const uint8_t *p = ( const uint8_t * )src; - return (( uint64_t )( p[0] ) << 0) | - (( uint64_t )( p[1] ) << 8) | - (( uint64_t )( p[2] ) << 16) | - (( uint64_t )( p[3] ) << 24) | - (( uint64_t )( p[4] ) << 32) | - (( uint64_t )( p[5] ) << 40) ; -} - -static BLAKE2_INLINE void store48( void *dst, uint64_t w ) -{ - uint8_t *p = ( uint8_t * )dst; - p[0] = (uint8_t)(w >> 0); - p[1] = (uint8_t)(w >> 8); - p[2] = (uint8_t)(w >> 16); - p[3] = (uint8_t)(w >> 24); - p[4] = (uint8_t)(w >> 32); - p[5] = (uint8_t)(w >> 40); -} - -static BLAKE2_INLINE uint32_t rotr32( const uint32_t w, const unsigned c ) -{ - return ( w >> c ) | ( w << ( 32 - c ) ); -} - -static BLAKE2_INLINE uint64_t rotr64( const uint64_t w, const unsigned c ) -{ - return ( w >> c ) | ( w << ( 64 - c ) ); -} - -/* prevents compiler optimizing out memset() */ -static BLAKE2_INLINE void secure_zero_memory(void *v, size_t n) -{ - static void *(*const volatile memset_v)(void *, int, size_t) = &memset; - memset_v(v, 0, n); -} - -#endif - -static const uint64_t blake2b_IV[8] = -{ - 0x6a09e667f3bcc908ULL, 0xbb67ae8584caa73bULL, - 0x3c6ef372fe94f82bULL, 0xa54ff53a5f1d36f1ULL, - 0x510e527fade682d1ULL, 0x9b05688c2b3e6c1fULL, - 0x1f83d9abfb41bd6bULL, 0x5be0cd19137e2179ULL -}; - -static const uint8_t blake2b_sigma[12][16] = -{ - { 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15 } , - { 14, 10, 4, 8, 9, 15, 13, 6, 1, 12, 0, 2, 11, 7, 5, 3 } , - { 11, 8, 12, 0, 5, 2, 15, 13, 10, 14, 3, 6, 7, 1, 9, 4 } , - { 7, 9, 3, 1, 13, 12, 11, 14, 2, 6, 5, 10, 4, 0, 15, 8 } , - { 9, 0, 5, 7, 2, 4, 10, 15, 14, 1, 11, 12, 6, 8, 3, 13 } , - { 2, 12, 6, 10, 0, 11, 8, 3, 4, 13, 7, 5, 15, 14, 1, 9 } , - { 12, 5, 1, 15, 14, 13, 4, 10, 0, 7, 6, 3, 9, 2, 8, 11 } , - { 13, 11, 7, 14, 12, 1, 3, 9, 5, 0, 15, 4, 8, 6, 2, 10 } , - { 6, 15, 14, 9, 11, 3, 0, 8, 12, 2, 13, 7, 1, 4, 10, 5 } , - { 10, 2, 8, 4, 7, 6, 1, 5, 15, 11, 9, 14, 3, 12, 13 , 0 } , - { 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15 } , - { 14, 10, 4, 8, 9, 15, 13, 6, 1, 12, 0, 2, 11, 7, 5, 3 } -}; - - -static void blake2b_set_lastnode( blake2b_state *S ) -{ - S->f[1] = (uint64_t)-1; -} - -/* Some helper functions, not necessarily useful */ -static int blake2b_is_lastblock( const blake2b_state *S ) -{ - return S->f[0] != 0; -} - -static void blake2b_set_lastblock( blake2b_state *S ) -{ - if( S->last_node ) blake2b_set_lastnode( S ); - - S->f[0] = (uint64_t)-1; -} - -static void blake2b_increment_counter( blake2b_state *S, const uint64_t inc ) -{ - S->t[0] += inc; - S->t[1] += ( S->t[0] < inc ); -} - -static void blake2b_init0( blake2b_state *S ) -{ - size_t i; - memset( S, 0, sizeof( blake2b_state ) ); - - for( i = 0; i < 8; ++i ) S->h[i] = blake2b_IV[i]; -} - -/* init xors IV with input parameter block */ -int blake2b_init_param( blake2b_state *S, const blake2b_param *P ) -{ - const uint8_t *p = ( const uint8_t * )( P ); - size_t i; - - blake2b_init0( S ); - - /* IV XOR ParamBlock */ - for( i = 0; i < 8; ++i ) - S->h[i] ^= load64( p + sizeof( S->h[i] ) * i ); - - S->outlen = P->digest_length; - return 0; -} - - - -int blake2b_init( blake2b_state *S, size_t outlen ) -{ - blake2b_param P[1]; - - if ( ( !outlen ) || ( outlen > BLAKE2B_OUTBYTES ) ) return -1; - - P->digest_length = (uint8_t)outlen; - P->key_length = 0; - P->fanout = 1; - P->depth = 1; - store32( &P->leaf_length, 0 ); - store32( &P->node_offset, 0 ); - store32( &P->xof_length, 0 ); - P->node_depth = 0; - P->inner_length = 0; - memset( P->reserved, 0, sizeof( P->reserved ) ); - memset( P->salt, 0, sizeof( P->salt ) ); - memset( P->personal, 0, sizeof( P->personal ) ); - return blake2b_init_param( S, P ); -} - - -int blake2b_init_key( blake2b_state *S, size_t outlen, const void *key, size_t keylen ) -{ - blake2b_param P[1]; - - if ( ( !outlen ) || ( outlen > BLAKE2B_OUTBYTES ) ) return -1; - - if ( !key || !keylen || keylen > BLAKE2B_KEYBYTES ) return -1; - - P->digest_length = (uint8_t)outlen; - P->key_length = (uint8_t)keylen; - P->fanout = 1; - P->depth = 1; - store32( &P->leaf_length, 0 ); - store32( &P->node_offset, 0 ); - store32( &P->xof_length, 0 ); - P->node_depth = 0; - P->inner_length = 0; - memset( P->reserved, 0, sizeof( P->reserved ) ); - memset( P->salt, 0, sizeof( P->salt ) ); - memset( P->personal, 0, sizeof( P->personal ) ); - - if( blake2b_init_param( S, P ) < 0 ) return -1; - - { - uint8_t block[BLAKE2B_BLOCKBYTES]; - memset( block, 0, BLAKE2B_BLOCKBYTES ); - memcpy( block, key, keylen ); - blake2b_update( S, block, BLAKE2B_BLOCKBYTES ); - secure_zero_memory( block, BLAKE2B_BLOCKBYTES ); /* Burn the key from stack */ - } - return 0; -} - -#define G(r,i,a,b,c,d) \ - do { \ - a = a + b + m[blake2b_sigma[r][2*i+0]]; \ - d = rotr64(d ^ a, 32); \ - c = c + d; \ - b = rotr64(b ^ c, 24); \ - a = a + b + m[blake2b_sigma[r][2*i+1]]; \ - d = rotr64(d ^ a, 16); \ - c = c + d; \ - b = rotr64(b ^ c, 63); \ - } while(0) - -#define ROUND(r) \ - do { \ - G(r,0,v[ 0],v[ 4],v[ 8],v[12]); \ - G(r,1,v[ 1],v[ 5],v[ 9],v[13]); \ - G(r,2,v[ 2],v[ 6],v[10],v[14]); \ - G(r,3,v[ 3],v[ 7],v[11],v[15]); \ - G(r,4,v[ 0],v[ 5],v[10],v[15]); \ - G(r,5,v[ 1],v[ 6],v[11],v[12]); \ - G(r,6,v[ 2],v[ 7],v[ 8],v[13]); \ - G(r,7,v[ 3],v[ 4],v[ 9],v[14]); \ - } while(0) - -static void blake2b_compress( blake2b_state *S, const uint8_t block[BLAKE2B_BLOCKBYTES] ) -{ - uint64_t m[16]; - uint64_t v[16]; - size_t i; - - for( i = 0; i < 16; ++i ) { - m[i] = load64( block + i * sizeof( m[i] ) ); - } - - for( i = 0; i < 8; ++i ) { - v[i] = S->h[i]; - } - - v[ 8] = blake2b_IV[0]; - v[ 9] = blake2b_IV[1]; - v[10] = blake2b_IV[2]; - v[11] = blake2b_IV[3]; - v[12] = blake2b_IV[4] ^ S->t[0]; - v[13] = blake2b_IV[5] ^ S->t[1]; - v[14] = blake2b_IV[6] ^ S->f[0]; - v[15] = blake2b_IV[7] ^ S->f[1]; - - ROUND( 0 ); - ROUND( 1 ); - ROUND( 2 ); - ROUND( 3 ); - ROUND( 4 ); - ROUND( 5 ); - ROUND( 6 ); - ROUND( 7 ); - ROUND( 8 ); - ROUND( 9 ); - ROUND( 10 ); - ROUND( 11 ); - - for( i = 0; i < 8; ++i ) { - S->h[i] = S->h[i] ^ v[i] ^ v[i + 8]; - } -} - -#undef G -#undef ROUND - -int blake2b_update( blake2b_state *S, const void *pin, size_t inlen ) -{ - const unsigned char * in = (const unsigned char *)pin; - if( inlen > 0 ) - { - size_t left = S->buflen; - size_t fill = BLAKE2B_BLOCKBYTES - left; - if( inlen > fill ) - { - S->buflen = 0; - memcpy( S->buf + left, in, fill ); /* Fill buffer */ - blake2b_increment_counter( S, BLAKE2B_BLOCKBYTES ); - blake2b_compress( S, S->buf ); /* Compress */ - in += fill; inlen -= fill; - while(inlen > BLAKE2B_BLOCKBYTES) { - blake2b_increment_counter(S, BLAKE2B_BLOCKBYTES); - blake2b_compress( S, in ); - in += BLAKE2B_BLOCKBYTES; - inlen -= BLAKE2B_BLOCKBYTES; - } - } - memcpy( S->buf + S->buflen, in, inlen ); - S->buflen += inlen; - } - return 0; -} - -int blake2b_final( blake2b_state *S, void *out, size_t outlen ) -{ - uint8_t buffer[BLAKE2B_OUTBYTES] = {0}; - size_t i; - - if( out == NULL || outlen < S->outlen ) - return -1; - - if( blake2b_is_lastblock( S ) ) - return -1; - - blake2b_increment_counter( S, S->buflen ); - blake2b_set_lastblock( S ); - memset( S->buf + S->buflen, 0, BLAKE2B_BLOCKBYTES - S->buflen ); /* Padding */ - blake2b_compress( S, S->buf ); - - for( i = 0; i < 8; ++i ) /* Output full hash to temp buffer */ - store64( buffer + sizeof( S->h[i] ) * i, S->h[i] ); - - memcpy( out, buffer, S->outlen ); - secure_zero_memory(buffer, sizeof(buffer)); - return 0; -} - -/* inlen, at least, should be uint64_t. Others can be size_t. */ -int blake2b( void *out, size_t outlen, const void *in, size_t inlen, const void *key, size_t keylen ) -{ - blake2b_state S[1]; - - /* Verify parameters */ - if ( NULL == in && inlen > 0 ) return -1; - - if ( NULL == out ) return -1; - - if( NULL == key && keylen > 0 ) return -1; - - if( !outlen || outlen > BLAKE2B_OUTBYTES ) return -1; - - if( keylen > BLAKE2B_KEYBYTES ) return -1; - - if( keylen > 0 ) - { - if( blake2b_init_key( S, outlen, key, keylen ) < 0 ) return -1; - } - else - { - if( blake2b_init( S, outlen ) < 0 ) return -1; - } - - blake2b_update( S, ( const uint8_t * )in, inlen ); - blake2b_final( S, out, outlen ); - return 0; -} - -int blake2( void *out, size_t outlen, const void *in, size_t inlen, const void *key, size_t keylen ) { - return blake2b(out, outlen, in, inlen, key, keylen); -} - -#if defined(SUPERCOP) -int crypto_hash( unsigned char *out, unsigned char *in, unsigned long long inlen ) -{ - return blake2b( out, BLAKE2B_OUTBYTES, in, inlen, NULL, 0 ); -} -#endif - -#if defined(BLAKE2B_SELFTEST) -#include -#include "blake2-kat.h" -int main( void ) -{ - uint8_t key[BLAKE2B_KEYBYTES]; - uint8_t buf[BLAKE2_KAT_LENGTH]; - size_t i, step; - - for( i = 0; i < BLAKE2B_KEYBYTES; ++i ) - key[i] = ( uint8_t )i; - - for( i = 0; i < BLAKE2_KAT_LENGTH; ++i ) - buf[i] = ( uint8_t )i; - - /* Test simple API */ - for( i = 0; i < BLAKE2_KAT_LENGTH; ++i ) - { - uint8_t hash[BLAKE2B_OUTBYTES]; - blake2b( hash, BLAKE2B_OUTBYTES, buf, i, key, BLAKE2B_KEYBYTES ); - - if( 0 != memcmp( hash, blake2b_keyed_kat[i], BLAKE2B_OUTBYTES ) ) - { - goto fail; - } - } - - /* Test streaming API */ - for(step = 1; step < BLAKE2B_BLOCKBYTES; ++step) { - for (i = 0; i < BLAKE2_KAT_LENGTH; ++i) { - uint8_t hash[BLAKE2B_OUTBYTES]; - blake2b_state S; - uint8_t * p = buf; - size_t mlen = i; - int err = 0; - - if( (err = blake2b_init_key(&S, BLAKE2B_OUTBYTES, key, BLAKE2B_KEYBYTES)) < 0 ) { - goto fail; - } - - while (mlen >= step) { - if ( (err = blake2b_update(&S, p, step)) < 0 ) { - goto fail; - } - mlen -= step; - p += step; - } - if ( (err = blake2b_update(&S, p, mlen)) < 0) { - goto fail; - } - if ( (err = blake2b_final(&S, hash, BLAKE2B_OUTBYTES)) < 0) { - goto fail; - } - - if (0 != memcmp(hash, blake2b_keyed_kat[i], BLAKE2B_OUTBYTES)) { - goto fail; - } - } - } - - puts( "ok" ); - return 0; -fail: - puts("error"); - return -1; -} -#endif - diff --git a/src/cache_hash.cpp b/src/cache_hash.cpp deleted file mode 100644 index c12d8f29ef..0000000000 --- a/src/cache_hash.cpp +++ /dev/null @@ -1,595 +0,0 @@ -/* - * Copyright (c) 2018 Andrew Kelley - * - * This file is part of zig, which is MIT licensed. - * See http://opensource.org/licenses/MIT - */ - -#include "stage2.h" -#include "cache_hash.hpp" -#include "all_types.hpp" -#include "buffer.hpp" -#include "os.hpp" - -#include - -void cache_init(CacheHash *ch, Buf *manifest_dir) { - int rc = blake2b_init(&ch->blake, 48); - assert(rc == 0); - ch->files = {}; - ch->manifest_dir = manifest_dir; - ch->manifest_file_path = nullptr; - ch->manifest_dirty = false; - ch->force_check_manifest = false; - ch->b64_digest = BUF_INIT; -} - -void cache_mem(CacheHash *ch, const char *ptr, size_t len) { - assert(ch->manifest_file_path == nullptr); - assert(ptr != nullptr); - blake2b_update(&ch->blake, ptr, len); -} - -void cache_slice(CacheHash *ch, Slice slice) { - // mix the length into the hash so that two juxtaposed cached slices can't collide - cache_usize(ch, slice.len); - cache_mem(ch, slice.ptr, slice.len); -} - -void cache_str(CacheHash *ch, const char *ptr) { - // + 1 to include the null byte - cache_mem(ch, ptr, strlen(ptr) + 1); -} - -void cache_int(CacheHash *ch, int x) { - assert(ch->manifest_file_path == nullptr); - // + 1 to include the null byte - uint8_t buf[sizeof(int) + 1]; - memcpy(buf, &x, sizeof(int)); - buf[sizeof(int)] = 0; - blake2b_update(&ch->blake, buf, sizeof(int) + 1); -} - -void cache_usize(CacheHash *ch, size_t x) { - assert(ch->manifest_file_path == nullptr); - // + 1 to include the null byte - uint8_t buf[sizeof(size_t) + 1]; - memcpy(buf, &x, sizeof(size_t)); - buf[sizeof(size_t)] = 0; - blake2b_update(&ch->blake, buf, sizeof(size_t) + 1); -} - -void cache_bool(CacheHash *ch, bool x) { - assert(ch->manifest_file_path == nullptr); - blake2b_update(&ch->blake, &x, 1); -} - -void cache_buf(CacheHash *ch, Buf *buf) { - assert(ch->manifest_file_path == nullptr); - assert(buf != nullptr); - // + 1 to include the null byte - blake2b_update(&ch->blake, buf_ptr(buf), buf_len(buf) + 1); -} - -void cache_buf_opt(CacheHash *ch, Buf *buf) { - assert(ch->manifest_file_path == nullptr); - if (buf == nullptr) { - cache_str(ch, ""); - cache_str(ch, ""); - } else { - cache_buf(ch, buf); - } -} - -void cache_list_of_link_lib(CacheHash *ch, LinkLib **ptr, size_t len) { - assert(ch->manifest_file_path == nullptr); - for (size_t i = 0; i < len; i += 1) { - LinkLib *lib = ptr[i]; - if (lib->provided_explicitly) { - cache_buf(ch, lib->name); - } - } - cache_str(ch, ""); -} - -void cache_list_of_buf(CacheHash *ch, Buf **ptr, size_t len) { - assert(ch->manifest_file_path == nullptr); - for (size_t i = 0; i < len; i += 1) { - Buf *buf = ptr[i]; - cache_buf(ch, buf); - } - cache_str(ch, ""); -} - -void cache_list_of_file(CacheHash *ch, Buf **ptr, size_t len) { - assert(ch->manifest_file_path == nullptr); - - for (size_t i = 0; i < len; i += 1) { - Buf *buf = ptr[i]; - cache_file(ch, buf); - } - cache_str(ch, ""); -} - -void cache_list_of_str(CacheHash *ch, const char **ptr, size_t len) { - assert(ch->manifest_file_path == nullptr); - - for (size_t i = 0; i < len; i += 1) { - const char *s = ptr[i]; - cache_str(ch, s); - } - cache_str(ch, ""); -} - -void cache_file(CacheHash *ch, Buf *file_path) { - assert(ch->manifest_file_path == nullptr); - assert(file_path != nullptr); - Buf *resolved_path = buf_alloc(); - *resolved_path = os_path_resolve(&file_path, 1); - CacheHashFile *chf = ch->files.add_one(); - chf->path = resolved_path; - cache_buf(ch, resolved_path); -} - -void cache_file_opt(CacheHash *ch, Buf *file_path) { - assert(ch->manifest_file_path == nullptr); - if (file_path == nullptr) { - cache_str(ch, ""); - cache_str(ch, ""); - } else { - cache_file(ch, file_path); - } -} - -// Ported from std/base64.zig -static uint8_t base64_fs_alphabet[] = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789-_"; -static void base64_encode(Slice dest, Slice source) { - size_t dest_len = ((source.len + 2) / 3) * 4; - assert(dest.len == dest_len); - - size_t i = 0; - size_t out_index = 0; - for (; i + 2 < source.len; i += 3) { - dest.ptr[out_index] = base64_fs_alphabet[(source.ptr[i] >> 2) & 0x3f]; - out_index += 1; - - dest.ptr[out_index] = base64_fs_alphabet[((source.ptr[i] & 0x3) << 4) | ((source.ptr[i + 1] & 0xf0) >> 4)]; - out_index += 1; - - dest.ptr[out_index] = base64_fs_alphabet[((source.ptr[i + 1] & 0xf) << 2) | ((source.ptr[i + 2] & 0xc0) >> 6)]; - out_index += 1; - - dest.ptr[out_index] = base64_fs_alphabet[source.ptr[i + 2] & 0x3f]; - out_index += 1; - } - - // Assert that we never need pad characters. - assert(i == source.len); -} - -// Ported from std/base64.zig -static Error base64_decode(Slice dest, Slice source) { - if (source.len % 4 != 0) - return ErrorInvalidFormat; - if (dest.len != (source.len / 4) * 3) - return ErrorInvalidFormat; - - // In Zig this is comptime computed. In C++ it's not worth it to do that. - uint8_t char_to_index[256]; - bool char_in_alphabet[256] = {0}; - for (size_t i = 0; i < 64; i += 1) { - uint8_t c = base64_fs_alphabet[i]; - assert(!char_in_alphabet[c]); - char_in_alphabet[c] = true; - char_to_index[c] = i; - } - - size_t src_cursor = 0; - size_t dest_cursor = 0; - - for (;src_cursor < source.len; src_cursor += 4) { - if (!char_in_alphabet[source.ptr[src_cursor + 0]]) return ErrorInvalidFormat; - if (!char_in_alphabet[source.ptr[src_cursor + 1]]) return ErrorInvalidFormat; - if (!char_in_alphabet[source.ptr[src_cursor + 2]]) return ErrorInvalidFormat; - if (!char_in_alphabet[source.ptr[src_cursor + 3]]) return ErrorInvalidFormat; - dest.ptr[dest_cursor + 0] = (char_to_index[source.ptr[src_cursor + 0]] << 2) | (char_to_index[source.ptr[src_cursor + 1]] >> 4); - dest.ptr[dest_cursor + 1] = (char_to_index[source.ptr[src_cursor + 1]] << 4) | (char_to_index[source.ptr[src_cursor + 2]] >> 2); - dest.ptr[dest_cursor + 2] = (char_to_index[source.ptr[src_cursor + 2]] << 6) | (char_to_index[source.ptr[src_cursor + 3]]); - dest_cursor += 3; - } - - assert(src_cursor == source.len); - assert(dest_cursor == dest.len); - return ErrorNone; -} - -static Error hash_file(uint8_t *digest, OsFile handle, Buf *contents) { - Error err; - - if (contents) { - buf_resize(contents, 0); - } - - blake2b_state blake; - int rc = blake2b_init(&blake, 48); - assert(rc == 0); - - for (;;) { - uint8_t buf[4096]; - size_t amt = 4096; - if ((err = os_file_read(handle, buf, &amt))) - return err; - if (amt == 0) { - rc = blake2b_final(&blake, digest, 48); - assert(rc == 0); - return ErrorNone; - } - blake2b_update(&blake, buf, amt); - if (contents) { - buf_append_mem(contents, (char*)buf, amt); - } - } -} - -// If the wall clock time, rounded to the same precision as the -// mtime, is equal to the mtime, then we cannot rely on this mtime -// yet. We will instead save an mtime value that indicates the hash -// must be unconditionally computed. -static bool is_problematic_timestamp(const OsTimeStamp *fs_clock) { - OsTimeStamp wall_clock = os_timestamp_calendar(); - // First make all the least significant zero bits in the fs_clock, also zero bits in the wall clock. - if (fs_clock->nsec == 0) { - wall_clock.nsec = 0; - if (fs_clock->sec == 0) { - wall_clock.sec = 0; - } else { - wall_clock.sec &= (-1ull) << ctzll(fs_clock->sec); - } - } else { - wall_clock.nsec &= (-1ull) << ctzll(fs_clock->nsec); - } - return wall_clock.nsec == fs_clock->nsec && wall_clock.sec == fs_clock->sec; -} - -static Error populate_file_hash(CacheHash *ch, CacheHashFile *chf, Buf *contents) { - Error err; - - assert(chf->path != nullptr); - - OsFile this_file; - if ((err = os_file_open_r(chf->path, &this_file, &chf->attr))) - return err; - - if (is_problematic_timestamp(&chf->attr.mtime)) { - chf->attr.mtime.sec = 0; - chf->attr.mtime.nsec = 0; - chf->attr.inode = 0; - } - - if ((err = hash_file(chf->bin_digest, this_file, contents))) { - os_file_close(&this_file); - return err; - } - os_file_close(&this_file); - - blake2b_update(&ch->blake, chf->bin_digest, 48); - - return ErrorNone; -} - -Error cache_hit(CacheHash *ch, Buf *out_digest) { - Error err; - - uint8_t bin_digest[48]; - int rc = blake2b_final(&ch->blake, bin_digest, 48); - assert(rc == 0); - - buf_resize(&ch->b64_digest, 64); - base64_encode(buf_to_slice(&ch->b64_digest), {bin_digest, 48}); - - if (ch->files.length == 0 && !ch->force_check_manifest) { - buf_resize(out_digest, 64); - base64_encode(buf_to_slice(out_digest), {bin_digest, 48}); - return ErrorNone; - } - - rc = blake2b_init(&ch->blake, 48); - assert(rc == 0); - blake2b_update(&ch->blake, bin_digest, 48); - - ch->manifest_file_path = buf_alloc(); - os_path_join(ch->manifest_dir, &ch->b64_digest, ch->manifest_file_path); - - buf_append_str(ch->manifest_file_path, ".txt"); - - if ((err = os_make_path(ch->manifest_dir))) - return err; - - if ((err = os_file_open_lock_rw(ch->manifest_file_path, &ch->manifest_file))) - return err; - - Buf line_buf = BUF_INIT; - buf_resize(&line_buf, 512); - if ((err = os_file_read_all(ch->manifest_file, &line_buf))) { - os_file_close(&ch->manifest_file); - return err; - } - - size_t input_file_count = ch->files.length; - bool any_file_changed = false; - Error return_code = ErrorNone; - size_t file_i = 0; - SplitIterator line_it = memSplit(buf_to_slice(&line_buf), str("\n")); - for (;; file_i += 1) { - Optional> opt_line = SplitIterator_next(&line_it); - - CacheHashFile *chf; - if (file_i < input_file_count) { - chf = &ch->files.at(file_i); - } else if (any_file_changed) { - // cache miss. - // keep the manifest file open with the rw lock - // reset the hash - rc = blake2b_init(&ch->blake, 48); - assert(rc == 0); - blake2b_update(&ch->blake, bin_digest, 48); - ch->files.resize(input_file_count); - // bring the hash up to the input file hashes - for (file_i = 0; file_i < input_file_count; file_i += 1) { - blake2b_update(&ch->blake, ch->files.at(file_i).bin_digest, 48); - } - // caller can notice that out_digest is unmodified. - return return_code; - } else if (!opt_line.is_some) { - break; - } else { - chf = ch->files.add_one(); - chf->path = nullptr; - } - - if (!opt_line.is_some) - break; - - SplitIterator it = memSplit(opt_line.value, str(" ")); - - Optional> opt_inode = SplitIterator_next(&it); - if (!opt_inode.is_some) { - return_code = ErrorInvalidFormat; - break; - } - chf->attr.inode = strtoull((const char *)opt_inode.value.ptr, nullptr, 10); - - Optional> opt_mtime_sec = SplitIterator_next(&it); - if (!opt_mtime_sec.is_some) { - return_code = ErrorInvalidFormat; - break; - } - chf->attr.mtime.sec = strtoull((const char *)opt_mtime_sec.value.ptr, nullptr, 10); - - Optional> opt_mtime_nsec = SplitIterator_next(&it); - if (!opt_mtime_nsec.is_some) { - return_code = ErrorInvalidFormat; - break; - } - chf->attr.mtime.nsec = strtoull((const char *)opt_mtime_nsec.value.ptr, nullptr, 10); - - Optional> opt_digest = SplitIterator_next(&it); - if (!opt_digest.is_some) { - return_code = ErrorInvalidFormat; - break; - } - if ((err = base64_decode({chf->bin_digest, 48}, opt_digest.value))) { - return_code = ErrorInvalidFormat; - break; - } - - Slice file_path = SplitIterator_rest(&it); - if (file_path.len == 0) { - return_code = ErrorInvalidFormat; - break; - } - Buf *this_path = buf_create_from_slice(file_path); - if (chf->path != nullptr && !buf_eql_buf(this_path, chf->path)) { - return_code = ErrorInvalidFormat; - break; - } - chf->path = this_path; - - // if the mtime matches we can trust the digest - OsFile this_file; - OsFileAttr actual_attr; - if ((err = os_file_open_r(chf->path, &this_file, &actual_attr))) { - fprintf(stderr, "Unable to open %s\n: %s", buf_ptr(chf->path), err_str(err)); - os_file_close(&ch->manifest_file); - return ErrorCacheUnavailable; - } - if (chf->attr.mtime.sec == actual_attr.mtime.sec && - chf->attr.mtime.nsec == actual_attr.mtime.nsec && - chf->attr.inode == actual_attr.inode) - { - os_file_close(&this_file); - } else { - // we have to recompute the digest. - // later we'll rewrite the manifest with the new mtime/digest values - ch->manifest_dirty = true; - chf->attr = actual_attr; - - if (is_problematic_timestamp(&actual_attr.mtime)) { - chf->attr.mtime.sec = 0; - chf->attr.mtime.nsec = 0; - chf->attr.inode = 0; - } - - uint8_t actual_digest[48]; - if ((err = hash_file(actual_digest, this_file, nullptr))) { - os_file_close(&this_file); - os_file_close(&ch->manifest_file); - return err; - } - os_file_close(&this_file); - if (memcmp(chf->bin_digest, actual_digest, 48) != 0) { - memcpy(chf->bin_digest, actual_digest, 48); - // keep going until we have the input file digests - any_file_changed = true; - } - } - if (!any_file_changed) { - blake2b_update(&ch->blake, chf->bin_digest, 48); - } - } - if (file_i < input_file_count || file_i == 0 || return_code != ErrorNone) { - // manifest file is empty or missing entries, so this is a cache miss - ch->manifest_dirty = true; - for (; file_i < input_file_count; file_i += 1) { - CacheHashFile *chf = &ch->files.at(file_i); - if ((err = populate_file_hash(ch, chf, nullptr))) { - fprintf(stderr, "Unable to hash %s: %s\n", buf_ptr(chf->path), err_str(err)); - os_file_close(&ch->manifest_file); - return ErrorCacheUnavailable; - } - } - if (return_code != ErrorNone && return_code != ErrorInvalidFormat) { - os_file_close(&ch->manifest_file); - } - return return_code; - } - // Cache Hit - return cache_final(ch, out_digest); -} - -Error cache_add_file_fetch(CacheHash *ch, Buf *resolved_path, Buf *contents) { - Error err; - - assert(ch->manifest_file_path != nullptr); - CacheHashFile *chf = ch->files.add_one(); - chf->path = resolved_path; - if ((err = populate_file_hash(ch, chf, contents))) { - os_file_close(&ch->manifest_file); - return err; - } - - return ErrorNone; -} - -Error cache_add_file(CacheHash *ch, Buf *path) { - Buf *resolved_path = buf_alloc(); - *resolved_path = os_path_resolve(&path, 1); - return cache_add_file_fetch(ch, resolved_path, nullptr); -} - -Error cache_add_dep_file(CacheHash *ch, Buf *dep_file_path, bool verbose) { - Error err; - Buf *contents = buf_alloc(); - if ((err = os_fetch_file_path(dep_file_path, contents))) { - if (err == ErrorFileNotFound) - return err; - if (verbose) { - fprintf(stderr, "%s: unable to read .d file: %s\n", err_str(err), buf_ptr(dep_file_path)); - } - return ErrorReadingDepFile; - } - auto it = stage2_DepTokenizer_init(buf_ptr(contents), buf_len(contents)); - // skip first token: target - { - auto result = stage2_DepTokenizer_next(&it); - switch (result.type_id) { - case stage2_DepNextResult::error: - if (verbose) { - fprintf(stderr, "%s: failed processing .d file: %s\n", result.textz, buf_ptr(dep_file_path)); - } - err = ErrorInvalidDepFile; - goto finish; - case stage2_DepNextResult::null: - err = ErrorNone; - goto finish; - case stage2_DepNextResult::target: - case stage2_DepNextResult::prereq: - err = ErrorNone; - break; - } - } - // Process 0+ preqreqs. - // clang is invoked in single-source mode so we never get more targets. - for (;;) { - auto result = stage2_DepTokenizer_next(&it); - switch (result.type_id) { - case stage2_DepNextResult::error: - if (verbose) { - fprintf(stderr, "%s: failed processing .d file: %s\n", result.textz, buf_ptr(dep_file_path)); - } - err = ErrorInvalidDepFile; - goto finish; - case stage2_DepNextResult::null: - case stage2_DepNextResult::target: - err = ErrorNone; - goto finish; - case stage2_DepNextResult::prereq: - break; - } - auto textbuf = buf_alloc(); - buf_init_from_str(textbuf, result.textz); - if ((err = cache_add_file(ch, textbuf))) { - if (verbose) { - fprintf(stderr, "unable to add %s to cache: %s\n", result.textz, err_str(err)); - fprintf(stderr, "when processing .d file: %s\n", buf_ptr(dep_file_path)); - } - goto finish; - } - } - - finish: - stage2_DepTokenizer_deinit(&it); - return err; -} - -static Error write_manifest_file(CacheHash *ch) { - Error err; - Buf contents = BUF_INIT; - buf_resize(&contents, 0); - uint8_t encoded_digest[65]; - encoded_digest[64] = 0; - for (size_t i = 0; i < ch->files.length; i += 1) { - CacheHashFile *chf = &ch->files.at(i); - base64_encode({encoded_digest, 64}, {chf->bin_digest, 48}); - buf_appendf(&contents, "%" ZIG_PRI_u64 " %" ZIG_PRI_u64 " %" ZIG_PRI_u64 " %s %s\n", - chf->attr.inode, chf->attr.mtime.sec, chf->attr.mtime.nsec, encoded_digest, buf_ptr(chf->path)); - } - if ((err = os_file_overwrite(ch->manifest_file, &contents))) - return err; - - return ErrorNone; -} - -Error cache_final(CacheHash *ch, Buf *out_digest) { - assert(ch->manifest_file_path != nullptr); - - // We don't close the manifest file yet, because we want to - // keep it locked until the API user is done using it. - // We also don't write out the manifest yet, because until - // cache_release is called we still might be working on creating - // the artifacts to cache. - - uint8_t bin_digest[48]; - int rc = blake2b_final(&ch->blake, bin_digest, 48); - assert(rc == 0); - buf_resize(out_digest, 64); - base64_encode(buf_to_slice(out_digest), {bin_digest, 48}); - - return ErrorNone; -} - -void cache_release(CacheHash *ch) { - assert(ch->manifest_file_path != nullptr); - - Error err; - - if (ch->manifest_dirty) { - if ((err = write_manifest_file(ch))) { - fprintf(stderr, "Warning: Unable to write cache file '%s': %s\n", - buf_ptr(ch->manifest_file_path), err_str(err)); - } - } - - os_file_close(&ch->manifest_file); -} - diff --git a/src/cache_hash.hpp b/src/cache_hash.hpp deleted file mode 100644 index ba2434076a..0000000000 --- a/src/cache_hash.hpp +++ /dev/null @@ -1,83 +0,0 @@ -/* - * Copyright (c) 2018 Andrew Kelley - * - * This file is part of zig, which is MIT licensed. - * See http://opensource.org/licenses/MIT - */ - -#ifndef ZIG_CACHE_HASH_HPP -#define ZIG_CACHE_HASH_HPP - -#include "blake2.h" -#include "os.hpp" - -struct LinkLib; - -struct CacheHashFile { - Buf *path; - OsFileAttr attr; - uint8_t bin_digest[48]; - Buf *contents; -}; - -struct CacheHash { - blake2b_state blake; - ZigList files; - Buf *manifest_dir; - Buf *manifest_file_path; - Buf b64_digest; - OsFile manifest_file; - bool manifest_dirty; - bool force_check_manifest; -}; - -// Always call this first to set up. -void cache_init(CacheHash *ch, Buf *manifest_dir); - -// Next, use the hash population functions to add the initial parameters. -void cache_mem(CacheHash *ch, const char *ptr, size_t len); -void cache_slice(CacheHash *ch, Slice slice); -void cache_str(CacheHash *ch, const char *ptr); -void cache_int(CacheHash *ch, int x); -void cache_bool(CacheHash *ch, bool x); -void cache_usize(CacheHash *ch, size_t x); -void cache_buf(CacheHash *ch, Buf *buf); -void cache_buf_opt(CacheHash *ch, Buf *buf); -void cache_list_of_link_lib(CacheHash *ch, LinkLib **ptr, size_t len); -void cache_list_of_buf(CacheHash *ch, Buf **ptr, size_t len); -void cache_list_of_file(CacheHash *ch, Buf **ptr, size_t len); -void cache_list_of_str(CacheHash *ch, const char **ptr, size_t len); -void cache_file(CacheHash *ch, Buf *path); -void cache_file_opt(CacheHash *ch, Buf *path); - -// Then call cache_hit when you're ready to see if you can skip the next step. -// out_b64_digest will be left unchanged if it was a cache miss. -// If you got a cache hit, the next step is cache_release. -// From this point on, there is a lock on the input params. Release -// the lock with cache_release. -// Set force_check_manifest if you plan to add files later, but have not -// added any files before calling cache_hit. CacheHash::b64_digest becomes -// available for use after this call, even in the case of a miss, and it -// is a hash of the input parameters only. -// If this function returns ErrorInvalidFormat, that error may be treated -// as a cache miss. -Error ATTRIBUTE_MUST_USE cache_hit(CacheHash *ch, Buf *out_b64_digest); - -// If you did not get a cache hit, call this function for every file -// that is depended on, and then finish with cache_final. -Error ATTRIBUTE_MUST_USE cache_add_file(CacheHash *ch, Buf *path); -// This opens a file created by -MD -MF args to Clang -Error ATTRIBUTE_MUST_USE cache_add_dep_file(CacheHash *ch, Buf *path, bool verbose); - -// This variant of cache_add_file returns the file contents. -// Also the file path argument must be already resolved. -Error ATTRIBUTE_MUST_USE cache_add_file_fetch(CacheHash *ch, Buf *resolved_path, Buf *contents); - -// out_b64_digest will be the same thing that cache_hit returns if you got a cache hit -Error ATTRIBUTE_MUST_USE cache_final(CacheHash *ch, Buf *out_b64_digest); - -// Until this function is called, no one will be able to get a lock on your input params. -void cache_release(CacheHash *ch); - - -#endif diff --git a/src/codegen.cpp b/src/codegen.cpp index ce6eeb1def..07728ef06e 100644 --- a/src/codegen.cpp +++ b/src/codegen.cpp @@ -8,7 +8,6 @@ #include "analyze.hpp" #include "ast_render.hpp" #include "codegen.hpp" -#include "compiler.hpp" #include "config.h" #include "errmsg.hpp" #include "error.hpp" @@ -21,7 +20,6 @@ #include "stage2.h" #include "dump_analysis.hpp" #include "softfloat.hpp" -#include "mem_profile.hpp" #include #include @@ -72,39 +70,6 @@ static const char *symbols_that_llvm_depends_on[] = { // TODO probably all of compiler-rt needs to go here }; -void codegen_set_clang_argv(CodeGen *g, const char **args, size_t len) { - g->clang_argv = args; - g->clang_argv_len = len; -} - -void codegen_set_llvm_argv(CodeGen *g, const char **args, size_t len) { - g->llvm_argv = args; - g->llvm_argv_len = len; -} - -void codegen_set_test_filter(CodeGen *g, Buf *filter) { - g->test_filter = filter; -} - -void codegen_set_test_name_prefix(CodeGen *g, Buf *prefix) { - g->test_name_prefix = prefix; -} - -void codegen_set_lib_version(CodeGen *g, bool is_versioned, size_t major, size_t minor, size_t patch) { - g->is_versioned = is_versioned; - g->version_major = major; - g->version_minor = minor; - g->version_patch = patch; -} - -void codegen_set_each_lib_rpath(CodeGen *g, bool each_lib_rpath) { - g->each_lib_rpath = each_lib_rpath; -} - -void codegen_set_errmsg_color(CodeGen *g, ErrColor err_color) { - g->err_color = err_color; -} - void codegen_set_strip(CodeGen *g, bool strip) { g->strip_debug_symbols = strip; if (!target_has_debug_info(g->zig_target)) { @@ -112,39 +77,6 @@ void codegen_set_strip(CodeGen *g, bool strip) { } } -void codegen_set_out_name(CodeGen *g, Buf *out_name) { - g->root_out_name = out_name; -} - -void codegen_add_lib_dir(CodeGen *g, const char *dir) { - g->lib_dirs.append(dir); -} - -void codegen_add_rpath(CodeGen *g, const char *name) { - g->rpath_list.append(buf_create_from_str(name)); -} - -LinkLib *codegen_add_link_lib(CodeGen *g, Buf *name) { - return add_link_lib(g, name); -} - -void codegen_add_forbidden_lib(CodeGen *codegen, Buf *lib) { - codegen->forbidden_libs.append(lib); -} - -void codegen_add_framework(CodeGen *g, const char *framework) { - g->darwin_frameworks.append(buf_create_from_str(framework)); -} - -void codegen_set_rdynamic(CodeGen *g, bool rdynamic) { - g->linker_rdynamic = rdynamic; -} - -void codegen_set_linker_script(CodeGen *g, const char *linker_script) { - g->linker_script = linker_script; -} - - static void render_const_val(CodeGen *g, ZigValue *const_val, const char *name); static void render_const_val_global(CodeGen *g, ZigValue *const_val, const char *name); static LLVMValueRef gen_const_val(CodeGen *g, ZigValue *const_val, const char *name); @@ -155,7 +87,6 @@ static LLVMValueRef build_alloca(CodeGen *g, ZigType *type_entry, const char *na static LLVMValueRef gen_await_early_return(CodeGen *g, IrInstGen *source_instr, LLVMValueRef target_frame_ptr, ZigType *result_type, ZigType *ptr_result_type, LLVMValueRef result_loc, bool non_async); -static Error get_tmp_filename(CodeGen *g, Buf *out, Buf *suffix); static void addLLVMAttr(LLVMValueRef val, LLVMAttributeIndex attr_index, const char *attr_name) { unsigned kind_id = LLVMGetEnumAttributeKindForName(attr_name, strlen(attr_name)); @@ -389,7 +320,7 @@ static uint32_t get_err_ret_trace_arg_index(CodeGen *g, ZigFn *fn_table_entry) { } static void maybe_export_dll(CodeGen *g, LLVMValueRef global_value, GlobalLinkageId linkage) { - if (linkage != GlobalLinkageIdInternal && g->zig_target->os == OsWindows && g->is_dynamic) { + if (linkage != GlobalLinkageIdInternal && g->zig_target->os == OsWindows && g->dll_export_fns) { LLVMSetDLLStorageClass(global_value, LLVMDLLExportStorageClass); } } @@ -541,7 +472,7 @@ static LLVMValueRef make_fn_llvm_value(CodeGen *g, ZigFn *fn) { g->build_mode != BuildModeSmallRelease && !fn->def_scope->safety_off; if (want_fn_safety) { - if (g->libc_link_lib != nullptr) { + if (g->link_libc) { addLLVMFnAttr(llvm_fn, "sspstrong"); addLLVMFnAttrStr(llvm_fn, "stack-protector-buffer-size", "4"); } @@ -3859,20 +3790,6 @@ static LLVMValueRef gen_valgrind_client_request(CodeGen *g, LLVMValueRef default zig_unreachable(); } -static bool want_valgrind_support(CodeGen *g) { - if (!target_has_valgrind_support(g->zig_target)) - return false; - switch (g->valgrind_support) { - case ValgrindSupportDisabled: - return false; - case ValgrindSupportEnabled: - return true; - case ValgrindSupportAuto: - return g->build_mode == BuildModeDebug; - } - zig_unreachable(); -} - static void gen_valgrind_undef(CodeGen *g, LLVMValueRef dest_ptr, LLVMValueRef byte_count) { static const uint32_t VG_USERREQ__MAKE_MEM_UNDEFINED = 1296236545; ZigType *usize = g->builtin_types.entry_usize; @@ -3895,7 +3812,7 @@ static void gen_undef_init(CodeGen *g, uint32_t ptr_align_bytes, ZigType *value_ LLVMValueRef byte_count = LLVMConstInt(usize->llvm_type, size_bytes, false); ZigLLVMBuildMemSet(g->builder, dest_ptr, fill_char, byte_count, ptr_align_bytes, false); // then tell valgrind that the memory is undefined even though we just memset it - if (want_valgrind_support(g)) { + if (g->valgrind_enabled) { gen_valgrind_undef(g, dest_ptr, byte_count); } } @@ -5598,7 +5515,7 @@ static LLVMValueRef ir_render_memset(CodeGen *g, IrExecutableGen *executable, Ir ZigLLVMBuildMemSet(g->builder, dest_ptr_casted, fill_char, len_val, get_ptr_align(g, ptr_type), ptr_type->data.pointer.is_volatile); - if (val_is_undef && want_valgrind_support(g)) { + if (val_is_undef && g->valgrind_enabled) { gen_valgrind_undef(g, dest_ptr_casted, len_val); } return nullptr; @@ -8350,13 +8267,6 @@ static void zig_llvm_emit_output(CodeGen *g) { exit(1); } - if (g->emit_bin) { - g->link_objects.append(&g->o_file_output_path); - if (g->bundle_compiler_rt && (g->out_type == OutTypeObj || (g->out_type == OutTypeLib && !g->is_dynamic))) { - zig_link_add_compiler_rt(g, g->sub_progress_node); - } - } - LLVMDisposeModule(g->module); g->module = nullptr; LLVMDisposeTargetData(g->target_data_ref); @@ -8751,75 +8661,12 @@ static const char *subsystem_to_str(TargetSubsystem subsystem) { zig_unreachable(); } -static bool detect_dynamic_link(CodeGen *g) { - if (g->is_dynamic) - return true; - if (g->zig_target->os == OsFreestanding) - return false; - if (target_os_requires_libc(g->zig_target->os)) - return true; - if (g->libc_link_lib != nullptr && target_is_glibc(g->zig_target)) - return true; - // If there are no dynamic libraries then we can disable dynamic linking. - for (size_t i = 0; i < g->link_libs_list.length; i += 1) { - LinkLib *link_lib = g->link_libs_list.at(i); - if (target_is_libc_lib_name(g->zig_target, buf_ptr(link_lib->name))) - continue; - if (target_is_libcpp_lib_name(g->zig_target, buf_ptr(link_lib->name))) - continue; - return true; - } - return false; -} - -static bool detect_pic(CodeGen *g) { - if (target_requires_pic(g->zig_target, g->libc_link_lib != nullptr)) - return true; - switch (g->want_pic) { - case WantPICDisabled: - return false; - case WantPICEnabled: - return true; - case WantPICAuto: - return g->have_dynamic_link; - } - zig_unreachable(); -} - -static bool detect_stack_probing(CodeGen *g) { - if (!target_supports_stack_probing(g->zig_target)) - return false; - switch (g->want_stack_check) { - case WantStackCheckDisabled: - return false; - case WantStackCheckEnabled: - return true; - case WantStackCheckAuto: - return g->build_mode == BuildModeSafeRelease || g->build_mode == BuildModeDebug; - } - zig_unreachable(); -} - -static bool detect_sanitize_c(CodeGen *g) { - if (!target_supports_sanitize_c(g->zig_target)) - return false; - switch (g->want_sanitize_c) { - case WantCSanitizeDisabled: - return false; - case WantCSanitizeEnabled: - return true; - case WantCSanitizeAuto: - return g->build_mode == BuildModeSafeRelease || g->build_mode == BuildModeDebug; - } - zig_unreachable(); -} - // Returns TargetSubsystemAuto to mean "no subsystem" TargetSubsystem detect_subsystem(CodeGen *g) { if (g->subsystem != TargetSubsystemAuto) return g->subsystem; if (g->zig_target->os == OsWindows) { - if (g->have_dllmain_crt_startup || (g->out_type == OutTypeLib && g->is_dynamic)) + if (g->have_dllmain_crt_startup) return TargetSubsystemAuto; if (g->have_c_main || g->is_test_build || g->have_winmain_crt_startup || g->have_wwinmain_crt_startup) return TargetSubsystemConsole; @@ -8831,15 +8678,6 @@ TargetSubsystem detect_subsystem(CodeGen *g) { return TargetSubsystemAuto; } -static bool detect_single_threaded(CodeGen *g) { - if (g->want_single_threaded) - return true; - if (target_is_single_threaded(g->zig_target)) { - return true; - } - return false; -} - static bool detect_err_ret_tracing(CodeGen *g) { return !g->strip_debug_symbols && g->build_mode != BuildModeFastRelease && @@ -8847,30 +8685,30 @@ static bool detect_err_ret_tracing(CodeGen *g) { } static LLVMCodeModel to_llvm_code_model(CodeGen *g) { - switch (g->code_model) { - case CodeModelDefault: - return LLVMCodeModelDefault; - case CodeModelTiny: - return LLVMCodeModelTiny; - case CodeModelSmall: - return LLVMCodeModelSmall; - case CodeModelKernel: - return LLVMCodeModelKernel; - case CodeModelMedium: - return LLVMCodeModelMedium; - case CodeModelLarge: - return LLVMCodeModelLarge; - } + switch (g->code_model) { + case CodeModelDefault: + return LLVMCodeModelDefault; + case CodeModelTiny: + return LLVMCodeModelTiny; + case CodeModelSmall: + return LLVMCodeModelSmall; + case CodeModelKernel: + return LLVMCodeModelKernel; + case CodeModelMedium: + return LLVMCodeModelMedium; + case CodeModelLarge: + return LLVMCodeModelLarge; + } - zig_unreachable(); + zig_unreachable(); } Buf *codegen_generate_builtin_source(CodeGen *g) { - g->have_dynamic_link = detect_dynamic_link(g); - g->have_pic = detect_pic(g); - g->have_stack_probing = detect_stack_probing(g); - g->have_sanitize_c = detect_sanitize_c(g); - g->is_single_threaded = detect_single_threaded(g); + // Note that this only runs when zig0 is building the self-hosted zig compiler code, + // so it makes a few assumption that are always true for that case. Once we have + // built the stage2 zig components then zig is in charge of generating the builtin.zig + // file. + g->have_err_ret_tracing = detect_err_ret_tracing(g); Buf *contents = buf_alloc(); @@ -8884,7 +8722,6 @@ Buf *codegen_generate_builtin_source(CodeGen *g) { const char *name = target_os_name(os_type); if (os_type == g->zig_target->os) { - g->target_os_index = i; cur_os = name; } } @@ -8898,7 +8735,6 @@ Buf *codegen_generate_builtin_source(CodeGen *g) { ZigLLVM_ArchType arch = target_arch_enum(arch_i); const char *arch_name = target_arch_name(arch); if (arch == g->zig_target->arch) { - g->target_arch_index = arch_i; cur_arch = arch_name; } } @@ -8913,7 +8749,6 @@ Buf *codegen_generate_builtin_source(CodeGen *g) { const char *name = target_abi_name(abi); if (abi == g->zig_target->abi) { - g->target_abi_index = i; cur_abi = name; } } @@ -8929,7 +8764,6 @@ Buf *codegen_generate_builtin_source(CodeGen *g) { ZigLLVM_ObjectFormatType target_oformat = target_object_format(g->zig_target); if (oformat == target_oformat) { - g->target_oformat_index = i; cur_obj_fmt = name; } } @@ -8979,23 +8813,9 @@ Buf *codegen_generate_builtin_source(CodeGen *g) { const char *endian_str = g->is_big_endian ? "Endian.Big" : "Endian.Little"; buf_appendf(contents, "pub const endian = %s;\n", endian_str); } - const char *out_type = nullptr; - switch (g->out_type) { - case OutTypeExe: - out_type = "Exe"; - break; - case OutTypeLib: - out_type = "Lib"; - break; - case OutTypeObj: - case OutTypeUnknown: // This happens when running the `zig builtin` command. - out_type = "Obj"; - break; - } - buf_appendf(contents, "pub const output_mode = OutputMode.%s;\n", out_type); - const char *link_type = g->have_dynamic_link ? "Dynamic" : "Static"; - buf_appendf(contents, "pub const link_mode = LinkMode.%s;\n", link_type); - buf_appendf(contents, "pub const is_test = %s;\n", bool_to_str(g->is_test_build)); + buf_appendf(contents, "pub const output_mode = OutputMode.Obj;\n"); + buf_appendf(contents, "pub const link_mode = LinkMode.Static;\n"); + buf_appendf(contents, "pub const is_test = false;\n"); buf_appendf(contents, "pub const single_threaded = %s;\n", bool_to_str(g->is_single_threaded)); buf_append_str(contents, "/// Deprecated: use `std.Target.cpu.arch`\n"); buf_appendf(contents, "pub const arch = Arch.%s;\n", cur_arch); @@ -9018,40 +8838,13 @@ Buf *codegen_generate_builtin_source(CodeGen *g) { } buf_appendf(contents, "pub const object_format = ObjectFormat.%s;\n", cur_obj_fmt); buf_appendf(contents, "pub const mode = %s;\n", build_mode_to_str(g->build_mode)); - buf_appendf(contents, "pub const link_libc = %s;\n", bool_to_str(g->libc_link_lib != nullptr)); - buf_appendf(contents, "pub const link_libcpp = %s;\n", bool_to_str(g->libcpp_link_lib != nullptr)); + buf_appendf(contents, "pub const link_libc = %s;\n", bool_to_str(g->link_libc)); + buf_appendf(contents, "pub const link_libcpp = %s;\n", bool_to_str(g->link_libcpp)); buf_appendf(contents, "pub const have_error_return_tracing = %s;\n", bool_to_str(g->have_err_ret_tracing)); - buf_appendf(contents, "pub const valgrind_support = %s;\n", bool_to_str(want_valgrind_support(g))); + buf_appendf(contents, "pub const valgrind_support = false;\n"); buf_appendf(contents, "pub const position_independent_code = %s;\n", bool_to_str(g->have_pic)); buf_appendf(contents, "pub const strip_debug_info = %s;\n", bool_to_str(g->strip_debug_symbols)); - - { - const char *code_model; - switch (g->code_model) { - case CodeModelDefault: - code_model = "default"; - break; - case CodeModelTiny: - code_model = "tiny"; - break; - case CodeModelSmall: - code_model = "small"; - break; - case CodeModelKernel: - code_model = "kernel"; - break; - case CodeModelMedium: - code_model = "medium"; - break; - case CodeModelLarge: - code_model = "large"; - break; - default: - zig_unreachable(); - } - - buf_appendf(contents, "pub const code_model = CodeModel.%s;\n", code_model); - } + buf_appendf(contents, "pub const code_model = CodeModel.default;\n"); { TargetSubsystem detected_subsystem = detect_subsystem(g); @@ -9060,15 +8853,6 @@ Buf *codegen_generate_builtin_source(CodeGen *g) { } } - if (g->is_test_build) { - buf_appendf(contents, - "pub var test_functions: []TestFn = undefined; // overwritten later\n" - ); - - buf_appendf(contents, "pub const test_io_mode = %s;\n", - g->test_is_evented ? ".evented" : ".blocking"); - } - return contents; } @@ -9077,95 +8861,35 @@ static ZigPackage *create_test_runner_pkg(CodeGen *g) { } static Error define_builtin_compile_vars(CodeGen *g) { + Error err; + if (g->std_package == nullptr) return ErrorNone; - Error err; - - Buf *manifest_dir = buf_alloc(); - os_path_join(get_global_cache_dir(), buf_create_from_str("builtin"), manifest_dir); - - CacheHash cache_hash; - cache_init(&cache_hash, manifest_dir); - - Buf *compiler_id; - if ((err = get_compiler_id(&compiler_id))) - return err; - - // Only a few things affect builtin.zig - cache_buf(&cache_hash, compiler_id); - cache_int(&cache_hash, g->build_mode); - cache_bool(&cache_hash, g->strip_debug_symbols); - cache_int(&cache_hash, g->out_type); - cache_bool(&cache_hash, detect_dynamic_link(g)); - cache_bool(&cache_hash, g->is_test_build); - cache_bool(&cache_hash, g->is_single_threaded); - cache_bool(&cache_hash, g->test_is_evented); - cache_int(&cache_hash, g->code_model); - cache_int(&cache_hash, g->zig_target->is_native_os); - cache_int(&cache_hash, g->zig_target->is_native_cpu); - cache_int(&cache_hash, g->zig_target->arch); - cache_int(&cache_hash, g->zig_target->vendor); - cache_int(&cache_hash, g->zig_target->os); - cache_int(&cache_hash, g->zig_target->abi); - if (g->zig_target->cache_hash != nullptr) { - cache_mem(&cache_hash, g->zig_target->cache_hash, g->zig_target->cache_hash_len); - } - if (g->zig_target->glibc_or_darwin_version != nullptr) { - cache_int(&cache_hash, g->zig_target->glibc_or_darwin_version->major); - cache_int(&cache_hash, g->zig_target->glibc_or_darwin_version->minor); - cache_int(&cache_hash, g->zig_target->glibc_or_darwin_version->patch); - } - cache_bool(&cache_hash, g->have_err_ret_tracing); - cache_bool(&cache_hash, g->libc_link_lib != nullptr); - cache_bool(&cache_hash, g->libcpp_link_lib != nullptr); - cache_bool(&cache_hash, g->valgrind_support); - cache_bool(&cache_hash, g->link_eh_frame_hdr); - cache_int(&cache_hash, detect_subsystem(g)); - - Buf digest = BUF_INIT; - buf_resize(&digest, 0); - if ((err = cache_hit(&cache_hash, &digest))) { - // Treat an invalid format error as a cache miss. - if (err != ErrorInvalidFormat) - return err; - } - - // We should always get a cache hit because there are no - // files in the input hash. - assert(buf_len(&digest) != 0); - - Buf *this_dir = buf_alloc(); - os_path_join(manifest_dir, &digest, this_dir); - - if ((err = os_make_path(this_dir))) - return err; - const char *builtin_zig_basename = "builtin.zig"; - Buf *builtin_zig_path = buf_alloc(); - os_path_join(this_dir, buf_create_from_str(builtin_zig_basename), builtin_zig_path); - bool hit; - if ((err = os_file_exists(builtin_zig_path, &hit))) - return err; Buf *contents; - if (hit) { - contents = buf_alloc(); - if ((err = os_fetch_file_path(builtin_zig_path, contents))) { - fprintf(stderr, "Unable to open '%s': %s\n", buf_ptr(builtin_zig_path), err_str(err)); + if (g->builtin_zig_path == nullptr) { + // Then this is zig0 building stage2. We can make many assumptions about the compilation. + g->builtin_zig_path = buf_alloc(); + os_path_join(g->output_dir, buf_create_from_str(builtin_zig_basename), g->builtin_zig_path); + + contents = codegen_generate_builtin_source(g); + if ((err = os_write_file(g->builtin_zig_path, contents))) { + fprintf(stderr, "Unable to write file '%s': %s\n", buf_ptr(g->builtin_zig_path), err_str(err)); exit(1); } } else { - contents = codegen_generate_builtin_source(g); - if ((err = os_write_file(builtin_zig_path, contents))) { - fprintf(stderr, "Unable to write file '%s': %s\n", buf_ptr(builtin_zig_path), err_str(err)); + contents = buf_alloc(); + if ((err = os_fetch_file_path(g->builtin_zig_path, contents))) { + fprintf(stderr, "unable to open '%s': %s\n", buf_ptr(g->builtin_zig_path), err_str(err)); exit(1); } } assert(g->main_pkg); assert(g->std_package); - g->compile_var_package = new_package(buf_ptr(this_dir), builtin_zig_basename, "builtin"); + g->compile_var_package = new_package(buf_ptr(g->output_dir), builtin_zig_basename, "builtin"); if (g->is_test_build) { if (g->test_runner_package == nullptr) { g->test_runner_package = create_test_runner_pkg(g); @@ -9180,7 +8904,7 @@ static Error define_builtin_compile_vars(CodeGen *g) { g->std_package->package_table.put(buf_create_from_str("builtin"), g->compile_var_package); g->std_package->package_table.put(buf_create_from_str("std"), g->std_package); g->std_package->package_table.put(buf_create_from_str("root"), g->root_pkg); - g->compile_var_import = add_source_file(g, g->compile_var_package, builtin_zig_path, contents, + g->compile_var_import = add_source_file(g, g->compile_var_package, g->builtin_zig_path, contents, SourceKindPkgMain); return ErrorNone; @@ -9190,17 +8914,8 @@ static void init(CodeGen *g) { if (g->module) return; - g->have_dynamic_link = detect_dynamic_link(g); - g->have_pic = detect_pic(g); - g->have_stack_probing = detect_stack_probing(g); - g->have_sanitize_c = detect_sanitize_c(g); - g->is_single_threaded = detect_single_threaded(g); g->have_err_ret_tracing = detect_err_ret_tracing(g); - if (target_is_single_threaded(g->zig_target)) { - g->is_single_threaded = true; - } - assert(g->root_out_name); g->module = LLVMModuleCreateWithName(buf_ptr(g->root_out_name)); @@ -9230,7 +8945,7 @@ static void init(CodeGen *g) { LLVMRelocMode reloc_mode; if (g->have_pic) { reloc_mode = LLVMRelocPIC; - } else if (g->have_dynamic_link) { + } else if (g->link_mode_dynamic) { reloc_mode = LLVMRelocDynamicNoPic; } else { reloc_mode = LLVMRelocStatic; @@ -9336,446 +9051,6 @@ static void init(CodeGen *g) { } } -static void detect_libc(CodeGen *g) { - Error err; - - if (g->libc != nullptr || g->libc_link_lib == nullptr) - return; - - if (target_can_build_libc(g->zig_target)) { - const char *generic_name = target_libc_generic_name(g->zig_target); - const char *arch_name = target_arch_name(g->zig_target->arch); - const char *abi_name = target_abi_name(g->zig_target->abi); - if (target_is_musl(g->zig_target)) { - // musl has some overrides. its headers are ABI-agnostic and so they all have the "musl" ABI name. - abi_name = "musl"; - // some architectures are handled by the same set of headers - arch_name = target_arch_musl_name(g->zig_target->arch); - } - Buf *arch_include_dir = buf_sprintf("%s" OS_SEP "libc" OS_SEP "include" OS_SEP "%s-%s-%s", - buf_ptr(g->zig_lib_dir), arch_name, target_os_name(g->zig_target->os), abi_name); - Buf *generic_include_dir = buf_sprintf("%s" OS_SEP "libc" OS_SEP "include" OS_SEP "generic-%s", - buf_ptr(g->zig_lib_dir), generic_name); - Buf *arch_os_include_dir = buf_sprintf("%s" OS_SEP "libc" OS_SEP "include" OS_SEP "%s-%s-any", - buf_ptr(g->zig_lib_dir), target_arch_name(g->zig_target->arch), target_os_name(g->zig_target->os)); - Buf *generic_os_include_dir = buf_sprintf("%s" OS_SEP "libc" OS_SEP "include" OS_SEP "any-%s-any", - buf_ptr(g->zig_lib_dir), target_os_name(g->zig_target->os)); - - g->libc_include_dir_len = 4; - g->libc_include_dir_list = heap::c_allocator.allocate(g->libc_include_dir_len); - g->libc_include_dir_list[0] = buf_ptr(arch_include_dir); - g->libc_include_dir_list[1] = buf_ptr(generic_include_dir); - g->libc_include_dir_list[2] = buf_ptr(arch_os_include_dir); - g->libc_include_dir_list[3] = buf_ptr(generic_os_include_dir); - return; - } - - if (g->zig_target->is_native_os) { - g->libc = heap::c_allocator.create(); - - if ((err = stage2_libc_find_native(g->libc))) { - fprintf(stderr, - "Unable to link against libc: Unable to find libc installation: %s\n" - "See `zig libc --help` for more details.\n", err_str(err)); - exit(1); - } - - bool want_sys_dir = !mem_eql_mem(g->libc->include_dir, g->libc->include_dir_len, - g->libc->sys_include_dir, g->libc->sys_include_dir_len); - size_t want_um_and_shared_dirs = (g->zig_target->os == OsWindows) ? 2 : 0; - size_t dir_count = 1 + want_sys_dir + want_um_and_shared_dirs; - g->libc_include_dir_len = 0; - g->libc_include_dir_list = heap::c_allocator.allocate(dir_count); - - g->libc_include_dir_list[g->libc_include_dir_len] = buf_ptr(buf_create_from_mem( - g->libc->include_dir, g->libc->include_dir_len)); - g->libc_include_dir_len += 1; - - if (want_sys_dir) { - g->libc_include_dir_list[g->libc_include_dir_len] = buf_ptr(buf_create_from_mem( - g->libc->sys_include_dir, g->libc->sys_include_dir_len)); - g->libc_include_dir_len += 1; - } - - if (want_um_and_shared_dirs != 0) { - Buf *include_dir_parent = buf_alloc(); - os_path_join(buf_create_from_mem(g->libc->include_dir, g->libc->include_dir_len), - buf_create_from_str(".."), include_dir_parent); - - Buf *buff1 = buf_alloc(); - os_path_join(include_dir_parent, buf_create_from_str("um"), buff1); - g->libc_include_dir_list[g->libc_include_dir_len] = buf_ptr(buff1); - g->libc_include_dir_len += 1; - - Buf *buff2 = buf_alloc(); - os_path_join(include_dir_parent, buf_create_from_str("shared"), buff2); - g->libc_include_dir_list[g->libc_include_dir_len] = buf_ptr(buff2); - g->libc_include_dir_len += 1; - } - assert(g->libc_include_dir_len == dir_count); - } else if ((g->out_type == OutTypeExe || (g->out_type == OutTypeLib && g->is_dynamic)) && - !target_os_is_darwin(g->zig_target->os)) - { - Buf triple_buf = BUF_INIT; - target_triple_zig(&triple_buf, g->zig_target); - fprintf(stderr, - "Zig is unable to provide a libc for the chosen target '%s'.\n" - "The target is non-native, so Zig also cannot use the native libc installation.\n" - "Choose a target which has a libc available (see `zig targets`), or\n" - "provide a libc installation text file (see `zig libc --help`).\n", buf_ptr(&triple_buf)); - exit(1); - } -} - -// does not add the "cc" arg -void add_cc_args(CodeGen *g, ZigList &args, const char *out_dep_path, - bool translate_c, FileExt source_kind) -{ - if (translate_c) { - args.append("-x"); - args.append("c"); - } - - args.append("-nostdinc"); - if (source_kind == FileExtCpp) { - args.append("-nostdinc++"); - } - args.append("-fno-spell-checking"); - - if (g->function_sections) { - args.append("-ffunction-sections"); - } - - if (!translate_c) { - switch (g->err_color) { - case ErrColorAuto: - break; - case ErrColorOff: - args.append("-fno-color-diagnostics"); - args.append("-fno-caret-diagnostics"); - break; - case ErrColorOn: - args.append("-fcolor-diagnostics"); - args.append("-fcaret-diagnostics"); - break; - } - } - - for (size_t i = 0; i < g->framework_dirs.length; i += 1) { - args.append("-iframework"); - args.append(g->framework_dirs.at(i)); - } - - if (g->libcpp_link_lib != nullptr) { - const char *libcxx_include_path = buf_ptr(buf_sprintf("%s" OS_SEP "libcxx" OS_SEP "include", - buf_ptr(g->zig_lib_dir))); - - const char *libcxxabi_include_path = buf_ptr(buf_sprintf("%s" OS_SEP "libcxxabi" OS_SEP "include", - buf_ptr(g->zig_lib_dir))); - - args.append("-isystem"); - args.append(libcxx_include_path); - - args.append("-isystem"); - args.append(libcxxabi_include_path); - - if (target_abi_is_musl(g->zig_target->abi)) { - args.append("-D_LIBCPP_HAS_MUSL_LIBC"); - } - args.append("-D_LIBCPP_DISABLE_VISIBILITY_ANNOTATIONS"); - args.append("-D_LIBCXXABI_DISABLE_VISIBILITY_ANNOTATIONS"); - } - - args.append("-target"); - args.append(buf_ptr(&g->llvm_triple_str)); - - switch (source_kind) { - case FileExtC: - case FileExtCpp: - case FileExtHeader: - // According to Rich Felker libc headers are supposed to go before C language headers. - // However as noted by @dimenus, appending libc headers before c_headers breaks intrinsics - // and other compiler specific items. - args.append("-isystem"); - args.append(buf_ptr(g->zig_c_headers_dir)); - - for (size_t i = 0; i < g->libc_include_dir_len; i += 1) { - const char *include_dir = g->libc_include_dir_list[i]; - args.append("-isystem"); - args.append(include_dir); - } - - if (g->zig_target->llvm_cpu_name != nullptr) { - args.append("-Xclang"); - args.append("-target-cpu"); - args.append("-Xclang"); - args.append(g->zig_target->llvm_cpu_name); - } - if (g->zig_target->llvm_cpu_features != nullptr) { - // https://github.com/ziglang/zig/issues/5017 - SplitIterator it = memSplit(str(g->zig_target->llvm_cpu_features), str(",")); - Optional> flag = SplitIterator_next(&it); - while (flag.is_some) { - args.append("-Xclang"); - args.append("-target-feature"); - args.append("-Xclang"); - args.append(buf_ptr(buf_create_from_slice(flag.value))); - flag = SplitIterator_next(&it); - } - } - if (translate_c) { - // this gives us access to preprocessing entities, presumably at - // the cost of performance - args.append("-Xclang"); - args.append("-detailed-preprocessing-record"); - } - if (out_dep_path != nullptr) { - args.append("-MD"); - args.append("-MV"); - args.append("-MF"); - args.append(out_dep_path); - } - break; - case FileExtAsm: - case FileExtLLVMIr: - case FileExtLLVMBitCode: - case FileExtUnknown: - break; - } - for (size_t i = 0; i < g->zig_target->llvm_cpu_features_asm_len; i += 1) { - args.append(g->zig_target->llvm_cpu_features_asm_ptr[i]); - } - - if (g->zig_target->os == OsFreestanding) { - args.append("-ffreestanding"); - } - - // windows.h has files such as pshpack1.h which do #pragma packing, triggering a clang warning. - // So for this target, we disable this warning. - if (g->zig_target->os == OsWindows && target_abi_is_gnu(g->zig_target->abi)) { - args.append("-Wno-pragma-pack"); - } - - if (!g->strip_debug_symbols) { - args.append("-g"); - } - - if (codegen_have_frame_pointer(g)) { - args.append("-fno-omit-frame-pointer"); - } else { - args.append("-fomit-frame-pointer"); - } - - if (g->have_sanitize_c) { - args.append("-fsanitize=undefined"); - args.append("-fsanitize-trap=undefined"); - } - - switch (g->build_mode) { - case BuildModeDebug: - // windows c runtime requires -D_DEBUG if using debug libraries - args.append("-D_DEBUG"); - args.append("-Og"); - - if (g->libc_link_lib != nullptr) { - args.append("-fstack-protector-strong"); - args.append("--param"); - args.append("ssp-buffer-size=4"); - } else { - args.append("-fno-stack-protector"); - } - break; - case BuildModeSafeRelease: - // See the comment in the BuildModeFastRelease case for why we pass -O2 rather - // than -O3 here. - args.append("-O2"); - if (g->libc_link_lib != nullptr) { - args.append("-D_FORTIFY_SOURCE=2"); - args.append("-fstack-protector-strong"); - args.append("--param"); - args.append("ssp-buffer-size=4"); - } else { - args.append("-fno-stack-protector"); - } - break; - case BuildModeFastRelease: - args.append("-DNDEBUG"); - // Here we pass -O2 rather than -O3 because, although we do the equivalent of - // -O3 in Zig code, the justification for the difference here is that Zig - // has better detection and prevention of undefined behavior, so -O3 is safer for - // Zig code than it is for C code. Also, C programmers are used to their code - // running in -O2 and thus the -O3 path has been tested less. - args.append("-O2"); - args.append("-fno-stack-protector"); - break; - case BuildModeSmallRelease: - args.append("-DNDEBUG"); - args.append("-Os"); - args.append("-fno-stack-protector"); - break; - } - - if (target_supports_fpic(g->zig_target) && g->have_pic) { - args.append("-fPIC"); - } - - for (size_t arg_i = 0; arg_i < g->clang_argv_len; arg_i += 1) { - args.append(g->clang_argv[arg_i]); - } - -} - -void codegen_translate_c(CodeGen *g, Buf *full_path) { - Error err; - - Buf *src_basename = buf_alloc(); - Buf *src_dirname = buf_alloc(); - os_path_split(full_path, src_dirname, src_basename); - - Buf noextname = BUF_INIT; - os_path_extname(src_basename, &noextname, nullptr); - - Buf *zig_basename = buf_sprintf("%s.zig", buf_ptr(&noextname)); - - detect_libc(g); - - Buf cache_digest = BUF_INIT; - buf_resize(&cache_digest, 0); - - CacheHash *cache_hash = nullptr; - if (g->enable_cache) { - if ((err = create_c_object_cache(g, &cache_hash, true))) { - // Already printed error; verbose = true - exit(1); - } - cache_file(cache_hash, full_path); - // to distinguish from generating a C object - cache_buf(cache_hash, buf_create_from_str("translate-c")); - - if ((err = cache_hit(cache_hash, &cache_digest))) { - if (err != ErrorInvalidFormat) { - fprintf(stderr, "unable to check cache: %s\n", err_str(err)); - exit(1); - } - } - if (cache_hash->manifest_file_path != nullptr) { - g->caches_to_release.append(cache_hash); - } - } - - if (g->enable_cache && buf_len(&cache_digest) != 0) { - // cache hit - Buf *cached_path = buf_sprintf("%s" OS_SEP CACHE_OUT_SUBDIR OS_SEP "%s" OS_SEP "%s", - buf_ptr(g->cache_dir), buf_ptr(&cache_digest), buf_ptr(zig_basename)); - fprintf(stdout, "%s\n", buf_ptr(cached_path)); - return; - } - - // cache miss or cache disabled - init(g); - - Buf *out_dep_path = nullptr; - const char *out_dep_path_cstr = nullptr; - - if (g->enable_cache) { - buf_alloc();// we can't know the digest until we do the C compiler invocation, so we - // need a tmp filename. - out_dep_path = buf_alloc(); - if ((err = get_tmp_filename(g, out_dep_path, buf_sprintf("%s.d", buf_ptr(zig_basename))))) { - fprintf(stderr, "unable to create tmp dir: %s\n", err_str(err)); - exit(1); - } - out_dep_path_cstr = buf_ptr(out_dep_path); - } - - ZigList clang_argv = {0}; - add_cc_args(g, clang_argv, out_dep_path_cstr, true, FileExtC); - - clang_argv.append(buf_ptr(full_path)); - - if (g->verbose_cc) { - fprintf(stderr, "clang"); - for (size_t i = 0; i < clang_argv.length; i += 1) { - fprintf(stderr, " %s", clang_argv.at(i)); - } - fprintf(stderr, "\n"); - } - - clang_argv.append(nullptr); // to make the [start...end] argument work - - const char *resources_path = buf_ptr(g->zig_c_headers_dir); - Stage2ErrorMsg *errors_ptr; - size_t errors_len; - Stage2Ast *ast; - - err = stage2_translate_c(&ast, &errors_ptr, &errors_len, - &clang_argv.at(0), &clang_argv.last(), resources_path); - - if (err == ErrorCCompileErrors && errors_len > 0) { - for (size_t i = 0; i < errors_len; i += 1) { - Stage2ErrorMsg *clang_err = &errors_ptr[i]; - - ErrorMsg *err_msg = err_msg_create_with_offset( - clang_err->filename_ptr ? - buf_create_from_mem(clang_err->filename_ptr, clang_err->filename_len) : nullptr, - clang_err->line, clang_err->column, clang_err->offset, clang_err->source, - buf_create_from_mem(clang_err->msg_ptr, clang_err->msg_len)); - print_err_msg(err_msg, g->err_color); - } - exit(1); - } - - if (err) { - fprintf(stderr, "unable to parse C file: %s\n", err_str(err)); - exit(1); - } - - if (!g->enable_cache) { - stage2_render_ast(ast, stdout); - return; - } - - // add the files depended on to the cache system - if ((err = cache_add_dep_file(cache_hash, out_dep_path, true))) { - // Don't treat the absence of the .d file as a fatal error, the - // compiler may not produce one eg. when compiling .s files - if (err != ErrorFileNotFound) { - fprintf(stderr, "Failed to add C source dependencies to cache: %s\n", err_str(err)); - exit(1); - } - } - if (err != ErrorFileNotFound) { - os_delete_file(out_dep_path); - } - - if ((err = cache_final(cache_hash, &cache_digest))) { - fprintf(stderr, "Unable to finalize cache hash: %s\n", err_str(err)); - exit(1); - } - - Buf *artifact_dir = buf_sprintf("%s" OS_SEP CACHE_OUT_SUBDIR OS_SEP "%s", - buf_ptr(g->cache_dir), buf_ptr(&cache_digest)); - - if ((err = os_make_path(artifact_dir))) { - fprintf(stderr, "Unable to make dir: %s\n", err_str(err)); - exit(1); - } - - Buf *cached_path = buf_sprintf("%s" OS_SEP "%s", buf_ptr(artifact_dir), buf_ptr(zig_basename)); - - FILE *out_file = fopen(buf_ptr(cached_path), "wb"); - if (out_file == nullptr) { - fprintf(stderr, "Unable to open output file: %s\n", strerror(errno)); - exit(1); - } - stage2_render_ast(ast, out_file); - if (fclose(out_file) != 0) { - fprintf(stderr, "Unable to write to output file: %s\n", strerror(errno)); - exit(1); - } - fprintf(stdout, "%s\n", buf_ptr(cached_path)); -} - static void update_test_functions_builtin_decl(CodeGen *g) { Error err; @@ -9875,49 +9150,46 @@ static void gen_root_source(CodeGen *g) { assert(root_import_alias == g->root_import); assert(g->root_out_name); - assert(g->out_type != OutTypeUnknown); - if (!g->is_dummy_so) { - // Zig has lazy top level definitions. Here we semantically analyze the panic function. - Buf *import_target_path; - Buf full_path = BUF_INIT; - ZigType *std_import; - if ((err = analyze_import(g, g->root_import, buf_create_from_str("std"), &std_import, - &import_target_path, &full_path))) - { - if (err == ErrorFileNotFound) { - fprintf(stderr, "unable to find '%s'", buf_ptr(import_target_path)); - } else { - fprintf(stderr, "unable to open '%s': %s\n", buf_ptr(&full_path), err_str(err)); - } - exit(1); + // Zig has lazy top level definitions. Here we semantically analyze the panic function. + Buf *import_target_path; + Buf full_path = BUF_INIT; + ZigType *std_import; + if ((err = analyze_import(g, g->root_import, buf_create_from_str("std"), &std_import, + &import_target_path, &full_path))) + { + if (err == ErrorFileNotFound) { + fprintf(stderr, "unable to find '%s'", buf_ptr(import_target_path)); + } else { + fprintf(stderr, "unable to open '%s': %s\n", buf_ptr(&full_path), err_str(err)); } - - Tld *builtin_tld = find_decl(g, &get_container_scope(std_import)->base, - buf_create_from_str("builtin")); - assert(builtin_tld != nullptr); - resolve_top_level_decl(g, builtin_tld, nullptr, false); - report_errors_and_maybe_exit(g); - assert(builtin_tld->id == TldIdVar); - TldVar *builtin_tld_var = (TldVar*)builtin_tld; - ZigValue *builtin_val = builtin_tld_var->var->const_value; - assert(builtin_val->type->id == ZigTypeIdMetaType); - ZigType *builtin_type = builtin_val->data.x_type; - - Tld *panic_tld = find_decl(g, &get_container_scope(builtin_type)->base, - buf_create_from_str("panic")); - assert(panic_tld != nullptr); - resolve_top_level_decl(g, panic_tld, nullptr, false); - report_errors_and_maybe_exit(g); - assert(panic_tld->id == TldIdVar); - TldVar *panic_tld_var = (TldVar*)panic_tld; - ZigValue *panic_fn_val = panic_tld_var->var->const_value; - assert(panic_fn_val->type->id == ZigTypeIdFn); - assert(panic_fn_val->data.x_ptr.special == ConstPtrSpecialFunction); - g->panic_fn = panic_fn_val->data.x_ptr.data.fn.fn_entry; - assert(g->panic_fn != nullptr); + exit(1); } + Tld *builtin_tld = find_decl(g, &get_container_scope(std_import)->base, + buf_create_from_str("builtin")); + assert(builtin_tld != nullptr); + resolve_top_level_decl(g, builtin_tld, nullptr, false); + report_errors_and_maybe_exit(g); + assert(builtin_tld->id == TldIdVar); + TldVar *builtin_tld_var = (TldVar*)builtin_tld; + ZigValue *builtin_val = builtin_tld_var->var->const_value; + assert(builtin_val->type->id == ZigTypeIdMetaType); + ZigType *builtin_type = builtin_val->data.x_type; + + Tld *panic_tld = find_decl(g, &get_container_scope(builtin_type)->base, + buf_create_from_str("panic")); + assert(panic_tld != nullptr); + resolve_top_level_decl(g, panic_tld, nullptr, false); + report_errors_and_maybe_exit(g); + assert(panic_tld->id == TldIdVar); + TldVar *panic_tld_var = (TldVar*)panic_tld; + ZigValue *panic_fn_val = panic_tld_var->var->const_value; + assert(panic_fn_val->type->id == ZigTypeIdFn); + assert(panic_fn_val->data.x_ptr.special == ConstPtrSpecialFunction); + g->panic_fn = panic_fn_val->data.x_ptr.data.fn.fn_entry; + assert(g->panic_fn != nullptr); + if (!g->error_during_imports) { semantic_analyze(g); } @@ -9934,781 +9206,6 @@ static void gen_root_source(CodeGen *g) { } -static void print_zig_cc_cmd(ZigList *args) { - for (size_t arg_i = 0; arg_i < args->length; arg_i += 1) { - const char *space_str = (arg_i == 0) ? "" : " "; - fprintf(stderr, "%s%s", space_str, args->at(arg_i)); - } - fprintf(stderr, "\n"); -} - -// Caller should delete the file when done or rename it into a better location. -static Error get_tmp_filename(CodeGen *g, Buf *out, Buf *suffix) { - Error err; - buf_resize(out, 0); - os_path_join(g->cache_dir, buf_create_from_str("tmp" OS_SEP), out); - if ((err = os_make_path(out))) { - return err; - } - const char base64[] = "abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789-_"; - assert(array_length(base64) == 64 + 1); - for (size_t i = 0; i < 12; i += 1) { - buf_append_char(out, base64[rand() % 64]); - } - buf_append_char(out, '-'); - buf_append_buf(out, suffix); - return ErrorNone; -} - -Error create_c_object_cache(CodeGen *g, CacheHash **out_cache_hash, bool verbose) { - Error err; - CacheHash *cache_hash = heap::c_allocator.create(); - Buf *manifest_dir = buf_sprintf("%s" OS_SEP CACHE_HASH_SUBDIR, buf_ptr(g->cache_dir)); - cache_init(cache_hash, manifest_dir); - - Buf *compiler_id; - if ((err = get_compiler_id(&compiler_id))) { - if (verbose) { - fprintf(stderr, "unable to get compiler id: %s\n", err_str(err)); - } - return err; - } - cache_buf(cache_hash, compiler_id); - cache_int(cache_hash, g->err_color); - cache_list_of_str(cache_hash, g->framework_dirs.items, g->framework_dirs.length); - cache_bool(cache_hash, g->libcpp_link_lib != nullptr); - cache_buf(cache_hash, g->zig_lib_dir); - cache_buf(cache_hash, g->zig_c_headers_dir); - cache_list_of_str(cache_hash, g->libc_include_dir_list, g->libc_include_dir_len); - cache_int(cache_hash, g->zig_target->is_native_os); - cache_int(cache_hash, g->zig_target->is_native_cpu); - cache_int(cache_hash, g->zig_target->arch); - cache_int(cache_hash, g->zig_target->vendor); - cache_int(cache_hash, g->zig_target->os); - cache_int(cache_hash, g->zig_target->abi); - cache_bool(cache_hash, g->strip_debug_symbols); - cache_int(cache_hash, g->build_mode); - cache_bool(cache_hash, g->have_pic); - cache_bool(cache_hash, g->have_sanitize_c); - cache_bool(cache_hash, want_valgrind_support(g)); - cache_bool(cache_hash, g->function_sections); - cache_int(cache_hash, g->code_model); - cache_bool(cache_hash, codegen_have_frame_pointer(g)); - cache_bool(cache_hash, g->libc_link_lib); - if (g->zig_target->cache_hash != nullptr) { - cache_mem(cache_hash, g->zig_target->cache_hash, g->zig_target->cache_hash_len); - } - - for (size_t arg_i = 0; arg_i < g->clang_argv_len; arg_i += 1) { - cache_str(cache_hash, g->clang_argv[arg_i]); - } - - *out_cache_hash = cache_hash; - return ErrorNone; -} - -static bool need_llvm_module(CodeGen *g) { - return buf_len(&g->main_pkg->root_src_path) != 0; -} - -// before gen_c_objects -static bool main_output_dir_is_just_one_c_object_pre(CodeGen *g) { - return g->enable_cache && g->c_source_files.length == 1 && !need_llvm_module(g) && - g->out_type == OutTypeObj && g->link_objects.length == 0; -} - -// after gen_c_objects -static bool main_output_dir_is_just_one_c_object_post(CodeGen *g) { - return g->enable_cache && g->link_objects.length == 1 && !need_llvm_module(g) && g->out_type == OutTypeObj; -} - -// returns true if it was a cache miss -static void gen_c_object(CodeGen *g, Buf *self_exe_path, CFile *c_file) { - Error err; - - Buf *artifact_dir; - Buf *o_final_path; - - Buf *o_dir = buf_sprintf("%s" OS_SEP CACHE_OUT_SUBDIR, buf_ptr(g->cache_dir)); - - Buf *c_source_file = buf_create_from_str(c_file->source_path); - Buf *c_source_basename = buf_alloc(); - os_path_split(c_source_file, nullptr, c_source_basename); - - Stage2ProgressNode *child_prog_node = stage2_progress_start(g->sub_progress_node, buf_ptr(c_source_basename), - buf_len(c_source_basename), 0); - - Buf *final_o_basename = buf_alloc(); - if (c_file->preprocessor_only_basename == nullptr) { - // We special case when doing build-obj for just one C file - if (main_output_dir_is_just_one_c_object_pre(g)) { - buf_init_from_buf(final_o_basename, g->root_out_name); - } else { - os_path_extname(c_source_basename, final_o_basename, nullptr); - } - buf_append_str(final_o_basename, target_o_file_ext(g->zig_target)); - } else { - buf_init_from_str(final_o_basename, c_file->preprocessor_only_basename); - } - - CacheHash *cache_hash; - if ((err = create_c_object_cache(g, &cache_hash, true))) { - // Already printed error; verbose = true - exit(1); - } - cache_file(cache_hash, c_source_file); - - // Note: not directory args, just args that always have a file next - static const char *file_args[] = { - "-include", - }; - for (size_t arg_i = 0; arg_i < c_file->args.length; arg_i += 1) { - const char *arg = c_file->args.at(arg_i); - cache_str(cache_hash, arg); - for (size_t file_arg_i = 0; file_arg_i < array_length(file_args); file_arg_i += 1) { - if (strcmp(arg, file_args[file_arg_i]) == 0 && arg_i + 1 < c_file->args.length) { - arg_i += 1; - cache_file(cache_hash, buf_create_from_str(c_file->args.at(arg_i))); - } - } - } - - Buf digest = BUF_INIT; - buf_resize(&digest, 0); - if ((err = cache_hit(cache_hash, &digest))) { - if (err != ErrorInvalidFormat) { - if (err == ErrorCacheUnavailable) { - // already printed error - } else { - fprintf(stderr, "unable to check cache when compiling C object: %s\n", err_str(err)); - } - exit(1); - } - } - bool is_cache_miss = g->disable_c_depfile || (buf_len(&digest) == 0); - if (is_cache_miss) { - // we can't know the digest until we do the C compiler invocation, so we - // need a tmp filename. - Buf *out_obj_path = buf_alloc(); - if ((err = get_tmp_filename(g, out_obj_path, final_o_basename))) { - fprintf(stderr, "unable to create tmp dir: %s\n", err_str(err)); - exit(1); - } - - Termination term; - ZigList args = {}; - args.append(buf_ptr(self_exe_path)); - args.append("clang"); - - if (c_file->preprocessor_only_basename == nullptr) { - args.append("-c"); - } - - Buf *out_dep_path = g->disable_c_depfile ? nullptr : buf_sprintf("%s.d", buf_ptr(out_obj_path)); - const char *out_dep_path_cstr = (out_dep_path == nullptr) ? nullptr : buf_ptr(out_dep_path); - FileExt ext = classify_file_ext(buf_ptr(c_source_basename), buf_len(c_source_basename)); - add_cc_args(g, args, out_dep_path_cstr, false, ext); - - args.append("-o"); - args.append(buf_ptr(out_obj_path)); - - args.append(buf_ptr(c_source_file)); - - for (size_t arg_i = 0; arg_i < c_file->args.length; arg_i += 1) { - args.append(c_file->args.at(arg_i)); - } - - if (g->verbose_cc) { - print_zig_cc_cmd(&args); - } - os_spawn_process(args, &term); - if (term.how != TerminationIdClean || term.code != 0) { - fprintf(stderr, "\nThe following command failed:\n"); - print_zig_cc_cmd(&args); - exit(1); - } - - if (out_dep_path != nullptr) { - // add the files depended on to the cache system - if ((err = cache_add_dep_file(cache_hash, out_dep_path, true))) { - // Don't treat the absence of the .d file as a fatal error, the - // compiler may not produce one eg. when compiling .s files - if (err != ErrorFileNotFound) { - fprintf(stderr, "Failed to add C source dependencies to cache: %s\n", err_str(err)); - exit(1); - } - } - if (err != ErrorFileNotFound) { - os_delete_file(out_dep_path); - } - - if ((err = cache_final(cache_hash, &digest))) { - fprintf(stderr, "Unable to finalize cache hash: %s\n", err_str(err)); - exit(1); - } - } - artifact_dir = buf_alloc(); - os_path_join(o_dir, &digest, artifact_dir); - if ((err = os_make_path(artifact_dir))) { - fprintf(stderr, "Unable to create output directory '%s': %s", - buf_ptr(artifact_dir), err_str(err)); - exit(1); - } - o_final_path = buf_alloc(); - os_path_join(artifact_dir, final_o_basename, o_final_path); - if ((err = os_rename(out_obj_path, o_final_path))) { - fprintf(stderr, "Unable to rename object: %s\n", err_str(err)); - exit(1); - } - } else { - // cache hit - artifact_dir = buf_alloc(); - os_path_join(o_dir, &digest, artifact_dir); - o_final_path = buf_alloc(); - os_path_join(artifact_dir, final_o_basename, o_final_path); - } - - g->c_artifact_dir = artifact_dir; - g->link_objects.append(o_final_path); - g->caches_to_release.append(cache_hash); - - stage2_progress_end(child_prog_node); -} - -// returns true if we had any cache misses -static void gen_c_objects(CodeGen *g) { - Error err; - - if (g->c_source_files.length == 0) - return; - - Buf *self_exe_path = buf_alloc(); - if ((err = os_self_exe_path(self_exe_path))) { - fprintf(stderr, "Unable to get self exe path: %s\n", err_str(err)); - exit(1); - } - - codegen_add_time_event(g, "Compile C Objects"); - const char *c_prog_name = "Compile C Objects"; - codegen_switch_sub_prog_node(g, stage2_progress_start(g->main_progress_node, c_prog_name, strlen(c_prog_name), - g->c_source_files.length)); - - for (size_t c_file_i = 0; c_file_i < g->c_source_files.length; c_file_i += 1) { - CFile *c_file = g->c_source_files.at(c_file_i); - gen_c_object(g, self_exe_path, c_file); - } -} - -void codegen_add_object(CodeGen *g, Buf *object_path) { - g->link_objects.append(object_path); -} - -// Must be coordinated with with CIntType enum -static const char *c_int_type_names[] = { - "short", - "unsigned short", - "int", - "unsigned int", - "long", - "unsigned long", - "long long", - "unsigned long long", -}; - -struct GenH { - ZigList types_to_declare; -}; - -static void prepend_c_type_to_decl_list(CodeGen *g, GenH *gen_h, ZigType *type_entry) { - if (type_entry->gen_h_loop_flag) - return; - type_entry->gen_h_loop_flag = true; - - switch (type_entry->id) { - case ZigTypeIdInvalid: - case ZigTypeIdMetaType: - case ZigTypeIdComptimeFloat: - case ZigTypeIdComptimeInt: - case ZigTypeIdEnumLiteral: - case ZigTypeIdUndefined: - case ZigTypeIdNull: - case ZigTypeIdBoundFn: - case ZigTypeIdErrorUnion: - case ZigTypeIdErrorSet: - case ZigTypeIdFnFrame: - case ZigTypeIdAnyFrame: - zig_unreachable(); - case ZigTypeIdVoid: - case ZigTypeIdUnreachable: - return; - case ZigTypeIdBool: - g->c_want_stdbool = true; - return; - case ZigTypeIdInt: - g->c_want_stdint = true; - return; - case ZigTypeIdFloat: - return; - case ZigTypeIdOpaque: - gen_h->types_to_declare.append(type_entry); - return; - case ZigTypeIdStruct: - if(type_entry->data.structure.layout == ContainerLayoutExtern) { - for (uint32_t i = 0; i < type_entry->data.structure.src_field_count; i += 1) { - TypeStructField *field = type_entry->data.structure.fields[i]; - prepend_c_type_to_decl_list(g, gen_h, field->type_entry); - } - } - gen_h->types_to_declare.append(type_entry); - return; - case ZigTypeIdUnion: - for (uint32_t i = 0; i < type_entry->data.unionation.src_field_count; i += 1) { - TypeUnionField *field = &type_entry->data.unionation.fields[i]; - prepend_c_type_to_decl_list(g, gen_h, field->type_entry); - } - gen_h->types_to_declare.append(type_entry); - return; - case ZigTypeIdEnum: - prepend_c_type_to_decl_list(g, gen_h, type_entry->data.enumeration.tag_int_type); - gen_h->types_to_declare.append(type_entry); - return; - case ZigTypeIdPointer: - prepend_c_type_to_decl_list(g, gen_h, type_entry->data.pointer.child_type); - return; - case ZigTypeIdArray: - prepend_c_type_to_decl_list(g, gen_h, type_entry->data.array.child_type); - return; - case ZigTypeIdVector: - prepend_c_type_to_decl_list(g, gen_h, type_entry->data.vector.elem_type); - return; - case ZigTypeIdOptional: - prepend_c_type_to_decl_list(g, gen_h, type_entry->data.maybe.child_type); - return; - case ZigTypeIdFn: - for (size_t i = 0; i < type_entry->data.fn.fn_type_id.param_count; i += 1) { - prepend_c_type_to_decl_list(g, gen_h, type_entry->data.fn.fn_type_id.param_info[i].type); - } - prepend_c_type_to_decl_list(g, gen_h, type_entry->data.fn.fn_type_id.return_type); - return; - } -} - -static void get_c_type(CodeGen *g, GenH *gen_h, ZigType *type_entry, Buf *out_buf) { - assert(type_entry); - - for (size_t i = 0; i < array_length(c_int_type_names); i += 1) { - if (type_entry == g->builtin_types.entry_c_int[i]) { - buf_init_from_str(out_buf, c_int_type_names[i]); - return; - } - } - if (type_entry == g->builtin_types.entry_c_longdouble) { - buf_init_from_str(out_buf, "long double"); - return; - } - if (type_entry == g->builtin_types.entry_c_void) { - buf_init_from_str(out_buf, "void"); - return; - } - if (type_entry == g->builtin_types.entry_isize) { - g->c_want_stdint = true; - buf_init_from_str(out_buf, "intptr_t"); - return; - } - if (type_entry == g->builtin_types.entry_usize) { - g->c_want_stdint = true; - buf_init_from_str(out_buf, "uintptr_t"); - return; - } - - prepend_c_type_to_decl_list(g, gen_h, type_entry); - - switch (type_entry->id) { - case ZigTypeIdVoid: - buf_init_from_str(out_buf, "void"); - break; - case ZigTypeIdBool: - buf_init_from_str(out_buf, "bool"); - break; - case ZigTypeIdUnreachable: - buf_init_from_str(out_buf, "__attribute__((__noreturn__)) void"); - break; - case ZigTypeIdFloat: - switch (type_entry->data.floating.bit_count) { - case 32: - buf_init_from_str(out_buf, "float"); - break; - case 64: - buf_init_from_str(out_buf, "double"); - break; - case 80: - buf_init_from_str(out_buf, "__float80"); - break; - case 128: - buf_init_from_str(out_buf, "__float128"); - break; - default: - zig_unreachable(); - } - break; - case ZigTypeIdInt: - buf_resize(out_buf, 0); - buf_appendf(out_buf, "%sint%" PRIu32 "_t", - type_entry->data.integral.is_signed ? "" : "u", - type_entry->data.integral.bit_count); - break; - case ZigTypeIdPointer: - { - Buf child_buf = BUF_INIT; - ZigType *child_type = type_entry->data.pointer.child_type; - get_c_type(g, gen_h, child_type, &child_buf); - - const char *const_str = type_entry->data.pointer.is_const ? "const " : ""; - buf_resize(out_buf, 0); - buf_appendf(out_buf, "%s%s *", const_str, buf_ptr(&child_buf)); - break; - } - case ZigTypeIdOptional: - { - ZigType *child_type = type_entry->data.maybe.child_type; - if (!type_has_bits(g, child_type)) { - buf_init_from_str(out_buf, "bool"); - return; - } else if (type_is_nonnull_ptr(g, child_type)) { - return get_c_type(g, gen_h, child_type, out_buf); - } else { - zig_unreachable(); - } - } - case ZigTypeIdStruct: - case ZigTypeIdOpaque: - { - buf_init_from_str(out_buf, "struct "); - buf_append_buf(out_buf, type_h_name(type_entry)); - return; - } - case ZigTypeIdUnion: - { - buf_init_from_str(out_buf, "union "); - buf_append_buf(out_buf, type_h_name(type_entry)); - return; - } - case ZigTypeIdEnum: - { - buf_init_from_str(out_buf, "enum "); - buf_append_buf(out_buf, type_h_name(type_entry)); - return; - } - case ZigTypeIdArray: - { - ZigTypeArray *array_data = &type_entry->data.array; - - Buf *child_buf = buf_alloc(); - get_c_type(g, gen_h, array_data->child_type, child_buf); - - buf_resize(out_buf, 0); - buf_appendf(out_buf, "%s", buf_ptr(child_buf)); - return; - } - case ZigTypeIdVector: - zig_panic("TODO implement get_c_type for vector types"); - case ZigTypeIdErrorUnion: - case ZigTypeIdErrorSet: - case ZigTypeIdFn: - zig_panic("TODO implement get_c_type for more types"); - case ZigTypeIdInvalid: - case ZigTypeIdMetaType: - case ZigTypeIdBoundFn: - case ZigTypeIdComptimeFloat: - case ZigTypeIdComptimeInt: - case ZigTypeIdEnumLiteral: - case ZigTypeIdUndefined: - case ZigTypeIdNull: - case ZigTypeIdFnFrame: - case ZigTypeIdAnyFrame: - zig_unreachable(); - } -} - -static const char *preprocessor_alphabet1 = "_abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ"; -static const char *preprocessor_alphabet2 = "_abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789"; - -static bool need_to_preprocessor_mangle(Buf *src) { - for (size_t i = 0; i < buf_len(src); i += 1) { - const char *alphabet = (i == 0) ? preprocessor_alphabet1 : preprocessor_alphabet2; - uint8_t byte = buf_ptr(src)[i]; - if (strchr(alphabet, byte) == nullptr) { - return true; - } - } - return false; -} - -static Buf *preprocessor_mangle(Buf *src) { - if (!need_to_preprocessor_mangle(src)) { - return buf_create_from_buf(src); - } - Buf *result = buf_alloc(); - for (size_t i = 0; i < buf_len(src); i += 1) { - const char *alphabet = (i == 0) ? preprocessor_alphabet1 : preprocessor_alphabet2; - uint8_t byte = buf_ptr(src)[i]; - if (strchr(alphabet, byte) == nullptr) { - // perform escape - buf_appendf(result, "_%02x_", byte); - } else { - buf_append_char(result, byte); - } - } - return result; -} - -static void gen_h_file_types(CodeGen* g, GenH* gen_h, Buf* out_buf) { - for (size_t type_i = 0; type_i < gen_h->types_to_declare.length; type_i += 1) { - ZigType *type_entry = gen_h->types_to_declare.at(type_i); - switch (type_entry->id) { - case ZigTypeIdInvalid: - case ZigTypeIdMetaType: - case ZigTypeIdVoid: - case ZigTypeIdBool: - case ZigTypeIdUnreachable: - case ZigTypeIdInt: - case ZigTypeIdFloat: - case ZigTypeIdPointer: - case ZigTypeIdComptimeFloat: - case ZigTypeIdComptimeInt: - case ZigTypeIdEnumLiteral: - case ZigTypeIdArray: - case ZigTypeIdUndefined: - case ZigTypeIdNull: - case ZigTypeIdErrorUnion: - case ZigTypeIdErrorSet: - case ZigTypeIdBoundFn: - case ZigTypeIdOptional: - case ZigTypeIdFn: - case ZigTypeIdVector: - case ZigTypeIdFnFrame: - case ZigTypeIdAnyFrame: - zig_unreachable(); - - case ZigTypeIdEnum: - if (type_entry->data.enumeration.layout == ContainerLayoutExtern) { - buf_appendf(out_buf, "enum %s {\n", buf_ptr(type_h_name(type_entry))); - for (uint32_t field_i = 0; field_i < type_entry->data.enumeration.src_field_count; field_i += 1) { - TypeEnumField *enum_field = &type_entry->data.enumeration.fields[field_i]; - Buf *value_buf = buf_alloc(); - bigint_append_buf(value_buf, &enum_field->value, 10); - buf_appendf(out_buf, " %s = %s", buf_ptr(enum_field->name), buf_ptr(value_buf)); - if (field_i != type_entry->data.enumeration.src_field_count - 1) { - buf_appendf(out_buf, ","); - } - buf_appendf(out_buf, "\n"); - } - buf_appendf(out_buf, "};\n\n"); - } else { - buf_appendf(out_buf, "enum %s;\n\n", buf_ptr(type_h_name(type_entry))); - } - break; - case ZigTypeIdStruct: - if (type_entry->data.structure.layout == ContainerLayoutExtern) { - buf_appendf(out_buf, "struct %s {\n", buf_ptr(type_h_name(type_entry))); - for (uint32_t field_i = 0; field_i < type_entry->data.structure.src_field_count; field_i += 1) { - TypeStructField *struct_field = type_entry->data.structure.fields[field_i]; - - Buf *type_name_buf = buf_alloc(); - get_c_type(g, gen_h, struct_field->type_entry, type_name_buf); - - if (struct_field->type_entry->id == ZigTypeIdArray) { - buf_appendf(out_buf, " %s %s[%" ZIG_PRI_u64 "];\n", buf_ptr(type_name_buf), - buf_ptr(struct_field->name), - struct_field->type_entry->data.array.len); - } else { - buf_appendf(out_buf, " %s %s;\n", buf_ptr(type_name_buf), buf_ptr(struct_field->name)); - } - - } - buf_appendf(out_buf, "};\n\n"); - } else { - buf_appendf(out_buf, "struct %s;\n\n", buf_ptr(type_h_name(type_entry))); - } - break; - case ZigTypeIdUnion: - if (type_entry->data.unionation.layout == ContainerLayoutExtern) { - buf_appendf(out_buf, "union %s {\n", buf_ptr(type_h_name(type_entry))); - for (uint32_t field_i = 0; field_i < type_entry->data.unionation.src_field_count; field_i += 1) { - TypeUnionField *union_field = &type_entry->data.unionation.fields[field_i]; - - Buf *type_name_buf = buf_alloc(); - get_c_type(g, gen_h, union_field->type_entry, type_name_buf); - buf_appendf(out_buf, " %s %s;\n", buf_ptr(type_name_buf), buf_ptr(union_field->name)); - } - buf_appendf(out_buf, "};\n\n"); - } else { - buf_appendf(out_buf, "union %s;\n\n", buf_ptr(type_h_name(type_entry))); - } - break; - case ZigTypeIdOpaque: - buf_appendf(out_buf, "struct %s;\n\n", buf_ptr(type_h_name(type_entry))); - break; - } - } -} - -static void gen_h_file_functions(CodeGen* g, GenH* gen_h, Buf* out_buf, Buf* export_macro) { - for (size_t fn_def_i = 0; fn_def_i < g->fn_defs.length; fn_def_i += 1) { - ZigFn *fn_table_entry = g->fn_defs.at(fn_def_i); - - if (fn_table_entry->export_list.length == 0) - continue; - - FnTypeId *fn_type_id = &fn_table_entry->type_entry->data.fn.fn_type_id; - - Buf return_type_c = BUF_INIT; - get_c_type(g, gen_h, fn_type_id->return_type, &return_type_c); - - Buf *symbol_name; - if (fn_table_entry->export_list.length == 0) { - symbol_name = &fn_table_entry->symbol_name; - } else { - GlobalExport *fn_export = &fn_table_entry->export_list.items[0]; - symbol_name = &fn_export->name; - } - - if (export_macro != nullptr) { - buf_appendf(out_buf, "%s %s %s(", - buf_ptr(export_macro), - buf_ptr(&return_type_c), - buf_ptr(symbol_name)); - } else { - buf_appendf(out_buf, "%s %s(", - buf_ptr(&return_type_c), - buf_ptr(symbol_name)); - } - - Buf param_type_c = BUF_INIT; - if (fn_type_id->param_count > 0) { - for (size_t param_i = 0; param_i < fn_type_id->param_count; param_i += 1) { - FnTypeParamInfo *param_info = &fn_type_id->param_info[param_i]; - AstNode *param_decl_node = get_param_decl_node(fn_table_entry, param_i); - Buf *param_name = param_decl_node->data.param_decl.name; - - const char *comma_str = (param_i == 0) ? "" : ", "; - const char *restrict_str = param_info->is_noalias ? "restrict" : ""; - get_c_type(g, gen_h, param_info->type, ¶m_type_c); - - if (param_info->type->id == ZigTypeIdArray) { - // Arrays decay to pointers - buf_appendf(out_buf, "%s%s%s %s[]", comma_str, buf_ptr(¶m_type_c), - restrict_str, buf_ptr(param_name)); - } else { - buf_appendf(out_buf, "%s%s%s %s", comma_str, buf_ptr(¶m_type_c), - restrict_str, buf_ptr(param_name)); - } - } - buf_appendf(out_buf, ")"); - } else { - buf_appendf(out_buf, "void)"); - } - - buf_appendf(out_buf, ";\n"); - } -} - -static void gen_h_file_variables(CodeGen* g, GenH* gen_h, Buf* h_buf, Buf* export_macro) { - for (size_t exp_var_i = 0; exp_var_i < g->global_vars.length; exp_var_i += 1) { - ZigVar* var = g->global_vars.at(exp_var_i)->var; - if (var->export_list.length == 0) - continue; - - Buf var_type_c = BUF_INIT; - get_c_type(g, gen_h, var->var_type, &var_type_c); - - if (export_macro != nullptr) { - buf_appendf(h_buf, "extern %s %s %s;\n", - buf_ptr(export_macro), - buf_ptr(&var_type_c), - var->name); - } else { - buf_appendf(h_buf, "extern %s %s;\n", - buf_ptr(&var_type_c), - var->name); - } - } -} - -static void gen_h_file(CodeGen *g) { - GenH gen_h_data = {0}; - GenH *gen_h = &gen_h_data; - - assert(!g->is_test_build); - assert(!g->disable_gen_h); - - Buf *out_h_path = buf_sprintf("%s" OS_SEP "%s.h", buf_ptr(g->output_dir), buf_ptr(g->root_out_name)); - - FILE *out_h = fopen(buf_ptr(out_h_path), "wb"); - if (!out_h) - zig_panic("unable to open %s: %s\n", buf_ptr(out_h_path), strerror(errno)); - - Buf *export_macro = nullptr; - if (g->is_dynamic) { - export_macro = preprocessor_mangle(buf_sprintf("%s_EXPORT", buf_ptr(g->root_out_name))); - buf_upcase(export_macro); - } - - Buf fns_buf = BUF_INIT; - buf_resize(&fns_buf, 0); - gen_h_file_functions(g, gen_h, &fns_buf, export_macro); - - Buf vars_buf = BUF_INIT; - buf_resize(&vars_buf, 0); - gen_h_file_variables(g, gen_h, &vars_buf, export_macro); - - // Types will be populated by exported functions and variables so it has to run last. - Buf types_buf = BUF_INIT; - buf_resize(&types_buf, 0); - gen_h_file_types(g, gen_h, &types_buf); - - Buf *ifdef_dance_name = preprocessor_mangle(buf_sprintf("%s_H", buf_ptr(g->root_out_name))); - buf_upcase(ifdef_dance_name); - - fprintf(out_h, "#ifndef %s\n", buf_ptr(ifdef_dance_name)); - fprintf(out_h, "#define %s\n\n", buf_ptr(ifdef_dance_name)); - - if (g->c_want_stdbool) - fprintf(out_h, "#include \n"); - if (g->c_want_stdint) - fprintf(out_h, "#include \n"); - - fprintf(out_h, "\n"); - - if (g->is_dynamic) { - fprintf(out_h, "#if defined(_WIN32)\n"); - fprintf(out_h, "#define %s __declspec(dllimport)\n", buf_ptr(export_macro)); - fprintf(out_h, "#else\n"); - fprintf(out_h, "#define %s __attribute__((visibility (\"default\")))\n", - buf_ptr(export_macro)); - fprintf(out_h, "#endif\n"); - fprintf(out_h, "\n"); - } - - fprintf(out_h, "#ifdef __cplusplus\n"); - fprintf(out_h, "extern \"C\" {\n"); - fprintf(out_h, "#endif\n"); - fprintf(out_h, "\n"); - - fprintf(out_h, "%s", buf_ptr(&types_buf)); - fprintf(out_h, "%s\n", buf_ptr(&fns_buf)); - fprintf(out_h, "%s\n", buf_ptr(&vars_buf)); - - fprintf(out_h, "#ifdef __cplusplus\n"); - fprintf(out_h, "} // extern \"C\"\n"); - fprintf(out_h, "#endif\n\n"); - - fprintf(out_h, "#endif // %s\n", buf_ptr(ifdef_dance_name)); - - if (fclose(out_h)) - zig_panic("unable to close h file: %s", strerror(errno)); -} - void codegen_print_timing_report(CodeGen *g, FILE *f) { double start_time = g->timing_events.at(0).time; double end_time = g->timing_events.last().time; @@ -10733,174 +9230,14 @@ void codegen_add_time_event(CodeGen *g, const char *name) { g->timing_events.append({seconds, name}); } -static void add_cache_pkg(CodeGen *g, CacheHash *ch, ZigPackage *pkg) { - if (buf_len(&pkg->root_src_path) == 0) - return; - pkg->added_to_cache = true; - - Buf *rel_full_path = buf_alloc(); - os_path_join(&pkg->root_src_dir, &pkg->root_src_path, rel_full_path); - cache_file(ch, rel_full_path); - - auto it = pkg->package_table.entry_iterator(); - for (;;) { - auto *entry = it.next(); - if (!entry) - break; - - if (!pkg->added_to_cache) { - cache_buf(ch, entry->key); - add_cache_pkg(g, ch, entry->value); - } - } -} - -// Called before init() -// is_cache_hit takes into account gen_c_objects -static Error check_cache(CodeGen *g, Buf *manifest_dir, Buf *digest) { - Error err; - - Buf *compiler_id; - if ((err = get_compiler_id(&compiler_id))) - return err; - - CacheHash *ch = &g->cache_hash; - cache_init(ch, manifest_dir); - - add_cache_pkg(g, ch, g->main_pkg); - if (g->linker_script != nullptr) { - cache_file(ch, buf_create_from_str(g->linker_script)); - } - cache_buf(ch, compiler_id); - cache_buf(ch, g->root_out_name); - cache_buf(ch, g->zig_lib_dir); - cache_buf(ch, g->zig_std_dir); - cache_list_of_link_lib(ch, g->link_libs_list.items, g->link_libs_list.length); - cache_list_of_buf(ch, g->darwin_frameworks.items, g->darwin_frameworks.length); - cache_list_of_buf(ch, g->rpath_list.items, g->rpath_list.length); - cache_list_of_buf(ch, g->forbidden_libs.items, g->forbidden_libs.length); - cache_int(ch, g->build_mode); - cache_int(ch, g->out_type); - cache_bool(ch, g->zig_target->is_native_os); - cache_bool(ch, g->zig_target->is_native_cpu); - cache_int(ch, g->zig_target->arch); - cache_int(ch, g->zig_target->vendor); - cache_int(ch, g->zig_target->os); - cache_int(ch, g->zig_target->abi); - if (g->zig_target->cache_hash != nullptr) { - cache_mem(ch, g->zig_target->cache_hash, g->zig_target->cache_hash_len); - } - if (g->zig_target->glibc_or_darwin_version != nullptr) { - cache_int(ch, g->zig_target->glibc_or_darwin_version->major); - cache_int(ch, g->zig_target->glibc_or_darwin_version->minor); - cache_int(ch, g->zig_target->glibc_or_darwin_version->patch); - } - if (g->zig_target->dynamic_linker != nullptr) { - cache_str(ch, g->zig_target->dynamic_linker); - } - cache_int(ch, detect_subsystem(g)); - cache_bool(ch, g->strip_debug_symbols); - cache_bool(ch, g->is_test_build); - if (g->is_test_build) { - cache_buf_opt(ch, g->test_filter); - cache_buf_opt(ch, g->test_name_prefix); - cache_bool(ch, g->test_is_evented); - } - cache_bool(ch, g->link_eh_frame_hdr); - cache_bool(ch, g->is_single_threaded); - cache_bool(ch, g->linker_rdynamic); - cache_bool(ch, g->each_lib_rpath); - cache_bool(ch, g->disable_gen_h); - cache_bool(ch, g->bundle_compiler_rt); - cache_bool(ch, want_valgrind_support(g)); - cache_bool(ch, g->have_pic); - cache_bool(ch, g->have_dynamic_link); - cache_bool(ch, g->have_stack_probing); - cache_bool(ch, g->have_sanitize_c); - cache_bool(ch, g->is_dummy_so); - cache_bool(ch, g->function_sections); - cache_bool(ch, g->enable_dump_analysis); - cache_bool(ch, g->enable_doc_generation); - cache_bool(ch, g->emit_bin); - cache_bool(ch, g->emit_llvm_ir); - cache_bool(ch, g->emit_asm); - cache_bool(ch, g->is_versioned); - cache_usize(ch, g->version_major); - cache_usize(ch, g->version_minor); - cache_usize(ch, g->version_patch); - cache_list_of_str(ch, g->llvm_argv, g->llvm_argv_len); - cache_list_of_str(ch, g->clang_argv, g->clang_argv_len); - cache_list_of_str(ch, g->lib_dirs.items, g->lib_dirs.length); - cache_list_of_str(ch, g->framework_dirs.items, g->framework_dirs.length); - if (g->libc) { - cache_slice(ch, Slice{g->libc->include_dir, g->libc->include_dir_len}); - cache_slice(ch, Slice{g->libc->sys_include_dir, g->libc->sys_include_dir_len}); - cache_slice(ch, Slice{g->libc->crt_dir, g->libc->crt_dir_len}); - cache_slice(ch, Slice{g->libc->msvc_lib_dir, g->libc->msvc_lib_dir_len}); - cache_slice(ch, Slice{g->libc->kernel32_lib_dir, g->libc->kernel32_lib_dir_len}); - } - cache_buf_opt(ch, g->version_script_path); - cache_buf_opt(ch, g->override_soname); - cache_buf_opt(ch, g->linker_optimization); - cache_int(ch, g->linker_gc_sections); - cache_int(ch, g->linker_allow_shlib_undefined); - cache_int(ch, g->linker_bind_global_refs_locally); - cache_bool(ch, g->linker_z_nodelete); - cache_bool(ch, g->linker_z_defs); - cache_usize(ch, g->stack_size_override); - - // gen_c_objects appends objects to g->link_objects which we want to include in the hash - gen_c_objects(g); - cache_list_of_file(ch, g->link_objects.items, g->link_objects.length); - - buf_resize(digest, 0); - if ((err = cache_hit(ch, digest))) { - if (err != ErrorInvalidFormat) - return err; - } - - if (ch->manifest_file_path != nullptr) { - g->caches_to_release.append(ch); - } - - return ErrorNone; -} - static void resolve_out_paths(CodeGen *g) { assert(g->output_dir != nullptr); assert(g->root_out_name != nullptr); if (g->emit_bin) { - Buf *out_basename = buf_create_from_buf(g->root_out_name); Buf *o_basename = buf_create_from_buf(g->root_out_name); - switch (g->out_type) { - case OutTypeUnknown: - zig_unreachable(); - case OutTypeObj: - if (need_llvm_module(g) && g->link_objects.length != 0 && !g->enable_cache && - buf_eql_buf(o_basename, out_basename)) - { - // make it not collide with main output object - buf_append_str(o_basename, ".root"); - } - buf_append_str(o_basename, target_o_file_ext(g->zig_target)); - buf_append_str(out_basename, target_o_file_ext(g->zig_target)); - break; - case OutTypeExe: - buf_append_str(o_basename, target_o_file_ext(g->zig_target)); - buf_append_str(out_basename, target_exe_file_ext(g->zig_target)); - break; - case OutTypeLib: - buf_append_str(o_basename, target_o_file_ext(g->zig_target)); - buf_resize(out_basename, 0); - buf_append_str(out_basename, target_lib_file_prefix(g->zig_target)); - buf_append_buf(out_basename, g->root_out_name); - buf_append_str(out_basename, target_lib_file_ext(g->zig_target, !g->is_dynamic, g->is_versioned, - g->version_major, g->version_minor, g->version_patch)); - break; - } + buf_append_str(o_basename, target_o_file_ext(g->zig_target)); os_path_join(g->output_dir, o_basename, &g->o_file_output_path); - os_path_join(g->output_dir, out_basename, &g->bin_file_output_path); } if (g->emit_asm) { Buf *asm_basename = buf_create_from_buf(g->root_out_name); @@ -10971,144 +9308,46 @@ static void output_type_information(CodeGen *g) { } } -static void init_output_dir(CodeGen *g, Buf *digest) { - if (main_output_dir_is_just_one_c_object_post(g)) { - g->output_dir = buf_alloc(); - os_path_dirname(g->link_objects.at(0), g->output_dir); - } else { - g->output_dir = buf_sprintf("%s" OS_SEP CACHE_OUT_SUBDIR OS_SEP "%s", - buf_ptr(g->cache_dir), buf_ptr(digest)); - } -} +void codegen_build_object(CodeGen *g) { + assert(g->output_dir != nullptr); -void codegen_build_and_link(CodeGen *g) { - Error err; - assert(g->out_type != OutTypeUnknown); - - if (!g->enable_cache) { - if (g->output_dir == nullptr) { - g->output_dir = buf_create_from_str("."); - } else if ((err = os_make_path(g->output_dir))) { - fprintf(stderr, "Unable to create output directory: %s\n", err_str(err)); - exit(1); - } - } - - g->have_dynamic_link = detect_dynamic_link(g); - g->have_pic = detect_pic(g); - g->is_single_threaded = detect_single_threaded(g); g->have_err_ret_tracing = detect_err_ret_tracing(g); - g->have_sanitize_c = detect_sanitize_c(g); - detect_libc(g); - Buf digest = BUF_INIT; - if (g->enable_cache) { - Buf *manifest_dir = buf_alloc(); - os_path_join(g->cache_dir, buf_create_from_str(CACHE_HASH_SUBDIR), manifest_dir); + init(g); - if ((err = check_cache(g, manifest_dir, &digest))) { - if (err == ErrorCacheUnavailable) { - // message already printed - } else if (err == ErrorNotDir) { - fprintf(stderr, "Unable to check cache: %s is not a directory\n", - buf_ptr(manifest_dir)); - } else { - fprintf(stderr, "Unable to check cache: %s: %s\n", buf_ptr(manifest_dir), err_str(err)); - } - exit(1); - } - } else { - // There is a call to this in check_cache - gen_c_objects(g); + codegen_add_time_event(g, "Semantic Analysis"); + const char *progress_name = "Semantic Analysis"; + codegen_switch_sub_prog_node(g, stage2_progress_start(g->main_progress_node, + progress_name, strlen(progress_name), 0)); + + gen_root_source(g); + + resolve_out_paths(g); + + if (g->enable_dump_analysis || g->enable_doc_generation) { + output_type_information(g); } - if (g->enable_cache && buf_len(&digest) != 0) { - init_output_dir(g, &digest); - resolve_out_paths(g); - } else { - if (need_llvm_module(g)) { - init(g); - - codegen_add_time_event(g, "Semantic Analysis"); - const char *progress_name = "Semantic Analysis"; - codegen_switch_sub_prog_node(g, stage2_progress_start(g->main_progress_node, - progress_name, strlen(progress_name), 0)); - - gen_root_source(g); - - } - if (g->enable_cache) { - if (buf_len(&digest) == 0) { - if ((err = cache_final(&g->cache_hash, &digest))) { - fprintf(stderr, "Unable to finalize cache hash: %s\n", err_str(err)); - exit(1); - } - } - init_output_dir(g, &digest); - - if ((err = os_make_path(g->output_dir))) { - fprintf(stderr, "Unable to create output directory: %s\n", err_str(err)); - exit(1); - } - } - resolve_out_paths(g); - - if (g->enable_dump_analysis || g->enable_doc_generation) { - output_type_information(g); - } - - if (need_llvm_module(g)) { - codegen_add_time_event(g, "Code Generation"); - { - const char *progress_name = "Code Generation"; - codegen_switch_sub_prog_node(g, stage2_progress_start(g->main_progress_node, - progress_name, strlen(progress_name), 0)); - } - - do_code_gen(g); - codegen_add_time_event(g, "LLVM Emit Output"); - { - const char *progress_name = "LLVM Emit Output"; - codegen_switch_sub_prog_node(g, stage2_progress_start(g->main_progress_node, - progress_name, strlen(progress_name), 0)); - } - zig_llvm_emit_output(g); - - if (!g->disable_gen_h && (g->out_type == OutTypeObj || g->out_type == OutTypeLib)) { - codegen_add_time_event(g, "Generate .h"); - { - const char *progress_name = "Generate .h"; - codegen_switch_sub_prog_node(g, stage2_progress_start(g->main_progress_node, - progress_name, strlen(progress_name), 0)); - } - gen_h_file(g); - } - } - - // If we're outputting assembly or llvm IR we skip linking. - // If we're making a library or executable we must link. - // If there is more than one object, we have to link them (with -r). - // Finally, if we didn't make an object from zig source, and we don't have caching enabled, - // then we have an object from C source that we must copy to the output dir which we do with a -r link. - if (g->emit_bin && - (g->out_type != OutTypeObj || g->link_objects.length > 1 || - (!need_llvm_module(g) && !g->enable_cache))) - { - codegen_link(g); - } + codegen_add_time_event(g, "Code Generation"); + { + const char *progress_name = "Code Generation"; + codegen_switch_sub_prog_node(g, stage2_progress_start(g->main_progress_node, + progress_name, strlen(progress_name), 0)); } - codegen_release_caches(g); + do_code_gen(g); + codegen_add_time_event(g, "LLVM Emit Output"); + { + const char *progress_name = "LLVM Emit Output"; + codegen_switch_sub_prog_node(g, stage2_progress_start(g->main_progress_node, + progress_name, strlen(progress_name), 0)); + } + zig_llvm_emit_output(g); + codegen_add_time_event(g, "Done"); codegen_switch_sub_prog_node(g, nullptr); } -void codegen_release_caches(CodeGen *g) { - while (g->caches_to_release.length != 0) { - cache_release(g->caches_to_release.pop()); - } -} - ZigPackage *codegen_create_package(CodeGen *g, const char *root_src_dir, const char *root_src_path, const char *pkg_path) { @@ -11125,43 +9364,17 @@ ZigPackage *codegen_create_package(CodeGen *g, const char *root_src_dir, const c return pkg; } -CodeGen *create_child_codegen(CodeGen *parent_gen, Buf *root_src_path, OutType out_type, - Stage2LibCInstallation *libc, const char *name, Stage2ProgressNode *parent_progress_node) -{ - Stage2ProgressNode *child_progress_node = stage2_progress_start( - parent_progress_node ? parent_progress_node : parent_gen->sub_progress_node, - name, strlen(name), 0); - - CodeGen *child_gen = codegen_create(nullptr, root_src_path, parent_gen->zig_target, out_type, - parent_gen->build_mode, parent_gen->zig_lib_dir, libc, get_global_cache_dir(), false, child_progress_node); - child_gen->root_out_name = buf_create_from_str(name); - child_gen->disable_gen_h = true; - child_gen->want_stack_check = WantStackCheckDisabled; - child_gen->want_sanitize_c = WantCSanitizeDisabled; - child_gen->verbose_tokenize = parent_gen->verbose_tokenize; - child_gen->verbose_ast = parent_gen->verbose_ast; - child_gen->verbose_link = parent_gen->verbose_link; - child_gen->verbose_ir = parent_gen->verbose_ir; - child_gen->verbose_llvm_ir = parent_gen->verbose_llvm_ir; - child_gen->verbose_cimport = parent_gen->verbose_cimport; - child_gen->verbose_cc = parent_gen->verbose_cc; - child_gen->verbose_llvm_cpu_features = parent_gen->verbose_llvm_cpu_features; - child_gen->llvm_argv = parent_gen->llvm_argv; - - codegen_set_strip(child_gen, parent_gen->strip_debug_symbols); - child_gen->want_pic = parent_gen->have_pic ? WantPICEnabled : WantPICDisabled; - child_gen->valgrind_support = ValgrindSupportDisabled; - - codegen_set_errmsg_color(child_gen, parent_gen->err_color); - - child_gen->enable_cache = true; - - return child_gen; +void codegen_destroy(CodeGen *g) { + if (g->pass1_arena != nullptr) { + g->pass1_arena->destruct(&heap::c_allocator); + g->pass1_arena = nullptr; + } + heap::c_allocator.destroy(g); } CodeGen *codegen_create(Buf *main_pkg_path, Buf *root_src_path, const ZigTarget *target, - OutType out_type, BuildMode build_mode, Buf *override_lib_dir, - Stage2LibCInstallation *libc, Buf *cache_dir, bool is_test_build, Stage2ProgressNode *progress_node) + BuildMode build_mode, Buf *override_lib_dir, + bool is_test_build, Stage2ProgressNode *progress_node) { CodeGen *g = heap::c_allocator.create(); g->emit_bin = true; @@ -11176,24 +9389,15 @@ CodeGen *codegen_create(Buf *main_pkg_path, Buf *root_src_path, const ZigTarget } g->subsystem = TargetSubsystemAuto; - g->libc = libc; g->zig_target = target; - g->cache_dir = cache_dir; - if (override_lib_dir == nullptr) { - g->zig_lib_dir = get_zig_lib_dir(); - } else { - g->zig_lib_dir = override_lib_dir; - } + assert(override_lib_dir != nullptr); + g->zig_lib_dir = override_lib_dir; g->zig_std_dir = buf_alloc(); os_path_join(g->zig_lib_dir, buf_create_from_str("std"), g->zig_std_dir); - g->zig_c_headers_dir = buf_alloc(); - os_path_join(g->zig_lib_dir, buf_create_from_str("include"), g->zig_c_headers_dir); - g->build_mode = build_mode; - g->out_type = out_type; g->import_table.init(32); g->builtin_fn_table.init(32); g->primitive_type_table.init(32); @@ -11256,18 +9460,6 @@ CodeGen *codegen_create(Buf *main_pkg_path, Buf *root_src_path, const ZigTarget g->zig_std_special_dir = buf_alloc(); os_path_join(g->zig_std_dir, buf_sprintf("special"), g->zig_std_special_dir); - assert(target != nullptr); - if (!target->is_native_os) { - g->each_lib_rpath = false; - } else { - g->each_lib_rpath = true; - } - - if (target_os_requires_libc(g->zig_target->os)) { - g->libc_link_lib = create_link_lib(buf_create_from_str("c")); - g->link_libs_list.append(g->libc_link_lib); - } - target_triple_llvm(&g->llvm_triple_str, g->zig_target); g->pointer_size_bytes = target_arch_pointer_bit_width(g->zig_target->arch) / 8; @@ -11302,36 +9494,21 @@ void codegen_switch_sub_prog_node(CodeGen *g, Stage2ProgressNode *node) { } ZigValue *CodeGen::Intern::for_undefined() { -#ifdef ZIG_ENABLE_MEM_PROFILE - mem::intern_counters.x_undefined += 1; -#endif return &this->x_undefined; } ZigValue *CodeGen::Intern::for_void() { -#ifdef ZIG_ENABLE_MEM_PROFILE - mem::intern_counters.x_void += 1; -#endif return &this->x_void; } ZigValue *CodeGen::Intern::for_null() { -#ifdef ZIG_ENABLE_MEM_PROFILE - mem::intern_counters.x_null += 1; -#endif return &this->x_null; } ZigValue *CodeGen::Intern::for_unreachable() { -#ifdef ZIG_ENABLE_MEM_PROFILE - mem::intern_counters.x_unreachable += 1; -#endif return &this->x_unreachable; } ZigValue *CodeGen::Intern::for_zero_byte() { -#ifdef ZIG_ENABLE_MEM_PROFILE - mem::intern_counters.zero_byte += 1; -#endif return &this->zero_byte; } diff --git a/src/codegen.hpp b/src/codegen.hpp index 3139071d52..5b4317c992 100644 --- a/src/codegen.hpp +++ b/src/codegen.hpp @@ -16,47 +16,20 @@ #include CodeGen *codegen_create(Buf *main_pkg_path, Buf *root_src_path, const ZigTarget *target, - OutType out_type, BuildMode build_mode, Buf *zig_lib_dir, - Stage2LibCInstallation *libc, Buf *cache_dir, bool is_test_build, Stage2ProgressNode *progress_node); + BuildMode build_mode, Buf *zig_lib_dir, + bool is_test_build, Stage2ProgressNode *progress_node); -CodeGen *create_child_codegen(CodeGen *parent_gen, Buf *root_src_path, OutType out_type, - Stage2LibCInstallation *libc, const char *name, Stage2ProgressNode *progress_node); +void codegen_build_object(CodeGen *g); +void codegen_destroy(CodeGen *); -void codegen_set_clang_argv(CodeGen *codegen, const char **args, size_t len); -void codegen_set_llvm_argv(CodeGen *codegen, const char **args, size_t len); -void codegen_set_each_lib_rpath(CodeGen *codegen, bool each_lib_rpath); - -void codegen_set_strip(CodeGen *codegen, bool strip); -void codegen_set_errmsg_color(CodeGen *codegen, ErrColor err_color); -void codegen_set_out_name(CodeGen *codegen, Buf *out_name); -void codegen_add_lib_dir(CodeGen *codegen, const char *dir); -void codegen_add_forbidden_lib(CodeGen *codegen, Buf *lib); -LinkLib *codegen_add_link_lib(CodeGen *codegen, Buf *lib); -void codegen_add_framework(CodeGen *codegen, const char *name); -void codegen_add_rpath(CodeGen *codegen, const char *name); -void codegen_set_rdynamic(CodeGen *g, bool rdynamic); -void codegen_set_linker_script(CodeGen *g, const char *linker_script); -void codegen_set_test_filter(CodeGen *g, Buf *filter); -void codegen_set_test_name_prefix(CodeGen *g, Buf *prefix); -void codegen_set_lib_version(CodeGen *g, bool is_versioned, size_t major, size_t minor, size_t patch); void codegen_add_time_event(CodeGen *g, const char *name); void codegen_print_timing_report(CodeGen *g, FILE *f); -void codegen_link(CodeGen *g); -void zig_link_add_compiler_rt(CodeGen *g, Stage2ProgressNode *progress_node); -void codegen_build_and_link(CodeGen *g); ZigPackage *codegen_create_package(CodeGen *g, const char *root_src_dir, const char *root_src_path, const char *pkg_path); -void codegen_add_assembly(CodeGen *g, Buf *path); -void codegen_add_object(CodeGen *g, Buf *object_path); - -void codegen_translate_c(CodeGen *g, Buf *full_path); - -Buf *codegen_generate_builtin_source(CodeGen *g); TargetSubsystem detect_subsystem(CodeGen *g); -void codegen_release_caches(CodeGen *codegen); bool codegen_fn_has_err_ret_tracing_arg(CodeGen *g, ZigType *return_type); bool codegen_fn_has_err_ret_tracing_stack(CodeGen *g, ZigFn *fn, bool is_async); diff --git a/src/compiler.cpp b/src/compiler.cpp deleted file mode 100644 index 6c477a1506..0000000000 --- a/src/compiler.cpp +++ /dev/null @@ -1,196 +0,0 @@ -#include "cache_hash.hpp" -#include "os.hpp" -#include "compiler.hpp" - -#include - -Error get_compiler_id(Buf **result) { - static Buf saved_compiler_id = BUF_INIT; - - if (saved_compiler_id.list.length != 0) { - *result = &saved_compiler_id; - return ErrorNone; - } - - Error err; - Buf *manifest_dir = buf_alloc(); - os_path_join(get_global_cache_dir(), buf_create_from_str("exe"), manifest_dir); - - CacheHash cache_hash; - CacheHash *ch = &cache_hash; - cache_init(ch, manifest_dir); - Buf self_exe_path = BUF_INIT; - if ((err = os_self_exe_path(&self_exe_path))) - return err; - - cache_file(ch, &self_exe_path); - - buf_resize(&saved_compiler_id, 0); - if ((err = cache_hit(ch, &saved_compiler_id))) { - if (err != ErrorInvalidFormat) - return err; - } - if (buf_len(&saved_compiler_id) != 0) { - cache_release(ch); - *result = &saved_compiler_id; - return ErrorNone; - } - ZigList lib_paths = {}; - if ((err = os_self_exe_shared_libs(lib_paths))) - return err; - #if defined(ZIG_OS_DARWIN) - // only add the self exe path on mac os - Buf *lib_path = lib_paths.at(0); - if ((err = cache_add_file(ch, lib_path))) - return err; - #else - for (size_t i = 0; i < lib_paths.length; i += 1) { - Buf *lib_path = lib_paths.at(i); - if ((err = cache_add_file(ch, lib_path))) - return err; - } - #endif - - if ((err = cache_final(ch, &saved_compiler_id))) - return err; - - cache_release(ch); - - *result = &saved_compiler_id; - return ErrorNone; -} - -static bool test_zig_install_prefix(Buf *test_path, Buf *out_zig_lib_dir) { - { - Buf *test_zig_dir = buf_sprintf("%s" OS_SEP "lib" OS_SEP "zig", buf_ptr(test_path)); - Buf *test_index_file = buf_sprintf("%s" OS_SEP "std" OS_SEP "std.zig", buf_ptr(test_zig_dir)); - int err; - bool exists; - if ((err = os_file_exists(test_index_file, &exists))) { - exists = false; - } - if (exists) { - buf_init_from_buf(out_zig_lib_dir, test_zig_dir); - return true; - } - } - - // Also try without "zig" - { - Buf *test_zig_dir = buf_sprintf("%s" OS_SEP "lib", buf_ptr(test_path)); - Buf *test_index_file = buf_sprintf("%s" OS_SEP "std" OS_SEP "std.zig", buf_ptr(test_zig_dir)); - int err; - bool exists; - if ((err = os_file_exists(test_index_file, &exists))) { - exists = false; - } - if (exists) { - buf_init_from_buf(out_zig_lib_dir, test_zig_dir); - return true; - } - } - - return false; -} - -static int find_zig_lib_dir(Buf *out_path) { - int err; - - Buf self_exe_path = BUF_INIT; - buf_resize(&self_exe_path, 0); - if (!(err = os_self_exe_path(&self_exe_path))) { - Buf *cur_path = &self_exe_path; - - for (;;) { - Buf *test_dir = buf_alloc(); - os_path_dirname(cur_path, test_dir); - - if (buf_eql_buf(test_dir, cur_path)) { - break; - } - - if (test_zig_install_prefix(test_dir, out_path)) { - return 0; - } - - cur_path = test_dir; - } - } - - return ErrorFileNotFound; -} - -Buf *get_zig_lib_dir(void) { - static Buf saved_lib_dir = BUF_INIT; - if (saved_lib_dir.list.length != 0) - return &saved_lib_dir; - buf_resize(&saved_lib_dir, 0); - - int err; - if ((err = find_zig_lib_dir(&saved_lib_dir))) { - fprintf(stderr, "Unable to find zig lib directory\n"); - exit(EXIT_FAILURE); - } - return &saved_lib_dir; -} - -Buf *get_zig_std_dir(Buf *zig_lib_dir) { - static Buf saved_std_dir = BUF_INIT; - if (saved_std_dir.list.length != 0) - return &saved_std_dir; - buf_resize(&saved_std_dir, 0); - - os_path_join(zig_lib_dir, buf_create_from_str("std"), &saved_std_dir); - - return &saved_std_dir; -} - -Buf *get_zig_special_dir(Buf *zig_lib_dir) { - static Buf saved_special_dir = BUF_INIT; - if (saved_special_dir.list.length != 0) - return &saved_special_dir; - buf_resize(&saved_special_dir, 0); - - os_path_join(get_zig_std_dir(zig_lib_dir), buf_sprintf("special"), &saved_special_dir); - - return &saved_special_dir; -} - -Buf *get_global_cache_dir(void) { - static Buf saved_global_cache_dir = BUF_INIT; - if (saved_global_cache_dir.list.length != 0) - return &saved_global_cache_dir; - buf_resize(&saved_global_cache_dir, 0); - - Buf app_data_dir = BUF_INIT; - Error err; - if ((err = os_get_app_data_dir(&app_data_dir, "zig"))) { - fprintf(stderr, "Unable to get application data dir: %s\n", err_str(err)); - exit(1); - } - os_path_join(&app_data_dir, buf_create_from_str("stage1"), &saved_global_cache_dir); - buf_deinit(&app_data_dir); - return &saved_global_cache_dir; -} - -FileExt classify_file_ext(const char *filename_ptr, size_t filename_len) { - if (mem_ends_with_str(filename_ptr, filename_len, ".c")) { - return FileExtC; - } else if (mem_ends_with_str(filename_ptr, filename_len, ".C") || - mem_ends_with_str(filename_ptr, filename_len, ".cc") || - mem_ends_with_str(filename_ptr, filename_len, ".cpp") || - mem_ends_with_str(filename_ptr, filename_len, ".cxx")) - { - return FileExtCpp; - } else if (mem_ends_with_str(filename_ptr, filename_len, ".ll")) { - return FileExtLLVMIr; - } else if (mem_ends_with_str(filename_ptr, filename_len, ".bc")) { - return FileExtLLVMBitCode; - } else if (mem_ends_with_str(filename_ptr, filename_len, ".s") || - mem_ends_with_str(filename_ptr, filename_len, ".S")) - { - return FileExtAsm; - } - // TODO look for .so, .so.X, .so.X.Y, .so.X.Y.Z - return FileExtUnknown; -} diff --git a/src/compiler.hpp b/src/compiler.hpp deleted file mode 100644 index ae2e6e9c5e..0000000000 --- a/src/compiler.hpp +++ /dev/null @@ -1,24 +0,0 @@ -/* - * Copyright (c) 2018 Andrew Kelley - * - * This file is part of zig, which is MIT licensed. - * See http://opensource.org/licenses/MIT - */ - -#ifndef ZIG_COMPILER_HPP -#define ZIG_COMPILER_HPP - -#include "all_types.hpp" - -Error get_compiler_id(Buf **result); - -Buf *get_zig_lib_dir(void); -Buf *get_zig_special_dir(Buf *zig_lib_dir); -Buf *get_zig_std_dir(Buf *zig_lib_dir); - -Buf *get_global_cache_dir(void); - - -FileExt classify_file_ext(const char *filename_ptr, size_t filename_len); - -#endif diff --git a/src/config.h.in b/src/config.h.in index 2ec6c25b38..8c147e7d65 100644 --- a/src/config.h.in +++ b/src/config.h.in @@ -22,6 +22,4 @@ #define ZIG_LLVM_CONFIG_EXE "@LLVM_CONFIG_EXE@" #define ZIG_DIA_GUIDS_LIB "@ZIG_DIA_GUIDS_LIB_ESCAPED@" -#cmakedefine ZIG_ENABLE_MEM_PROFILE - #endif diff --git a/src/config.zig.in b/src/config.zig.in index a44149111e..9e574bc1e8 100644 --- a/src/config.zig.in +++ b/src/config.zig.in @@ -3,3 +3,4 @@ pub const version: []const u8 = "@ZIG_VERSION@"; pub const log_scopes: []const []const u8 = &[_][]const u8{}; pub const zir_dumps: []const []const u8 = &[_][]const u8{}; pub const enable_tracy = false; +pub const is_stage1 = true; diff --git a/src/dump_analysis.cpp b/src/dump_analysis.cpp index 2f41341b14..df0d6f3ca2 100644 --- a/src/dump_analysis.cpp +++ b/src/dump_analysis.cpp @@ -6,11 +6,11 @@ */ #include "dump_analysis.hpp" -#include "compiler.hpp" #include "analyze.hpp" #include "config.h" #include "ir.hpp" #include "codegen.hpp" +#include "os.hpp" enum JsonWriterState { JsonWriterStateInvalid, @@ -1173,7 +1173,6 @@ static void anal_dump_fn(AnalDumpCtx *ctx, ZigFn *fn) { } void zig_print_analysis_dump(CodeGen *g, FILE *f, const char *one_indent, const char *nl) { - Error err; AnalDumpCtx ctx = {}; ctx.g = g; JsonWriter *jw = &ctx.jw; @@ -1199,15 +1198,6 @@ void zig_print_analysis_dump(CodeGen *g, FILE *f, const char *one_indent, const jw_object_field(jw, "params"); jw_begin_object(jw); { - jw_object_field(jw, "zigId"); - - Buf *compiler_id; - if ((err = get_compiler_id(&compiler_id))) { - fprintf(stderr, "Unable to determine compiler id: %s\n", err_str(err)); - exit(1); - } - jw_string(jw, buf_ptr(compiler_id)); - jw_object_field(jw, "zigVersion"); jw_string(jw, ZIG_VERSION_STRING); diff --git a/src/empty.cpp b/src/empty.cpp new file mode 100644 index 0000000000..e69de29bb2 diff --git a/src/errmsg.hpp b/src/errmsg.hpp index e8b2f5872d..73cbd4e0d9 100644 --- a/src/errmsg.hpp +++ b/src/errmsg.hpp @@ -10,12 +10,7 @@ #include "buffer.hpp" #include "list.hpp" - -enum ErrColor { - ErrColorAuto, - ErrColorOff, - ErrColorOn, -}; +#include "stage1.h" struct ErrorMsg { size_t line_start; diff --git a/src/glibc.cpp b/src/glibc.cpp deleted file mode 100644 index 62f5604ba7..0000000000 --- a/src/glibc.cpp +++ /dev/null @@ -1,392 +0,0 @@ -/* - * Copyright (c) 2019 Andrew Kelley - * - * This file is part of zig, which is MIT licensed. - * See http://opensource.org/licenses/MIT - */ - -#include "glibc.hpp" -#include "compiler.hpp" -#include "cache_hash.hpp" -#include "codegen.hpp" - -static const ZigGLibCLib glibc_libs[] = { - {"c", 6}, - {"m", 6}, - {"pthread", 0}, - {"dl", 2}, - {"rt", 1}, - {"ld", 2}, - {"util", 1}, -}; - -Error glibc_load_metadata(ZigGLibCAbi **out_result, Buf *zig_lib_dir, bool verbose) { - Error err; - - ZigGLibCAbi *glibc_abi = heap::c_allocator.create(); - glibc_abi->vers_txt_path = buf_sprintf("%s" OS_SEP "libc" OS_SEP "glibc" OS_SEP "vers.txt", buf_ptr(zig_lib_dir)); - glibc_abi->fns_txt_path = buf_sprintf("%s" OS_SEP "libc" OS_SEP "glibc" OS_SEP "fns.txt", buf_ptr(zig_lib_dir)); - glibc_abi->abi_txt_path = buf_sprintf("%s" OS_SEP "libc" OS_SEP "glibc" OS_SEP "abi.txt", buf_ptr(zig_lib_dir)); - glibc_abi->version_table.init(16); - - Buf *vers_txt_contents = buf_alloc(); - if ((err = os_fetch_file_path(glibc_abi->vers_txt_path, vers_txt_contents))) { - if (verbose) { - fprintf(stderr, "Unable to read %s: %s\n", buf_ptr(glibc_abi->vers_txt_path), err_str(err)); - } - return err; - } - Buf *fns_txt_contents = buf_alloc(); - if ((err = os_fetch_file_path(glibc_abi->fns_txt_path, fns_txt_contents))) { - if (verbose) { - fprintf(stderr, "Unable to read %s: %s\n", buf_ptr(glibc_abi->fns_txt_path), err_str(err)); - } - return err; - } - Buf *abi_txt_contents = buf_alloc(); - if ((err = os_fetch_file_path(glibc_abi->abi_txt_path, abi_txt_contents))) { - if (verbose) { - fprintf(stderr, "Unable to read %s: %s\n", buf_ptr(glibc_abi->abi_txt_path), err_str(err)); - } - return err; - } - - { - SplitIterator it = memSplit(buf_to_slice(vers_txt_contents), str("\r\n")); - for (;;) { - Optional> opt_component = SplitIterator_next(&it); - if (!opt_component.is_some) break; - Buf *ver_buf = buf_create_from_slice(opt_component.value); - Stage2SemVer *this_ver = glibc_abi->all_versions.add_one(); - if ((err = target_parse_glibc_version(this_ver, buf_ptr(ver_buf)))) { - if (verbose) { - fprintf(stderr, "Unable to parse glibc version '%s': %s\n", buf_ptr(ver_buf), err_str(err)); - } - return err; - } - } - } - { - SplitIterator it = memSplit(buf_to_slice(fns_txt_contents), str("\r\n")); - for (;;) { - Optional> opt_component = SplitIterator_next(&it); - if (!opt_component.is_some) break; - SplitIterator line_it = memSplit(opt_component.value, str(" ")); - Optional> opt_fn_name = SplitIterator_next(&line_it); - if (!opt_fn_name.is_some) { - if (verbose) { - fprintf(stderr, "%s: Expected function name\n", buf_ptr(glibc_abi->fns_txt_path)); - } - return ErrorInvalidFormat; - } - Optional> opt_lib_name = SplitIterator_next(&line_it); - if (!opt_lib_name.is_some) { - if (verbose) { - fprintf(stderr, "%s: Expected lib name\n", buf_ptr(glibc_abi->fns_txt_path)); - } - return ErrorInvalidFormat; - } - - Buf *this_fn_name = buf_create_from_slice(opt_fn_name.value); - Buf *this_lib_name = buf_create_from_slice(opt_lib_name.value); - glibc_abi->all_functions.append({ this_fn_name, glibc_lib_find(buf_ptr(this_lib_name)) }); - } - } - { - SplitIterator it = memSplit(buf_to_slice(abi_txt_contents), str("\r\n")); - ZigGLibCVerList *ver_list_base = nullptr; - int line_num = 0; - for (;;) { - if (ver_list_base == nullptr) { - line_num += 1; - Optional> opt_line = SplitIterator_next_separate(&it); - if (!opt_line.is_some) break; - - ver_list_base = heap::c_allocator.allocate(glibc_abi->all_functions.length); - SplitIterator line_it = memSplit(opt_line.value, str(" ")); - for (;;) { - ZigTarget *target = heap::c_allocator.create(); - Optional> opt_target = SplitIterator_next(&line_it); - if (!opt_target.is_some) break; - - SplitIterator component_it = memSplit(opt_target.value, str("-")); - Optional> opt_arch = SplitIterator_next(&component_it); - assert(opt_arch.is_some); - Optional> opt_os = SplitIterator_next(&component_it); - assert(opt_os.is_some); // it's always "linux" so we ignore it - Optional> opt_abi = SplitIterator_next(&component_it); - assert(opt_abi.is_some); - - - err = target_parse_arch(&target->arch, (char*)opt_arch.value.ptr, opt_arch.value.len); - assert(err == ErrorNone); - - target->os = OsLinux; - - err = target_parse_abi(&target->abi, (char*)opt_abi.value.ptr, opt_abi.value.len); - if (err != ErrorNone) { - fprintf(stderr, "Error parsing %s:%d: %s\n", buf_ptr(glibc_abi->abi_txt_path), - line_num, err_str(err)); - fprintf(stderr, "arch: '%.*s', os: '%.*s', abi: '%.*s'\n", - (int)opt_arch.value.len, (const char*)opt_arch.value.ptr, - (int)opt_os.value.len, (const char*)opt_os.value.ptr, - (int)opt_abi.value.len, (const char*)opt_abi.value.ptr); - fprintf(stderr, "parsed from target: '%.*s'\n", - (int)opt_target.value.len, (const char*)opt_target.value.ptr); - fprintf(stderr, "parsed from line:\n%.*s\n", (int)opt_line.value.len, opt_line.value.ptr); - fprintf(stderr, "Zig installation appears to be corrupted.\n"); - exit(1); - } - - glibc_abi->version_table.put(target, ver_list_base); - } - continue; - } - for (size_t fn_i = 0; fn_i < glibc_abi->all_functions.length; fn_i += 1) { - ZigGLibCVerList *ver_list = &ver_list_base[fn_i]; - line_num += 1; - Optional> opt_line = SplitIterator_next_separate(&it); - assert(opt_line.is_some); - - SplitIterator line_it = memSplit(opt_line.value, str(" ")); - for (;;) { - Optional> opt_ver = SplitIterator_next(&line_it); - if (!opt_ver.is_some) break; - assert(ver_list->len < 8); // increase the array len in the type - - unsigned long ver_index = strtoul(buf_ptr(buf_create_from_slice(opt_ver.value)), nullptr, 10); - assert(ver_index < 255); // use a bigger integer in the type - ver_list->versions[ver_list->len] = ver_index; - ver_list->len += 1; - } - } - ver_list_base = nullptr; - } - } - - *out_result = glibc_abi; - return ErrorNone; -} - -Error glibc_build_dummies_and_maps(CodeGen *g, const ZigGLibCAbi *glibc_abi, const ZigTarget *target, - Buf **out_dir, bool verbose, Stage2ProgressNode *progress_node) -{ - Error err; - - Buf *cache_dir = get_global_cache_dir(); - CacheHash *cache_hash = heap::c_allocator.create(); - Buf *manifest_dir = buf_sprintf("%s" OS_SEP CACHE_HASH_SUBDIR, buf_ptr(cache_dir)); - cache_init(cache_hash, manifest_dir); - - Buf *compiler_id; - if ((err = get_compiler_id(&compiler_id))) { - if (verbose) { - fprintf(stderr, "unable to get compiler id: %s\n", err_str(err)); - } - return err; - } - cache_buf(cache_hash, compiler_id); - cache_int(cache_hash, target->arch); - cache_int(cache_hash, target->abi); - cache_int(cache_hash, target->glibc_or_darwin_version->major); - cache_int(cache_hash, target->glibc_or_darwin_version->minor); - cache_int(cache_hash, target->glibc_or_darwin_version->patch); - - Buf digest = BUF_INIT; - buf_resize(&digest, 0); - if ((err = cache_hit(cache_hash, &digest))) { - // Treat an invalid format error as a cache miss. - if (err != ErrorInvalidFormat) - return err; - } - // We should always get a cache hit because there are no - // files in the input hash. - assert(buf_len(&digest) != 0); - - Buf *dummy_dir = buf_alloc(); - os_path_join(manifest_dir, &digest, dummy_dir); - - if ((err = os_make_path(dummy_dir))) - return err; - - Buf *test_if_exists_path = buf_alloc(); - os_path_join(dummy_dir, buf_create_from_str("ok"), test_if_exists_path); - - bool hit; - if ((err = os_file_exists(test_if_exists_path, &hit))) - return err; - - if (hit) { - *out_dir = dummy_dir; - return ErrorNone; - } - - - ZigGLibCVerList *ver_list_base = glibc_abi->version_table.get(target); - - uint8_t target_ver_index = 0; - for (;target_ver_index < glibc_abi->all_versions.length; target_ver_index += 1) { - const Stage2SemVer *this_ver = &glibc_abi->all_versions.at(target_ver_index); - if (this_ver->major == target->glibc_or_darwin_version->major && - this_ver->minor == target->glibc_or_darwin_version->minor && - this_ver->patch == target->glibc_or_darwin_version->patch) - { - break; - } - } - if (target_ver_index == glibc_abi->all_versions.length) { - if (verbose) { - fprintf(stderr, "Unrecognized glibc version: %d.%d.%d\n", - target->glibc_or_darwin_version->major, - target->glibc_or_darwin_version->minor, - target->glibc_or_darwin_version->patch); - } - return ErrorUnknownABI; - } - - Buf *map_file_path = buf_sprintf("%s" OS_SEP "all.map", buf_ptr(dummy_dir)); - Buf *map_contents = buf_alloc(); - - for (uint8_t ver_i = 0; ver_i < glibc_abi->all_versions.length; ver_i += 1) { - const Stage2SemVer *ver = &glibc_abi->all_versions.at(ver_i); - if (ver->patch == 0) { - buf_appendf(map_contents, "GLIBC_%d.%d { };\n", ver->major, ver->minor); - } else { - buf_appendf(map_contents, "GLIBC_%d.%d.%d { };\n", ver->major, ver->minor, ver->patch); - } - } - - if ((err = os_write_file(map_file_path, map_contents))) { - if (verbose) { - fprintf(stderr, "unable to write %s: %s", buf_ptr(map_file_path), err_str(err)); - } - return err; - } - - - for (size_t lib_i = 0; lib_i < array_length(glibc_libs); lib_i += 1) { - const ZigGLibCLib *lib = &glibc_libs[lib_i]; - Buf *zig_file_path = buf_sprintf("%s" OS_SEP "%s.zig", buf_ptr(dummy_dir), lib->name); - Buf *zig_body = buf_alloc(); - Buf *zig_footer = buf_alloc(); - - buf_appendf(zig_body, "comptime {\n"); - buf_appendf(zig_body, " asm (\n"); - - for (size_t fn_i = 0; fn_i < glibc_abi->all_functions.length; fn_i += 1) { - const ZigGLibCFn *libc_fn = &glibc_abi->all_functions.at(fn_i); - if (libc_fn->lib != lib) continue; - ZigGLibCVerList *ver_list = &ver_list_base[fn_i]; - // Pick the default symbol version: - // - If there are no versions, don't emit it - // - Take the greatest one <= than the target one - // - If none of them is <= than the - // specified one don't pick any default version - if (ver_list->len == 0) continue; - uint8_t chosen_def_ver_index = 255; - for (uint8_t ver_i = 0; ver_i < ver_list->len; ver_i += 1) { - uint8_t ver_index = ver_list->versions[ver_i]; - if ((chosen_def_ver_index == 255 || ver_index > chosen_def_ver_index) && - target_ver_index >= ver_index) - { - chosen_def_ver_index = ver_index; - } - } - for (uint8_t ver_i = 0; ver_i < ver_list->len; ver_i += 1) { - uint8_t ver_index = ver_list->versions[ver_i]; - - Buf *stub_name; - const Stage2SemVer *ver = &glibc_abi->all_versions.at(ver_index); - const char *sym_name = buf_ptr(libc_fn->name); - if (ver->patch == 0) { - stub_name = buf_sprintf("%s_%d_%d", sym_name, ver->major, ver->minor); - } else { - stub_name = buf_sprintf("%s_%d_%d_%d", sym_name, ver->major, ver->minor, ver->patch); - } - - buf_appendf(zig_footer, "export fn %s() void {}\n", buf_ptr(stub_name)); - - // Default symbol version definition vs normal symbol version definition - const char *at_sign_str = (chosen_def_ver_index != 255 && - ver_index == chosen_def_ver_index) ? "@@" : "@"; - if (ver->patch == 0) { - buf_appendf(zig_body, " \\\\ .symver %s, %s%sGLIBC_%d.%d\n", - buf_ptr(stub_name), sym_name, at_sign_str, ver->major, ver->minor); - } else { - buf_appendf(zig_body, " \\\\ .symver %s, %s%sGLIBC_%d.%d.%d\n", - buf_ptr(stub_name), sym_name, at_sign_str, ver->major, ver->minor, ver->patch); - } - // Hide the stub to keep the symbol table clean - buf_appendf(zig_body, " \\\\ .hidden %s\n", buf_ptr(stub_name)); - } - } - - buf_appendf(zig_body, " );\n"); - buf_appendf(zig_body, "}\n"); - buf_append_buf(zig_body, zig_footer); - - if ((err = os_write_file(zig_file_path, zig_body))) { - if (verbose) { - fprintf(stderr, "unable to write %s: %s", buf_ptr(zig_file_path), err_str(err)); - } - return err; - } - - bool is_ld = (strcmp(lib->name, "ld") == 0); - - CodeGen *child_gen = create_child_codegen(g, zig_file_path, OutTypeLib, nullptr, lib->name, progress_node); - codegen_set_lib_version(child_gen, true, lib->sover, 0, 0); - child_gen->is_dynamic = true; - child_gen->is_dummy_so = true; - child_gen->version_script_path = map_file_path; - child_gen->enable_cache = false; - child_gen->output_dir = dummy_dir; - if (is_ld) { - assert(g->zig_target->standard_dynamic_linker_path != nullptr); - Buf *ld_basename = buf_alloc(); - os_path_split(buf_create_from_str(g->zig_target->standard_dynamic_linker_path), - nullptr, ld_basename); - child_gen->override_soname = ld_basename; - } - codegen_build_and_link(child_gen); - } - - if ((err = os_write_file(test_if_exists_path, buf_alloc()))) { - if (verbose) { - fprintf(stderr, "unable to write %s: %s", buf_ptr(test_if_exists_path), err_str(err)); - } - return err; - } - *out_dir = dummy_dir; - return ErrorNone; -} - -uint32_t hash_glibc_target(const ZigTarget *x) { - return x->arch * (uint32_t)3250106448 + - x->os * (uint32_t)542534372 + - x->abi * (uint32_t)59162639; -} - -bool eql_glibc_target(const ZigTarget *a, const ZigTarget *b) { - return a->arch == b->arch && - a->os == b->os && - a->abi == b->abi; -} - -size_t glibc_lib_count(void) { - return array_length(glibc_libs); -} - -const ZigGLibCLib *glibc_lib_enum(size_t index) { - assert(index < array_length(glibc_libs)); - return &glibc_libs[index]; -} - -const ZigGLibCLib *glibc_lib_find(const char *name) { - for (size_t i = 0; i < array_length(glibc_libs); i += 1) { - if (strcmp(glibc_libs[i].name, name) == 0) { - return &glibc_libs[i]; - } - } - return nullptr; -} diff --git a/src/glibc.hpp b/src/glibc.hpp deleted file mode 100644 index c04dcb4629..0000000000 --- a/src/glibc.hpp +++ /dev/null @@ -1,50 +0,0 @@ -/* - * Copyright (c) 2019 Andrew Kelley - * - * This file is part of zig, which is MIT licensed. - * See http://opensource.org/licenses/MIT - */ - -#ifndef ZIG_GLIBC_HPP -#define ZIG_GLIBC_HPP - -#include "all_types.hpp" - -struct ZigGLibCLib { - const char *name; - uint8_t sover; -}; - -struct ZigGLibCFn { - Buf *name; - const ZigGLibCLib *lib; -}; - -struct ZigGLibCVerList { - uint8_t versions[8]; // 8 is just the max number, we know statically it's big enough - uint8_t len; -}; - -uint32_t hash_glibc_target(const ZigTarget *x); -bool eql_glibc_target(const ZigTarget *a, const ZigTarget *b); - -struct ZigGLibCAbi { - Buf *abi_txt_path; - Buf *vers_txt_path; - Buf *fns_txt_path; - ZigList all_versions; - ZigList all_functions; - // The value is a pointer to all_functions.length items and each item is an index - // into all_functions. - HashMap version_table; -}; - -Error glibc_load_metadata(ZigGLibCAbi **out_result, Buf *zig_lib_dir, bool verbose); -Error glibc_build_dummies_and_maps(CodeGen *codegen, const ZigGLibCAbi *glibc_abi, const ZigTarget *target, - Buf **out_dir, bool verbose, Stage2ProgressNode *progress_node); - -size_t glibc_lib_count(void); -const ZigGLibCLib *glibc_lib_enum(size_t index); -const ZigGLibCLib *glibc_lib_find(const char *name); - -#endif diff --git a/src/heap.cpp b/src/heap.cpp index 79c44d13dc..7e7a171bde 100644 --- a/src/heap.cpp +++ b/src/heap.cpp @@ -10,7 +10,6 @@ #include "config.h" #include "heap.hpp" -#include "mem_profile.hpp" namespace heap { @@ -48,21 +47,9 @@ void BootstrapAllocator::internal_deallocate(const mem::TypeInfo &info, void *pt mem::os::free(ptr); } -void CAllocator::init(const char *name) { -#ifdef ZIG_ENABLE_MEM_PROFILE - this->profile = bootstrap_allocator.create(); - this->profile->init(name, "CAllocator"); -#endif -} +void CAllocator::init(const char *name) { } -void CAllocator::deinit() { -#ifdef ZIG_ENABLE_MEM_PROFILE - assert(this->profile); - this->profile->deinit(); - bootstrap_allocator.destroy(this->profile); - this->profile = nullptr; -#endif -} +void CAllocator::deinit() { } CAllocator *CAllocator::construct(mem::Allocator *allocator, const char *name) { auto p = new(allocator->create()) CAllocator(); @@ -75,23 +62,11 @@ void CAllocator::destruct(mem::Allocator *allocator) { allocator->destroy(this); } -#ifdef ZIG_ENABLE_MEM_PROFILE -void CAllocator::print_report(FILE *file) { - this->profile->print_report(file); -} -#endif - void *CAllocator::internal_allocate(const mem::TypeInfo &info, size_t count) { -#ifdef ZIG_ENABLE_MEM_PROFILE - this->profile->record_alloc(info, count); -#endif return mem::os::calloc(count, info.size); } void *CAllocator::internal_allocate_nonzero(const mem::TypeInfo &info, size_t count) { -#ifdef ZIG_ENABLE_MEM_PROFILE - this->profile->record_alloc(info, count); -#endif return mem::os::malloc(count * info.size); } @@ -103,17 +78,10 @@ void *CAllocator::internal_reallocate(const mem::TypeInfo &info, void *old_ptr, } void *CAllocator::internal_reallocate_nonzero(const mem::TypeInfo &info, void *old_ptr, size_t old_count, size_t new_count) { -#ifdef ZIG_ENABLE_MEM_PROFILE - this->profile->record_dealloc(info, old_count); - this->profile->record_alloc(info, new_count); -#endif return mem::os::realloc(old_ptr, new_count * info.size); } void CAllocator::internal_deallocate(const mem::TypeInfo &info, void *ptr, size_t count) { -#ifdef ZIG_ENABLE_MEM_PROFILE - this->profile->record_dealloc(info, count); -#endif mem::os::free(ptr); } @@ -249,10 +217,6 @@ void ArenaAllocator::Impl::track_object(Object object) { } void ArenaAllocator::init(Allocator *backing, const char *name) { -#ifdef ZIG_ENABLE_MEM_PROFILE - this->profile = bootstrap_allocator.create(); - this->profile->init(name, "ArenaAllocator"); -#endif this->impl = bootstrap_allocator.create(); { auto &r = *this->impl; @@ -309,13 +273,6 @@ void ArenaAllocator::deinit() { t = prev; } } - -#ifdef ZIG_ENABLE_MEM_PROFILE - assert(this->profile); - this->profile->deinit(); - bootstrap_allocator.destroy(this->profile); - this->profile = nullptr; -#endif } ArenaAllocator *ArenaAllocator::construct(mem::Allocator *allocator, mem::Allocator *backing, const char *name) { @@ -329,23 +286,11 @@ void ArenaAllocator::destruct(mem::Allocator *allocator) { allocator->destroy(this); } -#ifdef ZIG_ENABLE_MEM_PROFILE -void ArenaAllocator::print_report(FILE *file) { - this->profile->print_report(file); -} -#endif - void *ArenaAllocator::internal_allocate(const mem::TypeInfo &info, size_t count) { -#ifdef ZIG_ENABLE_MEM_PROFILE - this->profile->record_alloc(info, count); -#endif return this->impl->allocate(info, count); } void *ArenaAllocator::internal_allocate_nonzero(const mem::TypeInfo &info, size_t count) { -#ifdef ZIG_ENABLE_MEM_PROFILE - this->profile->record_alloc(info, count); -#endif return this->impl->allocate(info, count); } @@ -354,17 +299,10 @@ void *ArenaAllocator::internal_reallocate(const mem::TypeInfo &info, void *old_p } void *ArenaAllocator::internal_reallocate_nonzero(const mem::TypeInfo &info, void *old_ptr, size_t old_count, size_t new_count) { -#ifdef ZIG_ENABLE_MEM_PROFILE - this->profile->record_dealloc(info, old_count); - this->profile->record_alloc(info, new_count); -#endif return this->impl->reallocate(info, old_ptr, old_count, new_count); } void ArenaAllocator::internal_deallocate(const mem::TypeInfo &info, void *ptr, size_t count) { -#ifdef ZIG_ENABLE_MEM_PROFILE - this->profile->record_dealloc(info, count); -#endif // noop } diff --git a/src/heap.hpp b/src/heap.hpp index e22ec42967..ec5c81026d 100644 --- a/src/heap.hpp +++ b/src/heap.hpp @@ -12,12 +12,6 @@ #include "util_base.hpp" #include "mem.hpp" -#ifdef ZIG_ENABLE_MEM_PROFILE -namespace mem { - struct Profile; -} -#endif - namespace heap { struct BootstrapAllocator final : mem::Allocator { @@ -40,9 +34,6 @@ struct CAllocator final : mem::Allocator { static CAllocator *construct(mem::Allocator *allocator, const char *name); void destruct(mem::Allocator *allocator) final; -#ifdef ZIG_ENABLE_MEM_PROFILE - void print_report(FILE *file = nullptr); -#endif private: ATTRIBUTE_RETURNS_NOALIAS void *internal_allocate(const mem::TypeInfo &info, size_t count) final; @@ -51,9 +42,6 @@ private: void *internal_reallocate_nonzero(const mem::TypeInfo &info, void *old_ptr, size_t old_count, size_t new_count) final; void internal_deallocate(const mem::TypeInfo &info, void *ptr, size_t count) final; -#ifdef ZIG_ENABLE_MEM_PROFILE - mem::Profile *profile; -#endif }; // @@ -71,9 +59,6 @@ struct ArenaAllocator final : mem::Allocator { static ArenaAllocator *construct(mem::Allocator *allocator, mem::Allocator *backing, const char *name); void destruct(mem::Allocator *allocator) final; -#ifdef ZIG_ENABLE_MEM_PROFILE - void print_report(FILE *file = nullptr); -#endif private: ATTRIBUTE_RETURNS_NOALIAS void *internal_allocate(const mem::TypeInfo &info, size_t count) final; @@ -82,10 +67,6 @@ private: void *internal_reallocate_nonzero(const mem::TypeInfo &info, void *old_ptr, size_t old_count, size_t new_count) final; void internal_deallocate(const mem::TypeInfo &info, void *ptr, size_t count) final; -#ifdef ZIG_ENABLE_MEM_PROFILE - mem::Profile *profile; -#endif - struct Impl; Impl *impl; }; diff --git a/src/install_files.h b/src/install_files.h deleted file mode 100644 index 8e7431145e..0000000000 --- a/src/install_files.h +++ /dev/null @@ -1,1907 +0,0 @@ -#ifndef ZIG_INSTALL_FILES_H -#define ZIG_INSTALL_FILES_H -static const char *ZIG_MUSL_SRC_FILES[] = { -"musl/src/aio/aio.c", -"musl/src/aio/aio_suspend.c", -"musl/src/aio/lio_listio.c", -"musl/src/complex/__cexp.c", -"musl/src/complex/__cexpf.c", -"musl/src/complex/cabs.c", -"musl/src/complex/cabsf.c", -"musl/src/complex/cabsl.c", -"musl/src/complex/cacos.c", -"musl/src/complex/cacosf.c", -"musl/src/complex/cacosh.c", -"musl/src/complex/cacoshf.c", -"musl/src/complex/cacoshl.c", -"musl/src/complex/cacosl.c", -"musl/src/complex/carg.c", -"musl/src/complex/cargf.c", -"musl/src/complex/cargl.c", -"musl/src/complex/casin.c", -"musl/src/complex/casinf.c", -"musl/src/complex/casinh.c", -"musl/src/complex/casinhf.c", -"musl/src/complex/casinhl.c", -"musl/src/complex/casinl.c", -"musl/src/complex/catan.c", -"musl/src/complex/catanf.c", -"musl/src/complex/catanh.c", -"musl/src/complex/catanhf.c", -"musl/src/complex/catanhl.c", -"musl/src/complex/catanl.c", -"musl/src/complex/ccos.c", -"musl/src/complex/ccosf.c", -"musl/src/complex/ccosh.c", -"musl/src/complex/ccoshf.c", -"musl/src/complex/ccoshl.c", -"musl/src/complex/ccosl.c", -"musl/src/complex/cexp.c", -"musl/src/complex/cexpf.c", -"musl/src/complex/cexpl.c", -"musl/src/complex/cimag.c", -"musl/src/complex/cimagf.c", -"musl/src/complex/cimagl.c", -"musl/src/complex/clog.c", -"musl/src/complex/clogf.c", -"musl/src/complex/clogl.c", -"musl/src/complex/conj.c", -"musl/src/complex/conjf.c", -"musl/src/complex/conjl.c", -"musl/src/complex/cpow.c", -"musl/src/complex/cpowf.c", -"musl/src/complex/cpowl.c", -"musl/src/complex/cproj.c", -"musl/src/complex/cprojf.c", -"musl/src/complex/cprojl.c", -"musl/src/complex/creal.c", -"musl/src/complex/crealf.c", -"musl/src/complex/creall.c", -"musl/src/complex/csin.c", -"musl/src/complex/csinf.c", -"musl/src/complex/csinh.c", -"musl/src/complex/csinhf.c", -"musl/src/complex/csinhl.c", -"musl/src/complex/csinl.c", -"musl/src/complex/csqrt.c", -"musl/src/complex/csqrtf.c", -"musl/src/complex/csqrtl.c", -"musl/src/complex/ctan.c", -"musl/src/complex/ctanf.c", -"musl/src/complex/ctanh.c", -"musl/src/complex/ctanhf.c", -"musl/src/complex/ctanhl.c", -"musl/src/complex/ctanl.c", -"musl/src/conf/confstr.c", -"musl/src/conf/fpathconf.c", -"musl/src/conf/legacy.c", -"musl/src/conf/pathconf.c", -"musl/src/conf/sysconf.c", -"musl/src/crypt/crypt.c", -"musl/src/crypt/crypt_blowfish.c", -"musl/src/crypt/crypt_des.c", -"musl/src/crypt/crypt_md5.c", -"musl/src/crypt/crypt_r.c", -"musl/src/crypt/crypt_sha256.c", -"musl/src/crypt/crypt_sha512.c", -"musl/src/crypt/encrypt.c", -"musl/src/ctype/__ctype_b_loc.c", -"musl/src/ctype/__ctype_get_mb_cur_max.c", -"musl/src/ctype/__ctype_tolower_loc.c", -"musl/src/ctype/__ctype_toupper_loc.c", -"musl/src/ctype/isalnum.c", -"musl/src/ctype/isalpha.c", -"musl/src/ctype/isascii.c", -"musl/src/ctype/isblank.c", -"musl/src/ctype/iscntrl.c", -"musl/src/ctype/isdigit.c", -"musl/src/ctype/isgraph.c", -"musl/src/ctype/islower.c", -"musl/src/ctype/isprint.c", -"musl/src/ctype/ispunct.c", -"musl/src/ctype/isspace.c", -"musl/src/ctype/isupper.c", -"musl/src/ctype/iswalnum.c", -"musl/src/ctype/iswalpha.c", -"musl/src/ctype/iswblank.c", -"musl/src/ctype/iswcntrl.c", -"musl/src/ctype/iswctype.c", -"musl/src/ctype/iswdigit.c", -"musl/src/ctype/iswgraph.c", -"musl/src/ctype/iswlower.c", -"musl/src/ctype/iswprint.c", -"musl/src/ctype/iswpunct.c", -"musl/src/ctype/iswspace.c", -"musl/src/ctype/iswupper.c", -"musl/src/ctype/iswxdigit.c", -"musl/src/ctype/isxdigit.c", -"musl/src/ctype/toascii.c", -"musl/src/ctype/tolower.c", -"musl/src/ctype/toupper.c", -"musl/src/ctype/towctrans.c", -"musl/src/ctype/wcswidth.c", -"musl/src/ctype/wctrans.c", -"musl/src/ctype/wcwidth.c", -"musl/src/dirent/alphasort.c", -"musl/src/dirent/closedir.c", -"musl/src/dirent/dirfd.c", -"musl/src/dirent/fdopendir.c", -"musl/src/dirent/opendir.c", -"musl/src/dirent/readdir.c", -"musl/src/dirent/readdir_r.c", -"musl/src/dirent/rewinddir.c", -"musl/src/dirent/scandir.c", -"musl/src/dirent/seekdir.c", -"musl/src/dirent/telldir.c", -"musl/src/dirent/versionsort.c", -"musl/src/env/__environ.c", -"musl/src/env/__init_tls.c", -"musl/src/env/__libc_start_main.c", -"musl/src/env/__reset_tls.c", -"musl/src/env/__stack_chk_fail.c", -"musl/src/env/clearenv.c", -"musl/src/env/getenv.c", -"musl/src/env/putenv.c", -"musl/src/env/secure_getenv.c", -"musl/src/env/setenv.c", -"musl/src/env/unsetenv.c", -"musl/src/errno/__errno_location.c", -"musl/src/errno/strerror.c", -"musl/src/exit/_Exit.c", -"musl/src/exit/abort.c", -"musl/src/exit/arm/__aeabi_atexit.c", -"musl/src/exit/assert.c", -"musl/src/exit/at_quick_exit.c", -"musl/src/exit/atexit.c", -"musl/src/exit/exit.c", -"musl/src/exit/quick_exit.c", -"musl/src/fcntl/creat.c", -"musl/src/fcntl/fcntl.c", -"musl/src/fcntl/open.c", -"musl/src/fcntl/openat.c", -"musl/src/fcntl/posix_fadvise.c", -"musl/src/fcntl/posix_fallocate.c", -"musl/src/fenv/__flt_rounds.c", -"musl/src/fenv/aarch64/fenv.s", -"musl/src/fenv/arm/fenv-hf.S", -"musl/src/fenv/arm/fenv.c", -"musl/src/fenv/fegetexceptflag.c", -"musl/src/fenv/feholdexcept.c", -"musl/src/fenv/fenv.c", -"musl/src/fenv/fesetexceptflag.c", -"musl/src/fenv/fesetround.c", -"musl/src/fenv/feupdateenv.c", -"musl/src/fenv/i386/fenv.s", -"musl/src/fenv/m68k/fenv.c", -"musl/src/fenv/mips/fenv-sf.c", -"musl/src/fenv/mips/fenv.S", -"musl/src/fenv/mips64/fenv-sf.c", -"musl/src/fenv/mips64/fenv.S", -"musl/src/fenv/mipsn32/fenv-sf.c", -"musl/src/fenv/mipsn32/fenv.S", -"musl/src/fenv/powerpc/fenv-sf.c", -"musl/src/fenv/powerpc/fenv.S", -"musl/src/fenv/powerpc64/fenv.c", -"musl/src/fenv/riscv64/fenv-sf.c", -"musl/src/fenv/riscv64/fenv.S", -"musl/src/fenv/s390x/fenv.c", -"musl/src/fenv/sh/fenv-nofpu.c", -"musl/src/fenv/sh/fenv.S", -"musl/src/fenv/x32/fenv.s", -"musl/src/fenv/x86_64/fenv.s", -"musl/src/internal/defsysinfo.c", -"musl/src/internal/floatscan.c", -"musl/src/internal/i386/defsysinfo.s", -"musl/src/internal/intscan.c", -"musl/src/internal/libc.c", -"musl/src/internal/procfdname.c", -"musl/src/internal/sh/__shcall.c", -"musl/src/internal/shgetc.c", -"musl/src/internal/syscall_ret.c", -"musl/src/internal/vdso.c", -"musl/src/internal/version.c", -"musl/src/ipc/ftok.c", -"musl/src/ipc/msgctl.c", -"musl/src/ipc/msgget.c", -"musl/src/ipc/msgrcv.c", -"musl/src/ipc/msgsnd.c", -"musl/src/ipc/semctl.c", -"musl/src/ipc/semget.c", -"musl/src/ipc/semop.c", -"musl/src/ipc/semtimedop.c", -"musl/src/ipc/shmat.c", -"musl/src/ipc/shmctl.c", -"musl/src/ipc/shmdt.c", -"musl/src/ipc/shmget.c", -"musl/src/ldso/__dlsym.c", -"musl/src/ldso/aarch64/dlsym.s", -"musl/src/ldso/aarch64/tlsdesc.s", -"musl/src/ldso/arm/dlsym.s", -"musl/src/ldso/arm/dlsym_time64.S", -"musl/src/ldso/arm/find_exidx.c", -"musl/src/ldso/arm/tlsdesc.S", -"musl/src/ldso/dl_iterate_phdr.c", -"musl/src/ldso/dladdr.c", -"musl/src/ldso/dlclose.c", -"musl/src/ldso/dlerror.c", -"musl/src/ldso/dlinfo.c", -"musl/src/ldso/dlopen.c", -"musl/src/ldso/dlsym.c", -"musl/src/ldso/i386/dlsym.s", -"musl/src/ldso/i386/dlsym_time64.S", -"musl/src/ldso/i386/tlsdesc.s", -"musl/src/ldso/m68k/dlsym.s", -"musl/src/ldso/m68k/dlsym_time64.S", -"musl/src/ldso/microblaze/dlsym.s", -"musl/src/ldso/microblaze/dlsym_time64.S", -"musl/src/ldso/mips/dlsym.s", -"musl/src/ldso/mips/dlsym_time64.S", -"musl/src/ldso/mips64/dlsym.s", -"musl/src/ldso/mipsn32/dlsym.s", -"musl/src/ldso/mipsn32/dlsym_time64.S", -"musl/src/ldso/or1k/dlsym.s", -"musl/src/ldso/or1k/dlsym_time64.S", -"musl/src/ldso/powerpc/dlsym.s", -"musl/src/ldso/powerpc/dlsym_time64.S", -"musl/src/ldso/powerpc64/dlsym.s", -"musl/src/ldso/riscv64/dlsym.s", -"musl/src/ldso/s390x/dlsym.s", -"musl/src/ldso/sh/dlsym.s", -"musl/src/ldso/sh/dlsym_time64.S", -"musl/src/ldso/tlsdesc.c", -"musl/src/ldso/x32/dlsym.s", -"musl/src/ldso/x86_64/dlsym.s", -"musl/src/ldso/x86_64/tlsdesc.s", -"musl/src/legacy/cuserid.c", -"musl/src/legacy/daemon.c", -"musl/src/legacy/err.c", -"musl/src/legacy/euidaccess.c", -"musl/src/legacy/ftw.c", -"musl/src/legacy/futimes.c", -"musl/src/legacy/getdtablesize.c", -"musl/src/legacy/getloadavg.c", -"musl/src/legacy/getpagesize.c", -"musl/src/legacy/getpass.c", -"musl/src/legacy/getusershell.c", -"musl/src/legacy/isastream.c", -"musl/src/legacy/lutimes.c", -"musl/src/legacy/ulimit.c", -"musl/src/legacy/utmpx.c", -"musl/src/legacy/valloc.c", -"musl/src/linux/adjtime.c", -"musl/src/linux/adjtimex.c", -"musl/src/linux/arch_prctl.c", -"musl/src/linux/brk.c", -"musl/src/linux/cache.c", -"musl/src/linux/cap.c", -"musl/src/linux/chroot.c", -"musl/src/linux/clock_adjtime.c", -"musl/src/linux/clone.c", -"musl/src/linux/copy_file_range.c", -"musl/src/linux/epoll.c", -"musl/src/linux/eventfd.c", -"musl/src/linux/fallocate.c", -"musl/src/linux/fanotify.c", -"musl/src/linux/flock.c", -"musl/src/linux/getdents.c", -"musl/src/linux/getrandom.c", -"musl/src/linux/inotify.c", -"musl/src/linux/ioperm.c", -"musl/src/linux/iopl.c", -"musl/src/linux/klogctl.c", -"musl/src/linux/membarrier.c", -"musl/src/linux/memfd_create.c", -"musl/src/linux/mlock2.c", -"musl/src/linux/module.c", -"musl/src/linux/mount.c", -"musl/src/linux/name_to_handle_at.c", -"musl/src/linux/open_by_handle_at.c", -"musl/src/linux/personality.c", -"musl/src/linux/pivot_root.c", -"musl/src/linux/ppoll.c", -"musl/src/linux/prctl.c", -"musl/src/linux/prlimit.c", -"musl/src/linux/process_vm.c", -"musl/src/linux/ptrace.c", -"musl/src/linux/quotactl.c", -"musl/src/linux/readahead.c", -"musl/src/linux/reboot.c", -"musl/src/linux/remap_file_pages.c", -"musl/src/linux/sbrk.c", -"musl/src/linux/sendfile.c", -"musl/src/linux/setfsgid.c", -"musl/src/linux/setfsuid.c", -"musl/src/linux/setgroups.c", -"musl/src/linux/sethostname.c", -"musl/src/linux/setns.c", -"musl/src/linux/settimeofday.c", -"musl/src/linux/signalfd.c", -"musl/src/linux/splice.c", -"musl/src/linux/stime.c", -"musl/src/linux/swap.c", -"musl/src/linux/sync_file_range.c", -"musl/src/linux/syncfs.c", -"musl/src/linux/sysinfo.c", -"musl/src/linux/tee.c", -"musl/src/linux/timerfd.c", -"musl/src/linux/unshare.c", -"musl/src/linux/utimes.c", -"musl/src/linux/vhangup.c", -"musl/src/linux/vmsplice.c", -"musl/src/linux/wait3.c", -"musl/src/linux/wait4.c", -"musl/src/linux/x32/sysinfo.c", -"musl/src/linux/xattr.c", -"musl/src/locale/__lctrans.c", -"musl/src/locale/__mo_lookup.c", -"musl/src/locale/bind_textdomain_codeset.c", -"musl/src/locale/c_locale.c", -"musl/src/locale/catclose.c", -"musl/src/locale/catgets.c", -"musl/src/locale/catopen.c", -"musl/src/locale/dcngettext.c", -"musl/src/locale/duplocale.c", -"musl/src/locale/freelocale.c", -"musl/src/locale/iconv.c", -"musl/src/locale/iconv_close.c", -"musl/src/locale/langinfo.c", -"musl/src/locale/locale_map.c", -"musl/src/locale/localeconv.c", -"musl/src/locale/newlocale.c", -"musl/src/locale/pleval.c", -"musl/src/locale/setlocale.c", -"musl/src/locale/strcoll.c", -"musl/src/locale/strfmon.c", -"musl/src/locale/strxfrm.c", -"musl/src/locale/textdomain.c", -"musl/src/locale/uselocale.c", -"musl/src/locale/wcscoll.c", -"musl/src/locale/wcsxfrm.c", -"musl/src/malloc/aligned_alloc.c", -"musl/src/malloc/expand_heap.c", -"musl/src/malloc/lite_malloc.c", -"musl/src/malloc/malloc.c", -"musl/src/malloc/malloc_usable_size.c", -"musl/src/malloc/memalign.c", -"musl/src/malloc/posix_memalign.c", -"musl/src/math/__cos.c", -"musl/src/math/__cosdf.c", -"musl/src/math/__cosl.c", -"musl/src/math/__expo2.c", -"musl/src/math/__expo2f.c", -"musl/src/math/__fpclassify.c", -"musl/src/math/__fpclassifyf.c", -"musl/src/math/__fpclassifyl.c", -"musl/src/math/__invtrigl.c", -"musl/src/math/__math_divzero.c", -"musl/src/math/__math_divzerof.c", -"musl/src/math/__math_invalid.c", -"musl/src/math/__math_invalidf.c", -"musl/src/math/__math_oflow.c", -"musl/src/math/__math_oflowf.c", -"musl/src/math/__math_uflow.c", -"musl/src/math/__math_uflowf.c", -"musl/src/math/__math_xflow.c", -"musl/src/math/__math_xflowf.c", -"musl/src/math/__polevll.c", -"musl/src/math/__rem_pio2.c", -"musl/src/math/__rem_pio2_large.c", -"musl/src/math/__rem_pio2f.c", -"musl/src/math/__rem_pio2l.c", -"musl/src/math/__signbit.c", -"musl/src/math/__signbitf.c", -"musl/src/math/__signbitl.c", -"musl/src/math/__sin.c", -"musl/src/math/__sindf.c", -"musl/src/math/__sinl.c", -"musl/src/math/__tan.c", -"musl/src/math/__tandf.c", -"musl/src/math/__tanl.c", -"musl/src/math/aarch64/ceil.c", -"musl/src/math/aarch64/ceilf.c", -"musl/src/math/aarch64/fabs.c", -"musl/src/math/aarch64/fabsf.c", -"musl/src/math/aarch64/floor.c", -"musl/src/math/aarch64/floorf.c", -"musl/src/math/aarch64/fma.c", -"musl/src/math/aarch64/fmaf.c", -"musl/src/math/aarch64/fmax.c", -"musl/src/math/aarch64/fmaxf.c", -"musl/src/math/aarch64/fmin.c", -"musl/src/math/aarch64/fminf.c", -"musl/src/math/aarch64/llrint.c", -"musl/src/math/aarch64/llrintf.c", -"musl/src/math/aarch64/llround.c", -"musl/src/math/aarch64/llroundf.c", -"musl/src/math/aarch64/lrint.c", -"musl/src/math/aarch64/lrintf.c", -"musl/src/math/aarch64/lround.c", -"musl/src/math/aarch64/lroundf.c", -"musl/src/math/aarch64/nearbyint.c", -"musl/src/math/aarch64/nearbyintf.c", -"musl/src/math/aarch64/rint.c", -"musl/src/math/aarch64/rintf.c", -"musl/src/math/aarch64/round.c", -"musl/src/math/aarch64/roundf.c", -"musl/src/math/aarch64/sqrt.c", -"musl/src/math/aarch64/sqrtf.c", -"musl/src/math/aarch64/trunc.c", -"musl/src/math/aarch64/truncf.c", -"musl/src/math/acos.c", -"musl/src/math/acosf.c", -"musl/src/math/acosh.c", -"musl/src/math/acoshf.c", -"musl/src/math/acoshl.c", -"musl/src/math/acosl.c", -"musl/src/math/arm/fabs.c", -"musl/src/math/arm/fabsf.c", -"musl/src/math/arm/fma.c", -"musl/src/math/arm/fmaf.c", -"musl/src/math/arm/sqrt.c", -"musl/src/math/arm/sqrtf.c", -"musl/src/math/asin.c", -"musl/src/math/asinf.c", -"musl/src/math/asinh.c", -"musl/src/math/asinhf.c", -"musl/src/math/asinhl.c", -"musl/src/math/asinl.c", -"musl/src/math/atan.c", -"musl/src/math/atan2.c", -"musl/src/math/atan2f.c", -"musl/src/math/atan2l.c", -"musl/src/math/atanf.c", -"musl/src/math/atanh.c", -"musl/src/math/atanhf.c", -"musl/src/math/atanhl.c", -"musl/src/math/atanl.c", -"musl/src/math/cbrt.c", -"musl/src/math/cbrtf.c", -"musl/src/math/cbrtl.c", -"musl/src/math/ceil.c", -"musl/src/math/ceilf.c", -"musl/src/math/ceill.c", -"musl/src/math/copysign.c", -"musl/src/math/copysignf.c", -"musl/src/math/copysignl.c", -"musl/src/math/cos.c", -"musl/src/math/cosf.c", -"musl/src/math/cosh.c", -"musl/src/math/coshf.c", -"musl/src/math/coshl.c", -"musl/src/math/cosl.c", -"musl/src/math/erf.c", -"musl/src/math/erff.c", -"musl/src/math/erfl.c", -"musl/src/math/exp.c", -"musl/src/math/exp10.c", -"musl/src/math/exp10f.c", -"musl/src/math/exp10l.c", -"musl/src/math/exp2.c", -"musl/src/math/exp2f.c", -"musl/src/math/exp2f_data.c", -"musl/src/math/exp2l.c", -"musl/src/math/exp_data.c", -"musl/src/math/expf.c", -"musl/src/math/expl.c", -"musl/src/math/expm1.c", -"musl/src/math/expm1f.c", -"musl/src/math/expm1l.c", -"musl/src/math/fabs.c", -"musl/src/math/fabsf.c", -"musl/src/math/fabsl.c", -"musl/src/math/fdim.c", -"musl/src/math/fdimf.c", -"musl/src/math/fdiml.c", -"musl/src/math/finite.c", -"musl/src/math/finitef.c", -"musl/src/math/floor.c", -"musl/src/math/floorf.c", -"musl/src/math/floorl.c", -"musl/src/math/fma.c", -"musl/src/math/fmaf.c", -"musl/src/math/fmal.c", -"musl/src/math/fmax.c", -"musl/src/math/fmaxf.c", -"musl/src/math/fmaxl.c", -"musl/src/math/fmin.c", -"musl/src/math/fminf.c", -"musl/src/math/fminl.c", -"musl/src/math/fmod.c", -"musl/src/math/fmodf.c", -"musl/src/math/fmodl.c", -"musl/src/math/frexp.c", -"musl/src/math/frexpf.c", -"musl/src/math/frexpl.c", -"musl/src/math/hypot.c", -"musl/src/math/hypotf.c", -"musl/src/math/hypotl.c", -"musl/src/math/i386/__invtrigl.s", -"musl/src/math/i386/acos.s", -"musl/src/math/i386/acosf.s", -"musl/src/math/i386/acosl.s", -"musl/src/math/i386/asin.s", -"musl/src/math/i386/asinf.s", -"musl/src/math/i386/asinl.s", -"musl/src/math/i386/atan.s", -"musl/src/math/i386/atan2.s", -"musl/src/math/i386/atan2f.s", -"musl/src/math/i386/atan2l.s", -"musl/src/math/i386/atanf.s", -"musl/src/math/i386/atanl.s", -"musl/src/math/i386/ceil.s", -"musl/src/math/i386/ceilf.s", -"musl/src/math/i386/ceill.s", -"musl/src/math/i386/exp2l.s", -"musl/src/math/i386/exp_ld.s", -"musl/src/math/i386/expl.s", -"musl/src/math/i386/expm1l.s", -"musl/src/math/i386/fabs.s", -"musl/src/math/i386/fabsf.s", -"musl/src/math/i386/fabsl.s", -"musl/src/math/i386/floor.s", -"musl/src/math/i386/floorf.s", -"musl/src/math/i386/floorl.s", -"musl/src/math/i386/fmod.s", -"musl/src/math/i386/fmodf.s", -"musl/src/math/i386/fmodl.s", -"musl/src/math/i386/hypot.s", -"musl/src/math/i386/hypotf.s", -"musl/src/math/i386/ldexp.s", -"musl/src/math/i386/ldexpf.s", -"musl/src/math/i386/ldexpl.s", -"musl/src/math/i386/llrint.s", -"musl/src/math/i386/llrintf.s", -"musl/src/math/i386/llrintl.s", -"musl/src/math/i386/log.s", -"musl/src/math/i386/log10.s", -"musl/src/math/i386/log10f.s", -"musl/src/math/i386/log10l.s", -"musl/src/math/i386/log1p.s", -"musl/src/math/i386/log1pf.s", -"musl/src/math/i386/log1pl.s", -"musl/src/math/i386/log2.s", -"musl/src/math/i386/log2f.s", -"musl/src/math/i386/log2l.s", -"musl/src/math/i386/logf.s", -"musl/src/math/i386/logl.s", -"musl/src/math/i386/lrint.s", -"musl/src/math/i386/lrintf.s", -"musl/src/math/i386/lrintl.s", -"musl/src/math/i386/remainder.s", -"musl/src/math/i386/remainderf.s", -"musl/src/math/i386/remainderl.s", -"musl/src/math/i386/remquo.s", -"musl/src/math/i386/remquof.s", -"musl/src/math/i386/remquol.s", -"musl/src/math/i386/rint.s", -"musl/src/math/i386/rintf.s", -"musl/src/math/i386/rintl.s", -"musl/src/math/i386/scalbln.s", -"musl/src/math/i386/scalblnf.s", -"musl/src/math/i386/scalblnl.s", -"musl/src/math/i386/scalbn.s", -"musl/src/math/i386/scalbnf.s", -"musl/src/math/i386/scalbnl.s", -"musl/src/math/i386/sqrt.s", -"musl/src/math/i386/sqrtf.s", -"musl/src/math/i386/sqrtl.s", -"musl/src/math/i386/trunc.s", -"musl/src/math/i386/truncf.s", -"musl/src/math/i386/truncl.s", -"musl/src/math/ilogb.c", -"musl/src/math/ilogbf.c", -"musl/src/math/ilogbl.c", -"musl/src/math/j0.c", -"musl/src/math/j0f.c", -"musl/src/math/j1.c", -"musl/src/math/j1f.c", -"musl/src/math/jn.c", -"musl/src/math/jnf.c", -"musl/src/math/ldexp.c", -"musl/src/math/ldexpf.c", -"musl/src/math/ldexpl.c", -"musl/src/math/lgamma.c", -"musl/src/math/lgamma_r.c", -"musl/src/math/lgammaf.c", -"musl/src/math/lgammaf_r.c", -"musl/src/math/lgammal.c", -"musl/src/math/llrint.c", -"musl/src/math/llrintf.c", -"musl/src/math/llrintl.c", -"musl/src/math/llround.c", -"musl/src/math/llroundf.c", -"musl/src/math/llroundl.c", -"musl/src/math/log.c", -"musl/src/math/log10.c", -"musl/src/math/log10f.c", -"musl/src/math/log10l.c", -"musl/src/math/log1p.c", -"musl/src/math/log1pf.c", -"musl/src/math/log1pl.c", -"musl/src/math/log2.c", -"musl/src/math/log2_data.c", -"musl/src/math/log2f.c", -"musl/src/math/log2f_data.c", -"musl/src/math/log2l.c", -"musl/src/math/log_data.c", -"musl/src/math/logb.c", -"musl/src/math/logbf.c", -"musl/src/math/logbl.c", -"musl/src/math/logf.c", -"musl/src/math/logf_data.c", -"musl/src/math/logl.c", -"musl/src/math/lrint.c", -"musl/src/math/lrintf.c", -"musl/src/math/lrintl.c", -"musl/src/math/lround.c", -"musl/src/math/lroundf.c", -"musl/src/math/lroundl.c", -"musl/src/math/mips/fabs.c", -"musl/src/math/mips/fabsf.c", -"musl/src/math/mips/sqrt.c", -"musl/src/math/mips/sqrtf.c", -"musl/src/math/modf.c", -"musl/src/math/modff.c", -"musl/src/math/modfl.c", -"musl/src/math/nan.c", -"musl/src/math/nanf.c", -"musl/src/math/nanl.c", -"musl/src/math/nearbyint.c", -"musl/src/math/nearbyintf.c", -"musl/src/math/nearbyintl.c", -"musl/src/math/nextafter.c", -"musl/src/math/nextafterf.c", -"musl/src/math/nextafterl.c", -"musl/src/math/nexttoward.c", -"musl/src/math/nexttowardf.c", -"musl/src/math/nexttowardl.c", -"musl/src/math/pow.c", -"musl/src/math/pow_data.c", -"musl/src/math/powerpc/fabs.c", -"musl/src/math/powerpc/fabsf.c", -"musl/src/math/powerpc/fma.c", -"musl/src/math/powerpc/fmaf.c", -"musl/src/math/powerpc/sqrt.c", -"musl/src/math/powerpc/sqrtf.c", -"musl/src/math/powerpc64/ceil.c", -"musl/src/math/powerpc64/ceilf.c", -"musl/src/math/powerpc64/fabs.c", -"musl/src/math/powerpc64/fabsf.c", -"musl/src/math/powerpc64/floor.c", -"musl/src/math/powerpc64/floorf.c", -"musl/src/math/powerpc64/fma.c", -"musl/src/math/powerpc64/fmaf.c", -"musl/src/math/powerpc64/fmax.c", -"musl/src/math/powerpc64/fmaxf.c", -"musl/src/math/powerpc64/fmin.c", -"musl/src/math/powerpc64/fminf.c", -"musl/src/math/powerpc64/lrint.c", -"musl/src/math/powerpc64/lrintf.c", -"musl/src/math/powerpc64/lround.c", -"musl/src/math/powerpc64/lroundf.c", -"musl/src/math/powerpc64/round.c", -"musl/src/math/powerpc64/roundf.c", -"musl/src/math/powerpc64/sqrt.c", -"musl/src/math/powerpc64/sqrtf.c", -"musl/src/math/powerpc64/trunc.c", -"musl/src/math/powerpc64/truncf.c", -"musl/src/math/powf.c", -"musl/src/math/powf_data.c", -"musl/src/math/powl.c", -"musl/src/math/remainder.c", -"musl/src/math/remainderf.c", -"musl/src/math/remainderl.c", -"musl/src/math/remquo.c", -"musl/src/math/remquof.c", -"musl/src/math/remquol.c", -"musl/src/math/rint.c", -"musl/src/math/rintf.c", -"musl/src/math/rintl.c", -"musl/src/math/riscv64/copysign.c", -"musl/src/math/riscv64/copysignf.c", -"musl/src/math/riscv64/fabs.c", -"musl/src/math/riscv64/fabsf.c", -"musl/src/math/riscv64/fma.c", -"musl/src/math/riscv64/fmaf.c", -"musl/src/math/riscv64/fmax.c", -"musl/src/math/riscv64/fmaxf.c", -"musl/src/math/riscv64/fmin.c", -"musl/src/math/riscv64/fminf.c", -"musl/src/math/riscv64/sqrt.c", -"musl/src/math/riscv64/sqrtf.c", -"musl/src/math/round.c", -"musl/src/math/roundf.c", -"musl/src/math/roundl.c", -"musl/src/math/s390x/ceil.c", -"musl/src/math/s390x/ceilf.c", -"musl/src/math/s390x/ceill.c", -"musl/src/math/s390x/fabs.c", -"musl/src/math/s390x/fabsf.c", -"musl/src/math/s390x/fabsl.c", -"musl/src/math/s390x/floor.c", -"musl/src/math/s390x/floorf.c", -"musl/src/math/s390x/floorl.c", -"musl/src/math/s390x/fma.c", -"musl/src/math/s390x/fmaf.c", -"musl/src/math/s390x/nearbyint.c", -"musl/src/math/s390x/nearbyintf.c", -"musl/src/math/s390x/nearbyintl.c", -"musl/src/math/s390x/rint.c", -"musl/src/math/s390x/rintf.c", -"musl/src/math/s390x/rintl.c", -"musl/src/math/s390x/round.c", -"musl/src/math/s390x/roundf.c", -"musl/src/math/s390x/roundl.c", -"musl/src/math/s390x/sqrt.c", -"musl/src/math/s390x/sqrtf.c", -"musl/src/math/s390x/sqrtl.c", -"musl/src/math/s390x/trunc.c", -"musl/src/math/s390x/truncf.c", -"musl/src/math/s390x/truncl.c", -"musl/src/math/scalb.c", -"musl/src/math/scalbf.c", -"musl/src/math/scalbln.c", -"musl/src/math/scalblnf.c", -"musl/src/math/scalblnl.c", -"musl/src/math/scalbn.c", -"musl/src/math/scalbnf.c", -"musl/src/math/scalbnl.c", -"musl/src/math/signgam.c", -"musl/src/math/significand.c", -"musl/src/math/significandf.c", -"musl/src/math/sin.c", -"musl/src/math/sincos.c", -"musl/src/math/sincosf.c", -"musl/src/math/sincosl.c", -"musl/src/math/sinf.c", -"musl/src/math/sinh.c", -"musl/src/math/sinhf.c", -"musl/src/math/sinhl.c", -"musl/src/math/sinl.c", -"musl/src/math/sqrt.c", -"musl/src/math/sqrtf.c", -"musl/src/math/sqrtl.c", -"musl/src/math/tan.c", -"musl/src/math/tanf.c", -"musl/src/math/tanh.c", -"musl/src/math/tanhf.c", -"musl/src/math/tanhl.c", -"musl/src/math/tanl.c", -"musl/src/math/tgamma.c", -"musl/src/math/tgammaf.c", -"musl/src/math/tgammal.c", -"musl/src/math/trunc.c", -"musl/src/math/truncf.c", -"musl/src/math/truncl.c", -"musl/src/math/x32/__invtrigl.s", -"musl/src/math/x32/acosl.s", -"musl/src/math/x32/asinl.s", -"musl/src/math/x32/atan2l.s", -"musl/src/math/x32/atanl.s", -"musl/src/math/x32/ceill.s", -"musl/src/math/x32/exp2l.s", -"musl/src/math/x32/expl.s", -"musl/src/math/x32/expm1l.s", -"musl/src/math/x32/fabs.s", -"musl/src/math/x32/fabsf.s", -"musl/src/math/x32/fabsl.s", -"musl/src/math/x32/floorl.s", -"musl/src/math/x32/fma.c", -"musl/src/math/x32/fmaf.c", -"musl/src/math/x32/fmodl.s", -"musl/src/math/x32/llrint.s", -"musl/src/math/x32/llrintf.s", -"musl/src/math/x32/llrintl.s", -"musl/src/math/x32/log10l.s", -"musl/src/math/x32/log1pl.s", -"musl/src/math/x32/log2l.s", -"musl/src/math/x32/logl.s", -"musl/src/math/x32/lrint.s", -"musl/src/math/x32/lrintf.s", -"musl/src/math/x32/lrintl.s", -"musl/src/math/x32/remainderl.s", -"musl/src/math/x32/rintl.s", -"musl/src/math/x32/sqrt.s", -"musl/src/math/x32/sqrtf.s", -"musl/src/math/x32/sqrtl.s", -"musl/src/math/x32/truncl.s", -"musl/src/math/x86_64/__invtrigl.s", -"musl/src/math/x86_64/acosl.s", -"musl/src/math/x86_64/asinl.s", -"musl/src/math/x86_64/atan2l.s", -"musl/src/math/x86_64/atanl.s", -"musl/src/math/x86_64/ceill.s", -"musl/src/math/x86_64/exp2l.s", -"musl/src/math/x86_64/expl.s", -"musl/src/math/x86_64/expm1l.s", -"musl/src/math/x86_64/fabs.s", -"musl/src/math/x86_64/fabsf.s", -"musl/src/math/x86_64/fabsl.s", -"musl/src/math/x86_64/floorl.s", -"musl/src/math/x86_64/fma.c", -"musl/src/math/x86_64/fmaf.c", -"musl/src/math/x86_64/fmodl.s", -"musl/src/math/x86_64/llrint.s", -"musl/src/math/x86_64/llrintf.s", -"musl/src/math/x86_64/llrintl.s", -"musl/src/math/x86_64/log10l.s", -"musl/src/math/x86_64/log1pl.s", -"musl/src/math/x86_64/log2l.s", -"musl/src/math/x86_64/logl.s", -"musl/src/math/x86_64/lrint.s", -"musl/src/math/x86_64/lrintf.s", -"musl/src/math/x86_64/lrintl.s", -"musl/src/math/x86_64/remainderl.s", -"musl/src/math/x86_64/rintl.s", -"musl/src/math/x86_64/sqrt.s", -"musl/src/math/x86_64/sqrtf.s", -"musl/src/math/x86_64/sqrtl.s", -"musl/src/math/x86_64/truncl.s", -"musl/src/misc/a64l.c", -"musl/src/misc/basename.c", -"musl/src/misc/dirname.c", -"musl/src/misc/ffs.c", -"musl/src/misc/ffsl.c", -"musl/src/misc/ffsll.c", -"musl/src/misc/fmtmsg.c", -"musl/src/misc/forkpty.c", -"musl/src/misc/get_current_dir_name.c", -"musl/src/misc/getauxval.c", -"musl/src/misc/getdomainname.c", -"musl/src/misc/getentropy.c", -"musl/src/misc/gethostid.c", -"musl/src/misc/getopt.c", -"musl/src/misc/getopt_long.c", -"musl/src/misc/getpriority.c", -"musl/src/misc/getresgid.c", -"musl/src/misc/getresuid.c", -"musl/src/misc/getrlimit.c", -"musl/src/misc/getrusage.c", -"musl/src/misc/getsubopt.c", -"musl/src/misc/initgroups.c", -"musl/src/misc/ioctl.c", -"musl/src/misc/issetugid.c", -"musl/src/misc/lockf.c", -"musl/src/misc/login_tty.c", -"musl/src/misc/mntent.c", -"musl/src/misc/nftw.c", -"musl/src/misc/openpty.c", -"musl/src/misc/ptsname.c", -"musl/src/misc/pty.c", -"musl/src/misc/realpath.c", -"musl/src/misc/setdomainname.c", -"musl/src/misc/setpriority.c", -"musl/src/misc/setrlimit.c", -"musl/src/misc/syscall.c", -"musl/src/misc/syslog.c", -"musl/src/misc/uname.c", -"musl/src/misc/wordexp.c", -"musl/src/mman/madvise.c", -"musl/src/mman/mincore.c", -"musl/src/mman/mlock.c", -"musl/src/mman/mlockall.c", -"musl/src/mman/mmap.c", -"musl/src/mman/mprotect.c", -"musl/src/mman/mremap.c", -"musl/src/mman/msync.c", -"musl/src/mman/munlock.c", -"musl/src/mman/munlockall.c", -"musl/src/mman/munmap.c", -"musl/src/mman/posix_madvise.c", -"musl/src/mman/shm_open.c", -"musl/src/mq/mq_close.c", -"musl/src/mq/mq_getattr.c", -"musl/src/mq/mq_notify.c", -"musl/src/mq/mq_open.c", -"musl/src/mq/mq_receive.c", -"musl/src/mq/mq_send.c", -"musl/src/mq/mq_setattr.c", -"musl/src/mq/mq_timedreceive.c", -"musl/src/mq/mq_timedsend.c", -"musl/src/mq/mq_unlink.c", -"musl/src/multibyte/btowc.c", -"musl/src/multibyte/c16rtomb.c", -"musl/src/multibyte/c32rtomb.c", -"musl/src/multibyte/internal.c", -"musl/src/multibyte/mblen.c", -"musl/src/multibyte/mbrlen.c", -"musl/src/multibyte/mbrtoc16.c", -"musl/src/multibyte/mbrtoc32.c", -"musl/src/multibyte/mbrtowc.c", -"musl/src/multibyte/mbsinit.c", -"musl/src/multibyte/mbsnrtowcs.c", -"musl/src/multibyte/mbsrtowcs.c", -"musl/src/multibyte/mbstowcs.c", -"musl/src/multibyte/mbtowc.c", -"musl/src/multibyte/wcrtomb.c", -"musl/src/multibyte/wcsnrtombs.c", -"musl/src/multibyte/wcsrtombs.c", -"musl/src/multibyte/wcstombs.c", -"musl/src/multibyte/wctob.c", -"musl/src/multibyte/wctomb.c", -"musl/src/network/accept.c", -"musl/src/network/accept4.c", -"musl/src/network/bind.c", -"musl/src/network/connect.c", -"musl/src/network/dn_comp.c", -"musl/src/network/dn_expand.c", -"musl/src/network/dn_skipname.c", -"musl/src/network/dns_parse.c", -"musl/src/network/ent.c", -"musl/src/network/ether.c", -"musl/src/network/freeaddrinfo.c", -"musl/src/network/gai_strerror.c", -"musl/src/network/getaddrinfo.c", -"musl/src/network/gethostbyaddr.c", -"musl/src/network/gethostbyaddr_r.c", -"musl/src/network/gethostbyname.c", -"musl/src/network/gethostbyname2.c", -"musl/src/network/gethostbyname2_r.c", -"musl/src/network/gethostbyname_r.c", -"musl/src/network/getifaddrs.c", -"musl/src/network/getnameinfo.c", -"musl/src/network/getpeername.c", -"musl/src/network/getservbyname.c", -"musl/src/network/getservbyname_r.c", -"musl/src/network/getservbyport.c", -"musl/src/network/getservbyport_r.c", -"musl/src/network/getsockname.c", -"musl/src/network/getsockopt.c", -"musl/src/network/h_errno.c", -"musl/src/network/herror.c", -"musl/src/network/hstrerror.c", -"musl/src/network/htonl.c", -"musl/src/network/htons.c", -"musl/src/network/if_freenameindex.c", -"musl/src/network/if_indextoname.c", -"musl/src/network/if_nameindex.c", -"musl/src/network/if_nametoindex.c", -"musl/src/network/in6addr_any.c", -"musl/src/network/in6addr_loopback.c", -"musl/src/network/inet_addr.c", -"musl/src/network/inet_aton.c", -"musl/src/network/inet_legacy.c", -"musl/src/network/inet_ntoa.c", -"musl/src/network/inet_ntop.c", -"musl/src/network/inet_pton.c", -"musl/src/network/listen.c", -"musl/src/network/lookup_ipliteral.c", -"musl/src/network/lookup_name.c", -"musl/src/network/lookup_serv.c", -"musl/src/network/netlink.c", -"musl/src/network/netname.c", -"musl/src/network/ns_parse.c", -"musl/src/network/ntohl.c", -"musl/src/network/ntohs.c", -"musl/src/network/proto.c", -"musl/src/network/recv.c", -"musl/src/network/recvfrom.c", -"musl/src/network/recvmmsg.c", -"musl/src/network/recvmsg.c", -"musl/src/network/res_init.c", -"musl/src/network/res_mkquery.c", -"musl/src/network/res_msend.c", -"musl/src/network/res_query.c", -"musl/src/network/res_querydomain.c", -"musl/src/network/res_send.c", -"musl/src/network/res_state.c", -"musl/src/network/resolvconf.c", -"musl/src/network/send.c", -"musl/src/network/sendmmsg.c", -"musl/src/network/sendmsg.c", -"musl/src/network/sendto.c", -"musl/src/network/serv.c", -"musl/src/network/setsockopt.c", -"musl/src/network/shutdown.c", -"musl/src/network/sockatmark.c", -"musl/src/network/socket.c", -"musl/src/network/socketpair.c", -"musl/src/passwd/fgetgrent.c", -"musl/src/passwd/fgetpwent.c", -"musl/src/passwd/fgetspent.c", -"musl/src/passwd/getgr_a.c", -"musl/src/passwd/getgr_r.c", -"musl/src/passwd/getgrent.c", -"musl/src/passwd/getgrent_a.c", -"musl/src/passwd/getgrouplist.c", -"musl/src/passwd/getpw_a.c", -"musl/src/passwd/getpw_r.c", -"musl/src/passwd/getpwent.c", -"musl/src/passwd/getpwent_a.c", -"musl/src/passwd/getspent.c", -"musl/src/passwd/getspnam.c", -"musl/src/passwd/getspnam_r.c", -"musl/src/passwd/lckpwdf.c", -"musl/src/passwd/nscd_query.c", -"musl/src/passwd/putgrent.c", -"musl/src/passwd/putpwent.c", -"musl/src/passwd/putspent.c", -"musl/src/prng/__rand48_step.c", -"musl/src/prng/__seed48.c", -"musl/src/prng/drand48.c", -"musl/src/prng/lcong48.c", -"musl/src/prng/lrand48.c", -"musl/src/prng/mrand48.c", -"musl/src/prng/rand.c", -"musl/src/prng/rand_r.c", -"musl/src/prng/random.c", -"musl/src/prng/seed48.c", -"musl/src/prng/srand48.c", -"musl/src/process/arm/vfork.s", -"musl/src/process/execl.c", -"musl/src/process/execle.c", -"musl/src/process/execlp.c", -"musl/src/process/execv.c", -"musl/src/process/execve.c", -"musl/src/process/execvp.c", -"musl/src/process/fexecve.c", -"musl/src/process/fork.c", -"musl/src/process/i386/vfork.s", -"musl/src/process/posix_spawn.c", -"musl/src/process/posix_spawn_file_actions_addchdir.c", -"musl/src/process/posix_spawn_file_actions_addclose.c", -"musl/src/process/posix_spawn_file_actions_adddup2.c", -"musl/src/process/posix_spawn_file_actions_addfchdir.c", -"musl/src/process/posix_spawn_file_actions_addopen.c", -"musl/src/process/posix_spawn_file_actions_destroy.c", -"musl/src/process/posix_spawn_file_actions_init.c", -"musl/src/process/posix_spawnattr_destroy.c", -"musl/src/process/posix_spawnattr_getflags.c", -"musl/src/process/posix_spawnattr_getpgroup.c", -"musl/src/process/posix_spawnattr_getsigdefault.c", -"musl/src/process/posix_spawnattr_getsigmask.c", -"musl/src/process/posix_spawnattr_init.c", -"musl/src/process/posix_spawnattr_sched.c", -"musl/src/process/posix_spawnattr_setflags.c", -"musl/src/process/posix_spawnattr_setpgroup.c", -"musl/src/process/posix_spawnattr_setsigdefault.c", -"musl/src/process/posix_spawnattr_setsigmask.c", -"musl/src/process/posix_spawnp.c", -"musl/src/process/s390x/vfork.s", -"musl/src/process/sh/vfork.s", -"musl/src/process/system.c", -"musl/src/process/vfork.c", -"musl/src/process/wait.c", -"musl/src/process/waitid.c", -"musl/src/process/waitpid.c", -"musl/src/process/x32/vfork.s", -"musl/src/process/x86_64/vfork.s", -"musl/src/regex/fnmatch.c", -"musl/src/regex/glob.c", -"musl/src/regex/regcomp.c", -"musl/src/regex/regerror.c", -"musl/src/regex/regexec.c", -"musl/src/regex/tre-mem.c", -"musl/src/sched/affinity.c", -"musl/src/sched/sched_cpucount.c", -"musl/src/sched/sched_get_priority_max.c", -"musl/src/sched/sched_getcpu.c", -"musl/src/sched/sched_getparam.c", -"musl/src/sched/sched_getscheduler.c", -"musl/src/sched/sched_rr_get_interval.c", -"musl/src/sched/sched_setparam.c", -"musl/src/sched/sched_setscheduler.c", -"musl/src/sched/sched_yield.c", -"musl/src/search/hsearch.c", -"musl/src/search/insque.c", -"musl/src/search/lsearch.c", -"musl/src/search/tdelete.c", -"musl/src/search/tdestroy.c", -"musl/src/search/tfind.c", -"musl/src/search/tsearch.c", -"musl/src/search/twalk.c", -"musl/src/select/poll.c", -"musl/src/select/pselect.c", -"musl/src/select/select.c", -"musl/src/setjmp/aarch64/longjmp.s", -"musl/src/setjmp/aarch64/setjmp.s", -"musl/src/setjmp/arm/longjmp.S", -"musl/src/setjmp/arm/setjmp.S", -"musl/src/setjmp/i386/longjmp.s", -"musl/src/setjmp/i386/setjmp.s", -"musl/src/setjmp/longjmp.c", -"musl/src/setjmp/m68k/longjmp.s", -"musl/src/setjmp/m68k/setjmp.s", -"musl/src/setjmp/microblaze/longjmp.s", -"musl/src/setjmp/microblaze/setjmp.s", -"musl/src/setjmp/mips/longjmp.S", -"musl/src/setjmp/mips/setjmp.S", -"musl/src/setjmp/mips64/longjmp.S", -"musl/src/setjmp/mips64/setjmp.S", -"musl/src/setjmp/mipsn32/longjmp.S", -"musl/src/setjmp/mipsn32/setjmp.S", -"musl/src/setjmp/or1k/longjmp.s", -"musl/src/setjmp/or1k/setjmp.s", -"musl/src/setjmp/powerpc/longjmp.S", -"musl/src/setjmp/powerpc/setjmp.S", -"musl/src/setjmp/powerpc64/longjmp.s", -"musl/src/setjmp/powerpc64/setjmp.s", -"musl/src/setjmp/riscv64/longjmp.S", -"musl/src/setjmp/riscv64/setjmp.S", -"musl/src/setjmp/s390x/longjmp.s", -"musl/src/setjmp/s390x/setjmp.s", -"musl/src/setjmp/setjmp.c", -"musl/src/setjmp/sh/longjmp.S", -"musl/src/setjmp/sh/setjmp.S", -"musl/src/setjmp/x32/longjmp.s", -"musl/src/setjmp/x32/setjmp.s", -"musl/src/setjmp/x86_64/longjmp.s", -"musl/src/setjmp/x86_64/setjmp.s", -"musl/src/signal/aarch64/restore.s", -"musl/src/signal/aarch64/sigsetjmp.s", -"musl/src/signal/arm/restore.s", -"musl/src/signal/arm/sigsetjmp.s", -"musl/src/signal/block.c", -"musl/src/signal/getitimer.c", -"musl/src/signal/i386/restore.s", -"musl/src/signal/i386/sigsetjmp.s", -"musl/src/signal/kill.c", -"musl/src/signal/killpg.c", -"musl/src/signal/m68k/sigsetjmp.s", -"musl/src/signal/microblaze/restore.s", -"musl/src/signal/microblaze/sigsetjmp.s", -"musl/src/signal/mips/restore.s", -"musl/src/signal/mips/sigsetjmp.s", -"musl/src/signal/mips64/restore.s", -"musl/src/signal/mips64/sigsetjmp.s", -"musl/src/signal/mipsn32/restore.s", -"musl/src/signal/mipsn32/sigsetjmp.s", -"musl/src/signal/or1k/sigsetjmp.s", -"musl/src/signal/powerpc/restore.s", -"musl/src/signal/powerpc/sigsetjmp.s", -"musl/src/signal/powerpc64/restore.s", -"musl/src/signal/powerpc64/sigsetjmp.s", -"musl/src/signal/psiginfo.c", -"musl/src/signal/psignal.c", -"musl/src/signal/raise.c", -"musl/src/signal/restore.c", -"musl/src/signal/riscv64/restore.s", -"musl/src/signal/riscv64/sigsetjmp.s", -"musl/src/signal/s390x/restore.s", -"musl/src/signal/s390x/sigsetjmp.s", -"musl/src/signal/setitimer.c", -"musl/src/signal/sh/restore.s", -"musl/src/signal/sh/sigsetjmp.s", -"musl/src/signal/sigaction.c", -"musl/src/signal/sigaddset.c", -"musl/src/signal/sigaltstack.c", -"musl/src/signal/sigandset.c", -"musl/src/signal/sigdelset.c", -"musl/src/signal/sigemptyset.c", -"musl/src/signal/sigfillset.c", -"musl/src/signal/sighold.c", -"musl/src/signal/sigignore.c", -"musl/src/signal/siginterrupt.c", -"musl/src/signal/sigisemptyset.c", -"musl/src/signal/sigismember.c", -"musl/src/signal/siglongjmp.c", -"musl/src/signal/signal.c", -"musl/src/signal/sigorset.c", -"musl/src/signal/sigpause.c", -"musl/src/signal/sigpending.c", -"musl/src/signal/sigprocmask.c", -"musl/src/signal/sigqueue.c", -"musl/src/signal/sigrelse.c", -"musl/src/signal/sigrtmax.c", -"musl/src/signal/sigrtmin.c", -"musl/src/signal/sigset.c", -"musl/src/signal/sigsetjmp.c", -"musl/src/signal/sigsetjmp_tail.c", -"musl/src/signal/sigsuspend.c", -"musl/src/signal/sigtimedwait.c", -"musl/src/signal/sigwait.c", -"musl/src/signal/sigwaitinfo.c", -"musl/src/signal/x32/getitimer.c", -"musl/src/signal/x32/restore.s", -"musl/src/signal/x32/setitimer.c", -"musl/src/signal/x32/sigsetjmp.s", -"musl/src/signal/x86_64/restore.s", -"musl/src/signal/x86_64/sigsetjmp.s", -"musl/src/stat/__xstat.c", -"musl/src/stat/chmod.c", -"musl/src/stat/fchmod.c", -"musl/src/stat/fchmodat.c", -"musl/src/stat/fstat.c", -"musl/src/stat/fstatat.c", -"musl/src/stat/futimens.c", -"musl/src/stat/futimesat.c", -"musl/src/stat/lchmod.c", -"musl/src/stat/lstat.c", -"musl/src/stat/mkdir.c", -"musl/src/stat/mkdirat.c", -"musl/src/stat/mkfifo.c", -"musl/src/stat/mkfifoat.c", -"musl/src/stat/mknod.c", -"musl/src/stat/mknodat.c", -"musl/src/stat/stat.c", -"musl/src/stat/statvfs.c", -"musl/src/stat/umask.c", -"musl/src/stat/utimensat.c", -"musl/src/stdio/__fclose_ca.c", -"musl/src/stdio/__fdopen.c", -"musl/src/stdio/__fmodeflags.c", -"musl/src/stdio/__fopen_rb_ca.c", -"musl/src/stdio/__lockfile.c", -"musl/src/stdio/__overflow.c", -"musl/src/stdio/__stdio_close.c", -"musl/src/stdio/__stdio_exit.c", -"musl/src/stdio/__stdio_read.c", -"musl/src/stdio/__stdio_seek.c", -"musl/src/stdio/__stdio_write.c", -"musl/src/stdio/__stdout_write.c", -"musl/src/stdio/__string_read.c", -"musl/src/stdio/__toread.c", -"musl/src/stdio/__towrite.c", -"musl/src/stdio/__uflow.c", -"musl/src/stdio/asprintf.c", -"musl/src/stdio/clearerr.c", -"musl/src/stdio/dprintf.c", -"musl/src/stdio/ext.c", -"musl/src/stdio/ext2.c", -"musl/src/stdio/fclose.c", -"musl/src/stdio/feof.c", -"musl/src/stdio/ferror.c", -"musl/src/stdio/fflush.c", -"musl/src/stdio/fgetc.c", -"musl/src/stdio/fgetln.c", -"musl/src/stdio/fgetpos.c", -"musl/src/stdio/fgets.c", -"musl/src/stdio/fgetwc.c", -"musl/src/stdio/fgetws.c", -"musl/src/stdio/fileno.c", -"musl/src/stdio/flockfile.c", -"musl/src/stdio/fmemopen.c", -"musl/src/stdio/fopen.c", -"musl/src/stdio/fopencookie.c", -"musl/src/stdio/fprintf.c", -"musl/src/stdio/fputc.c", -"musl/src/stdio/fputs.c", -"musl/src/stdio/fputwc.c", -"musl/src/stdio/fputws.c", -"musl/src/stdio/fread.c", -"musl/src/stdio/freopen.c", -"musl/src/stdio/fscanf.c", -"musl/src/stdio/fseek.c", -"musl/src/stdio/fsetpos.c", -"musl/src/stdio/ftell.c", -"musl/src/stdio/ftrylockfile.c", -"musl/src/stdio/funlockfile.c", -"musl/src/stdio/fwide.c", -"musl/src/stdio/fwprintf.c", -"musl/src/stdio/fwrite.c", -"musl/src/stdio/fwscanf.c", -"musl/src/stdio/getc.c", -"musl/src/stdio/getc_unlocked.c", -"musl/src/stdio/getchar.c", -"musl/src/stdio/getchar_unlocked.c", -"musl/src/stdio/getdelim.c", -"musl/src/stdio/getline.c", -"musl/src/stdio/gets.c", -"musl/src/stdio/getw.c", -"musl/src/stdio/getwc.c", -"musl/src/stdio/getwchar.c", -"musl/src/stdio/ofl.c", -"musl/src/stdio/ofl_add.c", -"musl/src/stdio/open_memstream.c", -"musl/src/stdio/open_wmemstream.c", -"musl/src/stdio/pclose.c", -"musl/src/stdio/perror.c", -"musl/src/stdio/popen.c", -"musl/src/stdio/printf.c", -"musl/src/stdio/putc.c", -"musl/src/stdio/putc_unlocked.c", -"musl/src/stdio/putchar.c", -"musl/src/stdio/putchar_unlocked.c", -"musl/src/stdio/puts.c", -"musl/src/stdio/putw.c", -"musl/src/stdio/putwc.c", -"musl/src/stdio/putwchar.c", -"musl/src/stdio/remove.c", -"musl/src/stdio/rename.c", -"musl/src/stdio/rewind.c", -"musl/src/stdio/scanf.c", -"musl/src/stdio/setbuf.c", -"musl/src/stdio/setbuffer.c", -"musl/src/stdio/setlinebuf.c", -"musl/src/stdio/setvbuf.c", -"musl/src/stdio/snprintf.c", -"musl/src/stdio/sprintf.c", -"musl/src/stdio/sscanf.c", -"musl/src/stdio/stderr.c", -"musl/src/stdio/stdin.c", -"musl/src/stdio/stdout.c", -"musl/src/stdio/swprintf.c", -"musl/src/stdio/swscanf.c", -"musl/src/stdio/tempnam.c", -"musl/src/stdio/tmpfile.c", -"musl/src/stdio/tmpnam.c", -"musl/src/stdio/ungetc.c", -"musl/src/stdio/ungetwc.c", -"musl/src/stdio/vasprintf.c", -"musl/src/stdio/vdprintf.c", -"musl/src/stdio/vfprintf.c", -"musl/src/stdio/vfscanf.c", -"musl/src/stdio/vfwprintf.c", -"musl/src/stdio/vfwscanf.c", -"musl/src/stdio/vprintf.c", -"musl/src/stdio/vscanf.c", -"musl/src/stdio/vsnprintf.c", -"musl/src/stdio/vsprintf.c", -"musl/src/stdio/vsscanf.c", -"musl/src/stdio/vswprintf.c", -"musl/src/stdio/vswscanf.c", -"musl/src/stdio/vwprintf.c", -"musl/src/stdio/vwscanf.c", -"musl/src/stdio/wprintf.c", -"musl/src/stdio/wscanf.c", -"musl/src/stdlib/abs.c", -"musl/src/stdlib/atof.c", -"musl/src/stdlib/atoi.c", -"musl/src/stdlib/atol.c", -"musl/src/stdlib/atoll.c", -"musl/src/stdlib/bsearch.c", -"musl/src/stdlib/div.c", -"musl/src/stdlib/ecvt.c", -"musl/src/stdlib/fcvt.c", -"musl/src/stdlib/gcvt.c", -"musl/src/stdlib/imaxabs.c", -"musl/src/stdlib/imaxdiv.c", -"musl/src/stdlib/labs.c", -"musl/src/stdlib/ldiv.c", -"musl/src/stdlib/llabs.c", -"musl/src/stdlib/lldiv.c", -"musl/src/stdlib/qsort.c", -"musl/src/stdlib/strtod.c", -"musl/src/stdlib/strtol.c", -"musl/src/stdlib/wcstod.c", -"musl/src/stdlib/wcstol.c", -"musl/src/string/arm/__aeabi_memcpy.s", -"musl/src/string/arm/__aeabi_memset.s", -"musl/src/string/arm/memcpy.c", -"musl/src/string/arm/memcpy_le.S", -"musl/src/string/bcmp.c", -"musl/src/string/bcopy.c", -"musl/src/string/bzero.c", -"musl/src/string/explicit_bzero.c", -"musl/src/string/i386/memcpy.s", -"musl/src/string/i386/memmove.s", -"musl/src/string/i386/memset.s", -"musl/src/string/index.c", -"musl/src/string/memccpy.c", -"musl/src/string/memchr.c", -"musl/src/string/memcmp.c", -"musl/src/string/memcpy.c", -"musl/src/string/memmem.c", -"musl/src/string/memmove.c", -"musl/src/string/mempcpy.c", -"musl/src/string/memrchr.c", -"musl/src/string/memset.c", -"musl/src/string/rindex.c", -"musl/src/string/stpcpy.c", -"musl/src/string/stpncpy.c", -"musl/src/string/strcasecmp.c", -"musl/src/string/strcasestr.c", -"musl/src/string/strcat.c", -"musl/src/string/strchr.c", -"musl/src/string/strchrnul.c", -"musl/src/string/strcmp.c", -"musl/src/string/strcpy.c", -"musl/src/string/strcspn.c", -"musl/src/string/strdup.c", -"musl/src/string/strerror_r.c", -"musl/src/string/strlcat.c", -"musl/src/string/strlcpy.c", -"musl/src/string/strlen.c", -"musl/src/string/strncasecmp.c", -"musl/src/string/strncat.c", -"musl/src/string/strncmp.c", -"musl/src/string/strncpy.c", -"musl/src/string/strndup.c", -"musl/src/string/strnlen.c", -"musl/src/string/strpbrk.c", -"musl/src/string/strrchr.c", -"musl/src/string/strsep.c", -"musl/src/string/strsignal.c", -"musl/src/string/strspn.c", -"musl/src/string/strstr.c", -"musl/src/string/strtok.c", -"musl/src/string/strtok_r.c", -"musl/src/string/strverscmp.c", -"musl/src/string/swab.c", -"musl/src/string/wcpcpy.c", -"musl/src/string/wcpncpy.c", -"musl/src/string/wcscasecmp.c", -"musl/src/string/wcscasecmp_l.c", -"musl/src/string/wcscat.c", -"musl/src/string/wcschr.c", -"musl/src/string/wcscmp.c", -"musl/src/string/wcscpy.c", -"musl/src/string/wcscspn.c", -"musl/src/string/wcsdup.c", -"musl/src/string/wcslen.c", -"musl/src/string/wcsncasecmp.c", -"musl/src/string/wcsncasecmp_l.c", -"musl/src/string/wcsncat.c", -"musl/src/string/wcsncmp.c", -"musl/src/string/wcsncpy.c", -"musl/src/string/wcsnlen.c", -"musl/src/string/wcspbrk.c", -"musl/src/string/wcsrchr.c", -"musl/src/string/wcsspn.c", -"musl/src/string/wcsstr.c", -"musl/src/string/wcstok.c", -"musl/src/string/wcswcs.c", -"musl/src/string/wmemchr.c", -"musl/src/string/wmemcmp.c", -"musl/src/string/wmemcpy.c", -"musl/src/string/wmemmove.c", -"musl/src/string/wmemset.c", -"musl/src/string/x86_64/memcpy.s", -"musl/src/string/x86_64/memmove.s", -"musl/src/string/x86_64/memset.s", -"musl/src/temp/__randname.c", -"musl/src/temp/mkdtemp.c", -"musl/src/temp/mkostemp.c", -"musl/src/temp/mkostemps.c", -"musl/src/temp/mkstemp.c", -"musl/src/temp/mkstemps.c", -"musl/src/temp/mktemp.c", -"musl/src/termios/cfgetospeed.c", -"musl/src/termios/cfmakeraw.c", -"musl/src/termios/cfsetospeed.c", -"musl/src/termios/tcdrain.c", -"musl/src/termios/tcflow.c", -"musl/src/termios/tcflush.c", -"musl/src/termios/tcgetattr.c", -"musl/src/termios/tcgetsid.c", -"musl/src/termios/tcsendbreak.c", -"musl/src/termios/tcsetattr.c", -"musl/src/thread/__lock.c", -"musl/src/thread/__set_thread_area.c", -"musl/src/thread/__syscall_cp.c", -"musl/src/thread/__timedwait.c", -"musl/src/thread/__tls_get_addr.c", -"musl/src/thread/__unmapself.c", -"musl/src/thread/__wait.c", -"musl/src/thread/aarch64/__set_thread_area.s", -"musl/src/thread/aarch64/__unmapself.s", -"musl/src/thread/aarch64/clone.s", -"musl/src/thread/aarch64/syscall_cp.s", -"musl/src/thread/arm/__aeabi_read_tp.s", -"musl/src/thread/arm/__set_thread_area.c", -"musl/src/thread/arm/__unmapself.s", -"musl/src/thread/arm/atomics.s", -"musl/src/thread/arm/clone.s", -"musl/src/thread/arm/syscall_cp.s", -"musl/src/thread/call_once.c", -"musl/src/thread/clone.c", -"musl/src/thread/cnd_broadcast.c", -"musl/src/thread/cnd_destroy.c", -"musl/src/thread/cnd_init.c", -"musl/src/thread/cnd_signal.c", -"musl/src/thread/cnd_timedwait.c", -"musl/src/thread/cnd_wait.c", -"musl/src/thread/default_attr.c", -"musl/src/thread/i386/__set_thread_area.s", -"musl/src/thread/i386/__unmapself.s", -"musl/src/thread/i386/clone.s", -"musl/src/thread/i386/syscall_cp.s", -"musl/src/thread/i386/tls.s", -"musl/src/thread/lock_ptc.c", -"musl/src/thread/m68k/__m68k_read_tp.s", -"musl/src/thread/m68k/clone.s", -"musl/src/thread/m68k/syscall_cp.s", -"musl/src/thread/microblaze/__set_thread_area.s", -"musl/src/thread/microblaze/__unmapself.s", -"musl/src/thread/microblaze/clone.s", -"musl/src/thread/microblaze/syscall_cp.s", -"musl/src/thread/mips/__unmapself.s", -"musl/src/thread/mips/clone.s", -"musl/src/thread/mips/syscall_cp.s", -"musl/src/thread/mips64/__unmapself.s", -"musl/src/thread/mips64/clone.s", -"musl/src/thread/mips64/syscall_cp.s", -"musl/src/thread/mipsn32/__unmapself.s", -"musl/src/thread/mipsn32/clone.s", -"musl/src/thread/mipsn32/syscall_cp.s", -"musl/src/thread/mtx_destroy.c", -"musl/src/thread/mtx_init.c", -"musl/src/thread/mtx_lock.c", -"musl/src/thread/mtx_timedlock.c", -"musl/src/thread/mtx_trylock.c", -"musl/src/thread/mtx_unlock.c", -"musl/src/thread/or1k/__set_thread_area.s", -"musl/src/thread/or1k/__unmapself.s", -"musl/src/thread/or1k/clone.s", -"musl/src/thread/or1k/syscall_cp.s", -"musl/src/thread/powerpc/__set_thread_area.s", -"musl/src/thread/powerpc/__unmapself.s", -"musl/src/thread/powerpc/clone.s", -"musl/src/thread/powerpc/syscall_cp.s", -"musl/src/thread/powerpc64/__set_thread_area.s", -"musl/src/thread/powerpc64/__unmapself.s", -"musl/src/thread/powerpc64/clone.s", -"musl/src/thread/powerpc64/syscall_cp.s", -"musl/src/thread/pthread_atfork.c", -"musl/src/thread/pthread_attr_destroy.c", -"musl/src/thread/pthread_attr_get.c", -"musl/src/thread/pthread_attr_init.c", -"musl/src/thread/pthread_attr_setdetachstate.c", -"musl/src/thread/pthread_attr_setguardsize.c", -"musl/src/thread/pthread_attr_setinheritsched.c", -"musl/src/thread/pthread_attr_setschedparam.c", -"musl/src/thread/pthread_attr_setschedpolicy.c", -"musl/src/thread/pthread_attr_setscope.c", -"musl/src/thread/pthread_attr_setstack.c", -"musl/src/thread/pthread_attr_setstacksize.c", -"musl/src/thread/pthread_barrier_destroy.c", -"musl/src/thread/pthread_barrier_init.c", -"musl/src/thread/pthread_barrier_wait.c", -"musl/src/thread/pthread_barrierattr_destroy.c", -"musl/src/thread/pthread_barrierattr_init.c", -"musl/src/thread/pthread_barrierattr_setpshared.c", -"musl/src/thread/pthread_cancel.c", -"musl/src/thread/pthread_cleanup_push.c", -"musl/src/thread/pthread_cond_broadcast.c", -"musl/src/thread/pthread_cond_destroy.c", -"musl/src/thread/pthread_cond_init.c", -"musl/src/thread/pthread_cond_signal.c", -"musl/src/thread/pthread_cond_timedwait.c", -"musl/src/thread/pthread_cond_wait.c", -"musl/src/thread/pthread_condattr_destroy.c", -"musl/src/thread/pthread_condattr_init.c", -"musl/src/thread/pthread_condattr_setclock.c", -"musl/src/thread/pthread_condattr_setpshared.c", -"musl/src/thread/pthread_create.c", -"musl/src/thread/pthread_detach.c", -"musl/src/thread/pthread_equal.c", -"musl/src/thread/pthread_getattr_np.c", -"musl/src/thread/pthread_getconcurrency.c", -"musl/src/thread/pthread_getcpuclockid.c", -"musl/src/thread/pthread_getschedparam.c", -"musl/src/thread/pthread_getspecific.c", -"musl/src/thread/pthread_join.c", -"musl/src/thread/pthread_key_create.c", -"musl/src/thread/pthread_kill.c", -"musl/src/thread/pthread_mutex_consistent.c", -"musl/src/thread/pthread_mutex_destroy.c", -"musl/src/thread/pthread_mutex_getprioceiling.c", -"musl/src/thread/pthread_mutex_init.c", -"musl/src/thread/pthread_mutex_lock.c", -"musl/src/thread/pthread_mutex_setprioceiling.c", -"musl/src/thread/pthread_mutex_timedlock.c", -"musl/src/thread/pthread_mutex_trylock.c", -"musl/src/thread/pthread_mutex_unlock.c", -"musl/src/thread/pthread_mutexattr_destroy.c", -"musl/src/thread/pthread_mutexattr_init.c", -"musl/src/thread/pthread_mutexattr_setprotocol.c", -"musl/src/thread/pthread_mutexattr_setpshared.c", -"musl/src/thread/pthread_mutexattr_setrobust.c", -"musl/src/thread/pthread_mutexattr_settype.c", -"musl/src/thread/pthread_once.c", -"musl/src/thread/pthread_rwlock_destroy.c", -"musl/src/thread/pthread_rwlock_init.c", -"musl/src/thread/pthread_rwlock_rdlock.c", -"musl/src/thread/pthread_rwlock_timedrdlock.c", -"musl/src/thread/pthread_rwlock_timedwrlock.c", -"musl/src/thread/pthread_rwlock_tryrdlock.c", -"musl/src/thread/pthread_rwlock_trywrlock.c", -"musl/src/thread/pthread_rwlock_unlock.c", -"musl/src/thread/pthread_rwlock_wrlock.c", -"musl/src/thread/pthread_rwlockattr_destroy.c", -"musl/src/thread/pthread_rwlockattr_init.c", -"musl/src/thread/pthread_rwlockattr_setpshared.c", -"musl/src/thread/pthread_self.c", -"musl/src/thread/pthread_setattr_default_np.c", -"musl/src/thread/pthread_setcancelstate.c", -"musl/src/thread/pthread_setcanceltype.c", -"musl/src/thread/pthread_setconcurrency.c", -"musl/src/thread/pthread_setname_np.c", -"musl/src/thread/pthread_setschedparam.c", -"musl/src/thread/pthread_setschedprio.c", -"musl/src/thread/pthread_setspecific.c", -"musl/src/thread/pthread_sigmask.c", -"musl/src/thread/pthread_spin_destroy.c", -"musl/src/thread/pthread_spin_init.c", -"musl/src/thread/pthread_spin_lock.c", -"musl/src/thread/pthread_spin_trylock.c", -"musl/src/thread/pthread_spin_unlock.c", -"musl/src/thread/pthread_testcancel.c", -"musl/src/thread/riscv64/__set_thread_area.s", -"musl/src/thread/riscv64/__unmapself.s", -"musl/src/thread/riscv64/clone.s", -"musl/src/thread/riscv64/syscall_cp.s", -"musl/src/thread/s390x/__set_thread_area.s", -"musl/src/thread/s390x/__tls_get_offset.s", -"musl/src/thread/s390x/__unmapself.s", -"musl/src/thread/s390x/clone.s", -"musl/src/thread/s390x/syscall_cp.s", -"musl/src/thread/sem_destroy.c", -"musl/src/thread/sem_getvalue.c", -"musl/src/thread/sem_init.c", -"musl/src/thread/sem_open.c", -"musl/src/thread/sem_post.c", -"musl/src/thread/sem_timedwait.c", -"musl/src/thread/sem_trywait.c", -"musl/src/thread/sem_unlink.c", -"musl/src/thread/sem_wait.c", -"musl/src/thread/sh/__set_thread_area.c", -"musl/src/thread/sh/__unmapself.c", -"musl/src/thread/sh/__unmapself_mmu.s", -"musl/src/thread/sh/atomics.s", -"musl/src/thread/sh/clone.s", -"musl/src/thread/sh/syscall_cp.s", -"musl/src/thread/synccall.c", -"musl/src/thread/syscall_cp.c", -"musl/src/thread/thrd_create.c", -"musl/src/thread/thrd_exit.c", -"musl/src/thread/thrd_join.c", -"musl/src/thread/thrd_sleep.c", -"musl/src/thread/thrd_yield.c", -"musl/src/thread/tls.c", -"musl/src/thread/tss_create.c", -"musl/src/thread/tss_delete.c", -"musl/src/thread/tss_set.c", -"musl/src/thread/vmlock.c", -"musl/src/thread/x32/__set_thread_area.s", -"musl/src/thread/x32/__unmapself.s", -"musl/src/thread/x32/clone.s", -"musl/src/thread/x32/syscall_cp.s", -"musl/src/thread/x86_64/__set_thread_area.s", -"musl/src/thread/x86_64/__unmapself.s", -"musl/src/thread/x86_64/clone.s", -"musl/src/thread/x86_64/syscall_cp.s", -"musl/src/time/__map_file.c", -"musl/src/time/__month_to_secs.c", -"musl/src/time/__secs_to_tm.c", -"musl/src/time/__tm_to_secs.c", -"musl/src/time/__tz.c", -"musl/src/time/__year_to_secs.c", -"musl/src/time/asctime.c", -"musl/src/time/asctime_r.c", -"musl/src/time/clock.c", -"musl/src/time/clock_getcpuclockid.c", -"musl/src/time/clock_getres.c", -"musl/src/time/clock_gettime.c", -"musl/src/time/clock_nanosleep.c", -"musl/src/time/clock_settime.c", -"musl/src/time/ctime.c", -"musl/src/time/ctime_r.c", -"musl/src/time/difftime.c", -"musl/src/time/ftime.c", -"musl/src/time/getdate.c", -"musl/src/time/gettimeofday.c", -"musl/src/time/gmtime.c", -"musl/src/time/gmtime_r.c", -"musl/src/time/localtime.c", -"musl/src/time/localtime_r.c", -"musl/src/time/mktime.c", -"musl/src/time/nanosleep.c", -"musl/src/time/strftime.c", -"musl/src/time/strptime.c", -"musl/src/time/time.c", -"musl/src/time/timegm.c", -"musl/src/time/timer_create.c", -"musl/src/time/timer_delete.c", -"musl/src/time/timer_getoverrun.c", -"musl/src/time/timer_gettime.c", -"musl/src/time/timer_settime.c", -"musl/src/time/times.c", -"musl/src/time/timespec_get.c", -"musl/src/time/utime.c", -"musl/src/time/wcsftime.c", -"musl/src/unistd/_exit.c", -"musl/src/unistd/access.c", -"musl/src/unistd/acct.c", -"musl/src/unistd/alarm.c", -"musl/src/unistd/chdir.c", -"musl/src/unistd/chown.c", -"musl/src/unistd/close.c", -"musl/src/unistd/ctermid.c", -"musl/src/unistd/dup.c", -"musl/src/unistd/dup2.c", -"musl/src/unistd/dup3.c", -"musl/src/unistd/faccessat.c", -"musl/src/unistd/fchdir.c", -"musl/src/unistd/fchown.c", -"musl/src/unistd/fchownat.c", -"musl/src/unistd/fdatasync.c", -"musl/src/unistd/fsync.c", -"musl/src/unistd/ftruncate.c", -"musl/src/unistd/getcwd.c", -"musl/src/unistd/getegid.c", -"musl/src/unistd/geteuid.c", -"musl/src/unistd/getgid.c", -"musl/src/unistd/getgroups.c", -"musl/src/unistd/gethostname.c", -"musl/src/unistd/getlogin.c", -"musl/src/unistd/getlogin_r.c", -"musl/src/unistd/getpgid.c", -"musl/src/unistd/getpgrp.c", -"musl/src/unistd/getpid.c", -"musl/src/unistd/getppid.c", -"musl/src/unistd/getsid.c", -"musl/src/unistd/getuid.c", -"musl/src/unistd/isatty.c", -"musl/src/unistd/lchown.c", -"musl/src/unistd/link.c", -"musl/src/unistd/linkat.c", -"musl/src/unistd/lseek.c", -"musl/src/unistd/mips/pipe.s", -"musl/src/unistd/mips64/pipe.s", -"musl/src/unistd/mipsn32/lseek.c", -"musl/src/unistd/mipsn32/pipe.s", -"musl/src/unistd/nice.c", -"musl/src/unistd/pause.c", -"musl/src/unistd/pipe.c", -"musl/src/unistd/pipe2.c", -"musl/src/unistd/posix_close.c", -"musl/src/unistd/pread.c", -"musl/src/unistd/preadv.c", -"musl/src/unistd/pwrite.c", -"musl/src/unistd/pwritev.c", -"musl/src/unistd/read.c", -"musl/src/unistd/readlink.c", -"musl/src/unistd/readlinkat.c", -"musl/src/unistd/readv.c", -"musl/src/unistd/renameat.c", -"musl/src/unistd/rmdir.c", -"musl/src/unistd/setegid.c", -"musl/src/unistd/seteuid.c", -"musl/src/unistd/setgid.c", -"musl/src/unistd/setpgid.c", -"musl/src/unistd/setpgrp.c", -"musl/src/unistd/setregid.c", -"musl/src/unistd/setresgid.c", -"musl/src/unistd/setresuid.c", -"musl/src/unistd/setreuid.c", -"musl/src/unistd/setsid.c", -"musl/src/unistd/setuid.c", -"musl/src/unistd/setxid.c", -"musl/src/unistd/sh/pipe.s", -"musl/src/unistd/sleep.c", -"musl/src/unistd/symlink.c", -"musl/src/unistd/symlinkat.c", -"musl/src/unistd/sync.c", -"musl/src/unistd/tcgetpgrp.c", -"musl/src/unistd/tcsetpgrp.c", -"musl/src/unistd/truncate.c", -"musl/src/unistd/ttyname.c", -"musl/src/unistd/ttyname_r.c", -"musl/src/unistd/ualarm.c", -"musl/src/unistd/unlink.c", -"musl/src/unistd/unlinkat.c", -"musl/src/unistd/usleep.c", -"musl/src/unistd/write.c", -"musl/src/unistd/writev.c", -"musl/src/unistd/x32/lseek.c", -}; -static const char *ZIG_MUSL_COMPAT_TIME32_FILES[] = { -"musl/compat/time32/__xstat.c", -"musl/compat/time32/adjtime32.c", -"musl/compat/time32/adjtimex_time32.c", -"musl/compat/time32/aio_suspend_time32.c", -"musl/compat/time32/clock_adjtime32.c", -"musl/compat/time32/clock_getres_time32.c", -"musl/compat/time32/clock_gettime32.c", -"musl/compat/time32/clock_nanosleep_time32.c", -"musl/compat/time32/clock_settime32.c", -"musl/compat/time32/cnd_timedwait_time32.c", -"musl/compat/time32/ctime32.c", -"musl/compat/time32/ctime32_r.c", -"musl/compat/time32/difftime32.c", -"musl/compat/time32/fstat_time32.c", -"musl/compat/time32/fstatat_time32.c", -"musl/compat/time32/ftime32.c", -"musl/compat/time32/futimens_time32.c", -"musl/compat/time32/futimes_time32.c", -"musl/compat/time32/futimesat_time32.c", -"musl/compat/time32/getitimer_time32.c", -"musl/compat/time32/getrusage_time32.c", -"musl/compat/time32/gettimeofday_time32.c", -"musl/compat/time32/gmtime32.c", -"musl/compat/time32/gmtime32_r.c", -"musl/compat/time32/localtime32.c", -"musl/compat/time32/localtime32_r.c", -"musl/compat/time32/lstat_time32.c", -"musl/compat/time32/lutimes_time32.c", -"musl/compat/time32/mktime32.c", -"musl/compat/time32/mq_timedreceive_time32.c", -"musl/compat/time32/mq_timedsend_time32.c", -"musl/compat/time32/mtx_timedlock_time32.c", -"musl/compat/time32/nanosleep_time32.c", -"musl/compat/time32/ppoll_time32.c", -"musl/compat/time32/pselect_time32.c", -"musl/compat/time32/pthread_cond_timedwait_time32.c", -"musl/compat/time32/pthread_mutex_timedlock_time32.c", -"musl/compat/time32/pthread_rwlock_timedrdlock_time32.c", -"musl/compat/time32/pthread_rwlock_timedwrlock_time32.c", -"musl/compat/time32/pthread_timedjoin_np_time32.c", -"musl/compat/time32/recvmmsg_time32.c", -"musl/compat/time32/sched_rr_get_interval_time32.c", -"musl/compat/time32/select_time32.c", -"musl/compat/time32/sem_timedwait_time32.c", -"musl/compat/time32/semtimedop_time32.c", -"musl/compat/time32/setitimer_time32.c", -"musl/compat/time32/settimeofday_time32.c", -"musl/compat/time32/sigtimedwait_time32.c", -"musl/compat/time32/stat_time32.c", -"musl/compat/time32/stime32.c", -"musl/compat/time32/thrd_sleep_time32.c", -"musl/compat/time32/time32.c", -"musl/compat/time32/time32gm.c", -"musl/compat/time32/timer_gettime32.c", -"musl/compat/time32/timer_settime32.c", -"musl/compat/time32/timerfd_gettime32.c", -"musl/compat/time32/timerfd_settime32.c", -"musl/compat/time32/timespec_get_time32.c", -"musl/compat/time32/utime_time32.c", -"musl/compat/time32/utimensat_time32.c", -"musl/compat/time32/utimes_time32.c", -"musl/compat/time32/wait3_time32.c", -"musl/compat/time32/wait4_time32.c", -}; -static const char *ZIG_LIBCXXABI_FILES[] = { -"src/abort_message.cpp", -"src/cxa_aux_runtime.cpp", -"src/cxa_default_handlers.cpp", -"src/cxa_demangle.cpp", -"src/cxa_exception.cpp", -"src/cxa_exception_storage.cpp", -"src/cxa_guard.cpp", -"src/cxa_handlers.cpp", -"src/cxa_noexception.cpp", -"src/cxa_personality.cpp", -"src/cxa_thread_atexit.cpp", -"src/cxa_unexpected.cpp", -"src/cxa_vector.cpp", -"src/cxa_virtual.cpp", -"src/fallback_malloc.cpp", -"src/private_typeinfo.cpp", -"src/stdlib_exception.cpp", -"src/stdlib_stdexcept.cpp", -"src/stdlib_typeinfo.cpp", -}; -static const char *ZIG_LIBCXX_FILES[] = { -"src/algorithm.cpp", -"src/any.cpp", -"src/bind.cpp", -"src/charconv.cpp", -"src/chrono.cpp", -"src/condition_variable.cpp", -"src/condition_variable_destructor.cpp", -"src/debug.cpp", -"src/exception.cpp", -"src/experimental/memory_resource.cpp", -"src/filesystem/directory_iterator.cpp", -"src/filesystem/operations.cpp", -"src/functional.cpp", -"src/future.cpp", -"src/hash.cpp", -"src/ios.cpp", -"src/iostream.cpp", -"src/locale.cpp", -"src/memory.cpp", -"src/mutex.cpp", -"src/mutex_destructor.cpp", -"src/new.cpp", -"src/optional.cpp", -"src/random.cpp", -"src/regex.cpp", -"src/shared_mutex.cpp", -"src/stdexcept.cpp", -"src/string.cpp", -"src/strstream.cpp", -"src/support/solaris/xlocale.cpp", -"src/support/win32/locale_win32.cpp", -"src/support/win32/support.cpp", -"src/support/win32/thread_win32.cpp", -"src/system_error.cpp", -"src/thread.cpp", -"src/typeinfo.cpp", -"src/utility.cpp", -"src/valarray.cpp", -"src/variant.cpp", -"src/vector.cpp", -}; -#endif diff --git a/src/ir.cpp b/src/ir.cpp index 6cb5d8bc2d..50076f9a86 100644 --- a/src/ir.cpp +++ b/src/ir.cpp @@ -22570,38 +22570,12 @@ static IrInstGen *ir_analyze_container_field_ptr(IrAnalyze *ira, Buf *field_name } static void add_link_lib_symbol(IrAnalyze *ira, Buf *lib_name, Buf *symbol_name, AstNode *source_node) { - bool is_libc = target_is_libc_lib_name(ira->codegen->zig_target, buf_ptr(lib_name)); - if (is_libc && ira->codegen->libc_link_lib == nullptr && !ira->codegen->reported_bad_link_libc_error) { - ir_add_error_node(ira, source_node, - buf_sprintf("dependency on library c must be explicitly specified in the build command")); + const char *msg = stage2_add_link_lib(&ira->codegen->stage1, buf_ptr(lib_name), buf_len(lib_name), + buf_ptr(symbol_name), buf_len(symbol_name)); + if (msg != nullptr) { + ir_add_error_node(ira, source_node, buf_create_from_str(msg)); ira->codegen->reported_bad_link_libc_error = true; } - - LinkLib *link_lib = add_link_lib(ira->codegen, lib_name); - for (size_t i = 0; i < link_lib->symbols.length; i += 1) { - Buf *existing_symbol_name = link_lib->symbols.at(i); - if (buf_eql_buf(existing_symbol_name, symbol_name)) { - return; - } - } - - if (!is_libc && !target_is_wasm(ira->codegen->zig_target) && !ira->codegen->have_pic && !ira->codegen->reported_bad_link_libc_error) { - ErrorMsg *msg = ir_add_error_node(ira, source_node, - buf_sprintf("dependency on dynamic library '%s' requires enabling Position Independent Code", - buf_ptr(lib_name))); - add_error_note(ira->codegen, msg, source_node, - buf_sprintf("fixed by `--library %s` or `-fPIC`", buf_ptr(lib_name))); - ira->codegen->reported_bad_link_libc_error = true; - } - - for (size_t i = 0; i < ira->codegen->forbidden_libs.length; i += 1) { - Buf *forbidden_lib_name = ira->codegen->forbidden_libs.at(i); - if (buf_eql_buf(lib_name, forbidden_lib_name)) { - ir_add_error_node(ira, source_node, - buf_sprintf("linking against forbidden library '%s'", buf_ptr(symbol_name))); - } - } - link_lib->symbols.append(symbol_name); } static IrInstGen *ir_error_dependency_loop(IrAnalyze *ira, IrInst* source_instr) { @@ -26355,13 +26329,6 @@ static IrInstGen *ir_analyze_instruction_type_name(IrAnalyze *ira, IrInstSrcType return result; } -static void ir_cimport_cache_paths(Buf *cache_dir, Buf *tmp_c_file_digest, Buf *out_zig_dir, Buf *out_zig_path) { - buf_resize(out_zig_dir, 0); - buf_resize(out_zig_path, 0); - buf_appendf(out_zig_dir, "%s" OS_SEP "o" OS_SEP "%s", - buf_ptr(cache_dir), buf_ptr(tmp_c_file_digest)); - buf_appendf(out_zig_path, "%s" OS_SEP "cimport.zig", buf_ptr(out_zig_dir)); -} static IrInstGen *ir_analyze_instruction_c_import(IrAnalyze *ira, IrInstSrcCImport *instruction) { Error err; AstNode *node = instruction->base.base.source_node; @@ -26393,145 +26360,7 @@ static IrInstGen *ir_analyze_instruction_c_import(IrAnalyze *ira, IrInstSrcCImpo cimport_pkg->package_table.put(buf_create_from_str("std"), ira->codegen->std_package); buf_init_from_buf(&cimport_pkg->pkg_path, namespace_name); - CacheHash *cache_hash; - if ((err = create_c_object_cache(ira->codegen, &cache_hash, false))) { - ir_add_error_node(ira, node, buf_sprintf("C import failed: unable to create cache: %s", err_str(err))); - return ira->codegen->invalid_inst_gen; - } - cache_buf(cache_hash, &cimport_scope->buf); - - // Set this because we're not adding any files before checking for a hit. - cache_hash->force_check_manifest = true; - - Buf tmp_c_file_digest = BUF_INIT; - buf_resize(&tmp_c_file_digest, 0); - if ((err = cache_hit(cache_hash, &tmp_c_file_digest))) { - if (err != ErrorInvalidFormat) { - ir_add_error_node(ira, node, buf_sprintf("C import failed: unable to check cache: %s", err_str(err))); - return ira->codegen->invalid_inst_gen; - } - } - ira->codegen->caches_to_release.append(cache_hash); - - Buf *out_zig_dir = buf_alloc(); - Buf *out_zig_path = buf_alloc(); - if (buf_len(&tmp_c_file_digest) == 0 || cache_hash->files.length == 0) { - // Cache Miss - Buf *tmp_c_file_dir = buf_sprintf("%s" OS_SEP "o" OS_SEP "%s", - buf_ptr(ira->codegen->cache_dir), buf_ptr(&cache_hash->b64_digest)); - Buf *resolve_paths[] = { - tmp_c_file_dir, - buf_create_from_str("cimport.h"), - }; - Buf tmp_c_file_path = os_path_resolve(resolve_paths, 2); - - if ((err = os_make_path(tmp_c_file_dir))) { - ir_add_error_node(ira, node, buf_sprintf("C import failed: unable to make dir: %s", err_str(err))); - return ira->codegen->invalid_inst_gen; - } - - if ((err = os_write_file(&tmp_c_file_path, &cimport_scope->buf))) { - ir_add_error_node(ira, node, buf_sprintf("C import failed: unable to write .h file: %s", err_str(err))); - return ira->codegen->invalid_inst_gen; - } - if (ira->codegen->verbose_cimport) { - fprintf(stderr, "@cImport source: %s\n", buf_ptr(&tmp_c_file_path)); - } - - Buf *tmp_dep_file = buf_sprintf("%s.d", buf_ptr(&tmp_c_file_path)); - - ZigList clang_argv = {0}; - - add_cc_args(ira->codegen, clang_argv, buf_ptr(tmp_dep_file), true, FileExtC); - - clang_argv.append(buf_ptr(&tmp_c_file_path)); - - if (ira->codegen->verbose_cc) { - fprintf(stderr, "clang"); - for (size_t i = 0; i < clang_argv.length; i += 1) { - fprintf(stderr, " %s", clang_argv.at(i)); - } - fprintf(stderr, "\n"); - } - - clang_argv.append(nullptr); // to make the [start...end] argument work - - Stage2ErrorMsg *errors_ptr; - size_t errors_len; - Stage2Ast *ast; - - const char *resources_path = buf_ptr(ira->codegen->zig_c_headers_dir); - - if ((err = stage2_translate_c(&ast, &errors_ptr, &errors_len, - &clang_argv.at(0), &clang_argv.last(), resources_path))) - { - if (err != ErrorCCompileErrors) { - ir_add_error_node(ira, node, buf_sprintf("C import failed: %s", err_str(err))); - return ira->codegen->invalid_inst_gen; - } - - ErrorMsg *parent_err_msg = ir_add_error_node(ira, node, buf_sprintf("C import failed")); - if (ira->codegen->libc_link_lib == nullptr) { - add_error_note(ira->codegen, parent_err_msg, node, - buf_sprintf("libc headers not available; compilation does not link against libc")); - } - for (size_t i = 0; i < errors_len; i += 1) { - Stage2ErrorMsg *clang_err = &errors_ptr[i]; - // Clang can emit "too many errors, stopping now", in which case `source` and `filename_ptr` are null - if (clang_err->source && clang_err->filename_ptr) { - ErrorMsg *err_msg = err_msg_create_with_offset( - clang_err->filename_ptr ? - buf_create_from_mem(clang_err->filename_ptr, clang_err->filename_len) : buf_alloc(), - clang_err->line, clang_err->column, clang_err->offset, clang_err->source, - buf_create_from_mem(clang_err->msg_ptr, clang_err->msg_len)); - err_msg_add_note(parent_err_msg, err_msg); - } - } - - return ira->codegen->invalid_inst_gen; - } - if (ira->codegen->verbose_cimport) { - fprintf(stderr, "@cImport .d file: %s\n", buf_ptr(tmp_dep_file)); - } - - if ((err = cache_add_dep_file(cache_hash, tmp_dep_file, false))) { - ir_add_error_node(ira, node, buf_sprintf("C import failed: unable to parse .d file: %s", err_str(err))); - return ira->codegen->invalid_inst_gen; - } - if ((err = cache_final(cache_hash, &tmp_c_file_digest))) { - ir_add_error_node(ira, node, buf_sprintf("C import failed: unable to finalize cache: %s", err_str(err))); - return ira->codegen->invalid_inst_gen; - } - - ir_cimport_cache_paths(ira->codegen->cache_dir, &tmp_c_file_digest, out_zig_dir, out_zig_path); - if ((err = os_make_path(out_zig_dir))) { - ir_add_error_node(ira, node, buf_sprintf("C import failed: unable to make output dir: %s", err_str(err))); - return ira->codegen->invalid_inst_gen; - } - FILE *out_file = fopen(buf_ptr(out_zig_path), "wb"); - if (out_file == nullptr) { - ir_add_error_node(ira, node, - buf_sprintf("C import failed: unable to open output file: %s", strerror(errno))); - return ira->codegen->invalid_inst_gen; - } - stage2_render_ast(ast, out_file); - if (fclose(out_file) != 0) { - ir_add_error_node(ira, node, - buf_sprintf("C import failed: unable to write to output file: %s", strerror(errno))); - return ira->codegen->invalid_inst_gen; - } - - if (ira->codegen->verbose_cimport) { - fprintf(stderr, "@cImport output: %s\n", buf_ptr(out_zig_path)); - } - - } else { - // Cache Hit - ir_cimport_cache_paths(ira->codegen->cache_dir, &tmp_c_file_digest, out_zig_dir, out_zig_path); - if (ira->codegen->verbose_cimport) { - fprintf(stderr, "@cImport cache hit: %s\n", buf_ptr(out_zig_path)); - } - } + Buf *out_zig_path = buf_create_from_str(stage2_cimport(&ira->codegen->stage1)); Buf *import_code = buf_alloc(); if ((err = file_fetch(ira->codegen, out_zig_path, import_code))) { diff --git a/src/link.cpp b/src/link.cpp deleted file mode 100644 index 3983b48b42..0000000000 --- a/src/link.cpp +++ /dev/null @@ -1,2985 +0,0 @@ -/* - * Copyright (c) 2015 Andrew Kelley - * - * This file is part of zig, which is MIT licensed. - * See http://opensource.org/licenses/MIT - */ - -#include "os.hpp" -#include "config.h" -#include "codegen.hpp" -#include "analyze.hpp" -#include "compiler.hpp" -#include "install_files.h" -#include "glibc.hpp" - -static const char *msvcrt_common_src[] = { - "misc" OS_SEP "_create_locale.c", - "misc" OS_SEP "_free_locale.c", - "misc" OS_SEP "onexit_table.c", - "misc" OS_SEP "register_tls_atexit.c", - "stdio" OS_SEP "acrt_iob_func.c", - "misc" OS_SEP "_configthreadlocale.c", - "misc" OS_SEP "_get_current_locale.c", - "misc" OS_SEP "invalid_parameter_handler.c", - "misc" OS_SEP "output_format.c", - "misc" OS_SEP "purecall.c", - "secapi" OS_SEP "_access_s.c", - "secapi" OS_SEP "_cgets_s.c", - "secapi" OS_SEP "_cgetws_s.c", - "secapi" OS_SEP "_chsize_s.c", - "secapi" OS_SEP "_controlfp_s.c", - "secapi" OS_SEP "_cprintf_s.c", - "secapi" OS_SEP "_cprintf_s_l.c", - "secapi" OS_SEP "_ctime32_s.c", - "secapi" OS_SEP "_ctime64_s.c", - "secapi" OS_SEP "_cwprintf_s.c", - "secapi" OS_SEP "_cwprintf_s_l.c", - "secapi" OS_SEP "_gmtime32_s.c", - "secapi" OS_SEP "_gmtime64_s.c", - "secapi" OS_SEP "_localtime32_s.c", - "secapi" OS_SEP "_localtime64_s.c", - "secapi" OS_SEP "_mktemp_s.c", - "secapi" OS_SEP "_sopen_s.c", - "secapi" OS_SEP "_strdate_s.c", - "secapi" OS_SEP "_strtime_s.c", - "secapi" OS_SEP "_umask_s.c", - "secapi" OS_SEP "_vcprintf_s.c", - "secapi" OS_SEP "_vcprintf_s_l.c", - "secapi" OS_SEP "_vcwprintf_s.c", - "secapi" OS_SEP "_vcwprintf_s_l.c", - "secapi" OS_SEP "_vscprintf_p.c", - "secapi" OS_SEP "_vscwprintf_p.c", - "secapi" OS_SEP "_vswprintf_p.c", - "secapi" OS_SEP "_waccess_s.c", - "secapi" OS_SEP "_wasctime_s.c", - "secapi" OS_SEP "_wctime32_s.c", - "secapi" OS_SEP "_wctime64_s.c", - "secapi" OS_SEP "_wstrtime_s.c", - "secapi" OS_SEP "_wmktemp_s.c", - "secapi" OS_SEP "_wstrdate_s.c", - "secapi" OS_SEP "asctime_s.c", - "secapi" OS_SEP "memcpy_s.c", - "secapi" OS_SEP "memmove_s.c", - "secapi" OS_SEP "rand_s.c", - "secapi" OS_SEP "sprintf_s.c", - "secapi" OS_SEP "strerror_s.c", - "secapi" OS_SEP "vsprintf_s.c", - "secapi" OS_SEP "wmemcpy_s.c", - "secapi" OS_SEP "wmemmove_s.c", - "stdio" OS_SEP "mingw_lock.c", -}; - -static const char *msvcrt_i386_src[] = { - "misc" OS_SEP "lc_locale_func.c", - "misc" OS_SEP "___mb_cur_max_func.c", -}; - -static const char *msvcrt_other_src[] = { - "misc" OS_SEP "__p___argv.c", - "misc" OS_SEP "__p__acmdln.c", - "misc" OS_SEP "__p__fmode.c", - "misc" OS_SEP "__p__wcmdln.c", -}; - -static const char *mingwex_generic_src[] = { - "complex" OS_SEP "_cabs.c", - "complex" OS_SEP "cabs.c", - "complex" OS_SEP "cabsf.c", - "complex" OS_SEP "cabsl.c", - "complex" OS_SEP "cacos.c", - "complex" OS_SEP "cacosf.c", - "complex" OS_SEP "cacosl.c", - "complex" OS_SEP "carg.c", - "complex" OS_SEP "cargf.c", - "complex" OS_SEP "cargl.c", - "complex" OS_SEP "casin.c", - "complex" OS_SEP "casinf.c", - "complex" OS_SEP "casinl.c", - "complex" OS_SEP "catan.c", - "complex" OS_SEP "catanf.c", - "complex" OS_SEP "catanl.c", - "complex" OS_SEP "ccos.c", - "complex" OS_SEP "ccosf.c", - "complex" OS_SEP "ccosl.c", - "complex" OS_SEP "cexp.c", - "complex" OS_SEP "cexpf.c", - "complex" OS_SEP "cexpl.c", - "complex" OS_SEP "cimag.c", - "complex" OS_SEP "cimagf.c", - "complex" OS_SEP "cimagl.c", - "complex" OS_SEP "clog.c", - "complex" OS_SEP "clog10.c", - "complex" OS_SEP "clog10f.c", - "complex" OS_SEP "clog10l.c", - "complex" OS_SEP "clogf.c", - "complex" OS_SEP "clogl.c", - "complex" OS_SEP "conj.c", - "complex" OS_SEP "conjf.c", - "complex" OS_SEP "conjl.c", - "complex" OS_SEP "cpow.c", - "complex" OS_SEP "cpowf.c", - "complex" OS_SEP "cpowl.c", - "complex" OS_SEP "cproj.c", - "complex" OS_SEP "cprojf.c", - "complex" OS_SEP "cprojl.c", - "complex" OS_SEP "creal.c", - "complex" OS_SEP "crealf.c", - "complex" OS_SEP "creall.c", - "complex" OS_SEP "csin.c", - "complex" OS_SEP "csinf.c", - "complex" OS_SEP "csinl.c", - "complex" OS_SEP "csqrt.c", - "complex" OS_SEP "csqrtf.c", - "complex" OS_SEP "csqrtl.c", - "complex" OS_SEP "ctan.c", - "complex" OS_SEP "ctanf.c", - "complex" OS_SEP "ctanl.c", - "crt" OS_SEP "dllentry.c", - "crt" OS_SEP "dllmain.c", - "gdtoa" OS_SEP "arithchk.c", - "gdtoa" OS_SEP "dmisc.c", - "gdtoa" OS_SEP "dtoa.c", - "gdtoa" OS_SEP "g__fmt.c", - "gdtoa" OS_SEP "g_dfmt.c", - "gdtoa" OS_SEP "g_ffmt.c", - "gdtoa" OS_SEP "g_xfmt.c", - "gdtoa" OS_SEP "gdtoa.c", - "gdtoa" OS_SEP "gethex.c", - "gdtoa" OS_SEP "gmisc.c", - "gdtoa" OS_SEP "hd_init.c", - "gdtoa" OS_SEP "hexnan.c", - "gdtoa" OS_SEP "misc.c", - "gdtoa" OS_SEP "qnan.c", - "gdtoa" OS_SEP "smisc.c", - "gdtoa" OS_SEP "strtodg.c", - "gdtoa" OS_SEP "strtodnrp.c", - "gdtoa" OS_SEP "strtof.c", - "gdtoa" OS_SEP "strtopx.c", - "gdtoa" OS_SEP "sum.c", - "gdtoa" OS_SEP "ulp.c", - "math" OS_SEP "abs64.c", - "math" OS_SEP "cbrt.c", - "math" OS_SEP "cbrtf.c", - "math" OS_SEP "cbrtl.c", - "math" OS_SEP "cephes_emath.c", - "math" OS_SEP "copysign.c", - "math" OS_SEP "copysignf.c", - "math" OS_SEP "coshf.c", - "math" OS_SEP "coshl.c", - "math" OS_SEP "erfl.c", - "math" OS_SEP "expf.c", - "math" OS_SEP "fabs.c", - "math" OS_SEP "fabsf.c", - "math" OS_SEP "fabsl.c", - "math" OS_SEP "fdim.c", - "math" OS_SEP "fdimf.c", - "math" OS_SEP "fdiml.c", - "math" OS_SEP "fma.c", - "math" OS_SEP "fmaf.c", - "math" OS_SEP "fmal.c", - "math" OS_SEP "fmax.c", - "math" OS_SEP "fmaxf.c", - "math" OS_SEP "fmaxl.c", - "math" OS_SEP "fmin.c", - "math" OS_SEP "fminf.c", - "math" OS_SEP "fminl.c", - "math" OS_SEP "fp_consts.c", - "math" OS_SEP "fp_constsf.c", - "math" OS_SEP "fp_constsl.c", - "math" OS_SEP "fpclassify.c", - "math" OS_SEP "fpclassifyf.c", - "math" OS_SEP "fpclassifyl.c", - "math" OS_SEP "frexpf.c", - "math" OS_SEP "hypot.c", - "math" OS_SEP "hypotf.c", - "math" OS_SEP "hypotl.c", - "math" OS_SEP "isnan.c", - "math" OS_SEP "isnanf.c", - "math" OS_SEP "isnanl.c", - "math" OS_SEP "ldexpf.c", - "math" OS_SEP "lgamma.c", - "math" OS_SEP "lgammaf.c", - "math" OS_SEP "lgammal.c", - "math" OS_SEP "llrint.c", - "math" OS_SEP "llrintf.c", - "math" OS_SEP "llrintl.c", - "math" OS_SEP "llround.c", - "math" OS_SEP "llroundf.c", - "math" OS_SEP "llroundl.c", - "math" OS_SEP "log10f.c", - "math" OS_SEP "logf.c", - "math" OS_SEP "lrint.c", - "math" OS_SEP "lrintf.c", - "math" OS_SEP "lrintl.c", - "math" OS_SEP "lround.c", - "math" OS_SEP "lroundf.c", - "math" OS_SEP "lroundl.c", - "math" OS_SEP "modf.c", - "math" OS_SEP "modff.c", - "math" OS_SEP "modfl.c", - "math" OS_SEP "nextafterf.c", - "math" OS_SEP "nextafterl.c", - "math" OS_SEP "nexttoward.c", - "math" OS_SEP "nexttowardf.c", - "math" OS_SEP "powf.c", - "math" OS_SEP "powi.c", - "math" OS_SEP "powif.c", - "math" OS_SEP "powil.c", - "math" OS_SEP "rint.c", - "math" OS_SEP "rintf.c", - "math" OS_SEP "rintl.c", - "math" OS_SEP "round.c", - "math" OS_SEP "roundf.c", - "math" OS_SEP "roundl.c", - "math" OS_SEP "s_erf.c", - "math" OS_SEP "sf_erf.c", - "math" OS_SEP "signbit.c", - "math" OS_SEP "signbitf.c", - "math" OS_SEP "signbitl.c", - "math" OS_SEP "signgam.c", - "math" OS_SEP "sinhf.c", - "math" OS_SEP "sinhl.c", - "math" OS_SEP "sqrt.c", - "math" OS_SEP "sqrtf.c", - "math" OS_SEP "sqrtl.c", - "math" OS_SEP "tanhf.c", - "math" OS_SEP "tanhl.c", - "math" OS_SEP "tgamma.c", - "math" OS_SEP "tgammaf.c", - "math" OS_SEP "tgammal.c", - "math" OS_SEP "truncl.c", - "misc" OS_SEP "alarm.c", - "misc" OS_SEP "basename.c", - "misc" OS_SEP "btowc.c", - "misc" OS_SEP "delay-f.c", - "misc" OS_SEP "delay-n.c", - "misc" OS_SEP "delayimp.c", - "misc" OS_SEP "dirent.c", - "misc" OS_SEP "dirname.c", - "misc" OS_SEP "feclearexcept.c", - "misc" OS_SEP "fegetenv.c", - "misc" OS_SEP "fegetexceptflag.c", - "misc" OS_SEP "fegetround.c", - "misc" OS_SEP "feholdexcept.c", - "misc" OS_SEP "feraiseexcept.c", - "misc" OS_SEP "fesetenv.c", - "misc" OS_SEP "fesetexceptflag.c", - "misc" OS_SEP "fesetround.c", - "misc" OS_SEP "fetestexcept.c", - "misc" OS_SEP "feupdateenv.c", - "misc" OS_SEP "ftruncate.c", - "misc" OS_SEP "ftw.c", - "misc" OS_SEP "ftw64.c", - "misc" OS_SEP "fwide.c", - "misc" OS_SEP "getlogin.c", - "misc" OS_SEP "getopt.c", - "misc" OS_SEP "gettimeofday.c", - "misc" OS_SEP "imaxabs.c", - "misc" OS_SEP "imaxdiv.c", - "misc" OS_SEP "isblank.c", - "misc" OS_SEP "iswblank.c", - "misc" OS_SEP "mbrtowc.c", - "misc" OS_SEP "mbsinit.c", - "misc" OS_SEP "mempcpy.c", - "misc" OS_SEP "mingw-aligned-malloc.c", - "misc" OS_SEP "mingw-fseek.c", - "misc" OS_SEP "mingw_getsp.S", - "misc" OS_SEP "mingw_matherr.c", - "misc" OS_SEP "mingw_mbwc_convert.c", - "misc" OS_SEP "mingw_usleep.c", - "misc" OS_SEP "mingw_wcstod.c", - "misc" OS_SEP "mingw_wcstof.c", - "misc" OS_SEP "mingw_wcstold.c", - "misc" OS_SEP "mkstemp.c", - "misc" OS_SEP "seterrno.c", - "misc" OS_SEP "sleep.c", - "misc" OS_SEP "strnlen.c", - "misc" OS_SEP "strsafe.c", - "misc" OS_SEP "strtoimax.c", - "misc" OS_SEP "strtold.c", - "misc" OS_SEP "strtoumax.c", - "misc" OS_SEP "tdelete.c", - "misc" OS_SEP "tfind.c", - "misc" OS_SEP "tsearch.c", - "misc" OS_SEP "twalk.c", - "misc" OS_SEP "uchar_c16rtomb.c", - "misc" OS_SEP "uchar_c32rtomb.c", - "misc" OS_SEP "uchar_mbrtoc16.c", - "misc" OS_SEP "uchar_mbrtoc32.c", - "misc" OS_SEP "wassert.c", - "misc" OS_SEP "wcrtomb.c", - "misc" OS_SEP "wcsnlen.c", - "misc" OS_SEP "wcstof.c", - "misc" OS_SEP "wcstoimax.c", - "misc" OS_SEP "wcstold.c", - "misc" OS_SEP "wcstoumax.c", - "misc" OS_SEP "wctob.c", - "misc" OS_SEP "wctrans.c", - "misc" OS_SEP "wctype.c", - "misc" OS_SEP "wdirent.c", - "misc" OS_SEP "winbs_uint64.c", - "misc" OS_SEP "winbs_ulong.c", - "misc" OS_SEP "winbs_ushort.c", - "misc" OS_SEP "wmemchr.c", - "misc" OS_SEP "wmemcmp.c", - "misc" OS_SEP "wmemcpy.c", - "misc" OS_SEP "wmemmove.c", - "misc" OS_SEP "wmempcpy.c", - "misc" OS_SEP "wmemset.c", - "stdio" OS_SEP "_Exit.c", - "stdio" OS_SEP "_findfirst64i32.c", - "stdio" OS_SEP "_findnext64i32.c", - "stdio" OS_SEP "_fstat.c", - "stdio" OS_SEP "_fstat64i32.c", - "stdio" OS_SEP "_ftime.c", - "stdio" OS_SEP "_getc_nolock.c", - "stdio" OS_SEP "_getwc_nolock.c", - "stdio" OS_SEP "_putc_nolock.c", - "stdio" OS_SEP "_putwc_nolock.c", - "stdio" OS_SEP "_stat.c", - "stdio" OS_SEP "_stat64i32.c", - "stdio" OS_SEP "_wfindfirst64i32.c", - "stdio" OS_SEP "_wfindnext64i32.c", - "stdio" OS_SEP "_wstat.c", - "stdio" OS_SEP "_wstat64i32.c", - "stdio" OS_SEP "asprintf.c", - "stdio" OS_SEP "atoll.c", - "stdio" OS_SEP "fgetpos64.c", - "stdio" OS_SEP "fopen64.c", - "stdio" OS_SEP "fseeko32.c", - "stdio" OS_SEP "fseeko64.c", - "stdio" OS_SEP "fsetpos64.c", - "stdio" OS_SEP "ftello.c", - "stdio" OS_SEP "ftello64.c", - "stdio" OS_SEP "ftruncate64.c", - "stdio" OS_SEP "lltoa.c", - "stdio" OS_SEP "lltow.c", - "stdio" OS_SEP "lseek64.c", - "stdio" OS_SEP "mingw_asprintf.c", - "stdio" OS_SEP "mingw_fprintf.c", - "stdio" OS_SEP "mingw_fprintfw.c", - "stdio" OS_SEP "mingw_fscanf.c", - "stdio" OS_SEP "mingw_fwscanf.c", - "stdio" OS_SEP "mingw_pformat.c", - "stdio" OS_SEP "mingw_pformatw.c", - "stdio" OS_SEP "mingw_printf.c", - "stdio" OS_SEP "mingw_printfw.c", - "stdio" OS_SEP "mingw_scanf.c", - "stdio" OS_SEP "mingw_snprintf.c", - "stdio" OS_SEP "mingw_snprintfw.c", - "stdio" OS_SEP "mingw_sprintf.c", - "stdio" OS_SEP "mingw_sprintfw.c", - "stdio" OS_SEP "mingw_sscanf.c", - "stdio" OS_SEP "mingw_swscanf.c", - "stdio" OS_SEP "mingw_vasprintf.c", - "stdio" OS_SEP "mingw_vfprintf.c", - "stdio" OS_SEP "mingw_vfprintfw.c", - "stdio" OS_SEP "mingw_vfscanf.c", - "stdio" OS_SEP "mingw_vprintf.c", - "stdio" OS_SEP "mingw_vprintfw.c", - "stdio" OS_SEP "mingw_vsnprintf.c", - "stdio" OS_SEP "mingw_vsnprintfw.c", - "stdio" OS_SEP "mingw_vsprintf.c", - "stdio" OS_SEP "mingw_vsprintfw.c", - "stdio" OS_SEP "mingw_wscanf.c", - "stdio" OS_SEP "mingw_wvfscanf.c", - "stdio" OS_SEP "scanf.S", - "stdio" OS_SEP "snprintf.c", - "stdio" OS_SEP "snwprintf.c", - "stdio" OS_SEP "strtof.c", - "stdio" OS_SEP "strtok_r.c", - "stdio" OS_SEP "truncate.c", - "stdio" OS_SEP "ulltoa.c", - "stdio" OS_SEP "ulltow.c", - "stdio" OS_SEP "vasprintf.c", - "stdio" OS_SEP "vfscanf.c", - "stdio" OS_SEP "vfscanf2.S", - "stdio" OS_SEP "vfwscanf.c", - "stdio" OS_SEP "vfwscanf2.S", - "stdio" OS_SEP "vscanf.c", - "stdio" OS_SEP "vscanf2.S", - "stdio" OS_SEP "vsnprintf.c", - "stdio" OS_SEP "vsnwprintf.c", - "stdio" OS_SEP "vsscanf.c", - "stdio" OS_SEP "vsscanf2.S", - "stdio" OS_SEP "vswscanf.c", - "stdio" OS_SEP "vswscanf2.S", - "stdio" OS_SEP "vwscanf.c", - "stdio" OS_SEP "vwscanf2.S", - "stdio" OS_SEP "wtoll.c", -}; - -static const char *mingwex_x86_src[] = { - "math" OS_SEP "x86" OS_SEP "acosf.c", - "math" OS_SEP "x86" OS_SEP "acosh.c", - "math" OS_SEP "x86" OS_SEP "acoshf.c", - "math" OS_SEP "x86" OS_SEP "acoshl.c", - "math" OS_SEP "x86" OS_SEP "acosl.c", - "math" OS_SEP "x86" OS_SEP "asinf.c", - "math" OS_SEP "x86" OS_SEP "asinh.c", - "math" OS_SEP "x86" OS_SEP "asinhf.c", - "math" OS_SEP "x86" OS_SEP "asinhl.c", - "math" OS_SEP "x86" OS_SEP "asinl.c", - "math" OS_SEP "x86" OS_SEP "atan2.c", - "math" OS_SEP "x86" OS_SEP "atan2f.c", - "math" OS_SEP "x86" OS_SEP "atan2l.c", - "math" OS_SEP "x86" OS_SEP "atanf.c", - "math" OS_SEP "x86" OS_SEP "atanh.c", - "math" OS_SEP "x86" OS_SEP "atanhf.c", - "math" OS_SEP "x86" OS_SEP "atanhl.c", - "math" OS_SEP "x86" OS_SEP "atanl.c", - "math" OS_SEP "x86" OS_SEP "ceilf.S", - "math" OS_SEP "x86" OS_SEP "ceill.S", - "math" OS_SEP "x86" OS_SEP "ceil.S", - "math" OS_SEP "x86" OS_SEP "_chgsignl.S", - "math" OS_SEP "x86" OS_SEP "copysignl.S", - "math" OS_SEP "x86" OS_SEP "cos.c", - "math" OS_SEP "x86" OS_SEP "cosf.c", - "math" OS_SEP "x86" OS_SEP "cosl.c", - "math" OS_SEP "x86" OS_SEP "cosl_internal.S", - "math" OS_SEP "x86" OS_SEP "cossin.c", - "math" OS_SEP "x86" OS_SEP "exp2f.S", - "math" OS_SEP "x86" OS_SEP "exp2l.S", - "math" OS_SEP "x86" OS_SEP "exp2.S", - "math" OS_SEP "x86" OS_SEP "exp.c", - "math" OS_SEP "x86" OS_SEP "expl.c", - "math" OS_SEP "x86" OS_SEP "expm1.c", - "math" OS_SEP "x86" OS_SEP "expm1f.c", - "math" OS_SEP "x86" OS_SEP "expm1l.c", - "math" OS_SEP "x86" OS_SEP "floorf.S", - "math" OS_SEP "x86" OS_SEP "floorl.S", - "math" OS_SEP "x86" OS_SEP "floor.S", - "math" OS_SEP "x86" OS_SEP "fmod.c", - "math" OS_SEP "x86" OS_SEP "fmodf.c", - "math" OS_SEP "x86" OS_SEP "fmodl.c", - "math" OS_SEP "x86" OS_SEP "fucom.c", - "math" OS_SEP "x86" OS_SEP "ilogbf.S", - "math" OS_SEP "x86" OS_SEP "ilogbl.S", - "math" OS_SEP "x86" OS_SEP "ilogb.S", - "math" OS_SEP "x86" OS_SEP "internal_logl.S", - "math" OS_SEP "x86" OS_SEP "ldexp.c", - "math" OS_SEP "x86" OS_SEP "ldexpl.c", - "math" OS_SEP "x86" OS_SEP "log10l.S", - "math" OS_SEP "x86" OS_SEP "log1pf.S", - "math" OS_SEP "x86" OS_SEP "log1pl.S", - "math" OS_SEP "x86" OS_SEP "log1p.S", - "math" OS_SEP "x86" OS_SEP "log2f.S", - "math" OS_SEP "x86" OS_SEP "log2l.S", - "math" OS_SEP "x86" OS_SEP "log2.S", - "math" OS_SEP "x86" OS_SEP "logb.c", - "math" OS_SEP "x86" OS_SEP "logbf.c", - "math" OS_SEP "x86" OS_SEP "logbl.c", - "math" OS_SEP "x86" OS_SEP "log.c", - "math" OS_SEP "x86" OS_SEP "logl.c", - "math" OS_SEP "x86" OS_SEP "nearbyintf.S", - "math" OS_SEP "x86" OS_SEP "nearbyintl.S", - "math" OS_SEP "x86" OS_SEP "nearbyint.S", - "math" OS_SEP "x86" OS_SEP "pow.c", - "math" OS_SEP "x86" OS_SEP "powl.c", - "math" OS_SEP "x86" OS_SEP "remainderf.S", - "math" OS_SEP "x86" OS_SEP "remainderl.S", - "math" OS_SEP "x86" OS_SEP "remainder.S", - "math" OS_SEP "x86" OS_SEP "remquof.S", - "math" OS_SEP "x86" OS_SEP "remquol.S", - "math" OS_SEP "x86" OS_SEP "remquo.S", - "math" OS_SEP "x86" OS_SEP "scalbnf.S", - "math" OS_SEP "x86" OS_SEP "scalbnl.S", - "math" OS_SEP "x86" OS_SEP "scalbn.S", - "math" OS_SEP "x86" OS_SEP "sin.c", - "math" OS_SEP "x86" OS_SEP "sinf.c", - "math" OS_SEP "x86" OS_SEP "sinl.c", - "math" OS_SEP "x86" OS_SEP "sinl_internal.S", - "math" OS_SEP "x86" OS_SEP "tanf.c", - "math" OS_SEP "x86" OS_SEP "tanl.S", - "math" OS_SEP "x86" OS_SEP "truncf.S", - "math" OS_SEP "x86" OS_SEP "trunc.S", -}; - -static const char *mingwex_arm32_src[] = { - "math" OS_SEP "arm" OS_SEP "_chgsignl.S", - "math" OS_SEP "arm" OS_SEP "exp2.c", - "math" OS_SEP "arm" OS_SEP "nearbyint.S", - "math" OS_SEP "arm" OS_SEP "nearbyintf.S", - "math" OS_SEP "arm" OS_SEP "nearbyintl.S", - "math" OS_SEP "arm" OS_SEP "trunc.S", - "math" OS_SEP "arm" OS_SEP "truncf.S", -}; - -static const char *mingwex_arm64_src[] = { - "math" OS_SEP "arm64" OS_SEP "_chgsignl.S", - "math" OS_SEP "arm64" OS_SEP "exp2f.S", - "math" OS_SEP "arm64" OS_SEP "exp2.S", - "math" OS_SEP "arm64" OS_SEP "nearbyintf.S", - "math" OS_SEP "arm64" OS_SEP "nearbyintl.S", - "math" OS_SEP "arm64" OS_SEP "nearbyint.S", - "math" OS_SEP "arm64" OS_SEP "truncf.S", - "math" OS_SEP "arm64" OS_SEP "trunc.S", -}; - -static const char *mingw_uuid_src[] = { - "libsrc/ativscp-uuid.c", - "libsrc/atsmedia-uuid.c", - "libsrc/bth-uuid.c", - "libsrc/cguid-uuid.c", - "libsrc/comcat-uuid.c", - "libsrc/devguid.c", - "libsrc/docobj-uuid.c", - "libsrc/dxva-uuid.c", - "libsrc/exdisp-uuid.c", - "libsrc/extras-uuid.c", - "libsrc/fwp-uuid.c", - "libsrc/guid_nul.c", - "libsrc/hlguids-uuid.c", - "libsrc/hlink-uuid.c", - "libsrc/mlang-uuid.c", - "libsrc/msctf-uuid.c", - "libsrc/mshtmhst-uuid.c", - "libsrc/mshtml-uuid.c", - "libsrc/msxml-uuid.c", - "libsrc/netcon-uuid.c", - "libsrc/ntddkbd-uuid.c", - "libsrc/ntddmou-uuid.c", - "libsrc/ntddpar-uuid.c", - "libsrc/ntddscsi-uuid.c", - "libsrc/ntddser-uuid.c", - "libsrc/ntddstor-uuid.c", - "libsrc/ntddvdeo-uuid.c", - "libsrc/oaidl-uuid.c", - "libsrc/objidl-uuid.c", - "libsrc/objsafe-uuid.c", - "libsrc/ocidl-uuid.c", - "libsrc/oleacc-uuid.c", - "libsrc/olectlid-uuid.c", - "libsrc/oleidl-uuid.c", - "libsrc/power-uuid.c", - "libsrc/powrprof-uuid.c", - "libsrc/uianimation-uuid.c", - "libsrc/usbcamdi-uuid.c", - "libsrc/usbiodef-uuid.c", - "libsrc/uuid.c", - "libsrc/vds-uuid.c", - "libsrc/virtdisk-uuid.c", - "libsrc/wia-uuid.c", -}; - -struct MinGWDef { - const char *name; - bool always_link; -}; -static const MinGWDef mingw_def_list[] = { - {"advapi32",true}, - {"bcrypt", false}, - {"comctl32",false}, - {"comdlg32",false}, - {"crypt32", false}, - {"cryptnet",false}, - {"gdi32", false}, - {"imm32", false}, - {"kernel32",true}, - {"lz32", false}, - {"mpr", false}, - {"msvcrt", true}, - {"mswsock", false}, - {"ncrypt", false}, - {"netapi32",false}, - {"ntdll", true}, - {"ole32", false}, - {"oleaut32",false}, - {"opengl32",false}, - {"psapi", false}, - {"rpcns4", false}, - {"rpcrt4", false}, - {"scarddlg",false}, - {"setupapi",false}, - {"shell32", true}, - {"shlwapi", false}, - {"urlmon", false}, - {"user32", true}, - {"version", false}, - {"winmm", false}, - {"winscard",false}, - {"winspool",false}, - {"wintrust",false}, - {"ws2_32", false}, -}; - -struct LinkJob { - CodeGen *codegen; - ZigList args; - bool link_in_crt; - HashMap rpath_table; - Stage2ProgressNode *build_dep_prog_node; -}; - -static const char *build_libc_object(CodeGen *parent_gen, const char *name, CFile *c_file, - Stage2ProgressNode *progress_node) -{ - CodeGen *child_gen = create_child_codegen(parent_gen, nullptr, OutTypeObj, nullptr, name, progress_node); - child_gen->root_out_name = buf_create_from_str(name); - ZigList c_source_files = {0}; - c_source_files.append(c_file); - child_gen->c_source_files = c_source_files; - codegen_build_and_link(child_gen); - return buf_ptr(&child_gen->bin_file_output_path); -} - -static const char *path_from_zig_lib(CodeGen *g, const char *dir, const char *subpath) { - Buf *dir1 = buf_alloc(); - os_path_join(g->zig_lib_dir, buf_create_from_str(dir), dir1); - Buf *result = buf_alloc(); - os_path_join(dir1, buf_create_from_str(subpath), result); - return buf_ptr(result); -} - -static const char *path_from_libc(CodeGen *g, const char *subpath) { - return path_from_zig_lib(g, "libc", subpath); -} - -static const char *path_from_libunwind(CodeGen *g, const char *subpath) { - return path_from_zig_lib(g, "libunwind", subpath); -} - -static const char *build_libunwind(CodeGen *parent, Stage2ProgressNode *progress_node) { - CodeGen *child_gen = create_child_codegen(parent, nullptr, OutTypeLib, nullptr, "unwind", progress_node); - LinkLib *new_link_lib = codegen_add_link_lib(child_gen, buf_create_from_str("c")); - new_link_lib->provided_explicitly = false; - enum SrcKind { - SrcCpp, - SrcC, - SrcAsm, - }; - static const struct { - const char *path; - SrcKind kind; - } unwind_src[] = { - {"src" OS_SEP "libunwind.cpp", SrcCpp}, - {"src" OS_SEP "Unwind-EHABI.cpp", SrcCpp}, - {"src" OS_SEP "Unwind-seh.cpp", SrcCpp}, - - {"src" OS_SEP "UnwindLevel1.c", SrcC}, - {"src" OS_SEP "UnwindLevel1-gcc-ext.c", SrcC}, - {"src" OS_SEP "Unwind-sjlj.c", SrcC}, - - {"src" OS_SEP "UnwindRegistersRestore.S", SrcAsm}, - {"src" OS_SEP "UnwindRegistersSave.S", SrcAsm}, - }; - ZigList c_source_files = {0}; - for (size_t i = 0; i < array_length(unwind_src); i += 1) { - CFile *c_file = heap::c_allocator.create(); - c_file->source_path = path_from_libunwind(parent, unwind_src[i].path); - switch (unwind_src[i].kind) { - case SrcC: - c_file->args.append("-std=c99"); - break; - case SrcCpp: - c_file->args.append("-fno-rtti"); - c_file->args.append("-I"); - c_file->args.append(path_from_zig_lib(parent, "libcxx", "include")); - break; - case SrcAsm: - break; - } - c_file->args.append("-I"); - c_file->args.append(path_from_libunwind(parent, "include")); - if (target_supports_fpic(parent->zig_target)) { - c_file->args.append("-fPIC"); - } - c_file->args.append("-D_LIBUNWIND_DISABLE_VISIBILITY_ANNOTATIONS"); - c_file->args.append("-Wa,--noexecstack"); - - // This is intentionally always defined because the macro definition means, should it only - // build for the target specified by compiler defines. Since we pass -target the compiler - // defines will be correct. - c_file->args.append("-D_LIBUNWIND_IS_NATIVE_ONLY"); - - if (parent->build_mode == BuildModeDebug) { - c_file->args.append("-D_DEBUG"); - } - if (parent->is_single_threaded) { - c_file->args.append("-D_LIBUNWIND_HAS_NO_THREADS"); - } - c_file->args.append("-Wno-bitwise-conditional-parentheses"); - c_source_files.append(c_file); - } - child_gen->c_source_files = c_source_files; - codegen_build_and_link(child_gen); - return buf_ptr(&child_gen->bin_file_output_path); -} - -static void mingw_add_cc_args(CodeGen *parent, CFile *c_file) { - c_file->args.append("-DHAVE_CONFIG_H"); - - c_file->args.append("-I"); - c_file->args.append(buf_ptr(buf_sprintf("%s" OS_SEP "libc" OS_SEP "mingw" OS_SEP "include", - buf_ptr(parent->zig_lib_dir)))); - - c_file->args.append("-isystem"); - c_file->args.append(buf_ptr(buf_sprintf("%s" OS_SEP "libc" OS_SEP "include" OS_SEP "any-windows-any", - buf_ptr(parent->zig_lib_dir)))); - - if (target_is_arm(parent->zig_target) && - target_arch_pointer_bit_width(parent->zig_target->arch) == 32) - { - c_file->args.append("-mfpu=vfp"); - } - - c_file->args.append("-std=gnu11"); - c_file->args.append("-D_CRTBLD"); - c_file->args.append("-D_WIN32_WINNT=0x0f00"); - c_file->args.append("-D__MSVCRT_VERSION__=0x700"); -} - -static void glibc_add_include_dirs_arch(CFile *c_file, ZigLLVM_ArchType arch, const char *nptl, const char *dir) { - bool is_x86 = arch == ZigLLVM_x86 || arch == ZigLLVM_x86_64; - bool is_aarch64 = arch == ZigLLVM_aarch64 || arch == ZigLLVM_aarch64_be; - bool is_mips = arch == ZigLLVM_mips || arch == ZigLLVM_mipsel || - arch == ZigLLVM_mips64el || arch == ZigLLVM_mips64; - bool is_arm = arch == ZigLLVM_arm || arch == ZigLLVM_armeb; - bool is_ppc = arch == ZigLLVM_ppc || arch == ZigLLVM_ppc64 || arch == ZigLLVM_ppc64le; - bool is_riscv = arch == ZigLLVM_riscv32 || arch == ZigLLVM_riscv64; - bool is_sparc = arch == ZigLLVM_sparc || arch == ZigLLVM_sparcel || arch == ZigLLVM_sparcv9; - bool is_64 = target_arch_pointer_bit_width(arch) == 64; - - if (is_x86) { - if (arch == ZigLLVM_x86_64) { - if (nptl != nullptr) { - c_file->args.append("-I"); - c_file->args.append(buf_ptr(buf_sprintf("%s" OS_SEP "x86_64" OS_SEP "%s", dir, nptl))); - } else { - c_file->args.append("-I"); - c_file->args.append(buf_ptr(buf_sprintf("%s" OS_SEP "x86_64", dir))); - } - } else if (arch == ZigLLVM_x86) { - if (nptl != nullptr) { - c_file->args.append("-I"); - c_file->args.append(buf_ptr(buf_sprintf("%s" OS_SEP "i386" OS_SEP "%s", dir, nptl))); - } else { - c_file->args.append("-I"); - c_file->args.append(buf_ptr(buf_sprintf("%s" OS_SEP "i386", dir))); - } - } - if (nptl != nullptr) { - c_file->args.append("-I"); - c_file->args.append(buf_ptr(buf_sprintf("%s" OS_SEP "x86" OS_SEP "%s", dir, nptl))); - } else { - c_file->args.append("-I"); - c_file->args.append(buf_ptr(buf_sprintf("%s" OS_SEP "x86", dir))); - } - } else if (is_arm) { - if (nptl != nullptr) { - c_file->args.append("-I"); - c_file->args.append(buf_ptr(buf_sprintf("%s" OS_SEP "arm" OS_SEP "%s", dir, nptl))); - } else { - c_file->args.append("-I"); - c_file->args.append(buf_ptr(buf_sprintf("%s" OS_SEP "arm", dir))); - } - } else if (is_mips) { - if (nptl != nullptr) { - c_file->args.append("-I"); - c_file->args.append(buf_ptr(buf_sprintf("%s" OS_SEP "mips" OS_SEP "%s", dir, nptl))); - } else { - if (is_64) { - c_file->args.append("-I"); - c_file->args.append(buf_ptr(buf_sprintf("%s" OS_SEP "mips" OS_SEP "mips64", dir))); - } else { - c_file->args.append("-I"); - c_file->args.append(buf_ptr(buf_sprintf("%s" OS_SEP "mips" OS_SEP "mips32", dir))); - } - c_file->args.append("-I"); - c_file->args.append(buf_ptr(buf_sprintf("%s" OS_SEP "mips", dir))); - } - } else if (is_sparc) { - if (nptl != nullptr) { - c_file->args.append("-I"); - c_file->args.append(buf_ptr(buf_sprintf("%s" OS_SEP "sparc" OS_SEP "%s", dir, nptl))); - } else { - if (is_64) { - c_file->args.append("-I"); - c_file->args.append(buf_ptr(buf_sprintf("%s" OS_SEP "sparc" OS_SEP "sparc64", dir))); - } else { - c_file->args.append("-I"); - c_file->args.append(buf_ptr(buf_sprintf("%s" OS_SEP "sparc" OS_SEP "sparc32", dir))); - } - c_file->args.append("-I"); - c_file->args.append(buf_ptr(buf_sprintf("%s" OS_SEP "sparc", dir))); - } - } else if (is_aarch64) { - if (nptl != nullptr) { - c_file->args.append("-I"); - c_file->args.append(buf_ptr(buf_sprintf("%s" OS_SEP "aarch64" OS_SEP "%s", dir, nptl))); - } else { - c_file->args.append("-I"); - c_file->args.append(buf_ptr(buf_sprintf("%s" OS_SEP "aarch64", dir))); - } - } else if (is_ppc) { - if (nptl != nullptr) { - c_file->args.append("-I"); - c_file->args.append(buf_ptr(buf_sprintf("%s" OS_SEP "powerpc" OS_SEP "%s", dir, nptl))); - } else { - if (is_64) { - c_file->args.append("-I"); - c_file->args.append(buf_ptr(buf_sprintf("%s" OS_SEP "powerpc" OS_SEP "powerpc64", dir))); - } else { - c_file->args.append("-I"); - c_file->args.append(buf_ptr(buf_sprintf("%s" OS_SEP "powerpc" OS_SEP "powerpc32", dir))); - } - c_file->args.append("-I"); - c_file->args.append(buf_ptr(buf_sprintf("%s" OS_SEP "powerpc", dir))); - } - } else if (is_riscv) { - if (nptl != nullptr) { - c_file->args.append("-I"); - c_file->args.append(buf_ptr(buf_sprintf("%s" OS_SEP "riscv" OS_SEP "%s", dir, nptl))); - } else { - c_file->args.append("-I"); - c_file->args.append(buf_ptr(buf_sprintf("%s" OS_SEP "riscv", dir))); - } - } -} - -static void glibc_add_include_dirs(CodeGen *parent, CFile *c_file) { - ZigLLVM_ArchType arch = parent->zig_target->arch; - const char *nptl = (parent->zig_target->os == OsLinux) ? "nptl" : "htl"; - const char *glibc = path_from_libc(parent, "glibc"); - - c_file->args.append("-I"); - c_file->args.append(buf_ptr(buf_sprintf("%s" OS_SEP "include", glibc))); - - if (parent->zig_target->os == OsLinux) { - glibc_add_include_dirs_arch(c_file, arch, nullptr, - path_from_libc(parent, "glibc" OS_SEP "sysdeps" OS_SEP "unix" OS_SEP "sysv" OS_SEP "linux")); - } - - if (nptl != nullptr) { - glibc_add_include_dirs_arch(c_file, arch, nptl, path_from_libc(parent, "glibc" OS_SEP "sysdeps")); - } - - if (parent->zig_target->os == OsLinux) { - c_file->args.append("-I"); - c_file->args.append(path_from_libc(parent, "glibc" OS_SEP "sysdeps" OS_SEP - "unix" OS_SEP "sysv" OS_SEP "linux" OS_SEP "generic")); - - c_file->args.append("-I"); - c_file->args.append(path_from_libc(parent, "glibc" OS_SEP "sysdeps" OS_SEP - "unix" OS_SEP "sysv" OS_SEP "linux" OS_SEP "include")); - c_file->args.append("-I"); - c_file->args.append(path_from_libc(parent, "glibc" OS_SEP "sysdeps" OS_SEP - "unix" OS_SEP "sysv" OS_SEP "linux")); - } - if (nptl != nullptr) { - c_file->args.append("-I"); - c_file->args.append(buf_ptr(buf_sprintf("%s" OS_SEP "sysdeps" OS_SEP "%s", glibc, nptl))); - } - - c_file->args.append("-I"); - c_file->args.append(path_from_libc(parent, "glibc" OS_SEP "sysdeps" OS_SEP "pthread")); - - c_file->args.append("-I"); - c_file->args.append(path_from_libc(parent, "glibc" OS_SEP "sysdeps" OS_SEP "unix" OS_SEP "sysv")); - - glibc_add_include_dirs_arch(c_file, arch, nullptr, - path_from_libc(parent, "glibc" OS_SEP "sysdeps" OS_SEP "unix")); - - c_file->args.append("-I"); - c_file->args.append(path_from_libc(parent, "glibc" OS_SEP "sysdeps" OS_SEP "unix")); - - glibc_add_include_dirs_arch(c_file, arch, nullptr, path_from_libc(parent, "glibc" OS_SEP "sysdeps")); - - c_file->args.append("-I"); - c_file->args.append(path_from_libc(parent, "glibc" OS_SEP "sysdeps" OS_SEP "generic")); - - c_file->args.append("-I"); - c_file->args.append(path_from_libc(parent, "glibc")); - - c_file->args.append("-I"); - c_file->args.append(buf_ptr(buf_sprintf("%s" OS_SEP "libc" OS_SEP "include" OS_SEP "%s-%s-%s", - buf_ptr(parent->zig_lib_dir), target_arch_name(parent->zig_target->arch), - target_os_name(parent->zig_target->os), target_abi_name(parent->zig_target->abi)))); - - c_file->args.append("-I"); - c_file->args.append(path_from_libc(parent, "include" OS_SEP "generic-glibc")); - - c_file->args.append("-I"); - c_file->args.append(buf_ptr(buf_sprintf("%s" OS_SEP "libc" OS_SEP "include" OS_SEP "%s-linux-any", - buf_ptr(parent->zig_lib_dir), target_arch_name(parent->zig_target->arch)))); - - c_file->args.append("-I"); - c_file->args.append(path_from_libc(parent, "include" OS_SEP "any-linux-any")); -} - -static const char *glibc_start_asm_path(CodeGen *parent, const char *file) { - ZigLLVM_ArchType arch = parent->zig_target->arch; - bool is_aarch64 = arch == ZigLLVM_aarch64 || arch == ZigLLVM_aarch64_be; - bool is_mips = arch == ZigLLVM_mips || arch == ZigLLVM_mipsel || - arch == ZigLLVM_mips64el || arch == ZigLLVM_mips64; - bool is_arm = arch == ZigLLVM_arm || arch == ZigLLVM_armeb; - bool is_ppc = arch == ZigLLVM_ppc || arch == ZigLLVM_ppc64 || arch == ZigLLVM_ppc64le; - bool is_riscv = arch == ZigLLVM_riscv32 || arch == ZigLLVM_riscv64; - bool is_sparc = arch == ZigLLVM_sparc || arch == ZigLLVM_sparcel || arch == ZigLLVM_sparcv9; - bool is_64 = target_arch_pointer_bit_width(arch) == 64; - - Buf result = BUF_INIT; - buf_resize(&result, 0); - buf_append_buf(&result, parent->zig_lib_dir); - buf_append_str(&result, OS_SEP "libc" OS_SEP "glibc" OS_SEP "sysdeps" OS_SEP); - if (is_sparc) { - if (is_64) { - buf_append_str(&result, "sparc" OS_SEP "sparc64"); - } else { - buf_append_str(&result, "sparc" OS_SEP "sparc32"); - } - } else if (is_arm) { - buf_append_str(&result, "arm"); - } else if (is_mips) { - buf_append_str(&result, "mips"); - } else if (arch == ZigLLVM_x86_64) { - buf_append_str(&result, "x86_64"); - } else if (arch == ZigLLVM_x86) { - buf_append_str(&result, "i386"); - } else if (is_aarch64) { - buf_append_str(&result, "aarch64"); - } else if (is_riscv) { - buf_append_str(&result, "riscv"); - } else if (is_ppc) { - if (is_64) { - buf_append_str(&result, "powerpc" OS_SEP "powerpc64"); - } else { - buf_append_str(&result, "powerpc" OS_SEP "powerpc32"); - } - } - - buf_append_str(&result, OS_SEP); - buf_append_str(&result, file); - return buf_ptr(&result); -} - -static const char *musl_start_asm_path(CodeGen *parent, const char *file) { - Buf *result = buf_sprintf("%s" OS_SEP "libc" OS_SEP "musl" OS_SEP "crt" OS_SEP "%s" OS_SEP "%s", - buf_ptr(parent->zig_lib_dir), target_arch_musl_name(parent->zig_target->arch), file); - return buf_ptr(result); -} - -static void musl_add_cc_args(CodeGen *parent, CFile *c_file, bool want_O3) { - c_file->args.append("-std=c99"); - c_file->args.append("-ffreestanding"); - // Musl adds these args to builds with gcc but clang does not support them. - //c_file->args.append("-fexcess-precision=standard"); - //c_file->args.append("-frounding-math"); - c_file->args.append("-Wa,--noexecstack"); - c_file->args.append("-D_XOPEN_SOURCE=700"); - - c_file->args.append("-I"); - c_file->args.append(buf_ptr(buf_sprintf("%s" OS_SEP "libc" OS_SEP "musl" OS_SEP "arch" OS_SEP "%s", - buf_ptr(parent->zig_lib_dir), target_arch_musl_name(parent->zig_target->arch)))); - - c_file->args.append("-I"); - c_file->args.append(buf_ptr(buf_sprintf("%s" OS_SEP "libc" OS_SEP "musl" OS_SEP "arch" OS_SEP "generic", - buf_ptr(parent->zig_lib_dir)))); - - c_file->args.append("-I"); - c_file->args.append(buf_ptr(buf_sprintf("%s" OS_SEP "libc" OS_SEP "musl" OS_SEP "src" OS_SEP "include", - buf_ptr(parent->zig_lib_dir)))); - - c_file->args.append("-I"); - c_file->args.append(buf_ptr(buf_sprintf("%s" OS_SEP "libc" OS_SEP "musl" OS_SEP "src" OS_SEP "internal", - buf_ptr(parent->zig_lib_dir)))); - - c_file->args.append("-I"); - c_file->args.append(buf_ptr(buf_sprintf("%s" OS_SEP "libc" OS_SEP "musl" OS_SEP "include", - buf_ptr(parent->zig_lib_dir)))); - - c_file->args.append("-I"); - c_file->args.append(buf_ptr(buf_sprintf( - "%s" OS_SEP "libc" OS_SEP "include" OS_SEP "%s-%s-musl", - buf_ptr(parent->zig_lib_dir), - target_arch_musl_name(parent->zig_target->arch), - target_os_name(parent->zig_target->os)))); - - c_file->args.append("-I"); - c_file->args.append(buf_ptr(buf_sprintf("%s" OS_SEP "libc" OS_SEP "include" OS_SEP "generic-musl", - buf_ptr(parent->zig_lib_dir)))); - - if (want_O3) - c_file->args.append("-O3"); - else - c_file->args.append("-Os"); - - c_file->args.append("-fomit-frame-pointer"); - c_file->args.append("-fno-unwind-tables"); - c_file->args.append("-fno-asynchronous-unwind-tables"); - c_file->args.append("-ffunction-sections"); - c_file->args.append("-fdata-sections"); -} - -static const char *musl_arch_names[] = { - "aarch64", - "arm", - "generic", - "i386", - "m68k", - "microblaze", - "mips", - "mips64", - "mipsn32", - "or1k", - "powerpc", - "powerpc64", - "riscv64", - "s390x", - "sh", - "x32", - "x86_64", -}; - -static bool is_musl_arch_name(const char *name) { - for (size_t i = 0; i < array_length(musl_arch_names); i += 1) { - if (strcmp(name, musl_arch_names[i]) == 0) - return true; - } - return false; -} - -enum MuslSrc { - MuslSrcAsm, - MuslSrcNormal, - MuslSrcO3, -}; - -static void add_musl_src_file(HashMap &source_table, - const char *file_path) -{ - Buf *src_file = buf_create_from_str(file_path); - - MuslSrc src_kind; - if (buf_ends_with_str(src_file, ".c")) { - bool want_O3 = buf_starts_with_str(src_file, "musl/src/malloc/") || - buf_starts_with_str(src_file, "musl/src/string/") || - buf_starts_with_str(src_file, "musl/src/internal/"); - src_kind = want_O3 ? MuslSrcO3 : MuslSrcNormal; - } else if (buf_ends_with_str(src_file, ".s") || buf_ends_with_str(src_file, ".S")) { - src_kind = MuslSrcAsm; - } else { - zig_unreachable(); - } - if (ZIG_OS_SEP_CHAR != '/') { - buf_replace(src_file, '/', ZIG_OS_SEP_CHAR); - } - source_table.put_unique(src_file, src_kind); -} - -static const char *build_musl(CodeGen *parent, Stage2ProgressNode *progress_node) { - CodeGen *child_gen = create_child_codegen(parent, nullptr, OutTypeLib, nullptr, "c", progress_node); - - // When there is a src//foo.* then it should substitute for src/foo.* - // Even a .s file can substitute for a .c file. - - const char *target_musl_arch_name = target_arch_musl_name(parent->zig_target->arch); - - HashMap source_table = {}; - source_table.init(2000); - - for (size_t i = 0; i < array_length(ZIG_MUSL_SRC_FILES); i += 1) { - add_musl_src_file(source_table, ZIG_MUSL_SRC_FILES[i]); - } - - static const char *time32_compat_arch_list[] = {"arm", "i386", "mips", "powerpc"}; - for (size_t arch_i = 0; arch_i < array_length(time32_compat_arch_list); arch_i += 1) { - if (strcmp(target_musl_arch_name, time32_compat_arch_list[arch_i]) == 0) { - for (size_t i = 0; i < array_length(ZIG_MUSL_COMPAT_TIME32_FILES); i += 1) { - add_musl_src_file(source_table, ZIG_MUSL_COMPAT_TIME32_FILES[i]); - } - } - } - - - ZigList c_source_files = {0}; - - Buf dirname = BUF_INIT; - Buf basename = BUF_INIT; - Buf noextbasename = BUF_INIT; - Buf dirbasename = BUF_INIT; - Buf before_arch_dir = BUF_INIT; - - auto source_it = source_table.entry_iterator(); - for (;;) { - auto *entry = source_it.next(); - if (!entry) break; - - Buf *src_file = entry->key; - MuslSrc src_kind = entry->value; - - os_path_split(src_file, &dirname, &basename); - os_path_extname(&basename, &noextbasename, nullptr); - os_path_split(&dirname, &before_arch_dir, &dirbasename); - - bool is_arch_specific = false; - // Architecture-specific implementations are under a / folder. - if (is_musl_arch_name(buf_ptr(&dirbasename))) { - // Not the architecture we're compiling for. - if (strcmp(buf_ptr(&dirbasename), target_musl_arch_name) != 0) - continue; - is_arch_specific = true; - } - - if (!is_arch_specific) { - Buf override_path = BUF_INIT; - - // Look for an arch specific override. - buf_resize(&override_path, 0); - buf_appendf(&override_path, "%s" OS_SEP "%s" OS_SEP "%s.s", - buf_ptr(&dirname), target_musl_arch_name, buf_ptr(&noextbasename)); - if (source_table.maybe_get(&override_path) != nullptr) - continue; - - buf_resize(&override_path, 0); - buf_appendf(&override_path, "%s" OS_SEP "%s" OS_SEP "%s.S", - buf_ptr(&dirname), target_musl_arch_name, buf_ptr(&noextbasename)); - if (source_table.maybe_get(&override_path) != nullptr) - continue; - - buf_resize(&override_path, 0); - buf_appendf(&override_path, "%s" OS_SEP "%s" OS_SEP "%s.c", - buf_ptr(&dirname), target_musl_arch_name, buf_ptr(&noextbasename)); - if (source_table.maybe_get(&override_path) != nullptr) - continue; - } - - Buf *full_path = buf_sprintf("%s" OS_SEP "libc" OS_SEP "%s", - buf_ptr(parent->zig_lib_dir), buf_ptr(src_file)); - - CFile *c_file = heap::c_allocator.create(); - c_file->source_path = buf_ptr(full_path); - - musl_add_cc_args(parent, c_file, src_kind == MuslSrcO3); - c_file->args.append("-Qunused-arguments"); - c_file->args.append("-w"); // disable all warnings - - c_source_files.append(c_file); - } - - child_gen->c_source_files = c_source_files; - codegen_build_and_link(child_gen); - return buf_ptr(&child_gen->bin_file_output_path); -} - -static const char *build_libcxxabi(CodeGen *parent, Stage2ProgressNode *progress_node) { - CodeGen *child_gen = create_child_codegen(parent, nullptr, OutTypeLib, nullptr, "c++abi", progress_node); - codegen_add_link_lib(child_gen, buf_create_from_str("c")); - - ZigList c_source_files = {0}; - - const char *cxxabi_include_path = buf_ptr(buf_sprintf("%s" OS_SEP "libcxxabi" OS_SEP "include", - buf_ptr(parent->zig_lib_dir))); - const char *cxx_include_path = buf_ptr(buf_sprintf("%s" OS_SEP "libcxx" OS_SEP "include", - buf_ptr(parent->zig_lib_dir))); - - for (size_t i = 0; i < array_length(ZIG_LIBCXXABI_FILES); i += 1) { - const char *rel_src_path = ZIG_LIBCXXABI_FILES[i]; - - CFile *c_file = heap::c_allocator.create(); - c_file->source_path = buf_ptr(buf_sprintf("%s" OS_SEP "libcxxabi" OS_SEP "%s", - buf_ptr(parent->zig_lib_dir), rel_src_path)); - - c_file->args.append("-DHAVE___CXA_THREAD_ATEXIT_IMPL"); - c_file->args.append("-D_LIBCPP_DISABLE_EXTERN_TEMPLATE"); - c_file->args.append("-D_LIBCPP_ENABLE_CXX17_REMOVED_UNEXPECTED_FUNCTIONS"); - c_file->args.append("-D_LIBCXXABI_BUILDING_LIBRARY"); - c_file->args.append("-D_LIBCXXABI_DISABLE_VISIBILITY_ANNOTATIONS"); - c_file->args.append("-D_LIBCPP_DISABLE_VISIBILITY_ANNOTATIONS"); - - if (target_abi_is_musl(parent->zig_target->abi)) { - c_file->args.append("-D_LIBCPP_HAS_MUSL_LIBC"); - } - - c_file->args.append("-I"); - c_file->args.append(cxxabi_include_path); - - c_file->args.append("-I"); - c_file->args.append(cxx_include_path); - - c_file->args.append("-O3"); - c_file->args.append("-DNDEBUG"); - if (target_supports_fpic(parent->zig_target)) { - c_file->args.append("-fPIC"); - } - c_file->args.append("-nostdinc++"); - c_file->args.append("-fstrict-aliasing"); - c_file->args.append("-funwind-tables"); - c_file->args.append("-D_DEBUG"); - c_file->args.append("-UNDEBUG"); - c_file->args.append("-std=c++11"); - - c_source_files.append(c_file); - } - - - child_gen->c_source_files = c_source_files; - codegen_build_and_link(child_gen); - return buf_ptr(&child_gen->bin_file_output_path); -} - -static const char *build_libcxx(CodeGen *parent, Stage2ProgressNode *progress_node) { - CodeGen *child_gen = create_child_codegen(parent, nullptr, OutTypeLib, nullptr, "c++", progress_node); - codegen_add_link_lib(child_gen, buf_create_from_str("c")); - - ZigList c_source_files = {0}; - - const char *cxxabi_include_path = buf_ptr(buf_sprintf("%s" OS_SEP "libcxxabi" OS_SEP "include", - buf_ptr(parent->zig_lib_dir))); - const char *cxx_include_path = buf_ptr(buf_sprintf("%s" OS_SEP "libcxx" OS_SEP "include", - buf_ptr(parent->zig_lib_dir))); - - for (size_t i = 0; i < array_length(ZIG_LIBCXX_FILES); i += 1) { - const char *rel_src_path = ZIG_LIBCXX_FILES[i]; - - Buf *src_path_buf = buf_create_from_str(rel_src_path); - if (parent->zig_target->os == OsWindows) { - // filesystem stuff isn't supported on Windows - if (buf_starts_with_str(src_path_buf, "src/filesystem/")) { - continue; - } - } else { - if (buf_starts_with_str(src_path_buf, "src/support/win32/")) { - continue; - } - } - - CFile *c_file = heap::c_allocator.create(); - c_file->source_path = buf_ptr(buf_sprintf("%s" OS_SEP "libcxx" OS_SEP "%s", - buf_ptr(parent->zig_lib_dir), rel_src_path)); - - c_file->args.append("-DNDEBUG"); - c_file->args.append("-D_LIBCPP_BUILDING_LIBRARY"); - c_file->args.append("-D_LIBCPP_HAS_NO_PRAGMA_SYSTEM_HEADER"); - c_file->args.append("-DLIBCXX_BUILDING_LIBCXXABI"); - c_file->args.append("-D_LIBCXXABI_DISABLE_VISIBILITY_ANNOTATIONS"); - c_file->args.append("-D_LIBCPP_DISABLE_VISIBILITY_ANNOTATIONS"); - - if (target_abi_is_musl(parent->zig_target->abi)) { - c_file->args.append("-D_LIBCPP_HAS_MUSL_LIBC"); - } - - c_file->args.append("-I"); - c_file->args.append(cxx_include_path); - - c_file->args.append("-I"); - c_file->args.append(cxxabi_include_path); - - c_file->args.append("-O3"); - c_file->args.append("-DNDEBUG"); - if (target_supports_fpic(parent->zig_target)) { - c_file->args.append("-fPIC"); - } - c_file->args.append("-nostdinc++"); - c_file->args.append("-fvisibility-inlines-hidden"); - c_file->args.append("-std=c++14"); - c_file->args.append("-Wno-user-defined-literals"); - - c_source_files.append(c_file); - } - - - child_gen->c_source_files = c_source_files; - codegen_build_and_link(child_gen); - return buf_ptr(&child_gen->bin_file_output_path); -} - -static void add_msvcrt_os_dep(CodeGen *parent, CodeGen *child_gen, const char *src_path) { - CFile *c_file = heap::c_allocator.create(); - c_file->source_path = buf_ptr(buf_sprintf("%s" OS_SEP "libc" OS_SEP "mingw" OS_SEP "%s", - buf_ptr(parent->zig_lib_dir), src_path)); - c_file->args.append("-DHAVE_CONFIG_H"); - c_file->args.append("-D__LIBMSVCRT__"); - - c_file->args.append("-I"); - c_file->args.append(path_from_libc(parent, "mingw" OS_SEP "include")); - - c_file->args.append("-std=gnu99"); - c_file->args.append("-D_CRTBLD"); - c_file->args.append("-D_WIN32_WINNT=0x0f00"); - c_file->args.append("-D__MSVCRT_VERSION__=0x700"); - - c_file->args.append("-isystem"); - c_file->args.append(path_from_libc(parent, "include" OS_SEP "any-windows-any")); - - c_file->args.append("-g"); - c_file->args.append("-O2"); - - child_gen->c_source_files.append(c_file); -} - -static void add_mingwex_dep(CodeGen *parent, CodeGen *child_gen, const char *src_path) { - CFile *c_file = heap::c_allocator.create(); - c_file->source_path = buf_ptr(buf_sprintf("%s" OS_SEP "libc" OS_SEP "mingw" OS_SEP "%s", - buf_ptr(parent->zig_lib_dir), src_path)); - c_file->args.append("-DHAVE_CONFIG_H"); - - c_file->args.append("-I"); - c_file->args.append(path_from_libc(parent, "mingw")); - - c_file->args.append("-I"); - c_file->args.append(path_from_libc(parent, "mingw" OS_SEP "include")); - - c_file->args.append("-std=gnu99"); - c_file->args.append("-D_CRTBLD"); - c_file->args.append("-D_WIN32_WINNT=0x0f00"); - c_file->args.append("-D__MSVCRT_VERSION__=0x700"); - c_file->args.append("-g"); - c_file->args.append("-O2"); - - c_file->args.append("-isystem"); - c_file->args.append(path_from_libc(parent, "include" OS_SEP "any-windows-any")); - - child_gen->c_source_files.append(c_file); -} - -static void add_mingw_uuid_dep(CodeGen *parent, CodeGen *child_gen, const char *src_path) { - CFile *c_file = heap::c_allocator.create(); - c_file->source_path = buf_ptr(buf_sprintf("%s" OS_SEP "libc" OS_SEP "mingw" OS_SEP "%s", - buf_ptr(parent->zig_lib_dir), src_path)); - c_file->args.append("-DHAVE_CONFIG_H"); - - c_file->args.append("-I"); - c_file->args.append(path_from_libc(parent, "mingw")); - - c_file->args.append("-I"); - c_file->args.append(path_from_libc(parent, "mingw" OS_SEP "include")); - - c_file->args.append("-std=gnu99"); - c_file->args.append("-D_CRTBLD"); - c_file->args.append("-D_WIN32_WINNT=0x0f00"); - c_file->args.append("-D__MSVCRT_VERSION__=0x700"); - c_file->args.append("-g"); - c_file->args.append("-O2"); - - c_file->args.append("-isystem"); - c_file->args.append(path_from_libc(parent, "include" OS_SEP "any-windows-any")); - - child_gen->c_source_files.append(c_file); -} - -static const char *get_libc_crt_file(CodeGen *parent, const char *file, Stage2ProgressNode *progress_node) { - if (parent->libc == nullptr && parent->zig_target->os == OsWindows) { - if (strcmp(file, "crt2.o") == 0) { - CFile *c_file = heap::c_allocator.create(); - c_file->source_path = buf_ptr(buf_sprintf( - "%s" OS_SEP "libc" OS_SEP "mingw" OS_SEP "crt" OS_SEP "crtexe.c", buf_ptr(parent->zig_lib_dir))); - mingw_add_cc_args(parent, c_file); - c_file->args.append("-U__CRTDLL__"); - c_file->args.append("-D__MSVCRT__"); - // Uncomment these 3 things for crtu - //c_file->args.append("-DUNICODE"); - //c_file->args.append("-D_UNICODE"); - //c_file->args.append("-DWPRFLAG=1"); - return build_libc_object(parent, "crt2", c_file, progress_node); - } else if (strcmp(file, "dllcrt2.o") == 0) { - CFile *c_file = heap::c_allocator.create(); - c_file->source_path = buf_ptr(buf_sprintf( - "%s" OS_SEP "libc" OS_SEP "mingw" OS_SEP "crt" OS_SEP "crtdll.c", buf_ptr(parent->zig_lib_dir))); - mingw_add_cc_args(parent, c_file); - c_file->args.append("-U__CRTDLL__"); - c_file->args.append("-D__MSVCRT__"); - return build_libc_object(parent, "dllcrt2", c_file, progress_node); - } else if (strcmp(file, "mingw32.lib") == 0) { - CodeGen *child_gen = create_child_codegen(parent, nullptr, OutTypeLib, nullptr, "mingw32", progress_node); - - static const char *deps[] = { - "mingw" OS_SEP "crt" OS_SEP "crt0_c.c", - "mingw" OS_SEP "crt" OS_SEP "dll_argv.c", - "mingw" OS_SEP "crt" OS_SEP "gccmain.c", - "mingw" OS_SEP "crt" OS_SEP "natstart.c", - "mingw" OS_SEP "crt" OS_SEP "pseudo-reloc-list.c", - "mingw" OS_SEP "crt" OS_SEP "wildcard.c", - "mingw" OS_SEP "crt" OS_SEP "charmax.c", - "mingw" OS_SEP "crt" OS_SEP "crt0_w.c", - "mingw" OS_SEP "crt" OS_SEP "dllargv.c", - "mingw" OS_SEP "crt" OS_SEP "gs_support.c", - "mingw" OS_SEP "crt" OS_SEP "_newmode.c", - "mingw" OS_SEP "crt" OS_SEP "tlssup.c", - "mingw" OS_SEP "crt" OS_SEP "xncommod.c", - "mingw" OS_SEP "crt" OS_SEP "cinitexe.c", - "mingw" OS_SEP "crt" OS_SEP "merr.c", - "mingw" OS_SEP "crt" OS_SEP "usermatherr.c", - "mingw" OS_SEP "crt" OS_SEP "pesect.c", - "mingw" OS_SEP "crt" OS_SEP "udllargc.c", - "mingw" OS_SEP "crt" OS_SEP "xthdloc.c", - "mingw" OS_SEP "crt" OS_SEP "CRT_fp10.c", - "mingw" OS_SEP "crt" OS_SEP "mingw_helpers.c", - "mingw" OS_SEP "crt" OS_SEP "pseudo-reloc.c", - "mingw" OS_SEP "crt" OS_SEP "udll_argv.c", - "mingw" OS_SEP "crt" OS_SEP "xtxtmode.c", - "mingw" OS_SEP "crt" OS_SEP "crt_handler.c", - "mingw" OS_SEP "crt" OS_SEP "tlsthrd.c", - "mingw" OS_SEP "crt" OS_SEP "tlsmthread.c", - "mingw" OS_SEP "crt" OS_SEP "tlsmcrt.c", - "mingw" OS_SEP "crt" OS_SEP "cxa_atexit.c", - }; - for (size_t i = 0; i < array_length(deps); i += 1) { - CFile *c_file = heap::c_allocator.create(); - c_file->source_path = path_from_libc(parent, deps[i]); - c_file->args.append("-DHAVE_CONFIG_H"); - c_file->args.append("-D_SYSCRT=1"); - c_file->args.append("-DCRTDLL=1"); - - c_file->args.append("-isystem"); - c_file->args.append(path_from_libc(parent, "include" OS_SEP "any-windows-any")); - - c_file->args.append("-isystem"); - c_file->args.append(path_from_libc(parent, "mingw" OS_SEP "include")); - - c_file->args.append("-std=gnu99"); - c_file->args.append("-D_CRTBLD"); - c_file->args.append("-D_WIN32_WINNT=0x0f00"); - c_file->args.append("-D__MSVCRT_VERSION__=0x700"); - c_file->args.append("-g"); - c_file->args.append("-O2"); - - child_gen->c_source_files.append(c_file); - } - codegen_build_and_link(child_gen); - return buf_ptr(&child_gen->bin_file_output_path); - } else if (strcmp(file, "msvcrt-os.lib") == 0) { - CodeGen *child_gen = create_child_codegen(parent, nullptr, OutTypeLib, nullptr, "msvcrt-os", progress_node); - - for (size_t i = 0; i < array_length(msvcrt_common_src); i += 1) { - add_msvcrt_os_dep(parent, child_gen, msvcrt_common_src[i]); - } - if (parent->zig_target->arch == ZigLLVM_x86) { - for (size_t i = 0; i < array_length(msvcrt_i386_src); i += 1) { - add_msvcrt_os_dep(parent, child_gen, msvcrt_i386_src[i]); - } - } else { - for (size_t i = 0; i < array_length(msvcrt_other_src); i += 1) { - add_msvcrt_os_dep(parent, child_gen, msvcrt_other_src[i]); - } - } - codegen_build_and_link(child_gen); - return buf_ptr(&child_gen->bin_file_output_path); - } else if (strcmp(file, "mingwex.lib") == 0) { - CodeGen *child_gen = create_child_codegen(parent, nullptr, OutTypeLib, nullptr, "mingwex", progress_node); - - for (size_t i = 0; i < array_length(mingwex_generic_src); i += 1) { - add_mingwex_dep(parent, child_gen, mingwex_generic_src[i]); - } - if (parent->zig_target->arch == ZigLLVM_x86 || parent->zig_target->arch == ZigLLVM_x86_64) { - for (size_t i = 0; i < array_length(mingwex_x86_src); i += 1) { - add_mingwex_dep(parent, child_gen, mingwex_x86_src[i]); - } - } else if (target_is_arm(parent->zig_target)) { - if (target_arch_pointer_bit_width(parent->zig_target->arch) == 32) { - for (size_t i = 0; i < array_length(mingwex_arm32_src); i += 1) { - add_mingwex_dep(parent, child_gen, mingwex_arm32_src[i]); - } - } else { - for (size_t i = 0; i < array_length(mingwex_arm64_src); i += 1) { - add_mingwex_dep(parent, child_gen, mingwex_arm64_src[i]); - } - } - } else { - zig_unreachable(); - } - codegen_build_and_link(child_gen); - return buf_ptr(&child_gen->bin_file_output_path); - } else if (strcmp(file, "uuid.lib") == 0) { - CodeGen *child_gen = create_child_codegen(parent, nullptr, OutTypeLib, nullptr, "uuid", progress_node); - for (size_t i = 0; i < array_length(mingw_uuid_src); i += 1) { - add_mingw_uuid_dep(parent, child_gen, mingw_uuid_src[i]); - } - codegen_build_and_link(child_gen); - return buf_ptr(&child_gen->bin_file_output_path); - } else { - zig_unreachable(); - } - } else if (parent->libc == nullptr && target_is_glibc(parent->zig_target)) { - if (strcmp(file, "crti.o") == 0) { - CFile *c_file = heap::c_allocator.create(); - c_file->source_path = glibc_start_asm_path(parent, "crti.S"); - glibc_add_include_dirs(parent, c_file); - c_file->args.append("-D_LIBC_REENTRANT"); - c_file->args.append("-include"); - c_file->args.append(path_from_libc(parent, "glibc" OS_SEP "include" OS_SEP "libc-modules.h")); - c_file->args.append("-DMODULE_NAME=libc"); - c_file->args.append("-Wno-nonportable-include-path"); - c_file->args.append("-include"); - c_file->args.append(path_from_libc(parent, "glibc" OS_SEP "include" OS_SEP "libc-symbols.h")); - c_file->args.append("-DTOP_NAMESPACE=glibc"); - c_file->args.append("-DASSEMBLER"); - c_file->args.append("-g"); - c_file->args.append("-Wa,--noexecstack"); - return build_libc_object(parent, "crti", c_file, progress_node); - } else if (strcmp(file, "crtn.o") == 0) { - CFile *c_file = heap::c_allocator.create(); - c_file->source_path = glibc_start_asm_path(parent, "crtn.S"); - glibc_add_include_dirs(parent, c_file); - c_file->args.append("-D_LIBC_REENTRANT"); - c_file->args.append("-DMODULE_NAME=libc"); - c_file->args.append("-DTOP_NAMESPACE=glibc"); - c_file->args.append("-DASSEMBLER"); - c_file->args.append("-g"); - c_file->args.append("-Wa,--noexecstack"); - return build_libc_object(parent, "crtn", c_file, progress_node); - } else if (strcmp(file, "start.os") == 0) { - CFile *c_file = heap::c_allocator.create(); - c_file->source_path = glibc_start_asm_path(parent, "start.S"); - glibc_add_include_dirs(parent, c_file); - c_file->args.append("-D_LIBC_REENTRANT"); - c_file->args.append("-include"); - c_file->args.append(path_from_libc(parent, "glibc" OS_SEP "include" OS_SEP "libc-modules.h")); - c_file->args.append("-DMODULE_NAME=libc"); - c_file->args.append("-Wno-nonportable-include-path"); - c_file->args.append("-include"); - c_file->args.append(path_from_libc(parent, "glibc" OS_SEP "include" OS_SEP "libc-symbols.h")); - c_file->args.append("-DPIC"); - c_file->args.append("-DSHARED"); - c_file->args.append("-DTOP_NAMESPACE=glibc"); - c_file->args.append("-DASSEMBLER"); - c_file->args.append("-g"); - c_file->args.append("-Wa,--noexecstack"); - return build_libc_object(parent, "start", c_file, progress_node); - } else if (strcmp(file, "abi-note.o") == 0) { - CFile *c_file = heap::c_allocator.create(); - c_file->source_path = path_from_libc(parent, "glibc" OS_SEP "csu" OS_SEP "abi-note.S"); - c_file->args.append("-I"); - c_file->args.append(path_from_libc(parent, "glibc" OS_SEP "csu")); - glibc_add_include_dirs(parent, c_file); - c_file->args.append("-D_LIBC_REENTRANT"); - c_file->args.append("-DMODULE_NAME=libc"); - c_file->args.append("-DTOP_NAMESPACE=glibc"); - c_file->args.append("-DASSEMBLER"); - c_file->args.append("-g"); - c_file->args.append("-Wa,--noexecstack"); - return build_libc_object(parent, "abi-note", c_file, progress_node); - } else if (strcmp(file, "Scrt1.o") == 0) { - const char *start_os = get_libc_crt_file(parent, "start.os", progress_node); - const char *abi_note_o = get_libc_crt_file(parent, "abi-note.o", progress_node); - CodeGen *child_gen = create_child_codegen(parent, nullptr, OutTypeObj, nullptr, "Scrt1", progress_node); - codegen_add_object(child_gen, buf_create_from_str(start_os)); - codegen_add_object(child_gen, buf_create_from_str(abi_note_o)); - codegen_build_and_link(child_gen); - return buf_ptr(&child_gen->bin_file_output_path); - } else if (strcmp(file, "libc_nonshared.a") == 0) { - CodeGen *child_gen = create_child_codegen(parent, nullptr, OutTypeLib, nullptr, "c_nonshared", progress_node); - { - CFile *c_file = heap::c_allocator.create(); - c_file->source_path = path_from_libc(parent, "glibc" OS_SEP "csu" OS_SEP "elf-init.c"); - c_file->args.append("-std=gnu11"); - c_file->args.append("-fgnu89-inline"); - c_file->args.append("-g"); - c_file->args.append("-O2"); - c_file->args.append("-fmerge-all-constants"); - c_file->args.append("-fno-stack-protector"); - c_file->args.append("-fmath-errno"); - c_file->args.append("-fno-stack-protector"); - c_file->args.append("-I"); - c_file->args.append(path_from_libc(parent, "glibc" OS_SEP "csu")); - glibc_add_include_dirs(parent, c_file); - c_file->args.append("-DSTACK_PROTECTOR_LEVEL=0"); - c_file->args.append("-fPIC"); - c_file->args.append("-fno-stack-protector"); - c_file->args.append("-ftls-model=initial-exec"); - c_file->args.append("-D_LIBC_REENTRANT"); - c_file->args.append("-include"); - c_file->args.append(path_from_libc(parent, "glibc" OS_SEP "include" OS_SEP "libc-modules.h")); - c_file->args.append("-DMODULE_NAME=libc"); - c_file->args.append("-Wno-nonportable-include-path"); - c_file->args.append("-include"); - c_file->args.append(path_from_libc(parent, "glibc" OS_SEP "include" OS_SEP "libc-symbols.h")); - c_file->args.append("-DPIC"); - c_file->args.append("-DLIBC_NONSHARED=1"); - c_file->args.append("-DTOP_NAMESPACE=glibc"); - codegen_add_object(child_gen, buf_create_from_str( - build_libc_object(parent, "elf-init", c_file, progress_node))); - } - static const struct { - const char *name; - const char *path; - } deps[] = { - {"atexit", "glibc" OS_SEP "stdlib" OS_SEP "atexit.c"}, - {"at_quick_exit", "glibc" OS_SEP "stdlib" OS_SEP "at_quick_exit.c"}, - {"stat", "glibc" OS_SEP "io" OS_SEP "stat.c"}, - {"fstat", "glibc" OS_SEP "io" OS_SEP "fstat.c"}, - {"lstat", "glibc" OS_SEP "io" OS_SEP "lstat.c"}, - {"stat64", "glibc" OS_SEP "io" OS_SEP "stat64.c"}, - {"fstat64", "glibc" OS_SEP "io" OS_SEP "fstat64.c"}, - {"lstat64", "glibc" OS_SEP "io" OS_SEP "lstat64.c"}, - {"fstatat", "glibc" OS_SEP "io" OS_SEP "fstatat.c"}, - {"fstatat64", "glibc" OS_SEP "io" OS_SEP "fstatat64.c"}, - {"mknod", "glibc" OS_SEP "io" OS_SEP "mknod.c"}, - {"mknodat", "glibc" OS_SEP "io" OS_SEP "mknodat.c"}, - {"pthread_atfork", "glibc" OS_SEP "nptl" OS_SEP "pthread_atfork.c"}, - {"stack_chk_fail_local", "glibc" OS_SEP "debug" OS_SEP "stack_chk_fail_local.c"}, - }; - for (size_t i = 0; i < array_length(deps); i += 1) { - CFile *c_file = heap::c_allocator.create(); - c_file->source_path = path_from_libc(parent, deps[i].path); - c_file->args.append("-std=gnu11"); - c_file->args.append("-fgnu89-inline"); - c_file->args.append("-g"); - c_file->args.append("-O2"); - c_file->args.append("-fmerge-all-constants"); - c_file->args.append("-fno-stack-protector"); - c_file->args.append("-fmath-errno"); - c_file->args.append("-ftls-model=initial-exec"); - c_file->args.append("-Wno-ignored-attributes"); - glibc_add_include_dirs(parent, c_file); - c_file->args.append("-D_LIBC_REENTRANT"); - c_file->args.append("-include"); - c_file->args.append(path_from_libc(parent, "glibc" OS_SEP "include" OS_SEP "libc-modules.h")); - c_file->args.append("-DMODULE_NAME=libc"); - c_file->args.append("-Wno-nonportable-include-path"); - c_file->args.append("-include"); - c_file->args.append(path_from_libc(parent, "glibc" OS_SEP "include" OS_SEP "libc-symbols.h")); - c_file->args.append("-DPIC"); - c_file->args.append("-DLIBC_NONSHARED=1"); - c_file->args.append("-DTOP_NAMESPACE=glibc"); - codegen_add_object(child_gen, buf_create_from_str( - build_libc_object(parent, deps[i].name, c_file, progress_node))); - } - codegen_build_and_link(child_gen); - return buf_ptr(&child_gen->bin_file_output_path); - } else { - zig_unreachable(); - } - } else if (parent->libc == nullptr && target_is_musl(parent->zig_target)) { - if (strcmp(file, "crti.o") == 0) { - CFile *c_file = heap::c_allocator.create(); - c_file->source_path = musl_start_asm_path(parent, "crti.s"); - musl_add_cc_args(parent, c_file, false); - c_file->args.append("-Qunused-arguments"); - return build_libc_object(parent, "crti", c_file, progress_node); - } else if (strcmp(file, "crtn.o") == 0) { - CFile *c_file = heap::c_allocator.create(); - c_file->source_path = musl_start_asm_path(parent, "crtn.s"); - c_file->args.append("-Qunused-arguments"); - musl_add_cc_args(parent, c_file, false); - return build_libc_object(parent, "crtn", c_file, progress_node); - } else if (strcmp(file, "crt1.o") == 0) { - CFile *c_file = heap::c_allocator.create(); - c_file->source_path = path_from_libc(parent, "musl" OS_SEP "crt" OS_SEP "crt1.c"); - musl_add_cc_args(parent, c_file, false); - c_file->args.append("-fno-stack-protector"); - c_file->args.append("-DCRT"); - return build_libc_object(parent, "crt1", c_file, progress_node); - } else if (strcmp(file, "Scrt1.o") == 0) { - CFile *c_file = heap::c_allocator.create(); - c_file->source_path = path_from_libc(parent, "musl" OS_SEP "crt" OS_SEP "Scrt1.c"); - musl_add_cc_args(parent, c_file, false); - c_file->args.append("-fPIC"); - c_file->args.append("-fno-stack-protector"); - c_file->args.append("-DCRT"); - return build_libc_object(parent, "Scrt1", c_file, progress_node); - } else { - zig_unreachable(); - } - } else { - assert(parent->libc != nullptr); - Buf *out_buf = buf_alloc(); - os_path_join(buf_create_from_mem(parent->libc->crt_dir, parent->libc->crt_dir_len), - buf_create_from_str(file), out_buf); - return buf_ptr(out_buf); - } -} - -static Buf *build_a_raw(CodeGen *parent_gen, const char *aname, Buf *full_path, OutType child_out_type, - Stage2ProgressNode *progress_node) -{ - CodeGen *child_gen = create_child_codegen(parent_gen, full_path, child_out_type, parent_gen->libc, aname, - progress_node); - - // This is so that compiler_rt and libc.zig libraries know whether they - // will eventually be linked with libc. They make different decisions - // about what to export depending on whether libc is linked. - if (parent_gen->libc_link_lib != nullptr) { - LinkLib *new_link_lib = codegen_add_link_lib(child_gen, parent_gen->libc_link_lib->name); - new_link_lib->provided_explicitly = parent_gen->libc_link_lib->provided_explicitly; - } - - // Override the inherited build mode parameter - if (!parent_gen->is_test_build) { - switch (parent_gen->build_mode) { - case BuildModeDebug: - case BuildModeFastRelease: - case BuildModeSafeRelease: - child_gen->build_mode = BuildModeFastRelease; - break; - case BuildModeSmallRelease: - break; - } - } - - child_gen->function_sections = true; - child_gen->want_stack_check = WantStackCheckDisabled; - - codegen_build_and_link(child_gen); - return &child_gen->bin_file_output_path; -} - -static Buf *build_compiler_rt(CodeGen *parent_gen, OutType child_out_type, Stage2ProgressNode *progress_node) { - Buf *full_path = buf_alloc(); - os_path_join(parent_gen->zig_std_special_dir, buf_create_from_str("compiler_rt.zig"), full_path); - - return build_a_raw(parent_gen, "compiler_rt", full_path, child_out_type, progress_node); -} - -static Buf *build_c(CodeGen *parent_gen, OutType child_out_type, Stage2ProgressNode *progress_node) { - Buf *full_path = buf_alloc(); - os_path_join(parent_gen->zig_std_special_dir, buf_create_from_str("c.zig"), full_path); - - return build_a_raw(parent_gen, "c", full_path, child_out_type, progress_node); -} - -static const char *get_darwin_arch_string(const ZigTarget *t) { - switch (t->arch) { - case ZigLLVM_aarch64: - return "arm64"; - case ZigLLVM_thumb: - case ZigLLVM_arm: - return "arm"; - case ZigLLVM_ppc: - return "ppc"; - case ZigLLVM_ppc64: - return "ppc64"; - case ZigLLVM_ppc64le: - return "ppc64le"; - default: - return ZigLLVMGetArchTypeName(t->arch); - } -} - - -static const char *getLDMOption(const ZigTarget *t) { - switch (t->arch) { - case ZigLLVM_x86: - return "elf_i386"; - case ZigLLVM_aarch64: - return "aarch64linux"; - case ZigLLVM_aarch64_be: - return "aarch64_be_linux"; - case ZigLLVM_arm: - case ZigLLVM_thumb: - return "armelf_linux_eabi"; - case ZigLLVM_armeb: - case ZigLLVM_thumbeb: - return "armebelf_linux_eabi"; - case ZigLLVM_ppc: - return "elf32ppclinux"; - case ZigLLVM_ppc64: - return "elf64ppc"; - case ZigLLVM_ppc64le: - return "elf64lppc"; - case ZigLLVM_sparc: - case ZigLLVM_sparcel: - return "elf32_sparc"; - case ZigLLVM_sparcv9: - return "elf64_sparc"; - case ZigLLVM_mips: - return "elf32btsmip"; - case ZigLLVM_mipsel: - return "elf32ltsmip"; - case ZigLLVM_mips64: - return "elf64btsmip"; - case ZigLLVM_mips64el: - return "elf64ltsmip"; - case ZigLLVM_systemz: - return "elf64_s390"; - case ZigLLVM_x86_64: - if (t->abi == ZigLLVM_GNUX32) { - return "elf32_x86_64"; - } - // Any target elf will use the freebsd osabi if suffixed with "_fbsd". - if (t->os == OsFreeBSD) { - return "elf_x86_64_fbsd"; - } - return "elf_x86_64"; - case ZigLLVM_riscv32: - return "elf32lriscv"; - case ZigLLVM_riscv64: - return "elf64lriscv"; - default: - zig_unreachable(); - } -} - -static void add_rpath(LinkJob *lj, Buf *rpath) { - if (lj->rpath_table.maybe_get(rpath) != nullptr) - return; - - lj->args.append("-rpath"); - lj->args.append(buf_ptr(rpath)); - - lj->rpath_table.put(rpath, true); -} - -static void add_glibc_libs(LinkJob *lj) { - Error err; - ZigGLibCAbi *glibc_abi; - if ((err = glibc_load_metadata(&glibc_abi, lj->codegen->zig_lib_dir, true))) { - fprintf(stderr, "%s\n", err_str(err)); - exit(1); - } - - Buf *artifact_dir; - if ((err = glibc_build_dummies_and_maps(lj->codegen, glibc_abi, lj->codegen->zig_target, - &artifact_dir, true, lj->build_dep_prog_node))) - { - fprintf(stderr, "%s\n", err_str(err)); - exit(1); - } - - size_t lib_count = glibc_lib_count(); - for (size_t i = 0; i < lib_count; i += 1) { - const ZigGLibCLib *lib = glibc_lib_enum(i); - Buf *so_path = buf_sprintf("%s" OS_SEP "lib%s.so.%d.0.0", buf_ptr(artifact_dir), lib->name, lib->sover); - lj->args.append(buf_ptr(so_path)); - } -} - -static void construct_linker_job_elf(LinkJob *lj) { - CodeGen *g = lj->codegen; - - lj->args.append("-error-limit=0"); - - if (g->out_type == OutTypeExe) { - lj->args.append("-z"); - size_t stack_size = (g->stack_size_override == 0) ? 16777216 : g->stack_size_override; - lj->args.append(buf_ptr(buf_sprintf("stack-size=%" ZIG_PRI_usize, stack_size))); - } - - if (g->linker_script) { - lj->args.append("-T"); - lj->args.append(g->linker_script); - } - - switch (g->linker_gc_sections) { - case OptionalBoolNull: - if (g->out_type != OutTypeObj) { - lj->args.append("--gc-sections"); - } - break; - case OptionalBoolTrue: - lj->args.append("--gc-sections"); - break; - case OptionalBoolFalse: - break; - } - - if (g->link_eh_frame_hdr) { - lj->args.append("--eh-frame-hdr"); - } - - if (g->linker_rdynamic) { - lj->args.append("--export-dynamic"); - } - - if (g->linker_optimization != nullptr) { - lj->args.append(buf_ptr(g->linker_optimization)); - } - - if (g->linker_z_nodelete) { - lj->args.append("-z"); - lj->args.append("nodelete"); - } - if (g->linker_z_defs) { - lj->args.append("-z"); - lj->args.append("defs"); - } - - lj->args.append("-m"); - lj->args.append(getLDMOption(g->zig_target)); - - bool is_lib = g->out_type == OutTypeLib; - bool is_dyn_lib = g->is_dynamic && is_lib; - if (!g->have_dynamic_link) { - if (g->zig_target->arch == ZigLLVM_arm || g->zig_target->arch == ZigLLVM_armeb || - g->zig_target->arch == ZigLLVM_thumb || g->zig_target->arch == ZigLLVM_thumbeb) - { - lj->args.append("-Bstatic"); - } else { - lj->args.append("-static"); - } - } else if (is_dyn_lib) { - lj->args.append("-shared"); - } - - if (target_requires_pie(g->zig_target) && g->out_type == OutTypeExe) { - lj->args.append("-pie"); - } - - assert(buf_len(&g->bin_file_output_path) != 0); - lj->args.append("-o"); - lj->args.append(buf_ptr(&g->bin_file_output_path)); - - if (lj->link_in_crt) { - const char *crt1o; - if (g->zig_target->os == OsNetBSD) { - crt1o = "crt0.o"; - } else if (target_is_android(g->zig_target)) { - if (g->have_dynamic_link) { - crt1o = "crtbegin_dynamic.o"; - } else { - crt1o = "crtbegin_static.o"; - } - } else if (!g->have_dynamic_link) { - crt1o = "crt1.o"; - } else { - crt1o = "Scrt1.o"; - } - lj->args.append(get_libc_crt_file(g, crt1o, lj->build_dep_prog_node)); - if (target_libc_needs_crti_crtn(g->zig_target)) { - lj->args.append(get_libc_crt_file(g, "crti.o", lj->build_dep_prog_node)); - } - } - - for (size_t i = 0; i < g->rpath_list.length; i += 1) { - Buf *rpath = g->rpath_list.at(i); - add_rpath(lj, rpath); - } - if (g->each_lib_rpath) { - for (size_t i = 0; i < g->lib_dirs.length; i += 1) { - const char *lib_dir = g->lib_dirs.at(i); - for (size_t i = 0; i < g->link_libs_list.length; i += 1) { - LinkLib *link_lib = g->link_libs_list.at(i); - if (buf_eql_str(link_lib->name, "c")) { - continue; - } - bool does_exist; - Buf *test_path = buf_sprintf("%s/lib%s.so", lib_dir, buf_ptr(link_lib->name)); - if (os_file_exists(test_path, &does_exist) != ErrorNone) { - zig_panic("link: unable to check if file exists: %s", buf_ptr(test_path)); - } - if (does_exist) { - add_rpath(lj, buf_create_from_str(lib_dir)); - break; - } - } - } - } - - for (size_t i = 0; i < g->lib_dirs.length; i += 1) { - const char *lib_dir = g->lib_dirs.at(i); - lj->args.append("-L"); - lj->args.append(lib_dir); - } - - if (g->libc_link_lib != nullptr) { - if (g->libc != nullptr) { - lj->args.append("-L"); - lj->args.append(buf_ptr(buf_create_from_mem(g->libc->crt_dir, g->libc->crt_dir_len))); - } - - if (g->have_dynamic_link && (is_dyn_lib || g->out_type == OutTypeExe)) { - assert(g->zig_target->dynamic_linker != nullptr); - lj->args.append("-dynamic-linker"); - lj->args.append(g->zig_target->dynamic_linker); - } - } - - if (is_dyn_lib) { - Buf *soname = (g->override_soname == nullptr) ? - buf_sprintf("lib%s.so.%" ZIG_PRI_usize, buf_ptr(g->root_out_name), g->version_major) : - g->override_soname; - lj->args.append("-soname"); - lj->args.append(buf_ptr(soname)); - - if (g->version_script_path != nullptr) { - lj->args.append("-version-script"); - lj->args.append(buf_ptr(g->version_script_path)); - } - } - - // .o files - for (size_t i = 0; i < g->link_objects.length; i += 1) { - lj->args.append((const char *)buf_ptr(g->link_objects.at(i))); - } - - if (!g->is_dummy_so && (g->out_type == OutTypeExe || is_dyn_lib)) { - if (g->libc_link_lib == nullptr) { - Buf *libc_a_path = build_c(g, OutTypeLib, lj->build_dep_prog_node); - lj->args.append(buf_ptr(libc_a_path)); - } - - Buf *compiler_rt_o_path = build_compiler_rt(g, OutTypeLib, lj->build_dep_prog_node); - lj->args.append(buf_ptr(compiler_rt_o_path)); - } - - // libraries - for (size_t i = 0; i < g->link_libs_list.length; i += 1) { - LinkLib *link_lib = g->link_libs_list.at(i); - if (buf_eql_str(link_lib->name, "c")) { - // libc is linked specially - continue; - } - if (target_is_libcpp_lib_name(g->zig_target, buf_ptr(link_lib->name))) { - // libc++ is linked specially - continue; - } - if (g->libc == nullptr && target_is_libc_lib_name(g->zig_target, buf_ptr(link_lib->name))) { - // these libraries are always linked below when targeting glibc - continue; - } - Buf *arg; - if (buf_starts_with_str(link_lib->name, "/") || buf_ends_with_str(link_lib->name, ".a") || - buf_ends_with_str(link_lib->name, ".so")) - { - arg = link_lib->name; - } else { - arg = buf_sprintf("-l%s", buf_ptr(link_lib->name)); - } - lj->args.append(buf_ptr(arg)); - } - - // libc++ dep - if (g->libcpp_link_lib != nullptr && g->out_type != OutTypeObj) { - lj->args.append(build_libcxxabi(g, lj->build_dep_prog_node)); - lj->args.append(build_libcxx(g, lj->build_dep_prog_node)); - } - - // libc dep - if (g->libc_link_lib != nullptr && g->out_type != OutTypeObj) { - if (g->libc != nullptr) { - if (!g->have_dynamic_link) { - lj->args.append("--start-group"); - lj->args.append("-lc"); - lj->args.append("-lm"); - lj->args.append("--end-group"); - } else { - lj->args.append("-lc"); - lj->args.append("-lm"); - } - - if (g->zig_target->os == OsFreeBSD || - g->zig_target->os == OsNetBSD) - { - lj->args.append("-lpthread"); - } - } else if (target_is_glibc(g->zig_target)) { - lj->args.append(build_libunwind(g, lj->build_dep_prog_node)); - add_glibc_libs(lj); - lj->args.append(get_libc_crt_file(g, "libc_nonshared.a", lj->build_dep_prog_node)); - } else if (target_is_musl(g->zig_target)) { - lj->args.append(build_libunwind(g, lj->build_dep_prog_node)); - lj->args.append(build_musl(g, lj->build_dep_prog_node)); - } else if (g->libcpp_link_lib != nullptr) { - lj->args.append(build_libunwind(g, lj->build_dep_prog_node)); - } else { - zig_unreachable(); - } - } - - // crt end - if (lj->link_in_crt) { - if (target_is_android(g->zig_target)) { - lj->args.append(get_libc_crt_file(g, "crtend_android.o", lj->build_dep_prog_node)); - } else if (target_libc_needs_crti_crtn(g->zig_target)) { - lj->args.append(get_libc_crt_file(g, "crtn.o", lj->build_dep_prog_node)); - } - } - - switch (g->linker_allow_shlib_undefined) { - case OptionalBoolNull: - if (!g->zig_target->is_native_os) { - lj->args.append("--allow-shlib-undefined"); - } - break; - case OptionalBoolFalse: - break; - case OptionalBoolTrue: - lj->args.append("--allow-shlib-undefined"); - break; - } - switch (g->linker_bind_global_refs_locally) { - case OptionalBoolNull: - case OptionalBoolFalse: - break; - case OptionalBoolTrue: - lj->args.append("-Bsymbolic"); - break; - } -} - -static void construct_linker_job_wasm(LinkJob *lj) { - CodeGen *g = lj->codegen; - - lj->args.append("-error-limit=0"); - // Increase the default stack size to a more reasonable value of 1MB instead of - // the default of 1 Wasm page being 64KB, unless overriden by the user. - size_t stack_size = (g->stack_size_override == 0) ? 1048576 : g->stack_size_override; - lj->args.append("-z"); - lj->args.append(buf_ptr(buf_sprintf("stack-size=%" ZIG_PRI_usize, stack_size))); - - // put stack before globals so that stack overflow results in segfault immediately before corrupting globals - // see https://github.com/ziglang/zig/issues/4496 - lj->args.append("--stack-first"); - - if (g->out_type != OutTypeExe) { - lj->args.append("--no-entry"); // So lld doesn't look for _start. - - // If there are any C source files we cannot rely on individual exports. - if (g->c_source_files.length != 0) { - lj->args.append("--export-all"); - } else { - auto export_it = g->exported_symbol_names.entry_iterator(); - decltype(g->exported_symbol_names)::Entry *curr_entry = nullptr; - while ((curr_entry = export_it.next()) != nullptr) { - Buf *arg = buf_sprintf("--export=%s", buf_ptr(curr_entry->key)); - lj->args.append(buf_ptr(arg)); - } - } - } - lj->args.append("--allow-undefined"); - lj->args.append("-o"); - lj->args.append(buf_ptr(&g->bin_file_output_path)); - - // .o files - for (size_t i = 0; i < g->link_objects.length; i += 1) { - lj->args.append((const char *)buf_ptr(g->link_objects.at(i))); - } - - if (g->out_type != OutTypeObj) { - Buf *libc_o_path = build_c(g, OutTypeObj, lj->build_dep_prog_node); - lj->args.append(buf_ptr(libc_o_path)); - - Buf *compiler_rt_o_path = build_compiler_rt(g, OutTypeObj, lj->build_dep_prog_node); - lj->args.append(buf_ptr(compiler_rt_o_path)); - } -} - -static void coff_append_machine_arg(CodeGen *g, ZigList *list) { - if (g->zig_target->arch == ZigLLVM_x86) { - list->append("-MACHINE:X86"); - } else if (g->zig_target->arch == ZigLLVM_x86_64) { - list->append("-MACHINE:X64"); - } else if (target_is_arm(g->zig_target)) { - if (target_arch_pointer_bit_width(g->zig_target->arch) == 32) { - list->append("-MACHINE:ARM"); - } else { - list->append("-MACHINE:ARM64"); - } - } -} - -static void link_diag_callback(void *context, const char *ptr, size_t len) { - Buf *diag = reinterpret_cast(context); - buf_append_mem(diag, ptr, len); -} - -static bool zig_lld_link(ZigLLVM_ObjectFormatType oformat, const char **args, size_t arg_count, - Buf *diag) -{ - Buf *stdout_diag = buf_alloc(); - buf_resize(diag, 0); - bool result = ZigLLDLink(oformat, args, arg_count, link_diag_callback, stdout_diag, diag); - buf_destroy(stdout_diag); - return result; -} - -static void add_uefi_link_args(LinkJob *lj) { - lj->args.append("-BASE:0"); - lj->args.append("-ENTRY:EfiMain"); - lj->args.append("-OPT:REF"); - lj->args.append("-SAFESEH:NO"); - lj->args.append("-MERGE:.rdata=.data"); - lj->args.append("-ALIGN:32"); - lj->args.append("-NODEFAULTLIB"); - lj->args.append("-SECTION:.xdata,D"); -} - -static void add_msvc_link_args(LinkJob *lj, bool is_library) { - CodeGen *g = lj->codegen; - - bool is_dynamic = g->is_dynamic; - const char *lib_str = is_dynamic ? "" : "lib"; - const char *d_str = (g->build_mode == BuildModeDebug) ? "d" : ""; - - if (!is_dynamic) { - Buf *cmt_lib_name = buf_sprintf("libcmt%s.lib", d_str); - lj->args.append(buf_ptr(cmt_lib_name)); - } else { - Buf *msvcrt_lib_name = buf_sprintf("msvcrt%s.lib", d_str); - lj->args.append(buf_ptr(msvcrt_lib_name)); - } - - Buf *vcruntime_lib_name = buf_sprintf("%svcruntime%s.lib", lib_str, d_str); - lj->args.append(buf_ptr(vcruntime_lib_name)); - - Buf *crt_lib_name = buf_sprintf("%sucrt%s.lib", lib_str, d_str); - lj->args.append(buf_ptr(crt_lib_name)); - - //Visual C++ 2015 Conformance Changes - //https://msdn.microsoft.com/en-us/library/bb531344.aspx - lj->args.append("legacy_stdio_definitions.lib"); - - // msvcrt depends on kernel32 and ntdll - lj->args.append("kernel32.lib"); - lj->args.append("ntdll.lib"); -} - -static void print_zig_cc_cmd(ZigList *args) { - for (size_t arg_i = 0; arg_i < args->length; arg_i += 1) { - const char *space_str = (arg_i == 0) ? "" : " "; - fprintf(stderr, "%s%s", space_str, args->at(arg_i)); - } - fprintf(stderr, "\n"); -} - -static const char *get_def_lib(CodeGen *parent, const char *name, Buf *def_in_file) { - Error err; - - Buf *self_exe_path = buf_alloc(); - if ((err = os_self_exe_path(self_exe_path))) { - fprintf(stderr, "Unable to get self exe path: %s\n", err_str(err)); - exit(1); - } - Buf *compiler_id; - if ((err = get_compiler_id(&compiler_id))) { - fprintf(stderr, "Unable to get compiler id: %s\n", err_str(err)); - exit(1); - } - - Buf *cache_dir = get_global_cache_dir(); - Buf *o_dir = buf_sprintf("%s" OS_SEP CACHE_OUT_SUBDIR, buf_ptr(cache_dir)); - Buf *manifest_dir = buf_sprintf("%s" OS_SEP CACHE_HASH_SUBDIR, buf_ptr(cache_dir)); - - Buf *def_include_dir = buf_sprintf("%s" OS_SEP "libc" OS_SEP "mingw" OS_SEP "def-include", - buf_ptr(parent->zig_lib_dir)); - - CacheHash *cache_hash = heap::c_allocator.create(); - cache_init(cache_hash, manifest_dir); - - cache_buf(cache_hash, compiler_id); - cache_file(cache_hash, def_in_file); - cache_buf(cache_hash, def_include_dir); - cache_int(cache_hash, parent->zig_target->arch); - - Buf digest = BUF_INIT; - buf_resize(&digest, 0); - if ((err = cache_hit(cache_hash, &digest))) { - if (err != ErrorInvalidFormat) { - if (err == ErrorCacheUnavailable) { - // already printed error - } else { - fprintf(stderr, "unable to check cache when processing .def.in file: %s\n", err_str(err)); - } - exit(1); - } - } - - Buf *artifact_dir; - Buf *lib_final_path; - Buf *final_lib_basename = buf_sprintf("%s.lib", name); - - bool is_cache_miss = (buf_len(&digest) == 0); - if (is_cache_miss) { - if ((err = cache_final(cache_hash, &digest))) { - fprintf(stderr, "Unable to finalize cache hash: %s\n", err_str(err)); - exit(1); - } - artifact_dir = buf_alloc(); - os_path_join(o_dir, &digest, artifact_dir); - if ((err = os_make_path(artifact_dir))) { - fprintf(stderr, "Unable to create output directory '%s': %s", - buf_ptr(artifact_dir), err_str(err)); - exit(1); - } - Buf *final_def_basename = buf_sprintf("%s.def", name); - Buf *def_final_path = buf_alloc(); - os_path_join(artifact_dir, final_def_basename, def_final_path); - - ZigList args = {}; - args.append(buf_ptr(self_exe_path)); - args.append("clang"); - args.append("-x"); - args.append("c"); - args.append(buf_ptr(def_in_file)); - args.append("-Wp,-w"); - args.append("-undef"); - args.append("-P"); - args.append("-I"); - args.append(buf_ptr(def_include_dir)); - if (target_is_arm(parent->zig_target)) { - if (target_arch_pointer_bit_width(parent->zig_target->arch) == 32) { - args.append("-DDEF_ARM32"); - } else { - args.append("-DDEF_ARM64"); - } - } else if (parent->zig_target->arch == ZigLLVM_x86) { - args.append("-DDEF_I386"); - } else if (parent->zig_target->arch == ZigLLVM_x86_64) { - args.append("-DDEF_X64"); - } else { - zig_unreachable(); - } - args.append("-E"); - args.append("-o"); - args.append(buf_ptr(def_final_path)); - - if (parent->verbose_cc) { - print_zig_cc_cmd(&args); - } - Termination term; - os_spawn_process(args, &term); - if (term.how != TerminationIdClean || term.code != 0) { - fprintf(stderr, "\nThe following command failed:\n"); - print_zig_cc_cmd(&args); - exit(1); - } - - lib_final_path = buf_alloc(); - os_path_join(artifact_dir, final_lib_basename, lib_final_path); - - if (ZigLLVMWriteImportLibrary(buf_ptr(def_final_path), - parent->zig_target->arch, - buf_ptr(lib_final_path), - /* kill_at */ true)) - { - zig_panic("link: could not emit %s", buf_ptr(lib_final_path)); - } - } else { - // cache hit - artifact_dir = buf_alloc(); - os_path_join(o_dir, &digest, artifact_dir); - lib_final_path = buf_alloc(); - os_path_join(artifact_dir, final_lib_basename, lib_final_path); - } - parent->caches_to_release.append(cache_hash); - - return buf_ptr(lib_final_path); -} - -static bool is_linking_system_lib(CodeGen *g, const char *name) { - for (size_t lib_i = 0; lib_i < g->link_libs_list.length; lib_i += 1) { - LinkLib *link_lib = g->link_libs_list.at(lib_i); - if (buf_eql_str(link_lib->name, name)) { - return true; - } - } - return false; -} - -static Error find_mingw_lib_def(LinkJob *lj, const char *name, Buf *out_path) { - CodeGen *g = lj->codegen; - Buf override_path = BUF_INIT; - Error err; - - char const *lib_path = nullptr; - if (g->zig_target->arch == ZigLLVM_x86) { - lib_path = "lib32"; - } else if (g->zig_target->arch == ZigLLVM_x86_64) { - lib_path = "lib64"; - } else if (target_is_arm(g->zig_target)) { - const bool is_32 = target_arch_pointer_bit_width(g->zig_target->arch) == 32; - lib_path = is_32 ? "libarm32" : "libarm64"; - } else { - zig_unreachable(); - } - - // Try the archtecture-specific path first - buf_resize(&override_path, 0); - buf_appendf(&override_path, "%s" OS_SEP "libc" OS_SEP "mingw" OS_SEP "%s" OS_SEP "%s.def", buf_ptr(g->zig_lib_dir), lib_path, name); - - bool does_exist; - if ((err = os_file_exists(&override_path, &does_exist)) != ErrorNone) { - return err; - } - - if (!does_exist) { - // Try the generic version - buf_resize(&override_path, 0); - buf_appendf(&override_path, "%s" OS_SEP "libc" OS_SEP "mingw" OS_SEP "lib-common" OS_SEP "%s.def", buf_ptr(g->zig_lib_dir), name); - - if ((err = os_file_exists(&override_path, &does_exist)) != ErrorNone) { - return err; - } - } - - if (!does_exist) { - // Try the generic version and preprocess it - buf_resize(&override_path, 0); - buf_appendf(&override_path, "%s" OS_SEP "libc" OS_SEP "mingw" OS_SEP "lib-common" OS_SEP "%s.def.in", buf_ptr(g->zig_lib_dir), name); - - if ((err = os_file_exists(&override_path, &does_exist)) != ErrorNone) { - return err; - } - } - - if (!does_exist) { - return ErrorFileNotFound; - } - - buf_init_from_buf(out_path, &override_path); - return ErrorNone; -} - -static void add_mingw_link_args(LinkJob *lj, bool is_library) { - CodeGen *g = lj->codegen; - - lj->args.append("-lldmingw"); - - bool is_dll = g->out_type == OutTypeLib && g->is_dynamic; - - if (g->zig_target->arch == ZigLLVM_x86) { - lj->args.append("-ALTERNATENAME:__image_base__=___ImageBase"); - } else { - lj->args.append("-ALTERNATENAME:__image_base__=__ImageBase"); - } - - if (is_dll) { - lj->args.append(get_libc_crt_file(g, "dllcrt2.o", lj->build_dep_prog_node)); - } else { - lj->args.append(get_libc_crt_file(g, "crt2.o", lj->build_dep_prog_node)); - } - - lj->args.append(get_libc_crt_file(g, "mingw32.lib", lj->build_dep_prog_node)); - lj->args.append(get_libc_crt_file(g, "mingwex.lib", lj->build_dep_prog_node)); - lj->args.append(get_libc_crt_file(g, "msvcrt-os.lib", lj->build_dep_prog_node)); - - for (size_t def_i = 0; def_i < array_length(mingw_def_list); def_i += 1) { - const char *name = mingw_def_list[def_i].name; - const bool always_link = mingw_def_list[def_i].always_link; - - if (always_link || is_linking_system_lib(g, name)) { - Buf lib_path = BUF_INIT; - Error err = find_mingw_lib_def(lj, name, &lib_path); - - if (err == ErrorFileNotFound) { - zig_panic("link: could not find .def file to build %s\n", name); - } else if (err != ErrorNone) { - zig_panic("link: unable to check if .def file for %s exists: %s", - name, err_str(err)); - } - - lj->args.append(get_def_lib(g, name, &lib_path)); - } - } -} - -static void add_win_link_args(LinkJob *lj, bool is_library, bool *have_windows_dll_import_libs) { - if (lj->link_in_crt) { - if (target_abi_is_gnu(lj->codegen->zig_target->abi)) { - *have_windows_dll_import_libs = true; - add_mingw_link_args(lj, is_library); - } else { - add_msvc_link_args(lj, is_library); - } - } else { - lj->args.append("-NODEFAULTLIB"); - if (!is_library) { - if (lj->codegen->have_winmain) { - lj->args.append("-ENTRY:WinMain"); - } else if (lj->codegen->have_wwinmain) { - lj->args.append("-ENTRY:wWinMain"); - } else if (lj->codegen->have_wwinmain_crt_startup) { - lj->args.append("-ENTRY:wWinMainCRTStartup"); - } else { - lj->args.append("-ENTRY:WinMainCRTStartup"); - } - } - } -} - -static bool is_mingw_link_lib(Buf *name) { - for (size_t def_i = 0; def_i < array_length(mingw_def_list); def_i += 1) { - if (buf_eql_str_ignore_case(name, mingw_def_list[def_i].name)) { - return true; - } - } - return false; -} -static void construct_linker_job_coff(LinkJob *lj) { - Error err; - CodeGen *g = lj->codegen; - - lj->args.append("-ERRORLIMIT:0"); - - lj->args.append("-NOLOGO"); - - if (!g->strip_debug_symbols) { - lj->args.append("-DEBUG"); - } - - if (g->out_type == OutTypeExe) { - // TODO compile time stack upper bound detection - size_t stack_size = (g->stack_size_override == 0) ? 16777216 : g->stack_size_override; - lj->args.append(buf_ptr(buf_sprintf("-STACK:%" ZIG_PRI_usize, stack_size))); - } - - coff_append_machine_arg(g, &lj->args); - - bool is_library = g->out_type == OutTypeLib; - if (is_library && g->is_dynamic) { - lj->args.append("-DLL"); - } - - lj->args.append(buf_ptr(buf_sprintf("-OUT:%s", buf_ptr(&g->bin_file_output_path)))); - - if (g->libc_link_lib != nullptr && g->libc != nullptr) { - Buf *buff0 = buf_create_from_str("-LIBPATH:"); - buf_append_mem(buff0, g->libc->crt_dir, g->libc->crt_dir_len); - lj->args.append(buf_ptr(buff0)); - - if (target_abi_is_gnu(g->zig_target->abi)) { - Buf *buff1 = buf_create_from_str("-LIBPATH:"); - buf_append_mem(buff1, g->libc->sys_include_dir, g->libc->sys_include_dir_len); - lj->args.append(buf_ptr(buff1)); - - Buf *buff2 = buf_create_from_str("-LIBPATH:"); - buf_append_mem(buff2, g->libc->include_dir, g->libc->include_dir_len); - lj->args.append(buf_ptr(buff2)); - } else { - Buf *buff1 = buf_create_from_str("-LIBPATH:"); - buf_append_mem(buff1, g->libc->msvc_lib_dir, g->libc->msvc_lib_dir_len); - lj->args.append(buf_ptr(buff1)); - - Buf *buff2 = buf_create_from_str("-LIBPATH:"); - buf_append_mem(buff2, g->libc->kernel32_lib_dir, g->libc->kernel32_lib_dir_len); - lj->args.append(buf_ptr(buff2)); - } - } - - for (size_t i = 0; i < g->lib_dirs.length; i += 1) { - const char *lib_dir = g->lib_dirs.at(i); - lj->args.append(buf_ptr(buf_sprintf("-LIBPATH:%s", lib_dir))); - } - - for (size_t i = 0; i < g->link_objects.length; i += 1) { - lj->args.append((const char *)buf_ptr(g->link_objects.at(i))); - } - - bool have_windows_dll_import_libs = false; - switch (detect_subsystem(g)) { - case TargetSubsystemAuto: - if (g->zig_target->os == OsUefi) { - add_uefi_link_args(lj); - } else { - add_win_link_args(lj, is_library, &have_windows_dll_import_libs); - } - break; - case TargetSubsystemConsole: - lj->args.append("-SUBSYSTEM:console"); - add_win_link_args(lj, is_library, &have_windows_dll_import_libs); - break; - case TargetSubsystemEfiApplication: - lj->args.append("-SUBSYSTEM:efi_application"); - add_uefi_link_args(lj); - break; - case TargetSubsystemEfiBootServiceDriver: - lj->args.append("-SUBSYSTEM:efi_boot_service_driver"); - add_uefi_link_args(lj); - break; - case TargetSubsystemEfiRom: - lj->args.append("-SUBSYSTEM:efi_rom"); - add_uefi_link_args(lj); - break; - case TargetSubsystemEfiRuntimeDriver: - lj->args.append("-SUBSYSTEM:efi_runtime_driver"); - add_uefi_link_args(lj); - break; - case TargetSubsystemNative: - lj->args.append("-SUBSYSTEM:native"); - add_win_link_args(lj, is_library, &have_windows_dll_import_libs); - break; - case TargetSubsystemPosix: - lj->args.append("-SUBSYSTEM:posix"); - add_win_link_args(lj, is_library, &have_windows_dll_import_libs); - break; - case TargetSubsystemWindows: - lj->args.append("-SUBSYSTEM:windows"); - add_win_link_args(lj, is_library, &have_windows_dll_import_libs); - break; - } - - // libc++ dep - if (g->libcpp_link_lib != nullptr && g->out_type != OutTypeObj) { - lj->args.append(build_libcxxabi(g, lj->build_dep_prog_node)); - lj->args.append(build_libcxx(g, lj->build_dep_prog_node)); - lj->args.append(build_libunwind(g, lj->build_dep_prog_node)); - } - - if (g->out_type == OutTypeExe || (g->out_type == OutTypeLib && g->is_dynamic)) { - if (g->libc_link_lib == nullptr && !g->is_dummy_so) { - Buf *libc_a_path = build_c(g, OutTypeLib, lj->build_dep_prog_node); - lj->args.append(buf_ptr(libc_a_path)); - } - - // msvc compiler_rt is missing some stuff, so we still build it and rely on weak linkage - Buf *compiler_rt_o_path = build_compiler_rt(g, OutTypeLib, lj->build_dep_prog_node); - lj->args.append(buf_ptr(compiler_rt_o_path)); - } - - for (size_t lib_i = 0; lib_i < g->link_libs_list.length; lib_i += 1) { - LinkLib *link_lib = g->link_libs_list.at(lib_i); - if (buf_eql_str(link_lib->name, "c")) { - continue; - } - if (target_is_libcpp_lib_name(g->zig_target, buf_ptr(link_lib->name))) { - // libc++ is linked specially - continue; - } - if (g->libc == nullptr && target_is_libc_lib_name(g->zig_target, buf_ptr(link_lib->name))) { - // these libraries are always linked below when targeting glibc - continue; - } - bool is_sys_lib = is_mingw_link_lib(link_lib->name); - if (have_windows_dll_import_libs && is_sys_lib) { - continue; - } - // If we're linking in the CRT or the libs are provided explictly we don't want to generate def/libs - if ((lj->link_in_crt && is_sys_lib) || link_lib->provided_explicitly) { - if (target_abi_is_gnu(lj->codegen->zig_target->abi)) { - if (buf_eql_str(link_lib->name, "uuid")) { - // mingw-w64 provides this lib - lj->args.append(get_libc_crt_file(g, "uuid.lib", lj->build_dep_prog_node)); - } else { - Buf* lib_name = buf_sprintf("lib%s.a", buf_ptr(link_lib->name)); - lj->args.append(buf_ptr(lib_name)); - } - } else { - Buf* lib_name = buf_sprintf("%s.lib", buf_ptr(link_lib->name)); - lj->args.append(buf_ptr(lib_name)); - } - continue; - } - - // This library may be a system one and we may have a suitable .lib file - - // Normalize the library name to lower case, the FS may be - // case-sensitive - char *name = strdup(buf_ptr(link_lib->name)); - assert(name != nullptr); - for (char *ch = name; *ch; ++ch) *ch = tolower(*ch); - - Buf lib_path = BUF_INIT; - err = find_mingw_lib_def(lj, name, &lib_path); - - if (err == ErrorFileNotFound) { - zig_panic("link: could not find .def file to build %s\n", name); - } else if (err != ErrorNone) { - zig_panic("link: unable to check if .def file for %s exists: %s", - name, err_str(err)); - } - - lj->args.append(get_def_lib(g, name, &lib_path)); - - mem::os::free(name); - } -} - -static void construct_linker_job_macho(LinkJob *lj) { - CodeGen *g = lj->codegen; - - lj->args.append("-error-limit"); - lj->args.append("0"); - lj->args.append("-demangle"); - - switch (g->linker_gc_sections) { - case OptionalBoolNull: - // TODO why do we not follow the same logic of elf here? - break; - case OptionalBoolTrue: - lj->args.append("--gc-sections"); - break; - case OptionalBoolFalse: - break; - } - - if (g->linker_rdynamic) { - lj->args.append("-export_dynamic"); - } - - if (g->linker_optimization != nullptr) { - lj->args.append(buf_ptr(g->linker_optimization)); - } - - if (g->linker_z_nodelete) { - lj->args.append("-z"); - lj->args.append("nodelete"); - } - if (g->linker_z_defs) { - lj->args.append("-z"); - lj->args.append("defs"); - } - - bool is_lib = g->out_type == OutTypeLib; - bool is_dyn_lib = g->is_dynamic && is_lib; - if (is_lib && !g->is_dynamic) { - lj->args.append("-static"); - } else { - lj->args.append("-dynamic"); - } - - if (is_dyn_lib) { - lj->args.append("-dylib"); - - Buf *compat_vers = buf_sprintf("%" ZIG_PRI_usize ".0.0", g->version_major); - lj->args.append("-compatibility_version"); - lj->args.append(buf_ptr(compat_vers)); - - Buf *cur_vers = buf_sprintf("%" ZIG_PRI_usize ".%" ZIG_PRI_usize ".%" ZIG_PRI_usize, - g->version_major, g->version_minor, g->version_patch); - lj->args.append("-current_version"); - lj->args.append(buf_ptr(cur_vers)); - - // TODO getting an error when running an executable when doing this rpath thing - //Buf *dylib_install_name = buf_sprintf("@rpath/lib%s.%" ZIG_PRI_usize ".dylib", - // buf_ptr(g->root_out_name), g->version_major); - //lj->args.append("-install_name"); - //lj->args.append(buf_ptr(dylib_install_name)); - - assert(buf_len(&g->bin_file_output_path) != 0); - } - - lj->args.append("-arch"); - lj->args.append(get_darwin_arch_string(g->zig_target)); - - if (g->zig_target->glibc_or_darwin_version != nullptr) { - if (g->zig_target->os == OsMacOSX) { - lj->args.append("-macosx_version_min"); - } else if (g->zig_target->os == OsIOS) { - if (g->zig_target->arch == ZigLLVM_x86 || g->zig_target->arch == ZigLLVM_x86_64) { - lj->args.append("-ios_simulator_version_min"); - } else { - lj->args.append("-iphoneos_version_min"); - } - } - - Buf *version_string = buf_sprintf("%d.%d.%d", - g->zig_target->glibc_or_darwin_version->major, - g->zig_target->glibc_or_darwin_version->minor, - g->zig_target->glibc_or_darwin_version->patch); - lj->args.append(buf_ptr(version_string)); - - lj->args.append("-sdk_version"); - lj->args.append(buf_ptr(version_string)); - } else if (stage2_is_zig0 && g->zig_target->os == OsMacOSX) { - // running `zig0`; `-pie` requires versions >= 10.5; select 10.13 - lj->args.append("-macosx_version_min"); - lj->args.append("10.13"); - lj->args.append("-sdk_version"); - lj->args.append("10.13"); - } - - if (g->out_type == OutTypeExe) { - lj->args.append("-pie"); - } - - lj->args.append("-o"); - lj->args.append(buf_ptr(&g->bin_file_output_path)); - - for (size_t i = 0; i < g->rpath_list.length; i += 1) { - Buf *rpath = g->rpath_list.at(i); - add_rpath(lj, rpath); - } - if (is_dyn_lib) { - add_rpath(lj, &g->bin_file_output_path); - } - - if (is_dyn_lib) { - if (g->system_linker_hack) { - lj->args.append("-headerpad_max_install_names"); - } - } - - for (size_t i = 0; i < g->lib_dirs.length; i += 1) { - const char *lib_dir = g->lib_dirs.at(i); - lj->args.append("-L"); - lj->args.append(lib_dir); - } - - // .o files - for (size_t i = 0; i < g->link_objects.length; i += 1) { - lj->args.append((const char *)buf_ptr(g->link_objects.at(i))); - } - - // compiler_rt on darwin is missing some stuff, so we still build it and rely on LinkOnce - if (g->out_type == OutTypeExe || is_dyn_lib) { - Buf *compiler_rt_o_path = build_compiler_rt(g, OutTypeLib, lj->build_dep_prog_node); - lj->args.append(buf_ptr(compiler_rt_o_path)); - } - - // libraries - for (size_t lib_i = 0; lib_i < g->link_libs_list.length; lib_i += 1) { - LinkLib *link_lib = g->link_libs_list.at(lib_i); - if (buf_eql_str(link_lib->name, "c")) { - // libc is linked specially - continue; - } - if (target_is_libcpp_lib_name(g->zig_target, buf_ptr(link_lib->name))) { - // libc++ is linked specially - continue; - } - if (g->zig_target->is_native_os && target_is_libc_lib_name(g->zig_target, buf_ptr(link_lib->name))) { - // libSystem is linked specially - continue; - } - - Buf *arg; - if (buf_starts_with_str(link_lib->name, "/") || buf_ends_with_str(link_lib->name, ".a") || - buf_ends_with_str(link_lib->name, ".dylib")) - { - arg = link_lib->name; - } else { - arg = buf_sprintf("-l%s", buf_ptr(link_lib->name)); - } - lj->args.append(buf_ptr(arg)); - } - - // libc++ dep - if (g->libcpp_link_lib != nullptr && g->out_type != OutTypeObj) { - lj->args.append(build_libcxxabi(g, lj->build_dep_prog_node)); - lj->args.append(build_libcxx(g, lj->build_dep_prog_node)); - } - - // libc dep - if (g->zig_target->is_native_os || stage2_is_zig0) { - // on Darwin, libSystem has libc in it, but also you have to use it - // to make syscalls because the syscall numbers are not documented - // and change between versions. - // so we always link against libSystem - lj->args.append("-lSystem"); - } - - for (size_t i = 0; i < g->framework_dirs.length; i += 1) { - const char *framework_dir = g->framework_dirs.at(i); - lj->args.append("-F"); - lj->args.append(framework_dir); - } - - for (size_t i = 0; i < g->darwin_frameworks.length; i += 1) { - lj->args.append("-framework"); - lj->args.append(buf_ptr(g->darwin_frameworks.at(i))); - } - - switch (g->linker_allow_shlib_undefined) { - case OptionalBoolNull: - if (!g->zig_target->is_native_os && !stage2_is_zig0) { - // TODO https://github.com/ziglang/zig/issues/5059 - lj->args.append("-undefined"); - lj->args.append("dynamic_lookup"); - } - break; - case OptionalBoolFalse: - break; - case OptionalBoolTrue: - lj->args.append("-undefined"); - lj->args.append("dynamic_lookup"); - break; - } - switch (g->linker_bind_global_refs_locally) { - case OptionalBoolNull: - case OptionalBoolFalse: - break; - case OptionalBoolTrue: - lj->args.append("-Bsymbolic"); - break; - } -} - -static void construct_linker_job(LinkJob *lj) { - switch (target_object_format(lj->codegen->zig_target)) { - case ZigLLVM_UnknownObjectFormat: - case ZigLLVM_XCOFF: - zig_unreachable(); - - case ZigLLVM_COFF: - return construct_linker_job_coff(lj); - case ZigLLVM_ELF: - return construct_linker_job_elf(lj); - case ZigLLVM_MachO: - return construct_linker_job_macho(lj); - case ZigLLVM_Wasm: - return construct_linker_job_wasm(lj); - } -} - -void zig_link_add_compiler_rt(CodeGen *g, Stage2ProgressNode *progress_node) { - Buf *compiler_rt_o_path = build_compiler_rt(g, OutTypeObj, progress_node); - g->link_objects.append(compiler_rt_o_path); -} - -void codegen_link(CodeGen *g) { - codegen_add_time_event(g, "Build Dependencies"); - LinkJob lj = {0}; - - { - const char *progress_name = "Build Dependencies"; - codegen_switch_sub_prog_node(g, stage2_progress_start(g->main_progress_node, - progress_name, strlen(progress_name), 0)); - lj.build_dep_prog_node = g->sub_progress_node; - } - - - // even though we're calling LLD as a library it thinks the first - // argument is its own exe name - lj.args.append("lld"); - - lj.rpath_table.init(4); - lj.codegen = g; - - if (g->out_type == OutTypeObj) { - lj.args.append("-r"); - } - - if (g->out_type == OutTypeLib && !g->is_dynamic && !target_is_wasm(g->zig_target)) { - ZigList file_names = {}; - for (size_t i = 0; i < g->link_objects.length; i += 1) { - file_names.append(buf_ptr(g->link_objects.at(i))); - } - ZigLLVM_OSType os_type = get_llvm_os_type(g->zig_target->os); - codegen_add_time_event(g, "LLVM Link"); - { - const char *progress_name = "Link"; - codegen_switch_sub_prog_node(g, stage2_progress_start(g->main_progress_node, - progress_name, strlen(progress_name), 0)); - } - if (g->verbose_link) { - fprintf(stderr, "ar rcs %s", buf_ptr(&g->bin_file_output_path)); - for (size_t i = 0; i < file_names.length; i += 1) { - fprintf(stderr, " %s", file_names.at(i)); - } - fprintf(stderr, "\n"); - } - if (ZigLLVMWriteArchive(buf_ptr(&g->bin_file_output_path), file_names.items, file_names.length, os_type)) { - fprintf(stderr, "Unable to write archive '%s'\n", buf_ptr(&g->bin_file_output_path)); - exit(1); - } - return; - } - - lj.link_in_crt = (g->libc_link_lib != nullptr && g->out_type == OutTypeExe); - - construct_linker_job(&lj); - - if (g->verbose_link) { - for (size_t i = 0; i < lj.args.length; i += 1) { - const char *space = (i != 0) ? " " : ""; - fprintf(stderr, "%s%s", space, lj.args.at(i)); - } - fprintf(stderr, "\n"); - } - - Buf diag = BUF_INIT; - - codegen_add_time_event(g, "LLVM Link"); - { - const char *progress_name = "Link"; - codegen_switch_sub_prog_node(g, stage2_progress_start(g->main_progress_node, - progress_name, strlen(progress_name), 0)); - } - if (g->system_linker_hack && g->zig_target->os == OsMacOSX) { - Termination term; - ZigList args = {}; - args.append("ld"); - for (size_t i = 1; i < lj.args.length; i += 1) { - args.append(lj.args.at(i)); - } - os_spawn_process(args, &term); - if (term.how != TerminationIdClean || term.code != 0) { - exit(1); - } - } else if (!zig_lld_link(target_object_format(g->zig_target), lj.args.items, lj.args.length, &diag)) { - fprintf(stderr, "%s\n", buf_ptr(&diag)); - exit(1); - } -} - diff --git a/src/main.cpp b/src/main.cpp deleted file mode 100644 index 003ba6b7c6..0000000000 --- a/src/main.cpp +++ /dev/null @@ -1,1474 +0,0 @@ -/* - * Copyright (c) 2015 Andrew Kelley - * - * This file is part of zig, which is MIT licensed. - * See http://opensource.org/licenses/MIT - */ - -#include "ast_render.hpp" -#include "buffer.hpp" -#include "codegen.hpp" -#include "compiler.hpp" -#include "config.h" -#include "error.hpp" -#include "heap.hpp" -#include "os.hpp" -#include "target.hpp" -#include "stage2.h" -#include "glibc.hpp" -#include "dump_analysis.hpp" -#include "mem_profile.hpp" - -#include - -static int print_error_usage(const char *arg0) { - fprintf(stderr, "See `%s --help` for detailed usage information\n", arg0); - return EXIT_FAILURE; -} - -static int print_full_usage(const char *arg0, FILE *file, int return_code) { - fprintf(file, - "Usage: %s [command] [options]\n" - "\n" - "Commands:\n" - " build build project from build.zig\n" - " build-exe [source] create executable from source or object files\n" - " build-lib [source] create library from source or object files\n" - " build-obj [source] create object from source or assembly\n" - " builtin show the source code of @import(\"builtin\")\n" - " cc use Zig as a drop-in C compiler\n" - " c++ use Zig as a drop-in C++ compiler\n" - " env print lib path, std path, compiler id and version\n" - " fmt parse files and render in canonical zig format\n" - " id print the base64-encoded compiler id\n" - " init-exe initialize a `zig build` application in the cwd\n" - " init-lib initialize a `zig build` library in the cwd\n" - " libc [paths_file] Display native libc paths file or validate one\n" - " run [source] [-- [args]] create executable and run immediately\n" - " translate-c [source] convert c code to zig code\n" - " targets list available compilation targets\n" - " test [source] create and run a test build\n" - " version print version number and exit\n" - " zen print zen of zig and exit\n" - "\n" - "Compile Options:\n" - " --c-source [options] [file] compile C source code\n" - " --cache-dir [path] override the local cache directory\n" - " --cache [auto|off|on] build in cache, print output path to stdout\n" - " --color [auto|off|on] enable or disable colored error messages\n" - " --disable-valgrind omit valgrind client requests in debug builds\n" - " --eh-frame-hdr enable C++ exception handling by passing --eh-frame-hdr to linker\n" - " --enable-valgrind include valgrind client requests release builds\n" - " -fstack-check enable stack probing in unsafe builds\n" - " -fno-stack-check disable stack probing in safe builds\n" - " -fsanitize-c enable C undefined behavior detection in unsafe builds\n" - " -fno-sanitize-c disable C undefined behavior detection in safe builds\n" - " --emit [asm|bin|llvm-ir] (deprecated) emit a specific file format as compilation output\n" - " -fPIC enable Position Independent Code\n" - " -fno-PIC disable Position Independent Code\n" - " -ftime-report print timing diagnostics\n" - " -fstack-report print stack size diagnostics\n" - " -fmem-report print memory usage diagnostics\n" - " -fdump-analysis write analysis.json file with type information\n" - " -femit-docs create a docs/ dir with html documentation\n" - " -fno-emit-docs do not produce docs/ dir with html documentation\n" - " -femit-bin (default) output machine code\n" - " -fno-emit-bin do not output machine code\n" - " -femit-asm output .s (assembly code)\n" - " -fno-emit-asm (default) do not output .s (assembly code)\n" - " -femit-llvm-ir produce a .ll file with LLVM IR\n" - " -fno-emit-llvm-ir (default) do not produce a .ll file with LLVM IR\n" - " -femit-h generate a C header file (.h)\n" - " -fno-emit-h (default) do not generate a C header file (.h)\n" - " --libc [file] Provide a file which specifies libc paths\n" - " --name [name] override output name\n" - " --output-dir [dir] override output directory (defaults to cwd)\n" - " --pkg-begin [name] [path] make pkg available to import and push current pkg\n" - " --pkg-end pop current pkg\n" - " --main-pkg-path set the directory of the root package\n" - " --release-fast build with optimizations on and safety off\n" - " --release-safe build with optimizations on and safety on\n" - " --release-small build with size optimizations on and safety off\n" - " --single-threaded source may assume it is only used single-threaded\n" - " -dynamic create a shared library (.so; .dll; .dylib)\n" - " --strip exclude debug symbols\n" - " -target [name] -- see the targets command\n" - " --verbose-tokenize enable compiler debug output for tokenization\n" - " --verbose-ast enable compiler debug output for AST parsing\n" - " --verbose-link enable compiler debug output for linking\n" - " --verbose-ir enable compiler debug output for Zig IR\n" - " --verbose-llvm-ir enable compiler debug output for LLVM IR\n" - " --verbose-cimport enable compiler debug output for C imports\n" - " --verbose-cc enable compiler debug output for C compilation\n" - " --verbose-llvm-cpu-features enable compiler debug output for LLVM CPU features\n" - " -dirafter [dir] add directory to AFTER include search path\n" - " -isystem [dir] add directory to SYSTEM include search path\n" - " -I[dir] add directory to include search path\n" - " -mllvm [arg] (unsupported) forward an arg to LLVM's option processing\n" - " --override-lib-dir [arg] override path to Zig lib directory\n" - " -ffunction-sections places each function in a separate section\n" - " -D[macro]=[value] define C [macro] to [value] (1 if [value] omitted)\n" - " -mcpu [cpu] specify target CPU and feature set\n" - " -code-model [default|tiny| set target code model\n" - " small|kernel|\n" - " medium|large]\n" - "\n" - "Link Options:\n" - " --bundle-compiler-rt for static libraries, include compiler-rt symbols\n" - " --dynamic-linker [path] set the path to ld.so\n" - " --each-lib-rpath add rpath for each used dynamic library\n" - " --library [lib] link against lib\n" - " --forbid-library [lib] make it an error to link against lib\n" - " --library-path [dir] add a directory to the library search path\n" - " --linker-script [path] use a custom linker script\n" - " --version-script [path] provide a version .map file\n" - " --object [obj] add object file to build\n" - " -L[dir] alias for --library-path\n" - " -l[lib] alias for --library\n" - " -rdynamic add all symbols to the dynamic symbol table\n" - " -rpath [path] add directory to the runtime library search path\n" - " --stack [size] (linux, windows, Wasm) override default stack size\n" - " --subsystem [subsystem] (windows) /SUBSYSTEM: to the linker\n" - " -F[dir] (darwin) add search path for frameworks\n" - " -framework [name] (darwin) link against framework\n" - " --ver-major [ver] dynamic library semver major version\n" - " --ver-minor [ver] dynamic library semver minor version\n" - " --ver-patch [ver] dynamic library semver patch version\n" - " -Bsymbolic bind global references locally\n" - "\n" - "Test Options:\n" - " --test-filter [text] skip tests that do not match filter\n" - " --test-name-prefix [text] add prefix to all tests\n" - " --test-cmd [arg] specify test execution command one arg at a time\n" - " --test-cmd-bin appends test binary path to test cmd args\n" - " --test-evented-io runs the test in evented I/O mode\n" - , arg0); - return return_code; -} - -static int print_libc_usage(const char *arg0, FILE *file, int return_code) { - fprintf(file, - "Usage: %s libc\n" - "\n" - "Detect the native libc installation and print the resulting paths to stdout.\n" - "You can save this into a file and then edit the paths to create a cross\n" - "compilation libc kit. Then you can pass `--libc [file]` for Zig to use it.\n" - "\n" - "When compiling natively and no `--libc` argument provided, Zig will create\n" - "`%s/native_libc.txt`\n" - "so that it does not have to detect libc on every invocation. You can remove\n" - "this file to have Zig re-detect the native libc.\n" - "\n\n" - "Usage: %s libc [file]\n" - "\n" - "Parse a libc installation text file and validate it.\n" - , arg0, buf_ptr(get_global_cache_dir()), arg0); - return return_code; -} - -enum Cmd { - CmdNone, - CmdBuild, - CmdBuiltin, - CmdRun, - CmdTargets, - CmdTest, - CmdTranslateC, - CmdVersion, - CmdZen, - CmdLibC, -}; - -static const char *default_zig_cache_name = "zig-cache"; - -struct CliPkg { - const char *name; - const char *path; - ZigList children; - CliPkg *parent; -}; - -static void add_package(CodeGen *g, CliPkg *cli_pkg, ZigPackage *pkg) { - for (size_t i = 0; i < cli_pkg->children.length; i += 1) { - CliPkg *child_cli_pkg = cli_pkg->children.at(i); - - Buf *dirname = buf_alloc(); - Buf *basename = buf_alloc(); - os_path_split(buf_create_from_str(child_cli_pkg->path), dirname, basename); - - ZigPackage *child_pkg = codegen_create_package(g, buf_ptr(dirname), buf_ptr(basename), - buf_ptr(buf_sprintf("%s.%s", buf_ptr(&pkg->pkg_path), child_cli_pkg->name))); - auto entry = pkg->package_table.put_unique(buf_create_from_str(child_cli_pkg->name), child_pkg); - if (entry) { - ZigPackage *existing_pkg = entry->value; - Buf *full_path = buf_alloc(); - os_path_join(&existing_pkg->root_src_dir, &existing_pkg->root_src_path, full_path); - fprintf(stderr, "Unable to add package '%s'->'%s': already exists as '%s'\n", - child_cli_pkg->name, child_cli_pkg->path, buf_ptr(full_path)); - exit(EXIT_FAILURE); - } - - add_package(g, child_cli_pkg, child_pkg); - } -} - -enum CacheOpt { - CacheOptAuto, - CacheOptOn, - CacheOptOff, -}; - -static bool get_cache_opt(CacheOpt opt, bool default_value) { - switch (opt) { - case CacheOptAuto: - return default_value; - case CacheOptOn: - return true; - case CacheOptOff: - return false; - } - zig_unreachable(); -} - -static int zig_error_no_build_file(void) { - fprintf(stderr, - "No 'build.zig' file found, in the current directory or any parent directories.\n" - "Initialize a 'build.zig' template file with `zig init-lib` or `zig init-exe`,\n" - "or see `zig --help` for more options.\n" - ); - return EXIT_FAILURE; -} - -static bool str_starts_with(const char *s1, const char *s2) { - size_t s2_len = strlen(s2); - if (strlen(s1) < s2_len) { - return false; - } - return memcmp(s1, s2, s2_len) == 0; -} - -extern "C" int ZigClang_main(int argc, char **argv); - -#ifdef ZIG_ENABLE_MEM_PROFILE -bool mem_report = false; -#endif - -int main_exit(Stage2ProgressNode *root_progress_node, int exit_code) { - if (root_progress_node != nullptr) { - stage2_progress_end(root_progress_node); - } - return exit_code; -} - -static int main0(int argc, char **argv) { - char *arg0 = argv[0]; - Error err; - - if (argc >= 2 && (strcmp(argv[1], "clang") == 0 || - strcmp(argv[1], "-cc1") == 0 || strcmp(argv[1], "-cc1as") == 0)) - { - return ZigClang_main(argc, argv); - } - - if (argc == 2 && strcmp(argv[1], "id") == 0) { - Buf *compiler_id; - if ((err = get_compiler_id(&compiler_id))) { - fprintf(stderr, "Unable to determine compiler id: %s\n", err_str(err)); - return EXIT_FAILURE; - } - printf("%s\n", buf_ptr(compiler_id)); - return EXIT_SUCCESS; - } - - enum InitKind { - InitKindNone, - InitKindExe, - InitKindLib, - }; - InitKind init_kind = InitKindNone; - if (argc >= 2) { - const char *init_cmd = argv[1]; - if (strcmp(init_cmd, "init-exe") == 0) { - init_kind = InitKindExe; - } else if (strcmp(init_cmd, "init-lib") == 0) { - init_kind = InitKindLib; - } - if (init_kind != InitKindNone) { - if (argc >= 3) { - fprintf(stderr, "Unexpected extra argument: %s\n", argv[2]); - return print_error_usage(arg0); - } - Buf *cmd_template_path = buf_alloc(); - os_path_join(get_zig_special_dir(get_zig_lib_dir()), buf_create_from_str(init_cmd), cmd_template_path); - Buf *build_zig_path = buf_alloc(); - os_path_join(cmd_template_path, buf_create_from_str("build.zig"), build_zig_path); - Buf *src_dir_path = buf_alloc(); - os_path_join(cmd_template_path, buf_create_from_str("src"), src_dir_path); - Buf *main_zig_path = buf_alloc(); - os_path_join(src_dir_path, buf_create_from_str("main.zig"), main_zig_path); - - Buf *cwd = buf_alloc(); - if ((err = os_get_cwd(cwd))) { - fprintf(stderr, "Unable to get cwd: %s\n", err_str(err)); - return EXIT_FAILURE; - } - Buf *cwd_basename = buf_alloc(); - os_path_split(cwd, nullptr, cwd_basename); - - Buf *build_zig_contents = buf_alloc(); - if ((err = os_fetch_file_path(build_zig_path, build_zig_contents))) { - fprintf(stderr, "Unable to read %s: %s\n", buf_ptr(build_zig_path), err_str(err)); - return EXIT_FAILURE; - } - Buf *modified_build_zig_contents = buf_alloc(); - for (size_t i = 0; i < buf_len(build_zig_contents); i += 1) { - char c = buf_ptr(build_zig_contents)[i]; - if (c == '$') { - buf_append_buf(modified_build_zig_contents, cwd_basename); - } else { - buf_append_char(modified_build_zig_contents, c); - } - } - - Buf *main_zig_contents = buf_alloc(); - if ((err = os_fetch_file_path(main_zig_path, main_zig_contents))) { - fprintf(stderr, "Unable to read %s: %s\n", buf_ptr(main_zig_path), err_str(err)); - return EXIT_FAILURE; - } - - Buf *out_build_zig_path = buf_create_from_str("build.zig"); - Buf *out_src_dir_path = buf_create_from_str("src"); - Buf *out_main_zig_path = buf_alloc(); - os_path_join(out_src_dir_path, buf_create_from_str("main.zig"), out_main_zig_path); - - bool already_exists; - if ((err = os_file_exists(out_build_zig_path, &already_exists))) { - fprintf(stderr, "Unable test existence of %s: %s\n", buf_ptr(out_build_zig_path), err_str(err)); - return EXIT_FAILURE; - } - if (already_exists) { - fprintf(stderr, "This file would be overwritten: %s\n", buf_ptr(out_build_zig_path)); - return EXIT_FAILURE; - } - - if ((err = os_make_dir(out_src_dir_path))) { - fprintf(stderr, "Unable to make directory: %s: %s\n", buf_ptr(out_src_dir_path), err_str(err)); - return EXIT_FAILURE; - } - if ((err = os_write_file(out_build_zig_path, modified_build_zig_contents))) { - fprintf(stderr, "Unable to write file: %s: %s\n", buf_ptr(out_build_zig_path), err_str(err)); - return EXIT_FAILURE; - } - if ((err = os_write_file(out_main_zig_path, main_zig_contents))) { - fprintf(stderr, "Unable to write file: %s: %s\n", buf_ptr(out_main_zig_path), err_str(err)); - return EXIT_FAILURE; - } - fprintf(stderr, "Created %s\n", buf_ptr(out_build_zig_path)); - fprintf(stderr, "Created %s\n", buf_ptr(out_main_zig_path)); - if (init_kind == InitKindExe) { - fprintf(stderr, "\nNext, try `zig build --help` or `zig build run`\n"); - } else if (init_kind == InitKindLib) { - fprintf(stderr, "\nNext, try `zig build --help` or `zig build test`\n"); - } else { - zig_unreachable(); - } - - return EXIT_SUCCESS; - } - } - - Cmd cmd = CmdNone; - const char *in_file = nullptr; - Buf *output_dir = nullptr; - bool strip = false; - bool is_dynamic = false; - OutType out_type = OutTypeUnknown; - const char *out_name = nullptr; - bool verbose_tokenize = false; - bool verbose_ast = false; - bool verbose_link = false; - bool verbose_ir = false; - bool verbose_llvm_ir = false; - bool verbose_cimport = false; - bool verbose_cc = false; - bool verbose_llvm_cpu_features = false; - bool link_eh_frame_hdr = false; - ErrColor color = ErrColorAuto; - CacheOpt enable_cache = CacheOptAuto; - const char *dynamic_linker = nullptr; - const char *libc_txt = nullptr; - ZigList clang_argv = {0}; - ZigList lib_dirs = {0}; - ZigList link_libs = {0}; - ZigList forbidden_link_libs = {0}; - ZigList framework_dirs = {0}; - ZigList frameworks = {0}; - bool have_libc = false; - const char *target_string = nullptr; - bool rdynamic = false; - const char *linker_script = nullptr; - Buf *version_script = nullptr; - ZigList rpath_list = {0}; - bool each_lib_rpath = false; - ZigList objects = {0}; - ZigList c_source_files = {0}; - const char *test_filter = nullptr; - const char *test_name_prefix = nullptr; - bool test_evented_io = false; - bool is_versioned = false; - size_t ver_major = 0; - size_t ver_minor = 0; - size_t ver_patch = 0; - bool timing_info = false; - bool stack_report = false; - bool enable_dump_analysis = false; - bool enable_doc_generation = false; - bool emit_bin = true; - const char *emit_bin_override_path = nullptr; - bool emit_asm = false; - bool emit_llvm_ir = false; - bool emit_h = false; - const char *cache_dir = nullptr; - CliPkg *cur_pkg = heap::c_allocator.create(); - BuildMode build_mode = BuildModeDebug; - ZigList test_exec_args = {0}; - int runtime_args_start = -1; - bool system_linker_hack = false; - TargetSubsystem subsystem = TargetSubsystemAuto; - bool want_single_threaded = false; - bool bundle_compiler_rt = false; - Buf *override_lib_dir = nullptr; - Buf *main_pkg_path = nullptr; - ValgrindSupport valgrind_support = ValgrindSupportAuto; - WantPIC want_pic = WantPICAuto; - WantStackCheck want_stack_check = WantStackCheckAuto; - WantCSanitize want_sanitize_c = WantCSanitizeAuto; - bool function_sections = false; - const char *mcpu = nullptr; - CodeModel code_model = CodeModelDefault; - bool want_native_include_dirs = false; - OptionalBool linker_bind_global_refs_locally = OptionalBoolNull; - size_t stack_size_override = 0; - - ZigList llvm_argv = {0}; - llvm_argv.append("zig (LLVM option parsing)"); - - if (argc >= 2 && strcmp(argv[1], "build") == 0) { - Buf zig_exe_path_buf = BUF_INIT; - if ((err = os_self_exe_path(&zig_exe_path_buf))) { - fprintf(stderr, "Unable to determine path to zig's own executable\n"); - return EXIT_FAILURE; - } - const char *zig_exe_path = buf_ptr(&zig_exe_path_buf); - const char *build_file = nullptr; - - init_all_targets(); - - ZigList args = {0}; - args.append(NULL); // placeholder - args.append(zig_exe_path); - args.append(NULL); // placeholder - args.append(NULL); // placeholder - for (int i = 2; i < argc; i += 1) { - if (strcmp(argv[i], "--help") == 0) { - args.append(argv[i]); - } else if (i + 1 < argc && strcmp(argv[i], "--build-file") == 0) { - build_file = argv[i + 1]; - i += 1; - } else if (i + 1 < argc && strcmp(argv[i], "--cache-dir") == 0) { - cache_dir = argv[i + 1]; - i += 1; - } else if (i + 1 < argc && strcmp(argv[i], "--override-lib-dir") == 0) { - override_lib_dir = buf_create_from_str(argv[i + 1]); - i += 1; - - args.append("--override-lib-dir"); - args.append(buf_ptr(override_lib_dir)); - } else { - args.append(argv[i]); - } - } - - Buf *zig_lib_dir = (override_lib_dir == nullptr) ? get_zig_lib_dir() : override_lib_dir; - - Buf *build_runner_path = buf_alloc(); - os_path_join(get_zig_special_dir(zig_lib_dir), buf_create_from_str("build_runner.zig"), build_runner_path); - - ZigTarget target; - if ((err = target_parse_triple(&target, "native", nullptr, nullptr))) { - fprintf(stderr, "Unable to get native target: %s\n", err_str(err)); - return EXIT_FAILURE; - } - - Buf *build_file_buf = buf_create_from_str((build_file != nullptr) ? build_file : "build.zig"); - Buf build_file_abs = os_path_resolve(&build_file_buf, 1); - Buf build_file_basename = BUF_INIT; - Buf build_file_dirname = BUF_INIT; - os_path_split(&build_file_abs, &build_file_dirname, &build_file_basename); - - for (;;) { - bool build_file_exists; - if ((err = os_file_exists(&build_file_abs, &build_file_exists))) { - fprintf(stderr, "unable to check existence of '%s': %s\n", buf_ptr(&build_file_abs), err_str(err)); - return 1; - } - if (build_file_exists) - break; - - if (build_file != nullptr) { - // they asked for a specific build file path. only look for that one - return zig_error_no_build_file(); - } - - Buf *next_dir = buf_alloc(); - os_path_dirname(&build_file_dirname, next_dir); - if (buf_eql_buf(&build_file_dirname, next_dir)) { - // no more parent directories to search, give up - return zig_error_no_build_file(); - } - os_path_join(next_dir, &build_file_basename, &build_file_abs); - buf_init_from_buf(&build_file_dirname, next_dir); - } - - Buf full_cache_dir = BUF_INIT; - if (cache_dir == nullptr) { - os_path_join(&build_file_dirname, buf_create_from_str(default_zig_cache_name), &full_cache_dir); - } else { - Buf *cache_dir_buf = buf_create_from_str(cache_dir); - full_cache_dir = os_path_resolve(&cache_dir_buf, 1); - } - Stage2ProgressNode *root_progress_node = stage2_progress_start_root(stage2_progress_create(), "", 0, 0); - - CodeGen *g = codegen_create(main_pkg_path, build_runner_path, &target, OutTypeExe, - BuildModeDebug, override_lib_dir, nullptr, &full_cache_dir, false, root_progress_node); - g->valgrind_support = valgrind_support; - g->enable_time_report = timing_info; - codegen_set_out_name(g, buf_create_from_str("build")); - - args.items[2] = buf_ptr(&build_file_dirname); - args.items[3] = buf_ptr(&full_cache_dir); - - ZigPackage *build_pkg = codegen_create_package(g, buf_ptr(&build_file_dirname), - buf_ptr(&build_file_basename), "std.special"); - g->main_pkg->package_table.put(buf_create_from_str("@build"), build_pkg); - g->enable_cache = get_cache_opt(enable_cache, true); - codegen_build_and_link(g); - if (root_progress_node != nullptr) { - stage2_progress_end(root_progress_node); - root_progress_node = nullptr; - } - - Termination term; - args.items[0] = buf_ptr(&g->bin_file_output_path); - os_spawn_process(args, &term); - if (term.how != TerminationIdClean || term.code != 0) { - fprintf(stderr, "\nBuild failed. The following command failed:\n"); - const char *prefix = ""; - for (size_t i = 0; i < args.length; i += 1) { - fprintf(stderr, "%s%s", prefix, args.at(i)); - prefix = " "; - } - fprintf(stderr, "\n"); - } - return (term.how == TerminationIdClean) ? term.code : -1; - } else if (argc >= 2 && strcmp(argv[1], "fmt") == 0) { - return stage2_fmt(argc, argv); - } else if (argc >= 2 && strcmp(argv[1], "env") == 0) { - return stage2_env(argc, argv); - } else if (argc >= 2 && strcmp(argv[1], "cc") == 0) { - return stage2_cc(argc, argv, false); - } else if (argc >= 2 && strcmp(argv[1], "c++") == 0) { - return stage2_cc(argc, argv, true); - } else for (int i = 1; i < argc; i += 1) { - char *arg = argv[i]; - - if (arg[0] == '-') { - if (strcmp(arg, "--") == 0) { - if (cmd == CmdRun) { - runtime_args_start = i + 1; - break; // rest of the args are for the program - } else { - fprintf(stderr, "Unexpected end-of-parameter mark: %s\n", arg); - } - } else if (strcmp(arg, "--release-fast") == 0) { - build_mode = BuildModeFastRelease; - } else if (strcmp(arg, "--release-safe") == 0) { - build_mode = BuildModeSafeRelease; - } else if (strcmp(arg, "--release-small") == 0) { - build_mode = BuildModeSmallRelease; - } else if (strcmp(arg, "--help") == 0) { - if (cmd == CmdLibC) { - return print_libc_usage(arg0, stdout, EXIT_SUCCESS); - } else { - return print_full_usage(arg0, stdout, EXIT_SUCCESS); - } - } else if (strcmp(arg, "--strip") == 0) { - strip = true; - } else if (strcmp(arg, "-dynamic") == 0) { - is_dynamic = true; - } else if (strcmp(arg, "--verbose-tokenize") == 0) { - verbose_tokenize = true; - } else if (strcmp(arg, "--verbose-ast") == 0) { - verbose_ast = true; - } else if (strcmp(arg, "--verbose-link") == 0) { - verbose_link = true; - } else if (strcmp(arg, "--verbose-ir") == 0) { - verbose_ir = true; - } else if (strcmp(arg, "--verbose-llvm-ir") == 0) { - verbose_llvm_ir = true; - } else if (strcmp(arg, "--verbose-cimport") == 0) { - verbose_cimport = true; - } else if (strcmp(arg, "--verbose-cc") == 0) { - verbose_cc = true; - } else if (strcmp(arg, "--verbose-llvm-cpu-features") == 0) { - verbose_llvm_cpu_features = true; - } else if (strcmp(arg, "-rdynamic") == 0) { - rdynamic = true; - } else if (strcmp(arg, "--each-lib-rpath") == 0) { - each_lib_rpath = true; - } else if (strcmp(arg, "-ftime-report") == 0) { - timing_info = true; - } else if (strcmp(arg, "-fstack-report") == 0) { - stack_report = true; - } else if (strcmp(arg, "-fmem-report") == 0) { -#ifdef ZIG_ENABLE_MEM_PROFILE - mem_report = true; - mem::report_print = true; -#else - fprintf(stderr, "-fmem-report requires configuring with -DZIG_ENABLE_MEM_PROFILE=ON\n"); - return print_error_usage(arg0); -#endif - } else if (strcmp(arg, "-fdump-analysis") == 0) { - enable_dump_analysis = true; - } else if (strcmp(arg, "-femit-docs") == 0) { - enable_doc_generation = true; - } else if (strcmp(arg, "--enable-valgrind") == 0) { - valgrind_support = ValgrindSupportEnabled; - } else if (strcmp(arg, "--disable-valgrind") == 0) { - valgrind_support = ValgrindSupportDisabled; - } else if (strcmp(arg, "--eh-frame-hdr") == 0) { - link_eh_frame_hdr = true; - } else if (strcmp(arg, "-fPIC") == 0) { - want_pic = WantPICEnabled; - } else if (strcmp(arg, "-fno-PIC") == 0) { - want_pic = WantPICDisabled; - } else if (strcmp(arg, "-fstack-check") == 0) { - want_stack_check = WantStackCheckEnabled; - } else if (strcmp(arg, "-fno-stack-check") == 0) { - want_stack_check = WantStackCheckDisabled; - } else if (strcmp(arg, "-fsanitize-c") == 0) { - want_sanitize_c = WantCSanitizeEnabled; - } else if (strcmp(arg, "-fno-sanitize-c") == 0) { - want_sanitize_c = WantCSanitizeDisabled; - } else if (strcmp(arg, "--system-linker-hack") == 0) { - system_linker_hack = true; - } else if (strcmp(arg, "--single-threaded") == 0) { - want_single_threaded = true;; - } else if (strcmp(arg, "--bundle-compiler-rt") == 0) { - bundle_compiler_rt = true; - } else if (strcmp(arg, "-Bsymbolic") == 0) { - linker_bind_global_refs_locally = OptionalBoolTrue; - } else if (strcmp(arg, "--test-cmd-bin") == 0) { - test_exec_args.append(nullptr); - } else if (arg[1] == 'D' && arg[2] != 0) { - clang_argv.append("-D"); - clang_argv.append(&arg[2]); - } else if (arg[1] == 'L' && arg[2] != 0) { - // alias for --library-path - lib_dirs.append(&arg[2]); - } else if (arg[1] == 'l' && arg[2] != 0) { - // alias for --library - const char *l = &arg[2]; - if (strcmp(l, "c") == 0) { - have_libc = true; - link_libs.append("c"); - } else if (strcmp(l, "c++") == 0 || strcmp(l, "stdc++") == 0) { - link_libs.append("c++"); - } else { - link_libs.append(l); - } - } else if (arg[1] == 'I' && arg[2] != 0) { - clang_argv.append("-I"); - clang_argv.append(&arg[2]); - } else if (arg[1] == 'F' && arg[2] != 0) { - framework_dirs.append(&arg[2]); - } else if (strcmp(arg, "--pkg-begin") == 0) { - if (i + 2 >= argc) { - fprintf(stderr, "Expected 2 arguments after --pkg-begin\n"); - return print_error_usage(arg0); - } - CliPkg *new_cur_pkg = heap::c_allocator.create(); - i += 1; - new_cur_pkg->name = argv[i]; - i += 1; - new_cur_pkg->path = argv[i]; - new_cur_pkg->parent = cur_pkg; - cur_pkg->children.append(new_cur_pkg); - cur_pkg = new_cur_pkg; - } else if (strcmp(arg, "--pkg-end") == 0) { - if (cur_pkg->parent == nullptr) { - fprintf(stderr, "Encountered --pkg-end with no matching --pkg-begin\n"); - return EXIT_FAILURE; - } - cur_pkg = cur_pkg->parent; - } else if (strcmp(arg, "-ffunction-sections") == 0) { - function_sections = true; - } else if (strcmp(arg, "--test-evented-io") == 0) { - test_evented_io = true; - } else if (strcmp(arg, "-femit-bin") == 0) { - emit_bin = true; - } else if (strcmp(arg, "-fno-emit-bin") == 0) { - emit_bin = false; - } else if (strcmp(arg, "-femit-asm") == 0) { - emit_asm = true; - } else if (strcmp(arg, "-fno-emit-asm") == 0) { - emit_asm = false; - } else if (strcmp(arg, "-femit-llvm-ir") == 0) { - emit_llvm_ir = true; - } else if (strcmp(arg, "-fno-emit-llvm-ir") == 0) { - emit_llvm_ir = false; - } else if (strcmp(arg, "-femit-h") == 0) { - emit_h = true; - } else if (strcmp(arg, "-fno-emit-h") == 0 || strcmp(arg, "--disable-gen-h") == 0) { - // the --disable-gen-h is there to support godbolt. once they upgrade to -fno-emit-h then we can remove this - emit_h = false; - } else if (str_starts_with(arg, "-mcpu=")) { - mcpu = arg + strlen("-mcpu="); - } else if (i + 1 >= argc) { - fprintf(stderr, "Expected another argument after %s\n", arg); - return print_error_usage(arg0); - } else { - i += 1; - if (strcmp(arg, "--output-dir") == 0) { - output_dir = buf_create_from_str(argv[i]); - } else if (strcmp(arg, "--color") == 0) { - if (strcmp(argv[i], "auto") == 0) { - color = ErrColorAuto; - } else if (strcmp(argv[i], "on") == 0) { - color = ErrColorOn; - } else if (strcmp(argv[i], "off") == 0) { - color = ErrColorOff; - } else { - fprintf(stderr, "--color options are 'auto', 'on', or 'off'\n"); - return print_error_usage(arg0); - } - } else if (strcmp(arg, "--cache") == 0) { - if (strcmp(argv[i], "auto") == 0) { - enable_cache = CacheOptAuto; - } else if (strcmp(argv[i], "on") == 0) { - enable_cache = CacheOptOn; - } else if (strcmp(argv[i], "off") == 0) { - enable_cache = CacheOptOff; - } else { - fprintf(stderr, "--cache options are 'auto', 'on', or 'off'\n"); - return print_error_usage(arg0); - } - } else if (strcmp(arg, "--emit") == 0) { - if (strcmp(argv[i], "asm") == 0) { - emit_asm = true; - emit_bin = false; - } else if (strcmp(argv[i], "bin") == 0) { - emit_bin = true; - } else if (strcmp(argv[i], "llvm-ir") == 0) { - emit_llvm_ir = true; - emit_bin = false; - } else { - fprintf(stderr, "--emit options are 'asm', 'bin', or 'llvm-ir'\n"); - return print_error_usage(arg0); - } - } else if (strcmp(arg, "--name") == 0) { - out_name = argv[i]; - } else if (strcmp(arg, "--dynamic-linker") == 0) { - dynamic_linker = argv[i]; - } else if (strcmp(arg, "--libc") == 0) { - libc_txt = argv[i]; - } else if (strcmp(arg, "-D") == 0) { - clang_argv.append("-D"); - clang_argv.append(argv[i]); - } else if (strcmp(arg, "-isystem") == 0) { - clang_argv.append("-isystem"); - clang_argv.append(argv[i]); - } else if (strcmp(arg, "-I") == 0) { - clang_argv.append("-I"); - clang_argv.append(argv[i]); - } else if (strcmp(arg, "-dirafter") == 0) { - clang_argv.append("-dirafter"); - clang_argv.append(argv[i]); - } else if (strcmp(arg, "-mllvm") == 0) { - clang_argv.append("-mllvm"); - clang_argv.append(argv[i]); - - llvm_argv.append(argv[i]); - } else if (strcmp(arg, "-code-model") == 0) { - if (strcmp(argv[i], "default") == 0) { - code_model = CodeModelDefault; - } else if (strcmp(argv[i], "tiny") == 0) { - code_model = CodeModelTiny; - } else if (strcmp(argv[i], "small") == 0) { - code_model = CodeModelSmall; - } else if (strcmp(argv[i], "kernel") == 0) { - code_model = CodeModelKernel; - } else if (strcmp(argv[i], "medium") == 0) { - code_model = CodeModelMedium; - } else if (strcmp(argv[i], "large") == 0) { - code_model = CodeModelLarge; - } else { - fprintf(stderr, "-code-model options are 'default', 'tiny', 'small', 'kernel', 'medium', or 'large'\n"); - return print_error_usage(arg0); - } - } else if (strcmp(arg, "--override-lib-dir") == 0) { - override_lib_dir = buf_create_from_str(argv[i]); - } else if (strcmp(arg, "--main-pkg-path") == 0) { - main_pkg_path = buf_create_from_str(argv[i]); - } else if (strcmp(arg, "--library-path") == 0 || strcmp(arg, "-L") == 0) { - lib_dirs.append(argv[i]); - } else if (strcmp(arg, "-F") == 0) { - framework_dirs.append(argv[i]); - } else if (strcmp(arg, "--library") == 0 || strcmp(arg, "-l") == 0) { - if (strcmp(argv[i], "c") == 0) { - have_libc = true; - link_libs.append("c"); - } else if (strcmp(argv[i], "c++") == 0 || strcmp(argv[i], "stdc++") == 0) { - link_libs.append("c++"); - } else { - link_libs.append(argv[i]); - } - } else if (strcmp(arg, "--forbid-library") == 0) { - forbidden_link_libs.append(argv[i]); - } else if (strcmp(arg, "--object") == 0) { - objects.append(argv[i]); - } else if (strcmp(arg, "--c-source") == 0) { - CFile *c_file = heap::c_allocator.create(); - for (;;) { - if (argv[i][0] == '-') { - c_file->args.append(argv[i]); - i += 1; - if (i < argc) { - continue; - } - - break; - } else { - c_file->source_path = argv[i]; - c_source_files.append(c_file); - break; - } - } - } else if (strcmp(arg, "--cache-dir") == 0) { - cache_dir = argv[i]; - } else if (strcmp(arg, "-target") == 0) { - target_string = argv[i]; - } else if (strcmp(arg, "-framework") == 0) { - frameworks.append(argv[i]); - } else if (strcmp(arg, "--linker-script") == 0) { - linker_script = argv[i]; - } else if (strcmp(arg, "--version-script") == 0) { - version_script = buf_create_from_str(argv[i]); - } else if (strcmp(arg, "-rpath") == 0) { - rpath_list.append(argv[i]); - } else if (strcmp(arg, "--test-filter") == 0) { - test_filter = argv[i]; - } else if (strcmp(arg, "--test-name-prefix") == 0) { - test_name_prefix = argv[i]; - } else if (strcmp(arg, "--ver-major") == 0) { - is_versioned = true; - ver_major = atoi(argv[i]); - } else if (strcmp(arg, "--ver-minor") == 0) { - is_versioned = true; - ver_minor = atoi(argv[i]); - } else if (strcmp(arg, "--ver-patch") == 0) { - is_versioned = true; - ver_patch = atoi(argv[i]); - } else if (strcmp(arg, "--test-cmd") == 0) { - test_exec_args.append(argv[i]); - } else if (strcmp(arg, "--stack") == 0) { - stack_size_override = atoi(argv[i]); - } else if (strcmp(arg, "--subsystem") == 0) { - if (strcmp(argv[i], "console") == 0) { - subsystem = TargetSubsystemConsole; - } else if (strcmp(argv[i], "windows") == 0) { - subsystem = TargetSubsystemWindows; - } else if (strcmp(argv[i], "posix") == 0) { - subsystem = TargetSubsystemPosix; - } else if (strcmp(argv[i], "native") == 0) { - subsystem = TargetSubsystemNative; - } else if (strcmp(argv[i], "efi_application") == 0) { - subsystem = TargetSubsystemEfiApplication; - } else if (strcmp(argv[i], "efi_boot_service_driver") == 0) { - subsystem = TargetSubsystemEfiBootServiceDriver; - } else if (strcmp(argv[i], "efi_rom") == 0) { - subsystem = TargetSubsystemEfiRom; - } else if (strcmp(argv[i], "efi_runtime_driver") == 0) { - subsystem = TargetSubsystemEfiRuntimeDriver; - } else { - fprintf(stderr, "invalid: --subsystem %s\n" - "Options are:\n" - " console\n" - " windows\n" - " posix\n" - " native\n" - " efi_application\n" - " efi_boot_service_driver\n" - " efi_rom\n" - " efi_runtime_driver\n" - , argv[i]); - return EXIT_FAILURE; - } - } else if (strcmp(arg, "-mcpu") == 0) { - mcpu = argv[i]; - } else { - fprintf(stderr, "Invalid argument: %s\n", arg); - return print_error_usage(arg0); - } - } - } else if (cmd == CmdNone) { - if (strcmp(arg, "build-exe") == 0) { - cmd = CmdBuild; - out_type = OutTypeExe; - } else if (strcmp(arg, "build-obj") == 0) { - cmd = CmdBuild; - out_type = OutTypeObj; - } else if (strcmp(arg, "build-lib") == 0) { - cmd = CmdBuild; - out_type = OutTypeLib; - } else if (strcmp(arg, "run") == 0) { - cmd = CmdRun; - out_type = OutTypeExe; - } else if (strcmp(arg, "version") == 0) { - cmd = CmdVersion; - } else if (strcmp(arg, "zen") == 0) { - cmd = CmdZen; - } else if (strcmp(arg, "libc") == 0) { - cmd = CmdLibC; - } else if (strcmp(arg, "translate-c") == 0) { - cmd = CmdTranslateC; - } else if (strcmp(arg, "test") == 0) { - cmd = CmdTest; - out_type = OutTypeExe; - } else if (strcmp(arg, "targets") == 0) { - cmd = CmdTargets; - } else if (strcmp(arg, "builtin") == 0) { - cmd = CmdBuiltin; - } else { - fprintf(stderr, "Unrecognized command: %s\n", arg); - return print_error_usage(arg0); - } - } else { - switch (cmd) { - case CmdBuild: - case CmdRun: - case CmdTranslateC: - case CmdTest: - case CmdLibC: - if (!in_file) { - in_file = arg; - } else { - fprintf(stderr, "Unexpected extra parameter: %s\n", arg); - return print_error_usage(arg0); - } - break; - case CmdBuiltin: - case CmdVersion: - case CmdZen: - case CmdTargets: - fprintf(stderr, "Unexpected extra parameter: %s\n", arg); - return print_error_usage(arg0); - case CmdNone: - zig_unreachable(); - } - } - } - - if (cur_pkg->parent != nullptr) { - fprintf(stderr, "Unmatched --pkg-begin\n"); - return EXIT_FAILURE; - } - - Stage2Progress *progress = stage2_progress_create(); - Stage2ProgressNode *root_progress_node = stage2_progress_start_root(progress, "", 0, 0); - if (color == ErrColorOff) stage2_progress_disable_tty(progress); - - init_all_targets(); - - ZigTarget target; - if ((err = target_parse_triple(&target, target_string, mcpu, dynamic_linker))) { - fprintf(stderr, "invalid target: %s\n" - "See `%s targets` to display valid targets.\n", err_str(err), arg0); - return print_error_usage(arg0); - } - - Buf zig_triple_buf = BUF_INIT; - target_triple_zig(&zig_triple_buf, &target); - - // If both output_dir and enable_cache are provided, and doing build-lib, we - // will just do a file copy at the end. This helps when bootstrapping zig from zig0 - // because we want to pass something like this: - // zig0 build-lib --cache on --output-dir ${CMAKE_BINARY_DIR} - // And we don't have access to `zig0 build` because that would require detecting native libc - // on systems where we are not able to build a libc from source for them. - // But that's the only reason this works, so otherwise we give an error here. - Buf *final_output_dir_step = nullptr; - if (output_dir != nullptr && enable_cache == CacheOptOn) { - if (cmd == CmdBuild && out_type == OutTypeLib) { - final_output_dir_step = output_dir; - output_dir = nullptr; - } else { - fprintf(stderr, "`--output-dir` is incompatible with --cache on.\n"); - return print_error_usage(arg0); - } - } - - if (target_requires_pic(&target, have_libc) && want_pic == WantPICDisabled) { - fprintf(stderr, "`--disable-pic` is incompatible with target '%s'\n", buf_ptr(&zig_triple_buf)); - return print_error_usage(arg0); - } - - if ((emit_asm || emit_llvm_ir) && in_file == nullptr) { - fprintf(stderr, "A root source file is required when using `-femit-asm` or `-femit-llvm-ir`\n"); - return print_error_usage(arg0); - } - - if (llvm_argv.length > 1) { - llvm_argv.append(nullptr); - ZigLLVMParseCommandLineOptions(llvm_argv.length - 1, llvm_argv.items); - } - - switch (cmd) { - case CmdLibC: { - if (in_file) { - Stage2LibCInstallation libc; - if ((err = stage2_libc_parse(&libc, in_file))) { - fprintf(stderr, "unable to parse libc file: %s\n", err_str(err)); - return main_exit(root_progress_node, EXIT_FAILURE); - } - return main_exit(root_progress_node, EXIT_SUCCESS); - } - Stage2LibCInstallation libc; - if ((err = stage2_libc_find_native(&libc))) { - fprintf(stderr, "unable to find native libc file: %s\n", err_str(err)); - return main_exit(root_progress_node, EXIT_FAILURE); - } - if ((err = stage2_libc_render(&libc, stdout))) { - fprintf(stderr, "unable to print libc file: %s\n", err_str(err)); - return main_exit(root_progress_node, EXIT_FAILURE); - } - return main_exit(root_progress_node, EXIT_SUCCESS); - } - case CmdBuiltin: { - CodeGen *g = codegen_create(main_pkg_path, nullptr, &target, - out_type, build_mode, override_lib_dir, nullptr, nullptr, false, root_progress_node); - codegen_set_strip(g, strip); - for (size_t i = 0; i < link_libs.length; i += 1) { - LinkLib *link_lib = codegen_add_link_lib(g, buf_create_from_str(link_libs.at(i))); - link_lib->provided_explicitly = true; - } - g->subsystem = subsystem; - g->valgrind_support = valgrind_support; - g->want_pic = want_pic; - g->want_stack_check = want_stack_check; - g->want_sanitize_c = want_sanitize_c; - g->want_single_threaded = want_single_threaded; - g->test_is_evented = test_evented_io; - Buf *builtin_source = codegen_generate_builtin_source(g); - if (fwrite(buf_ptr(builtin_source), 1, buf_len(builtin_source), stdout) != buf_len(builtin_source)) { - fprintf(stderr, "unable to write to stdout: %s\n", strerror(ferror(stdout))); - return main_exit(root_progress_node, EXIT_FAILURE); - } - return main_exit(root_progress_node, EXIT_SUCCESS); - } - case CmdRun: - case CmdBuild: - case CmdTranslateC: - case CmdTest: - { - if (cmd == CmdBuild && !in_file && objects.length == 0 && - c_source_files.length == 0) - { - fprintf(stderr, - "Expected at least one of these things:\n" - " * Zig root source file argument\n" - " * --object argument\n" - " * --c-source argument\n"); - return print_error_usage(arg0); - } else if ((cmd == CmdTranslateC || - cmd == CmdTest || cmd == CmdRun) && !in_file) - { - fprintf(stderr, "Expected source file argument.\n"); - return print_error_usage(arg0); - } else if (cmd == CmdRun && !emit_bin) { - fprintf(stderr, "Cannot run without emitting a binary file.\n"); - return print_error_usage(arg0); - } - - bool any_system_lib_dependencies = false; - for (size_t i = 0; i < link_libs.length; i += 1) { - if (!target_is_libc_lib_name(&target, link_libs.at(i)) && - !target_is_libcpp_lib_name(&target, link_libs.at(i))) - { - any_system_lib_dependencies = true; - break; - } - } - - if (target.is_native_os && (any_system_lib_dependencies || want_native_include_dirs)) { - Error err; - Stage2NativePaths paths; - if ((err = stage2_detect_native_paths(&paths))) { - fprintf(stderr, "unable to detect native system paths: %s\n", err_str(err)); - exit(1); - } - for (size_t i = 0; i < paths.warnings_len; i += 1) { - const char *warning = paths.warnings_ptr[i]; - fprintf(stderr, "warning: %s\n", warning); - } - for (size_t i = 0; i < paths.include_dirs_len; i += 1) { - const char *include_dir = paths.include_dirs_ptr[i]; - clang_argv.append("-isystem"); - clang_argv.append(include_dir); - } - for (size_t i = 0; i < paths.lib_dirs_len; i += 1) { - const char *lib_dir = paths.lib_dirs_ptr[i]; - lib_dirs.append(lib_dir); - } - for (size_t i = 0; i < paths.rpaths_len; i += 1) { - const char *rpath = paths.rpaths_ptr[i]; - rpath_list.append(rpath); - } - } - - - assert(cmd != CmdBuild || out_type != OutTypeUnknown); - - bool need_name = (cmd == CmdBuild || cmd == CmdTranslateC); - - if (cmd == CmdRun) { - out_name = "run"; - } - - Buf *in_file_buf = nullptr; - - Buf *buf_out_name = (cmd == CmdTest) ? buf_create_from_str("test") : - (out_name == nullptr) ? nullptr : buf_create_from_str(out_name); - - if (in_file) { - in_file_buf = buf_create_from_str(in_file); - - if (need_name && buf_out_name == nullptr) { - Buf basename = BUF_INIT; - os_path_split(in_file_buf, nullptr, &basename); - buf_out_name = buf_alloc(); - os_path_extname(&basename, buf_out_name, nullptr); - } - } - - if (need_name && buf_out_name == nullptr && c_source_files.length == 1) { - Buf basename = BUF_INIT; - os_path_split(buf_create_from_str(c_source_files.at(0)->source_path), nullptr, &basename); - buf_out_name = buf_alloc(); - os_path_extname(&basename, buf_out_name, nullptr); - } - if (need_name && buf_out_name == nullptr && objects.length == 1) { - Buf basename = BUF_INIT; - os_path_split(buf_create_from_str(objects.at(0)), nullptr, &basename); - buf_out_name = buf_alloc(); - os_path_extname(&basename, buf_out_name, nullptr); - } - if (need_name && buf_out_name == nullptr && emit_bin_override_path != nullptr) { - Buf basename = BUF_INIT; - os_path_split(buf_create_from_str(emit_bin_override_path), nullptr, &basename); - buf_out_name = buf_alloc(); - os_path_extname(&basename, buf_out_name, nullptr); - } - - if (need_name && buf_out_name == nullptr) { - fprintf(stderr, "--name [name] not provided and unable to infer\n\n"); - return print_error_usage(arg0); - } - - Buf *zig_root_source_file = (cmd == CmdTranslateC) ? nullptr : in_file_buf; - - if (cmd == CmdRun && buf_out_name == nullptr) { - buf_out_name = buf_create_from_str("run"); - } - Stage2LibCInstallation *libc = nullptr; - if (libc_txt != nullptr) { - libc = heap::c_allocator.create(); - if ((err = stage2_libc_parse(libc, libc_txt))) { - fprintf(stderr, "Unable to parse --libc text file: %s\n", err_str(err)); - return main_exit(root_progress_node, EXIT_FAILURE); - } - } - Buf *cache_dir_buf; - if (cache_dir == nullptr) { - if (cmd == CmdRun) { - cache_dir_buf = get_global_cache_dir(); - } else { - cache_dir_buf = buf_create_from_str(default_zig_cache_name); - } - } else { - cache_dir_buf = buf_create_from_str(cache_dir); - } - CodeGen *g = codegen_create(main_pkg_path, zig_root_source_file, &target, out_type, build_mode, - override_lib_dir, libc, cache_dir_buf, cmd == CmdTest, root_progress_node); - if (llvm_argv.length >= 2) codegen_set_llvm_argv(g, llvm_argv.items + 1, llvm_argv.length - 2); - g->valgrind_support = valgrind_support; - g->link_eh_frame_hdr = link_eh_frame_hdr; - g->want_pic = want_pic; - g->want_stack_check = want_stack_check; - g->want_sanitize_c = want_sanitize_c; - g->subsystem = subsystem; - - g->enable_time_report = timing_info; - g->enable_stack_report = stack_report; - g->enable_dump_analysis = enable_dump_analysis; - g->enable_doc_generation = enable_doc_generation; - g->emit_bin = emit_bin; - g->emit_asm = emit_asm; - g->emit_llvm_ir = emit_llvm_ir; - - codegen_set_out_name(g, buf_out_name); - codegen_set_lib_version(g, is_versioned, ver_major, ver_minor, ver_patch); - g->want_single_threaded = want_single_threaded; - codegen_set_linker_script(g, linker_script); - g->version_script_path = version_script; - if (each_lib_rpath) - codegen_set_each_lib_rpath(g, each_lib_rpath); - - codegen_set_clang_argv(g, clang_argv.items, clang_argv.length); - - codegen_set_strip(g, strip); - g->is_dynamic = is_dynamic; - g->verbose_tokenize = verbose_tokenize; - g->verbose_ast = verbose_ast; - g->verbose_link = verbose_link; - g->verbose_ir = verbose_ir; - g->verbose_llvm_ir = verbose_llvm_ir; - g->verbose_cimport = verbose_cimport; - g->verbose_cc = verbose_cc; - g->verbose_llvm_cpu_features = verbose_llvm_cpu_features; - g->output_dir = output_dir; - g->disable_gen_h = !emit_h; - g->bundle_compiler_rt = bundle_compiler_rt; - codegen_set_errmsg_color(g, color); - g->system_linker_hack = system_linker_hack; - g->function_sections = function_sections; - g->code_model = code_model; - - g->linker_bind_global_refs_locally = linker_bind_global_refs_locally; - g->stack_size_override = stack_size_override; - - for (size_t i = 0; i < lib_dirs.length; i += 1) { - codegen_add_lib_dir(g, lib_dirs.at(i)); - } - for (size_t i = 0; i < framework_dirs.length; i += 1) { - g->framework_dirs.append(framework_dirs.at(i)); - } - for (size_t i = 0; i < link_libs.length; i += 1) { - LinkLib *link_lib = codegen_add_link_lib(g, buf_create_from_str(link_libs.at(i))); - link_lib->provided_explicitly = true; - } - for (size_t i = 0; i < forbidden_link_libs.length; i += 1) { - Buf *forbidden_link_lib = buf_create_from_str(forbidden_link_libs.at(i)); - codegen_add_forbidden_lib(g, forbidden_link_lib); - } - for (size_t i = 0; i < frameworks.length; i += 1) { - codegen_add_framework(g, frameworks.at(i)); - } - for (size_t i = 0; i < rpath_list.length; i += 1) { - codegen_add_rpath(g, rpath_list.at(i)); - } - - codegen_set_rdynamic(g, rdynamic); - - if (test_filter) { - codegen_set_test_filter(g, buf_create_from_str(test_filter)); - } - g->test_is_evented = test_evented_io; - - if (test_name_prefix) { - codegen_set_test_name_prefix(g, buf_create_from_str(test_name_prefix)); - } - - add_package(g, cur_pkg, g->main_pkg); - - if (cmd == CmdBuild || cmd == CmdRun || cmd == CmdTest) { - g->c_source_files = c_source_files; - for (size_t i = 0; i < objects.length; i += 1) { - codegen_add_object(g, buf_create_from_str(objects.at(i))); - } - } - - - if (cmd == CmdBuild || cmd == CmdRun) { - g->enable_cache = get_cache_opt(enable_cache, cmd == CmdRun); - codegen_build_and_link(g); - if (root_progress_node != nullptr) { - stage2_progress_end(root_progress_node); - root_progress_node = nullptr; - } - if (timing_info) - codegen_print_timing_report(g, stdout); - if (stack_report) - zig_print_stack_report(g, stdout); - - if (cmd == CmdRun) { -#ifdef ZIG_ENABLE_MEM_PROFILE - if (mem::report_print) - mem::print_report(); -#endif - - const char *exec_path = buf_ptr(&g->bin_file_output_path); - ZigList args = {0}; - - args.append(exec_path); - if (runtime_args_start != -1) { - for (int i = runtime_args_start; i < argc; ++i) { - args.append(argv[i]); - } - } - args.append(nullptr); - - os_execv(exec_path, args.items); - - args.pop(); - Termination term; - os_spawn_process(args, &term); - return term.code; - } else if (cmd == CmdBuild) { - if (emit_bin_override_path != nullptr) { -#if defined(ZIG_OS_WINDOWS) - buf_replace(g->output_dir, '/', '\\'); -#endif - Buf *dest_path = buf_create_from_str(emit_bin_override_path); - Buf *source_path = &g->bin_file_output_path; - if ((err = os_update_file(source_path, dest_path))) { - fprintf(stderr, "unable to copy %s to %s: %s\n", buf_ptr(source_path), - buf_ptr(dest_path), err_str(err)); - return main_exit(root_progress_node, EXIT_FAILURE); - } - } else if (g->enable_cache) { -#if defined(ZIG_OS_WINDOWS) - buf_replace(&g->bin_file_output_path, '/', '\\'); - buf_replace(g->output_dir, '/', '\\'); -#endif - if (final_output_dir_step != nullptr) { - Buf *dest_basename = buf_alloc(); - os_path_split(&g->bin_file_output_path, nullptr, dest_basename); - Buf *dest_path = buf_alloc(); - os_path_join(final_output_dir_step, dest_basename, dest_path); - - if ((err = os_update_file(&g->bin_file_output_path, dest_path))) { - fprintf(stderr, "unable to copy %s to %s: %s\n", buf_ptr(&g->bin_file_output_path), - buf_ptr(dest_path), err_str(err)); - return main_exit(root_progress_node, EXIT_FAILURE); - } - } else { - if (printf("%s\n", buf_ptr(g->output_dir)) < 0) - return main_exit(root_progress_node, EXIT_FAILURE); - } - } - return main_exit(root_progress_node, EXIT_SUCCESS); - } else { - zig_unreachable(); - } - } else if (cmd == CmdTranslateC) { - g->enable_cache = get_cache_opt(enable_cache, false); - codegen_translate_c(g, in_file_buf); - if (timing_info) - codegen_print_timing_report(g, stderr); - return main_exit(root_progress_node, EXIT_SUCCESS); - } else if (cmd == CmdTest) { - ZigTarget native; - if ((err = target_parse_triple(&native, "native", nullptr, nullptr))) { - fprintf(stderr, "Unable to get native target: %s\n", err_str(err)); - return EXIT_FAILURE; - } - - g->enable_cache = get_cache_opt(enable_cache, output_dir == nullptr); - codegen_build_and_link(g); - if (root_progress_node != nullptr) { - stage2_progress_end(root_progress_node); - root_progress_node = nullptr; - } - - if (timing_info) { - codegen_print_timing_report(g, stdout); - } - - if (stack_report) { - zig_print_stack_report(g, stdout); - } - - if (!g->emit_bin) { - fprintf(stderr, "Semantic analysis complete. No binary produced due to -fno-emit-bin.\n"); - return main_exit(root_progress_node, EXIT_SUCCESS); - } - - Buf *test_exe_path_unresolved = &g->bin_file_output_path; - Buf *test_exe_path = buf_alloc(); - *test_exe_path = os_path_resolve(&test_exe_path_unresolved, 1); - - if (!g->emit_bin) { - fprintf(stderr, "Created %s but skipping execution because no binary generated.\n", - buf_ptr(test_exe_path)); - return main_exit(root_progress_node, EXIT_SUCCESS); - } - - for (size_t i = 0; i < test_exec_args.length; i += 1) { - if (test_exec_args.items[i] == nullptr) { - test_exec_args.items[i] = buf_ptr(test_exe_path); - } - } - - if (!target_can_exec(&native, &target) && test_exec_args.length == 0) { - fprintf(stderr, "Created %s but skipping execution because it is non-native.\n", - buf_ptr(test_exe_path)); - return main_exit(root_progress_node, EXIT_SUCCESS); - } - - Termination term; - if (test_exec_args.length == 0) { - test_exec_args.append(buf_ptr(test_exe_path)); - } - os_spawn_process(test_exec_args, &term); - if (term.how != TerminationIdClean || term.code != 0) { - fprintf(stderr, "\nTests failed. Use the following command to reproduce the failure:\n"); - fprintf(stderr, "%s\n", buf_ptr(test_exe_path)); - } - return main_exit(root_progress_node, (term.how == TerminationIdClean) ? term.code : -1); - } else { - zig_unreachable(); - } - } - case CmdVersion: - printf("%s\n", ZIG_VERSION_STRING); - return main_exit(root_progress_node, EXIT_SUCCESS); - case CmdZen: { - const char *ptr; - size_t len; - stage2_zen(&ptr, &len); - fwrite(ptr, len, 1, stdout); - return main_exit(root_progress_node, EXIT_SUCCESS); - } - case CmdTargets: - return stage2_cmd_targets(target_string, mcpu, dynamic_linker); - case CmdNone: - return print_full_usage(arg0, stderr, EXIT_FAILURE); - } - zig_unreachable(); -} - -int main(int argc, char **argv) { - stage2_attach_segfault_handler(); - os_init(); - mem::init(); - - auto result = main0(argc, argv); - -#ifdef ZIG_ENABLE_MEM_PROFILE - if (mem::report_print) - mem::intern_counters.print_report(); -#endif - mem::deinit(); - return result; -} diff --git a/src/mem.cpp b/src/mem.cpp index 51ee9a27ee..48dbd791de 100644 --- a/src/mem.cpp +++ b/src/mem.cpp @@ -7,7 +7,6 @@ #include "config.h" #include "mem.hpp" -#include "mem_profile.hpp" #include "heap.hpp" namespace mem { @@ -22,16 +21,4 @@ void deinit() { heap::bootstrap_allocator_state.deinit(); } -#ifdef ZIG_ENABLE_MEM_PROFILE -void print_report(FILE *file) { - heap::c_allocator_state.print_report(file); - intern_counters.print_report(file); -} -#endif - -#ifdef ZIG_ENABLE_MEM_PROFILE -bool report_print = false; -FILE *report_file{nullptr}; -#endif - } // namespace mem diff --git a/src/mem.hpp b/src/mem.hpp index 9e262b7d53..3008febbde 100644 --- a/src/mem.hpp +++ b/src/mem.hpp @@ -135,15 +135,6 @@ protected: virtual void internal_deallocate(const TypeInfo &info, void *ptr, size_t count) = 0; }; -#ifdef ZIG_ENABLE_MEM_PROFILE -void print_report(FILE *file = nullptr); - -// global memory report flag -extern bool report_print; -// global memory report default destination -extern FILE *report_file; -#endif - } // namespace mem #endif diff --git a/src/mem_profile.cpp b/src/mem_profile.cpp deleted file mode 100644 index 13ba57f913..0000000000 --- a/src/mem_profile.cpp +++ /dev/null @@ -1,181 +0,0 @@ -/* - * Copyright (c) 2020 Andrew Kelley - * - * This file is part of zig, which is MIT licensed. - * See http://opensource.org/licenses/MIT - */ - -#include "config.h" - -#ifdef ZIG_ENABLE_MEM_PROFILE - -#include "mem.hpp" -#include "mem_list.hpp" -#include "mem_profile.hpp" -#include "heap.hpp" - -namespace mem { - -void Profile::init(const char *name, const char *kind) { - this->name = name; - this->kind = kind; - this->usage_table.init(heap::bootstrap_allocator, 1024); -} - -void Profile::deinit() { - assert(this->name != nullptr); - if (mem::report_print) - this->print_report(); - this->usage_table.deinit(heap::bootstrap_allocator); - this->name = nullptr; -} - -void Profile::record_alloc(const TypeInfo &info, size_t count) { - if (count == 0) return; - auto existing_entry = this->usage_table.put_unique( - heap::bootstrap_allocator, - UsageKey{info.name_ptr, info.name_len}, - Entry{info, 1, count, 0, 0} ); - if (existing_entry != nullptr) { - assert(existing_entry->value.info.size == info.size); // allocated name does not match type - existing_entry->value.alloc.calls += 1; - existing_entry->value.alloc.objects += count; - } -} - -void Profile::record_dealloc(const TypeInfo &info, size_t count) { - if (count == 0) return; - auto existing_entry = this->usage_table.maybe_get(UsageKey{info.name_ptr, info.name_len}); - if (existing_entry == nullptr) { - fprintf(stderr, "deallocated name '"); - for (size_t i = 0; i < info.name_len; ++i) - fputc(info.name_ptr[i], stderr); - zig_panic("' (size %zu) not found in allocated table; compromised memory usage stats", info.size); - } - if (existing_entry->value.info.size != info.size) { - fprintf(stderr, "deallocated name '"); - for (size_t i = 0; i < info.name_len; ++i) - fputc(info.name_ptr[i], stderr); - zig_panic("' does not match expected type size %zu", info.size); - } - assert(existing_entry->value.alloc.calls - existing_entry->value.dealloc.calls > 0); - assert(existing_entry->value.alloc.objects - existing_entry->value.dealloc.objects >= count); - existing_entry->value.dealloc.calls += 1; - existing_entry->value.dealloc.objects += count; -} - -static size_t entry_remain_total_bytes(const Profile::Entry *entry) { - return (entry->alloc.objects - entry->dealloc.objects) * entry->info.size; -} - -static int entry_compare(const void *a, const void *b) { - size_t total_a = entry_remain_total_bytes(*reinterpret_cast(a)); - size_t total_b = entry_remain_total_bytes(*reinterpret_cast(b)); - if (total_a > total_b) - return -1; - if (total_a < total_b) - return 1; - return 0; -}; - -void Profile::print_report(FILE *file) { - if (!file) { - file = report_file; - if (!file) - file = stderr; - } - fprintf(file, "\n--- MEMORY PROFILE REPORT [%s]: %s ---\n", this->kind, this->name); - - List list; - auto it = this->usage_table.entry_iterator(); - for (;;) { - auto entry = it.next(); - if (!entry) - break; - list.append(&heap::bootstrap_allocator, &entry->value); - } - - qsort(list.items, list.length, sizeof(const Entry *), entry_compare); - - size_t total_bytes_alloc = 0; - size_t total_bytes_dealloc = 0; - - size_t total_calls_alloc = 0; - size_t total_calls_dealloc = 0; - - for (size_t i = 0; i < list.length; i += 1) { - const Entry *entry = list.at(i); - fprintf(file, " "); - for (size_t j = 0; j < entry->info.name_len; ++j) - fputc(entry->info.name_ptr[j], file); - fprintf(file, ": %zu bytes each", entry->info.size); - - fprintf(file, ", alloc{ %zu calls, %zu objects, total ", entry->alloc.calls, entry->alloc.objects); - const auto alloc_num_bytes = entry->alloc.objects * entry->info.size; - zig_pretty_print_bytes(file, alloc_num_bytes); - - fprintf(file, " }, dealloc{ %zu calls, %zu objects, total ", entry->dealloc.calls, entry->dealloc.objects); - const auto dealloc_num_bytes = entry->dealloc.objects * entry->info.size; - zig_pretty_print_bytes(file, dealloc_num_bytes); - - fprintf(file, " }, remain{ %zu calls, %zu objects, total ", - entry->alloc.calls - entry->dealloc.calls, - entry->alloc.objects - entry->dealloc.objects ); - const auto remain_num_bytes = alloc_num_bytes - dealloc_num_bytes; - zig_pretty_print_bytes(file, remain_num_bytes); - - fprintf(file, " }\n"); - - total_bytes_alloc += alloc_num_bytes; - total_bytes_dealloc += dealloc_num_bytes; - - total_calls_alloc += entry->alloc.calls; - total_calls_dealloc += entry->dealloc.calls; - } - - fprintf(file, "\n Total bytes allocated: "); - zig_pretty_print_bytes(file, total_bytes_alloc); - fprintf(file, ", deallocated: "); - zig_pretty_print_bytes(file, total_bytes_dealloc); - fprintf(file, ", remaining: "); - zig_pretty_print_bytes(file, total_bytes_alloc - total_bytes_dealloc); - - fprintf(file, "\n Total calls alloc: %zu, dealloc: %zu, remain: %zu\n", - total_calls_alloc, total_calls_dealloc, (total_calls_alloc - total_calls_dealloc)); - - list.deinit(&heap::bootstrap_allocator); -} - -uint32_t Profile::usage_hash(UsageKey key) { - // FNV 32-bit hash - uint32_t h = 2166136261; - for (size_t i = 0; i < key.name_len; ++i) { - h = h ^ key.name_ptr[i]; - h = h * 16777619; - } - return h; -} - -bool Profile::usage_equal(UsageKey a, UsageKey b) { - return memcmp(a.name_ptr, b.name_ptr, a.name_len > b.name_len ? a.name_len : b.name_len) == 0; -} - -void InternCounters::print_report(FILE *file) { - if (!file) { - file = report_file; - if (!file) - file = stderr; - } - fprintf(file, "\n--- IR INTERNING REPORT ---\n"); - fprintf(file, " undefined: interned %zu times\n", intern_counters.x_undefined); - fprintf(file, " void: interned %zu times\n", intern_counters.x_void); - fprintf(file, " null: interned %zu times\n", intern_counters.x_null); - fprintf(file, " unreachable: interned %zu times\n", intern_counters.x_unreachable); - fprintf(file, " zero_byte: interned %zu times\n", intern_counters.zero_byte); -} - -InternCounters intern_counters; - -} // namespace mem - -#endif diff --git a/src/mem_profile.hpp b/src/mem_profile.hpp deleted file mode 100644 index 3b13b7680b..0000000000 --- a/src/mem_profile.hpp +++ /dev/null @@ -1,71 +0,0 @@ -/* - * Copyright (c) 2020 Andrew Kelley - * - * This file is part of zig, which is MIT licensed. - * See http://opensource.org/licenses/MIT - */ - -#ifndef ZIG_MEM_PROFILE_HPP -#define ZIG_MEM_PROFILE_HPP - -#include "config.h" - -#ifdef ZIG_ENABLE_MEM_PROFILE - -#include - -#include "mem.hpp" -#include "mem_hash_map.hpp" -#include "util.hpp" - -namespace mem { - -struct Profile { - void init(const char *name, const char *kind); - void deinit(); - - void record_alloc(const TypeInfo &info, size_t count); - void record_dealloc(const TypeInfo &info, size_t count); - - void print_report(FILE *file = nullptr); - - struct Entry { - TypeInfo info; - - struct Use { - size_t calls; - size_t objects; - } alloc, dealloc; - }; - -private: - const char *name; - const char *kind; - - struct UsageKey { - const char *name_ptr; - size_t name_len; - }; - - static uint32_t usage_hash(UsageKey key); - static bool usage_equal(UsageKey a, UsageKey b); - - HashMap usage_table; -}; - -struct InternCounters { - size_t x_undefined; - size_t x_void; - size_t x_null; - size_t x_unreachable; - size_t zero_byte; - - void print_report(FILE *file = nullptr); -}; - -extern InternCounters intern_counters; - -} // namespace mem - -#endif -#endif diff --git a/src/mem_type_info.hpp b/src/mem_type_info.hpp index 8698992ca0..d8a7933268 100644 --- a/src/mem_type_info.hpp +++ b/src/mem_type_info.hpp @@ -10,18 +10,8 @@ #include "config.h" -#ifndef ZIG_TYPE_INFO_IMPLEMENTATION -# ifdef ZIG_ENABLE_MEM_PROFILE -# define ZIG_TYPE_INFO_IMPLEMENTATION 1 -# else -# define ZIG_TYPE_INFO_IMPLEMENTATION 0 -# endif -#endif - namespace mem { -#if ZIG_TYPE_INFO_IMPLEMENTATION == 0 - struct TypeInfo { size_t size; size_t alignment; @@ -32,105 +22,6 @@ struct TypeInfo { } }; -#elif ZIG_TYPE_INFO_IMPLEMENTATION == 1 - -// -// A non-portable way to get a human-readable type-name compatible with -// non-RTTI C++ compiler mode; eg. `-fno-rtti`. -// -// Minimum requirements are c++11 and a compiler that has a constant for the -// current function's decorated name whereby a template-type name can be -// computed. eg. `__PRETTY_FUNCTION__` or `__FUNCSIG__`. -// -// given the following snippet: -// -// | #include -// | -// | struct Top {}; -// | namespace mynamespace { -// | using custom = unsigned int; -// | struct Foo { -// | struct Bar {}; -// | }; -// | }; -// | -// | template -// | void foobar() { -// | #ifdef _MSC_VER -// | fprintf(stderr, "--> %s\n", __FUNCSIG__); -// | #else -// | fprintf(stderr, "--> %s\n", __PRETTY_FUNCTION__); -// | #endif -// | } -// | -// | int main() { -// | foobar(); -// | foobar(); -// | foobar(); -// | foobar(); -// | foobar(); -// | } -// -// gcc 9.2.0 produces: -// --> void foobar() [with T = Top] -// --> void foobar() [with T = unsigned int] -// --> void foobar() [with T = unsigned int] -// --> void foobar() [with T = mynamespace::Foo*] -// --> void foobar() [with T = mynamespace::Foo::Bar*] -// -// xcode 11.3.1/clang produces: -// --> void foobar() [T = Top] -// --> void foobar() [T = unsigned int] -// --> void foobar() [T = unsigned int] -// --> void foobar() [T = mynamespace::Foo *] -// --> void foobar() [T = mynamespace::Foo::Bar *] -// -// VStudio 2019 16.5.0/msvc produces: -// --> void __cdecl foobar(void) -// --> void __cdecl foobar(void) -// --> void __cdecl foobar(void) -// --> void __cdecl foobar(void) -// --> void __cdecl foobar(void) -// -struct TypeInfo { - const char *name_ptr; - size_t name_len; - size_t size; - size_t alignment; - - static constexpr TypeInfo to_type_info(const char *str, size_t start, size_t end, size_t size, size_t alignment) { - return TypeInfo{str + start, end - start, size, alignment}; - } - - static constexpr size_t index_of(const char *str, char c) { - return *str == c ? 0 : 1 + index_of(str + 1, c); - } - - template - static constexpr const char *decorated_name() { -#ifdef _MSC_VER - return __FUNCSIG__; -#else - return __PRETTY_FUNCTION__; -#endif - } - - static constexpr TypeInfo extract(const char *decorated, size_t size, size_t alignment) { -#ifdef _MSC_VER - return to_type_info(decorated, index_of(decorated, '<') + 1, index_of(decorated, '>'), size, alignment); -#else - return to_type_info(decorated, index_of(decorated, '=') + 2, index_of(decorated, ']'), size, alignment); -#endif - } - - template - static constexpr TypeInfo make() { - return TypeInfo::extract(TypeInfo::decorated_name(), sizeof(T), alignof(T)); - } -}; - -#endif // ZIG_TYPE_INFO_IMPLEMENTATION - } // namespace mem #endif diff --git a/src/stage1.cpp b/src/stage1.cpp new file mode 100644 index 0000000000..417076aa99 --- /dev/null +++ b/src/stage1.cpp @@ -0,0 +1,127 @@ +/* + * Copyright (c) 2020 Andrew Kelley + * + * This file is part of zig, which is MIT licensed. + * See http://opensource.org/licenses/MIT + */ + +#include "stage1.h" +#include "os.hpp" +#include "all_types.hpp" +#include "codegen.hpp" + +void zig_stage1_os_init(void) { + os_init(); + mem::init(); + init_all_targets(); +} + +struct ZigStage1 *zig_stage1_create(BuildMode optimize_mode, + const char *main_pkg_path_ptr, size_t main_pkg_path_len, + const char *root_src_path_ptr, size_t root_src_path_len, + const char *zig_lib_dir_ptr, size_t zig_lib_dir_len, + const ZigTarget *target, bool is_test_build, Stage2ProgressNode *progress_node) +{ + Buf *main_pkg_path = buf_create_from_mem(main_pkg_path_ptr, main_pkg_path_len); + Buf *root_src_path = buf_create_from_mem(root_src_path_ptr, root_src_path_len); + Buf *zig_lib_dir = buf_create_from_mem(zig_lib_dir_ptr, zig_lib_dir_len); + CodeGen *g = codegen_create(main_pkg_path, root_src_path, target, optimize_mode, + zig_lib_dir, is_test_build, progress_node); + return &g->stage1; +} + +void zig_stage1_destroy(struct ZigStage1 *stage1) { + CodeGen *codegen = reinterpret_cast(stage1); + codegen_destroy(codegen); +} + +static void add_package(CodeGen *g, ZigStage1Pkg *stage1_pkg, ZigPackage *pkg) { + for (size_t i = 0; i < stage1_pkg->children_len; i += 1) { + ZigStage1Pkg *child_cli_pkg = stage1_pkg->children_ptr[i]; + + Buf *dirname = buf_alloc(); + Buf *basename = buf_alloc(); + os_path_split(buf_create_from_mem(child_cli_pkg->path_ptr, child_cli_pkg->path_len), dirname, basename); + + ZigPackage *child_pkg = codegen_create_package(g, buf_ptr(dirname), buf_ptr(basename), + buf_ptr(buf_sprintf("%s.%.*s", buf_ptr(&pkg->pkg_path), + (int)child_cli_pkg->name_len, child_cli_pkg->name_ptr))); + auto entry = pkg->package_table.put_unique( + buf_create_from_mem(child_cli_pkg->name_ptr, child_cli_pkg->name_len), + child_pkg); + if (entry) { + ZigPackage *existing_pkg = entry->value; + Buf *full_path = buf_alloc(); + os_path_join(&existing_pkg->root_src_dir, &existing_pkg->root_src_path, full_path); + fprintf(stderr, "Unable to add package '%.*s'->'%.*s': already exists as '%s'\n", + (int)child_cli_pkg->name_len, child_cli_pkg->name_ptr, + (int)child_cli_pkg->path_len, child_cli_pkg->path_ptr, + buf_ptr(full_path)); + exit(EXIT_FAILURE); + } + + add_package(g, child_cli_pkg, child_pkg); + } +} + +void zig_stage1_build_object(struct ZigStage1 *stage1) { + CodeGen *g = reinterpret_cast(stage1); + + g->root_out_name = buf_create_from_mem(stage1->root_name_ptr, stage1->root_name_len); + g->zig_lib_dir = buf_create_from_mem(stage1->zig_lib_dir_ptr, stage1->zig_lib_dir_len); + g->zig_std_dir = buf_create_from_mem(stage1->zig_std_dir_ptr, stage1->zig_std_dir_len); + g->output_dir = buf_create_from_mem(stage1->output_dir_ptr, stage1->output_dir_len); + if (stage1->builtin_zig_path_len != 0) { + g->builtin_zig_path = buf_create_from_mem(stage1->builtin_zig_path_ptr, stage1->builtin_zig_path_len); + } + if (stage1->test_filter_len != 0) { + g->test_filter = buf_create_from_mem(stage1->test_filter_ptr, stage1->test_filter_len); + } + if (stage1->test_name_prefix_len != 0) { + g->test_name_prefix = buf_create_from_mem(stage1->test_name_prefix_ptr, stage1->test_name_prefix_len); + } + + g->link_mode_dynamic = stage1->link_mode_dynamic; + g->dll_export_fns = stage1->dll_export_fns; + g->have_pic = stage1->pic; + g->have_stack_probing = stage1->enable_stack_probing; + g->is_single_threaded = stage1->is_single_threaded; + g->valgrind_enabled = stage1->valgrind_enabled; + g->link_libc = stage1->link_libc; + g->link_libcpp = stage1->link_libcpp; + g->function_sections = stage1->function_sections; + + g->subsystem = stage1->subsystem; + + g->enable_time_report = stage1->enable_time_report; + g->enable_stack_report = stage1->enable_stack_report; + g->enable_dump_analysis = stage1->dump_analysis; + g->enable_doc_generation = stage1->enable_doc_generation; + g->emit_bin = stage1->emit_bin; + g->emit_asm = stage1->emit_asm; + g->emit_llvm_ir = stage1->emit_llvm_ir; + g->test_is_evented = stage1->test_is_evented; + + g->verbose_tokenize = stage1->verbose_tokenize; + g->verbose_ast = stage1->verbose_ast; + g->verbose_link = stage1->verbose_link; + g->verbose_ir = stage1->verbose_ir; + g->verbose_llvm_ir = stage1->verbose_llvm_ir; + g->verbose_cimport = stage1->verbose_cimport; + g->verbose_cc = stage1->verbose_cc; + g->verbose_llvm_cpu_features = stage1->verbose_llvm_cpu_features; + + g->err_color = stage1->err_color; + g->code_model = stage1->code_model; + + { + g->strip_debug_symbols = stage1->strip; + if (!target_has_debug_info(g->zig_target)) { + g->strip_debug_symbols = true; + } + } + + add_package(g, stage1->root_pkg, g->main_pkg); + + codegen_build_object(g); +} diff --git a/src/stage1.h b/src/stage1.h new file mode 100644 index 0000000000..b7144d8409 --- /dev/null +++ b/src/stage1.h @@ -0,0 +1,217 @@ +/* + * Copyright (c) 2020 Andrew Kelley + * + * This file is part of zig, which is MIT licensed. + * See http://opensource.org/licenses/MIT + */ + +// This file deals with exposing stage1 C++ code to stage2 Zig code. + +#ifndef ZIG_STAGE1_H +#define ZIG_STAGE1_H + +#include "zig_llvm.h" + +#include + +#ifdef __cplusplus +#define ZIG_EXTERN_C extern "C" +#else +#define ZIG_EXTERN_C +#endif + +// ABI warning +enum ErrColor { + ErrColorAuto, + ErrColorOff, + ErrColorOn, +}; + +// ABI warning +enum CodeModel { + CodeModelDefault, + CodeModelTiny, + CodeModelSmall, + CodeModelKernel, + CodeModelMedium, + CodeModelLarge, +}; + +// ABI warning +enum TargetSubsystem { + TargetSubsystemConsole, + TargetSubsystemWindows, + TargetSubsystemPosix, + TargetSubsystemNative, + TargetSubsystemEfiApplication, + TargetSubsystemEfiBootServiceDriver, + TargetSubsystemEfiRom, + TargetSubsystemEfiRuntimeDriver, + + // This means Zig should infer the subsystem. + // It's last so that the indexes of other items can line up + // with the enum in builtin.zig. + TargetSubsystemAuto +}; + + +// ABI warning +// Synchronize with target.cpp::os_list +enum Os { + OsFreestanding, + OsAnanas, + OsCloudABI, + OsDragonFly, + OsFreeBSD, + OsFuchsia, + OsIOS, + OsKFreeBSD, + OsLinux, + OsLv2, // PS3 + OsMacOSX, + OsNetBSD, + OsOpenBSD, + OsSolaris, + OsWindows, + OsHaiku, + OsMinix, + OsRTEMS, + OsNaCl, // Native Client + OsCNK, // BG/P Compute-Node Kernel + OsAIX, + OsCUDA, // NVIDIA CUDA + OsNVCL, // NVIDIA OpenCL + OsAMDHSA, // AMD HSA Runtime + OsPS4, + OsELFIAMCU, + OsTvOS, // Apple tvOS + OsWatchOS, // Apple watchOS + OsMesa3D, + OsContiki, + OsAMDPAL, + OsHermitCore, + OsHurd, + OsWASI, + OsEmscripten, + OsUefi, + OsOther, +}; + +// ABI warning +struct ZigTarget { + enum ZigLLVM_ArchType arch; + enum ZigLLVM_VendorType vendor; + + enum ZigLLVM_EnvironmentType abi; + Os os; + + bool is_native_os; + bool is_native_cpu; + + const char *llvm_cpu_name; + const char *llvm_cpu_features; + const char *cpu_builtin_str; + const char *os_builtin_str; + const char *dynamic_linker; + + const char **llvm_cpu_features_asm_ptr; + size_t llvm_cpu_features_asm_len; +}; + +// ABI warning +struct Stage2Progress; +// ABI warning +struct Stage2ProgressNode; + +enum BuildMode { + BuildModeDebug, + BuildModeFastRelease, + BuildModeSafeRelease, + BuildModeSmallRelease, +}; + + +struct ZigStage1Pkg { + const char *name_ptr; + size_t name_len; + + const char *path_ptr; + size_t path_len; + + struct ZigStage1Pkg **children_ptr; + size_t children_len; + + struct ZigStage1Pkg *parent; +}; + +// This struct is used by both main.cpp and stage1.zig. +struct ZigStage1 { + const char *root_name_ptr; + size_t root_name_len; + + const char *output_dir_ptr; + size_t output_dir_len; + + const char *builtin_zig_path_ptr; + size_t builtin_zig_path_len; + + const char *test_filter_ptr; + size_t test_filter_len; + + const char *test_name_prefix_ptr; + size_t test_name_prefix_len; + + const char *zig_lib_dir_ptr; + size_t zig_lib_dir_len; + + const char *zig_std_dir_ptr; + size_t zig_std_dir_len; + + void *userdata; + struct ZigStage1Pkg *root_pkg; + + CodeModel code_model; + TargetSubsystem subsystem; + ErrColor err_color; + + bool pic; + bool link_libc; + bool link_libcpp; + bool strip; + bool is_single_threaded; + bool dll_export_fns; + bool link_mode_dynamic; + bool valgrind_enabled; + bool function_sections; + bool enable_stack_probing; + bool enable_time_report; + bool enable_stack_report; + bool dump_analysis; + bool enable_doc_generation; + bool emit_bin; + bool emit_asm; + bool emit_llvm_ir; + bool test_is_evented; + bool verbose_tokenize; + bool verbose_ast; + bool verbose_link; + bool verbose_ir; + bool verbose_llvm_ir; + bool verbose_cimport; + bool verbose_cc; + bool verbose_llvm_cpu_features; +}; + +ZIG_EXTERN_C void zig_stage1_os_init(void); + +ZIG_EXTERN_C struct ZigStage1 *zig_stage1_create(enum BuildMode optimize_mode, + const char *main_pkg_path_ptr, size_t main_pkg_path_len, + const char *root_src_path_ptr, size_t root_src_path_len, + const char *zig_lib_dir_ptr, size_t zig_lib_dir_len, + const ZigTarget *target, bool is_test_build, Stage2ProgressNode *progress_node); + +ZIG_EXTERN_C void zig_stage1_build_object(struct ZigStage1 *); + +ZIG_EXTERN_C void zig_stage1_destroy(struct ZigStage1 *); + +#endif diff --git a/src/stage2.cpp b/src/stage2.cpp index ad6a9f9d97..f8b078c237 100644 --- a/src/stage2.cpp +++ b/src/stage2.cpp @@ -5,40 +5,12 @@ #include "util.hpp" #include "zig_llvm.h" #include "target.hpp" +#include "buffer.hpp" +#include "os.hpp" #include #include #include -Error stage2_translate_c(struct Stage2Ast **out_ast, - struct Stage2ErrorMsg **out_errors_ptr, size_t *out_errors_len, - const char **args_begin, const char **args_end, const char *resources_path) -{ - const char *msg = "stage0 called stage2_translate_c"; - stage2_panic(msg, strlen(msg)); -} - -void stage2_free_clang_errors(struct Stage2ErrorMsg *ptr, size_t len) { - const char *msg = "stage0 called stage2_free_clang_errors"; - stage2_panic(msg, strlen(msg)); -} - -void stage2_zen(const char **ptr, size_t *len) { - const char *msg = "stage0 called stage2_zen"; - stage2_panic(msg, strlen(msg)); -} - -int stage2_env(int argc, char** argv) { - const char *msg = "stage0 called stage2_env"; - stage2_panic(msg, strlen(msg)); -} - -int stage2_cc(int argc, char** argv, bool is_cpp) { - const char *msg = "stage0 called stage2_cc"; - stage2_panic(msg, strlen(msg)); -} - -void stage2_attach_segfault_handler(void) { } - void stage2_panic(const char *ptr, size_t len) { fwrite(ptr, 1, len, stderr); fprintf(stderr, "\n"); @@ -46,32 +18,6 @@ void stage2_panic(const char *ptr, size_t len) { abort(); } -void stage2_render_ast(struct Stage2Ast *ast, FILE *output_file) { - const char *msg = "stage0 called stage2_render_ast"; - stage2_panic(msg, strlen(msg)); -} - -int stage2_fmt(int argc, char **argv) { - const char *msg = "stage0 called stage2_fmt"; - stage2_panic(msg, strlen(msg)); -} - -stage2_DepTokenizer stage2_DepTokenizer_init(const char *input, size_t len) { - const char *msg = "stage0 called stage2_DepTokenizer_init"; - stage2_panic(msg, strlen(msg)); -} - -void stage2_DepTokenizer_deinit(stage2_DepTokenizer *self) { - const char *msg = "stage0 called stage2_DepTokenizer_deinit"; - stage2_panic(msg, strlen(msg)); -} - -stage2_DepNextResult stage2_DepTokenizer_next(stage2_DepTokenizer *self) { - const char *msg = "stage0 called stage2_DepTokenizer_next"; - stage2_panic(msg, strlen(msg)); -} - - struct Stage2Progress { int trash; }; @@ -196,10 +142,6 @@ static void get_native_target(ZigTarget *target) { if (target->abi == ZigLLVM_UnknownEnvironment) { target->abi = target_default_abi(target->arch, target->os); } - if (target_is_glibc(target)) { - target->glibc_or_darwin_version = heap::c_allocator.create(); - target_init_default_glibc_version(target); - } } Error stage2_target_parse(struct ZigTarget *target, const char *zig_triple, const char *mcpu, @@ -217,13 +159,11 @@ Error stage2_target_parse(struct ZigTarget *target, const char *zig_triple, cons if (mcpu == nullptr) { target->llvm_cpu_name = ZigLLVMGetHostCPUName(); target->llvm_cpu_features = ZigLLVMGetNativeFeatures(); - target->cache_hash = "native\n\n"; } else if (strcmp(mcpu, "baseline") == 0) { target->is_native_os = false; target->is_native_cpu = false; target->llvm_cpu_name = ""; target->llvm_cpu_features = ""; - target->cache_hash = "baseline\n\n"; } else { const char *msg = "stage0 can't handle CPU/features in the target"; stage2_panic(msg, strlen(msg)); @@ -264,11 +204,8 @@ Error stage2_target_parse(struct ZigTarget *target, const char *zig_triple, cons const char *msg = "stage0 can't handle CPU/features in the target"; stage2_panic(msg, strlen(msg)); } - target->cache_hash = "\n\n"; } - target->cache_hash_len = strlen(target->cache_hash); - if (dynamic_linker != nullptr) { target->dynamic_linker = dynamic_linker; } @@ -276,49 +213,29 @@ Error stage2_target_parse(struct ZigTarget *target, const char *zig_triple, cons return ErrorNone; } -int stage2_cmd_targets(const char *zig_triple, const char *mcpu, const char *dynamic_linker) { - const char *msg = "stage0 called stage2_cmd_targets"; +const char *stage2_fetch_file(struct ZigStage1 *stage1, const char *path_ptr, size_t path_len, + size_t *result_len) +{ + Error err; + Buf contents_buf = BUF_INIT; + Buf path_buf = BUF_INIT; + + buf_init_from_mem(&path_buf, path_ptr, path_len); + if ((err = os_fetch_file_path(&path_buf, &contents_buf))) { + return nullptr; + } + *result_len = buf_len(&contents_buf); + return buf_ptr(&contents_buf); +} + +const char *stage2_cimport(struct ZigStage1 *stage1) { + const char *msg = "stage0 called stage2_cimport"; stage2_panic(msg, strlen(msg)); } -enum Error stage2_libc_parse(struct Stage2LibCInstallation *libc, const char *libc_file) { - libc->include_dir = "/dummy/include"; - libc->include_dir_len = strlen(libc->include_dir); - libc->sys_include_dir = "/dummy/sys/include"; - libc->sys_include_dir_len = strlen(libc->sys_include_dir); - libc->crt_dir = ""; - libc->crt_dir_len = strlen(libc->crt_dir); - libc->msvc_lib_dir = ""; - libc->msvc_lib_dir_len = strlen(libc->msvc_lib_dir); - libc->kernel32_lib_dir = ""; - libc->kernel32_lib_dir_len = strlen(libc->kernel32_lib_dir); - return ErrorNone; +const char *stage2_add_link_lib(struct ZigStage1 *stage1, + const char *lib_name_ptr, size_t lib_name_len, + const char *symbol_name_ptr, size_t symbol_name_len) +{ + return nullptr; } - -enum Error stage2_libc_render(struct Stage2LibCInstallation *self, FILE *file) { - const char *msg = "stage0 called stage2_libc_render"; - stage2_panic(msg, strlen(msg)); -} - -enum Error stage2_libc_find_native(struct Stage2LibCInstallation *libc) { - const char *msg = "stage0 called stage2_libc_find_native"; - stage2_panic(msg, strlen(msg)); -} - -enum Error stage2_detect_native_paths(struct Stage2NativePaths *native_paths) { - native_paths->include_dirs_ptr = nullptr; - native_paths->include_dirs_len = 0; - - native_paths->lib_dirs_ptr = nullptr; - native_paths->lib_dirs_len = 0; - - native_paths->rpaths_ptr = nullptr; - native_paths->rpaths_len = 0; - - native_paths->warnings_ptr = nullptr; - native_paths->warnings_len = 0; - - return ErrorNone; -} - -const bool stage2_is_zig0 = true; diff --git a/src/stage2.h b/src/stage2.h index 2e64189450..4bc92631dc 100644 --- a/src/stage2.h +++ b/src/stage2.h @@ -5,6 +5,8 @@ * See http://opensource.org/licenses/MIT */ +// This file deals with exposing stage2 Zig code to stage1 C++ code. + #ifndef ZIG_STAGE2_H #define ZIG_STAGE2_H @@ -12,7 +14,7 @@ #include #include -#include "zig_llvm.h" +#include "stage1.h" #ifdef __cplusplus #define ZIG_EXTERN_C extern "C" @@ -27,7 +29,7 @@ #endif // ABI warning: the types and declarations in this file must match both those in -// stage2.cpp and src-self-hosted/stage2.zig. +// stage2.cpp and src-self-hosted/stage1.zig. // ABI warning enum Error { @@ -124,74 +126,9 @@ struct Stage2ErrorMsg { unsigned offset; // byte offset into source }; -// ABI warning -struct Stage2Ast; - -// ABI warning -ZIG_EXTERN_C enum Error stage2_translate_c(struct Stage2Ast **out_ast, - struct Stage2ErrorMsg **out_errors_ptr, size_t *out_errors_len, - const char **args_begin, const char **args_end, const char *resources_path); - -// ABI warning -ZIG_EXTERN_C void stage2_free_clang_errors(struct Stage2ErrorMsg *ptr, size_t len); - -// ABI warning -ZIG_EXTERN_C void stage2_render_ast(struct Stage2Ast *ast, FILE *output_file); - -// ABI warning -ZIG_EXTERN_C void stage2_zen(const char **ptr, size_t *len); - -// ABI warning -ZIG_EXTERN_C int stage2_env(int argc, char **argv); - -// ABI warning -ZIG_EXTERN_C int stage2_cc(int argc, char **argv, bool is_cpp); - -// ABI warning -ZIG_EXTERN_C void stage2_attach_segfault_handler(void); - // ABI warning ZIG_EXTERN_C ZIG_ATTRIBUTE_NORETURN void stage2_panic(const char *ptr, size_t len); -// ABI warning -ZIG_EXTERN_C int stage2_fmt(int argc, char **argv); - -// ABI warning -struct stage2_DepTokenizer { - void *handle; -}; - -// ABI warning -struct stage2_DepNextResult { - enum TypeId { - error, - null, - target, - prereq, - }; - - TypeId type_id; - - // when ent == error --> error text - // when ent == null --> undefined - // when ent == target --> target pathname - // when ent == prereq --> prereq pathname - const char *textz; -}; - -// ABI warning -ZIG_EXTERN_C stage2_DepTokenizer stage2_DepTokenizer_init(const char *input, size_t len); - -// ABI warning -ZIG_EXTERN_C void stage2_DepTokenizer_deinit(stage2_DepTokenizer *self); - -// ABI warning -ZIG_EXTERN_C stage2_DepNextResult stage2_DepTokenizer_next(stage2_DepTokenizer *self); - -// ABI warning -struct Stage2Progress; -// ABI warning -struct Stage2ProgressNode; // ABI warning ZIG_EXTERN_C Stage2Progress *stage2_progress_create(void); // ABI warning @@ -212,69 +149,6 @@ ZIG_EXTERN_C void stage2_progress_complete_one(Stage2ProgressNode *node); ZIG_EXTERN_C void stage2_progress_update_node(Stage2ProgressNode *node, size_t completed_count, size_t estimated_total_items); -// ABI warning -struct Stage2LibCInstallation { - const char *include_dir; - size_t include_dir_len; - const char *sys_include_dir; - size_t sys_include_dir_len; - const char *crt_dir; - size_t crt_dir_len; - const char *msvc_lib_dir; - size_t msvc_lib_dir_len; - const char *kernel32_lib_dir; - size_t kernel32_lib_dir_len; -}; - -// ABI warning -ZIG_EXTERN_C enum Error stage2_libc_parse(struct Stage2LibCInstallation *libc, const char *libc_file); -// ABI warning -ZIG_EXTERN_C enum Error stage2_libc_render(struct Stage2LibCInstallation *self, FILE *file); -// ABI warning -ZIG_EXTERN_C enum Error stage2_libc_find_native(struct Stage2LibCInstallation *libc); - -// ABI warning -// Synchronize with target.cpp::os_list -enum Os { - OsFreestanding, - OsAnanas, - OsCloudABI, - OsDragonFly, - OsFreeBSD, - OsFuchsia, - OsIOS, - OsKFreeBSD, - OsLinux, - OsLv2, // PS3 - OsMacOSX, - OsNetBSD, - OsOpenBSD, - OsSolaris, - OsWindows, - OsHaiku, - OsMinix, - OsRTEMS, - OsNaCl, // Native Client - OsCNK, // BG/P Compute-Node Kernel - OsAIX, - OsCUDA, // NVIDIA CUDA - OsNVCL, // NVIDIA OpenCL - OsAMDHSA, // AMD HSA Runtime - OsPS4, - OsELFIAMCU, - OsTvOS, // Apple tvOS - OsWatchOS, // Apple watchOS - OsMesa3D, - OsContiki, - OsAMDPAL, - OsHermitCore, - OsHurd, - OsWASI, - OsEmscripten, - OsUefi, - OsOther, -}; - // ABI warning struct Stage2SemVer { uint32_t major; @@ -282,56 +156,20 @@ struct Stage2SemVer { uint32_t patch; }; -// ABI warning -struct ZigTarget { - enum ZigLLVM_ArchType arch; - enum ZigLLVM_VendorType vendor; - - enum ZigLLVM_EnvironmentType abi; - Os os; - - bool is_native_os; - bool is_native_cpu; - - // null means default. this is double-purposed to be darwin min version - struct Stage2SemVer *glibc_or_darwin_version; - - const char *llvm_cpu_name; - const char *llvm_cpu_features; - const char *cpu_builtin_str; - const char *cache_hash; - size_t cache_hash_len; - const char *os_builtin_str; - const char *dynamic_linker; - const char *standard_dynamic_linker_path; - - const char **llvm_cpu_features_asm_ptr; - size_t llvm_cpu_features_asm_len; -}; - // ABI warning ZIG_EXTERN_C enum Error stage2_target_parse(struct ZigTarget *target, const char *zig_triple, const char *mcpu, const char *dynamic_linker); // ABI warning -ZIG_EXTERN_C int stage2_cmd_targets(const char *zig_triple, const char *mcpu, const char *dynamic_linker); - +ZIG_EXTERN_C const char *stage2_fetch_file(struct ZigStage1 *stage1, const char *path_ptr, size_t path_len, + size_t *result_len); // ABI warning -struct Stage2NativePaths { - const char **include_dirs_ptr; - size_t include_dirs_len; - const char **lib_dirs_ptr; - size_t lib_dirs_len; - const char **rpaths_ptr; - size_t rpaths_len; - const char **warnings_ptr; - size_t warnings_len; -}; -// ABI warning -ZIG_EXTERN_C enum Error stage2_detect_native_paths(struct Stage2NativePaths *native_paths); +ZIG_EXTERN_C const char *stage2_cimport(struct ZigStage1 *stage1); // ABI warning -ZIG_EXTERN_C const bool stage2_is_zig0; +ZIG_EXTERN_C const char *stage2_add_link_lib(struct ZigStage1 *stage1, + const char *lib_name_ptr, size_t lib_name_len, + const char *symbol_name_ptr, size_t symbol_name_len); #endif diff --git a/src/target.cpp b/src/target.cpp index dff134a01d..f1cab8eded 100644 --- a/src/target.cpp +++ b/src/target.cpp @@ -10,8 +10,6 @@ #include "target.hpp" #include "util.hpp" #include "os.hpp" -#include "compiler.hpp" -#include "glibc.hpp" #include @@ -346,33 +344,6 @@ const char *target_abi_name(ZigLLVM_EnvironmentType abi) { return ZigLLVMGetEnvironmentTypeName(abi); } -Error target_parse_glibc_version(Stage2SemVer *glibc_ver, const char *text) { - glibc_ver->major = 2; - glibc_ver->minor = 0; - glibc_ver->patch = 0; - SplitIterator it = memSplit(str(text), str("GLIBC_.")); - { - Optional> opt_component = SplitIterator_next(&it); - if (!opt_component.is_some) return ErrorUnknownABI; - glibc_ver->major = strtoul(buf_ptr(buf_create_from_slice(opt_component.value)), nullptr, 10); - } - { - Optional> opt_component = SplitIterator_next(&it); - if (!opt_component.is_some) return ErrorNone; - glibc_ver->minor = strtoul(buf_ptr(buf_create_from_slice(opt_component.value)), nullptr, 10); - } - { - Optional> opt_component = SplitIterator_next(&it); - if (!opt_component.is_some) return ErrorNone; - glibc_ver->patch = strtoul(buf_ptr(buf_create_from_slice(opt_component.value)), nullptr, 10); - } - return ErrorNone; -} - -void target_init_default_glibc_version(ZigTarget *target) { - *target->glibc_or_darwin_version = {2, 17, 0}; -} - Error target_parse_arch(ZigLLVM_ArchType *out_arch, const char *arch_ptr, size_t arch_len) { *out_arch = ZigLLVM_UnknownArch; for (size_t arch_i = 0; arch_i < array_length(arch_list); arch_i += 1) { @@ -756,66 +727,6 @@ const char *target_llvm_ir_file_ext(const ZigTarget *target) { return ".ll"; } -const char *target_exe_file_ext(const ZigTarget *target) { - if (target->os == OsWindows) { - return ".exe"; - } else if (target->os == OsUefi) { - return ".efi"; - } else if (target_is_wasm(target)) { - return ".wasm"; - } else { - return ""; - } -} - -const char *target_lib_file_prefix(const ZigTarget *target) { - if ((target->os == OsWindows && !target_abi_is_gnu(target->abi)) || - target->os == OsUefi || - target_is_wasm(target)) - { - return ""; - } else { - return "lib"; - } -} - -const char *target_lib_file_ext(const ZigTarget *target, bool is_static, bool is_versioned, - size_t version_major, size_t version_minor, size_t version_patch) -{ - if (target_is_wasm(target)) { - return ".wasm"; - } - if (target->os == OsWindows || target->os == OsUefi) { - if (is_static) { - if (target->os == OsWindows && target_abi_is_gnu(target->abi)) { - return ".a"; - } else { - return ".lib"; - } - } else { - return ".dll"; - } - } else { - if (is_static) { - return ".a"; - } else if (target_os_is_darwin(target->os)) { - if (is_versioned) { - return buf_ptr(buf_sprintf(".%" ZIG_PRI_usize ".%" ZIG_PRI_usize ".%" ZIG_PRI_usize ".dylib", - version_major, version_minor, version_patch)); - } else { - return ".dylib"; - } - } else { - if (is_versioned) { - return buf_ptr(buf_sprintf(".so.%" ZIG_PRI_usize ".%" ZIG_PRI_usize ".%" ZIG_PRI_usize, - version_major, version_minor, version_patch)); - } else { - return ".so"; - } - } - } -} - bool target_is_android(const ZigTarget *target) { return target->abi == ZigLLVM_Android; } @@ -992,40 +903,6 @@ bool target_os_requires_libc(Os os) { return (target_os_is_darwin(os) || os == OsFreeBSD || os == OsNetBSD || os == OsDragonFly); } -bool target_supports_fpic(const ZigTarget *target) { - // This is not whether the target supports Position Independent Code, but whether the -fPIC - // C compiler argument is valid. - return target->os != OsWindows; -} - -bool target_supports_clang_march_native(const ZigTarget *target) { - // Whether clang supports -march=native on this target. - // Arguably it should always work, but in reality it gives: - // error: the clang compiler does not support '-march=native' - // If we move CPU detection logic into Zig itelf, we will not need this, - // instead we will always pass target features and CPU configuration explicitly. - return target->arch != ZigLLVM_aarch64 && - target->arch != ZigLLVM_aarch64_be; -} - -bool target_supports_stack_probing(const ZigTarget *target) { - return target->os != OsWindows && target->os != OsUefi && (target->arch == ZigLLVM_x86 || target->arch == ZigLLVM_x86_64); -} - -bool target_supports_sanitize_c(const ZigTarget *target) { - return true; -} - -bool target_requires_pic(const ZigTarget *target, bool linking_libc) { - // This function returns whether non-pic code is completely invalid on the given target. - return target_is_android(target) || target->os == OsWindows || target->os == OsUefi || target_os_requires_libc(target->os) || - (linking_libc && target_is_glibc(target)); -} - -bool target_requires_pie(const ZigTarget *target) { - return target_is_android(target); -} - bool target_is_glibc(const ZigTarget *target) { return target->os == OsLinux && target_abi_is_gnu(target->abi); } @@ -1038,10 +915,6 @@ bool target_is_wasm(const ZigTarget *target) { return target->arch == ZigLLVM_wasm32 || target->arch == ZigLLVM_wasm64; } -bool target_is_single_threaded(const ZigTarget *target) { - return target_is_wasm(target); -} - ZigLLVM_EnvironmentType target_default_abi(ZigLLVM_ArchType arch, Os os) { if (arch == ZigLLVM_wasm32 || arch == ZigLLVM_wasm64) { return ZigLLVM_Musl; diff --git a/src/target.hpp b/src/target.hpp index 5e44301fff..c9db4754f9 100644 --- a/src/target.hpp +++ b/src/target.hpp @@ -12,22 +12,6 @@ struct Buf; -enum TargetSubsystem { - TargetSubsystemConsole, - TargetSubsystemWindows, - TargetSubsystemPosix, - TargetSubsystemNative, - TargetSubsystemEfiApplication, - TargetSubsystemEfiBootServiceDriver, - TargetSubsystemEfiRom, - TargetSubsystemEfiRuntimeDriver, - - // This means Zig should infer the subsystem. - // It's last so that the indexes of other items can line up - // with the enum in builtin.zig. - TargetSubsystemAuto -}; - enum CIntType { CIntTypeShort, CIntTypeUShort, @@ -46,9 +30,6 @@ Error target_parse_arch(ZigLLVM_ArchType *arch, const char *arch_ptr, size_t arc Error target_parse_os(Os *os, const char *os_ptr, size_t os_len); Error target_parse_abi(ZigLLVM_EnvironmentType *abi, const char *abi_ptr, size_t abi_len); -Error target_parse_glibc_version(Stage2SemVer *out, const char *text); -void target_init_default_glibc_version(ZigTarget *target); - size_t target_arch_count(void); ZigLLVM_ArchType target_arch_enum(size_t index); const char *target_arch_name(ZigLLVM_ArchType arch); @@ -85,10 +66,6 @@ uint32_t target_c_type_size_in_bits(const ZigTarget *target, CIntType id); const char *target_o_file_ext(const ZigTarget *target); const char *target_asm_file_ext(const ZigTarget *target); const char *target_llvm_ir_file_ext(const ZigTarget *target); -const char *target_exe_file_ext(const ZigTarget *target); -const char *target_lib_file_prefix(const ZigTarget *target); -const char *target_lib_file_ext(const ZigTarget *target, bool is_static, bool is_versioned, - size_t version_major, size_t version_minor, size_t version_patch); bool target_can_exec(const ZigTarget *host_target, const ZigTarget *guest_target); ZigLLVM_OSType get_llvm_os_type(Os os_type); @@ -104,10 +81,6 @@ bool target_can_build_libc(const ZigTarget *target); const char *target_libc_generic_name(const ZigTarget *target); bool target_is_libc_lib_name(const ZigTarget *target, const char *name); bool target_is_libcpp_lib_name(const ZigTarget *target, const char *name); -bool target_supports_fpic(const ZigTarget *target); -bool target_supports_clang_march_native(const ZigTarget *target); -bool target_requires_pic(const ZigTarget *target, bool linking_libc); -bool target_requires_pie(const ZigTarget *target); bool target_abi_is_gnu(ZigLLVM_EnvironmentType abi); bool target_abi_is_musl(ZigLLVM_EnvironmentType abi); bool target_is_glibc(const ZigTarget *target); @@ -115,9 +88,6 @@ bool target_is_musl(const ZigTarget *target); bool target_is_wasm(const ZigTarget *target); bool target_is_riscv(const ZigTarget *target); bool target_is_android(const ZigTarget *target); -bool target_is_single_threaded(const ZigTarget *target); -bool target_supports_stack_probing(const ZigTarget *target); -bool target_supports_sanitize_c(const ZigTarget *target); bool target_has_debug_info(const ZigTarget *target); const char *target_arch_musl_name(ZigLLVM_ArchType arch); diff --git a/src/zig0.cpp b/src/zig0.cpp new file mode 100644 index 0000000000..ad90a17eb3 --- /dev/null +++ b/src/zig0.cpp @@ -0,0 +1,307 @@ +/* + * Copyright (c) 2015 Andrew Kelley + * + * This file is part of zig, which is MIT licensed. + * See http://opensource.org/licenses/MIT + */ + +// This file is the entry point for zig0, which is *only* used to build +// stage2, the self-hosted compiler, into an object file, which is then +// linked by the same build system (cmake) that linked this binary. + +#include "stage1.h" +#include "heap.hpp" +#include "stage2.h" +#include "target.hpp" +#include "error.hpp" + +#include +#include + +static int print_error_usage(const char *arg0) { + fprintf(stderr, "See `%s --help` for detailed usage information\n", arg0); + return EXIT_FAILURE; +} + +static int print_full_usage(const char *arg0, FILE *file, int return_code) { + fprintf(file, + "Usage: %s [options] builds an object file\n" + "\n" + "Options:\n" + " --color [auto|off|on] enable or disable colored error messages\n" + " --name [name] override output name\n" + " --output-dir [dir] override output directory (defaults to cwd)\n" + " --pkg-begin [name] [path] make pkg available to import and push current pkg\n" + " --pkg-end pop current pkg\n" + " --main-pkg-path set the directory of the root package\n" + " --release-fast build with optimizations on and safety off\n" + " --release-safe build with optimizations on and safety on\n" + " --release-small build with size optimizations on and safety off\n" + " --single-threaded source may assume it is only used single-threaded\n" + " -dynamic create a shared library (.so; .dll; .dylib)\n" + " --strip exclude debug symbols\n" + " -target [name] -- see the targets command\n" + " -mcpu [cpu] specify target CPU and feature set\n" + " --verbose-tokenize enable compiler debug output for tokenization\n" + " --verbose-ast enable compiler debug output for AST parsing\n" + " --verbose-link enable compiler debug output for linking\n" + " --verbose-ir enable compiler debug output for Zig IR\n" + " --verbose-llvm-ir enable compiler debug output for LLVM IR\n" + " --verbose-cimport enable compiler debug output for C imports\n" + " --verbose-cc enable compiler debug output for C compilation\n" + " --verbose-llvm-cpu-features enable compiler debug output for LLVM CPU features\n" + "\n" + , arg0); + return return_code; +} + +static bool str_starts_with(const char *s1, const char *s2) { + size_t s2_len = strlen(s2); + if (strlen(s1) < s2_len) { + return false; + } + return memcmp(s1, s2, s2_len) == 0; +} + +int main_exit(Stage2ProgressNode *root_progress_node, int exit_code) { + if (root_progress_node != nullptr) { + stage2_progress_end(root_progress_node); + } + return exit_code; +} + +int main(int argc, char **argv) { + zig_stage1_os_init(); + + char *arg0 = argv[0]; + Error err; + + const char *in_file = nullptr; + const char *output_dir = nullptr; + bool strip = false; + const char *out_name = nullptr; + bool verbose_tokenize = false; + bool verbose_ast = false; + bool verbose_link = false; + bool verbose_ir = false; + bool verbose_llvm_ir = false; + bool verbose_cimport = false; + bool verbose_cc = false; + bool verbose_llvm_cpu_features = false; + ErrColor color = ErrColorAuto; + const char *dynamic_linker = nullptr; + bool link_libc = false; + bool link_libcpp = false; + const char *target_string = nullptr; + ZigStage1Pkg *cur_pkg = heap::c_allocator.create(); + BuildMode build_mode = BuildModeDebug; + TargetSubsystem subsystem = TargetSubsystemAuto; + const char *override_lib_dir = nullptr; + const char *main_pkg_path = nullptr; + const char *mcpu = nullptr; + + for (int i = 1; i < argc; i += 1) { + char *arg = argv[i]; + + if (arg[0] == '-') { + if (strcmp(arg, "--") == 0) { + fprintf(stderr, "Unexpected end-of-parameter mark: %s\n", arg); + } else if (strcmp(arg, "--release-fast") == 0) { + build_mode = BuildModeFastRelease; + } else if (strcmp(arg, "--release-safe") == 0) { + build_mode = BuildModeSafeRelease; + } else if (strcmp(arg, "--release-small") == 0) { + build_mode = BuildModeSmallRelease; + } else if (strcmp(arg, "--help") == 0) { + return print_full_usage(arg0, stdout, EXIT_SUCCESS); + } else if (strcmp(arg, "--strip") == 0) { + strip = true; + } else if (strcmp(arg, "--verbose-tokenize") == 0) { + verbose_tokenize = true; + } else if (strcmp(arg, "--verbose-ast") == 0) { + verbose_ast = true; + } else if (strcmp(arg, "--verbose-link") == 0) { + verbose_link = true; + } else if (strcmp(arg, "--verbose-ir") == 0) { + verbose_ir = true; + } else if (strcmp(arg, "--verbose-llvm-ir") == 0) { + verbose_llvm_ir = true; + } else if (strcmp(arg, "--verbose-cimport") == 0) { + verbose_cimport = true; + } else if (strcmp(arg, "--verbose-cc") == 0) { + verbose_cc = true; + } else if (strcmp(arg, "--verbose-llvm-cpu-features") == 0) { + verbose_llvm_cpu_features = true; + } else if (arg[1] == 'l' && arg[2] != 0) { + // alias for --library + const char *l = &arg[2]; + if (strcmp(l, "c") == 0) { + link_libc = true; + } else if (strcmp(l, "c++") == 0 || strcmp(l, "stdc++") == 0) { + link_libcpp = true; + } + } else if (strcmp(arg, "--pkg-begin") == 0) { + if (i + 2 >= argc) { + fprintf(stderr, "Expected 2 arguments after --pkg-begin\n"); + return print_error_usage(arg0); + } + ZigStage1Pkg *new_cur_pkg = heap::c_allocator.create(); + i += 1; + new_cur_pkg->name_ptr = argv[i]; + new_cur_pkg->name_len = strlen(argv[i]); + i += 1; + new_cur_pkg->path_ptr = argv[i]; + new_cur_pkg->path_len = strlen(argv[i]); + new_cur_pkg->parent = cur_pkg; + cur_pkg->children_ptr = heap::c_allocator.reallocate(cur_pkg->children_ptr, + cur_pkg->children_len, cur_pkg->children_len + 1); + cur_pkg->children_ptr[cur_pkg->children_len] = new_cur_pkg; + cur_pkg->children_len += 1; + + cur_pkg = new_cur_pkg; + } else if (strcmp(arg, "--pkg-end") == 0) { + if (cur_pkg->parent == nullptr) { + fprintf(stderr, "Encountered --pkg-end with no matching --pkg-begin\n"); + return EXIT_FAILURE; + } + cur_pkg = cur_pkg->parent; + } else if (str_starts_with(arg, "-mcpu=")) { + mcpu = arg + strlen("-mcpu="); + } else if (i + 1 >= argc) { + fprintf(stderr, "Expected another argument after %s\n", arg); + return print_error_usage(arg0); + } else { + i += 1; + if (strcmp(arg, "--output-dir") == 0) { + output_dir = argv[i]; + } else if (strcmp(arg, "--color") == 0) { + if (strcmp(argv[i], "auto") == 0) { + color = ErrColorAuto; + } else if (strcmp(argv[i], "on") == 0) { + color = ErrColorOn; + } else if (strcmp(argv[i], "off") == 0) { + color = ErrColorOff; + } else { + fprintf(stderr, "--color options are 'auto', 'on', or 'off'\n"); + return print_error_usage(arg0); + } + } else if (strcmp(arg, "--name") == 0) { + out_name = argv[i]; + } else if (strcmp(arg, "--dynamic-linker") == 0) { + dynamic_linker = argv[i]; + } else if (strcmp(arg, "--override-lib-dir") == 0) { + override_lib_dir = argv[i]; + } else if (strcmp(arg, "--main-pkg-path") == 0) { + main_pkg_path = argv[i]; + } else if (strcmp(arg, "--library") == 0 || strcmp(arg, "-l") == 0) { + if (strcmp(argv[i], "c") == 0) { + link_libc = true; + } else if (strcmp(argv[i], "c++") == 0 || strcmp(argv[i], "stdc++") == 0) { + link_libcpp = true; + } + } else if (strcmp(arg, "-target") == 0) { + target_string = argv[i]; + } else if (strcmp(arg, "--subsystem") == 0) { + if (strcmp(argv[i], "console") == 0) { + subsystem = TargetSubsystemConsole; + } else if (strcmp(argv[i], "windows") == 0) { + subsystem = TargetSubsystemWindows; + } else if (strcmp(argv[i], "posix") == 0) { + subsystem = TargetSubsystemPosix; + } else if (strcmp(argv[i], "native") == 0) { + subsystem = TargetSubsystemNative; + } else if (strcmp(argv[i], "efi_application") == 0) { + subsystem = TargetSubsystemEfiApplication; + } else if (strcmp(argv[i], "efi_boot_service_driver") == 0) { + subsystem = TargetSubsystemEfiBootServiceDriver; + } else if (strcmp(argv[i], "efi_rom") == 0) { + subsystem = TargetSubsystemEfiRom; + } else if (strcmp(argv[i], "efi_runtime_driver") == 0) { + subsystem = TargetSubsystemEfiRuntimeDriver; + } else { + fprintf(stderr, "invalid: --subsystem %s\n" + "Options are:\n" + " console\n" + " windows\n" + " posix\n" + " native\n" + " efi_application\n" + " efi_boot_service_driver\n" + " efi_rom\n" + " efi_runtime_driver\n" + , argv[i]); + return EXIT_FAILURE; + } + } else if (strcmp(arg, "-mcpu") == 0) { + mcpu = argv[i]; + } else { + fprintf(stderr, "Invalid argument: %s\n", arg); + return print_error_usage(arg0); + } + } + } else if (!in_file) { + in_file = arg; + } else { + fprintf(stderr, "Unexpected extra parameter: %s\n", arg); + return print_error_usage(arg0); + } + } + + if (cur_pkg->parent != nullptr) { + fprintf(stderr, "Unmatched --pkg-begin\n"); + return EXIT_FAILURE; + } + + Stage2Progress *progress = stage2_progress_create(); + Stage2ProgressNode *root_progress_node = stage2_progress_start_root(progress, "", 0, 0); + if (color == ErrColorOff) stage2_progress_disable_tty(progress); + + ZigTarget target; + if ((err = target_parse_triple(&target, target_string, mcpu, dynamic_linker))) { + fprintf(stderr, "invalid target: %s\n", err_str(err)); + return print_error_usage(arg0); + } + + if (in_file == nullptr) { + fprintf(stderr, "missing zig file\n"); + return print_error_usage(arg0); + } + + if (out_name == nullptr) { + fprintf(stderr, "missing --name\n"); + return print_error_usage(arg0); + } + + ZigStage1 *stage1 = zig_stage1_create(build_mode, + main_pkg_path, (main_pkg_path == nullptr) ? 0 : strlen(main_pkg_path), + in_file, strlen(in_file), + override_lib_dir, strlen(override_lib_dir), &target, false, + root_progress_node); + + stage1->root_name_ptr = out_name; + stage1->root_name_len = strlen(out_name); + stage1->strip = strip; + stage1->verbose_tokenize = verbose_tokenize; + stage1->verbose_ast = verbose_ast; + stage1->verbose_link = verbose_link; + stage1->verbose_ir = verbose_ir; + stage1->verbose_llvm_ir = verbose_llvm_ir; + stage1->verbose_cimport = verbose_cimport; + stage1->verbose_cc = verbose_cc; + stage1->verbose_llvm_cpu_features = verbose_llvm_cpu_features; + stage1->output_dir_ptr = output_dir; + stage1->output_dir_len = strlen(output_dir); + stage1->root_pkg = cur_pkg; + stage1->err_color = color; + stage1->link_libc = link_libc; + stage1->link_libcpp = link_libcpp; + stage1->subsystem = subsystem; + stage1->pic = true; + stage1->emit_bin = true; + + zig_stage1_build_object(stage1); + + zig_stage1_destroy(stage1); + + return main_exit(root_progress_node, EXIT_SUCCESS); +}