Designated const initializers with {} would overwrite the parent field.

This commit is contained in:
Christoffer Lerno
2025-05-18 23:40:52 +02:00
parent 498803e9ba
commit c7f0d54328
3 changed files with 37 additions and 7 deletions

View File

@@ -32,6 +32,7 @@
- $define did not correctly handle generic types #2140.
- Incorrect parsing of call attributes #2144.
- Error when using named argument on trailing macro body expansion #2139.
- Designated const initializers with `{}` would overwrite the parent field.
### Stdlib changes
- Added `String.quick_ztr` and `String.is_zstr`

View File

@@ -939,18 +939,16 @@ static inline void sema_update_const_initializer_with_designator_struct(ConstIni
DesignatorElement **next_element = curr + 1;
bool is_last_path_element = next_element == end;
// Optimize in case this is a zero, e.g. [12].b = {}
if (is_last_path_element && sema_initializer_list_is_empty(value))
{
const_init->kind = CONST_INIT_ZERO;
ASSERT(type_flatten(value->type)->type_kind != TYPE_SLICE);
return;
}
Decl **elements = const_init->type->decl->strukt.members;
// Convert a zero struct and expand it into all its parts.
if (const_init->kind == CONST_INIT_ZERO)
{
if (is_last_path_element && sema_initializer_list_is_empty(value))
{
// In this case we can ignore it.
return;
}
const_init->init_struct = NULL;
// Allocate array containing all elements { a, b, c ... }
FOREACH_IDX(i, Decl *, el, elements)

View File

@@ -0,0 +1,31 @@
// #target: macos-x64
module test;
typedef Kind = int;
const Kind KIND_0 = 0;
const Kind KIND_1 = 1;
struct Foo
{
int a;
}
struct Descriptor2
{
Kind kind;
Foo flags;
}
Descriptor2 descriptor1 = {
.kind = KIND_1,
.flags = {},
};
fn int main()
{
Descriptor2 d = descriptor1;
return 0;
}
/* #expect: test.ll
@test.descriptor1 = local_unnamed_addr global %Descriptor2 { i32 1, %Foo zeroinitializer }, align 4