llvm / llvm/llvm-project

Compound literals and definitions of objects with incomplete type are incorrectly allowed when the type is completed in the initializer

Open
#178,330 1 comment 0 reactions 0 assignees View on GitHub
clang:frontend
Dominant language
LLVM
Stars
40.5k
Forks
18.7k
PR merge metrics
PR metrics pending

Description

The following program demonstrates the issue:
```c
int main(){
struct A a={(struct A{int x;}){}.x};
(struct B){(struct B{int y;}){}.y};
}
```
Clang appears to allow definitions of objects with incomplete type, so long as the first init declarator has an initializer wherein the type is completed. Same with compound literals, if the type is incomplete and the braced initializer completes the type then clang allows it. GCC rejects both, the latter only with -pedantic-errors. MSVC rejects both. I think this should not be allowed, since a can be referenced before the definition appears. Compare with something like:
```c
struct C c[sizeof(struct C{int z;})];
```
Here `c` cannot be named until after the type is completed, so it makes more sense to allow this. GCC and MSVC also allow this, though the standard is not clear as to whether this is supposed to be allowed. Same with type names:
```c
sizeof(struct D[sizeof(struct D{int w;})]);
```

Contributor guide

Open the contributing guide

Research direction

Start by compiling the supplied reproducer with Clang and the comparison compilers, including GCC with and without -pedantic-errors. Then trace Clang's handling of incomplete struct object definitions and compound literals; done means the two disputed forms are rejected while the described sizeof cases retain their current behavior, with regression coverage.

Written by the indexing model from the issue text.

Assessment

Tech stack
c
Domain
compilers
Issue type
Bug
Difficulty
4/5
Estimated time
3-5 days
Activity status
Stale
Clarity
Mostly clear
Newbie friendliness
38/100

Get new issues in your inbox

A short digest of beginner-friendly GitHub issues.