https://github.com/MaskRay created https://github.com/llvm/llvm-project/pull/182792
For ms_struct structs on Itanium layout targets, the packed attribute is ignored on bit-fields (2014 commit 76e1818a2b1248579557de2927c135c322577c82), mismatching the GCC behavior. Remove the `!IsMsStruct` guard to fix it. >From 7eb24d007ee65b6ccf139f4cb09e34837f8144a8 Mon Sep 17 00:00:00 2001 From: Fangrui Song <[email protected]> Date: Sun, 22 Feb 2026 18:33:48 -0800 Subject: [PATCH] Fix packed being ignored on ms_struct bitfields For ms_struct structs on Itanium layout targets, the packed attribute is ignored on bit-fields (2014 commit 76e1818a2b1248579557de2927c135c322577c82), mismatching the GCC behavior. Remove the `!IsMsStruct` guard to fix it. --- clang/lib/AST/RecordLayoutBuilder.cpp | 2 +- clang/test/CodeGen/ms_struct-bitfield.c | 4 ++-- clang/test/CodeGen/ms_struct-packed.c | 18 ++++++++++++++++++ 3 files changed, 21 insertions(+), 3 deletions(-) create mode 100644 clang/test/CodeGen/ms_struct-packed.c diff --git a/clang/lib/AST/RecordLayoutBuilder.cpp b/clang/lib/AST/RecordLayoutBuilder.cpp index 36b8eea92c0a4..dd052dd52e76e 100644 --- a/clang/lib/AST/RecordLayoutBuilder.cpp +++ b/clang/lib/AST/RecordLayoutBuilder.cpp @@ -1676,7 +1676,7 @@ void ItaniumRecordLayoutBuilder::LayoutBitField(const FieldDecl *D) { unsigned UnpackedFieldAlign = FieldAlign; // Ignore the field alignment if the field is packed unless it has zero-size. - if (!IsMsStruct && FieldPacked && FieldSize != 0) + if (FieldPacked && FieldSize != 0) FieldAlign = 1; // But, if there's an 'aligned' attribute on the field, honor that. diff --git a/clang/test/CodeGen/ms_struct-bitfield.c b/clang/test/CodeGen/ms_struct-bitfield.c index 37b0245e57c45..4598b880dd975 100644 --- a/clang/test/CodeGen/ms_struct-bitfield.c +++ b/clang/test/CodeGen/ms_struct-bitfield.c @@ -172,5 +172,5 @@ struct { __attribute__((packed)) unsigned short c : 6; } ATTR t13; int s13 = sizeof(t13); -// CHECK: @s13 ={{.*}} global i32 4 -// CHECK-ARM: @s13 ={{.*}} global i32 4 +// CHECK: @s13 ={{.*}} global i32 3 +// CHECK-ARM: @s13 ={{.*}} global i32 3 diff --git a/clang/test/CodeGen/ms_struct-packed.c b/clang/test/CodeGen/ms_struct-packed.c new file mode 100644 index 0000000000000..0cbf61a759b81 --- /dev/null +++ b/clang/test/CodeGen/ms_struct-packed.c @@ -0,0 +1,18 @@ +// RUN: %clang_cc1 -emit-llvm-only -triple x86_64 %s + +/// Packed struct: different storage unit types should pack without alignment +/// padding between storage units. +struct __attribute__((packed,ms_struct)) P1 { + short a : 8; + int b : 30; +}; + +static int p1[(sizeof(struct P1) == 6) ? 1 : -1]; + +// Packed struct with char and int fields. +struct [[gnu::ms_struct,gnu::packed]] P2 { + char a : 4; + int b : 20; +}; + +static int p2[(sizeof(struct P2) == 5) ? 1 : -1]; _______________________________________________ cfe-commits mailing list [email protected] https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
