Commit d25c93a868
Changed files (7)
src
link
Elf
src/arch/x86_64/bits.zig
@@ -569,6 +569,7 @@ pub const Memory = struct {
pub const Immediate = union(enum) {
signed: i32,
unsigned: u64,
+ reloc: Symbol,
pub fn u(x: u64) Immediate {
return .{ .unsigned = x };
@@ -578,39 +579,19 @@ pub const Immediate = union(enum) {
return .{ .signed = x };
}
- pub fn asSigned(imm: Immediate, bit_size: u64) i64 {
- return switch (imm) {
- .signed => |x| switch (bit_size) {
- 1, 8 => @as(i8, @intCast(x)),
- 16 => @as(i16, @intCast(x)),
- 32, 64 => x,
- else => unreachable,
- },
- .unsigned => |x| switch (bit_size) {
- 1, 8 => @as(i8, @bitCast(@as(u8, @intCast(x)))),
- 16 => @as(i16, @bitCast(@as(u16, @intCast(x)))),
- 32 => @as(i32, @bitCast(@as(u32, @intCast(x)))),
- 64 => @bitCast(x),
- else => unreachable,
- },
- };
+ pub fn rel(symbol: Symbol) Immediate {
+ return .{ .reloc = symbol };
}
- pub fn asUnsigned(imm: Immediate, bit_size: u64) u64 {
- return switch (imm) {
- .signed => |x| switch (bit_size) {
- 1, 8 => @as(u8, @bitCast(@as(i8, @intCast(x)))),
- 16 => @as(u16, @bitCast(@as(i16, @intCast(x)))),
- 32, 64 => @as(u32, @bitCast(x)),
- else => unreachable,
- },
- .unsigned => |x| switch (bit_size) {
- 1, 8 => @as(u8, @intCast(x)),
- 16 => @as(u16, @intCast(x)),
- 32 => @as(u32, @intCast(x)),
- 64 => x,
- else => unreachable,
- },
- };
+ pub fn format(
+ imm: Immediate,
+ comptime fmt: []const u8,
+ options: std.fmt.FormatOptions,
+ writer: anytype,
+ ) @TypeOf(writer).Error!void {
+ switch (imm) {
+ .reloc => |x| try std.fmt.formatType(x, fmt, options, writer, 0),
+ inline else => |x| try writer.print("{d}", .{x}),
+ }
}
};
src/arch/x86_64/CodeGen.zig
@@ -1379,14 +1379,19 @@ fn asmImmediate(self: *Self, tag: Mir.Inst.FixedTag, imm: Immediate) !void {
.ops = switch (imm) {
.signed => .i_s,
.unsigned => .i_u,
+ .reloc => .rel,
+ },
+ .data = switch (imm) {
+ .reloc => |x| .{ .reloc = x },
+ .signed, .unsigned => .{ .i = .{
+ .fixes = tag[0],
+ .i = switch (imm) {
+ .signed => |s| @bitCast(s),
+ .unsigned => |u| @intCast(u),
+ .reloc => unreachable,
+ },
+ } },
},
- .data = .{ .i = .{
- .fixes = tag[0],
- .i = switch (imm) {
- .signed => |s| @bitCast(s),
- .unsigned => |u| @intCast(u),
- },
- } },
});
}
@@ -1406,6 +1411,7 @@ fn asmRegisterImmediate(self: *Self, tag: Mir.Inst.FixedTag, reg: Register, imm:
const ops: Mir.Inst.Ops = switch (imm) {
.signed => .ri_s,
.unsigned => |u| if (math.cast(u32, u)) |_| .ri_u else .ri64,
+ .reloc => unreachable,
};
_ = try self.addInst(.{
.tag = tag[1],
@@ -1417,6 +1423,7 @@ fn asmRegisterImmediate(self: *Self, tag: Mir.Inst.FixedTag, reg: Register, imm:
.i = switch (imm) {
.signed => |s| @bitCast(s),
.unsigned => |u| @intCast(u),
+ .reloc => unreachable,
},
} },
.ri64 => .{ .rx = .{
@@ -1488,6 +1495,7 @@ fn asmRegisterRegisterRegisterImmediate(
.i = switch (imm) {
.signed => |s| @bitCast(@as(i8, @intCast(s))),
.unsigned => |u| @intCast(u),
+ .reloc => unreachable,
},
} },
});
@@ -1505,6 +1513,7 @@ fn asmRegisterRegisterImmediate(
.ops = switch (imm) {
.signed => .rri_s,
.unsigned => .rri_u,
+ .reloc => unreachable,
},
.data = .{ .rri = .{
.fixes = tag[0],
@@ -1513,6 +1522,7 @@ fn asmRegisterRegisterImmediate(
.i = switch (imm) {
.signed => |s| @bitCast(s),
.unsigned => |u| @intCast(u),
+ .reloc => unreachable,
},
} },
});
@@ -1610,6 +1620,7 @@ fn asmRegisterMemoryImmediate(
if (switch (imm) {
.signed => |s| if (math.cast(i16, s)) |x| @as(u16, @bitCast(x)) else null,
.unsigned => |u| math.cast(u16, u),
+ .reloc => unreachable,
}) |small_imm| {
_ = try self.addInst(.{
.tag = tag[1],
@@ -1625,6 +1636,7 @@ fn asmRegisterMemoryImmediate(
const payload = try self.addExtra(Mir.Imm32{ .imm = switch (imm) {
.signed => |s| @bitCast(s),
.unsigned => unreachable,
+ .reloc => unreachable,
} });
assert(payload + 1 == try self.addExtra(Mir.Memory.encode(m)));
_ = try self.addInst(.{
@@ -1632,6 +1644,7 @@ fn asmRegisterMemoryImmediate(
.ops = switch (imm) {
.signed => .rmi_s,
.unsigned => .rmi_u,
+ .reloc => unreachable,
},
.data = .{ .rx = .{
.fixes = tag[0],
@@ -1679,6 +1692,7 @@ fn asmMemoryImmediate(self: *Self, tag: Mir.Inst.FixedTag, m: Memory, imm: Immed
const payload = try self.addExtra(Mir.Imm32{ .imm = switch (imm) {
.signed => |s| @bitCast(s),
.unsigned => |u| @intCast(u),
+ .reloc => unreachable,
} });
assert(payload + 1 == try self.addExtra(Mir.Memory.encode(m)));
_ = try self.addInst(.{
@@ -1686,6 +1700,7 @@ fn asmMemoryImmediate(self: *Self, tag: Mir.Inst.FixedTag, m: Memory, imm: Immed
.ops = switch (imm) {
.signed => .mi_s,
.unsigned => .mi_u,
+ .reloc => unreachable,
},
.data = .{ .x = .{
.fixes = tag[0],
@@ -12310,33 +12325,10 @@ fn genCall(self: *Self, info: union(enum) {
if (self.bin_file.cast(.elf)) |elf_file| {
const zo = elf_file.zigObjectPtr().?;
const sym_index = try zo.getOrCreateMetadataForNav(elf_file, func.owner_nav);
- if (self.mod.pic) {
- const callee_reg: Register = switch (resolved_cc) {
- .SysV => callee: {
- if (!fn_info.is_var_args) break :callee .rax;
- const param_regs = abi.getCAbiIntParamRegs(resolved_cc);
- break :callee if (call_info.gp_count < param_regs.len)
- param_regs[call_info.gp_count]
- else
- .r10;
- },
- .Win64 => .rax,
- else => unreachable,
- };
- try self.genSetReg(
- callee_reg,
- Type.usize,
- .{ .lea_symbol = .{ .sym = sym_index } },
- .{},
- );
- try self.asmRegister(.{ ._, .call }, callee_reg);
- } else try self.asmMemory(.{ ._, .call }, .{
- .base = .{ .reloc = .{
- .atom_index = try self.owner.getSymbolIndex(self),
- .sym_index = sym_index,
- } },
- .mod = .{ .rm = .{ .size = .qword } },
- });
+ try self.asmImmediate(.{ ._, .call }, Immediate.rel(.{
+ .atom_index = try self.owner.getSymbolIndex(self),
+ .sym_index = sym_index,
+ }));
} else if (self.bin_file.cast(.coff)) |coff_file| {
const atom = try coff_file.getOrCreateAtomForNav(func.owner_nav);
const sym_index = coff_file.getAtom(atom).getSymbolIndex().?;
src/arch/x86_64/Disassembler.zig
@@ -8,7 +8,7 @@ const bits = @import("bits.zig");
const encoder = @import("encoder.zig");
const Encoding = @import("Encoding.zig");
-const Immediate = bits.Immediate;
+const Immediate = Instruction.Immediate;
const Instruction = encoder.Instruction;
const LegacyPrefixes = encoder.LegacyPrefixes;
const Memory = Instruction.Memory;
src/arch/x86_64/encoder.zig
@@ -7,7 +7,6 @@ const testing = std.testing;
const bits = @import("bits.zig");
const Encoding = @import("Encoding.zig");
const FrameIndex = bits.FrameIndex;
-const Immediate = bits.Immediate;
const Register = bits.Register;
const Symbol = bits.Symbol;
@@ -28,6 +27,55 @@ pub const Instruction = struct {
repnz,
};
+ pub const Immediate = union(enum) {
+ signed: i32,
+ unsigned: u64,
+
+ pub fn u(x: u64) Immediate {
+ return .{ .unsigned = x };
+ }
+
+ pub fn s(x: i32) Immediate {
+ return .{ .signed = x };
+ }
+
+ pub fn asSigned(imm: Immediate, bit_size: u64) i64 {
+ return switch (imm) {
+ .signed => |x| switch (bit_size) {
+ 1, 8 => @as(i8, @intCast(x)),
+ 16 => @as(i16, @intCast(x)),
+ 32, 64 => x,
+ else => unreachable,
+ },
+ .unsigned => |x| switch (bit_size) {
+ 1, 8 => @as(i8, @bitCast(@as(u8, @intCast(x)))),
+ 16 => @as(i16, @bitCast(@as(u16, @intCast(x)))),
+ 32 => @as(i32, @bitCast(@as(u32, @intCast(x)))),
+ 64 => @bitCast(x),
+ else => unreachable,
+ },
+ };
+ }
+
+ pub fn asUnsigned(imm: Immediate, bit_size: u64) u64 {
+ return switch (imm) {
+ .signed => |x| switch (bit_size) {
+ 1, 8 => @as(u8, @bitCast(@as(i8, @intCast(x)))),
+ 16 => @as(u16, @bitCast(@as(i16, @intCast(x)))),
+ 32, 64 => @as(u32, @bitCast(x)),
+ else => unreachable,
+ },
+ .unsigned => |x| switch (bit_size) {
+ 1, 8 => @as(u8, @intCast(x)),
+ 16 => @as(u16, @intCast(x)),
+ 32 => @as(u32, @intCast(x)),
+ 64 => x,
+ else => unreachable,
+ },
+ };
+ }
+ };
+
pub const Memory = union(enum) {
sib: Sib,
rip: Rip,
@@ -1119,7 +1167,7 @@ test "encode" {
const inst = try Instruction.new(.none, .mov, &.{
.{ .reg = .rbx },
- .{ .imm = Immediate.u(4) },
+ .{ .imm = Instruction.Immediate.u(4) },
});
try inst.encode(buf.writer(), .{});
try testing.expectEqualSlices(u8, &.{ 0x48, 0xc7, 0xc3, 0x4, 0x0, 0x0, 0x0 }, buf.items);
@@ -1129,47 +1177,47 @@ test "lower I encoding" {
var enc = TestEncode{};
try enc.encode(.push, &.{
- .{ .imm = Immediate.u(0x10) },
+ .{ .imm = Instruction.Immediate.u(0x10) },
});
try expectEqualHexStrings("\x6A\x10", enc.code(), "push 0x10");
try enc.encode(.push, &.{
- .{ .imm = Immediate.u(0x1000) },
+ .{ .imm = Instruction.Immediate.u(0x1000) },
});
try expectEqualHexStrings("\x66\x68\x00\x10", enc.code(), "push 0x1000");
try enc.encode(.push, &.{
- .{ .imm = Immediate.u(0x10000000) },
+ .{ .imm = Instruction.Immediate.u(0x10000000) },
});
try expectEqualHexStrings("\x68\x00\x00\x00\x10", enc.code(), "push 0x10000000");
try enc.encode(.adc, &.{
.{ .reg = .rax },
- .{ .imm = Immediate.u(0x10000000) },
+ .{ .imm = Instruction.Immediate.u(0x10000000) },
});
try expectEqualHexStrings("\x48\x15\x00\x00\x00\x10", enc.code(), "adc rax, 0x10000000");
try enc.encode(.add, &.{
.{ .reg = .al },
- .{ .imm = Immediate.u(0x10) },
+ .{ .imm = Instruction.Immediate.u(0x10) },
});
try expectEqualHexStrings("\x04\x10", enc.code(), "add al, 0x10");
try enc.encode(.add, &.{
.{ .reg = .rax },
- .{ .imm = Immediate.u(0x10) },
+ .{ .imm = Instruction.Immediate.u(0x10) },
});
try expectEqualHexStrings("\x48\x83\xC0\x10", enc.code(), "add rax, 0x10");
try enc.encode(.sbb, &.{
.{ .reg = .ax },
- .{ .imm = Immediate.u(0x10) },
+ .{ .imm = Instruction.Immediate.u(0x10) },
});
try expectEqualHexStrings("\x66\x1D\x10\x00", enc.code(), "sbb ax, 0x10");
try enc.encode(.xor, &.{
.{ .reg = .al },
- .{ .imm = Immediate.u(0x10) },
+ .{ .imm = Instruction.Immediate.u(0x10) },
});
try expectEqualHexStrings("\x34\x10", enc.code(), "xor al, 0x10");
}
@@ -1179,43 +1227,43 @@ test "lower MI encoding" {
try enc.encode(.mov, &.{
.{ .reg = .r12 },
- .{ .imm = Immediate.u(0x1000) },
+ .{ .imm = Instruction.Immediate.u(0x1000) },
});
try expectEqualHexStrings("\x49\xC7\xC4\x00\x10\x00\x00", enc.code(), "mov r12, 0x1000");
try enc.encode(.mov, &.{
.{ .mem = Instruction.Memory.sib(.byte, .{ .base = .{ .reg = .r12 } }) },
- .{ .imm = Immediate.u(0x10) },
+ .{ .imm = Instruction.Immediate.u(0x10) },
});
try expectEqualHexStrings("\x41\xC6\x04\x24\x10", enc.code(), "mov BYTE PTR [r12], 0x10");
try enc.encode(.mov, &.{
.{ .reg = .r12 },
- .{ .imm = Immediate.u(0x1000) },
+ .{ .imm = Instruction.Immediate.u(0x1000) },
});
try expectEqualHexStrings("\x49\xC7\xC4\x00\x10\x00\x00", enc.code(), "mov r12, 0x1000");
try enc.encode(.mov, &.{
.{ .reg = .r12 },
- .{ .imm = Immediate.u(0x1000) },
+ .{ .imm = Instruction.Immediate.u(0x1000) },
});
try expectEqualHexStrings("\x49\xC7\xC4\x00\x10\x00\x00", enc.code(), "mov r12, 0x1000");
try enc.encode(.mov, &.{
.{ .reg = .rax },
- .{ .imm = Immediate.u(0x10) },
+ .{ .imm = Instruction.Immediate.u(0x10) },
});
try expectEqualHexStrings("\x48\xc7\xc0\x10\x00\x00\x00", enc.code(), "mov rax, 0x10");
try enc.encode(.mov, &.{
.{ .mem = Instruction.Memory.sib(.dword, .{ .base = .{ .reg = .r11 } }) },
- .{ .imm = Immediate.u(0x10) },
+ .{ .imm = Instruction.Immediate.u(0x10) },
});
try expectEqualHexStrings("\x41\xc7\x03\x10\x00\x00\x00", enc.code(), "mov DWORD PTR [r11], 0x10");
try enc.encode(.mov, &.{
.{ .mem = Instruction.Memory.rip(.qword, 0x10) },
- .{ .imm = Immediate.u(0x10) },
+ .{ .imm = Instruction.Immediate.u(0x10) },
});
try expectEqualHexStrings(
"\x48\xC7\x05\x10\x00\x00\x00\x10\x00\x00\x00",
@@ -1225,19 +1273,19 @@ test "lower MI encoding" {
try enc.encode(.mov, &.{
.{ .mem = Instruction.Memory.sib(.qword, .{ .base = .{ .reg = .rbp }, .disp = -8 }) },
- .{ .imm = Immediate.u(0x10) },
+ .{ .imm = Instruction.Immediate.u(0x10) },
});
try expectEqualHexStrings("\x48\xc7\x45\xf8\x10\x00\x00\x00", enc.code(), "mov QWORD PTR [rbp - 8], 0x10");
try enc.encode(.mov, &.{
.{ .mem = Instruction.Memory.sib(.word, .{ .base = .{ .reg = .rbp }, .disp = -2 }) },
- .{ .imm = Immediate.s(-16) },
+ .{ .imm = Instruction.Immediate.s(-16) },
});
try expectEqualHexStrings("\x66\xC7\x45\xFE\xF0\xFF", enc.code(), "mov WORD PTR [rbp - 2], -16");
try enc.encode(.mov, &.{
.{ .mem = Instruction.Memory.sib(.byte, .{ .base = .{ .reg = .rbp }, .disp = -1 }) },
- .{ .imm = Immediate.u(0x10) },
+ .{ .imm = Instruction.Immediate.u(0x10) },
});
try expectEqualHexStrings("\xC6\x45\xFF\x10", enc.code(), "mov BYTE PTR [rbp - 1], 0x10");
@@ -1247,7 +1295,7 @@ test "lower MI encoding" {
.disp = 0x10000000,
.scale_index = .{ .scale = 2, .index = .rcx },
}) },
- .{ .imm = Immediate.u(0x10) },
+ .{ .imm = Instruction.Immediate.u(0x10) },
});
try expectEqualHexStrings(
"\x48\xC7\x04\x4D\x00\x00\x00\x10\x10\x00\x00\x00",
@@ -1257,43 +1305,43 @@ test "lower MI encoding" {
try enc.encode(.adc, &.{
.{ .mem = Instruction.Memory.sib(.byte, .{ .base = .{ .reg = .rbp }, .disp = -0x10 }) },
- .{ .imm = Immediate.u(0x10) },
+ .{ .imm = Instruction.Immediate.u(0x10) },
});
try expectEqualHexStrings("\x80\x55\xF0\x10", enc.code(), "adc BYTE PTR [rbp - 0x10], 0x10");
try enc.encode(.adc, &.{
.{ .mem = Instruction.Memory.rip(.qword, 0) },
- .{ .imm = Immediate.u(0x10) },
+ .{ .imm = Instruction.Immediate.u(0x10) },
});
try expectEqualHexStrings("\x48\x83\x15\x00\x00\x00\x00\x10", enc.code(), "adc QWORD PTR [rip], 0x10");
try enc.encode(.adc, &.{
.{ .reg = .rax },
- .{ .imm = Immediate.u(0x10) },
+ .{ .imm = Instruction.Immediate.u(0x10) },
});
try expectEqualHexStrings("\x48\x83\xD0\x10", enc.code(), "adc rax, 0x10");
try enc.encode(.add, &.{
.{ .mem = Instruction.Memory.sib(.dword, .{ .base = .{ .reg = .rdx }, .disp = -8 }) },
- .{ .imm = Immediate.u(0x10) },
+ .{ .imm = Instruction.Immediate.u(0x10) },
});
try expectEqualHexStrings("\x83\x42\xF8\x10", enc.code(), "add DWORD PTR [rdx - 8], 0x10");
try enc.encode(.add, &.{
.{ .reg = .rax },
- .{ .imm = Immediate.u(0x10) },
+ .{ .imm = Instruction.Immediate.u(0x10) },
});
try expectEqualHexStrings("\x48\x83\xC0\x10", enc.code(), "add rax, 0x10");
try enc.encode(.add, &.{
.{ .mem = Instruction.Memory.sib(.qword, .{ .base = .{ .reg = .rbp }, .disp = -0x10 }) },
- .{ .imm = Immediate.s(-0x10) },
+ .{ .imm = Instruction.Immediate.s(-0x10) },
});
try expectEqualHexStrings("\x48\x83\x45\xF0\xF0", enc.code(), "add QWORD PTR [rbp - 0x10], -0x10");
try enc.encode(.@"and", &.{
.{ .mem = Instruction.Memory.sib(.dword, .{ .base = .{ .reg = .ds }, .disp = 0x10000000 }) },
- .{ .imm = Immediate.u(0x10) },
+ .{ .imm = Instruction.Immediate.u(0x10) },
});
try expectEqualHexStrings(
"\x83\x24\x25\x00\x00\x00\x10\x10",
@@ -1303,7 +1351,7 @@ test "lower MI encoding" {
try enc.encode(.@"and", &.{
.{ .mem = Instruction.Memory.sib(.dword, .{ .base = .{ .reg = .es }, .disp = 0x10000000 }) },
- .{ .imm = Immediate.u(0x10) },
+ .{ .imm = Instruction.Immediate.u(0x10) },
});
try expectEqualHexStrings(
"\x26\x83\x24\x25\x00\x00\x00\x10\x10",
@@ -1313,7 +1361,7 @@ test "lower MI encoding" {
try enc.encode(.@"and", &.{
.{ .mem = Instruction.Memory.sib(.dword, .{ .base = .{ .reg = .r12 }, .disp = 0x10000000 }) },
- .{ .imm = Immediate.u(0x10) },
+ .{ .imm = Instruction.Immediate.u(0x10) },
});
try expectEqualHexStrings(
"\x41\x83\xA4\x24\x00\x00\x00\x10\x10",
@@ -1323,7 +1371,7 @@ test "lower MI encoding" {
try enc.encode(.sub, &.{
.{ .mem = Instruction.Memory.sib(.dword, .{ .base = .{ .reg = .r11 }, .disp = 0x10000000 }) },
- .{ .imm = Immediate.u(0x10) },
+ .{ .imm = Instruction.Immediate.u(0x10) },
});
try expectEqualHexStrings(
"\x41\x83\xAB\x00\x00\x00\x10\x10",
@@ -1542,14 +1590,14 @@ test "lower RMI encoding" {
try enc.encode(.imul, &.{
.{ .reg = .r11 },
.{ .reg = .r12 },
- .{ .imm = Immediate.s(-2) },
+ .{ .imm = Instruction.Immediate.s(-2) },
});
try expectEqualHexStrings("\x4D\x6B\xDC\xFE", enc.code(), "imul r11, r12, -2");
try enc.encode(.imul, &.{
.{ .reg = .r11 },
.{ .mem = Instruction.Memory.rip(.qword, -16) },
- .{ .imm = Immediate.s(-1024) },
+ .{ .imm = Instruction.Immediate.s(-1024) },
});
try expectEqualHexStrings(
"\x4C\x69\x1D\xF0\xFF\xFF\xFF\x00\xFC\xFF\xFF",
@@ -1560,7 +1608,7 @@ test "lower RMI encoding" {
try enc.encode(.imul, &.{
.{ .reg = .bx },
.{ .mem = Instruction.Memory.sib(.word, .{ .base = .{ .reg = .rbp }, .disp = -16 }) },
- .{ .imm = Immediate.s(-1024) },
+ .{ .imm = Instruction.Immediate.s(-1024) },
});
try expectEqualHexStrings(
"\x66\x69\x5D\xF0\x00\xFC",
@@ -1571,7 +1619,7 @@ test "lower RMI encoding" {
try enc.encode(.imul, &.{
.{ .reg = .bx },
.{ .mem = Instruction.Memory.sib(.word, .{ .base = .{ .reg = .rbp }, .disp = -16 }) },
- .{ .imm = Immediate.u(1024) },
+ .{ .imm = Instruction.Immediate.u(1024) },
});
try expectEqualHexStrings(
"\x66\x69\x5D\xF0\x00\x04",
@@ -1687,7 +1735,7 @@ test "lower M encoding" {
try expectEqualHexStrings("\x65\xFF\x14\x25\x00\x00\x00\x00", enc.code(), "call gs:0x0");
try enc.encode(.call, &.{
- .{ .imm = Immediate.s(0) },
+ .{ .imm = Instruction.Immediate.s(0) },
});
try expectEqualHexStrings("\xE8\x00\x00\x00\x00", enc.code(), "call 0x0");
@@ -1746,7 +1794,7 @@ test "lower OI encoding" {
try enc.encode(.mov, &.{
.{ .reg = .rax },
- .{ .imm = Immediate.u(0x1000000000000000) },
+ .{ .imm = Instruction.Immediate.u(0x1000000000000000) },
});
try expectEqualHexStrings(
"\x48\xB8\x00\x00\x00\x00\x00\x00\x00\x10",
@@ -1756,7 +1804,7 @@ test "lower OI encoding" {
try enc.encode(.mov, &.{
.{ .reg = .r11 },
- .{ .imm = Immediate.u(0x1000000000000000) },
+ .{ .imm = Instruction.Immediate.u(0x1000000000000000) },
});
try expectEqualHexStrings(
"\x49\xBB\x00\x00\x00\x00\x00\x00\x00\x10",
@@ -1766,19 +1814,19 @@ test "lower OI encoding" {
try enc.encode(.mov, &.{
.{ .reg = .r11d },
- .{ .imm = Immediate.u(0x10000000) },
+ .{ .imm = Instruction.Immediate.u(0x10000000) },
});
try expectEqualHexStrings("\x41\xBB\x00\x00\x00\x10", enc.code(), "mov r11d, 0x10000000");
try enc.encode(.mov, &.{
.{ .reg = .r11w },
- .{ .imm = Immediate.u(0x1000) },
+ .{ .imm = Instruction.Immediate.u(0x1000) },
});
try expectEqualHexStrings("\x66\x41\xBB\x00\x10", enc.code(), "mov r11w, 0x1000");
try enc.encode(.mov, &.{
.{ .reg = .r11b },
- .{ .imm = Immediate.u(0x10) },
+ .{ .imm = Instruction.Immediate.u(0x10) },
});
try expectEqualHexStrings("\x41\xB3\x10", enc.code(), "mov r11b, 0x10");
}
@@ -1900,7 +1948,7 @@ test "invalid instruction" {
.{ .reg = .r12d },
});
try invalidInstruction(.push, &.{
- .{ .imm = Immediate.u(0x1000000000000000) },
+ .{ .imm = Instruction.Immediate.u(0x1000000000000000) },
});
}
@@ -2213,7 +2261,7 @@ const Assembler = struct {
.immediate => {
const is_neg = if (as.expect(.minus)) |_| true else |_| false;
const imm_tok = try as.expect(.numeral);
- const imm: Immediate = if (is_neg) blk: {
+ const imm: Instruction.Immediate = if (is_neg) blk: {
const imm = try std.fmt.parseInt(i32, as.source(imm_tok), 0);
break :blk .{ .signed = imm * -1 };
} else .{ .unsigned = try std.fmt.parseInt(u64, as.source(imm_tok), 0) };
src/arch/x86_64/Lower.zig
@@ -475,7 +475,7 @@ fn generic(lower: *Lower, inst: Mir.Inst) Error!void {
.rrmi => inst.data.rrix.fixes,
.mi_u, .mi_s => inst.data.x.fixes,
.m => inst.data.x.fixes,
- .extern_fn_reloc, .got_reloc, .direct_reloc, .import_reloc, .tlv_reloc => ._,
+ .extern_fn_reloc, .got_reloc, .direct_reloc, .import_reloc, .tlv_reloc, .rel => ._,
else => return lower.fail("TODO lower .{s}", .{@tagName(inst.ops)}),
};
try lower.emit(switch (fixes) {
@@ -607,7 +607,7 @@ fn generic(lower: *Lower, inst: Mir.Inst) Error!void {
.{ .mem = lower.mem(inst.data.rrix.payload) },
.{ .imm = lower.imm(inst.ops, inst.data.rrix.i) },
},
- .extern_fn_reloc => &.{
+ .extern_fn_reloc, .rel => &.{
.{ .imm = lower.reloc(.{ .linker_extern_fn = inst.data.reloc }) },
},
.got_reloc, .direct_reloc, .import_reloc => ops: {
@@ -650,7 +650,7 @@ const std = @import("std");
const Air = @import("../../Air.zig");
const Allocator = std.mem.Allocator;
const ErrorMsg = Zcu.ErrorMsg;
-const Immediate = bits.Immediate;
+const Immediate = Instruction.Immediate;
const Instruction = encoder.Instruction;
const Lower = @This();
const Memory = Instruction.Memory;
src/arch/x86_64/Mir.zig
@@ -769,7 +769,7 @@ pub const Inst = struct {
/// Uses `imm` payload.
i_u,
/// Relative displacement operand.
- /// Uses `imm` payload.
+ /// Uses `reloc` payload.
rel,
/// Register, memory operands.
/// Uses `rx` payload with extra data of type `Memory`.
src/link/Elf/Atom.zig
@@ -1215,12 +1215,11 @@ const x86_64 = struct {
);
},
- .PLT32 => try cwriter.writeInt(i32, @as(i32, @intCast(S + A - P)), .little),
-
- .PC32 => {
+ .PLT32 => {
const S_ = if (target.flags.zig_jump_table) ZJT else S;
try cwriter.writeInt(i32, @as(i32, @intCast(S_ + A - P)), .little);
},
+ .PC32 => try cwriter.writeInt(i32, @as(i32, @intCast(S + A - P)), .little),
.GOTPCREL => try cwriter.writeInt(i32, @as(i32, @intCast(G + GOT + A - P)), .little),
.GOTPC32 => try cwriter.writeInt(i32, @as(i32, @intCast(GOT + A - P)), .little),
@@ -1620,7 +1619,7 @@ const x86_64 = struct {
const bits = @import("../../arch/x86_64/bits.zig");
const encoder = @import("../../arch/x86_64/encoder.zig");
const Disassembler = @import("../../arch/x86_64/Disassembler.zig");
- const Immediate = bits.Immediate;
+ const Immediate = Instruction.Immediate;
const Instruction = encoder.Instruction;
};