llvm-project
146 строк · 5.0 Кб
1//===- unittests/AST/ASTDumperTest.cpp --- Test of AST node dump() methods ===//
2//
3// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4// See https://llvm.org/LICENSE.txt for license information.
5// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6//
7//===----------------------------------------------------------------------===//
8//
9// This file contains tests for TypeLoc::dump() and related methods.
10// Most of these are lit tests via clang -ast-dump. However some nodes are not
11// included in dumps of (TranslationUnit)Decl, but still relevant when dumped
12// directly.
13//
14//===----------------------------------------------------------------------===//
15
16#include "ASTPrint.h"17#include "clang/AST/ASTContext.h"18#include "clang/AST/Decl.h"19#include "clang/Testing/TestAST.h"20#include "llvm/ADT/StringRef.h"21#include "gmock/gmock.h"22#include "gtest/gtest.h"23
24using namespace clang;25using namespace ast_matchers;26
27namespace {28using testing::ElementsAre;29using testing::StartsWith;30
31std::vector<std::string> dumpTypeLoc(llvm::StringRef Name, ASTContext &Ctx) {32auto Lookup = Ctx.getTranslationUnitDecl()->lookup(&Ctx.Idents.get(Name));33DeclaratorDecl *D = nullptr;34if ((D = Lookup.find_first<DeclaratorDecl>()))35;36else if (auto *TD = Lookup.find_first<FunctionTemplateDecl>())37D = TD->getTemplatedDecl();38EXPECT_NE(D, nullptr) << Name;39if (!D)40return {};41EXPECT_NE(D->getTypeSourceInfo(), nullptr);42if (!D->getTypeSourceInfo())43return {};44std::string S;45{46llvm::raw_string_ostream OS(S);47D->getTypeSourceInfo()->getTypeLoc().dump(OS, Ctx);48}49// Split result into lines.50std::vector<std::string> Result;51auto Remaining = llvm::StringRef(S).trim("\n");52while (!Remaining.empty()) {53auto [First, Rest] = Remaining.split('\n');54Result.push_back(First.str());55Remaining = Rest;56}57return Result;58}
59
60TEST(ASTDumper, TypeLocChain) {61TestAST AST(R"cc(62const int **x;
63)cc");64EXPECT_THAT(65dumpTypeLoc("x", AST.context()),66ElementsAre(""67"PointerTypeLoc <input.mm:2:11, col:16> 'const int **'",68"`-PointerTypeLoc <col:11, col:15> 'const int *'",69" `-QualifiedTypeLoc <col:11> 'const int'",70" `-BuiltinTypeLoc <col:11> 'int'"));71}
72
73TEST(ASTDumper, AutoType) {74TestInputs Inputs(R"cc(75template <class, class> concept C = true;
76C<int> auto str1 = "hello";
77auto str2 = "hello";
78)cc");79Inputs.ExtraArgs.push_back("-std=c++20");80TestAST AST(Inputs);81EXPECT_THAT(82dumpTypeLoc("str1", AST.context()),83ElementsAre(""84"AutoTypeLoc <input.mm:3:5, col:12> 'C<int> auto' undeduced",85StartsWith("|-Concept"), //86"`-TemplateArgument <col:7> type 'int'",87StartsWith(" `-BuiltinType")));88EXPECT_THAT(dumpTypeLoc("str2", AST.context()),89ElementsAre(""90"AutoTypeLoc <input.mm:4:5> 'auto' undeduced"));91}
92
93
94TEST(ASTDumper, FunctionTypeLoc) {95TestAST AST(R"cc(96void x(int, double *y);
97
98auto trailing() -> int;
99
100template <class T> int tmpl(T&&);
101)cc");102EXPECT_THAT(103dumpTypeLoc("x", AST.context()),104ElementsAre(""105"FunctionProtoTypeLoc <input.mm:2:5, col:26> 'void (int, "106"double *)' cdecl",107StartsWith("|-ParmVarDecl"),108"| `-BuiltinTypeLoc <col:12> 'int'",109StartsWith("|-ParmVarDecl"),110"| `-PointerTypeLoc <col:17, col:24> 'double *'",111"| `-BuiltinTypeLoc <col:17> 'double'",112"`-BuiltinTypeLoc <col:5> 'void'"));113
114EXPECT_THAT(dumpTypeLoc("trailing", AST.context()),115ElementsAre(""116"FunctionProtoTypeLoc <input.mm:4:5, col:24> "117"'auto () -> int' trailing_return cdecl",118"`-BuiltinTypeLoc <col:24> 'int'"));119
120EXPECT_THAT(121dumpTypeLoc("tmpl", AST.context()),122ElementsAre(""123"FunctionProtoTypeLoc <input.mm:6:24, col:36> "124"'int (T &&)' cdecl",125StartsWith("|-ParmVarDecl"),126"| `-RValueReferenceTypeLoc <col:33, col:34> 'T &&'",127"| `-TemplateTypeParmTypeLoc <col:33> 'T' depth 0 index 0",128StartsWith("| `-TemplateTypeParm"),129"`-BuiltinTypeLoc <col:24> 'int'"));130
131// Dynamic-exception-spec needs C++14 or earlier.132TestInputs Throws(R"cc(133void throws() throw(int);
134)cc");135Throws.ExtraArgs.push_back("-std=c++14");136AST = TestAST(Throws);137EXPECT_THAT(dumpTypeLoc("throws", AST.context()),138ElementsAre(""139"FunctionProtoTypeLoc <input.mm:2:5, col:28> "140"'void () throw(int)' exceptionspec_dynamic cdecl",141// FIXME: include TypeLoc for int142"|-Exceptions: 'int'",143"`-BuiltinTypeLoc <col:5> 'void'"));144}
145
146} // namespace147