12#include "clang/AST/ASTContext.h"
13#include "clang/AST/Decl.h"
14#include "clang/Sema/CodeCompleteConsumer.h"
15#include "llvm/ADT/StringRef.h"
16#include "gmock/gmock.h"
17#include "gtest/gtest.h"
24using ::testing::Field;
25using ::testing::Matcher;
26using ::testing::SizeIs;
27using ::testing::UnorderedElementsAreArray;
29class ExpectedTypeConversionTest :
public ::testing::Test {
31 void build(llvm::StringRef Code) {
32 assert(!AST &&
"AST built twice");
36 const NamedDecl *decl(llvm::StringRef Name) {
return &
findDecl(*AST, Name); }
38 QualType typeOf(llvm::StringRef Name) {
39 return cast<ValueDecl>(decl(Name))->getType().getCanonicalType();
43 std::optional<OpaqueType> fromCompletionResult(
const NamedDecl *D) {
45 astCtx(), CodeCompletionResult(D, CCP_Declaration));
50 using EquivClass = std::set<std::string>;
52 Matcher<std::map<std::string, EquivClass>>
53 classesAre(llvm::ArrayRef<EquivClass> Classes) {
54 using MapEntry = std::map<std::string, EquivClass>::value_type;
56 std::vector<Matcher<MapEntry>> Elements;
57 Elements.reserve(Classes.size());
58 for (
auto &Cls : Classes)
59 Elements.push_back(
Field(&MapEntry::second, Cls));
60 return UnorderedElementsAreArray(Elements);
65 std::map<std::string, EquivClass>
66 buildEquivClasses(llvm::ArrayRef<llvm::StringRef> DeclNames) {
67 std::map<std::string, EquivClass> Classes;
68 for (llvm::StringRef Name : DeclNames) {
70 Classes[std::string(
Type->raw())].insert(std::string(Name));
75 ASTContext &astCtx() {
return AST->getASTContext(); }
79 std::optional<ParsedAST> AST;
82TEST_F(ExpectedTypeConversionTest, BasicTypes) {
98 // user-defined types.
103 EXPECT_THAT(buildEquivClasses({"b",
"i",
"ui",
"ll",
"f",
"d",
"iptr",
"bptr",
113TEST_F(ExpectedTypeConversionTest, ReferencesDontMatter) {
117 const int & const_ref = noref;
121 EXPECT_THAT(buildEquivClasses({"noref",
"ref",
"const_ref",
"rv_ref"}),
125TEST_F(ExpectedTypeConversionTest, ArraysDecay) {
128 int (&arr_ref)[2] = arr;
132 EXPECT_THAT(buildEquivClasses({"arr",
"arr_ref",
"ptr"}), SizeIs(1));
135TEST_F(ExpectedTypeConversionTest, FunctionReturns) {
145 EXPECT_EQ(fromCompletionResult(decl(
"returns_int")), IntTy);
148 EXPECT_EQ(fromCompletionResult(decl(
"returns_ptr")), IntPtrTy);
151TEST_F(ExpectedTypeConversionTest, Templates) {
154int* returns_not_dependent();
156T* returns_dependent();
159int* var_not_dependent = nullptr;
161T* var_dependent = nullptr;
167 EXPECT_EQ(fromCompletionResult(decl(
"returns_not_dependent")), IntPtrTy);
168 EXPECT_EQ(fromCompletionResult(decl(
"returns_dependent")), std::nullopt);
170 EXPECT_EQ(fromCompletionResult(decl(
"var_not_dependent")), IntPtrTy);
171 EXPECT_EQ(fromCompletionResult(decl(
"var_dependent")), std::nullopt);
A representation of a type that can be computed based on clang AST and compared for equality.
static std::optional< OpaqueType > fromCompletionResult(ASTContext &Ctx, const CodeCompletionResult &R)
Create a type from a code completion result.
static std::optional< OpaqueType > fromType(ASTContext &Ctx, QualType Type)
Construct an instance from a clang::QualType.
FIXME: Skip testing on windows temporarily due to the different escaping code mode.
TEST_F(BackgroundIndexTest, NoCrashOnErrorFile)
const NamedDecl & findDecl(ParsedAST &AST, llvm::StringRef QName)
@ Type
An inlay hint that for a type annotation.
===– Representation.cpp - ClangDoc Representation --------—*- C++ -*-===//
static TestTU withCode(llvm::StringRef Code)