translate-c: Fix translation of fn pointers

Closes #4332
This commit is contained in:
LemonBoy 2020-01-30 23:16:52 +01:00 committed by Andrew Kelley
parent 1e78070a40
commit 176bc53858
2 changed files with 21 additions and 22 deletions

View File

@ -3446,31 +3446,10 @@ fn qualTypeToLog2IntRef(rp: RestorePoint, qt: ZigClangQualType, source_loc: ZigC
}
fn qualTypeChildIsFnProto(qt: ZigClangQualType) bool {
const ty = ZigClangQualType_getTypePtr(qt);
const ty = qualTypeCanon(qt);
switch (ZigClangType_getTypeClass(ty)) {
.FunctionProto, .FunctionNoProto => return true,
.Elaborated => {
const elaborated_ty = @ptrCast(*const ZigClangElaboratedType, ty);
return qualTypeChildIsFnProto(ZigClangElaboratedType_getNamedType(elaborated_ty));
},
.Typedef => {
const typedef_ty = @ptrCast(*const ZigClangTypedefType, ty);
const typedef_decl = ZigClangTypedefType_getDecl(typedef_ty);
return qualTypeChildIsFnProto(ZigClangTypedefNameDecl_getUnderlyingType(typedef_decl));
},
.Paren => {
const paren_type = @ptrCast(*const ZigClangParenType, ty);
const inner_type = ZigClangParenType_getInnerType(paren_type);
switch (ZigClangQualType_getTypeClass(inner_type)) {
.FunctionProto, .FunctionNoProto => return true,
else => return false,
}
},
.Attributed => {
const attr_type = @ptrCast(*const ZigClangAttributedType, ty);
return qualTypeChildIsFnProto(ZigClangAttributedType_getEquivalentType(attr_type));
},
else => return false,
}
}

View File

@ -3,6 +3,26 @@ const builtin = @import("builtin");
const Target = @import("std").Target;
pub fn addCases(cases: *tests.TranslateCContext) void {
cases.add("function prototype translated as optional",
\\typedef void (*fnptr_ty)(void);
\\typedef __attribute__((cdecl)) void (*fnptr_attr_ty)(void);
\\struct foo {
\\ __attribute__((cdecl)) void (*foo)(void);
\\ void (*bar)(void);
\\ fnptr_ty baz;
\\ fnptr_attr_ty qux;
\\};
, &[_][]const u8{
\\pub const fnptr_ty = ?fn () callconv(.C) void;
\\pub const fnptr_attr_ty = ?fn () callconv(.C) void;
\\pub const struct_foo = extern struct {
\\ foo: ?fn () callconv(.C) void,
\\ bar: ?fn () callconv(.C) void,
\\ baz: fnptr_ty,
\\ qux: fnptr_attr_ty,
\\};
});
cases.add("function prototype with parenthesis",
\\void (f0) (void *L);
\\void ((f1)) (void *L);