Merge pull request #7681 from kubkon/stage2-aarch64-fn-args
stage2: basic fn args for aarch64
This commit is contained in:
@@ -2837,7 +2837,19 @@ fn Function(comptime arch: std.Target.Cpu.Arch) type {
|
||||
mem.writeIntLittle(u32, try self.code.addManyAsArray(4), Instruction.movk(reg, @intCast(u16, x >> 48), 48).toU32());
|
||||
}
|
||||
},
|
||||
.register => return self.fail(src, "TODO implement genSetReg for aarch64 {}", .{mcv}),
|
||||
.register => |src_reg| {
|
||||
// If the registers are the same, nothing to do.
|
||||
if (src_reg.id() == reg.id())
|
||||
return;
|
||||
|
||||
// mov reg, src_reg
|
||||
writeInt(u32, try self.code.addManyAsArray(4), Instruction.orr(
|
||||
reg,
|
||||
.xzr,
|
||||
src_reg,
|
||||
Instruction.Shift.none,
|
||||
).toU32());
|
||||
},
|
||||
.memory => |addr| {
|
||||
if (self.bin_file.options.pie) {
|
||||
// For MachO, the binary, with the exception of object files, has to be a PIE.
|
||||
@@ -3475,6 +3487,59 @@ fn Function(comptime arch: std.Target.Cpu.Arch) type {
|
||||
else => return self.fail(src, "TODO implement function parameters for {} on arm", .{cc}),
|
||||
}
|
||||
},
|
||||
.aarch64 => {
|
||||
switch (cc) {
|
||||
.Naked => {
|
||||
assert(result.args.len == 0);
|
||||
result.return_value = .{ .unreach = {} };
|
||||
result.stack_byte_count = 0;
|
||||
result.stack_align = 1;
|
||||
return result;
|
||||
},
|
||||
.Unspecified, .C => {
|
||||
// ARM64 Procedure Call Standard
|
||||
var ncrn: usize = 0; // Next Core Register Number
|
||||
var nsaa: u32 = 0; // Next stacked argument address
|
||||
|
||||
for (param_types) |ty, i| {
|
||||
// We round up NCRN only for non-Apple platforms which allow the 16-byte aligned
|
||||
// values to spread across odd-numbered registers.
|
||||
if (ty.abiAlignment(self.target.*) == 16 and !self.target.isDarwin()) {
|
||||
// Round up NCRN to the next even number
|
||||
ncrn += ncrn % 2;
|
||||
}
|
||||
|
||||
const param_size = @intCast(u32, ty.abiSize(self.target.*));
|
||||
if (std.math.divCeil(u32, param_size, 8) catch unreachable <= 8 - ncrn) {
|
||||
if (param_size <= 8) {
|
||||
result.args[i] = .{ .register = c_abi_int_param_regs[ncrn] };
|
||||
ncrn += 1;
|
||||
} else {
|
||||
return self.fail(src, "TODO MCValues with multiple registers", .{});
|
||||
}
|
||||
} else if (ncrn < 8 and nsaa == 0) {
|
||||
return self.fail(src, "TODO MCValues split between registers and stack", .{});
|
||||
} else {
|
||||
ncrn = 8;
|
||||
// TODO Apple allows the arguments on the stack to be non-8-byte aligned provided
|
||||
// that the entire stack space consumed by the arguments is 8-byte aligned.
|
||||
if (ty.abiAlignment(self.target.*) == 8) {
|
||||
if (nsaa % 8 != 0) {
|
||||
nsaa += 8 - (nsaa % 8);
|
||||
}
|
||||
}
|
||||
|
||||
result.args[i] = .{ .stack_offset = nsaa };
|
||||
nsaa += param_size;
|
||||
}
|
||||
}
|
||||
|
||||
result.stack_byte_count = nsaa;
|
||||
result.stack_align = 16;
|
||||
},
|
||||
else => return self.fail(src, "TODO implement function parameters for {} on aarch64", .{cc}),
|
||||
}
|
||||
},
|
||||
else => if (param_types.len != 0)
|
||||
return self.fail(src, "TODO implement codegen parameters for {}", .{self.target.cpu.arch}),
|
||||
}
|
||||
|
||||
@@ -298,7 +298,7 @@ pub fn openPath(allocator: *Allocator, sub_path: []const u8, options: link.Optio
|
||||
self.base.file = file;
|
||||
|
||||
// Create dSYM bundle.
|
||||
const d_sym_path = try fmt.allocPrint(allocator, "{}.dSYM/Contents/Resources/DWARF/", .{sub_path});
|
||||
const d_sym_path = try fmt.allocPrint(allocator, "{s}.dSYM/Contents/Resources/DWARF/", .{sub_path});
|
||||
defer allocator.free(d_sym_path);
|
||||
var d_sym_bundle = try options.emit.?.directory.handle.makeOpenPath(d_sym_path, .{});
|
||||
defer d_sym_bundle.close();
|
||||
|
||||
@@ -155,4 +155,48 @@ pub fn addCases(ctx: *TestContext) !void {
|
||||
"Hello, World!\n",
|
||||
);
|
||||
}
|
||||
|
||||
{
|
||||
var case = ctx.exe("exit fn taking argument", macos_aarch64);
|
||||
|
||||
case.addCompareOutput(
|
||||
\\export fn _start() noreturn {
|
||||
\\ exit(0);
|
||||
\\}
|
||||
\\
|
||||
\\fn exit(ret: usize) noreturn {
|
||||
\\ asm volatile ("svc #0x80"
|
||||
\\ :
|
||||
\\ : [number] "{x16}" (1),
|
||||
\\ [arg1] "{x0}" (ret)
|
||||
\\ : "memory"
|
||||
\\ );
|
||||
\\ unreachable;
|
||||
\\}
|
||||
,
|
||||
"",
|
||||
);
|
||||
}
|
||||
|
||||
{
|
||||
var case = ctx.exe("exit fn taking argument", linux_aarch64);
|
||||
|
||||
case.addCompareOutput(
|
||||
\\export fn _start() noreturn {
|
||||
\\ exit(0);
|
||||
\\}
|
||||
\\
|
||||
\\fn exit(ret: usize) noreturn {
|
||||
\\ asm volatile ("svc #0"
|
||||
\\ :
|
||||
\\ : [number] "{x8}" (93),
|
||||
\\ [arg1] "{x0}" (ret)
|
||||
\\ : "memory", "cc"
|
||||
\\ );
|
||||
\\ unreachable;
|
||||
\\}
|
||||
,
|
||||
"",
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user