From a44085dc2ab81877fc71fb50e846454c2694a14c Mon Sep 17 00:00:00 2001 From: Guillaume Wenzek Date: Tue, 3 Jan 2023 12:05:09 +0100 Subject: [PATCH] add -fopt-bisect-limit --- src/Compilation.zig | 2 ++ src/codegen/llvm.zig | 4 ++++ src/codegen/llvm/bindings.zig | 3 +++ src/link.zig | 1 + src/main.zig | 5 +++++ src/zig_llvm.cpp | 13 +++++++++++++ src/zig_llvm.h | 2 ++ tools/stage2_gdb_pretty_printers.py | 5 +++++ 8 files changed, 35 insertions(+) diff --git a/src/Compilation.zig b/src/Compilation.zig index 4c7489c0c84696729c5985f811e9fc643f79e818..3aa9663ed543e91a4142a9e3a67a7f76a00bbe4c 100644 --- a/src/Compilation.zig +++ b/src/Compilation.zig @@ -968,6 +968,7 @@ pub const InitOptions = struct { linker_print_gc_sections: bool = false, linker_print_icf_sections: bool = false, linker_print_map: bool = false, + linker_opt_bisect_limit: i32 = -1, each_lib_rpath: ?bool = null, build_id: ?bool = null, disable_c_depfile: bool = false, @@ -1826,6 +1827,7 @@ pub fn create(gpa: Allocator, options: InitOptions) !*Compilation { .print_gc_sections = options.linker_print_gc_sections, .print_icf_sections = options.linker_print_icf_sections, .print_map = options.linker_print_map, + .opt_bisect_limit = options.linker_opt_bisect_limit, .z_nodelete = options.linker_z_nodelete, .z_notext = options.linker_z_notext, .z_defs = options.linker_z_defs, diff --git a/src/codegen/llvm.zig b/src/codegen/llvm.zig index c693beaabffe8a28c50adb39def1eee7233a310c..235949d1172e11219a41c63ec46d89f0171f7b76 100644 --- a/src/codegen/llvm.zig +++ b/src/codegen/llvm.zig @@ -520,6 +520,10 @@ pub const Object = struct { if (options.pie) llvm_module.setModulePIELevel(); if (code_model != .Default) llvm_module.setModuleCodeModel(code_model); + if (options.opt_bisect_limit >= 0) { + context.setOptBisectLimit(std.math.lossyCast(c_int, options.opt_bisect_limit)); + } + return Object{ .gpa = gpa, .module = options.module.?, diff --git a/src/codegen/llvm/bindings.zig b/src/codegen/llvm/bindings.zig index e1f2af347100e9c4de8ba24494db4171deb96bb1..c78c951eee0a80b74eb35009ff25190947b66d01 100644 --- a/src/codegen/llvm/bindings.zig +++ b/src/codegen/llvm/bindings.zig @@ -85,6 +85,9 @@ pub const Context = opaque { pub const createBuilder = LLVMCreateBuilderInContext; extern fn LLVMCreateBuilderInContext(C: *Context) *Builder; + + pub const setOptBisectLimit = ZigLLVMSetOptBisectLimit; + extern fn ZigLLVMSetOptBisectLimit(C: *Context, limit: c_int) void; }; pub const Value = opaque { diff --git a/src/link.zig b/src/link.zig index 33c5feb7277992776c7b53bfef646fe3b06413fa..0a526db0de431029a7cd4c428d230f2d2766ca5a 100644 --- a/src/link.zig +++ b/src/link.zig @@ -169,6 +169,7 @@ pub const Options = struct { print_gc_sections: bool, print_icf_sections: bool, print_map: bool, + opt_bisect_limit: i32, objects: []Compilation.LinkObject, framework_dirs: []const []const u8, diff --git a/src/main.zig b/src/main.zig index ffb65b43aa3426f52f3414c8b9f5f6464e241c89..421164de1cecf63aa00c0628e2fdc76d6db5a6fd 100644 --- a/src/main.zig +++ b/src/main.zig @@ -536,6 +536,7 @@ const usage_build_generic = \\ --test-runner [path] Specify a custom test runner \\ \\Debug Options (Zig Compiler Development): + \\ -fopt-bisect-limit [limit] Only run [limit] first LLVM optimization passes \\ -ftime-report Print timing diagnostics \\ -fstack-report Print stack size diagnostics \\ --verbose-link Display linker invocations @@ -729,6 +730,7 @@ fn buildOutputType( var linker_print_gc_sections: bool = false; var linker_print_icf_sections: bool = false; var linker_print_map: bool = false; + var linker_opt_bisect_limit: i32 = -1; var linker_z_nocopyreloc = false; var linker_z_nodelete = false; var linker_z_notext = false; @@ -1285,6 +1287,8 @@ fn buildOutputType( no_builtin = false; } else if (mem.eql(u8, arg, "-fno-builtin")) { no_builtin = true; + } else if (mem.startsWith(u8, arg, "-fopt-bisect-limit=")) { + linker_opt_bisect_limit = std.math.lossyCast(i32, parseIntSuffix(arg, "-fopt-bisect-limit=".len)); } else if (mem.eql(u8, arg, "--eh-frame-hdr")) { link_eh_frame_hdr = true; } else if (mem.eql(u8, arg, "--emit-relocs")) { @@ -2996,6 +3000,7 @@ fn buildOutputType( .linker_print_gc_sections = linker_print_gc_sections, .linker_print_icf_sections = linker_print_icf_sections, .linker_print_map = linker_print_map, + .linker_opt_bisect_limit = linker_opt_bisect_limit, .linker_global_base = linker_global_base, .linker_export_symbol_names = linker_export_symbol_names.items, .linker_z_nocopyreloc = linker_z_nocopyreloc, diff --git a/src/zig_llvm.cpp b/src/zig_llvm.cpp index c38e311f67903f90879f89e9eebcf499b62b66f9..4f73bd2c3c53b381728c5975e7a456f2f76ced79 100644 --- a/src/zig_llvm.cpp +++ b/src/zig_llvm.cpp @@ -31,6 +31,7 @@ #include #include #include +#include #include #include #include @@ -412,6 +413,18 @@ ZIG_EXTERN_C LLVMTypeRef ZigLLVMTokenTypeInContext(LLVMContextRef context_ref) { return wrap(Type::getTokenTy(*unwrap(context_ref))); } + +ZIG_EXTERN_C void ZigLLVMSetOptBisectLimit(LLVMContextRef context_ref, int limit) { + // In LLVM15 we just have an OptBisect singleton we can edit. + OptBisect& bisect = getOptBisector(); + bisect.setLimit(limit); + + // In LLVM16 OptBisect will be wrapped in OptPassGate, and will need to be set per context. + // static OptBisect _opt_bisector; + // _opt_bisector.setLimit(limit); + // unwrap(context_ref)->setOptPassGate(_opt_bisector); +} + LLVMValueRef ZigLLVMAddFunctionInAddressSpace(LLVMModuleRef M, const char *Name, LLVMTypeRef FunctionTy, unsigned AddressSpace) { Function* func = Function::Create(unwrap(FunctionTy), GlobalValue::ExternalLinkage, AddressSpace, Name, unwrap(M)); return wrap(func); diff --git a/src/zig_llvm.h b/src/zig_llvm.h index 7f9bd0a1619d30239a1ab92c3b9675d8c1bdb987..70c53f61a4fe8c03ed8790ad9061ab3e57b2809b 100644 --- a/src/zig_llvm.h +++ b/src/zig_llvm.h @@ -67,6 +67,8 @@ ZIG_EXTERN_C LLVMTargetMachineRef ZigLLVMCreateTargetMachine(LLVMTargetRef T, co ZIG_EXTERN_C LLVMTypeRef ZigLLVMTokenTypeInContext(LLVMContextRef context_ref); +ZIG_EXTERN_C void ZigLLVMSetOptBisectLimit(LLVMContextRef context_ref, int limit); + ZIG_EXTERN_C LLVMValueRef ZigLLVMAddFunctionInAddressSpace(LLVMModuleRef M, const char *Name, LLVMTypeRef FunctionTy, unsigned AddressSpace); diff --git a/tools/stage2_gdb_pretty_printers.py b/tools/stage2_gdb_pretty_printers.py index 5eca2fdec2ebab35829d959b36c0f6cfa031a99a..215b27699fa74d588b2e88816e1d4c938a3d07d2 100644 --- a/tools/stage2_gdb_pretty_printers.py +++ b/tools/stage2_gdb_pretty_printers.py @@ -2,8 +2,13 @@ # put "source /path/to/stage2_gdb_pretty_printers.py" in ~/.gdbinit to load it automatically. import re import gdb.printing + +import sys +from pathlib import Path +sys.path.insert(0, str(Path(__file__).parent)) import stage2_pretty_printers_common as common + class TypePrinter: def __init__(self, val): self.val = val -- 2.54.0