mirror of
https://github.com/ziglang/zig.git
synced 2026-02-13 04:48:20 +00:00
Merge pull request #20751 from Rexicon226/riscv-eflags
elf: add riscv eflag collisions
This commit is contained in:
commit
7aaebd1774
10
src/dev.zig
10
src/dev.zig
@ -26,6 +26,10 @@ pub const Env = enum {
|
||||
/// - `zig build-* -fno-llvm -fno-lld -target x86_64-linux`
|
||||
@"x86_64-linux",
|
||||
|
||||
/// - sema
|
||||
/// - `zig build-* -fno-llvm -fno-lld -target riscv64-linux`
|
||||
@"riscv64-linux",
|
||||
|
||||
pub inline fn supports(comptime dev_env: Env, comptime feature: Feature) bool {
|
||||
return switch (dev_env) {
|
||||
.full => true,
|
||||
@ -131,6 +135,12 @@ pub const Env = enum {
|
||||
=> true,
|
||||
else => Env.sema.supports(feature),
|
||||
},
|
||||
.@"riscv64-linux" => switch (feature) {
|
||||
.riscv64_backend,
|
||||
.elf_linker,
|
||||
=> true,
|
||||
else => Env.sema.supports(feature),
|
||||
},
|
||||
};
|
||||
}
|
||||
|
||||
|
||||
@ -229,6 +229,8 @@ comdat_groups_table: std.AutoHashMapUnmanaged(u32, ComdatGroupOwner.Index) = .{}
|
||||
/// such as `resolver` and `comdat_groups_table`.
|
||||
strings: StringTable = .{},
|
||||
|
||||
first_eflags: ?elf.Elf64_Word = null,
|
||||
|
||||
/// When allocating, the ideal_capacity is calculated by
|
||||
/// actual_capacity + (actual_capacity / ideal_factor)
|
||||
const ideal_factor = 3;
|
||||
@ -553,7 +555,7 @@ pub fn lowerAnonDecl(
|
||||
pt: Zcu.PerThread,
|
||||
decl_val: InternPool.Index,
|
||||
explicit_alignment: InternPool.Alignment,
|
||||
src_loc: Module.LazySrcLoc,
|
||||
src_loc: Zcu.LazySrcLoc,
|
||||
) !codegen.Result {
|
||||
return self.zigObjectPtr().?.lowerAnonDecl(self, pt, decl_val, explicit_alignment, src_loc);
|
||||
}
|
||||
@ -1161,7 +1163,11 @@ pub fn flushModule(self: *Elf, arena: Allocator, tid: Zcu.PerThread.Id, prog_nod
|
||||
|
||||
for (positionals.items) |obj| {
|
||||
self.parsePositional(obj.path, obj.must_link) catch |err| switch (err) {
|
||||
error.MalformedObject, error.MalformedArchive, error.InvalidCpuArch => continue, // already reported
|
||||
error.MalformedObject,
|
||||
error.MalformedArchive,
|
||||
error.MismatchedEflags,
|
||||
error.InvalidCpuArch,
|
||||
=> continue, // already reported
|
||||
else => |e| try self.reportParseError(
|
||||
obj.path,
|
||||
"unexpected error: parsing input file failed with error {s}",
|
||||
@ -1270,7 +1276,11 @@ pub fn flushModule(self: *Elf, arena: Allocator, tid: Zcu.PerThread.Id, prog_nod
|
||||
|
||||
for (positionals.items) |obj| {
|
||||
self.parsePositional(obj.path, obj.must_link) catch |err| switch (err) {
|
||||
error.MalformedObject, error.MalformedArchive, error.InvalidCpuArch => continue, // already reported
|
||||
error.MalformedObject,
|
||||
error.MalformedArchive,
|
||||
error.MismatchedEflags,
|
||||
error.InvalidCpuArch,
|
||||
=> continue, // already reported
|
||||
else => |e| try self.reportParseError(
|
||||
obj.path,
|
||||
"unexpected error: parsing input file failed with error {s}",
|
||||
@ -1700,6 +1710,7 @@ pub const ParseError = error{
|
||||
MalformedObject,
|
||||
MalformedArchive,
|
||||
InvalidCpuArch,
|
||||
MismatchedEflags,
|
||||
OutOfMemory,
|
||||
Overflow,
|
||||
InputOutput,
|
||||
@ -1879,6 +1890,48 @@ fn parseLdScript(self: *Elf, lib: SystemLib) ParseError!void {
|
||||
}
|
||||
}
|
||||
|
||||
pub fn validateEFlags(self: *Elf, file_index: File.Index, e_flags: elf.Elf64_Word) !void {
|
||||
const target = self.base.comp.root_mod.resolved_target.result;
|
||||
|
||||
if (self.first_eflags == null) {
|
||||
self.first_eflags = e_flags;
|
||||
return; // there isn't anything to conflict with yet
|
||||
}
|
||||
const self_eflags: *elf.Elf64_Word = &self.first_eflags.?;
|
||||
|
||||
switch (target.cpu.arch) {
|
||||
.riscv64 => {
|
||||
if (e_flags != self_eflags.*) {
|
||||
const riscv_eflags: riscv.RiscvEflags = @bitCast(e_flags);
|
||||
const self_riscv_eflags: *riscv.RiscvEflags = @ptrCast(self_eflags);
|
||||
|
||||
self_riscv_eflags.rvc = self_riscv_eflags.rvc or riscv_eflags.rvc;
|
||||
self_riscv_eflags.tso = self_riscv_eflags.tso or riscv_eflags.tso;
|
||||
|
||||
var is_error: bool = false;
|
||||
if (self_riscv_eflags.fabi != riscv_eflags.fabi) {
|
||||
is_error = true;
|
||||
_ = try self.reportParseError2(
|
||||
file_index,
|
||||
"cannot link object files with different float-point ABIs",
|
||||
.{},
|
||||
);
|
||||
}
|
||||
if (self_riscv_eflags.rve != riscv_eflags.rve) {
|
||||
is_error = true;
|
||||
_ = try self.reportParseError2(
|
||||
file_index,
|
||||
"cannot link object files with different RVEs",
|
||||
.{},
|
||||
);
|
||||
}
|
||||
if (is_error) return error.MismatchedEflags;
|
||||
}
|
||||
},
|
||||
else => {},
|
||||
}
|
||||
}
|
||||
|
||||
fn accessLibPath(
|
||||
self: *Elf,
|
||||
arena: Allocator,
|
||||
@ -3025,7 +3078,7 @@ pub fn lowerUnnamedConst(self: *Elf, pt: Zcu.PerThread, val: Value, decl_index:
|
||||
pub fn updateExports(
|
||||
self: *Elf,
|
||||
pt: Zcu.PerThread,
|
||||
exported: Module.Exported,
|
||||
exported: Zcu.Exported,
|
||||
export_indices: []const u32,
|
||||
) link.File.UpdateExportsError!void {
|
||||
if (build_options.skip_non_native and builtin.object_format != .elf) {
|
||||
@ -6432,8 +6485,6 @@ const LlvmObject = @import("../codegen/llvm.zig").Object;
|
||||
const MergeSection = merge_section.MergeSection;
|
||||
const MergeSubsection = merge_section.MergeSubsection;
|
||||
const Zcu = @import("../Zcu.zig");
|
||||
/// Deprecated.
|
||||
const Module = Zcu;
|
||||
const Object = @import("Elf/Object.zig");
|
||||
const InternPool = @import("../InternPool.zig");
|
||||
const PltSection = synthetic_sections.PltSection;
|
||||
@ -6446,3 +6497,4 @@ const Value = @import("../Value.zig");
|
||||
const VerneedSection = synthetic_sections.VerneedSection;
|
||||
const ZigGotSection = synthetic_sections.ZigGotSection;
|
||||
const ZigObject = @import("Elf/ZigObject.zig");
|
||||
const riscv = @import("riscv.zig");
|
||||
|
||||
@ -93,6 +93,7 @@ fn parseCommon(self: *Object, allocator: Allocator, handle: std.fs.File, elf_fil
|
||||
);
|
||||
return error.InvalidCpuArch;
|
||||
}
|
||||
try elf_file.validateEFlags(self.index, self.header.?.e_flags);
|
||||
|
||||
if (self.header.?.e_shnum == 0) return;
|
||||
|
||||
|
||||
@ -19,7 +19,11 @@ pub fn flushStaticLib(elf_file: *Elf, comp: *Compilation, module_obj_path: ?[]co
|
||||
|
||||
for (positionals.items) |obj| {
|
||||
parsePositional(elf_file, obj.path) catch |err| switch (err) {
|
||||
error.MalformedObject, error.MalformedArchive, error.InvalidCpuArch => continue, // already reported
|
||||
error.MalformedObject,
|
||||
error.MalformedArchive,
|
||||
error.InvalidCpuArch,
|
||||
error.MismatchedEflags,
|
||||
=> continue, // already reported
|
||||
error.UnknownFileType => try elf_file.reportParseError(obj.path, "unknown file type for an object file", .{}),
|
||||
else => |e| try elf_file.reportParseError(
|
||||
obj.path,
|
||||
@ -168,7 +172,11 @@ pub fn flushObject(elf_file: *Elf, comp: *Compilation, module_obj_path: ?[]const
|
||||
|
||||
for (positionals.items) |obj| {
|
||||
elf_file.parsePositional(obj.path, obj.must_link) catch |err| switch (err) {
|
||||
error.MalformedObject, error.MalformedArchive, error.InvalidCpuArch => continue, // already reported
|
||||
error.MalformedObject,
|
||||
error.MalformedArchive,
|
||||
error.InvalidCpuArch,
|
||||
error.MismatchedEflags,
|
||||
=> continue, // already reported
|
||||
else => |e| try elf_file.reportParseError(
|
||||
obj.path,
|
||||
"unexpected error: parsing input file failed with error {s}",
|
||||
|
||||
@ -95,6 +95,20 @@ fn bitSlice(
|
||||
return @truncate((value >> low) & (1 << (high - low + 1)) - 1);
|
||||
}
|
||||
|
||||
pub const RiscvEflags = packed struct(u32) {
|
||||
rvc: bool,
|
||||
fabi: enum(u2) {
|
||||
soft = 0b00,
|
||||
single = 0b01,
|
||||
double = 0b10,
|
||||
quad = 0b11,
|
||||
},
|
||||
rve: bool,
|
||||
tso: bool,
|
||||
_reserved: u19,
|
||||
_unused: u8,
|
||||
};
|
||||
|
||||
const encoder = @import("../arch/riscv64/encoder.zig");
|
||||
const Encoding = @import("../arch/riscv64/Encoding.zig");
|
||||
const mem = std.mem;
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user