[clang] Reapply "[Clang][Sema] Refactor collection of multi-level template argument lists (#106585)" (PR #111173)

2024-10-07 Thread Krystian Stasiowski via cfe-commits


@@ -4159,7 +4159,7 @@ FunctionTemplateDecl *FunctionDecl::getPrimaryTemplate() 
const {
   if (FunctionTemplateSpecializationInfo *Info
 = TemplateOrSpecialization
 .dyn_cast()) {
-return Info->getTemplate();
+return Info->getTemplate()->getMostRecentDecl();

sdkrystian wrote:

CC @zyn0217 & @erichkeane 

https://github.com/llvm/llvm-project/pull/73
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] Reapply "[Clang][Sema] Refactor collection of multi-level template argument lists (#106585)" (PR #111173)

2024-10-07 Thread Krystian Stasiowski via cfe-commits


@@ -4159,7 +4159,7 @@ FunctionTemplateDecl *FunctionDecl::getPrimaryTemplate() 
const {
   if (FunctionTemplateSpecializationInfo *Info
 = TemplateOrSpecialization
 .dyn_cast()) {
-return Info->getTemplate();
+return Info->getTemplate()->getMostRecentDecl();

sdkrystian wrote:

@mizvekov I reverted the change where `getPrimaryTemplate` returns the most 
recent declaration & changed `getTemplateInstantiationPattern` to use the most 
recent declaration of the primary template instead in 
d312bd464bae21d127f468075cb78178f782ca9a.

https://github.com/llvm/llvm-project/pull/73
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] Reapply "[Clang][Sema] Refactor collection of multi-level template argument lists (#106585)" (PR #111173)

2024-10-04 Thread Krystian Stasiowski via cfe-commits


@@ -4159,7 +4159,7 @@ FunctionTemplateDecl *FunctionDecl::getPrimaryTemplate() 
const {
   if (FunctionTemplateSpecializationInfo *Info
 = TemplateOrSpecialization
 .dyn_cast()) {
-return Info->getTemplate();
+return Info->getTemplate()->getMostRecentDecl();

sdkrystian wrote:

> Why do we need to get the most recent declaration in all these places?

@mizvekov One of the changes made by this patch is to set the 
`isMemberSpecialization` flag on a per-declaration basis. This ensures that 
`getTemplateInstantiationArgs` behaves correctly for implicitly instantiated 
declarations that are explicitly specialized for an implicitly instantiated 
specialization of their enclosing class template.

When we look up the name of a template, we typically find the most recent 
declaration of that template. If that declaration is an explicit specialization 
of a member template, we use the correct declaration when we try to find the 
definition of that template. However, if the member template is explicitly 
specialized _after_ we lookup its name, we end up with an expression naming the 
implicitly instantiated in-class declaration of that template. If we call 
`getTemplateInstantiationPattern` on that declaration, it will incorrectly 
return the pattern from the primary template.

https://github.com/llvm/llvm-project/pull/73
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] Reapply "[Clang][Sema] Refactor collection of multi-level template argument lists (#106585)" (PR #111173)

2024-10-04 Thread Krystian Stasiowski via cfe-commits

sdkrystian wrote:

@zyn0217 I have quite a few test cases I'll be adding soon

https://github.com/llvm/llvm-project/pull/73
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] Reapply "[Clang][Sema] Refactor collection of multi-level template argument lists (#106585)" (PR #111173)

2024-10-04 Thread Krystian Stasiowski via cfe-commits

sdkrystian wrote:

@erichkeane All changes made since the last review are in 
dfa5179f07b5a85c1daafd93b9f1d4bed9b4e27b

https://github.com/llvm/llvm-project/pull/73
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] Reapply "[Clang][Sema] Refactor collection of multi-level template argument lists (#106585)" (PR #111173)

2024-10-04 Thread Krystian Stasiowski via cfe-commits

https://github.com/sdkrystian updated 
https://github.com/llvm/llvm-project/pull/73

>From 51f84ce80ddda9e12591f263a24a19238fc69cb8 Mon Sep 17 00:00:00 2001
From: Krystian Stasiowski 
Date: Mon, 23 Sep 2024 10:51:21 -0400
Subject: [PATCH 1/2] Reapply "[Clang][Sema] Refactor collection of multi-level
 template argument lists (#106585)"

---
 clang/docs/ReleaseNotes.rst   |   3 +
 clang/include/clang/AST/DeclTemplate.h|  66 +-
 clang/include/clang/Sema/Sema.h   |  25 +-
 clang/lib/AST/DeclTemplate.cpp|  30 +-
 clang/lib/Sema/SemaConcept.cpp|  29 +-
 clang/lib/Sema/SemaDecl.cpp   |  31 +-
 clang/lib/Sema/SemaDeclCXX.cpp|   4 +-
 clang/lib/Sema/SemaTemplate.cpp   | 179 +++--
 clang/lib/Sema/SemaTemplateDeduction.cpp  |  33 +-
 clang/lib/Sema/SemaTemplateDeductionGuide.cpp |  45 +-
 clang/lib/Sema/SemaTemplateInstantiate.cpp| 712 +-
 .../lib/Sema/SemaTemplateInstantiateDecl.cpp  |  46 +-
 clang/lib/Serialization/ASTReader.cpp |   3 +-
 clang/lib/Serialization/ASTReaderDecl.cpp |  18 +-
 clang/lib/Serialization/ASTWriterDecl.cpp |  17 +-
 .../temp/temp.constr/temp.constr.decl/p4.cpp  | 175 +
 16 files changed, 762 insertions(+), 654 deletions(-)
 create mode 100644 clang/test/CXX/temp/temp.constr/temp.constr.decl/p4.cpp

diff --git a/clang/docs/ReleaseNotes.rst b/clang/docs/ReleaseNotes.rst
index 44d5f348ed2d54..fdb1a5942e4157 100644
--- a/clang/docs/ReleaseNotes.rst
+++ b/clang/docs/ReleaseNotes.rst
@@ -473,6 +473,9 @@ Bug Fixes to C++ Support
   containing outer unexpanded parameters were not correctly expanded. 
(#GH101754)
 - Fixed a bug in constraint expression comparison where the ``sizeof...`` 
expression was not handled properly
   in certain friend declarations. (#GH93099)
+- Clang now uses the correct set of template argument lists when comparing the 
constraints of
+  out-of-line definitions and member templates explicitly specialized for a 
given implicit instantiation of
+  a class template. (#GH102320)
 
 Bug Fixes to AST Handling
 ^
diff --git a/clang/include/clang/AST/DeclTemplate.h 
b/clang/include/clang/AST/DeclTemplate.h
index 687715a22e9fd3..05739f39d2a496 100644
--- a/clang/include/clang/AST/DeclTemplate.h
+++ b/clang/include/clang/AST/DeclTemplate.h
@@ -781,15 +781,11 @@ class RedeclarableTemplateDecl : public TemplateDecl,
  EntryType *Entry, void *InsertPos);
 
   struct CommonBase {
-CommonBase() : InstantiatedFromMember(nullptr, false) {}
+CommonBase() {}
 
 /// The template from which this was most
 /// directly instantiated (or null).
-///
-/// The boolean value indicates whether this template
-/// was explicitly specialized.
-llvm::PointerIntPair
-  InstantiatedFromMember;
+RedeclarableTemplateDecl *InstantiatedFromMember = nullptr;
 
 /// If non-null, points to an array of specializations (including
 /// partial specializations) known only by their external declaration IDs.
@@ -809,14 +805,19 @@ class RedeclarableTemplateDecl : public TemplateDecl,
   };
 
   /// Pointer to the common data shared by all declarations of this
-  /// template.
-  mutable CommonBase *Common = nullptr;
+  /// template, and a flag indicating if the template is a member
+  /// specialization.
+  mutable llvm::PointerIntPair Common;
+
+  CommonBase *getCommonPtrInternal() const { return Common.getPointer(); }
 
   /// Retrieves the "common" pointer shared by all (re-)declarations of
   /// the same template. Calling this routine may implicitly allocate memory
   /// for the common pointer.
   CommonBase *getCommonPtr() const;
 
+  void setCommonPtr(CommonBase *C) const { Common.setPointer(C); }
+
   virtual CommonBase *newCommon(ASTContext &C) const = 0;
 
   // Construct a template decl with name, parameters, and templated element.
@@ -857,15 +858,12 @@ class RedeclarableTemplateDecl : public TemplateDecl,
   /// template<> template
   /// struct X::Inner { /* ... */ };
   /// \endcode
-  bool isMemberSpecialization() const {
-return getCommonPtr()->InstantiatedFromMember.getInt();
-  }
+  bool isMemberSpecialization() const { return Common.getInt(); }
 
   /// Note that this member template is a specialization.
   void setMemberSpecialization() {
-assert(getCommonPtr()->InstantiatedFromMember.getPointer() &&
-   "Only member templates can be member template specializations");
-getCommonPtr()->InstantiatedFromMember.setInt(true);
+assert(!isMemberSpecialization() && "already a member specialization");
+Common.setInt(true);
   }
 
   /// Retrieve the member template from which this template was
@@ -905,12 +903,12 @@ class RedeclarableTemplateDecl : public TemplateDecl,
   /// void X::f(T, U);
   /// \endcode
   RedeclarableTemplateDecl *getInstantiatedFromMemberTemplate() const {
-return getCommonPtr()->InstantiatedFrom

[clang] Reapply "[Clang][Sema] Refactor collection of multi-level template argument lists (#106585)" (PR #111173)

2024-10-04 Thread Krystian Stasiowski via cfe-commits

https://github.com/sdkrystian created 
https://github.com/llvm/llvm-project/pull/73

Reapplies #106585, fixing an issue where non-dependent names of member 
templates appearing prior to that member template being explicitly specialized 
for an implicitly instantiated class template specialization would incorrectly 
use the definition of the explicitly specialized member template.


>From 14fe45b5e42f3993757f691a9f09899dcba8fb5b Mon Sep 17 00:00:00 2001
From: Krystian Stasiowski 
Date: Mon, 23 Sep 2024 10:51:21 -0400
Subject: [PATCH 1/2] Reapply "[Clang][Sema] Refactor collection of multi-level
 template argument lists (#106585)"

This reverts commit 1818ca5c4ae87ed222a18177caa7c8dde6c67efa.
---
 clang/docs/ReleaseNotes.rst   |   3 +
 clang/include/clang/AST/DeclTemplate.h|  66 +-
 clang/include/clang/Sema/Sema.h   |  25 +-
 clang/lib/AST/DeclTemplate.cpp|  30 +-
 clang/lib/Sema/SemaConcept.cpp|  29 +-
 clang/lib/Sema/SemaDecl.cpp   |  31 +-
 clang/lib/Sema/SemaDeclCXX.cpp|   4 +-
 clang/lib/Sema/SemaTemplate.cpp   | 179 +++--
 clang/lib/Sema/SemaTemplateDeduction.cpp  |  33 +-
 clang/lib/Sema/SemaTemplateDeductionGuide.cpp |  45 +-
 clang/lib/Sema/SemaTemplateInstantiate.cpp| 713 +-
 .../lib/Sema/SemaTemplateInstantiateDecl.cpp  |  46 +-
 clang/lib/Serialization/ASTReader.cpp |   3 +-
 clang/lib/Serialization/ASTReaderDecl.cpp |  18 +-
 clang/lib/Serialization/ASTWriterDecl.cpp |  17 +-
 .../temp/temp.constr/temp.constr.decl/p4.cpp  | 175 +
 16 files changed, 763 insertions(+), 654 deletions(-)
 create mode 100644 clang/test/CXX/temp/temp.constr/temp.constr.decl/p4.cpp

diff --git a/clang/docs/ReleaseNotes.rst b/clang/docs/ReleaseNotes.rst
index b47e06cb0c5d68..14867a029581e9 100644
--- a/clang/docs/ReleaseNotes.rst
+++ b/clang/docs/ReleaseNotes.rst
@@ -424,6 +424,9 @@ Bug Fixes to C++ Support
 - Fixed an assertion failure in debug mode, and potential crashes in release 
mode, when
   diagnosing a failed cast caused indirectly by a failed implicit conversion 
to the type of the constructor parameter.
 - Fixed an assertion failure by adjusting integral to boolean vector 
conversions (#GH108326)
+- Clang now uses the correct set of template argument lists when comparing the 
constraints of
+  out-of-line definitions and member templates explicitly specialized for a 
given implicit instantiation of
+  a class template. (#GH102320)
 
 Bug Fixes to AST Handling
 ^
diff --git a/clang/include/clang/AST/DeclTemplate.h 
b/clang/include/clang/AST/DeclTemplate.h
index 687715a22e9fd3..05739f39d2a496 100644
--- a/clang/include/clang/AST/DeclTemplate.h
+++ b/clang/include/clang/AST/DeclTemplate.h
@@ -781,15 +781,11 @@ class RedeclarableTemplateDecl : public TemplateDecl,
  EntryType *Entry, void *InsertPos);
 
   struct CommonBase {
-CommonBase() : InstantiatedFromMember(nullptr, false) {}
+CommonBase() {}
 
 /// The template from which this was most
 /// directly instantiated (or null).
-///
-/// The boolean value indicates whether this template
-/// was explicitly specialized.
-llvm::PointerIntPair
-  InstantiatedFromMember;
+RedeclarableTemplateDecl *InstantiatedFromMember = nullptr;
 
 /// If non-null, points to an array of specializations (including
 /// partial specializations) known only by their external declaration IDs.
@@ -809,14 +805,19 @@ class RedeclarableTemplateDecl : public TemplateDecl,
   };
 
   /// Pointer to the common data shared by all declarations of this
-  /// template.
-  mutable CommonBase *Common = nullptr;
+  /// template, and a flag indicating if the template is a member
+  /// specialization.
+  mutable llvm::PointerIntPair Common;
+
+  CommonBase *getCommonPtrInternal() const { return Common.getPointer(); }
 
   /// Retrieves the "common" pointer shared by all (re-)declarations of
   /// the same template. Calling this routine may implicitly allocate memory
   /// for the common pointer.
   CommonBase *getCommonPtr() const;
 
+  void setCommonPtr(CommonBase *C) const { Common.setPointer(C); }
+
   virtual CommonBase *newCommon(ASTContext &C) const = 0;
 
   // Construct a template decl with name, parameters, and templated element.
@@ -857,15 +858,12 @@ class RedeclarableTemplateDecl : public TemplateDecl,
   /// template<> template
   /// struct X::Inner { /* ... */ };
   /// \endcode
-  bool isMemberSpecialization() const {
-return getCommonPtr()->InstantiatedFromMember.getInt();
-  }
+  bool isMemberSpecialization() const { return Common.getInt(); }
 
   /// Note that this member template is a specialization.
   void setMemberSpecialization() {
-assert(getCommonPtr()->InstantiatedFromMember.getPointer() &&
-   "Only member templates can be member template specializations");
-getCommonPtr()->InstantiatedFromMem

[clang] [Clang][Sema] fix noexecpt mismatch of friend declaration (PR #102267)

2024-10-04 Thread Krystian Stasiowski via cfe-commits


@@ -4698,7 +4698,22 @@ void Sema::InstantiateExceptionSpec(SourceLocation 
PointOfInstantiation,
   // Enter the scope of this instantiation. We don't use
   // PushDeclContext because we don't have a scope.
   Sema::ContextRAII savedContext(*this, Decl);
+
+  FunctionDecl *Source = Proto->getExtProtoInfo().ExceptionSpec.SourceTemplate;
+  FunctionTemplateDecl *SourceTemplate = 
Source->getDescribedFunctionTemplate();
+  llvm::SmallDenseMap InstTemplateParams;
+  if (CurrentInstantiationScope && SourceTemplate)
+if (TemplateParameterList *TPL = SourceTemplate->getTemplateParameters())
+  for (NamedDecl *TemplateParam : *TPL)
+if (auto *Found =
+CurrentInstantiationScope->findInstantiationOf(TemplateParam))
+  if (auto *InstTemplateParam = Found->dyn_cast())
+InstTemplateParams[TemplateParam] = InstTemplateParam;
+

sdkrystian wrote:

Yeah, we should wait until I reland #106585 and then we can fix this. What we 
can then do is normalize the exception specification the same way we normalize 
constraints prior to comparing them.

https://github.com/llvm/llvm-project/pull/102267
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [Clang][Sema] Refactor collection of multi-level template argument lists (PR #106585)

2024-09-30 Thread Krystian Stasiowski via cfe-commits

sdkrystian wrote:

@zyn0217 I plan to reapply the patch after addressing the issues discussed 
above, but I have to get some more pressing work stuff done first :)

https://github.com/llvm/llvm-project/pull/106585
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [Clang][Sema] Refactor collection of multi-level template argument lists (PR #106585)

2024-09-24 Thread Krystian Stasiowski via cfe-commits

sdkrystian wrote:

Another example using class templates:
```cpp
template
struct A
{
template
struct B;
};

template<>
template
struct A<0>::B : A<1>::B { };

template<>
template
struct A<1>::B
{
static constexpr bool x = true;
};

static_assert(A<0>::B::x); // error: implicit instantiation of undefined 
template 'A<1>::B'
```
This currently results in a crash on trunk. With this patch applied, we 
instantiate the undefined class template declared in the definition of `A` and 
complain.

These differences in behavior arise from the fact that we bind names to the 
most recent redeclaration of an entity when creating `Expr` nodes that refer to 
that entity. In the above example, the explicit specialization of `A<1>::B` is 
declared after it is referenced in the explicit specialization of `A<0>::B`, 
resulting in the initial declaration being used to instantiate `B`.

IMO this behavior is correct per [[temp.expl.spec] 
p7](http://eel.is/c++draft/temp.expl.spec#7):
> If a template, a member template or a member of a class template is 
> explicitly specialized, a declaration of that specialization shall be 
> reachable from every use of that specialization that would cause an implicit 
> instantiation to take place, in every translation unit in which such a use 
> occurs; no diagnostic is required.

However, I would like to know what @erichkeane, @mizvekov, and @zygoloid think.

In any case, the QT example can be fixed by reordering the explicit 
specialization such that each specialization is declared before being 
referenced.

https://github.com/llvm/llvm-project/pull/106585
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [Clang][Sema] Refactor collection of multi-level template argument lists (PR #106585)

2024-09-23 Thread Krystian Stasiowski via cfe-commits

sdkrystian wrote:

Reduced further to:
```cpp
template
struct A
{
template
static constexpr bool f();
};

template<>
template
constexpr bool A<0>::f()
{
return A<1>::f(); // note: undefined function 'f' cannot be used in 
a constant expression
}

template<>
template
constexpr bool A<1>::f()
{
return true;
}

static_assert(A<0>::f()); // error: static assertion expression is not an 
integral constant expression
```

https://github.com/llvm/llvm-project/pull/106585
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [Clang][Sema] Refactor collection of multi-level template argument lists (PR #106585)

2024-09-23 Thread Krystian Stasiowski via cfe-commits

sdkrystian wrote:

I've manually reduced the standalone reproducer to the following:
```cpp
template
struct A
{
template
static constexpr bool f();
};

template<>
template
constexpr bool A<0>::f()
{
return A<1>::f();
}

template<>
template
constexpr bool A<1>::f()
{
return true;
}

template
constexpr bool g()
{
return A::template f(); // note: undefined function 'f' cannot 
be used in a constant expression
}

template bool g<0>();

static_assert(g<1>()); // error: static assertion expression is not an integral 
constant expression
```
The error does not occur if the explicit instantiation definition (i.e. 
`template bool g<0>()`) is removed. I'm looking into it.

https://github.com/llvm/llvm-project/pull/106585
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [Clang][Sema] Refactor collection of multi-level template argument lists (PR #106585)

2024-09-20 Thread Krystian Stasiowski via cfe-commits

https://github.com/sdkrystian closed 
https://github.com/llvm/llvm-project/pull/106585
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [clang] Fix false warning on reinterpret_casting unknown template type (PR #109430)

2024-09-20 Thread Krystian Stasiowski via cfe-commits

https://github.com/sdkrystian edited 
https://github.com/llvm/llvm-project/pull/109430
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [clang] Fix false warning on reinterpret_casting unknown template type (PR #109430)

2024-09-20 Thread Krystian Stasiowski via cfe-commits

https://github.com/sdkrystian requested changes to this pull request.


https://github.com/llvm/llvm-project/pull/109430
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [clang] Fix false warning on reinterpret_casting unknown template type (PR #109430)

2024-09-20 Thread Krystian Stasiowski via cfe-commits


@@ -2092,6 +2092,10 @@ void Sema::CheckCompatibleReinterpretCast(QualType 
SrcType, QualType DestType,
 }
   }
 
+  if (SrcTy->isTemplateTypeParmType() || DestTy->isTemplateTypeParmType()) {

sdkrystian wrote:

This should probably be`if (SrcTy->isDependentType() || 
DestTy->isDependentType())`. Otherwise we will continue to warn for the 
following:
```cpp
template
void f(T** x) {
  *reinterpret_cast(x);
}
```

https://github.com/llvm/llvm-project/pull/109430
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] Reapply "[Clang][Sema] Use the correct lookup context when building overloaded 'operator->' in the current instantiation (#104458)" (PR #109422)

2024-09-20 Thread Krystian Stasiowski via cfe-commits

sdkrystian wrote:

> Does this need a release note? 

I don't think so, since this fixes a bug introduced in the same release.

> Also, can you point out the 'diff' from the previous commit?

The condition of [the assert in 
`SemaExprCXX.cpp`](https://github.com/llvm/llvm-project/pull/109422/files#diff-1420e9cbc74252d1c2e98a97f80d3741bb4a44e8469d326ba3aa337260ee9800R8009)
 was changed from `BaseType->isDependentType()` to `Base->isTypeDependent()`, 
as was the condition on [line 1318 in 
`SemaExprMember.cpp`](https://github.com/llvm/llvm-project/pull/109422/files#diff-666d45282070e66014f8fb70e6c089762ea67ad4891f9819fdf5f8a5d5a0f570R1318).

> I'm really not a fan of the 'out' parameter, I'd prefer perhaps returning a 
> `std::pair` + structured binding. WDYT?

My initial solution was to return `ExprEmpty()`, but I changed to using an out 
parameter in response to review feedback (I don't like out parameters either).

https://github.com/llvm/llvm-project/pull/109422
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] Reapply "[Clang][Sema] Use the correct lookup context when building overloaded 'operator->' in the current instantiation (#104458)" (PR #109422)

2024-09-20 Thread Krystian Stasiowski via cfe-commits

https://github.com/sdkrystian edited 
https://github.com/llvm/llvm-project/pull/109422
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] Reapply "[Clang][Sema] Use the correct lookup context when building overloaded 'operator->' in the current instantiation (#104458)" (PR #109422)

2024-09-20 Thread Krystian Stasiowski via cfe-commits

https://github.com/sdkrystian updated 
https://github.com/llvm/llvm-project/pull/109422

>From d1b0cad696cca10c28ba32c290bc220ee917b48d Mon Sep 17 00:00:00 2001
From: Krystian Stasiowski 
Date: Thu, 15 Aug 2024 11:27:34 -0400
Subject: [PATCH 1/8] Reapply "[Clang][Sema] Use the correct lookup context
 when building overloaded 'operator->' in the current instantiation (#104458)"

---
 clang/include/clang/Sema/Sema.h   |  3 +--
 clang/lib/Sema/SemaExprCXX.cpp| 25 ---
 clang/lib/Sema/SemaOverload.cpp   | 14 +++
 clang/lib/Sema/TreeTransform.h|  4 +--
 .../temp.res/temp.dep/temp.dep.type/p4.cpp| 24 ++
 5 files changed, 35 insertions(+), 35 deletions(-)

diff --git a/clang/include/clang/Sema/Sema.h b/clang/include/clang/Sema/Sema.h
index 68c782a15c6f1b..040584f53a 100644
--- a/clang/include/clang/Sema/Sema.h
+++ b/clang/include/clang/Sema/Sema.h
@@ -10639,8 +10639,7 @@ class Sema final : public SemaBase {
   /// BuildOverloadedArrowExpr - Build a call to an overloaded @c operator->
   ///  (if one exists), where @c Base is an expression of class type and
   /// @c Member is the name of the member we're trying to find.
-  ExprResult BuildOverloadedArrowExpr(Scope *S, Expr *Base,
-  SourceLocation OpLoc,
+  ExprResult BuildOverloadedArrowExpr(Expr *Base, SourceLocation OpLoc,
   bool *NoArrowOperatorFound = nullptr);
 
   ExprResult BuildCXXMemberCallExpr(Expr *Exp, NamedDecl *FoundDecl,
diff --git a/clang/lib/Sema/SemaExprCXX.cpp b/clang/lib/Sema/SemaExprCXX.cpp
index 14feafd1e6b17f..f6e09f62cd3782 100644
--- a/clang/lib/Sema/SemaExprCXX.cpp
+++ b/clang/lib/Sema/SemaExprCXX.cpp
@@ -7966,18 +7966,6 @@ ExprResult Sema::ActOnStartCXXMemberReference(Scope *S, 
Expr *Base,
 
   QualType BaseType = Base->getType();
   MayBePseudoDestructor = false;
-  if (BaseType->isDependentType()) {
-// If we have a pointer to a dependent type and are using the -> operator,
-// the object type is the type that the pointer points to. We might still
-// have enough information about that type to do something useful.
-if (OpKind == tok::arrow)
-  if (const PointerType *Ptr = BaseType->getAs())
-BaseType = Ptr->getPointeeType();
-
-ObjectType = ParsedType::make(BaseType);
-MayBePseudoDestructor = true;
-return Base;
-  }
 
   // C++ [over.match.oper]p8:
   //   [...] When operator->returns, the operator-> is applied  to the value
@@ -7992,7 +7980,7 @@ ExprResult Sema::ActOnStartCXXMemberReference(Scope *S, 
Expr *Base,
 SmallVector OperatorArrows;
 CTypes.insert(Context.getCanonicalType(BaseType));
 
-while (BaseType->isRecordType()) {
+while (BaseType->getAsRecordDecl()) {
   if (OperatorArrows.size() >= getLangOpts().ArrowDepth) {
 Diag(OpLoc, diag::err_operator_arrow_depth_exceeded)
   << StartingType << getLangOpts().ArrowDepth << 
Base->getSourceRange();
@@ -8003,7 +7991,7 @@ ExprResult Sema::ActOnStartCXXMemberReference(Scope *S, 
Expr *Base,
   }
 
   Result = BuildOverloadedArrowExpr(
-  S, Base, OpLoc,
+  Base, OpLoc,
   // When in a template specialization and on the first loop iteration,
   // potentially give the default diagnostic (with the fixit in a
   // separate note) instead of having the error reported back to here
@@ -8029,7 +8017,14 @@ ExprResult Sema::ActOnStartCXXMemberReference(Scope *S, 
Expr *Base,
   }
 }
 return ExprError();
+  } else if (Result.isUnset()) {
+// BuildOverloadedArrowExpr returns an empty expression to indicate
+// that we need to build a dependent overloaded arrow expression.
+assert(BaseType->isDependentType());
+BaseType = Context.DependentTy;
+break;
   }
+
   Base = Result.get();
   if (CXXOperatorCallExpr *OpCall = dyn_cast(Base))
 OperatorArrows.push_back(OpCall->getDirectCallee());
@@ -8067,7 +8062,7 @@ ExprResult Sema::ActOnStartCXXMemberReference(Scope *S, 
Expr *Base,
   // it's legal for the type to be incomplete if this is a pseudo-destructor
   // call.  We'll do more incomplete-type checks later in the lookup process,
   // so just skip this check for ObjC types.
-  if (!BaseType->isRecordType()) {
+  if (!BaseType->getAsRecordDecl()) {
 ObjectType = ParsedType::make(BaseType);
 MayBePseudoDestructor = true;
 return Base;
diff --git a/clang/lib/Sema/SemaOverload.cpp b/clang/lib/Sema/SemaOverload.cpp
index 861b0a91240b3b..c09059f4c5510b 100644
--- a/clang/lib/Sema/SemaOverload.cpp
+++ b/clang/lib/Sema/SemaOverload.cpp
@@ -15878,10 +15878,9 @@ Sema::BuildCallToObjectOfClassType(Scope *S, Expr *Obj,
   return CheckForImmediateInvocation(MaybeBindToTemporary(TheCall), Method);
 }
 
-ExprResult
-Sema::BuildOverloadedArrowExpr(Scope *S, Expr *Base, SourceLocation OpLoc,
- 

[clang] Reapply "[Clang][Sema] Use the correct lookup context when building overloaded 'operator->' in the current instantiation (#104458)" (PR #109422)

2024-09-20 Thread Krystian Stasiowski via cfe-commits

https://github.com/sdkrystian created 
https://github.com/llvm/llvm-project/pull/109422

Reapplies #104458, fixing a bug that occurs when a templated class declares 
`operator->` to return a non-dependent class type.

>From d1b0cad696cca10c28ba32c290bc220ee917b48d Mon Sep 17 00:00:00 2001
From: Krystian Stasiowski 
Date: Thu, 15 Aug 2024 11:27:34 -0400
Subject: [PATCH 1/7] Reapply "[Clang][Sema] Use the correct lookup context
 when building overloaded 'operator->' in the current instantiation (#104458)"

---
 clang/include/clang/Sema/Sema.h   |  3 +--
 clang/lib/Sema/SemaExprCXX.cpp| 25 ---
 clang/lib/Sema/SemaOverload.cpp   | 14 +++
 clang/lib/Sema/TreeTransform.h|  4 +--
 .../temp.res/temp.dep/temp.dep.type/p4.cpp| 24 ++
 5 files changed, 35 insertions(+), 35 deletions(-)

diff --git a/clang/include/clang/Sema/Sema.h b/clang/include/clang/Sema/Sema.h
index 68c782a15c6f1b..040584f53a 100644
--- a/clang/include/clang/Sema/Sema.h
+++ b/clang/include/clang/Sema/Sema.h
@@ -10639,8 +10639,7 @@ class Sema final : public SemaBase {
   /// BuildOverloadedArrowExpr - Build a call to an overloaded @c operator->
   ///  (if one exists), where @c Base is an expression of class type and
   /// @c Member is the name of the member we're trying to find.
-  ExprResult BuildOverloadedArrowExpr(Scope *S, Expr *Base,
-  SourceLocation OpLoc,
+  ExprResult BuildOverloadedArrowExpr(Expr *Base, SourceLocation OpLoc,
   bool *NoArrowOperatorFound = nullptr);
 
   ExprResult BuildCXXMemberCallExpr(Expr *Exp, NamedDecl *FoundDecl,
diff --git a/clang/lib/Sema/SemaExprCXX.cpp b/clang/lib/Sema/SemaExprCXX.cpp
index 14feafd1e6b17f..f6e09f62cd3782 100644
--- a/clang/lib/Sema/SemaExprCXX.cpp
+++ b/clang/lib/Sema/SemaExprCXX.cpp
@@ -7966,18 +7966,6 @@ ExprResult Sema::ActOnStartCXXMemberReference(Scope *S, 
Expr *Base,
 
   QualType BaseType = Base->getType();
   MayBePseudoDestructor = false;
-  if (BaseType->isDependentType()) {
-// If we have a pointer to a dependent type and are using the -> operator,
-// the object type is the type that the pointer points to. We might still
-// have enough information about that type to do something useful.
-if (OpKind == tok::arrow)
-  if (const PointerType *Ptr = BaseType->getAs())
-BaseType = Ptr->getPointeeType();
-
-ObjectType = ParsedType::make(BaseType);
-MayBePseudoDestructor = true;
-return Base;
-  }
 
   // C++ [over.match.oper]p8:
   //   [...] When operator->returns, the operator-> is applied  to the value
@@ -7992,7 +7980,7 @@ ExprResult Sema::ActOnStartCXXMemberReference(Scope *S, 
Expr *Base,
 SmallVector OperatorArrows;
 CTypes.insert(Context.getCanonicalType(BaseType));
 
-while (BaseType->isRecordType()) {
+while (BaseType->getAsRecordDecl()) {
   if (OperatorArrows.size() >= getLangOpts().ArrowDepth) {
 Diag(OpLoc, diag::err_operator_arrow_depth_exceeded)
   << StartingType << getLangOpts().ArrowDepth << 
Base->getSourceRange();
@@ -8003,7 +7991,7 @@ ExprResult Sema::ActOnStartCXXMemberReference(Scope *S, 
Expr *Base,
   }
 
   Result = BuildOverloadedArrowExpr(
-  S, Base, OpLoc,
+  Base, OpLoc,
   // When in a template specialization and on the first loop iteration,
   // potentially give the default diagnostic (with the fixit in a
   // separate note) instead of having the error reported back to here
@@ -8029,7 +8017,14 @@ ExprResult Sema::ActOnStartCXXMemberReference(Scope *S, 
Expr *Base,
   }
 }
 return ExprError();
+  } else if (Result.isUnset()) {
+// BuildOverloadedArrowExpr returns an empty expression to indicate
+// that we need to build a dependent overloaded arrow expression.
+assert(BaseType->isDependentType());
+BaseType = Context.DependentTy;
+break;
   }
+
   Base = Result.get();
   if (CXXOperatorCallExpr *OpCall = dyn_cast(Base))
 OperatorArrows.push_back(OpCall->getDirectCallee());
@@ -8067,7 +8062,7 @@ ExprResult Sema::ActOnStartCXXMemberReference(Scope *S, 
Expr *Base,
   // it's legal for the type to be incomplete if this is a pseudo-destructor
   // call.  We'll do more incomplete-type checks later in the lookup process,
   // so just skip this check for ObjC types.
-  if (!BaseType->isRecordType()) {
+  if (!BaseType->getAsRecordDecl()) {
 ObjectType = ParsedType::make(BaseType);
 MayBePseudoDestructor = true;
 return Base;
diff --git a/clang/lib/Sema/SemaOverload.cpp b/clang/lib/Sema/SemaOverload.cpp
index 861b0a91240b3b..c09059f4c5510b 100644
--- a/clang/lib/Sema/SemaOverload.cpp
+++ b/clang/lib/Sema/SemaOverload.cpp
@@ -15878,10 +15878,9 @@ Sema::BuildCallToObjectOfClassType(Scope *S, Expr *Obj,
   return CheckForImmediateInvocation(MaybeBindToTemporary(TheCa

[clang] [Clang][Sema] Refactor collection of multi-level template argument lists (PR #106585)

2024-09-17 Thread Krystian Stasiowski via cfe-commits


@@ -585,8 +585,8 @@ static bool CheckConstraintSatisfaction(
 
   ArrayRef TemplateArgs =
   TemplateArgsLists.getNumSubstitutedLevels() > 0
-  ? TemplateArgsLists.getOutermost()
-  : ArrayRef {};
+  ? TemplateArgsLists.getInnermost()

sdkrystian wrote:

Yeah, the old implementation was just wrong.

https://github.com/llvm/llvm-project/pull/106585
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [Clang][Sema] Use the correct lookup context when building overloaded 'operator->' in the current instantiation (PR #104458)

2024-09-17 Thread Krystian Stasiowski via cfe-commits

sdkrystian wrote:

@porglezomp Sorry, I'm currently at cppcon but I'll try reland it when I have a 
moment.

https://github.com/llvm/llvm-project/pull/104458
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [Clang][Sema] Refactor collection of multi-level template argument lists (PR #106585)

2024-09-17 Thread Krystian Stasiowski via cfe-commits


@@ -585,8 +585,8 @@ static bool CheckConstraintSatisfaction(
 
   ArrayRef TemplateArgs =
   TemplateArgsLists.getNumSubstitutedLevels() > 0
-  ? TemplateArgsLists.getOutermost()
-  : ArrayRef {};
+  ? TemplateArgsLists.getInnermost()

sdkrystian wrote:

The innermost template arguments are the ones that actually pertain to the 
template we are instantiating... the outermost arguments pertain to some 
unrelated containing template.

https://github.com/llvm/llvm-project/pull/106585
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [Clang][Sema] Refactor collection of multi-level template argument lists (PR #106585)

2024-09-17 Thread Krystian Stasiowski via cfe-commits

sdkrystian wrote:

Ping @erichkeane 

https://github.com/llvm/llvm-project/pull/106585
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [Clang][Sema] fix noexecpt mismatch of friend declaration (PR #102267)

2024-09-17 Thread Krystian Stasiowski via cfe-commits

sdkrystian wrote:

@ericniebler Once I merge #106585, I have a follow up patch ready that will fix 
#101330.

https://github.com/llvm/llvm-project/pull/102267
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [Clang][Sema] Use the correct lookup context when building overloaded 'operator->' in the current instantiation (PR #104458)

2024-09-13 Thread Krystian Stasiowski via cfe-commits

sdkrystian wrote:

I have a fix, so I'll reapply this sometime today.

https://github.com/llvm/llvm-project/pull/104458
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [Clang][Sema] Use the correct lookup context when building overloaded 'operator->' in the current instantiation (PR #104458)

2024-09-09 Thread Krystian Stasiowski via cfe-commits

https://github.com/sdkrystian closed 
https://github.com/llvm/llvm-project/pull/104458
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [Clang][Sema] Use the correct lookup context when building overloaded 'operator->' in the current instantiation (PR #104458)

2024-09-09 Thread Krystian Stasiowski via cfe-commits

https://github.com/sdkrystian edited 
https://github.com/llvm/llvm-project/pull/104458
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [Clang][Sema] Use the correct lookup context when building overloaded 'operator->' in the current instantiation (PR #104458)

2024-09-09 Thread Krystian Stasiowski via cfe-commits

https://github.com/sdkrystian updated 
https://github.com/llvm/llvm-project/pull/104458

>From 11f67c73a8de04ce94dbed467de043668234e202 Mon Sep 17 00:00:00 2001
From: Krystian Stasiowski 
Date: Thu, 15 Aug 2024 11:27:34 -0400
Subject: [PATCH 1/5] [Clang][Sema] Use the correct lookup context when
 building overloaded 'operator->' in the current instantiation

---
 clang/include/clang/Sema/Sema.h   |  3 +--
 clang/lib/Sema/SemaExprCXX.cpp| 25 ---
 clang/lib/Sema/SemaOverload.cpp   | 14 +++
 clang/lib/Sema/TreeTransform.h|  4 +--
 .../temp.res/temp.dep/temp.dep.type/p4.cpp| 24 ++
 5 files changed, 35 insertions(+), 35 deletions(-)

diff --git a/clang/include/clang/Sema/Sema.h b/clang/include/clang/Sema/Sema.h
index 68c782a15c6f1b..040584f53a 100644
--- a/clang/include/clang/Sema/Sema.h
+++ b/clang/include/clang/Sema/Sema.h
@@ -10639,8 +10639,7 @@ class Sema final : public SemaBase {
   /// BuildOverloadedArrowExpr - Build a call to an overloaded @c operator->
   ///  (if one exists), where @c Base is an expression of class type and
   /// @c Member is the name of the member we're trying to find.
-  ExprResult BuildOverloadedArrowExpr(Scope *S, Expr *Base,
-  SourceLocation OpLoc,
+  ExprResult BuildOverloadedArrowExpr(Expr *Base, SourceLocation OpLoc,
   bool *NoArrowOperatorFound = nullptr);
 
   ExprResult BuildCXXMemberCallExpr(Expr *Exp, NamedDecl *FoundDecl,
diff --git a/clang/lib/Sema/SemaExprCXX.cpp b/clang/lib/Sema/SemaExprCXX.cpp
index 14feafd1e6b17f..f6e09f62cd3782 100644
--- a/clang/lib/Sema/SemaExprCXX.cpp
+++ b/clang/lib/Sema/SemaExprCXX.cpp
@@ -7966,18 +7966,6 @@ ExprResult Sema::ActOnStartCXXMemberReference(Scope *S, 
Expr *Base,
 
   QualType BaseType = Base->getType();
   MayBePseudoDestructor = false;
-  if (BaseType->isDependentType()) {
-// If we have a pointer to a dependent type and are using the -> operator,
-// the object type is the type that the pointer points to. We might still
-// have enough information about that type to do something useful.
-if (OpKind == tok::arrow)
-  if (const PointerType *Ptr = BaseType->getAs())
-BaseType = Ptr->getPointeeType();
-
-ObjectType = ParsedType::make(BaseType);
-MayBePseudoDestructor = true;
-return Base;
-  }
 
   // C++ [over.match.oper]p8:
   //   [...] When operator->returns, the operator-> is applied  to the value
@@ -7992,7 +7980,7 @@ ExprResult Sema::ActOnStartCXXMemberReference(Scope *S, 
Expr *Base,
 SmallVector OperatorArrows;
 CTypes.insert(Context.getCanonicalType(BaseType));
 
-while (BaseType->isRecordType()) {
+while (BaseType->getAsRecordDecl()) {
   if (OperatorArrows.size() >= getLangOpts().ArrowDepth) {
 Diag(OpLoc, diag::err_operator_arrow_depth_exceeded)
   << StartingType << getLangOpts().ArrowDepth << 
Base->getSourceRange();
@@ -8003,7 +7991,7 @@ ExprResult Sema::ActOnStartCXXMemberReference(Scope *S, 
Expr *Base,
   }
 
   Result = BuildOverloadedArrowExpr(
-  S, Base, OpLoc,
+  Base, OpLoc,
   // When in a template specialization and on the first loop iteration,
   // potentially give the default diagnostic (with the fixit in a
   // separate note) instead of having the error reported back to here
@@ -8029,7 +8017,14 @@ ExprResult Sema::ActOnStartCXXMemberReference(Scope *S, 
Expr *Base,
   }
 }
 return ExprError();
+  } else if (Result.isUnset()) {
+// BuildOverloadedArrowExpr returns an empty expression to indicate
+// that we need to build a dependent overloaded arrow expression.
+assert(BaseType->isDependentType());
+BaseType = Context.DependentTy;
+break;
   }
+
   Base = Result.get();
   if (CXXOperatorCallExpr *OpCall = dyn_cast(Base))
 OperatorArrows.push_back(OpCall->getDirectCallee());
@@ -8067,7 +8062,7 @@ ExprResult Sema::ActOnStartCXXMemberReference(Scope *S, 
Expr *Base,
   // it's legal for the type to be incomplete if this is a pseudo-destructor
   // call.  We'll do more incomplete-type checks later in the lookup process,
   // so just skip this check for ObjC types.
-  if (!BaseType->isRecordType()) {
+  if (!BaseType->getAsRecordDecl()) {
 ObjectType = ParsedType::make(BaseType);
 MayBePseudoDestructor = true;
 return Base;
diff --git a/clang/lib/Sema/SemaOverload.cpp b/clang/lib/Sema/SemaOverload.cpp
index 861b0a91240b3b..c09059f4c5510b 100644
--- a/clang/lib/Sema/SemaOverload.cpp
+++ b/clang/lib/Sema/SemaOverload.cpp
@@ -15878,10 +15878,9 @@ Sema::BuildCallToObjectOfClassType(Scope *S, Expr *Obj,
   return CheckForImmediateInvocation(MaybeBindToTemporary(TheCall), Method);
 }
 
-ExprResult
-Sema::BuildOverloadedArrowExpr(Scope *S, Expr *Base, SourceLocation OpLoc,
-   bool *NoAr

[clang] [Clang][Sema] Use the correct lookup context when building overloaded 'operator->' in the current instantiation (PR #104458)

2024-09-09 Thread Krystian Stasiowski via cfe-commits

https://github.com/sdkrystian updated 
https://github.com/llvm/llvm-project/pull/104458

>From 11f67c73a8de04ce94dbed467de043668234e202 Mon Sep 17 00:00:00 2001
From: Krystian Stasiowski 
Date: Thu, 15 Aug 2024 11:27:34 -0400
Subject: [PATCH 1/4] [Clang][Sema] Use the correct lookup context when
 building overloaded 'operator->' in the current instantiation

---
 clang/include/clang/Sema/Sema.h   |  3 +--
 clang/lib/Sema/SemaExprCXX.cpp| 25 ---
 clang/lib/Sema/SemaOverload.cpp   | 14 +++
 clang/lib/Sema/TreeTransform.h|  4 +--
 .../temp.res/temp.dep/temp.dep.type/p4.cpp| 24 ++
 5 files changed, 35 insertions(+), 35 deletions(-)

diff --git a/clang/include/clang/Sema/Sema.h b/clang/include/clang/Sema/Sema.h
index 68c782a15c6f1b..040584f53a 100644
--- a/clang/include/clang/Sema/Sema.h
+++ b/clang/include/clang/Sema/Sema.h
@@ -10639,8 +10639,7 @@ class Sema final : public SemaBase {
   /// BuildOverloadedArrowExpr - Build a call to an overloaded @c operator->
   ///  (if one exists), where @c Base is an expression of class type and
   /// @c Member is the name of the member we're trying to find.
-  ExprResult BuildOverloadedArrowExpr(Scope *S, Expr *Base,
-  SourceLocation OpLoc,
+  ExprResult BuildOverloadedArrowExpr(Expr *Base, SourceLocation OpLoc,
   bool *NoArrowOperatorFound = nullptr);
 
   ExprResult BuildCXXMemberCallExpr(Expr *Exp, NamedDecl *FoundDecl,
diff --git a/clang/lib/Sema/SemaExprCXX.cpp b/clang/lib/Sema/SemaExprCXX.cpp
index 14feafd1e6b17f..f6e09f62cd3782 100644
--- a/clang/lib/Sema/SemaExprCXX.cpp
+++ b/clang/lib/Sema/SemaExprCXX.cpp
@@ -7966,18 +7966,6 @@ ExprResult Sema::ActOnStartCXXMemberReference(Scope *S, 
Expr *Base,
 
   QualType BaseType = Base->getType();
   MayBePseudoDestructor = false;
-  if (BaseType->isDependentType()) {
-// If we have a pointer to a dependent type and are using the -> operator,
-// the object type is the type that the pointer points to. We might still
-// have enough information about that type to do something useful.
-if (OpKind == tok::arrow)
-  if (const PointerType *Ptr = BaseType->getAs())
-BaseType = Ptr->getPointeeType();
-
-ObjectType = ParsedType::make(BaseType);
-MayBePseudoDestructor = true;
-return Base;
-  }
 
   // C++ [over.match.oper]p8:
   //   [...] When operator->returns, the operator-> is applied  to the value
@@ -7992,7 +7980,7 @@ ExprResult Sema::ActOnStartCXXMemberReference(Scope *S, 
Expr *Base,
 SmallVector OperatorArrows;
 CTypes.insert(Context.getCanonicalType(BaseType));
 
-while (BaseType->isRecordType()) {
+while (BaseType->getAsRecordDecl()) {
   if (OperatorArrows.size() >= getLangOpts().ArrowDepth) {
 Diag(OpLoc, diag::err_operator_arrow_depth_exceeded)
   << StartingType << getLangOpts().ArrowDepth << 
Base->getSourceRange();
@@ -8003,7 +7991,7 @@ ExprResult Sema::ActOnStartCXXMemberReference(Scope *S, 
Expr *Base,
   }
 
   Result = BuildOverloadedArrowExpr(
-  S, Base, OpLoc,
+  Base, OpLoc,
   // When in a template specialization and on the first loop iteration,
   // potentially give the default diagnostic (with the fixit in a
   // separate note) instead of having the error reported back to here
@@ -8029,7 +8017,14 @@ ExprResult Sema::ActOnStartCXXMemberReference(Scope *S, 
Expr *Base,
   }
 }
 return ExprError();
+  } else if (Result.isUnset()) {
+// BuildOverloadedArrowExpr returns an empty expression to indicate
+// that we need to build a dependent overloaded arrow expression.
+assert(BaseType->isDependentType());
+BaseType = Context.DependentTy;
+break;
   }
+
   Base = Result.get();
   if (CXXOperatorCallExpr *OpCall = dyn_cast(Base))
 OperatorArrows.push_back(OpCall->getDirectCallee());
@@ -8067,7 +8062,7 @@ ExprResult Sema::ActOnStartCXXMemberReference(Scope *S, 
Expr *Base,
   // it's legal for the type to be incomplete if this is a pseudo-destructor
   // call.  We'll do more incomplete-type checks later in the lookup process,
   // so just skip this check for ObjC types.
-  if (!BaseType->isRecordType()) {
+  if (!BaseType->getAsRecordDecl()) {
 ObjectType = ParsedType::make(BaseType);
 MayBePseudoDestructor = true;
 return Base;
diff --git a/clang/lib/Sema/SemaOverload.cpp b/clang/lib/Sema/SemaOverload.cpp
index 861b0a91240b3b..c09059f4c5510b 100644
--- a/clang/lib/Sema/SemaOverload.cpp
+++ b/clang/lib/Sema/SemaOverload.cpp
@@ -15878,10 +15878,9 @@ Sema::BuildCallToObjectOfClassType(Scope *S, Expr *Obj,
   return CheckForImmediateInvocation(MaybeBindToTemporary(TheCall), Method);
 }
 
-ExprResult
-Sema::BuildOverloadedArrowExpr(Scope *S, Expr *Base, SourceLocation OpLoc,
-   bool *NoAr

[clang] [Clang][Sema] Use the correct lookup context when building overloaded 'operator->' in the current instantiation (PR #104458)

2024-09-04 Thread Krystian Stasiowski via cfe-commits

https://github.com/sdkrystian edited 
https://github.com/llvm/llvm-project/pull/104458
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [Clang][Sema] Use the correct lookup context when building overloaded 'operator->' in the current instantiation (PR #104458)

2024-09-04 Thread Krystian Stasiowski via cfe-commits


@@ -7981,7 +7969,7 @@ ExprResult Sema::ActOnStartCXXMemberReference(Scope *S, 
Expr *Base,
 SmallVector OperatorArrows;
 CTypes.insert(Context.getCanonicalType(BaseType));
 
-while (BaseType->isRecordType()) {
+while (BaseType->getAsRecordDecl()) {

sdkrystian wrote:

Perhaps it would be worth introducing `Type::isCXXRecord` for this check. We do 
it quite often... @cor3ntin WDYT?

https://github.com/llvm/llvm-project/pull/104458
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [Clang][Sema] Use the correct lookup context when building overloaded 'operator->' in the current instantiation (PR #104458)

2024-09-03 Thread Krystian Stasiowski via cfe-commits


@@ -7981,7 +7969,7 @@ ExprResult Sema::ActOnStartCXXMemberReference(Scope *S, 
Expr *Base,
 SmallVector OperatorArrows;
 CTypes.insert(Context.getCanonicalType(BaseType));
 
-while (BaseType->isRecordType()) {
+while (BaseType->getAsRecordDecl()) {

sdkrystian wrote:

It's essentially a shortcut for `BaseType->isRecordType() || 
isa(BaseType->getCanonicalTypeInternal())`

https://github.com/llvm/llvm-project/pull/104458
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [Clang][Sema] Use the correct lookup context when building overloaded 'operator->' in the current instantiation (PR #104458)

2024-09-03 Thread Krystian Stasiowski via cfe-commits

https://github.com/sdkrystian updated 
https://github.com/llvm/llvm-project/pull/104458

>From a719de89be6af3607f67baddd8868f8e0fc7882f Mon Sep 17 00:00:00 2001
From: Krystian Stasiowski 
Date: Thu, 15 Aug 2024 11:27:34 -0400
Subject: [PATCH 1/3] [Clang][Sema] Use the correct lookup context when
 building overloaded 'operator->' in the current instantiation

---
 clang/include/clang/Sema/Sema.h   |  3 +--
 clang/lib/Sema/SemaExprCXX.cpp| 25 ---
 clang/lib/Sema/SemaOverload.cpp   | 14 +++
 clang/lib/Sema/TreeTransform.h|  4 +--
 .../temp.res/temp.dep/temp.dep.type/p4.cpp| 24 ++
 5 files changed, 35 insertions(+), 35 deletions(-)

diff --git a/clang/include/clang/Sema/Sema.h b/clang/include/clang/Sema/Sema.h
index 0358259945c796..023b99db41db42 100644
--- a/clang/include/clang/Sema/Sema.h
+++ b/clang/include/clang/Sema/Sema.h
@@ -10639,8 +10639,7 @@ class Sema final : public SemaBase {
   /// BuildOverloadedArrowExpr - Build a call to an overloaded @c operator->
   ///  (if one exists), where @c Base is an expression of class type and
   /// @c Member is the name of the member we're trying to find.
-  ExprResult BuildOverloadedArrowExpr(Scope *S, Expr *Base,
-  SourceLocation OpLoc,
+  ExprResult BuildOverloadedArrowExpr(Expr *Base, SourceLocation OpLoc,
   bool *NoArrowOperatorFound = nullptr);
 
   ExprResult BuildCXXMemberCallExpr(Expr *Exp, NamedDecl *FoundDecl,
diff --git a/clang/lib/Sema/SemaExprCXX.cpp b/clang/lib/Sema/SemaExprCXX.cpp
index b7531581d37ff0..45c0d0e22d9605 100644
--- a/clang/lib/Sema/SemaExprCXX.cpp
+++ b/clang/lib/Sema/SemaExprCXX.cpp
@@ -7955,18 +7955,6 @@ ExprResult Sema::ActOnStartCXXMemberReference(Scope *S, 
Expr *Base,
 
   QualType BaseType = Base->getType();
   MayBePseudoDestructor = false;
-  if (BaseType->isDependentType()) {
-// If we have a pointer to a dependent type and are using the -> operator,
-// the object type is the type that the pointer points to. We might still
-// have enough information about that type to do something useful.
-if (OpKind == tok::arrow)
-  if (const PointerType *Ptr = BaseType->getAs())
-BaseType = Ptr->getPointeeType();
-
-ObjectType = ParsedType::make(BaseType);
-MayBePseudoDestructor = true;
-return Base;
-  }
 
   // C++ [over.match.oper]p8:
   //   [...] When operator->returns, the operator-> is applied  to the value
@@ -7981,7 +7969,7 @@ ExprResult Sema::ActOnStartCXXMemberReference(Scope *S, 
Expr *Base,
 SmallVector OperatorArrows;
 CTypes.insert(Context.getCanonicalType(BaseType));
 
-while (BaseType->isRecordType()) {
+while (BaseType->getAsRecordDecl()) {
   if (OperatorArrows.size() >= getLangOpts().ArrowDepth) {
 Diag(OpLoc, diag::err_operator_arrow_depth_exceeded)
   << StartingType << getLangOpts().ArrowDepth << 
Base->getSourceRange();
@@ -7992,7 +7980,7 @@ ExprResult Sema::ActOnStartCXXMemberReference(Scope *S, 
Expr *Base,
   }
 
   Result = BuildOverloadedArrowExpr(
-  S, Base, OpLoc,
+  Base, OpLoc,
   // When in a template specialization and on the first loop iteration,
   // potentially give the default diagnostic (with the fixit in a
   // separate note) instead of having the error reported back to here
@@ -8018,7 +8006,14 @@ ExprResult Sema::ActOnStartCXXMemberReference(Scope *S, 
Expr *Base,
   }
 }
 return ExprError();
+  } else if (Result.isUnset()) {
+// BuildOverloadedArrowExpr returns an empty expression to indicate
+// that we need to build a dependent overloaded arrow expression.
+assert(BaseType->isDependentType());
+BaseType = Context.DependentTy;
+break;
   }
+
   Base = Result.get();
   if (CXXOperatorCallExpr *OpCall = dyn_cast(Base))
 OperatorArrows.push_back(OpCall->getDirectCallee());
@@ -8056,7 +8051,7 @@ ExprResult Sema::ActOnStartCXXMemberReference(Scope *S, 
Expr *Base,
   // it's legal for the type to be incomplete if this is a pseudo-destructor
   // call.  We'll do more incomplete-type checks later in the lookup process,
   // so just skip this check for ObjC types.
-  if (!BaseType->isRecordType()) {
+  if (!BaseType->getAsRecordDecl()) {
 ObjectType = ParsedType::make(BaseType);
 MayBePseudoDestructor = true;
 return Base;
diff --git a/clang/lib/Sema/SemaOverload.cpp b/clang/lib/Sema/SemaOverload.cpp
index 95551173df91a5..6170ae579fd2a0 100644
--- a/clang/lib/Sema/SemaOverload.cpp
+++ b/clang/lib/Sema/SemaOverload.cpp
@@ -15876,10 +15876,9 @@ Sema::BuildCallToObjectOfClassType(Scope *S, Expr *Obj,
   return CheckForImmediateInvocation(MaybeBindToTemporary(TheCall), Method);
 }
 
-ExprResult
-Sema::BuildOverloadedArrowExpr(Scope *S, Expr *Base, SourceLocation OpLoc,
-   bool *NoAr

[clang] [Clang][Sema] Use the correct lookup context when building overloaded 'operator->' in the current instantiation (PR #104458)

2024-09-03 Thread Krystian Stasiowski via cfe-commits


@@ -7939,7 +7927,14 @@ ExprResult Sema::ActOnStartCXXMemberReference(Scope *S, 
Expr *Base,
   }
 }
 return ExprError();
+  } else if (Result.isUnset()) {
+// BuildOverloadedArrowExpr returns an empty expression to indicate
+// that we need to build a dependent overloaded arrow expression.

sdkrystian wrote:

@cor3ntin Pushed changes that do what you described

https://github.com/llvm/llvm-project/pull/104458
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [Clang][Sema] Use the correct lookup context when building overloaded 'operator->' in the current instantiation (PR #104458)

2024-09-03 Thread Krystian Stasiowski via cfe-commits


@@ -7939,7 +7927,14 @@ ExprResult Sema::ActOnStartCXXMemberReference(Scope *S, 
Expr *Base,
   }
 }
 return ExprError();
+  } else if (Result.isUnset()) {
+// BuildOverloadedArrowExpr returns an empty expression to indicate
+// that we need to build a dependent overloaded arrow expression.

sdkrystian wrote:

> I have 2 concerns with that 
> 1/ It's a bit too clever of an interface

Although I agree it's an imperfect interface, this is more of a "transitional" 
fix. Ideally we will build the full AST for calls to members of the current 
instantiation in the future. For now, the usage of `ExprEmpty` in this patch 
isn't unfounded so I think it's "good enough". Alternatively I can add a `bool& 
IsDependent` out parameter to implement this functionality. 

> 2/ We should make sure this can only happens in Sema, right? I wonder if we 
> need an ActOnOverloadedArrowExpr to wrap that logic such that (it would 
> duplicate the lookup code but i think that's a better outcome)

I'm not entirely sure what this means. Are you saying that we should expect the 
result to _not_ be `ExprEmpty` during instantiation?

https://github.com/llvm/llvm-project/pull/104458
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [Clang][Sema] Use the correct lookup context when building overloaded 'operator->' in the current instantiation (PR #104458)

2024-09-03 Thread Krystian Stasiowski via cfe-commits

sdkrystian wrote:

@cor3ntin Excellent, then I think this is good to go

https://github.com/llvm/llvm-project/pull/104458
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [Clang][Sema] Refactor collection of multi-level template argument lists (PR #106585)

2024-09-03 Thread Krystian Stasiowski via cfe-commits

sdkrystian wrote:

Ping @mizvekov 

https://github.com/llvm/llvm-project/pull/106585
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [Clang][Sema] Use the correct lookup context when building overloaded 'operator->' in the current instantiation (PR #104458)

2024-09-03 Thread Krystian Stasiowski via cfe-commits

sdkrystian wrote:

@cor3ntin After giving it another look, I think the existing tests are 
sufficient (the tests updated by this PR were written by me to test this exact 
scenario). WDYT?

https://github.com/llvm/llvm-project/pull/104458
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [Clang][Sema] Refactor collection of multi-level template argument lists (PR #106585)

2024-09-03 Thread Krystian Stasiowski via cfe-commits


@@ -2112,6 +2078,33 @@ DeclResult Sema::CheckClassTemplate(
   NewClass->setLexicalDeclContext(CurContext);
   NewTemplate->setLexicalDeclContext(CurContext);
 
+  // Ensure that the template parameter lists are compatible. Skip this check
+  // for a friend in a dependent context: the template parameter list itself
+  // could be dependent.
+  if (ShouldAddRedecl && PrevClassTemplate &&
+  !TemplateParameterListsAreEqual(
+  NewTemplate, TemplateParams, PrevClassTemplate,
+  PrevClassTemplate->getTemplateParameters(),
+  /*Complain=*/true, TPL_TemplateMatch))
+return true;
+
+  // Check the template parameter list of this declaration, possibly
+  // merging in the template parameter list from the previous class
+  // template declaration. Skip this check for a friend in a dependent
+  // context, because the template parameter list might be dependent.
+  if (ShouldAddRedecl &&
+  CheckTemplateParameterList(
+  TemplateParams,
+  PrevClassTemplate ? PrevClassTemplate->getTemplateParameters()
+: nullptr,
+  (SS.isSet() && SemanticContext && SemanticContext->isRecord() &&
+   SemanticContext->isDependentContext())
+  ? TPC_ClassTemplateMember
+  : TUK == TagUseKind::Friend ? TPC_FriendClassTemplate
+  : TPC_ClassTemplate,
+  SkipBody))

sdkrystian wrote:

@zyn0217 Since this is existing code which I moved, I would prefer to keep it 
as-is and perhaps address this in some future NFC patch.

https://github.com/llvm/llvm-project/pull/106585
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [Clang][Sema] Refactor collection of multi-level template argument lists (PR #106585)

2024-09-03 Thread Krystian Stasiowski via cfe-commits


@@ -33,11 +33,12 @@ class D{}; // expected-note{{previous definition is here}}
 template
 class D{}; // expected-error{{class template partial specialization does 
not specialize any template argument; to define the primary template, remove 
the template argument list}} expected-error{{redefinition of 'D'}}
 
-template requires C1 // expected-note{{previous template 
declaration is here}}
-class E{};
+template requires C1
+class E{}; // expected-note{{previous definition is here}}
 
-template // expected-error{{requires clause differs in template 
redeclaration}}
+template

sdkrystian wrote:

I can move the point at which we emit the redefinition error to be after the 
check for equivalent _template-heads_, if you'd like. Then we would get the 
"requires clause differs in template redeclaration" error instead.

https://github.com/llvm/llvm-project/pull/106585
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [Clang][Sema] Refactor collection of multi-level template argument lists (PR #106585)

2024-08-30 Thread Krystian Stasiowski via cfe-commits

https://github.com/sdkrystian edited 
https://github.com/llvm/llvm-project/pull/106585
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [Clang][Sema] Refactor collection of multi-level template argument lists (PR #106585)

2024-08-30 Thread Krystian Stasiowski via cfe-commits

sdkrystian wrote:

> Also, do you plan to fix #102320 in this or the follow-up patches?

@zyn0217 This patch (in its current state) fixes #102320 :)

https://github.com/llvm/llvm-project/pull/106585
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [Clang][Sema] Refactor collection of multi-level template argument lists (PR #106585)

2024-08-30 Thread Krystian Stasiowski via cfe-commits

https://github.com/sdkrystian edited 
https://github.com/llvm/llvm-project/pull/106585
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [Clang][Sema] Refactor collection of multi-level template argument lists (PR #106585)

2024-08-30 Thread Krystian Stasiowski via cfe-commits


@@ -1669,25 +1640,43 @@ namespace {
 
 ExprResult RebuildLambdaExpr(SourceLocation StartLoc, SourceLocation 
EndLoc,
  LambdaScopeInfo *LSI) {
+#if 1
   CXXMethodDecl *MD = LSI->CallOperator;
-  for (ParmVarDecl *PVD : MD->parameters()) {
-assert(PVD && "null in a parameter list");
-if (!PVD->hasDefaultArg())
-  continue;
-Expr *UninstExpr = PVD->getUninstantiatedDefaultArg();
-// FIXME: Obtain the source location for the '=' token.
-SourceLocation EqualLoc = UninstExpr->getBeginLoc();
-if (SemaRef.SubstDefaultArgument(EqualLoc, PVD, TemplateArgs)) {
-  // If substitution fails, the default argument is set to a
-  // RecoveryExpr that wraps the uninstantiated default argument so
-  // that downstream diagnostics are omitted.
-  ExprResult ErrorResult = SemaRef.CreateRecoveryExpr(
-  UninstExpr->getBeginLoc(), UninstExpr->getEndLoc(),
-  { UninstExpr }, UninstExpr->getType());
-  if (ErrorResult.isUsable())
-PVD->setDefaultArg(ErrorResult.get());
+  // if (MD->getParentFunctionOrMethod()) {
+  if (true) {
+#if 0
+NamedDecl *Pattern = MD;
+  std::optional> Innermost;
+if (FunctionTemplateDecl *FTD = MD->getDescribedFunctionTemplate()) {
+  Pattern = FTD;
+  Innermost = FTD->getInjectedTemplateArgs();
+}
+MultiLevelTemplateArgumentList MLTAL =
+SemaRef.getTemplateInstantiationArgs(Pattern, 
Pattern->getLexicalDeclContext(),
+ /*Final=*/false, Innermost,
+ /*RelativeToPrimary=*/true);
+#endif
+;

sdkrystian wrote:

This is leftover from when I was experimenting with correctly substituting 
lambda default arguments. It proved to be too much work, so I abandoned that 
effort.

https://github.com/llvm/llvm-project/pull/106585
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [Clang][Sema] Refactor collection of multi-level template argument lists (PR #106585)

2024-08-30 Thread Krystian Stasiowski via cfe-commits


@@ -171,374 +139,379 @@ bool isLambdaEnclosedByTypeAliasDecl(
   .TraverseType(Underlying);
 }
 
-// Add template arguments from a variable template instantiation.
-Response
-HandleVarTemplateSpec(const VarTemplateSpecializationDecl *VarTemplSpec,
-  MultiLevelTemplateArgumentList &Result,
-  bool SkipForSpecialization) {
-  // For a class-scope explicit specialization, there are no template arguments
-  // at this level, but there may be enclosing template arguments.
-  if (VarTemplSpec->isClassScopeExplicitSpecialization())
-return Response::DontClearRelativeToPrimaryNextDecl(VarTemplSpec);
-
-  // We're done when we hit an explicit specialization.
-  if (VarTemplSpec->getSpecializationKind() == TSK_ExplicitSpecialization &&
-  !isa(VarTemplSpec))
-return Response::Done();
-
-  // If this variable template specialization was instantiated from a
-  // specialized member that is a variable template, we're done.
-  assert(VarTemplSpec->getSpecializedTemplate() && "No variable template?");
-  llvm::PointerUnion
-  Specialized = VarTemplSpec->getSpecializedTemplateOrPartial();
-  if (VarTemplatePartialSpecializationDecl *Partial =
-  Specialized.dyn_cast()) {
-if (!SkipForSpecialization)
-  Result.addOuterTemplateArguments(
-  Partial, VarTemplSpec->getTemplateInstantiationArgs().asArray(),
-  /*Final=*/false);
-if (Partial->isMemberSpecialization())
-  return Response::Done();
-  } else {
-VarTemplateDecl *Tmpl = Specialized.get();
-if (!SkipForSpecialization)
-  Result.addOuterTemplateArguments(
-  Tmpl, VarTemplSpec->getTemplateInstantiationArgs().asArray(),
-  /*Final=*/false);
-if (Tmpl->isMemberSpecialization())
-  return Response::Done();
+struct TemplateInstantiationArgumentCollecter
+: DeclVisitor {
+  Sema &S;
+  MultiLevelTemplateArgumentList &Result;
+  std::optional> Innermost;
+  bool RelativeToPrimary;
+  bool ForConstraintInstantiation;
+
+  TemplateInstantiationArgumentCollecter(
+  Sema &S, MultiLevelTemplateArgumentList &Result,
+  std::optional> Innermost,
+  bool RelativeToPrimary, bool ForConstraintInstantiation)
+  : S(S), Result(Result), Innermost(Innermost),
+RelativeToPrimary(RelativeToPrimary),
+ForConstraintInstantiation(ForConstraintInstantiation) {}
+
+  Decl *Done() { return nullptr; }
+
+  Decl *ChangeDecl(const Decl *D) {
+RelativeToPrimary = false;
+return const_cast(D);
   }
-  return Response::DontClearRelativeToPrimaryNextDecl(VarTemplSpec);
-}
 
-// If we have a template template parameter with translation unit context,
-// then we're performing substitution into a default template argument of
-// this template template parameter before we've constructed the template
-// that will own this template template parameter. In this case, we
-// use empty template parameter lists for all of the outer templates
-// to avoid performing any substitutions.
-Response
-HandleDefaultTempArgIntoTempTempParam(const TemplateTemplateParmDecl *TTP,
-  MultiLevelTemplateArgumentList &Result) {
-  for (unsigned I = 0, N = TTP->getDepth() + 1; I != N; ++I)
-Result.addOuterTemplateArguments(std::nullopt);
-  return Response::Done();
-}
+  Decl *ChangeDecl(const DeclContext *DC) {
+return ChangeDecl(Decl::castFromDeclContext(DC));
+  }
 
-Response HandlePartialClassTemplateSpec(
-const ClassTemplatePartialSpecializationDecl *PartialClassTemplSpec,
-MultiLevelTemplateArgumentList &Result, bool SkipForSpecialization) {
-  if (!SkipForSpecialization)
-  Result.addOuterRetainedLevels(PartialClassTemplSpec->getTemplateDepth());
-  return Response::Done();
-}
+  Decl *UseNextDecl(const Decl *D) { return ChangeDecl(D->getDeclContext()); }
 
-// Add template arguments from a class template instantiation.
-Response
-HandleClassTemplateSpec(const ClassTemplateSpecializationDecl *ClassTemplSpec,
-MultiLevelTemplateArgumentList &Result,
-bool SkipForSpecialization) {
-  if (!ClassTemplSpec->isClassScopeExplicitSpecialization()) {
-// We're done when we hit an explicit specialization.
-if (ClassTemplSpec->getSpecializationKind() == TSK_ExplicitSpecialization 
&&
-!isa(ClassTemplSpec))
-  return Response::Done();
+  Decl *DontClearRelativeToPrimaryNextDecl(const Decl *D) {
+return const_cast(Decl::castFromDeclContext(D->getDeclContext()));
+  }
 
-if (!SkipForSpecialization)
-  Result.addOuterTemplateArguments(
-  const_cast(ClassTemplSpec),
-  ClassTemplSpec->getTemplateInstantiationArgs().asArray(),
-  /*Final=*/false);
+  void AddInnermostTemplateArguments(const Decl *D) {
+assert(Innermost);
+Result.addOuterTemplateArguments(const_cast(D), *Innermost,
+ /*Final=*/false);
+Innermost.reset();
+  }
 
-

[clang] [Clang][Sema] Refactor collection of multi-level template argument lists (PR #106585)

2024-08-30 Thread Krystian Stasiowski via cfe-commits


@@ -1056,16 +1052,20 @@ bool Sema::AreConstraintExpressionsEqual(const 
NamedDecl *Old,
 bool Sema::FriendConstraintsDependOnEnclosingTemplate(const FunctionDecl *FD) {
   assert(FD->getFriendObjectKind() && "Must be a friend!");
 
+  FunctionTemplateDecl *FTD = FD->getDescribedFunctionTemplate();
   // The logic for non-templates is handled in ASTContext::isSameEntity, so we
   // don't have to bother checking 'DependsOnEnclosingTemplate' for a
   // non-function-template.
-  assert(FD->getDescribedFunctionTemplate() &&
- "Non-function templates don't need to be checked");
+  assert(FTD && "Non-function templates don't need to be checked");
 
   SmallVector ACs;
-  FD->getDescribedFunctionTemplate()->getAssociatedConstraints(ACs);
+  FTD->getAssociatedConstraints(ACs);
 
+#if 0

sdkrystian wrote:

Yup. There are still a few others I need to clean up

https://github.com/llvm/llvm-project/pull/106585
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [Clang][Sema] Refactor collection of multi-level template argument lists (PR #106585)

2024-08-30 Thread Krystian Stasiowski via cfe-commits


@@ -317,7 +317,8 @@ struct ConvertConstructorToDeductionGuideTransform {
 }
 
 if (NestedPattern)
-  OuterInstantiationArgs = SemaRef.getTemplateInstantiationArgs(Template);
+  OuterInstantiationArgs = SemaRef.getTemplateInstantiationArgs(
+  /*D=*/nullptr, Template->getDeclContext());

sdkrystian wrote:

This is an artifact from when I was figuring out the implementation... I'll 
revert this change.

https://github.com/llvm/llvm-project/pull/106585
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [Clang][Sema] Refactor collection of multi-level template argument lists (PR #106585)

2024-08-30 Thread Krystian Stasiowski via cfe-commits


@@ -809,8 +809,9 @@ class RedeclarableTemplateDecl : public TemplateDecl,
   };
 
   /// Pointer to the common data shared by all declarations of this
-  /// template.
-  mutable CommonBase *Common = nullptr;
+  /// template, and a flag indicating if the template is a member
+  /// specialization.
+  mutable llvm::PointerIntPair Common;

sdkrystian wrote:

> Do you think it is more appropriate to move the flag to 
> `Common->InstantiatedFromMember`? That way the flag won't be scattered, right?

I moved the flag here because we want to set the flag before we know whether it 
is a redeclaration.

https://github.com/llvm/llvm-project/pull/106585
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [Clang][Sema] Use the correct lookup context when building overloaded 'operator->' in the current instantiation (PR #104458)

2024-08-26 Thread Krystian Stasiowski via cfe-commits

sdkrystian wrote:

@cor3ntin What's the deadline?

https://github.com/llvm/llvm-project/pull/104458
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [Clang][Sema] Use the correct lookup context when building overloaded 'operator->' in the current instantiation (PR #104458)

2024-08-26 Thread Krystian Stasiowski via cfe-commits

sdkrystian wrote:

> Can you please add more details in your summary about the problem and how the 
> PR will fix the problem.
@shafik I will once I get back to this PR.

> @sdkrystian do you plan to add more tests?
@cor3ntin I do, I just haven't gotten around to it yet :)

https://github.com/llvm/llvm-project/pull/104458
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [Clang][Sema] Rebuild template parameters for out-of-line template definitions and partial specializations (PR #104030)

2024-08-22 Thread Krystian Stasiowski via cfe-commits

https://github.com/sdkrystian closed 
https://github.com/llvm/llvm-project/pull/104030
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [Clang][Sema] Rebuild template parameters for out-of-line template definitions and partial specializations (PR #104030)

2024-08-22 Thread Krystian Stasiowski via cfe-commits

https://github.com/sdkrystian updated 
https://github.com/llvm/llvm-project/pull/104030

>From 14db4ba124a36ea778515fe0228ae959081f6d65 Mon Sep 17 00:00:00 2001
From: Krystian Stasiowski 
Date: Wed, 14 Aug 2024 09:00:30 -0400
Subject: [PATCH 1/3] [Clang][Sema] Rebuild template parameters for out-of-line
 template definitions and partial specializations

---
 clang/lib/Sema/SemaDecl.cpp   |   6 +
 clang/lib/Sema/SemaTemplate.cpp   |  20 ++--
 .../test/CXX/temp/temp.decls/temp.mem/p1.cpp  | 112 +-
 3 files changed, 129 insertions(+), 9 deletions(-)

diff --git a/clang/lib/Sema/SemaDecl.cpp b/clang/lib/Sema/SemaDecl.cpp
index 503e93f9257137..b0ccbbe34b70c3 100644
--- a/clang/lib/Sema/SemaDecl.cpp
+++ b/clang/lib/Sema/SemaDecl.cpp
@@ -7502,6 +7502,12 @@ NamedDecl *Sema::ActOnVariableDeclarator(
 /*never a friend*/ false, IsMemberSpecialization, Invalid);
 
 if (TemplateParams) {
+  if (DC->isDependentContext()) {
+ContextRAII SavedContext(*this, DC);
+if (RebuildTemplateParamsInCurrentInstantiation(TemplateParams))
+  Invalid = true;
+  }
+
   if (!TemplateParams->size() &&
   D.getName().getKind() != UnqualifiedIdKind::IK_TemplateId) {
 // There is an extraneous 'template<>' for this variable. Complain
diff --git a/clang/lib/Sema/SemaTemplate.cpp b/clang/lib/Sema/SemaTemplate.cpp
index 992565701d40ca..f8f41d0bafffc3 100644
--- a/clang/lib/Sema/SemaTemplate.cpp
+++ b/clang/lib/Sema/SemaTemplate.cpp
@@ -8089,13 +8089,14 @@ DeclResult Sema::ActOnClassTemplateSpecialization(
 return true;
   }
 
+  DeclContext *DC = ClassTemplate->getDeclContext();
+
   bool isMemberSpecialization = false;
   bool isPartialSpecialization = false;
 
   if (SS.isSet()) {
 if (TUK != TagUseKind::Reference && TUK != TagUseKind::Friend &&
-diagnoseQualifiedDeclaration(SS, ClassTemplate->getDeclContext(),
- ClassTemplate->getDeclName(),
+diagnoseQualifiedDeclaration(SS, DC, ClassTemplate->getDeclName(),
  TemplateNameLoc, &TemplateId,
  /*IsMemberSpecialization=*/false))
   return true;
@@ -8117,6 +8118,12 @@ DeclResult Sema::ActOnClassTemplateSpecialization(
   if (TemplateParams && CheckTemplateDeclScope(S, TemplateParams))
 return true;
 
+  if (TemplateParams && DC->isDependentContext()) {
+ContextRAII SavedContext(*this, DC);
+if (RebuildTemplateParamsInCurrentInstantiation(TemplateParams))
+  return true;
+  }
+
   if (TemplateParams && TemplateParams->size() > 0) {
 isPartialSpecialization = true;
 
@@ -8282,9 +8289,8 @@ DeclResult Sema::ActOnClassTemplateSpecialization(
   = cast_or_null(PrevDecl);
 ClassTemplatePartialSpecializationDecl *Partial =
 ClassTemplatePartialSpecializationDecl::Create(
-Context, Kind, ClassTemplate->getDeclContext(), KWLoc,
-TemplateNameLoc, TemplateParams, ClassTemplate, CanonicalConverted,
-CanonType, PrevPartial);
+Context, Kind, DC, KWLoc, TemplateNameLoc, TemplateParams,
+ClassTemplate, CanonicalConverted, CanonType, PrevPartial);
 Partial->setTemplateArgsAsWritten(TemplateArgs);
 SetNestedNameSpecifier(*this, Partial, SS);
 if (TemplateParameterLists.size() > 1 && SS.isSet()) {
@@ -8306,8 +8312,8 @@ DeclResult Sema::ActOnClassTemplateSpecialization(
 // Create a new class template specialization declaration node for
 // this explicit specialization or friend declaration.
 Specialization = ClassTemplateSpecializationDecl::Create(
-Context, Kind, ClassTemplate->getDeclContext(), KWLoc, TemplateNameLoc,
-ClassTemplate, CanonicalConverted, PrevDecl);
+Context, Kind, DC, KWLoc, TemplateNameLoc, ClassTemplate,
+CanonicalConverted, PrevDecl);
 Specialization->setTemplateArgsAsWritten(TemplateArgs);
 SetNestedNameSpecifier(*this, Specialization, SS);
 if (TemplateParameterLists.size() > 0) {
diff --git a/clang/test/CXX/temp/temp.decls/temp.mem/p1.cpp 
b/clang/test/CXX/temp/temp.decls/temp.mem/p1.cpp
index b48e145e1468db..64b1274419e35d 100644
--- a/clang/test/CXX/temp/temp.decls/temp.mem/p1.cpp
+++ b/clang/test/CXX/temp/temp.decls/temp.mem/p1.cpp
@@ -1,5 +1,4 @@
-// RUN: %clang_cc1 -fsyntax-only -verify %s
-// expected-no-diagnostics
+// RUN: %clang_cc1 -fsyntax-only -std=c++20 -verify %s
 
 template  struct A {
   static T cond;
@@ -35,3 +34,112 @@ namespace PR6376 {
 
   Z z0;
 }
+
+namespace OutOfLine {
+  template
+  struct A {
+struct B { };
+
+template
+void f();
+
+template
+void g() { } // expected-note {{previous definition is here}}
+
+template
+static int x;
+
+template
+static int x;
+
+template
+static constexpr int x = 0; // expected-note {{previous definition 
is here}}
+
+template
+struct C;
+
+template
+struct C;
+
+templ

[clang] [libcxx] Reapply "[Clang] Implement resolution for CWG1835 (#92957, #98547)" (PR #100425)

2024-08-19 Thread Krystian Stasiowski via cfe-commits

sdkrystian wrote:

@cor3ntin This wouldn't fix [the case that abseil users complained 
about](https://github.com/llvm/llvm-project/pull/98547#issuecomment-2224998395) 
(example reduced from [the 
source](https://github.com/abseil/abseil-cpp/blob/master/absl/container/internal/compressed_tuple.h#L256)):
```cpp
template 
class CompressedTuple
: private internal_compressed_tuple::CompressedTupleImpl<
  CompressedTuple, absl::index_sequence_for,
  internal_compressed_tuple::ShouldAnyUseBase()> {

  template 
  using StorageT = internal_compressed_tuple::Storage, I>;

 public:
  template 
  constexpr ElemT&& get() && {
return std::move(*this).StorageT::get();
  }
};
```

Moreover, this fails to address cases where the base class declares a 
non-static data member with the same name as the class template:
```cpp
template
struct A
{
int A;
};

template
struct B : A
{
bool f()
{
return this->A < 1; // '<' would be interpreted as the start of a 
template argument list
}
};
```

I think that implementing CWG1835's resolution as it stands is our best option. 
Doing so results in the most consistent behavior (e.g. 'use template when the 
object expression is dependent'), the most obvious fixes to achieve the 
intended interpretation (i.e. 'add `template` prior to the intended template 
name' [as opposed to surrounding the class member access expression in 
parentheses]). Given that we can now identify _almost_ all cases where 
`template` is missing with this patch and issue a warning, and that these cases 
wouldn't be resolved by any of the proposed compromises, I think our best 
option is to simply implement the resolution with enhanced recovery/  

https://github.com/llvm/llvm-project/pull/100425
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [libcxx] Reapply "[Clang] Implement resolution for CWG1835 (#92957, #98547)" (PR #100425)

2024-08-19 Thread Krystian Stasiowski via cfe-commits

sdkrystian wrote:

CWG reviewed [CWG2920](https://cplusplus.github.io/CWG/issues/2920.html) during 
the 08-16 teleconference:
> The resolution for [issue 
> 1835](https://cplusplus.github.io/CWG/issues/1835.html) in P1787 has 
> addressed real concerns. CWG recognizes that real-world code now no longer 
> compiles, although the fix for the affected source code is trivial. A limited 
> exception to support some of the existing code might be feasible. CWG 
> solicits a paper with specification and analysis.

[The meeting 
minutes](https://wiki.edg.com/bin/view/Wg21telecons2024/Teleconference2024-08-16#CWG2920)
 portray a general feeling of apathy from CWG for code broken by the 
resolution. With the enhanced detection and recovery from missing `template` 
keywords implemented in this PR (see [my 
comment](https://github.com/llvm/llvm-project/pull/100425#issuecomment-2258973782)
 for examples; all cases reported by users are addressed), I feel that we can 
go ahead with relanding this patch. WDYT @AaronBallman, @cor3ntin, and 
@mizvekov?

https://github.com/llvm/llvm-project/pull/100425
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [Clang][Sema] Use the correct lookup context when building overloaded 'operator->' in the current instantiation (PR #104458)

2024-08-15 Thread Krystian Stasiowski via cfe-commits

https://github.com/sdkrystian updated 
https://github.com/llvm/llvm-project/pull/104458

>From 9f4fb3fb8df6d0981723ce9b8da809d9f2284348 Mon Sep 17 00:00:00 2001
From: Krystian Stasiowski 
Date: Thu, 15 Aug 2024 11:27:34 -0400
Subject: [PATCH 1/2] [Clang][Sema] Use the correct lookup context when
 building overloaded 'operator->' in the current instantiation

---
 clang/include/clang/Sema/Sema.h   |  3 +--
 clang/lib/Sema/SemaExprCXX.cpp| 25 ---
 clang/lib/Sema/SemaOverload.cpp   | 14 +++
 clang/lib/Sema/TreeTransform.h|  4 +--
 .../temp.res/temp.dep/temp.dep.type/p4.cpp| 24 ++
 5 files changed, 35 insertions(+), 35 deletions(-)

diff --git a/clang/include/clang/Sema/Sema.h b/clang/include/clang/Sema/Sema.h
index 25cb6c8fbf6104..b9c5c5e4b92ed9 100644
--- a/clang/include/clang/Sema/Sema.h
+++ b/clang/include/clang/Sema/Sema.h
@@ -10616,8 +10616,7 @@ class Sema final : public SemaBase {
   /// BuildOverloadedArrowExpr - Build a call to an overloaded @c operator->
   ///  (if one exists), where @c Base is an expression of class type and
   /// @c Member is the name of the member we're trying to find.
-  ExprResult BuildOverloadedArrowExpr(Scope *S, Expr *Base,
-  SourceLocation OpLoc,
+  ExprResult BuildOverloadedArrowExpr(Expr *Base, SourceLocation OpLoc,
   bool *NoArrowOperatorFound = nullptr);
 
   ExprResult BuildCXXMemberCallExpr(Expr *Exp, NamedDecl *FoundDecl,
diff --git a/clang/lib/Sema/SemaExprCXX.cpp b/clang/lib/Sema/SemaExprCXX.cpp
index 124435330ca104..d33d635ff76c5b 100644
--- a/clang/lib/Sema/SemaExprCXX.cpp
+++ b/clang/lib/Sema/SemaExprCXX.cpp
@@ -7876,18 +7876,6 @@ ExprResult Sema::ActOnStartCXXMemberReference(Scope *S, 
Expr *Base,
 
   QualType BaseType = Base->getType();
   MayBePseudoDestructor = false;
-  if (BaseType->isDependentType()) {
-// If we have a pointer to a dependent type and are using the -> operator,
-// the object type is the type that the pointer points to. We might still
-// have enough information about that type to do something useful.
-if (OpKind == tok::arrow)
-  if (const PointerType *Ptr = BaseType->getAs())
-BaseType = Ptr->getPointeeType();
-
-ObjectType = ParsedType::make(BaseType);
-MayBePseudoDestructor = true;
-return Base;
-  }
 
   // C++ [over.match.oper]p8:
   //   [...] When operator->returns, the operator-> is applied  to the value
@@ -7902,7 +7890,7 @@ ExprResult Sema::ActOnStartCXXMemberReference(Scope *S, 
Expr *Base,
 SmallVector OperatorArrows;
 CTypes.insert(Context.getCanonicalType(BaseType));
 
-while (BaseType->isRecordType()) {
+while (BaseType->getAsRecordDecl()) {
   if (OperatorArrows.size() >= getLangOpts().ArrowDepth) {
 Diag(OpLoc, diag::err_operator_arrow_depth_exceeded)
   << StartingType << getLangOpts().ArrowDepth << 
Base->getSourceRange();
@@ -7913,7 +7901,7 @@ ExprResult Sema::ActOnStartCXXMemberReference(Scope *S, 
Expr *Base,
   }
 
   Result = BuildOverloadedArrowExpr(
-  S, Base, OpLoc,
+  Base, OpLoc,
   // When in a template specialization and on the first loop iteration,
   // potentially give the default diagnostic (with the fixit in a
   // separate note) instead of having the error reported back to here
@@ -7939,7 +7927,14 @@ ExprResult Sema::ActOnStartCXXMemberReference(Scope *S, 
Expr *Base,
   }
 }
 return ExprError();
+  } else if (Result.isUnset()) {
+// BuildOverloadedArrowExpr returns an empty expression to indicate
+// that we need to build a dependent overloaded arrow expression.
+assert(BaseType->isDependentType());
+BaseType = Context.DependentTy;
+break;
   }
+
   Base = Result.get();
   if (CXXOperatorCallExpr *OpCall = dyn_cast(Base))
 OperatorArrows.push_back(OpCall->getDirectCallee());
@@ -7977,7 +7972,7 @@ ExprResult Sema::ActOnStartCXXMemberReference(Scope *S, 
Expr *Base,
   // it's legal for the type to be incomplete if this is a pseudo-destructor
   // call.  We'll do more incomplete-type checks later in the lookup process,
   // so just skip this check for ObjC types.
-  if (!BaseType->isRecordType()) {
+  if (!BaseType->getAsRecordDecl()) {
 ObjectType = ParsedType::make(BaseType);
 MayBePseudoDestructor = true;
 return Base;
diff --git a/clang/lib/Sema/SemaOverload.cpp b/clang/lib/Sema/SemaOverload.cpp
index 52f640eb96b73b..4340181f316560 100644
--- a/clang/lib/Sema/SemaOverload.cpp
+++ b/clang/lib/Sema/SemaOverload.cpp
@@ -15864,10 +15864,9 @@ Sema::BuildCallToObjectOfClassType(Scope *S, Expr *Obj,
   return CheckForImmediateInvocation(MaybeBindToTemporary(TheCall), Method);
 }
 
-ExprResult
-Sema::BuildOverloadedArrowExpr(Scope *S, Expr *Base, SourceLocation OpLoc,
-   bool *NoAr

[clang] [Clang][Sema] Use the correct lookup context when building overloaded 'operator->' in the current instantiation (PR #104458)

2024-08-15 Thread Krystian Stasiowski via cfe-commits

https://github.com/sdkrystian created 
https://github.com/llvm/llvm-project/pull/104458

Fixes #104268. Still need tests.

>From 9f4fb3fb8df6d0981723ce9b8da809d9f2284348 Mon Sep 17 00:00:00 2001
From: Krystian Stasiowski 
Date: Thu, 15 Aug 2024 11:27:34 -0400
Subject: [PATCH] [Clang][Sema] Use the correct lookup context when building
 overloaded 'operator->' in the current instantiation

---
 clang/include/clang/Sema/Sema.h   |  3 +--
 clang/lib/Sema/SemaExprCXX.cpp| 25 ---
 clang/lib/Sema/SemaOverload.cpp   | 14 +++
 clang/lib/Sema/TreeTransform.h|  4 +--
 .../temp.res/temp.dep/temp.dep.type/p4.cpp| 24 ++
 5 files changed, 35 insertions(+), 35 deletions(-)

diff --git a/clang/include/clang/Sema/Sema.h b/clang/include/clang/Sema/Sema.h
index 25cb6c8fbf6104..b9c5c5e4b92ed9 100644
--- a/clang/include/clang/Sema/Sema.h
+++ b/clang/include/clang/Sema/Sema.h
@@ -10616,8 +10616,7 @@ class Sema final : public SemaBase {
   /// BuildOverloadedArrowExpr - Build a call to an overloaded @c operator->
   ///  (if one exists), where @c Base is an expression of class type and
   /// @c Member is the name of the member we're trying to find.
-  ExprResult BuildOverloadedArrowExpr(Scope *S, Expr *Base,
-  SourceLocation OpLoc,
+  ExprResult BuildOverloadedArrowExpr(Expr *Base, SourceLocation OpLoc,
   bool *NoArrowOperatorFound = nullptr);
 
   ExprResult BuildCXXMemberCallExpr(Expr *Exp, NamedDecl *FoundDecl,
diff --git a/clang/lib/Sema/SemaExprCXX.cpp b/clang/lib/Sema/SemaExprCXX.cpp
index 124435330ca104..d33d635ff76c5b 100644
--- a/clang/lib/Sema/SemaExprCXX.cpp
+++ b/clang/lib/Sema/SemaExprCXX.cpp
@@ -7876,18 +7876,6 @@ ExprResult Sema::ActOnStartCXXMemberReference(Scope *S, 
Expr *Base,
 
   QualType BaseType = Base->getType();
   MayBePseudoDestructor = false;
-  if (BaseType->isDependentType()) {
-// If we have a pointer to a dependent type and are using the -> operator,
-// the object type is the type that the pointer points to. We might still
-// have enough information about that type to do something useful.
-if (OpKind == tok::arrow)
-  if (const PointerType *Ptr = BaseType->getAs())
-BaseType = Ptr->getPointeeType();
-
-ObjectType = ParsedType::make(BaseType);
-MayBePseudoDestructor = true;
-return Base;
-  }
 
   // C++ [over.match.oper]p8:
   //   [...] When operator->returns, the operator-> is applied  to the value
@@ -7902,7 +7890,7 @@ ExprResult Sema::ActOnStartCXXMemberReference(Scope *S, 
Expr *Base,
 SmallVector OperatorArrows;
 CTypes.insert(Context.getCanonicalType(BaseType));
 
-while (BaseType->isRecordType()) {
+while (BaseType->getAsRecordDecl()) {
   if (OperatorArrows.size() >= getLangOpts().ArrowDepth) {
 Diag(OpLoc, diag::err_operator_arrow_depth_exceeded)
   << StartingType << getLangOpts().ArrowDepth << 
Base->getSourceRange();
@@ -7913,7 +7901,7 @@ ExprResult Sema::ActOnStartCXXMemberReference(Scope *S, 
Expr *Base,
   }
 
   Result = BuildOverloadedArrowExpr(
-  S, Base, OpLoc,
+  Base, OpLoc,
   // When in a template specialization and on the first loop iteration,
   // potentially give the default diagnostic (with the fixit in a
   // separate note) instead of having the error reported back to here
@@ -7939,7 +7927,14 @@ ExprResult Sema::ActOnStartCXXMemberReference(Scope *S, 
Expr *Base,
   }
 }
 return ExprError();
+  } else if (Result.isUnset()) {
+// BuildOverloadedArrowExpr returns an empty expression to indicate
+// that we need to build a dependent overloaded arrow expression.
+assert(BaseType->isDependentType());
+BaseType = Context.DependentTy;
+break;
   }
+
   Base = Result.get();
   if (CXXOperatorCallExpr *OpCall = dyn_cast(Base))
 OperatorArrows.push_back(OpCall->getDirectCallee());
@@ -7977,7 +7972,7 @@ ExprResult Sema::ActOnStartCXXMemberReference(Scope *S, 
Expr *Base,
   // it's legal for the type to be incomplete if this is a pseudo-destructor
   // call.  We'll do more incomplete-type checks later in the lookup process,
   // so just skip this check for ObjC types.
-  if (!BaseType->isRecordType()) {
+  if (!BaseType->getAsRecordDecl()) {
 ObjectType = ParsedType::make(BaseType);
 MayBePseudoDestructor = true;
 return Base;
diff --git a/clang/lib/Sema/SemaOverload.cpp b/clang/lib/Sema/SemaOverload.cpp
index 52f640eb96b73b..4340181f316560 100644
--- a/clang/lib/Sema/SemaOverload.cpp
+++ b/clang/lib/Sema/SemaOverload.cpp
@@ -15864,10 +15864,9 @@ Sema::BuildCallToObjectOfClassType(Scope *S, Expr *Obj,
   return CheckForImmediateInvocation(MaybeBindToTemporary(TheCall), Method);
 }
 
-ExprResult
-Sema::BuildOverloadedArrowExpr(Scope *S, Expr *Base, SourceLocation OpLoc,
-   

[clang] [Clang][Sema] Rebuild template parameters for out-of-line template definitions and partial specializations (PR #104030)

2024-08-14 Thread Krystian Stasiowski via cfe-commits

https://github.com/sdkrystian created 
https://github.com/llvm/llvm-project/pull/104030

We need to rebuild the template parameters of out-of-line 
definitions/specializations of member templates in the context of the current 
instantiation for the purposes of declaration matching. We already do this for 
function templates and class templates, but not variable templates, partial 
specializations of variable template, and partial specializations of class 
templates. This patch fixes the latter cases.

>From 0b99f8d40fa3e74021e496dfa5000fa51d972704 Mon Sep 17 00:00:00 2001
From: Krystian Stasiowski 
Date: Wed, 14 Aug 2024 09:00:30 -0400
Subject: [PATCH] [Clang][Sema] Rebuild template parameters for out-of-line
 template definitions and partial specializations

---
 clang/lib/Sema/SemaDecl.cpp   |   6 +
 clang/lib/Sema/SemaTemplate.cpp   |  20 ++--
 .../test/CXX/temp/temp.decls/temp.mem/p1.cpp  | 112 +-
 3 files changed, 129 insertions(+), 9 deletions(-)

diff --git a/clang/lib/Sema/SemaDecl.cpp b/clang/lib/Sema/SemaDecl.cpp
index 641b180527da55..4490aed2645951 100644
--- a/clang/lib/Sema/SemaDecl.cpp
+++ b/clang/lib/Sema/SemaDecl.cpp
@@ -7490,6 +7490,12 @@ NamedDecl *Sema::ActOnVariableDeclarator(
 /*never a friend*/ false, IsMemberSpecialization, Invalid);
 
 if (TemplateParams) {
+  if (DC->isDependentContext()) {
+ContextRAII SavedContext(*this, DC);
+if (RebuildTemplateParamsInCurrentInstantiation(TemplateParams))
+  Invalid = true;
+  }
+
   if (!TemplateParams->size() &&
   D.getName().getKind() != UnqualifiedIdKind::IK_TemplateId) {
 // There is an extraneous 'template<>' for this variable. Complain
diff --git a/clang/lib/Sema/SemaTemplate.cpp b/clang/lib/Sema/SemaTemplate.cpp
index 29e7978ba5b1f8..78aea38cd35216 100644
--- a/clang/lib/Sema/SemaTemplate.cpp
+++ b/clang/lib/Sema/SemaTemplate.cpp
@@ -8086,13 +8086,14 @@ DeclResult Sema::ActOnClassTemplateSpecialization(
 return true;
   }
 
+  DeclContext *DC = ClassTemplate->getDeclContext();
+
   bool isMemberSpecialization = false;
   bool isPartialSpecialization = false;
 
   if (SS.isSet()) {
 if (TUK != TagUseKind::Reference && TUK != TagUseKind::Friend &&
-diagnoseQualifiedDeclaration(SS, ClassTemplate->getDeclContext(),
- ClassTemplate->getDeclName(),
+diagnoseQualifiedDeclaration(SS, DC, ClassTemplate->getDeclName(),
  TemplateNameLoc, &TemplateId,
  /*IsMemberSpecialization=*/false))
   return true;
@@ -8114,6 +8115,12 @@ DeclResult Sema::ActOnClassTemplateSpecialization(
   if (TemplateParams && CheckTemplateDeclScope(S, TemplateParams))
 return true;
 
+  if (TemplateParams && DC->isDependentContext()) {
+ContextRAII SavedContext(*this, DC);
+if (RebuildTemplateParamsInCurrentInstantiation(TemplateParams))
+  return true;
+  }
+
   if (TemplateParams && TemplateParams->size() > 0) {
 isPartialSpecialization = true;
 
@@ -8279,9 +8286,8 @@ DeclResult Sema::ActOnClassTemplateSpecialization(
   = cast_or_null(PrevDecl);
 ClassTemplatePartialSpecializationDecl *Partial =
 ClassTemplatePartialSpecializationDecl::Create(
-Context, Kind, ClassTemplate->getDeclContext(), KWLoc,
-TemplateNameLoc, TemplateParams, ClassTemplate, CanonicalConverted,
-CanonType, PrevPartial);
+Context, Kind, DC, KWLoc, TemplateNameLoc, TemplateParams,
+ClassTemplate, CanonicalConverted, CanonType, PrevPartial);
 Partial->setTemplateArgsAsWritten(TemplateArgs);
 SetNestedNameSpecifier(*this, Partial, SS);
 if (TemplateParameterLists.size() > 1 && SS.isSet()) {
@@ -8303,8 +8309,8 @@ DeclResult Sema::ActOnClassTemplateSpecialization(
 // Create a new class template specialization declaration node for
 // this explicit specialization or friend declaration.
 Specialization = ClassTemplateSpecializationDecl::Create(
-Context, Kind, ClassTemplate->getDeclContext(), KWLoc, TemplateNameLoc,
-ClassTemplate, CanonicalConverted, PrevDecl);
+Context, Kind, DC, KWLoc, TemplateNameLoc, ClassTemplate,
+CanonicalConverted, PrevDecl);
 Specialization->setTemplateArgsAsWritten(TemplateArgs);
 SetNestedNameSpecifier(*this, Specialization, SS);
 if (TemplateParameterLists.size() > 0) {
diff --git a/clang/test/CXX/temp/temp.decls/temp.mem/p1.cpp 
b/clang/test/CXX/temp/temp.decls/temp.mem/p1.cpp
index b48e145e1468db..64b1274419e35d 100644
--- a/clang/test/CXX/temp/temp.decls/temp.mem/p1.cpp
+++ b/clang/test/CXX/temp/temp.decls/temp.mem/p1.cpp
@@ -1,5 +1,4 @@
-// RUN: %clang_cc1 -fsyntax-only -verify %s
-// expected-no-diagnostics
+// RUN: %clang_cc1 -fsyntax-only -std=c++20 -verify %s
 
 template  struct A {
   static T cond;
@@ -35,3 +34,112 @@ namespace PR6376 {
 
   Z z0;
 }
+
+namespace 

[clang] [Clang][Sema] fix noexecpt mismatch of friend declaration (PR #102267)

2024-08-12 Thread Krystian Stasiowski via cfe-commits

sdkrystian wrote:

I don't think this is the right approach. What I think we _should_ be doing is 
to compare the operands of the _noexcept-specifier_ the same way we compare 
constraints (i.e. substitute so all references to template parameters have the 
correct depth and _then_ check whether the substituted expressions are 
equivalent). WDYT @mizvekov? 

https://github.com/llvm/llvm-project/pull/102267
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [Clang][AST][NFC] Store template parameter position for TemplateTypeParmType in TypeBit (PR #102481)

2024-08-08 Thread Krystian Stasiowski via cfe-commits

https://github.com/sdkrystian closed 
https://github.com/llvm/llvm-project/pull/102481
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [Clang][AST][NFC] Store template parameter position for TemplateTypeParmType in TypeBit (PR #102481)

2024-08-08 Thread Krystian Stasiowski via cfe-commits

sdkrystian wrote:

@mizvekov 
[llvm-compile-time-tracker](https://llvm-compile-time-tracker.com/compare.php?from=3e3ea54aada44212b4e273f2fc879a419dea053f&to=77585f02c39d182e6aef60856ec6816d28ce0888&stat=instructions:u)
 reports a 0.07% improvement in userspace instruction retired. Not bad :).

https://github.com/llvm/llvm-project/pull/102481
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [Clang][AST][NFC] Store template parameter position for TemplateTypeParmType in TypeBit (PR #102481)

2024-08-08 Thread Krystian Stasiowski via cfe-commits


@@ -6131,52 +6149,30 @@ class BTFTagAttributedType : public Type, public 
llvm::FoldingSetNode {
 class TemplateTypeParmType : public Type, public llvm::FoldingSetNode {
   friend class ASTContext; // ASTContext creates these
 
-  // Helper data collector for canonical types.
-  struct CanonicalTTPTInfo {
-unsigned Depth : 15;
-unsigned ParameterPack : 1;
-unsigned Index : 16;
-  };
-
-  union {
-// Info for the canonical type.
-CanonicalTTPTInfo CanTTPTInfo;
-
-// Info for the non-canonical type.
-TemplateTypeParmDecl *TTPDecl;
-  };
+  // The associated TemplateTypeParmDecl for the non-canonical type.
+  TemplateTypeParmDecl *TTPDecl;

sdkrystian wrote:

There are a few other cases where we can tail allocate data for types... I 
think I'll submit a patch that tail allocates members for a few other `Type` 
derived classes.

https://github.com/llvm/llvm-project/pull/102481
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [Clang][AST][NFC] Store template parameter position for TemplateTypeParmType in TypeBit (PR #102481)

2024-08-08 Thread Krystian Stasiowski via cfe-commits

sdkrystian wrote:

> LGTM
> 
> Are there any performance numbers worth mentioning?

I haven't checked... I'll check with llvm-compile-time-tracker.

https://github.com/llvm/llvm-project/pull/102481
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [Clang][AST][NFC] Store template parameter position for TemplateTypeParmType in TypeBit (PR #102481)

2024-08-08 Thread Krystian Stasiowski via cfe-commits

https://github.com/sdkrystian created 
https://github.com/llvm/llvm-project/pull/102481

`TemplateTypeParmType` currently stores the depth, index, and whether a 
template type parameter is a pack in a union of `CanonicalTTPTInfo` and 
`TemplateTypeParmDecl*`, and only the canonical type stores the position 
information. These bits can be stored for all `TemplateTypeParmTypes` in 
`TypeBits` to avoid unnecessary indirection when accessing the position 
information.

>From 77585f02c39d182e6aef60856ec6816d28ce0888 Mon Sep 17 00:00:00 2001
From: Krystian Stasiowski 
Date: Thu, 8 Aug 2024 10:36:52 -0400
Subject: [PATCH] [Clang][AST][NFC] Store template parameter position for
 TemplateTypeParmType in TypeBits

---
 clang/include/clang/AST/Type.h | 72 --
 clang/lib/AST/ASTContext.cpp   |  6 +--
 2 files changed, 37 insertions(+), 41 deletions(-)

diff --git a/clang/include/clang/AST/Type.h b/clang/include/clang/AST/Type.h
index 0c886526c61ce..03832cf56dd06 100644
--- a/clang/include/clang/AST/Type.h
+++ b/clang/include/clang/AST/Type.h
@@ -2134,6 +2134,23 @@ class alignas(TypeAlignment) Type : public 
ExtQualsTypeCommonBase {
 unsigned hasTypeDifferentFromDecl : 1;
   };
 
+  class TemplateTypeParmTypeBitfields {
+friend class TemplateTypeParmType;
+
+LLVM_PREFERRED_TYPE(TypeBitfields)
+unsigned : NumTypeBits;
+
+/// The depth of the template parameter.
+unsigned Depth : 15;
+
+/// Whether this is a template parameter pack.
+LLVM_PREFERRED_TYPE(bool)
+unsigned ParameterPack : 1;
+
+/// The index of the template parameter.
+unsigned Index : 16;
+  };
+
   class SubstTemplateTypeParmTypeBitfields {
 friend class SubstTemplateTypeParmType;
 
@@ -2257,6 +2274,7 @@ class alignas(TypeAlignment) Type : public 
ExtQualsTypeCommonBase {
 TypeWithKeywordBitfields TypeWithKeywordBits;
 ElaboratedTypeBitfields ElaboratedTypeBits;
 VectorTypeBitfields VectorTypeBits;
+TemplateTypeParmTypeBitfields TemplateTypeParmTypeBits;
 SubstTemplateTypeParmTypeBitfields SubstTemplateTypeParmTypeBits;
 SubstTemplateTypeParmPackTypeBitfields SubstTemplateTypeParmPackTypeBits;
 TemplateSpecializationTypeBitfields TemplateSpecializationTypeBits;
@@ -6131,52 +6149,30 @@ class BTFTagAttributedType : public Type, public 
llvm::FoldingSetNode {
 class TemplateTypeParmType : public Type, public llvm::FoldingSetNode {
   friend class ASTContext; // ASTContext creates these
 
-  // Helper data collector for canonical types.
-  struct CanonicalTTPTInfo {
-unsigned Depth : 15;
-unsigned ParameterPack : 1;
-unsigned Index : 16;
-  };
-
-  union {
-// Info for the canonical type.
-CanonicalTTPTInfo CanTTPTInfo;
-
-// Info for the non-canonical type.
-TemplateTypeParmDecl *TTPDecl;
-  };
+  // The associated TemplateTypeParmDecl for the non-canonical type.
+  TemplateTypeParmDecl *TTPDecl;
 
-  /// Build a non-canonical type.
-  TemplateTypeParmType(TemplateTypeParmDecl *TTPDecl, QualType Canon)
+  TemplateTypeParmType(unsigned D, unsigned I, bool PP,
+   TemplateTypeParmDecl *TTPDecl, QualType Canon)
   : Type(TemplateTypeParm, Canon,
  TypeDependence::DependentInstantiation |
- (Canon->getDependence() & TypeDependence::UnexpandedPack)),
-TTPDecl(TTPDecl) {}
-
-  /// Build the canonical type.
-  TemplateTypeParmType(unsigned D, unsigned I, bool PP)
-  : Type(TemplateTypeParm, QualType(this, 0),
- TypeDependence::DependentInstantiation |
- (PP ? TypeDependence::UnexpandedPack : TypeDependence::None)) 
{
-CanTTPTInfo.Depth = D;
-CanTTPTInfo.Index = I;
-CanTTPTInfo.ParameterPack = PP;
-  }
-
-  const CanonicalTTPTInfo& getCanTTPTInfo() const {
-QualType Can = getCanonicalTypeInternal();
-return Can->castAs()->CanTTPTInfo;
+ (PP ? TypeDependence::UnexpandedPack : TypeDependence::None)),
+TTPDecl(TTPDecl) {
+assert(!TTPDecl == Canon.isNull());
+TemplateTypeParmTypeBits.Depth = D;
+TemplateTypeParmTypeBits.Index = I;
+TemplateTypeParmTypeBits.ParameterPack = PP;
   }
 
 public:
-  unsigned getDepth() const { return getCanTTPTInfo().Depth; }
-  unsigned getIndex() const { return getCanTTPTInfo().Index; }
-  bool isParameterPack() const { return getCanTTPTInfo().ParameterPack; }
-
-  TemplateTypeParmDecl *getDecl() const {
-return isCanonicalUnqualified() ? nullptr : TTPDecl;
+  unsigned getDepth() const { return TemplateTypeParmTypeBits.Depth; }
+  unsigned getIndex() const { return TemplateTypeParmTypeBits.Index; }
+  bool isParameterPack() const {
+return TemplateTypeParmTypeBits.ParameterPack;
   }
 
+  TemplateTypeParmDecl *getDecl() const { return TTPDecl; }
+
   IdentifierInfo *getIdentifier() const;
 
   bool isSugared() const { return false; }
diff --git a/clang/lib/AST/ASTContext.cpp b/clang/lib/AST/ASTContext.cpp
index 995d01734eea0..c55d28b506887 100644
---

[clang] [Clang][Sema] Make UnresolvedLookupExprs in class scope explicit specializations instantiation dependent (PR #100392)

2024-08-06 Thread Krystian Stasiowski via cfe-commits

https://github.com/sdkrystian closed 
https://github.com/llvm/llvm-project/pull/100392
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [Clang][Sema] Make UnresolvedLookupExprs in class scope explicit specializations instantiation dependent (PR #100392)

2024-08-06 Thread Krystian Stasiowski via cfe-commits

https://github.com/sdkrystian updated 
https://github.com/llvm/llvm-project/pull/100392

>From 2721a3142f4cf7e22eec27f8c209a2a4e8f98519 Mon Sep 17 00:00:00 2001
From: Krystian Stasiowski 
Date: Wed, 24 Jul 2024 10:15:47 -0400
Subject: [PATCH 1/3] [Clang][Sema] Make UnresolvedLookupExprs in class scope
 explicit specializations instantiation dependent

---
 clang/include/clang/AST/ExprCXX.h |  7 ---
 clang/lib/AST/ASTImporter.cpp |  5 +++--
 clang/lib/AST/ExprCXX.cpp | 19 +++
 clang/lib/Sema/SemaCoroutine.cpp  |  3 ++-
 clang/lib/Sema/SemaDecl.cpp   |  2 +-
 clang/lib/Sema/SemaDeclCXX.cpp|  2 +-
 clang/lib/Sema/SemaExpr.cpp   |  2 +-
 clang/lib/Sema/SemaExprMember.cpp |  3 ++-
 clang/lib/Sema/SemaOpenMP.cpp |  6 --
 clang/lib/Sema/SemaOverload.cpp   |  6 +++---
 clang/lib/Sema/SemaTemplate.cpp   |  3 ++-
 clang/lib/Sema/TreeTransform.h|  8 
 12 files changed, 38 insertions(+), 28 deletions(-)

diff --git a/clang/include/clang/AST/ExprCXX.h 
b/clang/include/clang/AST/ExprCXX.h
index f86f1818110e6..847a6ea408e98 100644
--- a/clang/include/clang/AST/ExprCXX.h
+++ b/clang/include/clang/AST/ExprCXX.h
@@ -3229,7 +3229,7 @@ class UnresolvedLookupExpr final
const DeclarationNameInfo &NameInfo, bool RequiresADL,
const TemplateArgumentListInfo *TemplateArgs,
UnresolvedSetIterator Begin, UnresolvedSetIterator End,
-   bool KnownDependent);
+   bool KnownDependent, bool KnownInstantiationDependent);
 
   UnresolvedLookupExpr(EmptyShell Empty, unsigned NumResults,
bool HasTemplateKWAndArgsInfo);
@@ -3248,7 +3248,7 @@ class UnresolvedLookupExpr final
  NestedNameSpecifierLoc QualifierLoc,
  const DeclarationNameInfo &NameInfo, bool RequiresADL,
  UnresolvedSetIterator Begin, UnresolvedSetIterator End,
- bool KnownDependent);
+ bool KnownDependent, bool KnownInstantiationDependent);
 
   // After canonicalization, there may be dependent template arguments in
   // CanonicalConverted But none of Args is dependent. When any of
@@ -3258,7 +3258,8 @@ class UnresolvedLookupExpr final
  NestedNameSpecifierLoc QualifierLoc, SourceLocation TemplateKWLoc,
  const DeclarationNameInfo &NameInfo, bool RequiresADL,
  const TemplateArgumentListInfo *Args, UnresolvedSetIterator Begin,
- UnresolvedSetIterator End, bool KnownDependent);
+ UnresolvedSetIterator End, bool KnownDependent,
+ bool KnownInstantiationDependent);
 
   static UnresolvedLookupExpr *CreateEmpty(const ASTContext &Context,
unsigned NumResults,
diff --git a/clang/lib/AST/ASTImporter.cpp b/clang/lib/AST/ASTImporter.cpp
index c835b7241ce09..83d8cd73f2cfa 100644
--- a/clang/lib/AST/ASTImporter.cpp
+++ b/clang/lib/AST/ASTImporter.cpp
@@ -8633,13 +8633,14 @@ 
ASTNodeImporter::VisitUnresolvedLookupExpr(UnresolvedLookupExpr *E) {
 return UnresolvedLookupExpr::Create(
 Importer.getToContext(), *ToNamingClassOrErr, *ToQualifierLocOrErr,
 *ToTemplateKeywordLocOrErr, ToNameInfo, E->requiresADL(), &ToTAInfo,
-ToDecls.begin(), ToDecls.end(), KnownDependent);
+ToDecls.begin(), ToDecls.end(), KnownDependent,
+E->isInstantiationDependent());
   }
 
   return UnresolvedLookupExpr::Create(
   Importer.getToContext(), *ToNamingClassOrErr, *ToQualifierLocOrErr,
   ToNameInfo, E->requiresADL(), ToDecls.begin(), ToDecls.end(),
-  /*KnownDependent=*/E->isTypeDependent());
+  /*KnownDependent=*/E->isTypeDependent(), E->isInstantiationDependent());
 }
 
 ExpectedStmt
diff --git a/clang/lib/AST/ExprCXX.cpp b/clang/lib/AST/ExprCXX.cpp
index 6212989e21737..83ce404add5f5 100644
--- a/clang/lib/AST/ExprCXX.cpp
+++ b/clang/lib/AST/ExprCXX.cpp
@@ -402,10 +402,11 @@ UnresolvedLookupExpr::UnresolvedLookupExpr(
 NestedNameSpecifierLoc QualifierLoc, SourceLocation TemplateKWLoc,
 const DeclarationNameInfo &NameInfo, bool RequiresADL,
 const TemplateArgumentListInfo *TemplateArgs, UnresolvedSetIterator Begin,
-UnresolvedSetIterator End, bool KnownDependent)
+UnresolvedSetIterator End, bool KnownDependent,
+bool KnownInstantiationDependent)
 : OverloadExpr(UnresolvedLookupExprClass, Context, QualifierLoc,
TemplateKWLoc, NameInfo, TemplateArgs, Begin, End,
-   KnownDependent, false, false),
+   KnownDependent, KnownInstantiationDependent, false),
   NamingClass(NamingClass) {
   UnresolvedLookupExprBits.RequiresADL = RequiresADL;
 }
@@ -420,7 +421,7 @@ UnresolvedLookupExpr *UnresolvedLookupExpr::Create(
 const ASTContext &Context, CXXRecordDecl *NamingClass,
 NestedNameSpecifierLoc QualifierLoc, const DeclarationNameInfo &NameInfo,
 bool RequiresADL, UnresolvedSetIterator Begin, UnresolvedSetIterator End,
-bool KnownDepende

[clang] [Clang][Sema] Ensure that the selected candidate for a member function explicit specialization is more constrained than all others (PR #101721)

2024-08-06 Thread Krystian Stasiowski via cfe-commits

https://github.com/sdkrystian closed 
https://github.com/llvm/llvm-project/pull/101721
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [Clang][Sema] Ensure that the selected candidate for a member function explicit specialization is more constrained than all others (PR #101721)

2024-08-06 Thread Krystian Stasiowski via cfe-commits

https://github.com/sdkrystian updated 
https://github.com/llvm/llvm-project/pull/101721

>From dd1c7b5fe3e1c4bca73cc5b4162ae73c3d7783fb Mon Sep 17 00:00:00 2001
From: Krystian Stasiowski 
Date: Fri, 2 Aug 2024 11:32:49 -0400
Subject: [PATCH 1/5] [Clang][Sema] Ensure that the selected candidate for a
 member function explicit specialization is more constrained than all others

---
 clang/lib/Sema/SemaTemplate.cpp | 80 +++--
 1 file changed, 56 insertions(+), 24 deletions(-)

diff --git a/clang/lib/Sema/SemaTemplate.cpp b/clang/lib/Sema/SemaTemplate.cpp
index 1346a4a3f0012..c96925ba73ae2 100644
--- a/clang/lib/Sema/SemaTemplate.cpp
+++ b/clang/lib/Sema/SemaTemplate.cpp
@@ -9062,51 +9062,83 @@ Sema::CheckMemberSpecialization(NamedDecl *Member, 
LookupResult &Previous) {
   if (Previous.empty()) {
 // Nowhere to look anyway.
   } else if (FunctionDecl *Function = dyn_cast(Member)) {
-SmallVector Candidates;
-bool Ambiguous = false;
-for (LookupResult::iterator I = Previous.begin(), E = Previous.end();
-   I != E; ++I) {
-  CXXMethodDecl *Method =
-  dyn_cast((*I)->getUnderlyingDecl());
-  if (!Method)
+LookupResult::Filter Filter = Previous.makeFilter();
+while (Filter.hasNext()) {
+  auto *Method =
+  dyn_cast(Filter.next()->getUnderlyingDecl());
+  // Discard any candidates that aren't member functions.
+  if (!Method) {
+Filter.erase();
 continue;
+  }
+
   QualType Adjusted = Function->getType();
   if (!hasExplicitCallingConv(Adjusted))
 Adjusted = adjustCCAndNoReturn(Adjusted, Method->getType());
+  // Discard any candidates with the wrong type.
   // This doesn't handle deduced return types, but both function
   // declarations should be undeduced at this point.
-  if (!Context.hasSameType(Adjusted, Method->getType()))
+  if (!Context.hasSameType(Adjusted, Method->getType())) {
+Filter.erase();
 continue;
+  }
+
+  // Discard any candidates with unsatisfied constraints.
   if (ConstraintSatisfaction Satisfaction;
   Method->getTrailingRequiresClause() &&
   (CheckFunctionConstraints(Method, Satisfaction,
 /*UsageLoc=*/Member->getLocation(),
 /*ForOverloadResolution=*/true) ||
-   !Satisfaction.IsSatisfied))
-continue;
-  Candidates.push_back(Method);
-  FunctionDecl *MoreConstrained =
-  Instantiation ? getMoreConstrainedFunction(
-  Method, cast(Instantiation))
-: Method;
-  if (!MoreConstrained) {
-Ambiguous = true;
+   !Satisfaction.IsSatisfied)) {
+Filter.erase();
 continue;
   }
-  if (MoreConstrained == Method) {
-Ambiguous = false;
-FoundInstantiation = *I;
-Instantiation = Method;
-InstantiatedFrom = Method->getInstantiatedFromMemberFunction();
-MSInfo = Method->getMemberSpecializationInfo();
+}
+Filter.done();
+
+// If we have no candidates left after filtering, we are done.
+if (Previous.empty())
+  return false;
+
+// Find the function that is more constrained than every other function it
+// has been compared to.
+UnresolvedSetIterator Best = Previous.begin();
+CXXMethodDecl *BestMethod = nullptr;
+for (UnresolvedSetIterator I = Previous.begin(), E = Previous.end(); I != 
E;
+ ++I) {
+  auto *Method = cast(I->getUnderlyingDecl());
+  if (I == Best ||
+  getMoreConstrainedFunction(Method, BestMethod) == Method) {
+Best = I;
+BestMethod = Method;
+  }
+}
+
+FoundInstantiation = *Best;
+Instantiation = BestMethod;
+InstantiatedFrom = BestMethod->getInstantiatedFromMemberFunction();
+MSInfo = BestMethod->getMemberSpecializationInfo();
+
+// Make sure the best candidate is more specialized than all of the others.
+bool Ambiguous = false;
+for (UnresolvedSetIterator I = Previous.begin(), E = Previous.end(); I != 
E;
+ ++I) {
+  auto *Method = cast(I->getUnderlyingDecl());
+  if (I != Best &&
+  getMoreConstrainedFunction(Method, BestMethod) != BestMethod) {
+Ambiguous = true;
+break;
   }
 }
+
 if (Ambiguous) {
   Diag(Member->getLocation(), diag::err_function_member_spec_ambiguous)
   << Member << (InstantiatedFrom ? InstantiatedFrom : Instantiation);
-  for (FunctionDecl *Candidate : Candidates)
+  for (NamedDecl *Candidate : Previous) {
+Candidate = Candidate->getUnderlyingDecl();
 Diag(Candidate->getLocation(), diag::note_function_member_spec_matched)
 << Candidate;
+  }
   return true;
 }
   } else if (isa(Member)) {

>From 8d9a4f0fc1da8b376a4c1e5cbf5e868ee20c790a Mon Sep 17 00:00:00 2001
From: Krystian Stasiowski 
Date: Fri, 2 Aug 2024 12:

[clang] [Clang][Sema] Ensure that the selected candidate for a member function explicit specialization is more constrained than all others (PR #101721)

2024-08-06 Thread Krystian Stasiowski via cfe-commits

https://github.com/sdkrystian updated 
https://github.com/llvm/llvm-project/pull/101721

>From 046bf3e993cd8905869cb244ddb7df019b44ae78 Mon Sep 17 00:00:00 2001
From: Krystian Stasiowski 
Date: Fri, 2 Aug 2024 11:32:49 -0400
Subject: [PATCH 1/5] [Clang][Sema] Ensure that the selected candidate for a
 member function explicit specialization is more constrained than all others

---
 clang/lib/Sema/SemaTemplate.cpp | 80 +++--
 1 file changed, 56 insertions(+), 24 deletions(-)

diff --git a/clang/lib/Sema/SemaTemplate.cpp b/clang/lib/Sema/SemaTemplate.cpp
index 87b1f98bbe5ac..b1c9ec21b152e 100644
--- a/clang/lib/Sema/SemaTemplate.cpp
+++ b/clang/lib/Sema/SemaTemplate.cpp
@@ -9062,51 +9062,83 @@ Sema::CheckMemberSpecialization(NamedDecl *Member, 
LookupResult &Previous) {
   if (Previous.empty()) {
 // Nowhere to look anyway.
   } else if (FunctionDecl *Function = dyn_cast(Member)) {
-SmallVector Candidates;
-bool Ambiguous = false;
-for (LookupResult::iterator I = Previous.begin(), E = Previous.end();
-   I != E; ++I) {
-  CXXMethodDecl *Method =
-  dyn_cast((*I)->getUnderlyingDecl());
-  if (!Method)
+LookupResult::Filter Filter = Previous.makeFilter();
+while (Filter.hasNext()) {
+  auto *Method =
+  dyn_cast(Filter.next()->getUnderlyingDecl());
+  // Discard any candidates that aren't member functions.
+  if (!Method) {
+Filter.erase();
 continue;
+  }
+
   QualType Adjusted = Function->getType();
   if (!hasExplicitCallingConv(Adjusted))
 Adjusted = adjustCCAndNoReturn(Adjusted, Method->getType());
+  // Discard any candidates with the wrong type.
   // This doesn't handle deduced return types, but both function
   // declarations should be undeduced at this point.
-  if (!Context.hasSameType(Adjusted, Method->getType()))
+  if (!Context.hasSameType(Adjusted, Method->getType())) {
+Filter.erase();
 continue;
+  }
+
+  // Discard any candidates with unsatisfied constraints.
   if (ConstraintSatisfaction Satisfaction;
   Method->getTrailingRequiresClause() &&
   (CheckFunctionConstraints(Method, Satisfaction,
 /*UsageLoc=*/Member->getLocation(),
 /*ForOverloadResolution=*/true) ||
-   !Satisfaction.IsSatisfied))
-continue;
-  Candidates.push_back(Method);
-  FunctionDecl *MoreConstrained =
-  Instantiation ? getMoreConstrainedFunction(
-  Method, cast(Instantiation))
-: Method;
-  if (!MoreConstrained) {
-Ambiguous = true;
+   !Satisfaction.IsSatisfied)) {
+Filter.erase();
 continue;
   }
-  if (MoreConstrained == Method) {
-Ambiguous = false;
-FoundInstantiation = *I;
-Instantiation = Method;
-InstantiatedFrom = Method->getInstantiatedFromMemberFunction();
-MSInfo = Method->getMemberSpecializationInfo();
+}
+Filter.done();
+
+// If we have no candidates left after filtering, we are done.
+if (Previous.empty())
+  return false;
+
+// Find the function that is more constrained than every other function it
+// has been compared to.
+UnresolvedSetIterator Best = Previous.begin();
+CXXMethodDecl *BestMethod = nullptr;
+for (UnresolvedSetIterator I = Previous.begin(), E = Previous.end(); I != 
E;
+ ++I) {
+  auto *Method = cast(I->getUnderlyingDecl());
+  if (I == Best ||
+  getMoreConstrainedFunction(Method, BestMethod) == Method) {
+Best = I;
+BestMethod = Method;
+  }
+}
+
+FoundInstantiation = *Best;
+Instantiation = BestMethod;
+InstantiatedFrom = BestMethod->getInstantiatedFromMemberFunction();
+MSInfo = BestMethod->getMemberSpecializationInfo();
+
+// Make sure the best candidate is more specialized than all of the others.
+bool Ambiguous = false;
+for (UnresolvedSetIterator I = Previous.begin(), E = Previous.end(); I != 
E;
+ ++I) {
+  auto *Method = cast(I->getUnderlyingDecl());
+  if (I != Best &&
+  getMoreConstrainedFunction(Method, BestMethod) != BestMethod) {
+Ambiguous = true;
+break;
   }
 }
+
 if (Ambiguous) {
   Diag(Member->getLocation(), diag::err_function_member_spec_ambiguous)
   << Member << (InstantiatedFrom ? InstantiatedFrom : Instantiation);
-  for (FunctionDecl *Candidate : Candidates)
+  for (NamedDecl *Candidate : Previous) {
+Candidate = Candidate->getUnderlyingDecl();
 Diag(Candidate->getLocation(), diag::note_function_member_spec_matched)
 << Candidate;
+  }
   return true;
 }
   } else if (isa(Member)) {

>From ccbd6012a79745e6999ae22aed681dfb80ad4f14 Mon Sep 17 00:00:00 2001
From: Krystian Stasiowski 
Date: Fri, 2 Aug 2024 12:

[clang] [Clang][Sema] Make UnresolvedLookupExprs in class scope explicit specializations instantiation dependent (PR #100392)

2024-08-06 Thread Krystian Stasiowski via cfe-commits

https://github.com/sdkrystian updated 
https://github.com/llvm/llvm-project/pull/100392

>From 7d0e70feb5e657c1830901e3ed9a01c1d56c7526 Mon Sep 17 00:00:00 2001
From: Krystian Stasiowski 
Date: Wed, 24 Jul 2024 10:15:47 -0400
Subject: [PATCH 1/3] [Clang][Sema] Make UnresolvedLookupExprs in class scope
 explicit specializations instantiation dependent

---
 clang/include/clang/AST/ExprCXX.h |  7 ---
 clang/lib/AST/ASTImporter.cpp |  5 +++--
 clang/lib/AST/ExprCXX.cpp | 19 +++
 clang/lib/Sema/SemaCoroutine.cpp  |  3 ++-
 clang/lib/Sema/SemaDecl.cpp   |  2 +-
 clang/lib/Sema/SemaDeclCXX.cpp|  2 +-
 clang/lib/Sema/SemaExpr.cpp   |  2 +-
 clang/lib/Sema/SemaExprMember.cpp |  3 ++-
 clang/lib/Sema/SemaOpenMP.cpp |  6 --
 clang/lib/Sema/SemaOverload.cpp   |  6 +++---
 clang/lib/Sema/SemaTemplate.cpp   |  3 ++-
 clang/lib/Sema/TreeTransform.h|  8 
 12 files changed, 38 insertions(+), 28 deletions(-)

diff --git a/clang/include/clang/AST/ExprCXX.h 
b/clang/include/clang/AST/ExprCXX.h
index f86f1818110e6..847a6ea408e98 100644
--- a/clang/include/clang/AST/ExprCXX.h
+++ b/clang/include/clang/AST/ExprCXX.h
@@ -3229,7 +3229,7 @@ class UnresolvedLookupExpr final
const DeclarationNameInfo &NameInfo, bool RequiresADL,
const TemplateArgumentListInfo *TemplateArgs,
UnresolvedSetIterator Begin, UnresolvedSetIterator End,
-   bool KnownDependent);
+   bool KnownDependent, bool KnownInstantiationDependent);
 
   UnresolvedLookupExpr(EmptyShell Empty, unsigned NumResults,
bool HasTemplateKWAndArgsInfo);
@@ -3248,7 +3248,7 @@ class UnresolvedLookupExpr final
  NestedNameSpecifierLoc QualifierLoc,
  const DeclarationNameInfo &NameInfo, bool RequiresADL,
  UnresolvedSetIterator Begin, UnresolvedSetIterator End,
- bool KnownDependent);
+ bool KnownDependent, bool KnownInstantiationDependent);
 
   // After canonicalization, there may be dependent template arguments in
   // CanonicalConverted But none of Args is dependent. When any of
@@ -3258,7 +3258,8 @@ class UnresolvedLookupExpr final
  NestedNameSpecifierLoc QualifierLoc, SourceLocation TemplateKWLoc,
  const DeclarationNameInfo &NameInfo, bool RequiresADL,
  const TemplateArgumentListInfo *Args, UnresolvedSetIterator Begin,
- UnresolvedSetIterator End, bool KnownDependent);
+ UnresolvedSetIterator End, bool KnownDependent,
+ bool KnownInstantiationDependent);
 
   static UnresolvedLookupExpr *CreateEmpty(const ASTContext &Context,
unsigned NumResults,
diff --git a/clang/lib/AST/ASTImporter.cpp b/clang/lib/AST/ASTImporter.cpp
index 103235547f482..49cbd60cafd0e 100644
--- a/clang/lib/AST/ASTImporter.cpp
+++ b/clang/lib/AST/ASTImporter.cpp
@@ -8629,13 +8629,14 @@ 
ASTNodeImporter::VisitUnresolvedLookupExpr(UnresolvedLookupExpr *E) {
 return UnresolvedLookupExpr::Create(
 Importer.getToContext(), *ToNamingClassOrErr, *ToQualifierLocOrErr,
 *ToTemplateKeywordLocOrErr, ToNameInfo, E->requiresADL(), &ToTAInfo,
-ToDecls.begin(), ToDecls.end(), KnownDependent);
+ToDecls.begin(), ToDecls.end(), KnownDependent,
+E->isInstantiationDependent());
   }
 
   return UnresolvedLookupExpr::Create(
   Importer.getToContext(), *ToNamingClassOrErr, *ToQualifierLocOrErr,
   ToNameInfo, E->requiresADL(), ToDecls.begin(), ToDecls.end(),
-  /*KnownDependent=*/E->isTypeDependent());
+  /*KnownDependent=*/E->isTypeDependent(), E->isInstantiationDependent());
 }
 
 ExpectedStmt
diff --git a/clang/lib/AST/ExprCXX.cpp b/clang/lib/AST/ExprCXX.cpp
index 6212989e21737..83ce404add5f5 100644
--- a/clang/lib/AST/ExprCXX.cpp
+++ b/clang/lib/AST/ExprCXX.cpp
@@ -402,10 +402,11 @@ UnresolvedLookupExpr::UnresolvedLookupExpr(
 NestedNameSpecifierLoc QualifierLoc, SourceLocation TemplateKWLoc,
 const DeclarationNameInfo &NameInfo, bool RequiresADL,
 const TemplateArgumentListInfo *TemplateArgs, UnresolvedSetIterator Begin,
-UnresolvedSetIterator End, bool KnownDependent)
+UnresolvedSetIterator End, bool KnownDependent,
+bool KnownInstantiationDependent)
 : OverloadExpr(UnresolvedLookupExprClass, Context, QualifierLoc,
TemplateKWLoc, NameInfo, TemplateArgs, Begin, End,
-   KnownDependent, false, false),
+   KnownDependent, KnownInstantiationDependent, false),
   NamingClass(NamingClass) {
   UnresolvedLookupExprBits.RequiresADL = RequiresADL;
 }
@@ -420,7 +421,7 @@ UnresolvedLookupExpr *UnresolvedLookupExpr::Create(
 const ASTContext &Context, CXXRecordDecl *NamingClass,
 NestedNameSpecifierLoc QualifierLoc, const DeclarationNameInfo &NameInfo,
 bool RequiresADL, UnresolvedSetIterator Begin, UnresolvedSetIterator End,
-bool KnownDepende

[clang] [Clang][Sema] Make UnresolvedLookupExprs in class scope explicit specializations instantiation dependent (PR #100392)

2024-08-05 Thread Krystian Stasiowski via cfe-commits

https://github.com/sdkrystian updated 
https://github.com/llvm/llvm-project/pull/100392

>From 7d0e70feb5e657c1830901e3ed9a01c1d56c7526 Mon Sep 17 00:00:00 2001
From: Krystian Stasiowski 
Date: Wed, 24 Jul 2024 10:15:47 -0400
Subject: [PATCH] [Clang][Sema] Make UnresolvedLookupExprs in class scope
 explicit specializations instantiation dependent

---
 clang/include/clang/AST/ExprCXX.h |  7 ---
 clang/lib/AST/ASTImporter.cpp |  5 +++--
 clang/lib/AST/ExprCXX.cpp | 19 +++
 clang/lib/Sema/SemaCoroutine.cpp  |  3 ++-
 clang/lib/Sema/SemaDecl.cpp   |  2 +-
 clang/lib/Sema/SemaDeclCXX.cpp|  2 +-
 clang/lib/Sema/SemaExpr.cpp   |  2 +-
 clang/lib/Sema/SemaExprMember.cpp |  3 ++-
 clang/lib/Sema/SemaOpenMP.cpp |  6 --
 clang/lib/Sema/SemaOverload.cpp   |  6 +++---
 clang/lib/Sema/SemaTemplate.cpp   |  3 ++-
 clang/lib/Sema/TreeTransform.h|  8 
 12 files changed, 38 insertions(+), 28 deletions(-)

diff --git a/clang/include/clang/AST/ExprCXX.h 
b/clang/include/clang/AST/ExprCXX.h
index f86f1818110e6..847a6ea408e98 100644
--- a/clang/include/clang/AST/ExprCXX.h
+++ b/clang/include/clang/AST/ExprCXX.h
@@ -3229,7 +3229,7 @@ class UnresolvedLookupExpr final
const DeclarationNameInfo &NameInfo, bool RequiresADL,
const TemplateArgumentListInfo *TemplateArgs,
UnresolvedSetIterator Begin, UnresolvedSetIterator End,
-   bool KnownDependent);
+   bool KnownDependent, bool KnownInstantiationDependent);
 
   UnresolvedLookupExpr(EmptyShell Empty, unsigned NumResults,
bool HasTemplateKWAndArgsInfo);
@@ -3248,7 +3248,7 @@ class UnresolvedLookupExpr final
  NestedNameSpecifierLoc QualifierLoc,
  const DeclarationNameInfo &NameInfo, bool RequiresADL,
  UnresolvedSetIterator Begin, UnresolvedSetIterator End,
- bool KnownDependent);
+ bool KnownDependent, bool KnownInstantiationDependent);
 
   // After canonicalization, there may be dependent template arguments in
   // CanonicalConverted But none of Args is dependent. When any of
@@ -3258,7 +3258,8 @@ class UnresolvedLookupExpr final
  NestedNameSpecifierLoc QualifierLoc, SourceLocation TemplateKWLoc,
  const DeclarationNameInfo &NameInfo, bool RequiresADL,
  const TemplateArgumentListInfo *Args, UnresolvedSetIterator Begin,
- UnresolvedSetIterator End, bool KnownDependent);
+ UnresolvedSetIterator End, bool KnownDependent,
+ bool KnownInstantiationDependent);
 
   static UnresolvedLookupExpr *CreateEmpty(const ASTContext &Context,
unsigned NumResults,
diff --git a/clang/lib/AST/ASTImporter.cpp b/clang/lib/AST/ASTImporter.cpp
index 103235547f482..49cbd60cafd0e 100644
--- a/clang/lib/AST/ASTImporter.cpp
+++ b/clang/lib/AST/ASTImporter.cpp
@@ -8629,13 +8629,14 @@ 
ASTNodeImporter::VisitUnresolvedLookupExpr(UnresolvedLookupExpr *E) {
 return UnresolvedLookupExpr::Create(
 Importer.getToContext(), *ToNamingClassOrErr, *ToQualifierLocOrErr,
 *ToTemplateKeywordLocOrErr, ToNameInfo, E->requiresADL(), &ToTAInfo,
-ToDecls.begin(), ToDecls.end(), KnownDependent);
+ToDecls.begin(), ToDecls.end(), KnownDependent,
+E->isInstantiationDependent());
   }
 
   return UnresolvedLookupExpr::Create(
   Importer.getToContext(), *ToNamingClassOrErr, *ToQualifierLocOrErr,
   ToNameInfo, E->requiresADL(), ToDecls.begin(), ToDecls.end(),
-  /*KnownDependent=*/E->isTypeDependent());
+  /*KnownDependent=*/E->isTypeDependent(), E->isInstantiationDependent());
 }
 
 ExpectedStmt
diff --git a/clang/lib/AST/ExprCXX.cpp b/clang/lib/AST/ExprCXX.cpp
index 6212989e21737..83ce404add5f5 100644
--- a/clang/lib/AST/ExprCXX.cpp
+++ b/clang/lib/AST/ExprCXX.cpp
@@ -402,10 +402,11 @@ UnresolvedLookupExpr::UnresolvedLookupExpr(
 NestedNameSpecifierLoc QualifierLoc, SourceLocation TemplateKWLoc,
 const DeclarationNameInfo &NameInfo, bool RequiresADL,
 const TemplateArgumentListInfo *TemplateArgs, UnresolvedSetIterator Begin,
-UnresolvedSetIterator End, bool KnownDependent)
+UnresolvedSetIterator End, bool KnownDependent,
+bool KnownInstantiationDependent)
 : OverloadExpr(UnresolvedLookupExprClass, Context, QualifierLoc,
TemplateKWLoc, NameInfo, TemplateArgs, Begin, End,
-   KnownDependent, false, false),
+   KnownDependent, KnownInstantiationDependent, false),
   NamingClass(NamingClass) {
   UnresolvedLookupExprBits.RequiresADL = RequiresADL;
 }
@@ -420,7 +421,7 @@ UnresolvedLookupExpr *UnresolvedLookupExpr::Create(
 const ASTContext &Context, CXXRecordDecl *NamingClass,
 NestedNameSpecifierLoc QualifierLoc, const DeclarationNameInfo &NameInfo,
 bool RequiresADL, UnresolvedSetIterator Begin, UnresolvedSetIterator End,
-bool KnownDependent) 

[clang] [Clang][NFC] Remove trailing whitespace from SemaExpr.cpp (PR #102001)

2024-08-05 Thread Krystian Stasiowski via cfe-commits

https://github.com/sdkrystian edited 
https://github.com/llvm/llvm-project/pull/102001
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [Clang][NFC] Remove trailing whitespace from SemaExpr.cpp (PR #102001)

2024-08-05 Thread Krystian Stasiowski via cfe-commits

https://github.com/sdkrystian closed 
https://github.com/llvm/llvm-project/pull/102001
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [Clang][NFC] Remove trailing whitespace from SemaExpr.cpp (PR #102001)

2024-08-05 Thread Krystian Stasiowski via cfe-commits

https://github.com/sdkrystian edited 
https://github.com/llvm/llvm-project/pull/102001
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [Clang][NFC] Remove trailing whitespace from SemaExpr.cpp (PR #102001)

2024-08-05 Thread Krystian Stasiowski via cfe-commits

https://github.com/sdkrystian created 
https://github.com/llvm/llvm-project/pull/102001

None

>From 42012dba14c04b00ea0c8f542a9bfc0983002a9e Mon Sep 17 00:00:00 2001
From: Krystian Stasiowski 
Date: Mon, 5 Aug 2024 11:03:04 -0400
Subject: [PATCH] [Clang][NFC] Remove trailing whitespace from SemaExpr.cpp

---
 clang/lib/Sema/SemaExpr.cpp | 8 
 1 file changed, 4 insertions(+), 4 deletions(-)

diff --git a/clang/lib/Sema/SemaExpr.cpp b/clang/lib/Sema/SemaExpr.cpp
index 74c0e01705905..d0ba12fe80f9a 100644
--- a/clang/lib/Sema/SemaExpr.cpp
+++ b/clang/lib/Sema/SemaExpr.cpp
@@ -17008,10 +17008,10 @@ Sema::VerifyIntegerConstantExpression(Expr *E, 
llvm::APSInt *Result,
 if (!isa(E))
   E = Result ? ConstantExpr::Create(Context, E, APValue(*Result))
  : ConstantExpr::Create(Context, E);
-
+
 if (Notes.empty())
   return E;
-
+
 // If our only note is the usual "invalid subexpression" note, just point
 // the caret at its location rather than producing an essentially
 // redundant note.
@@ -17020,7 +17020,7 @@ Sema::VerifyIntegerConstantExpression(Expr *E, 
llvm::APSInt *Result,
   DiagLoc = Notes[0].first;
   Notes.clear();
 }
-
+
 if (getLangOpts().CPlusPlus) {
   if (!Diagnoser.Suppress) {
 Diagnoser.diagnoseNotICE(*this, DiagLoc) << E->getSourceRange();
@@ -17033,7 +17033,7 @@ Sema::VerifyIntegerConstantExpression(Expr *E, 
llvm::APSInt *Result,
 Diagnoser.diagnoseFold(*this, DiagLoc) << E->getSourceRange();
 for (const PartialDiagnosticAt &Note : Notes)
   Diag(Note.first, Note.second);
-
+
 return E;
   }
 

___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [Clang][Sema] Make UnresolvedLookupExprs in class scope explicit specializations instantiation dependent (PR #100392)

2024-08-05 Thread Krystian Stasiowski via cfe-commits

sdkrystian wrote:

> Can we get rid of the whitespace only changes?

@cor3ntin I have my editor configured to remove trailing whitespace on save. 
I'll just merge a commit to `main` that removes the trailing whitespace.

> Can we maybe introduce an enum, it's a lot of booleans that will be easy to 
> mix. Maybe passing ExprDependence would be reasonable here

This sounds more like an unrelated refactoring change. I'm going to hold off on 
doing that in this patch. 

https://github.com/llvm/llvm-project/pull/100392
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [Clang][Sema] Ensure that the selected candidate for a member function explicit specialization is more constrained than all others (PR #101721)

2024-08-05 Thread Krystian Stasiowski via cfe-commits


@@ -10465,7 +10466,7 @@ Sema::ActOnFunctionDeclarator(Scope *S, Declarator &D, 
DeclContext *DC,
 Previous))
   NewFD->setInvalidDecl();
   }
-} else if (isMemberSpecialization && isa(NewFD)) {
+} else if (isMemberSpecialization && !FunctionTemplate) {

sdkrystian wrote:

Yes

https://github.com/llvm/llvm-project/pull/101721
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [Clang][Sema] Ensure that the selected candidate for a member function explicit specialization is more constrained than all others (PR #101721)

2024-08-05 Thread Krystian Stasiowski via cfe-commits

https://github.com/sdkrystian edited 
https://github.com/llvm/llvm-project/pull/101721
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [Clang][Sema] Ensure that the selected candidate for a member function explicit specialization is more constrained than all others (PR #101721)

2024-08-05 Thread Krystian Stasiowski via cfe-commits

https://github.com/sdkrystian edited 
https://github.com/llvm/llvm-project/pull/101721
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [Clang][Sema] Ensure that the selected candidate for a member function explicit specialization is more constrained than all others (PR #101721)

2024-08-05 Thread Krystian Stasiowski via cfe-commits


@@ -7964,8 +7964,9 @@ NamedDecl *Sema::ActOnVariableDeclarator(
 D.setRedeclaration(CheckVariableDeclaration(NewVD, Previous));
   } else {
 // If this is an explicit specialization of a static data member, check it.
-if (IsMemberSpecialization && !IsVariableTemplateSpecialization &&
-!NewVD->isInvalidDecl() && CheckMemberSpecialization(NewVD, Previous))
+if (IsMemberSpecialization && !IsVariableTemplate &&
+!IsVariableTemplateSpecialization && !NewVD->isInvalidDecl() &&
+CheckMemberSpecialization(NewVD, Previous))

sdkrystian wrote:

> Hm, do we not want to do these checks for an explicit specialization of a 
> member template? Or do we also do those checks somewhere else?

`CheckMemberSpecialization` only handles explicit specializations of 
non-template members specialized for an implicit instantiation of a class 
template. 

Explicit specializations of _member templates_ specialized for an implicit 
instantiation of a class template are handled on the same codepath as normal 
templates, and we set the correct "instantiated from" template there.

https://github.com/llvm/llvm-project/pull/101721
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [libcxx] Reapply "[Clang] Implement resolution for CWG1835 (#92957, #98547)" (PR #100425)

2024-08-01 Thread Krystian Stasiowski via cfe-commits


@@ -1779,6 +1779,42 @@ void Parser::checkPotentialAngleBracket(ExprResult 
&PotentialTemplateName) {
 Priority);
 }
 
+bool Parser::isMissingTemplateKeywordBeforeScope(bool AnnotateInvalid) {
+  assert(Tok.is(tok::coloncolon));
+  Sema::DisableTypoCorrectionRAII DTC(Actions);
+  ColonProtectionRAIIObject ColonProtection(*this);
+
+  SourceLocation StartLoc = Tok.getLocation();
+  if (TryAnnotateTypeOrScopeToken())
+return true;
+  if (Tok.isSimpleTypeSpecifier(getLangOpts()))
+return false;
+  CXXScopeSpec SS;
+  ParseOptionalCXXScopeSpecifier(SS, /*ObjectType=*/nullptr,
+ /*ObjectHasErrors=*/false,
+ /*EnteringContext=*/false);
+  ExprResult Result = tryParseCXXIdExpression(SS, 
/*isAddressOfOperand=*/false);

sdkrystian wrote:

@zygoloid Do you otherwise think that it's reasonable to apply this change to 
_all_ C++ language modes (given the existence of [this 
thread](https://lists.isocpp.org/core/2024/07/16028.php) on the core reflector 
resulting from the initial application of this patch _without_ the enhanced 
identification of missing `template`)? 

https://github.com/llvm/llvm-project/pull/100425
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [libcxx] Reapply "[Clang] Implement resolution for CWG1835 (#92957, #98547)" (PR #100425)

2024-07-31 Thread Krystian Stasiowski via cfe-commits

https://github.com/sdkrystian edited 
https://github.com/llvm/llvm-project/pull/100425
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [libcxx] Reapply "[Clang] Implement resolution for CWG1835 (#92957, #98547)" (PR #100425)

2024-07-31 Thread Krystian Stasiowski via cfe-commits


@@ -1779,6 +1779,42 @@ void Parser::checkPotentialAngleBracket(ExprResult 
&PotentialTemplateName) {
 Priority);
 }
 
+bool Parser::isMissingTemplateKeywordBeforeScope(bool AnnotateInvalid) {
+  assert(Tok.is(tok::coloncolon));
+  Sema::DisableTypoCorrectionRAII DTC(Actions);
+  ColonProtectionRAIIObject ColonProtection(*this);
+
+  SourceLocation StartLoc = Tok.getLocation();
+  if (TryAnnotateTypeOrScopeToken())
+return true;
+  if (Tok.isSimpleTypeSpecifier(getLangOpts()))
+return false;
+  CXXScopeSpec SS;
+  ParseOptionalCXXScopeSpecifier(SS, /*ObjectType=*/nullptr,
+ /*ObjectHasErrors=*/false,
+ /*EnteringContext=*/false);
+  ExprResult Result = tryParseCXXIdExpression(SS, 
/*isAddressOfOperand=*/false);

sdkrystian wrote:

> Parsing the same expression twice could also be problematic in some cases -- 
> for example, if it contains a lambda, we might assign it the wrong mangling 
> number. Can we arrange things such that for a valid program, we only parse 
> the expression once?

@zygoloid That already is the case:
```cpp
template
struct A
{
constexpr static int x = 0;

template
using B = A;
};

template
struct B
{
constexpr static int x = 0;
};

template
void f(T t)
{
t.A<0>::template B::x; // ok, interpreted as '((t.A) < 
0) > ::template B::x'
  // lambda expression is only parsed once

t.A<0>::template C::x; // warning: use 'template' 
keyword to treat 'A' as a dependent template name
   // lambda expression is parsed 
twice
}
```


https://github.com/llvm/llvm-project/pull/100425
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [libcxx] Reapply "[Clang] Implement resolution for CWG1835 (#92957, #98547)" (PR #100425)

2024-07-30 Thread Krystian Stasiowski via cfe-commits

https://github.com/sdkrystian edited 
https://github.com/llvm/llvm-project/pull/100425
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [libcxx] Reapply "[Clang] Implement resolution for CWG1835 (#92957, #98547)" (PR #100425)

2024-07-30 Thread Krystian Stasiowski via cfe-commits


@@ -1779,6 +1779,42 @@ void Parser::checkPotentialAngleBracket(ExprResult 
&PotentialTemplateName) {
 Priority);
 }
 
+bool Parser::isMissingTemplateKeywordBeforeScope(bool AnnotateInvalid) {
+  assert(Tok.is(tok::coloncolon));
+  Sema::DisableTypoCorrectionRAII DTC(Actions);
+  ColonProtectionRAIIObject ColonProtection(*this);
+
+  SourceLocation StartLoc = Tok.getLocation();
+  if (TryAnnotateTypeOrScopeToken())
+return true;
+  if (Tok.isSimpleTypeSpecifier(getLangOpts()))
+return false;
+  CXXScopeSpec SS;
+  ParseOptionalCXXScopeSpecifier(SS, /*ObjectType=*/nullptr,
+ /*ObjectHasErrors=*/false,
+ /*EnteringContext=*/false);
+  ExprResult Result = tryParseCXXIdExpression(SS, 
/*isAddressOfOperand=*/false);

sdkrystian wrote:

For a well-formed program, any tentative parsing done here will happen anyways 
when parsing the second operand of the `>` operator. Only for an _ill-formed_ 
program (i.e. one where `template` is missing) do we instantiate things that 
should not be instantiated.

As an alternative, we could also just lookup the name immediately following the 
`::` _nested-name-specifier_ and make the determination based on that. 

https://github.com/llvm/llvm-project/pull/100425
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [libcxx] Reapply "[Clang] Implement resolution for CWG1835 (#92957, #98547)" (PR #100425)

2024-07-30 Thread Krystian Stasiowski via cfe-commits

sdkrystian wrote:

With these changes, we can now issue warnings for the missing `template` 
keyword in the _vast_ majority of cases:
```cpp
template
struct A { int x; };

template
struct B { int x; };

template
struct C { int x; };

template
struct D { int x; };

template
constexpr inline int V = I;

int y;

template
void f(T t) {
  t.A<0>::x;// expected-warning {{use 'template' 
keyword to treat 'A' as a dependent template name}}
  t.A::x;// expected-warning {{use 'template' 
keyword to treat 'A' as a dependent template name}}
  t.A::x;   // expected-warning {{use 'template' 
keyword to treat 'A' as a dependent template name}}
  t.A::x;   // expected-warning {{use 'template' 
keyword to treat 'A' as a dependent template name}}
  t.A>(0)>::x;   // expected-warning {{use 'template' 
keyword to treat 'A' as a dependent template name}}
  t.A>(0)>::x; // expected-warning {{use 'template' 
keyword to treat 'A' as a dependent template name}}
  t.B<1, true>::x;  // expected-warning {{use 'template' 
keyword to treat 'B' as a dependent template name}}
  t.C<2, int, 4>::x;// expected-warning {{use 'template' 
keyword to treat 'C' as a dependent template name}}
  t.A>::x; // expected-warning {{use 'template' 
keyword to treat 'A' as a dependent template name}}
  t.B<1, V<1>>::x;  // expected-warning {{use 'template' 
keyword to treat 'B' as a dependent template name}}
  t.C, int, V<3>>::x;  // expected-warning {{use 'template' 
keyword to treat 'C' as a dependent template name}}
  t.A<1 && T::template f<0>()>::x;  // expected-warning {{use 'template' 
keyword to treat 'A' as a dependent template name}}

  t.A<(1 > 2)>::x;   // expected-warning {{use 'template' keyword to 
treat 'A' as a dependent template name}}
  t.A<(1 < 3)>::x;   // expected-warning {{use 'template' keyword to 
treat 'A' as a dependent template name}}

  t.B::x < int, 1>::x;  // expected-warning {{use 'template' keyword to 
treat 'x' as a dependent template name}}

  t.B::x < 0, 1>::x;// expected-error   {{no member named 'x' in the 
global namespace}}
 // expected-error   {{missing 'template' keyword 
prior to dependent template name 'B'}}

  t.A<1 < 4>::x; // expected-warning {{use 'template' keyword to 
treat 'A' as a dependent template name}}

  t.A::x; // expected-error   {{no member named 'x' in the 
global namespace}}
 // expected-error   {{missing 'template' keyword 
prior to dependent template name 'A'}}

  t.A::x; // expected-warning {{use 'template' keyword to 
treat 'A' as a dependent template name}}

  t.A<1 > 4>::x; // expected-error   {{no member named 'x' in the 
global namespace}}

  t.A<0>::y; // ok, parsed as '((t.A) < 0) > ::y'
}
```
Would like to get feedback from @AaronBallman, @cor3ntin, @hokein, and perhaps 
@zygoloid on this :). 

I highly doubt the [discussion on the 
reflector](https://lists.isocpp.org/core/2024/07/16028.php) will result in any 
mitigation mechanisms being added (see my reply 
[here](https://lists.isocpp.org/core/2024/07/16039.php)). If any action _is_ 
taken, the most I foresee would be applying it in C++23 & later. 

https://github.com/llvm/llvm-project/pull/100425
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [libcxx] Reapply "[Clang] Implement resolution for CWG1835 (#92957, #98547)" (PR #100425)

2024-07-30 Thread Krystian Stasiowski via cfe-commits

sdkrystian wrote:

With these changes, we can now issue warnings for the missing `template` 
keyword in the _vast_ majority of cases:
```cpp
template
struct A { int x; };

template
struct B { int x; };

template
struct C { int x; };

template
struct D { int x; };

template
constexpr inline int V = I;

int y;

template
void f(T t) {
  t.A<0>::x;// expected-warning {{use 'template' 
keyword to treat 'A' as a dependent template name}}
  t.A::x;// expected-warning {{use 'template' 
keyword to treat 'A' as a dependent template name}}
  t.A::x;   // expected-warning {{use 'template' 
keyword to treat 'A' as a dependent template name}}
  t.A::x;   // expected-warning {{use 'template' 
keyword to treat 'A' as a dependent template name}}
  t.A>(0)>::x;   // expected-warning {{use 'template' 
keyword to treat 'A' as a dependent template name}}
  t.A>(0)>::x; // expected-warning {{use 'template' 
keyword to treat 'A' as a dependent template name}}
  t.B<1, true>::x;  // expected-warning {{use 'template' 
keyword to treat 'B' as a dependent template name}}
  t.C<2, int, 4>::x;// expected-warning {{use 'template' 
keyword to treat 'C' as a dependent template name}}
  t.A>::x; // expected-warning {{use 'template' 
keyword to treat 'A' as a dependent template name}}
  t.B<1, V<1>>::x;  // expected-warning {{use 'template' 
keyword to treat 'B' as a dependent template name}}
  t.C, int, V<3>>::x;  // expected-warning {{use 'template' 
keyword to treat 'C' as a dependent template name}}
  t.A<1 && T::template f<0>()>::x;  // expected-warning {{use 'template' 
keyword to treat 'A' as a dependent template name}}

  t.A<(1 > 2)>::x;   // expected-warning {{use 'template' keyword to 
treat 'A' as a dependent template name}}
  t.A<(1 < 3)>::x;   // expected-warning {{use 'template' keyword to 
treat 'A' as a dependent template name}}

  t.B::x < int, 1>::x;  // expected-warning {{use 'template' keyword to 
treat 'x' as a dependent template name}}

  t.B::x < 0, 1>::x;// expected-error   {{no member named 'x' in the 
global namespace}}
 // expected-error   {{missing 'template' keyword 
prior to dependent template name 'B'}}

  t.A<1 < 4>::x; // expected-warning {{use 'template' keyword to 
treat 'A' as a dependent template name}}

  t.A::x; // expected-error   {{no member named 'x' in the 
global namespace}}
 // expected-error   {{missing 'template' keyword 
prior to dependent template name 'A'}}

  t.A::x; // expected-warning {{use 'template' keyword to 
treat 'A' as a dependent template name}}

  t.A<1 > 4>::x; // expected-error   {{no member named 'x' in the 
global namespace}}

  t.A<0>::y; // ok, parsed as '((t.A) < 0) > ::y'
}
```
Would like to get feedback from @AaronBallman, @cor3ntin, @hokein, and perhaps 
@zygoloid on this :). 

I highly doubt the [discussion on the 
reflector](https://lists.isocpp.org/core/2024/07/16028.php) will result in any 
mitigation mechanisms being added (see my reply 
[here](https://lists.isocpp.org/core/2024/07/16039.php)). If any action _is_ 
taken, the most I foresee would be applying it in C++23 & later. 

https://github.com/llvm/llvm-project/pull/100425
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [libcxx] Reapply "[Clang] Implement resolution for CWG1835 (#92957, #98547)" (PR #100425)

2024-07-30 Thread Krystian Stasiowski via cfe-commits

sdkrystian wrote:

Also added support for names prefixed with the `template` keyword. 

https://github.com/llvm/llvm-project/pull/100425
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [libcxx] Reapply "[Clang] Implement resolution for CWG1835 (#92957, #98547)" (PR #100425)

2024-07-30 Thread Krystian Stasiowski via cfe-commits

https://github.com/sdkrystian edited 
https://github.com/llvm/llvm-project/pull/100425
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [libcxx] Reapply "[Clang] Implement resolution for CWG1835 (#92957, #98547)" (PR #100425)

2024-07-30 Thread Krystian Stasiowski via cfe-commits

sdkrystian wrote:

I've further improved `isTemplateArgumentList` so we only consider `<` as the 
start of a potential template-argument-list if it follows an _identifier_ or 
the name in an _operator-function-id_/_literal-operator-id_ when trying to find 
the closing `>`. Also, explicit casts (a la `static_cast`) are handled, as are 
constructs which may either be a _type-id_ or an explicit type conversion 
(functional notation).

https://github.com/llvm/llvm-project/pull/100425
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [Clang][Parse] Fix ambiguity with nested-name-specifiers that may declarative (PR #96364)

2024-07-29 Thread Krystian Stasiowski via cfe-commits

https://github.com/sdkrystian closed 
https://github.com/llvm/llvm-project/pull/96364
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [Clang][Parse] Fix ambiguity with nested-name-specifiers that may declarative (PR #96364)

2024-07-29 Thread Krystian Stasiowski via cfe-commits

sdkrystian wrote:

I think this is ready to merge. I have [a 
branch](https://github.com/sdkrystian/llvm-project/tree/perf/backtrack-raii) 
which fully implements annotated/unannotated preprocessor backtrack using RAII 
objects, but I think this is beyond the scope of this PR.

https://github.com/llvm/llvm-project/pull/96364
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [Clang][Parse] Fix ambiguity with nested-name-specifiers that may declarative (PR #96364)

2024-07-29 Thread Krystian Stasiowski via cfe-commits

https://github.com/sdkrystian updated 
https://github.com/llvm/llvm-project/pull/96364

>From 496e0cf24b07622bd9354297c20091c2057a55c6 Mon Sep 17 00:00:00 2001
From: Krystian Stasiowski 
Date: Wed, 12 Jun 2024 14:14:26 -0400
Subject: [PATCH 1/8] [Clang][Parse] Fix ambiguity with nested-name-specifiers
 that may be declarative

---
 clang/include/clang/Lex/Preprocessor.h| 14 +++-
 clang/include/clang/Parse/Parser.h| 13 ++-
 clang/lib/Lex/PPCaching.cpp   | 39 -
 clang/lib/Parse/ParseCXXInlineMethods.cpp | 41 +
 clang/lib/Parse/ParseDecl.cpp | 83 ---
 clang/lib/Parse/ParseExprCXX.cpp  | 19 ++---
 .../CXX/dcl.decl/dcl.meaning/dcl.mptr/p2.cpp  | 64 ++
 clang/test/CXX/temp/temp.res/p3.cpp   | 10 +--
 8 files changed, 182 insertions(+), 101 deletions(-)
 create mode 100644 clang/test/CXX/dcl.decl/dcl.meaning/dcl.mptr/p2.cpp

diff --git a/clang/include/clang/Lex/Preprocessor.h 
b/clang/include/clang/Lex/Preprocessor.h
index fc7d0053f2323..b2dbd7d5375b5 100644
--- a/clang/include/clang/Lex/Preprocessor.h
+++ b/clang/include/clang/Lex/Preprocessor.h
@@ -1160,6 +1160,9 @@ class Preprocessor {
   /// invoked (at which point the last position is popped).
   std::vector BacktrackPositions;
 
+  std::vector>
+  UnannotatedBacktrackPositions;
+
   /// True if \p Preprocessor::SkipExcludedConditionalBlock() is running.
   /// This is used to guard against calling this function recursively.
   ///
@@ -1722,7 +1725,7 @@ class Preprocessor {
   /// at some point after EnableBacktrackAtThisPos. If you don't, caching of
   /// tokens will continue indefinitely.
   ///
-  void EnableBacktrackAtThisPos();
+  void EnableBacktrackAtThisPos(bool Unannotated = false);
 
   /// Disable the last EnableBacktrackAtThisPos call.
   void CommitBacktrackedTokens();
@@ -1733,7 +1736,11 @@ class Preprocessor {
 
   /// True if EnableBacktrackAtThisPos() was called and
   /// caching of tokens is on.
+
   bool isBacktrackEnabled() const { return !BacktrackPositions.empty(); }
+  bool isUnannotatedBacktrackEnabled() const {
+return !UnannotatedBacktrackPositions.empty();
+  }
 
   /// Lex the next token for this preprocessor.
   void Lex(Token &Result);
@@ -1841,8 +1848,9 @@ class Preprocessor {
   void RevertCachedTokens(unsigned N) {
 assert(isBacktrackEnabled() &&
"Should only be called when tokens are cached for backtracking");
-assert(signed(CachedLexPos) - signed(N) >= 
signed(BacktrackPositions.back())
- && "Should revert tokens up to the last backtrack position, not 
more");
+assert(signed(CachedLexPos) - signed(N) >=
+   signed(BacktrackPositions.back() >> 1) &&
+   "Should revert tokens up to the last backtrack position, not more");
 assert(signed(CachedLexPos) - signed(N) >= 0 &&
"Corrupted backtrack positions ?");
 CachedLexPos -= N;
diff --git a/clang/include/clang/Parse/Parser.h 
b/clang/include/clang/Parse/Parser.h
index 35bb1a19d40f0..7f5e21127d1e5 100644
--- a/clang/include/clang/Parse/Parser.h
+++ b/clang/include/clang/Parse/Parser.h
@@ -1034,7 +1034,7 @@ class Parser : public CodeCompletionHandler {
 bool isActive;
 
   public:
-explicit TentativeParsingAction(Parser &p)
+explicit TentativeParsingAction(Parser &p, bool Unannotated = false)
 : P(p), PrevPreferredType(P.PreferredType) {
   PrevTok = P.Tok;
   PrevTentativelyDeclaredIdentifierCount =
@@ -1042,7 +1042,7 @@ class Parser : public CodeCompletionHandler {
   PrevParenCount = P.ParenCount;
   PrevBracketCount = P.BracketCount;
   PrevBraceCount = P.BraceCount;
-  P.PP.EnableBacktrackAtThisPos();
+  P.PP.EnableBacktrackAtThisPos(Unannotated);
   isActive = true;
 }
 void Commit() {
@@ -1073,13 +1073,11 @@ class Parser : public CodeCompletionHandler {
   class RevertingTentativeParsingAction
   : private Parser::TentativeParsingAction {
   public:
-RevertingTentativeParsingAction(Parser &P)
-: Parser::TentativeParsingAction(P) {}
+using TentativeParsingAction::TentativeParsingAction;
+
 ~RevertingTentativeParsingAction() { Revert(); }
   };
 
-  class UnannotatedTentativeParsingAction;
-
   /// ObjCDeclContextSwitch - An object used to switch context from
   /// an objective-c decl context to its enclosing decl context and
   /// back.
@@ -1984,7 +1982,8 @@ class Parser : public CodeCompletionHandler {
   CXXScopeSpec &SS, ParsedType ObjectType, bool ObjectHasErrors,
   bool EnteringContext, bool *MayBePseudoDestructor = nullptr,
   bool IsTypename = false, const IdentifierInfo **LastII = nullptr,
-  bool OnlyNamespace = false, bool InUsingDeclaration = false);
+  bool OnlyNamespace = false, bool InUsingDeclaration = false,
+  bool Disambiguation = false);
 
   
//======//
   // C++11 5.1.2: Lambda e

[clang] [Clang][Parse] Fix ambiguity with nested-name-specifiers that may declarative (PR #96364)

2024-07-29 Thread Krystian Stasiowski via cfe-commits

https://github.com/sdkrystian updated 
https://github.com/llvm/llvm-project/pull/96364

>From 691b0d3b23aa89af08ff6b1f4e09ff62c4b36ef6 Mon Sep 17 00:00:00 2001
From: Krystian Stasiowski 
Date: Wed, 12 Jun 2024 14:14:26 -0400
Subject: [PATCH 1/8] [Clang][Parse] Fix ambiguity with nested-name-specifiers
 that may be declarative

---
 clang/include/clang/Lex/Preprocessor.h| 14 +++-
 clang/include/clang/Parse/Parser.h| 13 ++-
 clang/lib/Lex/PPCaching.cpp   | 39 -
 clang/lib/Parse/ParseCXXInlineMethods.cpp | 41 +
 clang/lib/Parse/ParseDecl.cpp | 83 ---
 clang/lib/Parse/ParseExprCXX.cpp  | 19 ++---
 .../CXX/dcl.decl/dcl.meaning/dcl.mptr/p2.cpp  | 64 ++
 clang/test/CXX/temp/temp.res/p3.cpp   | 10 +--
 8 files changed, 182 insertions(+), 101 deletions(-)
 create mode 100644 clang/test/CXX/dcl.decl/dcl.meaning/dcl.mptr/p2.cpp

diff --git a/clang/include/clang/Lex/Preprocessor.h 
b/clang/include/clang/Lex/Preprocessor.h
index fc7d0053f2323..b2dbd7d5375b5 100644
--- a/clang/include/clang/Lex/Preprocessor.h
+++ b/clang/include/clang/Lex/Preprocessor.h
@@ -1160,6 +1160,9 @@ class Preprocessor {
   /// invoked (at which point the last position is popped).
   std::vector BacktrackPositions;
 
+  std::vector>
+  UnannotatedBacktrackPositions;
+
   /// True if \p Preprocessor::SkipExcludedConditionalBlock() is running.
   /// This is used to guard against calling this function recursively.
   ///
@@ -1722,7 +1725,7 @@ class Preprocessor {
   /// at some point after EnableBacktrackAtThisPos. If you don't, caching of
   /// tokens will continue indefinitely.
   ///
-  void EnableBacktrackAtThisPos();
+  void EnableBacktrackAtThisPos(bool Unannotated = false);
 
   /// Disable the last EnableBacktrackAtThisPos call.
   void CommitBacktrackedTokens();
@@ -1733,7 +1736,11 @@ class Preprocessor {
 
   /// True if EnableBacktrackAtThisPos() was called and
   /// caching of tokens is on.
+
   bool isBacktrackEnabled() const { return !BacktrackPositions.empty(); }
+  bool isUnannotatedBacktrackEnabled() const {
+return !UnannotatedBacktrackPositions.empty();
+  }
 
   /// Lex the next token for this preprocessor.
   void Lex(Token &Result);
@@ -1841,8 +1848,9 @@ class Preprocessor {
   void RevertCachedTokens(unsigned N) {
 assert(isBacktrackEnabled() &&
"Should only be called when tokens are cached for backtracking");
-assert(signed(CachedLexPos) - signed(N) >= 
signed(BacktrackPositions.back())
- && "Should revert tokens up to the last backtrack position, not 
more");
+assert(signed(CachedLexPos) - signed(N) >=
+   signed(BacktrackPositions.back() >> 1) &&
+   "Should revert tokens up to the last backtrack position, not more");
 assert(signed(CachedLexPos) - signed(N) >= 0 &&
"Corrupted backtrack positions ?");
 CachedLexPos -= N;
diff --git a/clang/include/clang/Parse/Parser.h 
b/clang/include/clang/Parse/Parser.h
index 35bb1a19d40f0..7f5e21127d1e5 100644
--- a/clang/include/clang/Parse/Parser.h
+++ b/clang/include/clang/Parse/Parser.h
@@ -1034,7 +1034,7 @@ class Parser : public CodeCompletionHandler {
 bool isActive;
 
   public:
-explicit TentativeParsingAction(Parser &p)
+explicit TentativeParsingAction(Parser &p, bool Unannotated = false)
 : P(p), PrevPreferredType(P.PreferredType) {
   PrevTok = P.Tok;
   PrevTentativelyDeclaredIdentifierCount =
@@ -1042,7 +1042,7 @@ class Parser : public CodeCompletionHandler {
   PrevParenCount = P.ParenCount;
   PrevBracketCount = P.BracketCount;
   PrevBraceCount = P.BraceCount;
-  P.PP.EnableBacktrackAtThisPos();
+  P.PP.EnableBacktrackAtThisPos(Unannotated);
   isActive = true;
 }
 void Commit() {
@@ -1073,13 +1073,11 @@ class Parser : public CodeCompletionHandler {
   class RevertingTentativeParsingAction
   : private Parser::TentativeParsingAction {
   public:
-RevertingTentativeParsingAction(Parser &P)
-: Parser::TentativeParsingAction(P) {}
+using TentativeParsingAction::TentativeParsingAction;
+
 ~RevertingTentativeParsingAction() { Revert(); }
   };
 
-  class UnannotatedTentativeParsingAction;
-
   /// ObjCDeclContextSwitch - An object used to switch context from
   /// an objective-c decl context to its enclosing decl context and
   /// back.
@@ -1984,7 +1982,8 @@ class Parser : public CodeCompletionHandler {
   CXXScopeSpec &SS, ParsedType ObjectType, bool ObjectHasErrors,
   bool EnteringContext, bool *MayBePseudoDestructor = nullptr,
   bool IsTypename = false, const IdentifierInfo **LastII = nullptr,
-  bool OnlyNamespace = false, bool InUsingDeclaration = false);
+  bool OnlyNamespace = false, bool InUsingDeclaration = false,
+  bool Disambiguation = false);
 
   
//======//
   // C++11 5.1.2: Lambda e

[clang] [Clang][Parse] Fix ambiguity with nested-name-specifiers that may declarative (PR #96364)

2024-07-29 Thread Krystian Stasiowski via cfe-commits

https://github.com/sdkrystian updated 
https://github.com/llvm/llvm-project/pull/96364

>From 037fb12412e9b3787e91d0a8ca826e098eab4e85 Mon Sep 17 00:00:00 2001
From: Krystian Stasiowski 
Date: Wed, 12 Jun 2024 14:14:26 -0400
Subject: [PATCH 1/8] [Clang][Parse] Fix ambiguity with nested-name-specifiers
 that may be declarative

---
 clang/include/clang/Lex/Preprocessor.h| 14 +++-
 clang/include/clang/Parse/Parser.h| 13 ++-
 clang/lib/Lex/PPCaching.cpp   | 39 -
 clang/lib/Parse/ParseCXXInlineMethods.cpp | 41 +
 clang/lib/Parse/ParseDecl.cpp | 83 ---
 clang/lib/Parse/ParseExprCXX.cpp  | 19 ++---
 .../CXX/dcl.decl/dcl.meaning/dcl.mptr/p2.cpp  | 64 ++
 clang/test/CXX/temp/temp.res/p3.cpp   | 10 +--
 8 files changed, 182 insertions(+), 101 deletions(-)
 create mode 100644 clang/test/CXX/dcl.decl/dcl.meaning/dcl.mptr/p2.cpp

diff --git a/clang/include/clang/Lex/Preprocessor.h 
b/clang/include/clang/Lex/Preprocessor.h
index fc7d0053f2323..b2dbd7d5375b5 100644
--- a/clang/include/clang/Lex/Preprocessor.h
+++ b/clang/include/clang/Lex/Preprocessor.h
@@ -1160,6 +1160,9 @@ class Preprocessor {
   /// invoked (at which point the last position is popped).
   std::vector BacktrackPositions;
 
+  std::vector>
+  UnannotatedBacktrackPositions;
+
   /// True if \p Preprocessor::SkipExcludedConditionalBlock() is running.
   /// This is used to guard against calling this function recursively.
   ///
@@ -1722,7 +1725,7 @@ class Preprocessor {
   /// at some point after EnableBacktrackAtThisPos. If you don't, caching of
   /// tokens will continue indefinitely.
   ///
-  void EnableBacktrackAtThisPos();
+  void EnableBacktrackAtThisPos(bool Unannotated = false);
 
   /// Disable the last EnableBacktrackAtThisPos call.
   void CommitBacktrackedTokens();
@@ -1733,7 +1736,11 @@ class Preprocessor {
 
   /// True if EnableBacktrackAtThisPos() was called and
   /// caching of tokens is on.
+
   bool isBacktrackEnabled() const { return !BacktrackPositions.empty(); }
+  bool isUnannotatedBacktrackEnabled() const {
+return !UnannotatedBacktrackPositions.empty();
+  }
 
   /// Lex the next token for this preprocessor.
   void Lex(Token &Result);
@@ -1841,8 +1848,9 @@ class Preprocessor {
   void RevertCachedTokens(unsigned N) {
 assert(isBacktrackEnabled() &&
"Should only be called when tokens are cached for backtracking");
-assert(signed(CachedLexPos) - signed(N) >= 
signed(BacktrackPositions.back())
- && "Should revert tokens up to the last backtrack position, not 
more");
+assert(signed(CachedLexPos) - signed(N) >=
+   signed(BacktrackPositions.back() >> 1) &&
+   "Should revert tokens up to the last backtrack position, not more");
 assert(signed(CachedLexPos) - signed(N) >= 0 &&
"Corrupted backtrack positions ?");
 CachedLexPos -= N;
diff --git a/clang/include/clang/Parse/Parser.h 
b/clang/include/clang/Parse/Parser.h
index 613bab9120dfc..602a68c2feaff 100644
--- a/clang/include/clang/Parse/Parser.h
+++ b/clang/include/clang/Parse/Parser.h
@@ -1034,7 +1034,7 @@ class Parser : public CodeCompletionHandler {
 bool isActive;
 
   public:
-explicit TentativeParsingAction(Parser &p)
+explicit TentativeParsingAction(Parser &p, bool Unannotated = false)
 : P(p), PrevPreferredType(P.PreferredType) {
   PrevTok = P.Tok;
   PrevTentativelyDeclaredIdentifierCount =
@@ -1042,7 +1042,7 @@ class Parser : public CodeCompletionHandler {
   PrevParenCount = P.ParenCount;
   PrevBracketCount = P.BracketCount;
   PrevBraceCount = P.BraceCount;
-  P.PP.EnableBacktrackAtThisPos();
+  P.PP.EnableBacktrackAtThisPos(Unannotated);
   isActive = true;
 }
 void Commit() {
@@ -1073,13 +1073,11 @@ class Parser : public CodeCompletionHandler {
   class RevertingTentativeParsingAction
   : private Parser::TentativeParsingAction {
   public:
-RevertingTentativeParsingAction(Parser &P)
-: Parser::TentativeParsingAction(P) {}
+using TentativeParsingAction::TentativeParsingAction;
+
 ~RevertingTentativeParsingAction() { Revert(); }
   };
 
-  class UnannotatedTentativeParsingAction;
-
   /// ObjCDeclContextSwitch - An object used to switch context from
   /// an objective-c decl context to its enclosing decl context and
   /// back.
@@ -1984,7 +1982,8 @@ class Parser : public CodeCompletionHandler {
   CXXScopeSpec &SS, ParsedType ObjectType, bool ObjectHasErrors,
   bool EnteringContext, bool *MayBePseudoDestructor = nullptr,
   bool IsTypename = false, const IdentifierInfo **LastII = nullptr,
-  bool OnlyNamespace = false, bool InUsingDeclaration = false);
+  bool OnlyNamespace = false, bool InUsingDeclaration = false,
+  bool Disambiguation = false);
 
   
//======//
   // C++11 5.1.2: Lambda e

[clang] [Clang][Parse] Fix ambiguity with nested-name-specifiers that may declarative (PR #96364)

2024-07-29 Thread Krystian Stasiowski via cfe-commits

https://github.com/sdkrystian updated 
https://github.com/llvm/llvm-project/pull/96364

>From 037fb12412e9b3787e91d0a8ca826e098eab4e85 Mon Sep 17 00:00:00 2001
From: Krystian Stasiowski 
Date: Wed, 12 Jun 2024 14:14:26 -0400
Subject: [PATCH 1/7] [Clang][Parse] Fix ambiguity with nested-name-specifiers
 that may be declarative

---
 clang/include/clang/Lex/Preprocessor.h| 14 +++-
 clang/include/clang/Parse/Parser.h| 13 ++-
 clang/lib/Lex/PPCaching.cpp   | 39 -
 clang/lib/Parse/ParseCXXInlineMethods.cpp | 41 +
 clang/lib/Parse/ParseDecl.cpp | 83 ---
 clang/lib/Parse/ParseExprCXX.cpp  | 19 ++---
 .../CXX/dcl.decl/dcl.meaning/dcl.mptr/p2.cpp  | 64 ++
 clang/test/CXX/temp/temp.res/p3.cpp   | 10 +--
 8 files changed, 182 insertions(+), 101 deletions(-)
 create mode 100644 clang/test/CXX/dcl.decl/dcl.meaning/dcl.mptr/p2.cpp

diff --git a/clang/include/clang/Lex/Preprocessor.h 
b/clang/include/clang/Lex/Preprocessor.h
index fc7d0053f2323..b2dbd7d5375b5 100644
--- a/clang/include/clang/Lex/Preprocessor.h
+++ b/clang/include/clang/Lex/Preprocessor.h
@@ -1160,6 +1160,9 @@ class Preprocessor {
   /// invoked (at which point the last position is popped).
   std::vector BacktrackPositions;
 
+  std::vector>
+  UnannotatedBacktrackPositions;
+
   /// True if \p Preprocessor::SkipExcludedConditionalBlock() is running.
   /// This is used to guard against calling this function recursively.
   ///
@@ -1722,7 +1725,7 @@ class Preprocessor {
   /// at some point after EnableBacktrackAtThisPos. If you don't, caching of
   /// tokens will continue indefinitely.
   ///
-  void EnableBacktrackAtThisPos();
+  void EnableBacktrackAtThisPos(bool Unannotated = false);
 
   /// Disable the last EnableBacktrackAtThisPos call.
   void CommitBacktrackedTokens();
@@ -1733,7 +1736,11 @@ class Preprocessor {
 
   /// True if EnableBacktrackAtThisPos() was called and
   /// caching of tokens is on.
+
   bool isBacktrackEnabled() const { return !BacktrackPositions.empty(); }
+  bool isUnannotatedBacktrackEnabled() const {
+return !UnannotatedBacktrackPositions.empty();
+  }
 
   /// Lex the next token for this preprocessor.
   void Lex(Token &Result);
@@ -1841,8 +1848,9 @@ class Preprocessor {
   void RevertCachedTokens(unsigned N) {
 assert(isBacktrackEnabled() &&
"Should only be called when tokens are cached for backtracking");
-assert(signed(CachedLexPos) - signed(N) >= 
signed(BacktrackPositions.back())
- && "Should revert tokens up to the last backtrack position, not 
more");
+assert(signed(CachedLexPos) - signed(N) >=
+   signed(BacktrackPositions.back() >> 1) &&
+   "Should revert tokens up to the last backtrack position, not more");
 assert(signed(CachedLexPos) - signed(N) >= 0 &&
"Corrupted backtrack positions ?");
 CachedLexPos -= N;
diff --git a/clang/include/clang/Parse/Parser.h 
b/clang/include/clang/Parse/Parser.h
index 613bab9120dfc..602a68c2feaff 100644
--- a/clang/include/clang/Parse/Parser.h
+++ b/clang/include/clang/Parse/Parser.h
@@ -1034,7 +1034,7 @@ class Parser : public CodeCompletionHandler {
 bool isActive;
 
   public:
-explicit TentativeParsingAction(Parser &p)
+explicit TentativeParsingAction(Parser &p, bool Unannotated = false)
 : P(p), PrevPreferredType(P.PreferredType) {
   PrevTok = P.Tok;
   PrevTentativelyDeclaredIdentifierCount =
@@ -1042,7 +1042,7 @@ class Parser : public CodeCompletionHandler {
   PrevParenCount = P.ParenCount;
   PrevBracketCount = P.BracketCount;
   PrevBraceCount = P.BraceCount;
-  P.PP.EnableBacktrackAtThisPos();
+  P.PP.EnableBacktrackAtThisPos(Unannotated);
   isActive = true;
 }
 void Commit() {
@@ -1073,13 +1073,11 @@ class Parser : public CodeCompletionHandler {
   class RevertingTentativeParsingAction
   : private Parser::TentativeParsingAction {
   public:
-RevertingTentativeParsingAction(Parser &P)
-: Parser::TentativeParsingAction(P) {}
+using TentativeParsingAction::TentativeParsingAction;
+
 ~RevertingTentativeParsingAction() { Revert(); }
   };
 
-  class UnannotatedTentativeParsingAction;
-
   /// ObjCDeclContextSwitch - An object used to switch context from
   /// an objective-c decl context to its enclosing decl context and
   /// back.
@@ -1984,7 +1982,8 @@ class Parser : public CodeCompletionHandler {
   CXXScopeSpec &SS, ParsedType ObjectType, bool ObjectHasErrors,
   bool EnteringContext, bool *MayBePseudoDestructor = nullptr,
   bool IsTypename = false, const IdentifierInfo **LastII = nullptr,
-  bool OnlyNamespace = false, bool InUsingDeclaration = false);
+  bool OnlyNamespace = false, bool InUsingDeclaration = false,
+  bool Disambiguation = false);
 
   
//======//
   // C++11 5.1.2: Lambda e

[clang] [libcxx] Reapply "[Clang] Implement resolution for CWG1835 (#92957, #98547)" (PR #100425)

2024-07-29 Thread Krystian Stasiowski via cfe-commits


@@ -767,6 +757,7 @@ bool Sema::BuildCXXNestedNameSpecifier(Scope *S, 
NestedNameSpecInfo &IdInfo,
   else
 Diag(IdInfo.IdentifierLoc, diag::err_undeclared_var_use)
 << IdInfo.Identifier;
+#endif

sdkrystian wrote:

Yeah, these changes shouldn't really be part of this PR. Just something I 
noticed when refactoring `BuildCXXNestedNameSpecifier` that needs to go. I'll 
address it in another PR.

https://github.com/llvm/llvm-project/pull/100425
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [Clang][Sema] Make UnresolvedLookupExprs in class scope explicit specializations instantiation dependent (PR #100392)

2024-07-29 Thread Krystian Stasiowski via cfe-commits

https://github.com/sdkrystian updated 
https://github.com/llvm/llvm-project/pull/100392

>From c4f8a620a2a4692c9fa27b41f7e86c8cb042e533 Mon Sep 17 00:00:00 2001
From: Krystian Stasiowski 
Date: Wed, 24 Jul 2024 10:15:47 -0400
Subject: [PATCH] [Clang][Sema] Make UnresolvedLookupExprs in class scope
 explicit specializations instantiation dependent

---
 clang/include/clang/AST/ExprCXX.h |  7 ---
 clang/lib/AST/ASTImporter.cpp |  5 +++--
 clang/lib/AST/ExprCXX.cpp | 19 +++
 clang/lib/Sema/SemaCoroutine.cpp  |  3 ++-
 clang/lib/Sema/SemaDecl.cpp   |  2 +-
 clang/lib/Sema/SemaDeclCXX.cpp|  2 +-
 clang/lib/Sema/SemaExpr.cpp   | 10 +-
 clang/lib/Sema/SemaExprMember.cpp |  3 ++-
 clang/lib/Sema/SemaOpenMP.cpp |  6 --
 clang/lib/Sema/SemaOverload.cpp   |  6 +++---
 clang/lib/Sema/SemaTemplate.cpp   |  3 ++-
 clang/lib/Sema/TreeTransform.h|  8 
 12 files changed, 42 insertions(+), 32 deletions(-)

diff --git a/clang/include/clang/AST/ExprCXX.h 
b/clang/include/clang/AST/ExprCXX.h
index f86f1818110e6..847a6ea408e98 100644
--- a/clang/include/clang/AST/ExprCXX.h
+++ b/clang/include/clang/AST/ExprCXX.h
@@ -3229,7 +3229,7 @@ class UnresolvedLookupExpr final
const DeclarationNameInfo &NameInfo, bool RequiresADL,
const TemplateArgumentListInfo *TemplateArgs,
UnresolvedSetIterator Begin, UnresolvedSetIterator End,
-   bool KnownDependent);
+   bool KnownDependent, bool KnownInstantiationDependent);
 
   UnresolvedLookupExpr(EmptyShell Empty, unsigned NumResults,
bool HasTemplateKWAndArgsInfo);
@@ -3248,7 +3248,7 @@ class UnresolvedLookupExpr final
  NestedNameSpecifierLoc QualifierLoc,
  const DeclarationNameInfo &NameInfo, bool RequiresADL,
  UnresolvedSetIterator Begin, UnresolvedSetIterator End,
- bool KnownDependent);
+ bool KnownDependent, bool KnownInstantiationDependent);
 
   // After canonicalization, there may be dependent template arguments in
   // CanonicalConverted But none of Args is dependent. When any of
@@ -3258,7 +3258,8 @@ class UnresolvedLookupExpr final
  NestedNameSpecifierLoc QualifierLoc, SourceLocation TemplateKWLoc,
  const DeclarationNameInfo &NameInfo, bool RequiresADL,
  const TemplateArgumentListInfo *Args, UnresolvedSetIterator Begin,
- UnresolvedSetIterator End, bool KnownDependent);
+ UnresolvedSetIterator End, bool KnownDependent,
+ bool KnownInstantiationDependent);
 
   static UnresolvedLookupExpr *CreateEmpty(const ASTContext &Context,
unsigned NumResults,
diff --git a/clang/lib/AST/ASTImporter.cpp b/clang/lib/AST/ASTImporter.cpp
index da1981d8dd05f..f7a0deb9f3556 100644
--- a/clang/lib/AST/ASTImporter.cpp
+++ b/clang/lib/AST/ASTImporter.cpp
@@ -8572,13 +8572,14 @@ 
ASTNodeImporter::VisitUnresolvedLookupExpr(UnresolvedLookupExpr *E) {
 return UnresolvedLookupExpr::Create(
 Importer.getToContext(), *ToNamingClassOrErr, *ToQualifierLocOrErr,
 *ToTemplateKeywordLocOrErr, ToNameInfo, E->requiresADL(), &ToTAInfo,
-ToDecls.begin(), ToDecls.end(), KnownDependent);
+ToDecls.begin(), ToDecls.end(), KnownDependent,
+E->isInstantiationDependent());
   }
 
   return UnresolvedLookupExpr::Create(
   Importer.getToContext(), *ToNamingClassOrErr, *ToQualifierLocOrErr,
   ToNameInfo, E->requiresADL(), ToDecls.begin(), ToDecls.end(),
-  /*KnownDependent=*/E->isTypeDependent());
+  /*KnownDependent=*/E->isTypeDependent(), E->isInstantiationDependent());
 }
 
 ExpectedStmt
diff --git a/clang/lib/AST/ExprCXX.cpp b/clang/lib/AST/ExprCXX.cpp
index e2c9643151126..76d5f87933136 100644
--- a/clang/lib/AST/ExprCXX.cpp
+++ b/clang/lib/AST/ExprCXX.cpp
@@ -402,10 +402,11 @@ UnresolvedLookupExpr::UnresolvedLookupExpr(
 NestedNameSpecifierLoc QualifierLoc, SourceLocation TemplateKWLoc,
 const DeclarationNameInfo &NameInfo, bool RequiresADL,
 const TemplateArgumentListInfo *TemplateArgs, UnresolvedSetIterator Begin,
-UnresolvedSetIterator End, bool KnownDependent)
+UnresolvedSetIterator End, bool KnownDependent,
+bool KnownInstantiationDependent)
 : OverloadExpr(UnresolvedLookupExprClass, Context, QualifierLoc,
TemplateKWLoc, NameInfo, TemplateArgs, Begin, End,
-   KnownDependent, false, false),
+   KnownDependent, KnownInstantiationDependent, false),
   NamingClass(NamingClass) {
   UnresolvedLookupExprBits.RequiresADL = RequiresADL;
 }
@@ -420,7 +421,7 @@ UnresolvedLookupExpr *UnresolvedLookupExpr::Create(
 const ASTContext &Context, CXXRecordDecl *NamingClass,
 NestedNameSpecifierLoc QualifierLoc, const DeclarationNameInfo &NameInfo,
 bool RequiresADL, UnresolvedSetIterator Begin, UnresolvedSetIterator End,
-bool KnownDep

[clang] [libcxx] Reapply "[Clang] Implement resolution for CWG1835 (#92957, #98547)" (PR #100425)

2024-07-26 Thread Krystian Stasiowski via cfe-commits

sdkrystian wrote:

> I am still concerned about the double error on the `t.A<1 < 4>::x` example.
The ideal outcome would be to turn the second error into a note.
How feasible to fix you think that is?

That's trivial to fix, just need to add a note variant of the "missing 
template" diagnostic. 

https://github.com/llvm/llvm-project/pull/100425
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [libcxx] Reapply "[Clang] Implement resolution for CWG1835 (#92957, #98547)" (PR #100425)

2024-07-26 Thread Krystian Stasiowski via cfe-commits

sdkrystian wrote:

@AaronBallman @cor3ntin @mizvekov So, I've made improvements to our 
implementation of `isTemplateArgumentList` that allow us to issue a warning 
instead of an error for most of the cases where applying the DR breaks existing 
code:
```cpp
template
struct A { int x; };

template
struct B { int x; };

template
struct C { int x; };

template
constexpr inline int V = I;

int y;

template
void f(T t)
{
t.A<0>::x;   // warning: use 'template' keyword to treat 'A' as 
a dependent template name
t.B<1, true>::x; // warning: use 'template' keyword to treat 'B' as 
a dependent template name
t.C<2, int, 4>::x;   // warning: use 'template' keyword to treat 'C' as 
a dependent template name
t.A>::x;// warning: use 'template' keyword to treat 'A' as 
a dependent template name
t.B<1, V<1>>::x; // warning: use 'template' keyword to treat 'B' as 
a dependent template name
t.C, int, V<3>>::x; // warning: use 'template' keyword to treat 'C' as 
a dependent template name

t.A<(1 > 2)>::x; // warning: use 'template' keyword to treat 'A' as 
a dependent template name
t.A<(1 < 3)>::x; // warning: use 'template' keyword to treat 'A' as 
a dependent template name

t.A<1 < 4>::x;   // error: no member named 'x' in the global 
namespace
 // error: missing 'template' keyword prior to 
dependent template name 'A'

t.A<1 > 4>::x;   // error: no member named 'x' in the global 
namespace

t.A<0>::y;   // ok, parsed as '((t.A) < 0) > ::y'
}
```
This is accomplished by (attempting to) look past the end of the potential 
_template-argument-list_, and if the token following the `>` is `::`, we try to 
parse it as an _id-expression_/type. If it ends up being invalid, then we 
consider it being an intended template name and we issue the warning.

Since we can look past the potential _template-argument-list_ in most cases, we 
could probably apply CWG1835 in all language modes with minimal impact on 
existing code. 

https://github.com/llvm/llvm-project/pull/100425
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


  1   2   3   4   5   6   7   8   9   >