Each target can opt into different sets of legalize features. By performing these transformations before liveness, instructions that become unreferenced will have up-to-date liveness information.
120 lines
3.9 KiB
Zig
120 lines
3.9 KiB
Zig
//! Stub linker support for GOFF based on LLVM.
|
|
|
|
const Xcoff = @This();
|
|
|
|
const std = @import("std");
|
|
const builtin = @import("builtin");
|
|
|
|
const Allocator = std.mem.Allocator;
|
|
const assert = std.debug.assert;
|
|
const log = std.log.scoped(.link);
|
|
const Path = std.Build.Cache.Path;
|
|
|
|
const Zcu = @import("../Zcu.zig");
|
|
const InternPool = @import("../InternPool.zig");
|
|
const Compilation = @import("../Compilation.zig");
|
|
const link = @import("../link.zig");
|
|
const trace = @import("../tracy.zig").trace;
|
|
const build_options = @import("build_options");
|
|
const Air = @import("../Air.zig");
|
|
const LlvmObject = @import("../codegen/llvm.zig").Object;
|
|
|
|
base: link.File,
|
|
llvm_object: LlvmObject.Ptr,
|
|
|
|
pub fn createEmpty(
|
|
arena: Allocator,
|
|
comp: *Compilation,
|
|
emit: Path,
|
|
options: link.File.OpenOptions,
|
|
) !*Xcoff {
|
|
const target = comp.root_mod.resolved_target.result;
|
|
const use_lld = build_options.have_llvm and comp.config.use_lld;
|
|
const use_llvm = comp.config.use_llvm;
|
|
|
|
assert(use_llvm); // Caught by Compilation.Config.resolve.
|
|
assert(!use_lld); // Caught by Compilation.Config.resolve.
|
|
assert(target.os.tag == .aix); // Caught by Compilation.Config.resolve.
|
|
|
|
const llvm_object = try LlvmObject.create(arena, comp);
|
|
const xcoff = try arena.create(Xcoff);
|
|
xcoff.* = .{
|
|
.base = .{
|
|
.tag = .xcoff,
|
|
.comp = comp,
|
|
.emit = emit,
|
|
.zcu_object_sub_path = emit.sub_path,
|
|
.gc_sections = options.gc_sections orelse false,
|
|
.print_gc_sections = options.print_gc_sections,
|
|
.stack_size = options.stack_size orelse 0,
|
|
.allow_shlib_undefined = options.allow_shlib_undefined orelse false,
|
|
.file = null,
|
|
.disable_lld_caching = options.disable_lld_caching,
|
|
.build_id = options.build_id,
|
|
},
|
|
.llvm_object = llvm_object,
|
|
};
|
|
|
|
return xcoff;
|
|
}
|
|
|
|
pub fn open(
|
|
arena: Allocator,
|
|
comp: *Compilation,
|
|
emit: Path,
|
|
options: link.File.OpenOptions,
|
|
) !*Xcoff {
|
|
const target = comp.root_mod.resolved_target.result;
|
|
assert(target.ofmt == .xcoff);
|
|
return createEmpty(arena, comp, emit, options);
|
|
}
|
|
|
|
pub fn deinit(self: *Xcoff) void {
|
|
self.llvm_object.deinit();
|
|
}
|
|
|
|
pub fn updateFunc(
|
|
self: *Xcoff,
|
|
pt: Zcu.PerThread,
|
|
func_index: InternPool.Index,
|
|
air: Air,
|
|
liveness: Air.Liveness,
|
|
) link.File.UpdateNavError!void {
|
|
if (build_options.skip_non_native and builtin.object_format != .xcoff)
|
|
@panic("Attempted to compile for object format that was disabled by build configuration");
|
|
|
|
try self.llvm_object.updateFunc(pt, func_index, air, liveness);
|
|
}
|
|
|
|
pub fn updateNav(self: *Xcoff, pt: Zcu.PerThread, nav: InternPool.Nav.Index) link.File.UpdateNavError!void {
|
|
if (build_options.skip_non_native and builtin.object_format != .xcoff)
|
|
@panic("Attempted to compile for object format that was disabled by build configuration");
|
|
|
|
return self.llvm_object.updateNav(pt, nav);
|
|
}
|
|
|
|
pub fn updateExports(
|
|
self: *Xcoff,
|
|
pt: Zcu.PerThread,
|
|
exported: Zcu.Exported,
|
|
export_indices: []const Zcu.Export.Index,
|
|
) !void {
|
|
if (build_options.skip_non_native and builtin.object_format != .xcoff)
|
|
@panic("Attempted to compile for object format that was disabled by build configuration");
|
|
|
|
return self.llvm_object.updateExports(pt, exported, export_indices);
|
|
}
|
|
|
|
pub fn flush(self: *Xcoff, arena: Allocator, tid: Zcu.PerThread.Id, prog_node: std.Progress.Node) link.File.FlushError!void {
|
|
return self.flushModule(arena, tid, prog_node);
|
|
}
|
|
|
|
pub fn flushModule(self: *Xcoff, arena: Allocator, tid: Zcu.PerThread.Id, prog_node: std.Progress.Node) link.File.FlushError!void {
|
|
if (build_options.skip_non_native and builtin.object_format != .xcoff)
|
|
@panic("Attempted to compile for object format that was disabled by build configuration");
|
|
|
|
_ = tid;
|
|
|
|
try self.base.emitLlvmObject(arena, self.llvm_object, prog_node);
|
|
}
|