mirror of
https://codeberg.org/ziglang/zig.git
synced 2025-12-06 13:54:21 +00:00
x86_64: fix windows calling convention abi
This commit is contained in:
parent
bc4da9a907
commit
d5f09f56e0
4 changed files with 5540 additions and 9763 deletions
|
|
@ -12103,7 +12103,7 @@ fn firstParamSRet(fn_info: InternPool.Key.FuncType, zcu: *Zcu, target: *const st
|
|||
return switch (fn_info.cc) {
|
||||
.auto => returnTypeByRef(zcu, target, return_type),
|
||||
.x86_64_sysv => firstParamSRetSystemV(return_type, zcu, target),
|
||||
.x86_64_win => x86_64_abi.classifyWindows(return_type, zcu, target) == .memory,
|
||||
.x86_64_win => x86_64_abi.classifyWindows(return_type, zcu, target, .ret) == .memory,
|
||||
.x86_sysv, .x86_win => isByRef(return_type, zcu),
|
||||
.x86_stdcall => !isScalar(zcu, return_type),
|
||||
.wasm_mvp => wasm_c_abi.classifyType(return_type, zcu) == .indirect,
|
||||
|
|
@ -12205,7 +12205,7 @@ fn lowerFnRetTy(o: *Object, pt: Zcu.PerThread, fn_info: InternPool.Key.FuncType)
|
|||
fn lowerWin64FnRetTy(o: *Object, pt: Zcu.PerThread, fn_info: InternPool.Key.FuncType) Allocator.Error!Builder.Type {
|
||||
const zcu = pt.zcu;
|
||||
const return_type = Type.fromInterned(fn_info.return_type);
|
||||
switch (x86_64_abi.classifyWindows(return_type, zcu, zcu.getTarget())) {
|
||||
switch (x86_64_abi.classifyWindows(return_type, zcu, zcu.getTarget(), .ret)) {
|
||||
.integer => {
|
||||
if (isScalar(zcu, return_type)) {
|
||||
return o.lowerType(pt, return_type);
|
||||
|
|
@ -12476,7 +12476,7 @@ const ParamTypeIterator = struct {
|
|||
|
||||
fn nextWin64(it: *ParamTypeIterator, ty: Type) ?Lowering {
|
||||
const zcu = it.pt.zcu;
|
||||
switch (x86_64_abi.classifyWindows(ty, zcu, zcu.getTarget())) {
|
||||
switch (x86_64_abi.classifyWindows(ty, zcu, zcu.getTarget(), .arg)) {
|
||||
.integer => {
|
||||
if (isScalar(zcu, ty)) {
|
||||
it.zig_index += 1;
|
||||
|
|
|
|||
File diff suppressed because it is too large
Load diff
|
|
@ -110,7 +110,9 @@ pub const Class = enum {
|
|||
}
|
||||
};
|
||||
|
||||
pub fn classifyWindows(ty: Type, zcu: *Zcu, target: *const std.Target) Class {
|
||||
pub const Context = enum { ret, arg, other };
|
||||
|
||||
pub fn classifyWindows(ty: Type, zcu: *Zcu, target: *const std.Target, ctx: Context) Class {
|
||||
// https://docs.microsoft.com/en-gb/cpp/build/x64-calling-convention?view=vs-2017
|
||||
// "There's a strict one-to-one correspondence between a function call's arguments
|
||||
// and the registers used for those arguments. Any argument that doesn't fit in 8
|
||||
|
|
@ -148,8 +150,9 @@ pub fn classifyWindows(ty: Type, zcu: *Zcu, target: *const std.Target) Class {
|
|||
},
|
||||
|
||||
.float => switch (ty.floatBits(target)) {
|
||||
16, 32, 64, 128 => .sse,
|
||||
16, 32, 64 => .sse,
|
||||
80 => .memory,
|
||||
128 => if (ctx == .arg) .memory else .sse,
|
||||
else => unreachable,
|
||||
},
|
||||
.vector => .sse,
|
||||
|
|
@ -166,8 +169,6 @@ pub fn classifyWindows(ty: Type, zcu: *Zcu, target: *const std.Target) Class {
|
|||
};
|
||||
}
|
||||
|
||||
pub const Context = enum { ret, arg, other };
|
||||
|
||||
/// There are a maximum of 8 possible return slots. Returned values are in
|
||||
/// the beginning of the array; unused slots are filled with .none.
|
||||
pub fn classifySystemV(ty: Type, zcu: *Zcu, target: *const std.Target, ctx: Context) [8]Class {
|
||||
|
|
|
|||
|
|
@ -5172,15 +5172,6 @@ test mulSaturate {
|
|||
try test_mul_saturate.testIntVectors();
|
||||
}
|
||||
|
||||
inline fn multiply(comptime Type: type, lhs: Type, rhs: Type) Type {
|
||||
return lhs * rhs;
|
||||
}
|
||||
test multiply {
|
||||
const test_multiply = binary(multiply, .{});
|
||||
try test_multiply.testFloats();
|
||||
try test_multiply.testFloatVectors();
|
||||
}
|
||||
|
||||
inline fn divide(comptime Type: type, lhs: Type, rhs: Type) Type {
|
||||
return lhs / rhs;
|
||||
}
|
||||
|
|
@ -5264,7 +5255,7 @@ inline fn mod(comptime Type: type, lhs: Type, rhs: Type) Type {
|
|||
return @mod(lhs, rhs);
|
||||
}
|
||||
test mod {
|
||||
if (@import("builtin").object_format == .coff) return error.SkipZigTest;
|
||||
if (@import("builtin").object_format == .coff and @import("builtin").target.abi != .gnu) return error.SkipZigTest;
|
||||
const test_mod = binary(mod, .{});
|
||||
try test_mod.testInts();
|
||||
try test_mod.testIntVectors();
|
||||
|
|
|
|||
Loading…
Add table
Reference in a new issue