diff options
author | Kim Gräsman <kim.grasman@gmail.com> | 2022-07-09 23:29:39 +0200 |
---|---|---|
committer | Kim Gräsman <kim.grasman@gmail.com> | 2022-07-24 22:02:19 +0200 |
commit | d2d4d15d8dcfebc388b07618ba3a9471223fc9d3 (patch) | |
tree | e79b271c21ddb578e9146f6b7535312cf9a2ebef | |
parent | 0f7a7aba8c949f97b579a4643367e9b9ffddf7c2 (diff) |
Allow forward-declaration of elaborated types in type decls
This covers the common C pattern of declaring a typedef for a struct before the
struct itself, e.g.
typedef struct foo foo_t;
struct foo {
int value;
foo_t *next;
};
Fixes issue #1065.
-rw-r--r-- | iwyu.cc | 5 | ||||
-rw-r--r-- | tests/c/elaborated_struct.c | 8 |
2 files changed, 13 insertions, 0 deletions
@@ -170,6 +170,7 @@ using clang::Decl; using clang::DeclContext; using clang::DeclRefExpr; using clang::DeducedTemplateSpecializationType; +using clang::ElaboratedType; using clang::EnumConstantDecl; using clang::EnumDecl; using clang::EnumType; @@ -2610,6 +2611,10 @@ class IwyuBaseAstVisitor : public BaseAstVisitor<Derived> { } parent_type = GetTypeOf(decl); + } else if (ast_node->IsA<ElaboratedType>()) { + // If it's not a ValueDecl, it must be a type decl. Elaborated types in + // type decls are forward-declarable. + return true; } } diff --git a/tests/c/elaborated_struct.c b/tests/c/elaborated_struct.c index 941ad69..5ef008c 100644 --- a/tests/c/elaborated_struct.c +++ b/tests/c/elaborated_struct.c @@ -28,6 +28,14 @@ int UseStruct(struct Struct* s); struct ForwardDeclared; void UseForwardDeclared(struct ForwardDeclared*); +// If a forward-declaration is seen before an actual struct declaration in the +// same file, no diagnostic is expected (see issue #1065). +typedef struct local_struct local_struct_t; +struct local_struct { + int x; + local_struct_t* next; +}; + /**** IWYU_SUMMARY tests/c/elaborated_struct.c should add these lines: |