[clang-tools-extra] [clangd] Don't show inlay hints for PseudoObjectExprs in C++ (PR #71366)

Younan Zhang via cfe-commits cfe-commits at lists.llvm.org
Mon Nov 6 01:33:53 PST 2023


https://github.com/zyn0217 updated https://github.com/llvm/llvm-project/pull/71366

>From 4a878b63cbdd33833b998896120a992178438180 Mon Sep 17 00:00:00 2001
From: Younan Zhang <zyn7109 at gmail.com>
Date: Mon, 6 Nov 2023 16:50:02 +0800
Subject: [PATCH 1/2] [clangd] Don't show inlay hints for PseudoObjectExprs in
 C++

This closes https://github.com/clangd/clangd/issues/1813.

PseudoObjectExprs in C++ are currently not very interesting but probably
mess up inlay hints.
---
 clang-tools-extra/clangd/InlayHints.cpp       | 13 ++++++++++
 .../clangd/unittests/InlayHintTests.cpp       | 24 +++++++++++++++++++
 2 files changed, 37 insertions(+)

diff --git a/clang-tools-extra/clangd/InlayHints.cpp b/clang-tools-extra/clangd/InlayHints.cpp
index 3da047f95421385..867c70e5dbc80c6 100644
--- a/clang-tools-extra/clangd/InlayHints.cpp
+++ b/clang-tools-extra/clangd/InlayHints.cpp
@@ -589,6 +589,19 @@ class InlayHintVisitor : public RecursiveASTVisitor<InlayHintVisitor> {
     return true;
   }
 
+  bool dataTraverseStmtPre(Stmt *S) {
+    // Do not show inlay hints for PseudoObjectExprs. They're never
+    // genuine user codes in C++.
+    //
+    // For example, __builtin_dump_struct would expand to a PseudoObjectExpr
+    // that includes a couple of calls to a printf function. Printing parameter
+    // names for that anyway would end up with duplicate parameter names (which,
+    // however, got de-duplicated after visiting) for the printf function.
+    if (AST.getLangOpts().CPlusPlus && isa<PseudoObjectExpr>(S))
+      return false;
+    return true;
+  }
+
   bool VisitCallExpr(CallExpr *E) {
     if (!Cfg.InlayHints.Parameters)
       return true;
diff --git a/clang-tools-extra/clangd/unittests/InlayHintTests.cpp b/clang-tools-extra/clangd/unittests/InlayHintTests.cpp
index 20c1cdd985dbc01..2b6c27b17b537a9 100644
--- a/clang-tools-extra/clangd/unittests/InlayHintTests.cpp
+++ b/clang-tools-extra/clangd/unittests/InlayHintTests.cpp
@@ -1724,6 +1724,30 @@ TEST(InlayHints, RestrictRange) {
               ElementsAre(labelIs(": int"), labelIs(": char")));
 }
 
+TEST(ParameterHints, PseudoObjectExpr) {
+  Annotations Code(R"cpp(
+    struct S {
+      __declspec(property(get=GetX, put=PutX)) int x[];
+      int GetX(int y, int z) { return 42 + y; }
+      void PutX(int y) { x = y; } // Not `x = y: y`
+    };
+
+    int printf(const char *Format, ...);
+
+    int main() {
+      S s;
+      __builtin_dump_struct(&s, printf); // Not `Format: __builtin_dump_struct()`
+      printf($Param[["Hello, %d"]], 42); // Normal calls are not affected.
+      return s.x[1][2]; // Not `x[y: 1][z: 2]`
+    }
+  )cpp");
+  auto TU = TestTU::withCode(Code.code());
+  TU.ExtraArgs.push_back("-fms-extensions");
+  auto AST = TU.build();
+  EXPECT_THAT(inlayHints(AST, std::nullopt),
+              ElementsAre(HintMatcher(ExpectedHint{"Format: ", "Param"}, Code)));
+}
+
 TEST(ParameterHints, ArgPacksAndConstructors) {
   assertParameterHints(
       R"cpp(

>From 240b7f89e9bc9eb57f35f43be2f971b4fde76b46 Mon Sep 17 00:00:00 2001
From: Younan Zhang <zyn7109 at gmail.com>
Date: Mon, 6 Nov 2023 17:32:50 +0800
Subject: [PATCH 2/2] Don't make the patch C++-specific

---
 clang-tools-extra/clangd/InlayHints.cpp | 4 ++--
 1 file changed, 2 insertions(+), 2 deletions(-)

diff --git a/clang-tools-extra/clangd/InlayHints.cpp b/clang-tools-extra/clangd/InlayHints.cpp
index 867c70e5dbc80c6..1b54b570c1c5d4f 100644
--- a/clang-tools-extra/clangd/InlayHints.cpp
+++ b/clang-tools-extra/clangd/InlayHints.cpp
@@ -591,13 +591,13 @@ class InlayHintVisitor : public RecursiveASTVisitor<InlayHintVisitor> {
 
   bool dataTraverseStmtPre(Stmt *S) {
     // Do not show inlay hints for PseudoObjectExprs. They're never
-    // genuine user codes in C++.
+    // genuine user codes.
     //
     // For example, __builtin_dump_struct would expand to a PseudoObjectExpr
     // that includes a couple of calls to a printf function. Printing parameter
     // names for that anyway would end up with duplicate parameter names (which,
     // however, got de-duplicated after visiting) for the printf function.
-    if (AST.getLangOpts().CPlusPlus && isa<PseudoObjectExpr>(S))
+    if (isa<PseudoObjectExpr>(S))
       return false;
     return true;
   }



More information about the cfe-commits mailing list