kadircet created this revision. kadircet added reviewers: sammccall, ilya-biryukov. Herald added subscribers: cfe-commits, usaxena95, arphaman, jkorous, MaskRay. Herald added a project: clang.
Default args might exist but be unparsed or uninstantiated. getDefaultArg asserts on those. This patch makes sure we don't crash in such scenarios. Repository: rG LLVM Github Monorepo https://reviews.llvm.org/D73723 Files: clang-tools-extra/clangd/Hover.cpp clang-tools-extra/clangd/unittests/HoverTests.cpp Index: clang-tools-extra/clangd/unittests/HoverTests.cpp =================================================================== --- clang-tools-extra/clangd/unittests/HoverTests.cpp +++ clang-tools-extra/clangd/unittests/HoverTests.cpp @@ -1609,6 +1609,22 @@ HI.Type = "unsigned long"; HI.Value = "1"; }}, + { + R"cpp( + template <typename T = int> + void foo(const T& = T()) { + [[f^oo]]<>(3); + })cpp", + [](HoverInfo &HI) { + HI.Name = "foo"; + HI.Kind = index::SymbolKind::Function; + HI.Type = "void (const int &)"; + HI.ReturnType = "void"; + HI.Parameters = { + {std::string("const int &"), llvm::None, std::string("T()")}}; + HI.Definition = "template <> void foo<int>(const int &)"; + HI.NamespaceScope = ""; + }}, }; // Create a tiny index, so tests above can verify documentation is fetched. Index: clang-tools-extra/clangd/Hover.cpp =================================================================== --- clang-tools-extra/clangd/Hover.cpp +++ clang-tools-extra/clangd/Hover.cpp @@ -269,10 +269,17 @@ } if (!PVD->getName().empty()) P.Name = PVD->getNameAsString(); - if (PVD->hasDefaultArg()) { + // Default argument can be unparsed or uninstatiated. For the former we + // can't do much as token information is only stored in Sema and not + // attached to the AST node. For the latter though, it is safe to proceed as + // we only print the expression. + if (PVD->hasDefaultArg() && !PVD->hasUnparsedDefaultArg()) { P.Default.emplace(); llvm::raw_string_ostream Out(*P.Default); - PVD->getDefaultArg()->printPretty(Out, nullptr, Policy); + const Expr *Init = PVD->hasUninstantiatedDefaultArg() + ? PVD->getUninstantiatedDefaultArg() + : PVD->getDefaultArg(); + Init->printPretty(Out, nullptr, Policy); } }
Index: clang-tools-extra/clangd/unittests/HoverTests.cpp =================================================================== --- clang-tools-extra/clangd/unittests/HoverTests.cpp +++ clang-tools-extra/clangd/unittests/HoverTests.cpp @@ -1609,6 +1609,22 @@ HI.Type = "unsigned long"; HI.Value = "1"; }}, + { + R"cpp( + template <typename T = int> + void foo(const T& = T()) { + [[f^oo]]<>(3); + })cpp", + [](HoverInfo &HI) { + HI.Name = "foo"; + HI.Kind = index::SymbolKind::Function; + HI.Type = "void (const int &)"; + HI.ReturnType = "void"; + HI.Parameters = { + {std::string("const int &"), llvm::None, std::string("T()")}}; + HI.Definition = "template <> void foo<int>(const int &)"; + HI.NamespaceScope = ""; + }}, }; // Create a tiny index, so tests above can verify documentation is fetched. Index: clang-tools-extra/clangd/Hover.cpp =================================================================== --- clang-tools-extra/clangd/Hover.cpp +++ clang-tools-extra/clangd/Hover.cpp @@ -269,10 +269,17 @@ } if (!PVD->getName().empty()) P.Name = PVD->getNameAsString(); - if (PVD->hasDefaultArg()) { + // Default argument can be unparsed or uninstatiated. For the former we + // can't do much as token information is only stored in Sema and not + // attached to the AST node. For the latter though, it is safe to proceed as + // we only print the expression. + if (PVD->hasDefaultArg() && !PVD->hasUnparsedDefaultArg()) { P.Default.emplace(); llvm::raw_string_ostream Out(*P.Default); - PVD->getDefaultArg()->printPretty(Out, nullptr, Policy); + const Expr *Init = PVD->hasUninstantiatedDefaultArg() + ? PVD->getUninstantiatedDefaultArg() + : PVD->getDefaultArg(); + Init->printPretty(Out, nullptr, Policy); } }
_______________________________________________ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits