[clang] [clang-tools-extra] [clang][CodeComplete] skip explicit obj param in SignatureHelp (PR #146649)

2025-07-03 Thread Mythreya Kuricheti via cfe-commits

https://github.com/MythreyaK updated 
https://github.com/llvm/llvm-project/pull/146649

>From 7f8581f01c3c25363b77100635c6df7223badba3 Mon Sep 17 00:00:00 2001
From: Mythreya Kuricheti 
Date: Wed, 2 Jul 2025 01:26:25 -0700
Subject: [PATCH 1/2] [clang][CodeComplete] skip explicit obj param in
 SignatureHelp

---
 .../clangd/unittests/CodeCompleteTests.cpp| 28 +++
 clang/lib/Sema/SemaCodeComplete.cpp   |  8 ++
 .../skip-explicit-object-parameter.cpp| 24 
 3 files changed, 54 insertions(+), 6 deletions(-)

diff --git a/clang-tools-extra/clangd/unittests/CodeCompleteTests.cpp 
b/clang-tools-extra/clangd/unittests/CodeCompleteTests.cpp
index b7c64c7a06745..b18d712ee9aef 100644
--- a/clang-tools-extra/clangd/unittests/CodeCompleteTests.cpp
+++ b/clang-tools-extra/clangd/unittests/CodeCompleteTests.cpp
@@ -3266,6 +3266,34 @@ TEST(SignatureHelpTest, VariadicType) {
   }
 }
 
+TEST(SignatureHelpTest, SkipExplicitObjectParameter) {
+  Annotations Code(R"cpp(
+struct A {
+  void foo(this auto&& self, int arg); 
+};
+int main() {
+  A a {};
+  a.foo(^);
+}
+  )cpp");
+
+  auto TU = TestTU::withCode(Code.code());
+  TU.ExtraArgs = {"-std=c++23"};
+
+  MockFS FS;
+  auto Inputs = TU.inputs(FS);
+
+  auto Preamble = TU.preamble();
+  ASSERT_TRUE(Preamble);
+
+  const auto Result = signatureHelp(testPath(TU.Filename), Code.point(),
+*Preamble, Inputs, MarkupKind::PlainText);
+
+  EXPECT_EQ(1, Result.signatures.size());
+
+  EXPECT_THAT(Result.signatures[0], AllOf(sig("foo([[int arg]]) -> void")));
+}
+
 TEST(CompletionTest, IncludedCompletionKinds) {
   Annotations Test(R"cpp(#include "^)cpp");
   auto TU = TestTU::withCode(Test.code());
diff --git a/clang/lib/Sema/SemaCodeComplete.cpp 
b/clang/lib/Sema/SemaCodeComplete.cpp
index b5d4a94da83df..0077cf05bd5b0 100644
--- a/clang/lib/Sema/SemaCodeComplete.cpp
+++ b/clang/lib/Sema/SemaCodeComplete.cpp
@@ -4034,6 +4034,14 @@ static void AddOverloadParameterChunks(
   return;
 }
 
+// C++23 introduces an explicit object parameter, a.k.a. "deducing this"
+// Skip it for autocomplete and treat the next parameter as the first
+// parameter
+if (Function && FirstParameter &&
+Function->getParamDecl(P)->isExplicitObjectParameter()) {
+  continue;
+}
+
 if (FirstParameter)
   FirstParameter = false;
 else
diff --git a/clang/test/CodeCompletion/skip-explicit-object-parameter.cpp 
b/clang/test/CodeCompletion/skip-explicit-object-parameter.cpp
index 55c16bb126fee..0eb71dce95849 100644
--- a/clang/test/CodeCompletion/skip-explicit-object-parameter.cpp
+++ b/clang/test/CodeCompletion/skip-explicit-object-parameter.cpp
@@ -6,9 +6,21 @@ int main() {
   A a {};
   a.
 }
-// RUN: %clang_cc1 -cc1 -fsyntax-only -code-completion-at=%s:%(line-2):5 
-std=c++23 %s | FileCheck %s
-// CHECK: COMPLETION: A : A::
-// CHECK-NEXT: COMPLETION: foo : [#void#]foo(<#int arg#>)
-// CHECK-NEXT: COMPLETION: operator= : [#A &#]operator=(<#const A &#>)
-// CHECK-NEXT: COMPLETION: operator= : [#A &#]operator=(<#A &&#>)
-// CHECK-NEXT: COMPLETION: ~A : [#void#]~A()
+// RUN: %clang_cc1 -cc1 -fsyntax-only -code-completion-at=%s:%(line-2):5 
-std=c++23 %s | FileCheck -check-prefix=CHECK-CC1 %s
+// CHECK-CC1: COMPLETION: A : A::
+// CHECK-NEXT-CC1: COMPLETION: foo : [#void#]foo(<#int arg#>)
+// CHECK-NEXT-CC1: COMPLETION: operator= : [#A &#]operator=(<#const A &#>)
+// CHECK-NEXT-CC1: COMPLETION: operator= : [#A &#]operator=(<#A &&#>)
+// CHECK-NEXT-CC1: COMPLETION: ~A : [#void#]~A()
+
+struct B {
+  template 
+  void foo(this T&& self, int arg);
+};
+
+int main2() {
+  B b {};
+  b.foo();
+}
+// RUN: %clang_cc1 -cc1 -fsyntax-only -code-completion-at=%s:%(line-2):9 
-std=c++23 %s | FileCheck -check-prefix=CHECK-CC2 %s
+// CHECK-CC2: OVERLOAD: [#void#]foo(int arg)

>From a7fae2277ea9267f65ecdfaf05c4b79bcc7a44c4 Mon Sep 17 00:00:00 2001
From: Mythreya Kuricheti 
Date: Thu, 3 Jul 2025 02:27:05 -0700
Subject: [PATCH 2/2] Update tests from code review

---
 .../clangd/unittests/CodeCompleteTests.cpp| 52 ++-
 .../skip-explicit-object-parameter.cpp| 26 --
 2 files changed, 61 insertions(+), 17 deletions(-)

diff --git a/clang-tools-extra/clangd/unittests/CodeCompleteTests.cpp 
b/clang-tools-extra/clangd/unittests/CodeCompleteTests.cpp
index b18d712ee9aef..5912937e2c80f 100644
--- a/clang-tools-extra/clangd/unittests/CodeCompleteTests.cpp
+++ b/clang-tools-extra/clangd/unittests/CodeCompleteTests.cpp
@@ -3270,10 +3270,13 @@ TEST(SignatureHelpTest, SkipExplicitObjectParameter) {
   Annotations Code(R"cpp(
 struct A {
   void foo(this auto&& self, int arg); 
+  void bar(this A self, int arg);
 };
 int main() {
   A a {};
-  a.foo(^);
+  a.foo($c1^);
+  (&A::bar)($c2^);
+  // TODO: (&A::foo)(^c3)
 }
   )cpp");
 
@@ -3286,12 +3289,22 @@ TEST(SignatureHelpTest, SkipExplicitObjectPara

[clang] [clang-tools-extra] [clang][CodeComplete] skip explicit obj param in SignatureHelp (PR #146649)

2025-07-03 Thread Mythreya Kuricheti via cfe-commits


@@ -1,14 +1,42 @@
 struct A {
-  void foo(this A self, int arg);
+  void foo(this auto&& self, int arg);
+  void bar(this A self, int arg);
 };
 
-int main() {
+int func1() {
   A a {};
   a.
 }
-// RUN: %clang_cc1 -cc1 -fsyntax-only -code-completion-at=%s:%(line-2):5 
-std=c++23 %s | FileCheck %s
-// CHECK: COMPLETION: A : A::
-// CHECK-NEXT: COMPLETION: foo : [#void#]foo(<#int arg#>)
-// CHECK-NEXT: COMPLETION: operator= : [#A &#]operator=(<#const A &#>)
-// CHECK-NEXT: COMPLETION: operator= : [#A &#]operator=(<#A &&#>)
-// CHECK-NEXT: COMPLETION: ~A : [#void#]~A()
+// RUN: %clang_cc1 -fsyntax-only -code-completion-at=%s:%(line-2):5 -std=c++23 
%s | FileCheck -check-prefix=CHECK-CC1 %s
+// CHECK-CC1: COMPLETION: A : A::
+// CHECK-NEXT-CC1: COMPLETION: bar : [#void#]bar(<#int arg#>)
+// CHECK-NEXT-CC1: COMPLETION: foo : [#void#]foo(<#int arg#>)
+// CHECK-NEXT-CC1: COMPLETION: operator= : [#A &#]operator=(<#const A &#>)
+// CHECK-NEXT-CC1: COMPLETION: operator= : [#A &#]operator=(<#A &&#>)
+// CHECK-NEXT-CC1: COMPLETION: ~A : [#void#]~A()
+
+struct B {
+  template 
+  void foo(this T&& self, int arg);
+};
+
+int func2() {
+  B b {};
+  b.foo();
+}
+// RUN: %clang_cc1 -fsyntax-only -code-completion-at=%s:%(line-2):9 -std=c++23 
%s | FileCheck -check-prefix=CHECK-CC2 %s
+// CHECK-CC2: OVERLOAD: [#void#]foo(int arg)

MythreyaK wrote:

My current understanding is that this line checks that the given overload 
exists, but not that other overloads do not. Do I need to ensure that this is 
the only overload?



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


[clang] [clang-tools-extra] [clang][CodeComplete] skip explicit obj param in SignatureHelp (PR #146649)

2025-07-02 Thread Mythreya Kuricheti via cfe-commits

MythreyaK wrote:

Seems to be working as expected. I'll add a test case for this as well. 

![image](https://github.com/user-attachments/assets/f736c68f-a64d-4af6-876a-d647d0d6541e)
![image](https://github.com/user-attachments/assets/e40ee898-a161-4564-869c-b566e7b3452b)


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


[clang] [clang-tools-extra] [clang][CodeComplete] skip explicit obj param in SignatureHelp (PR #146649)

2025-07-03 Thread Mythreya Kuricheti via cfe-commits

MythreyaK wrote:

The completion for `(&A::foo2)` is just `(A, int)`, not `foo(A, int)`. I tried 
to add a test case, like in this [godbolt](https://godbolt.org/z/77zE7e3oE) 
example, 

```cpp
struct A {
void foo1(this A self, int arg) {}
template 
void foo2(this T&& self, int arg, float arg2) {}
};

int main() {
A a {};
(&A::foo1)(a, 1);
(&A::foo2)(a, 1, 3.4); // possible?
// (&A::foo2)(a, 1 /* , 3.4*/); // causes a compiler crash
return 0;
}
```

but causes a crash ([example](https://godbolt.org/z/oo198z8Gh)). So I haven't 
added those cases, but left a `TODO`. Should I leave a `TODO: PR 146649` 
instead?



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


[clang] [clang-tools-extra] [clang][CodeComplete] skip explicit obj param in SignatureHelp (PR #146649)

2025-07-02 Thread Mythreya Kuricheti via cfe-commits

MythreyaK wrote:

> How does completion handle things like this?

@cor3ntin Oh I totally forgot about this! Thanks! I'll check it in the evening.

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


[clang] [clang-tools-extra] [clang][CodeComplete] skip explicit obj param in SignatureHelp (PR #146649)

2025-07-02 Thread Mythreya Kuricheti via cfe-commits

https://github.com/MythreyaK updated 
https://github.com/llvm/llvm-project/pull/146649

>From 7f8581f01c3c25363b77100635c6df7223badba3 Mon Sep 17 00:00:00 2001
From: Mythreya Kuricheti 
Date: Wed, 2 Jul 2025 01:26:25 -0700
Subject: [PATCH] [clang][CodeComplete] skip explicit obj param in
 SignatureHelp

---
 .../clangd/unittests/CodeCompleteTests.cpp| 28 +++
 clang/lib/Sema/SemaCodeComplete.cpp   |  8 ++
 .../skip-explicit-object-parameter.cpp| 24 
 3 files changed, 54 insertions(+), 6 deletions(-)

diff --git a/clang-tools-extra/clangd/unittests/CodeCompleteTests.cpp 
b/clang-tools-extra/clangd/unittests/CodeCompleteTests.cpp
index b7c64c7a06745..b18d712ee9aef 100644
--- a/clang-tools-extra/clangd/unittests/CodeCompleteTests.cpp
+++ b/clang-tools-extra/clangd/unittests/CodeCompleteTests.cpp
@@ -3266,6 +3266,34 @@ TEST(SignatureHelpTest, VariadicType) {
   }
 }
 
+TEST(SignatureHelpTest, SkipExplicitObjectParameter) {
+  Annotations Code(R"cpp(
+struct A {
+  void foo(this auto&& self, int arg); 
+};
+int main() {
+  A a {};
+  a.foo(^);
+}
+  )cpp");
+
+  auto TU = TestTU::withCode(Code.code());
+  TU.ExtraArgs = {"-std=c++23"};
+
+  MockFS FS;
+  auto Inputs = TU.inputs(FS);
+
+  auto Preamble = TU.preamble();
+  ASSERT_TRUE(Preamble);
+
+  const auto Result = signatureHelp(testPath(TU.Filename), Code.point(),
+*Preamble, Inputs, MarkupKind::PlainText);
+
+  EXPECT_EQ(1, Result.signatures.size());
+
+  EXPECT_THAT(Result.signatures[0], AllOf(sig("foo([[int arg]]) -> void")));
+}
+
 TEST(CompletionTest, IncludedCompletionKinds) {
   Annotations Test(R"cpp(#include "^)cpp");
   auto TU = TestTU::withCode(Test.code());
diff --git a/clang/lib/Sema/SemaCodeComplete.cpp 
b/clang/lib/Sema/SemaCodeComplete.cpp
index b5d4a94da83df..0077cf05bd5b0 100644
--- a/clang/lib/Sema/SemaCodeComplete.cpp
+++ b/clang/lib/Sema/SemaCodeComplete.cpp
@@ -4034,6 +4034,14 @@ static void AddOverloadParameterChunks(
   return;
 }
 
+// C++23 introduces an explicit object parameter, a.k.a. "deducing this"
+// Skip it for autocomplete and treat the next parameter as the first
+// parameter
+if (Function && FirstParameter &&
+Function->getParamDecl(P)->isExplicitObjectParameter()) {
+  continue;
+}
+
 if (FirstParameter)
   FirstParameter = false;
 else
diff --git a/clang/test/CodeCompletion/skip-explicit-object-parameter.cpp 
b/clang/test/CodeCompletion/skip-explicit-object-parameter.cpp
index 55c16bb126fee..0eb71dce95849 100644
--- a/clang/test/CodeCompletion/skip-explicit-object-parameter.cpp
+++ b/clang/test/CodeCompletion/skip-explicit-object-parameter.cpp
@@ -6,9 +6,21 @@ int main() {
   A a {};
   a.
 }
-// RUN: %clang_cc1 -cc1 -fsyntax-only -code-completion-at=%s:%(line-2):5 
-std=c++23 %s | FileCheck %s
-// CHECK: COMPLETION: A : A::
-// CHECK-NEXT: COMPLETION: foo : [#void#]foo(<#int arg#>)
-// CHECK-NEXT: COMPLETION: operator= : [#A &#]operator=(<#const A &#>)
-// CHECK-NEXT: COMPLETION: operator= : [#A &#]operator=(<#A &&#>)
-// CHECK-NEXT: COMPLETION: ~A : [#void#]~A()
+// RUN: %clang_cc1 -cc1 -fsyntax-only -code-completion-at=%s:%(line-2):5 
-std=c++23 %s | FileCheck -check-prefix=CHECK-CC1 %s
+// CHECK-CC1: COMPLETION: A : A::
+// CHECK-NEXT-CC1: COMPLETION: foo : [#void#]foo(<#int arg#>)
+// CHECK-NEXT-CC1: COMPLETION: operator= : [#A &#]operator=(<#const A &#>)
+// CHECK-NEXT-CC1: COMPLETION: operator= : [#A &#]operator=(<#A &&#>)
+// CHECK-NEXT-CC1: COMPLETION: ~A : [#void#]~A()
+
+struct B {
+  template 
+  void foo(this T&& self, int arg);
+};
+
+int main2() {
+  B b {};
+  b.foo();
+}
+// RUN: %clang_cc1 -cc1 -fsyntax-only -code-completion-at=%s:%(line-2):9 
-std=c++23 %s | FileCheck -check-prefix=CHECK-CC2 %s
+// CHECK-CC2: OVERLOAD: [#void#]foo(int arg)

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


[clang] [clang-tools-extra] [clang][CodeComplete] skip explicit obj param in SignatureHelp (PR #146649)

2025-07-02 Thread Mythreya Kuricheti via cfe-commits

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