Skip to content

Commit 355f1c7

Browse files
committed
[Clang] Fix PR28101
Fixes #28475 (PR28101) by setting identifier for invalid member variables with template parameters, so that the invalid declarators would not crash clang. See also: 942c03910a Differential Revision: https://reviews.llvm.org/D115248
1 parent 5ef2ec7 commit 355f1c7

File tree

3 files changed

+40
-0
lines changed

3 files changed

+40
-0
lines changed

clang/docs/ReleaseNotes.rst

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -69,6 +69,9 @@ Bug Fixes
6969
like ``auto&`` or ``auto**`` were added. These constraints are now checked.
7070
This fixes `Issue 53911 <https://github.com/llvm/llvm-project/issues/53911>`_
7171
and `Issue 54443 <https://github.com/llvm/llvm-project/issues/54443>`_.
72+
- Previously invalid member variables with template parameters would crash clang.
73+
Now fixed by setting identifiers for them.
74+
This fixes `Issue 28475 (PR28101) <https://github.com/llvm/llvm-project/issues/28475>`_.
7275

7376
Improvements to Clang's diagnostics
7477
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^

clang/lib/Sema/SemaDeclCXX.cpp

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -3427,6 +3427,7 @@ Sema::ActOnCXXMemberDeclarator(Scope *S, AccessSpecifier AS, Declarator &D,
34273427
<< SourceRange(D.getName().TemplateId->LAngleLoc,
34283428
D.getName().TemplateId->RAngleLoc)
34293429
<< D.getName().TemplateId->LAngleLoc;
3430+
D.SetIdentifier(Name.getAsIdentifierInfo(), Loc);
34303431
}
34313432

34323433
if (SS.isSet() && !SS.isInvalid()) {

clang/test/SemaCXX/PR28101.cpp

Lines changed: 36 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,36 @@
1+
// RUN: %clang_cc1 -fsyntax-only -verify -std=c++17 %s
2+
3+
template <typename T> struct A {
4+
A(void *) {}
5+
T(A<T>){}; // expected-error{{member 'A' cannot have template arguments}}\
6+
// expected-error2{{member 'A' has the same name as its class}}
7+
};
8+
// Don't crash.
9+
A<int> instantiate1() { return {nullptr}; } // expected-note{{in instantiation of template class 'A<int>' requested here}}
10+
11+
template <typename T> struct B {
12+
B(void *) {}
13+
T B<T>{}; // expected-error{{member 'B' cannot have template arguments}}\
14+
// expected-error2{{member 'B' has the same name as its class}}
15+
};
16+
// Don't crash.
17+
B<int> instantiate2() { return {nullptr}; } // expected-note{{in instantiation of template class 'B<int>' requested here}}
18+
19+
template <typename T> struct S {};
20+
21+
template <typename T> struct C {
22+
C(void *) {}
23+
T S<T>{}; // expected-error{{member 'S' cannot have template arguments}}
24+
};
25+
// Don't crash.
26+
C<int> instantiate3() { return {nullptr}; }
27+
28+
template <typename T, template <typename> typename U> class D {
29+
public:
30+
D(void *) {}
31+
T(D<T, U<T>>) {} // expected-error{{member 'D' cannot have template arguments}}\
32+
// expected-error{{expected ';' at end of declaration list}}\
33+
// expected-error2{{member 'D' has the same name as its class}}
34+
};
35+
// Don't crash.
36+
D<int, S> instantiate4() { return D<int, S>(nullptr); } // expected-note{{in instantiation of template class 'D<int, S>' requested here}}

0 commit comments

Comments
 (0)