mirror of
https://github.com/ziglang/zig.git
synced 2026-01-10 17:35:12 +00:00
Merge pull request #10499 from paulsnar/paulsnar/stage1-packed-structs-cabi
stage1: Fix LLVM C ABI type resolution for small packed structs
This commit is contained in:
commit
5b0be0d436
@ -8962,7 +8962,7 @@ static void resolve_llvm_types_struct(CodeGen *g, ZigType *struct_type, ResolveS
|
||||
struct_type->data.structure.llvm_full_type_queue_index = SIZE_MAX;
|
||||
}
|
||||
|
||||
if (struct_type->abi_size <= 16 && struct_type->data.structure.layout == ContainerLayoutExtern)
|
||||
if (struct_type->abi_size <= 16 && (struct_type->data.structure.layout == ContainerLayoutExtern || struct_type->data.structure.layout == ContainerLayoutPacked))
|
||||
resolve_llvm_c_abi_type(g, struct_type);
|
||||
}
|
||||
|
||||
|
||||
@ -75,6 +75,24 @@ struct MedStructMixed {
|
||||
void zig_med_struct_mixed(struct MedStructMixed);
|
||||
struct MedStructMixed zig_ret_med_struct_mixed();
|
||||
|
||||
struct SmallPackedStruct {
|
||||
uint8_t a: 2;
|
||||
uint8_t b: 2;
|
||||
uint8_t c: 2;
|
||||
uint8_t d: 2;
|
||||
uint8_t e: 1;
|
||||
};
|
||||
|
||||
struct BigPackedStruct {
|
||||
uint64_t a: 64;
|
||||
uint64_t b: 64;
|
||||
uint64_t c: 64;
|
||||
uint64_t d: 64;
|
||||
uint8_t e: 8;
|
||||
};
|
||||
|
||||
//void zig_small_packed_struct(struct SmallPackedStruct); // #1481
|
||||
void zig_big_packed_struct(struct BigPackedStruct);
|
||||
|
||||
struct SplitStructInts {
|
||||
uint64_t a;
|
||||
@ -137,6 +155,16 @@ void run_c_tests(void) {
|
||||
zig_small_struct_ints(s);
|
||||
}
|
||||
|
||||
{
|
||||
struct BigPackedStruct s = {1, 2, 3, 4, 5};
|
||||
zig_big_packed_struct(s);
|
||||
}
|
||||
|
||||
{
|
||||
struct SmallPackedStruct s = {0, 1, 2, 3, 1};
|
||||
//zig_small_packed_struct(s);
|
||||
}
|
||||
|
||||
{
|
||||
struct SplitStructInts s = {1234, 100, 1337};
|
||||
zig_split_struct_ints(s);
|
||||
@ -318,6 +346,44 @@ void c_split_struct_mixed(struct SplitStructMixed x) {
|
||||
assert_or_panic(y.c == 1337.0f);
|
||||
}
|
||||
|
||||
struct SmallPackedStruct c_ret_small_packed_struct() {
|
||||
struct SmallPackedStruct s = {
|
||||
.a = 0,
|
||||
.b = 1,
|
||||
.c = 2,
|
||||
.d = 3,
|
||||
.e = 1,
|
||||
};
|
||||
return s;
|
||||
}
|
||||
|
||||
void c_small_packed_struct(struct SmallPackedStruct x) {
|
||||
assert_or_panic(x.a == 0);
|
||||
assert_or_panic(x.a == 1);
|
||||
assert_or_panic(x.a == 2);
|
||||
assert_or_panic(x.a == 3);
|
||||
assert_or_panic(x.e == 1);
|
||||
}
|
||||
|
||||
struct BigPackedStruct c_ret_big_packed_struct() {
|
||||
struct BigPackedStruct s = {
|
||||
.a = 1,
|
||||
.b = 2,
|
||||
.c = 3,
|
||||
.d = 4,
|
||||
.e = 5,
|
||||
};
|
||||
return s;
|
||||
}
|
||||
|
||||
void c_big_packed_struct(struct BigPackedStruct x) {
|
||||
assert_or_panic(x.a == 1);
|
||||
assert_or_panic(x.b == 2);
|
||||
assert_or_panic(x.c == 3);
|
||||
assert_or_panic(x.d == 4);
|
||||
assert_or_panic(x.e == 5);
|
||||
}
|
||||
|
||||
struct SplitStructMixed c_ret_split_struct_mixed() {
|
||||
struct SplitStructMixed s = {
|
||||
.a = 1234,
|
||||
|
||||
@ -230,6 +230,65 @@ export fn zig_small_struct_ints(x: SmallStructInts) void {
|
||||
expect(x.d == 4) catch @panic("test failure");
|
||||
}
|
||||
|
||||
const SmallPackedStruct = packed struct {
|
||||
a: u2,
|
||||
b: u2,
|
||||
c: u2,
|
||||
d: u2,
|
||||
e: bool,
|
||||
};
|
||||
const c_small_packed_struct: fn (SmallPackedStruct) callconv(.C) void = @compileError("TODO: #1481");
|
||||
extern fn c_ret_small_packed_struct() SmallPackedStruct;
|
||||
|
||||
// waiting on #1481
|
||||
//export fn zig_small_packed_struct(x: SmallPackedStruct) void {
|
||||
// expect(x.a == 0) catch @panic("test failure");
|
||||
// expect(x.b == 1) catch @panic("test failure");
|
||||
// expect(x.c == 2) catch @panic("test failure");
|
||||
// expect(x.d == 3) catch @panic("test failure");
|
||||
// expect(x.e) catch @panic("test failure");
|
||||
//}
|
||||
|
||||
test "C ABI small packed struct" {
|
||||
var s = SmallPackedStruct{ .a = 0, .b = 1, .c = 2, .d = 3, .e = true };
|
||||
_ = s; //c_small_packed_struct(s); // waiting on #1481
|
||||
var s2 = c_ret_small_packed_struct();
|
||||
try expect(s2.a == 0);
|
||||
try expect(s2.b == 1);
|
||||
try expect(s2.c == 2);
|
||||
try expect(s2.d == 3);
|
||||
try expect(s2.e);
|
||||
}
|
||||
|
||||
const BigPackedStruct = packed struct {
|
||||
a: u64,
|
||||
b: u64,
|
||||
c: u64,
|
||||
d: u64,
|
||||
e: u8,
|
||||
};
|
||||
extern fn c_big_packed_struct(BigPackedStruct) void;
|
||||
extern fn c_ret_big_packed_struct() BigPackedStruct;
|
||||
|
||||
export fn zig_big_packed_struct(x: BigPackedStruct) void {
|
||||
expect(x.a == 1) catch @panic("test failure");
|
||||
expect(x.b == 2) catch @panic("test failure");
|
||||
expect(x.c == 3) catch @panic("test failure");
|
||||
expect(x.d == 4) catch @panic("test failure");
|
||||
expect(x.e == 5) catch @panic("test failure");
|
||||
}
|
||||
|
||||
test "C ABI big packed struct" {
|
||||
var s = BigPackedStruct{ .a = 1, .b = 2, .c = 3, .d = 4, .e = 5 };
|
||||
c_big_packed_struct(s);
|
||||
var s2 = c_ret_big_packed_struct();
|
||||
try expect(s2.a == 1);
|
||||
try expect(s2.b == 2);
|
||||
try expect(s2.c == 3);
|
||||
try expect(s2.d == 4);
|
||||
try expect(s2.e == 5);
|
||||
}
|
||||
|
||||
const SplitStructInt = extern struct {
|
||||
a: u64,
|
||||
b: u8,
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user