Skip to content

Commit 788dec3

Browse files
committed
Translator: demote records with fields with demoted types
Closes #182
1 parent 4051ee8 commit 788dec3

File tree

3 files changed

+13
-19
lines changed

3 files changed

+13
-19
lines changed

src/Translator.zig

Lines changed: 8 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -541,6 +541,13 @@ fn transRecordDecl(t: *Translator, scope: *Scope, record_qt: QualType) Error!voi
541541
break :init ZigTag.opaque_literal.init();
542542
}
543543

544+
// Demote record to opaque if it contains an opaque field
545+
if (t.typeWasDemotedToOpaque(field.qt)) {
546+
try t.opaque_demotes.put(t.gpa, base.qt, {});
547+
try t.warn(scope, field_loc, "{s} demoted to opaque type - has opaque field", .{container_kind_name});
548+
break :init ZigTag.opaque_literal.init();
549+
}
550+
544551
var field_name = field.name.lookup(t.comp);
545552
if (field.name_tok == 0) {
546553
field_name = try std.fmt.allocPrint(t.arena, "unnamed_{d}", .{unnamed_field_count});
@@ -1461,18 +1468,7 @@ fn typeIsOpaque(t: *Translator, qt: QualType) bool {
14611468
}
14621469

14631470
fn typeWasDemotedToOpaque(t: *Translator, qt: QualType) bool {
1464-
const base = qt.base(t.comp);
1465-
switch (base.type) {
1466-
.@"struct", .@"union" => |record_ty| {
1467-
if (t.opaque_demotes.contains(base.qt)) return true;
1468-
for (record_ty.fields) |field| {
1469-
if (t.typeWasDemotedToOpaque(field.qt)) return true;
1470-
}
1471-
return false;
1472-
},
1473-
.@"enum" => return t.opaque_demotes.contains(base.qt),
1474-
else => return false,
1475-
}
1471+
return t.opaque_demotes.contains(qt);
14761472
}
14771473

14781474
fn typeHasWrappingOverflow(t: *Translator, qt: QualType) bool {

test/cases/translate/Demote_function_that_dereference_types_that_contain_opaque_type.c

Lines changed: 2 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -13,10 +13,8 @@ void deref(struct outer *s) {
1313
//
1414
// pub const struct_inner = opaque {};
1515
//
16-
// pub const struct_outer = extern struct {
17-
// thing: c_int = 0,
18-
// sub_struct: struct_inner = @import("std").mem.zeroes(struct_inner),
19-
// };
16+
// warning: struct demoted to opaque type - has opaque field
17+
// pub const struct_outer = opaque {};
2018
//
2119
// warning: unable to translate function, demoted to extern
2220
//

test/cases/translate/pointer_to_opaque_demoted_struct.c

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -10,6 +10,6 @@ typedef struct {
1010
//
1111
// :2:17: warning: struct demoted to opaque type - unable to translate type of field foo
1212
// pub const Foo = opaque {};
13-
// pub const Bar = extern struct {
14-
// bar: ?*Foo = null,
15-
// };
13+
//
14+
// warning: struct demoted to opaque type - unable to translate type of field foo
15+
// pub const Foo = opaque {};

0 commit comments

Comments
 (0)