1 //===- unittest/Format/TokenAnnotatorTest.cpp - Formatting unit tests -----===// 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 #include "clang/Format/Format.h" 10 11 #include "FormatTestUtils.h" 12 #include "TestLexer.h" 13 #include "gtest/gtest.h" 14 15 namespace clang { 16 namespace format { 17 18 // Not really the equality, but everything we need. 19 static bool operator==(const FormatToken &LHS, 20 const FormatToken &RHS) noexcept { 21 return LHS.Tok.getKind() == RHS.Tok.getKind() && 22 LHS.getType() == RHS.getType(); 23 } 24 25 namespace { 26 27 class TokenAnnotatorTest : public ::testing::Test { 28 protected: 29 TokenList annotate(llvm::StringRef Code, 30 const FormatStyle &Style = getLLVMStyle()) { 31 return TestLexer(Allocator, Buffers, Style).annotate(Code); 32 } 33 llvm::SpecificBumpPtrAllocator<FormatToken> Allocator; 34 std::vector<std::unique_ptr<llvm::MemoryBuffer>> Buffers; 35 }; 36 37 #define EXPECT_TOKEN_KIND(FormatTok, Kind) \ 38 EXPECT_EQ((FormatTok)->Tok.getKind(), Kind) << *(FormatTok) 39 #define EXPECT_TOKEN_TYPE(FormatTok, Type) \ 40 EXPECT_EQ((FormatTok)->getType(), Type) << *(FormatTok) 41 #define EXPECT_TOKEN(FormatTok, Kind, Type) \ 42 do { \ 43 EXPECT_TOKEN_KIND(FormatTok, Kind); \ 44 EXPECT_TOKEN_TYPE(FormatTok, Type); \ 45 } while (false) 46 47 TEST_F(TokenAnnotatorTest, UnderstandsUsesOfStarAndAmpInMacroDefinition) { 48 // This is a regression test for mis-parsing the & after decltype as a binary 49 // operator instead of a reference (when inside a macro definition). 50 auto Tokens = annotate("auto x = [](const decltype(x) &ptr) {};"); 51 EXPECT_EQ(Tokens.size(), 18u) << Tokens; 52 EXPECT_TOKEN(Tokens[7], tok::kw_decltype, TT_Unknown); 53 EXPECT_TOKEN(Tokens[8], tok::l_paren, TT_TypeDeclarationParen); 54 EXPECT_TOKEN(Tokens[9], tok::identifier, TT_Unknown); 55 EXPECT_TOKEN(Tokens[10], tok::r_paren, TT_TypeDeclarationParen); 56 EXPECT_TOKEN(Tokens[11], tok::amp, TT_PointerOrReference); 57 // Same again with * instead of &: 58 Tokens = annotate("auto x = [](const decltype(x) *ptr) {};"); 59 EXPECT_EQ(Tokens.size(), 18u) << Tokens; 60 EXPECT_TOKEN(Tokens[10], tok::r_paren, TT_TypeDeclarationParen); 61 EXPECT_TOKEN(Tokens[11], tok::star, TT_PointerOrReference); 62 63 // Also check that we parse correctly within a macro definition: 64 Tokens = annotate("#define lambda [](const decltype(x) &ptr) {}"); 65 EXPECT_EQ(Tokens.size(), 17u) << Tokens; 66 EXPECT_TOKEN(Tokens[7], tok::kw_decltype, TT_Unknown); 67 EXPECT_TOKEN(Tokens[8], tok::l_paren, TT_TypeDeclarationParen); 68 EXPECT_TOKEN(Tokens[9], tok::identifier, TT_Unknown); 69 EXPECT_TOKEN(Tokens[10], tok::r_paren, TT_TypeDeclarationParen); 70 EXPECT_TOKEN(Tokens[11], tok::amp, TT_PointerOrReference); 71 // Same again with * instead of &: 72 Tokens = annotate("#define lambda [](const decltype(x) *ptr) {}"); 73 EXPECT_EQ(Tokens.size(), 17u) << Tokens; 74 EXPECT_TOKEN(Tokens[10], tok::r_paren, TT_TypeDeclarationParen); 75 EXPECT_TOKEN(Tokens[11], tok::star, TT_PointerOrReference); 76 } 77 78 TEST_F(TokenAnnotatorTest, UnderstandsClasses) { 79 auto Tokens = annotate("class C {};"); 80 EXPECT_EQ(Tokens.size(), 6u) << Tokens; 81 EXPECT_TOKEN(Tokens[2], tok::l_brace, TT_ClassLBrace); 82 83 Tokens = annotate("const class C {} c;"); 84 EXPECT_EQ(Tokens.size(), 8u) << Tokens; 85 EXPECT_TOKEN(Tokens[3], tok::l_brace, TT_ClassLBrace); 86 87 Tokens = annotate("const class {} c;"); 88 EXPECT_EQ(Tokens.size(), 7u) << Tokens; 89 EXPECT_TOKEN(Tokens[2], tok::l_brace, TT_ClassLBrace); 90 } 91 92 TEST_F(TokenAnnotatorTest, UnderstandsStructs) { 93 auto Tokens = annotate("struct S {};"); 94 EXPECT_EQ(Tokens.size(), 6u) << Tokens; 95 EXPECT_TOKEN(Tokens[2], tok::l_brace, TT_StructLBrace); 96 } 97 98 TEST_F(TokenAnnotatorTest, UnderstandsUnions) { 99 auto Tokens = annotate("union U {};"); 100 EXPECT_EQ(Tokens.size(), 6u) << Tokens; 101 EXPECT_TOKEN(Tokens[2], tok::l_brace, TT_UnionLBrace); 102 103 Tokens = annotate("union U { void f() { return; } };"); 104 EXPECT_EQ(Tokens.size(), 14u) << Tokens; 105 EXPECT_TOKEN(Tokens[2], tok::l_brace, TT_UnionLBrace); 106 EXPECT_TOKEN(Tokens[7], tok::l_brace, TT_FunctionLBrace); 107 } 108 109 TEST_F(TokenAnnotatorTest, UnderstandsEnums) { 110 auto Tokens = annotate("enum E {};"); 111 EXPECT_EQ(Tokens.size(), 6u) << Tokens; 112 EXPECT_TOKEN(Tokens[2], tok::l_brace, TT_EnumLBrace); 113 } 114 115 TEST_F(TokenAnnotatorTest, UnderstandsLBracesInMacroDefinition) { 116 auto Tokens = annotate("#define BEGIN NS {"); 117 EXPECT_EQ(Tokens.size(), 6u) << Tokens; 118 EXPECT_TOKEN(Tokens[4], tok::l_brace, TT_Unknown); 119 } 120 121 TEST_F(TokenAnnotatorTest, UnderstandsDelete) { 122 auto Tokens = annotate("delete (void *)p;"); 123 EXPECT_EQ(Tokens.size(), 8u) << Tokens; 124 EXPECT_TOKEN(Tokens[4], tok::r_paren, TT_CastRParen); 125 126 Tokens = annotate("delete[] (void *)p;"); 127 EXPECT_EQ(Tokens.size(), 10u) << Tokens; 128 EXPECT_TOKEN(Tokens[6], tok::r_paren, TT_CastRParen); 129 130 Tokens = annotate("delete[] /*comment*/ (void *)p;"); 131 EXPECT_EQ(Tokens.size(), 11u) << Tokens; 132 EXPECT_TOKEN(Tokens[7], tok::r_paren, TT_CastRParen); 133 134 Tokens = annotate("delete[/*comment*/] (void *)p;"); 135 EXPECT_EQ(Tokens.size(), 11u) << Tokens; 136 EXPECT_TOKEN(Tokens[7], tok::r_paren, TT_CastRParen); 137 138 Tokens = annotate("delete/*comment*/[] (void *)p;"); 139 EXPECT_EQ(Tokens.size(), 11u) << Tokens; 140 EXPECT_TOKEN(Tokens[7], tok::r_paren, TT_CastRParen); 141 } 142 143 TEST_F(TokenAnnotatorTest, UnderstandsRequiresClausesAndConcepts) { 144 auto Tokens = annotate("template <typename T>\n" 145 "concept C = (Foo && Bar) && (Bar && Baz);"); 146 147 ASSERT_EQ(Tokens.size(), 21u) << Tokens; 148 EXPECT_TOKEN(Tokens[10], tok::ampamp, TT_BinaryOperator); 149 EXPECT_TOKEN(Tokens[13], tok::ampamp, TT_BinaryOperator); 150 EXPECT_TOKEN(Tokens[16], tok::ampamp, TT_BinaryOperator); 151 152 Tokens = annotate("template <typename T>\n" 153 "concept C = requires(T t) {\n" 154 " { t.foo() };\n" 155 "} && Bar<T> && Baz<T>;"); 156 ASSERT_EQ(Tokens.size(), 35u) << Tokens; 157 EXPECT_TOKEN(Tokens[8], tok::kw_requires, TT_RequiresExpression); 158 EXPECT_TOKEN(Tokens[9], tok::l_paren, TT_RequiresExpressionLParen); 159 EXPECT_TOKEN(Tokens[13], tok::l_brace, TT_RequiresExpressionLBrace); 160 EXPECT_TOKEN(Tokens[23], tok::ampamp, TT_BinaryOperator); 161 EXPECT_TOKEN(Tokens[28], tok::ampamp, TT_BinaryOperator); 162 163 Tokens = annotate("template<typename T>\n" 164 "requires C1<T> && (C21<T> || C22<T> && C2e<T>) && C3<T>\n" 165 "struct Foo;"); 166 ASSERT_EQ(Tokens.size(), 36u) << Tokens; 167 EXPECT_TOKEN(Tokens[5], tok::kw_requires, TT_RequiresClause); 168 EXPECT_TOKEN(Tokens[6], tok::identifier, TT_Unknown); 169 EXPECT_EQ(Tokens[6]->FakeLParens.size(), 1u); 170 EXPECT_TOKEN(Tokens[10], tok::ampamp, TT_BinaryOperator); 171 EXPECT_TOKEN(Tokens[16], tok::pipepipe, TT_BinaryOperator); 172 EXPECT_TOKEN(Tokens[21], tok::ampamp, TT_BinaryOperator); 173 EXPECT_TOKEN(Tokens[27], tok::ampamp, TT_BinaryOperator); 174 EXPECT_TOKEN(Tokens[31], tok::greater, TT_TemplateCloser); 175 EXPECT_EQ(Tokens[31]->FakeRParens, 1u); 176 EXPECT_TRUE(Tokens[31]->ClosesRequiresClause); 177 178 Tokens = 179 annotate("template<typename T>\n" 180 "requires (C1<T> && (C21<T> || C22<T> && C2e<T>) && C3<T>)\n" 181 "struct Foo;"); 182 ASSERT_EQ(Tokens.size(), 38u) << Tokens; 183 EXPECT_TOKEN(Tokens[5], tok::kw_requires, TT_RequiresClause); 184 EXPECT_TOKEN(Tokens[7], tok::identifier, TT_Unknown); 185 EXPECT_EQ(Tokens[7]->FakeLParens.size(), 1u); 186 EXPECT_TOKEN(Tokens[11], tok::ampamp, TT_BinaryOperator); 187 EXPECT_TOKEN(Tokens[17], tok::pipepipe, TT_BinaryOperator); 188 EXPECT_TOKEN(Tokens[22], tok::ampamp, TT_BinaryOperator); 189 EXPECT_TOKEN(Tokens[28], tok::ampamp, TT_BinaryOperator); 190 EXPECT_TOKEN(Tokens[32], tok::greater, TT_TemplateCloser); 191 EXPECT_EQ(Tokens[32]->FakeRParens, 1u); 192 EXPECT_TOKEN(Tokens[33], tok::r_paren, TT_Unknown); 193 EXPECT_TRUE(Tokens[33]->ClosesRequiresClause); 194 195 Tokens = annotate("template <typename T>\n" 196 "void foo(T) noexcept requires Bar<T>;"); 197 ASSERT_EQ(Tokens.size(), 18u) << Tokens; 198 EXPECT_TOKEN(Tokens[11], tok::kw_requires, TT_RequiresClause); 199 200 Tokens = annotate("template <typename T>\n" 201 "struct S {\n" 202 " void foo() const requires Bar<T>;\n" 203 " void bar() const & requires Baz<T>;\n" 204 " void bar() && requires Baz2<T>;\n" 205 " void baz() const & noexcept requires Baz<T>;\n" 206 " void baz() && noexcept requires Baz2<T>;\n" 207 "};\n" 208 "\n" 209 "void S::bar() const & requires Baz<T> { }"); 210 ASSERT_EQ(Tokens.size(), 85u) << Tokens; 211 EXPECT_TOKEN(Tokens[13], tok::kw_requires, TT_RequiresClause); 212 EXPECT_TOKEN(Tokens[25], tok::kw_requires, TT_RequiresClause); 213 EXPECT_TOKEN(Tokens[36], tok::kw_requires, TT_RequiresClause); 214 EXPECT_TOKEN(Tokens[49], tok::kw_requires, TT_RequiresClause); 215 EXPECT_TOKEN(Tokens[61], tok::kw_requires, TT_RequiresClause); 216 EXPECT_TOKEN(Tokens[77], tok::kw_requires, TT_RequiresClause); 217 218 Tokens = annotate("void Class::member() && requires(Constant) {}"); 219 ASSERT_EQ(Tokens.size(), 14u) << Tokens; 220 EXPECT_TOKEN(Tokens[7], tok::kw_requires, TT_RequiresClause); 221 222 Tokens = annotate("void Class::member() && requires(Constant<T>) {}"); 223 ASSERT_EQ(Tokens.size(), 17u) << Tokens; 224 EXPECT_TOKEN(Tokens[7], tok::kw_requires, TT_RequiresClause); 225 226 Tokens = 227 annotate("void Class::member() && requires(Namespace::Constant<T>) {}"); 228 ASSERT_EQ(Tokens.size(), 19u) << Tokens; 229 EXPECT_TOKEN(Tokens[7], tok::kw_requires, TT_RequiresClause); 230 231 Tokens = annotate("void Class::member() && requires(typename " 232 "Namespace::Outer<T>::Inner::Constant) {}"); 233 ASSERT_EQ(Tokens.size(), 24u) << Tokens; 234 EXPECT_TOKEN(Tokens[7], tok::kw_requires, TT_RequiresClause); 235 236 Tokens = annotate("struct [[nodiscard]] zero_t {\n" 237 " template<class T>\n" 238 " requires requires { number_zero_v<T>; }\n" 239 " [[nodiscard]] constexpr operator T() const { " 240 "return number_zero_v<T>; }\n" 241 "};"); 242 ASSERT_EQ(Tokens.size(), 44u); 243 EXPECT_TOKEN(Tokens[13], tok::kw_requires, TT_RequiresClause); 244 EXPECT_TOKEN(Tokens[14], tok::kw_requires, TT_RequiresExpression); 245 EXPECT_TOKEN(Tokens[15], tok::l_brace, TT_RequiresExpressionLBrace); 246 EXPECT_TOKEN(Tokens[21], tok::r_brace, TT_Unknown); 247 EXPECT_EQ(Tokens[21]->MatchingParen, Tokens[15]); 248 EXPECT_TRUE(Tokens[21]->ClosesRequiresClause); 249 } 250 251 TEST_F(TokenAnnotatorTest, UnderstandsRequiresExpressions) { 252 auto Tokens = annotate("bool b = requires(int i) { i + 5; };"); 253 ASSERT_EQ(Tokens.size(), 16u) << Tokens; 254 EXPECT_TOKEN(Tokens[3], tok::kw_requires, TT_RequiresExpression); 255 EXPECT_TOKEN(Tokens[4], tok::l_paren, TT_RequiresExpressionLParen); 256 EXPECT_TOKEN(Tokens[8], tok::l_brace, TT_RequiresExpressionLBrace); 257 258 Tokens = annotate("if (requires(int i) { i + 5; }) return;"); 259 ASSERT_EQ(Tokens.size(), 17u) << Tokens; 260 EXPECT_TOKEN(Tokens[2], tok::kw_requires, TT_RequiresExpression); 261 EXPECT_TOKEN(Tokens[3], tok::l_paren, TT_RequiresExpressionLParen); 262 EXPECT_TOKEN(Tokens[7], tok::l_brace, TT_RequiresExpressionLBrace); 263 264 Tokens = annotate("if (func() && requires(int i) { i + 5; }) return;"); 265 ASSERT_EQ(Tokens.size(), 21u) << Tokens; 266 EXPECT_TOKEN(Tokens[6], tok::kw_requires, TT_RequiresExpression); 267 EXPECT_TOKEN(Tokens[7], tok::l_paren, TT_RequiresExpressionLParen); 268 EXPECT_TOKEN(Tokens[11], tok::l_brace, TT_RequiresExpressionLBrace); 269 270 Tokens = annotate("foo(requires(const T t) {});"); 271 ASSERT_EQ(Tokens.size(), 13u) << Tokens; 272 EXPECT_TOKEN(Tokens[2], tok::kw_requires, TT_RequiresExpression); 273 EXPECT_TOKEN(Tokens[3], tok::l_paren, TT_RequiresExpressionLParen); 274 EXPECT_TOKEN(Tokens[8], tok::l_brace, TT_RequiresExpressionLBrace); 275 276 Tokens = annotate("foo(requires(const int t) {});"); 277 ASSERT_EQ(Tokens.size(), 13u) << Tokens; 278 EXPECT_TOKEN(Tokens[2], tok::kw_requires, TT_RequiresExpression); 279 EXPECT_TOKEN(Tokens[3], tok::l_paren, TT_RequiresExpressionLParen); 280 EXPECT_TOKEN(Tokens[8], tok::l_brace, TT_RequiresExpressionLBrace); 281 282 Tokens = annotate("foo(requires(const T t) {});"); 283 ASSERT_EQ(Tokens.size(), 13u) << Tokens; 284 EXPECT_TOKEN(Tokens[2], tok::kw_requires, TT_RequiresExpression); 285 EXPECT_TOKEN(Tokens[3], tok::l_paren, TT_RequiresExpressionLParen); 286 EXPECT_TOKEN(Tokens[8], tok::l_brace, TT_RequiresExpressionLBrace); 287 288 Tokens = annotate("foo(requires(int const* volatile t) {});"); 289 ASSERT_EQ(Tokens.size(), 15u) << Tokens; 290 EXPECT_TOKEN(Tokens[2], tok::kw_requires, TT_RequiresExpression); 291 EXPECT_TOKEN(Tokens[3], tok::l_paren, TT_RequiresExpressionLParen); 292 EXPECT_TOKEN(Tokens[10], tok::l_brace, TT_RequiresExpressionLBrace); 293 294 Tokens = annotate("foo(requires(T const* volatile t) {});"); 295 ASSERT_EQ(Tokens.size(), 15u) << Tokens; 296 EXPECT_TOKEN(Tokens[2], tok::kw_requires, TT_RequiresExpression); 297 EXPECT_TOKEN(Tokens[3], tok::l_paren, TT_RequiresExpressionLParen); 298 EXPECT_TOKEN(Tokens[10], tok::l_brace, TT_RequiresExpressionLBrace); 299 300 Tokens = 301 annotate("foo(requires(const typename Outer<T>::Inner * const t) {});"); 302 ASSERT_EQ(Tokens.size(), 21u) << Tokens; 303 EXPECT_TOKEN(Tokens[2], tok::kw_requires, TT_RequiresExpression); 304 EXPECT_TOKEN(Tokens[3], tok::l_paren, TT_RequiresExpressionLParen); 305 EXPECT_TOKEN(Tokens[16], tok::l_brace, TT_RequiresExpressionLBrace); 306 307 Tokens = annotate("template <typename T>\n" 308 "concept C = requires(T T) {\n" 309 " requires Bar<T> && Foo<T>;\n" 310 "};"); 311 ASSERT_EQ(Tokens.size(), 28u) << Tokens; 312 EXPECT_TOKEN(Tokens[8], tok::kw_requires, TT_RequiresExpression); 313 EXPECT_TOKEN(Tokens[9], tok::l_paren, TT_RequiresExpressionLParen); 314 EXPECT_TOKEN(Tokens[13], tok::l_brace, TT_RequiresExpressionLBrace); 315 EXPECT_TOKEN(Tokens[14], tok::kw_requires, 316 TT_RequiresClauseInARequiresExpression); 317 318 Tokens = annotate("template <typename T>\n" 319 "concept C = requires(T T) {\n" 320 " { t.func() } -> std::same_as<int>;" 321 " requires Bar<T> && Foo<T>;\n" 322 "};"); 323 ASSERT_EQ(Tokens.size(), 43u) << Tokens; 324 EXPECT_TOKEN(Tokens[8], tok::kw_requires, TT_RequiresExpression); 325 EXPECT_TOKEN(Tokens[9], tok::l_paren, TT_RequiresExpressionLParen); 326 EXPECT_TOKEN(Tokens[13], tok::l_brace, TT_RequiresExpressionLBrace); 327 EXPECT_TOKEN(Tokens[29], tok::kw_requires, 328 TT_RequiresClauseInARequiresExpression); 329 } 330 331 TEST_F(TokenAnnotatorTest, RequiresDoesNotChangeParsingOfTheRest) { 332 auto NumberOfAdditionalRequiresClauseTokens = 5u; 333 auto NumberOfTokensBeforeRequires = 5u; 334 335 auto BaseTokens = annotate("template<typename T>\n" 336 "T Pi = 3.14;"); 337 auto ConstrainedTokens = annotate("template<typename T>\n" 338 " requires Foo<T>\n" 339 "T Pi = 3.14;"); 340 341 auto NumberOfBaseTokens = 11u; 342 343 ASSERT_EQ(BaseTokens.size(), NumberOfBaseTokens) << BaseTokens; 344 ASSERT_EQ(ConstrainedTokens.size(), 345 NumberOfBaseTokens + NumberOfAdditionalRequiresClauseTokens) 346 << ConstrainedTokens; 347 348 for (auto I = 0u; I < NumberOfBaseTokens; ++I) 349 if (I < NumberOfTokensBeforeRequires) 350 EXPECT_EQ(*BaseTokens[I], *ConstrainedTokens[I]) << I; 351 else 352 EXPECT_EQ(*BaseTokens[I], 353 *ConstrainedTokens[I + NumberOfAdditionalRequiresClauseTokens]) 354 << I; 355 356 BaseTokens = annotate("template<typename T>\n" 357 "struct Bar;"); 358 ConstrainedTokens = annotate("template<typename T>\n" 359 " requires Foo<T>\n" 360 "struct Bar;"); 361 NumberOfBaseTokens = 9u; 362 363 ASSERT_EQ(BaseTokens.size(), NumberOfBaseTokens) << BaseTokens; 364 ASSERT_EQ(ConstrainedTokens.size(), 365 NumberOfBaseTokens + NumberOfAdditionalRequiresClauseTokens) 366 << ConstrainedTokens; 367 368 for (auto I = 0u; I < NumberOfBaseTokens; ++I) 369 if (I < NumberOfTokensBeforeRequires) 370 EXPECT_EQ(*BaseTokens[I], *ConstrainedTokens[I]) << I; 371 else 372 EXPECT_EQ(*BaseTokens[I], 373 *ConstrainedTokens[I + NumberOfAdditionalRequiresClauseTokens]) 374 << I; 375 376 BaseTokens = annotate("template<typename T>\n" 377 "struct Bar {" 378 " T foo();\n" 379 " T bar();\n" 380 "};"); 381 ConstrainedTokens = annotate("template<typename T>\n" 382 " requires Foo<T>\n" 383 "struct Bar {" 384 " T foo();\n" 385 " T bar();\n" 386 "};"); 387 NumberOfBaseTokens = 21u; 388 389 ASSERT_EQ(BaseTokens.size(), NumberOfBaseTokens) << BaseTokens; 390 ASSERT_EQ(ConstrainedTokens.size(), 391 NumberOfBaseTokens + NumberOfAdditionalRequiresClauseTokens) 392 << ConstrainedTokens; 393 394 for (auto I = 0u; I < NumberOfBaseTokens; ++I) 395 if (I < NumberOfTokensBeforeRequires) 396 EXPECT_EQ(*BaseTokens[I], *ConstrainedTokens[I]) << I; 397 else 398 EXPECT_EQ(*BaseTokens[I], 399 *ConstrainedTokens[I + NumberOfAdditionalRequiresClauseTokens]) 400 << I; 401 402 BaseTokens = annotate("template<typename T>\n" 403 "Bar(T) -> Bar<T>;"); 404 ConstrainedTokens = annotate("template<typename T>\n" 405 " requires Foo<T>\n" 406 "Bar(T) -> Bar<T>;"); 407 NumberOfBaseTokens = 16u; 408 409 ASSERT_EQ(BaseTokens.size(), NumberOfBaseTokens) << BaseTokens; 410 ASSERT_EQ(ConstrainedTokens.size(), 411 NumberOfBaseTokens + NumberOfAdditionalRequiresClauseTokens) 412 << ConstrainedTokens; 413 414 for (auto I = 0u; I < NumberOfBaseTokens; ++I) 415 if (I < NumberOfTokensBeforeRequires) 416 EXPECT_EQ(*BaseTokens[I], *ConstrainedTokens[I]) << I; 417 else 418 EXPECT_EQ(*BaseTokens[I], 419 *ConstrainedTokens[I + NumberOfAdditionalRequiresClauseTokens]) 420 << I; 421 422 BaseTokens = annotate("template<typename T>\n" 423 "T foo();"); 424 ConstrainedTokens = annotate("template<typename T>\n" 425 " requires Foo<T>\n" 426 "T foo();"); 427 NumberOfBaseTokens = 11u; 428 429 ASSERT_EQ(BaseTokens.size(), NumberOfBaseTokens) << BaseTokens; 430 ASSERT_EQ(ConstrainedTokens.size(), 431 NumberOfBaseTokens + NumberOfAdditionalRequiresClauseTokens) 432 << ConstrainedTokens; 433 434 for (auto I = 0u; I < NumberOfBaseTokens; ++I) 435 if (I < NumberOfTokensBeforeRequires) 436 EXPECT_EQ(*BaseTokens[I], *ConstrainedTokens[I]) << I; 437 else 438 EXPECT_EQ(*BaseTokens[I], 439 *ConstrainedTokens[I + NumberOfAdditionalRequiresClauseTokens]) 440 << I; 441 442 BaseTokens = annotate("template<typename T>\n" 443 "T foo() {\n" 444 " auto bar = baz();\n" 445 " return bar + T{};\n" 446 "}"); 447 ConstrainedTokens = annotate("template<typename T>\n" 448 " requires Foo<T>\n" 449 "T foo() {\n" 450 " auto bar = baz();\n" 451 " return bar + T{};\n" 452 "}"); 453 NumberOfBaseTokens = 26u; 454 455 ASSERT_EQ(BaseTokens.size(), NumberOfBaseTokens) << BaseTokens; 456 ASSERT_EQ(ConstrainedTokens.size(), 457 NumberOfBaseTokens + NumberOfAdditionalRequiresClauseTokens) 458 << ConstrainedTokens; 459 460 for (auto I = 0u; I < NumberOfBaseTokens; ++I) 461 if (I < NumberOfTokensBeforeRequires) 462 EXPECT_EQ(*BaseTokens[I], *ConstrainedTokens[I]) << I; 463 else 464 EXPECT_EQ(*BaseTokens[I], 465 *ConstrainedTokens[I + NumberOfAdditionalRequiresClauseTokens]) 466 << I; 467 468 BaseTokens = annotate("template<typename T>\n" 469 "T foo();"); 470 ConstrainedTokens = annotate("template<typename T>\n" 471 "T foo() requires Foo<T>;"); 472 NumberOfBaseTokens = 11u; 473 NumberOfTokensBeforeRequires = 9u; 474 475 ASSERT_EQ(BaseTokens.size(), NumberOfBaseTokens) << BaseTokens; 476 ASSERT_EQ(ConstrainedTokens.size(), 477 NumberOfBaseTokens + NumberOfAdditionalRequiresClauseTokens) 478 << ConstrainedTokens; 479 480 for (auto I = 0u; I < NumberOfBaseTokens; ++I) 481 if (I < NumberOfTokensBeforeRequires) 482 EXPECT_EQ(*BaseTokens[I], *ConstrainedTokens[I]) << I; 483 else 484 EXPECT_EQ(*BaseTokens[I], 485 *ConstrainedTokens[I + NumberOfAdditionalRequiresClauseTokens]) 486 << I; 487 488 BaseTokens = annotate("template<typename T>\n" 489 "T foo() {\n" 490 " auto bar = baz();\n" 491 " return bar + T{};\n" 492 "}"); 493 ConstrainedTokens = annotate("template<typename T>\n" 494 "T foo() requires Foo<T> {\n" 495 " auto bar = baz();\n" 496 " return bar + T{};\n" 497 "}"); 498 NumberOfBaseTokens = 26u; 499 500 ASSERT_EQ(BaseTokens.size(), NumberOfBaseTokens) << BaseTokens; 501 ASSERT_EQ(ConstrainedTokens.size(), 502 NumberOfBaseTokens + NumberOfAdditionalRequiresClauseTokens) 503 << ConstrainedTokens; 504 505 for (auto I = 0u; I < NumberOfBaseTokens; ++I) 506 if (I < NumberOfTokensBeforeRequires) 507 EXPECT_EQ(*BaseTokens[I], *ConstrainedTokens[I]) << I; 508 else 509 EXPECT_EQ(*BaseTokens[I], 510 *ConstrainedTokens[I + NumberOfAdditionalRequiresClauseTokens]) 511 << I; 512 513 BaseTokens = annotate("template<typename T>\n" 514 "Bar(T) -> Bar<typename T::I>;"); 515 ConstrainedTokens = annotate("template<typename T>\n" 516 " requires requires(T &&t) {\n" 517 " typename T::I;\n" 518 " }\n" 519 "Bar(T) -> Bar<typename T::I>;"); 520 NumberOfBaseTokens = 19u; 521 NumberOfAdditionalRequiresClauseTokens = 14u; 522 NumberOfTokensBeforeRequires = 5u; 523 524 ASSERT_EQ(BaseTokens.size(), NumberOfBaseTokens) << BaseTokens; 525 ASSERT_EQ(ConstrainedTokens.size(), 526 NumberOfBaseTokens + NumberOfAdditionalRequiresClauseTokens) 527 << ConstrainedTokens; 528 529 for (auto I = 0u; I < NumberOfBaseTokens; ++I) 530 if (I < NumberOfTokensBeforeRequires) 531 EXPECT_EQ(*BaseTokens[I], *ConstrainedTokens[I]) << I; 532 else 533 EXPECT_EQ(*BaseTokens[I], 534 *ConstrainedTokens[I + NumberOfAdditionalRequiresClauseTokens]) 535 << I; 536 537 BaseTokens = annotate("struct [[nodiscard]] zero_t {\n" 538 " template<class T>\n" 539 " [[nodiscard]] constexpr operator T() const { " 540 "return number_zero_v<T>; }\n" 541 "};"); 542 543 ConstrainedTokens = annotate("struct [[nodiscard]] zero_t {\n" 544 " template<class T>\n" 545 " requires requires { number_zero_v<T>; }\n" 546 " [[nodiscard]] constexpr operator T() const { " 547 "return number_zero_v<T>; }\n" 548 "};"); 549 NumberOfBaseTokens = 35u; 550 NumberOfAdditionalRequiresClauseTokens = 9u; 551 NumberOfTokensBeforeRequires = 13u; 552 553 ASSERT_EQ(BaseTokens.size(), NumberOfBaseTokens) << BaseTokens; 554 ASSERT_EQ(ConstrainedTokens.size(), 555 NumberOfBaseTokens + NumberOfAdditionalRequiresClauseTokens) 556 << ConstrainedTokens; 557 558 for (auto I = 0u; I < NumberOfBaseTokens; ++I) 559 if (I < NumberOfTokensBeforeRequires) 560 EXPECT_EQ(*BaseTokens[I], *ConstrainedTokens[I]) << I; 561 else 562 EXPECT_EQ(*BaseTokens[I], 563 *ConstrainedTokens[I + NumberOfAdditionalRequiresClauseTokens]) 564 << I; 565 } 566 567 } // namespace 568 } // namespace format 569 } // namespace clang 570