@@ -18,13 +18,13 @@ struct StructuralEquivalenceTest : ::testing::Test {
18
18
std::unique_ptr<ASTUnit> AST0, AST1;
19
19
std::string Code0, Code1; // Buffers for SourceManager
20
20
21
- // Get a pair of Decl pointers to the synthetised declarations from the given
22
- // code snipets. By default we search for the unique Decl with name 'foo' in
23
- // both snippets.
24
- std::tuple<NamedDecl *, NamedDecl * >
25
- makeNamedDecls ( const std::string &SrcCode0, const std::string &SrcCode1,
26
- Language Lang, const char * const Identifier = " foo " ) {
27
-
21
+ // Get a pair of node pointers into the synthesized AST from the given code
22
+ // snippets. To determine the returned node, a separate matcher is specified
23
+ // for both snippets. The first matching node is returned .
24
+ template < typename NodeType, typename MatcherType >
25
+ std::tuple<NodeType *, NodeType *> makeDecls (
26
+ const std::string &SrcCode0, const std::string &SrcCode1, Language Lang,
27
+ const MatcherType &Matcher0, const MatcherType &Matcher1) {
28
28
this ->Code0 = SrcCode0;
29
29
this ->Code1 = SrcCode1;
30
30
ArgVector Args = getBasicRunOptionsForLanguage (Lang);
@@ -34,28 +34,32 @@ struct StructuralEquivalenceTest : ::testing::Test {
34
34
AST0 = tooling::buildASTFromCodeWithArgs (Code0, Args, InputFileName);
35
35
AST1 = tooling::buildASTFromCodeWithArgs (Code1, Args, InputFileName);
36
36
37
- ASTContext &Ctx0 = AST0->getASTContext (), &Ctx1 = AST1->getASTContext ();
38
-
39
- auto getDecl = [](ASTContext &Ctx, const std::string &Name) -> NamedDecl * {
40
- IdentifierInfo *SearchedII = &Ctx.Idents .get (Name);
41
- assert (SearchedII && " Declaration with the identifier "
42
- " should be specified in test!" );
43
- DeclarationName SearchDeclName (SearchedII);
44
- SmallVector<NamedDecl *, 4 > FoundDecls;
45
- Ctx.getTranslationUnitDecl ()->localUncachedLookup (SearchDeclName,
46
- FoundDecls);
37
+ NodeType *D0 = FirstDeclMatcher<NodeType>().match (
38
+ AST0->getASTContext ().getTranslationUnitDecl (), Matcher0);
39
+ NodeType *D1 = FirstDeclMatcher<NodeType>().match (
40
+ AST1->getASTContext ().getTranslationUnitDecl (), Matcher1);
47
41
48
- // We should find one Decl but one only.
49
- assert (FoundDecls. size () == 1 );
42
+ return std::make_tuple (D0, D1);
43
+ }
50
44
51
- return FoundDecls[0 ];
52
- };
45
+ // Get a pair of node pointers into the synthesized AST from the given code
46
+ // snippets. The same matcher is used for both snippets.
47
+ template <typename NodeType, typename MatcherType>
48
+ std::tuple<NodeType *, NodeType *> makeDecls (
49
+ const std::string &SrcCode0, const std::string &SrcCode1, Language Lang,
50
+ const MatcherType &AMatcher) {
51
+ return makeDecls<NodeType, MatcherType>(
52
+ SrcCode0, SrcCode1, Lang, AMatcher, AMatcher);
53
+ }
53
54
54
- NamedDecl *D0 = getDecl (Ctx0, Identifier);
55
- NamedDecl *D1 = getDecl (Ctx1, Identifier);
56
- assert (D0);
57
- assert (D1);
58
- return std::make_tuple (D0, D1);
55
+ // Get a pair of Decl pointers to the synthesized declarations from the given
56
+ // code snippets. We search for the first NamedDecl with given name in both
57
+ // snippets.
58
+ std::tuple<NamedDecl *, NamedDecl *> makeNamedDecls (
59
+ const std::string &SrcCode0, const std::string &SrcCode1,
60
+ Language Lang, const char *const Identifier = " foo" ) {
61
+ auto Matcher = namedDecl (hasName (Identifier));
62
+ return makeDecls<NamedDecl>(SrcCode0, SrcCode1, Lang, Matcher);
59
63
}
60
64
61
65
bool testStructuralMatch (NamedDecl *D0, NamedDecl *D1) {
@@ -110,35 +114,29 @@ TEST_F(StructuralEquivalenceTest, CharVsSignedCharInStruct) {
110
114
}
111
115
112
116
TEST_F (StructuralEquivalenceTest, IntVsSignedIntTemplateSpec) {
113
- auto Decls = makeNamedDecls (
114
- " template <class T> struct foo; template<> struct foo<int>{};" ,
115
- " template <class T> struct foo; template<> struct foo<signed int>{};" ,
116
- Lang_CXX);
117
- ClassTemplateSpecializationDecl *Spec0 =
118
- *cast<ClassTemplateDecl>(get<0 >(Decls))->spec_begin ();
119
- ClassTemplateSpecializationDecl *Spec1 =
120
- *cast<ClassTemplateDecl>(get<1 >(Decls))->spec_begin ();
121
- ASSERT_TRUE (Spec0 != nullptr );
122
- ASSERT_TRUE (Spec1 != nullptr );
117
+ auto Decls = makeDecls<ClassTemplateSpecializationDecl>(
118
+ R"( template <class T> struct foo; template<> struct foo<int>{};)" ,
119
+ R"( template <class T> struct foo; template<> struct foo<signed int>{};)" ,
120
+ Lang_CXX,
121
+ classTemplateSpecializationDecl ());
122
+ auto Spec0 = get<0 >(Decls);
123
+ auto Spec1 = get<1 >(Decls);
123
124
EXPECT_TRUE (testStructuralMatch (Spec0, Spec1));
124
125
}
125
126
126
127
TEST_F (StructuralEquivalenceTest, CharVsSignedCharTemplateSpec) {
127
- auto Decls = makeNamedDecls (
128
- " template <class T> struct foo; template<> struct foo<char>{};" ,
129
- " template <class T> struct foo; template<> struct foo<signed char>{};" ,
130
- Lang_CXX);
131
- ClassTemplateSpecializationDecl *Spec0 =
132
- *cast<ClassTemplateDecl>(get<0 >(Decls))->spec_begin ();
133
- ClassTemplateSpecializationDecl *Spec1 =
134
- *cast<ClassTemplateDecl>(get<1 >(Decls))->spec_begin ();
135
- ASSERT_TRUE (Spec0 != nullptr );
136
- ASSERT_TRUE (Spec1 != nullptr );
128
+ auto Decls = makeDecls<ClassTemplateSpecializationDecl>(
129
+ R"( template <class T> struct foo; template<> struct foo<char>{};)" ,
130
+ R"( template <class T> struct foo; template<> struct foo<signed char>{};)" ,
131
+ Lang_CXX,
132
+ classTemplateSpecializationDecl ());
133
+ auto Spec0 = get<0 >(Decls);
134
+ auto Spec1 = get<1 >(Decls);
137
135
EXPECT_FALSE (testStructuralMatch (Spec0, Spec1));
138
136
}
139
137
140
138
TEST_F (StructuralEquivalenceTest, CharVsSignedCharTemplateSpecWithInheritance) {
141
- auto Decls = makeNamedDecls (
139
+ auto Decls = makeDecls<ClassTemplateSpecializationDecl> (
142
140
R"(
143
141
struct true_type{};
144
142
template <class T> struct foo;
@@ -149,14 +147,9 @@ TEST_F(StructuralEquivalenceTest, CharVsSignedCharTemplateSpecWithInheritance) {
149
147
template <class T> struct foo;
150
148
template<> struct foo<signed char> : true_type {};
151
149
)" ,
152
- Lang_CXX);
153
- ClassTemplateSpecializationDecl *Spec0 =
154
- *cast<ClassTemplateDecl>(get<0 >(Decls))->spec_begin ();
155
- ClassTemplateSpecializationDecl *Spec1 =
156
- *cast<ClassTemplateDecl>(get<1 >(Decls))->spec_begin ();
157
- ASSERT_TRUE (Spec0 != nullptr );
158
- ASSERT_TRUE (Spec1 != nullptr );
159
- EXPECT_FALSE (testStructuralMatch (Spec0, Spec1));
150
+ Lang_CXX,
151
+ classTemplateSpecializationDecl ());
152
+ EXPECT_FALSE (testStructuralMatch (Decls));
160
153
}
161
154
162
155
// This test is disabled for now.
@@ -203,5 +196,350 @@ TEST_F(StructuralEquivalenceTest, WrongOrderOfFieldsInClass) {
203
196
EXPECT_FALSE (testStructuralMatch (Decls));
204
197
}
205
198
199
+ struct StructuralEquivalenceFunctionTest : StructuralEquivalenceTest {
200
+ };
201
+
202
+ TEST_F (StructuralEquivalenceFunctionTest, ParamConstWithRef) {
203
+ auto t = makeNamedDecls (" void foo(int&);" ,
204
+ " void foo(const int&);" , Lang_CXX);
205
+ EXPECT_FALSE (testStructuralMatch (t));
206
+ }
207
+
208
+ TEST_F (StructuralEquivalenceFunctionTest, ParamConstSimple) {
209
+ auto t = makeNamedDecls (" void foo(int);" ,
210
+ " void foo(const int);" , Lang_CXX);
211
+ EXPECT_TRUE (testStructuralMatch (t));
212
+ // consider this OK
213
+ }
214
+
215
+ TEST_F (StructuralEquivalenceFunctionTest, Throw) {
216
+ auto t = makeNamedDecls (" void foo();" ,
217
+ " void foo() throw();" , Lang_CXX);
218
+ EXPECT_FALSE (testStructuralMatch (t));
219
+ }
220
+
221
+ TEST_F (StructuralEquivalenceFunctionTest, Noexcept) {
222
+ auto t = makeNamedDecls (" void foo();" ,
223
+ " void foo() noexcept;" , Lang_CXX11);
224
+ EXPECT_FALSE (testStructuralMatch (t));
225
+ }
226
+
227
+ TEST_F (StructuralEquivalenceFunctionTest, ThrowVsNoexcept) {
228
+ auto t = makeNamedDecls (" void foo() throw();" ,
229
+ " void foo() noexcept;" , Lang_CXX11);
230
+ EXPECT_FALSE (testStructuralMatch (t));
231
+ }
232
+
233
+ TEST_F (StructuralEquivalenceFunctionTest, ThrowVsNoexceptFalse) {
234
+ auto t = makeNamedDecls (" void foo() throw();" ,
235
+ " void foo() noexcept(false);" , Lang_CXX11);
236
+ EXPECT_FALSE (testStructuralMatch (t));
237
+ }
238
+
239
+ TEST_F (StructuralEquivalenceFunctionTest, ThrowVsNoexceptTrue) {
240
+ auto t = makeNamedDecls (" void foo() throw();" ,
241
+ " void foo() noexcept(true);" , Lang_CXX11);
242
+ EXPECT_FALSE (testStructuralMatch (t));
243
+ }
244
+
245
+ TEST_F (StructuralEquivalenceFunctionTest, DISABLED_NoexceptNonMatch) {
246
+ // The expression is not checked yet.
247
+ auto t = makeNamedDecls (" void foo() noexcept(false);" ,
248
+ " void foo() noexcept(true);" , Lang_CXX11);
249
+ EXPECT_FALSE (testStructuralMatch (t));
250
+ }
251
+
252
+ TEST_F (StructuralEquivalenceFunctionTest, NoexceptMatch) {
253
+ auto t = makeNamedDecls (" void foo() noexcept(false);" ,
254
+ " void foo() noexcept(false);" , Lang_CXX11);
255
+ EXPECT_TRUE (testStructuralMatch (t));
256
+ }
257
+
258
+ TEST_F (StructuralEquivalenceFunctionTest, NoexceptVsNoexceptFalse) {
259
+ auto t = makeNamedDecls (" void foo() noexcept;" ,
260
+ " void foo() noexcept(false);" , Lang_CXX11);
261
+ EXPECT_FALSE (testStructuralMatch (t));
262
+ }
263
+
264
+ TEST_F (StructuralEquivalenceFunctionTest, NoexceptVsNoexceptTrue) {
265
+ auto t = makeNamedDecls (" void foo() noexcept;" ,
266
+ " void foo() noexcept(true);" , Lang_CXX11);
267
+ EXPECT_FALSE (testStructuralMatch (t));
268
+ }
269
+
270
+ TEST_F (StructuralEquivalenceFunctionTest, ReturnType) {
271
+ auto t = makeNamedDecls (" char foo();" ,
272
+ " int foo();" , Lang_CXX);
273
+ EXPECT_FALSE (testStructuralMatch (t));
274
+ }
275
+
276
+ TEST_F (StructuralEquivalenceFunctionTest, ReturnConst) {
277
+ auto t = makeNamedDecls (" char foo();" ,
278
+ " const char foo();" , Lang_CXX);
279
+ EXPECT_FALSE (testStructuralMatch (t));
280
+ }
281
+
282
+ TEST_F (StructuralEquivalenceFunctionTest, ReturnRef) {
283
+ auto t = makeNamedDecls (" char &foo();" ,
284
+ " char &&foo();" , Lang_CXX11);
285
+ EXPECT_FALSE (testStructuralMatch (t));
286
+ }
287
+
288
+ TEST_F (StructuralEquivalenceFunctionTest, ParamCount) {
289
+ auto t = makeNamedDecls (" void foo(int);" ,
290
+ " void foo(int, int);" , Lang_CXX);
291
+ EXPECT_FALSE (testStructuralMatch (t));
292
+ }
293
+
294
+ TEST_F (StructuralEquivalenceFunctionTest, ParamType) {
295
+ auto t = makeNamedDecls (" void foo(int);" ,
296
+ " void foo(char);" , Lang_CXX);
297
+ EXPECT_FALSE (testStructuralMatch (t));
298
+ }
299
+
300
+ TEST_F (StructuralEquivalenceFunctionTest, ParamName) {
301
+ auto t = makeNamedDecls (" void foo(int a);" ,
302
+ " void foo(int b);" , Lang_CXX);
303
+ EXPECT_TRUE (testStructuralMatch (t));
304
+ }
305
+
306
+ TEST_F (StructuralEquivalenceFunctionTest, Variadic) {
307
+ auto t = makeNamedDecls (" void foo(int x...);" ,
308
+ " void foo(int x);" , Lang_CXX);
309
+ EXPECT_FALSE (testStructuralMatch (t));
310
+ }
311
+
312
+ TEST_F (StructuralEquivalenceFunctionTest, ParamPtr) {
313
+ auto t = makeNamedDecls (" void foo(int *);" ,
314
+ " void foo(int);" , Lang_CXX);
315
+ EXPECT_FALSE (testStructuralMatch (t));
316
+ }
317
+
318
+ TEST_F (StructuralEquivalenceFunctionTest, NameInParen) {
319
+ auto t = makeNamedDecls (
320
+ " void ((foo))();" ,
321
+ " void foo();" ,
322
+ Lang_CXX);
323
+ EXPECT_TRUE (testStructuralMatch (t));
324
+ }
325
+
326
+ TEST_F (StructuralEquivalenceFunctionTest, NameInParenWithExceptionSpec) {
327
+ auto t = makeNamedDecls (
328
+ " void (foo)() throw(int);" ,
329
+ " void (foo)() noexcept;" ,
330
+ Lang_CXX11);
331
+ EXPECT_FALSE (testStructuralMatch (t));
332
+ }
333
+
334
+ TEST_F (StructuralEquivalenceFunctionTest, NameInParenWithConst) {
335
+ auto t = makeNamedDecls (
336
+ " struct A { void (foo)() const; };" ,
337
+ " struct A { void (foo)(); };" ,
338
+ Lang_CXX11);
339
+ EXPECT_FALSE (testStructuralMatch (t));
340
+ }
341
+
342
+ struct StructuralEquivalenceCXXMethodTest : StructuralEquivalenceTest {
343
+ };
344
+
345
+ TEST_F (StructuralEquivalenceCXXMethodTest, Virtual) {
346
+ auto t = makeDecls<CXXMethodDecl>(
347
+ " struct X { void foo(); };" ,
348
+ " struct X { virtual void foo(); };" , Lang_CXX,
349
+ cxxMethodDecl (hasName (" foo" )));
350
+ EXPECT_FALSE (testStructuralMatch (t));
351
+ }
352
+
353
+ TEST_F (StructuralEquivalenceCXXMethodTest, Pure) {
354
+ auto t = makeNamedDecls (" struct X { virtual void foo(); };" ,
355
+ " struct X { virtual void foo() = 0; };" , Lang_CXX);
356
+ EXPECT_FALSE (testStructuralMatch (t));
357
+ }
358
+
359
+ TEST_F (StructuralEquivalenceCXXMethodTest, DISABLED_Final) {
360
+ // The final-ness is not checked yet.
361
+ auto t = makeNamedDecls (" struct X { virtual void foo(); };" ,
362
+ " struct X { virtual void foo() final; };" , Lang_CXX);
363
+ EXPECT_FALSE (testStructuralMatch (t));
364
+ }
365
+
366
+ TEST_F (StructuralEquivalenceCXXMethodTest, Const) {
367
+ auto t = makeNamedDecls (" struct X { void foo(); };" ,
368
+ " struct X { void foo() const; };" , Lang_CXX);
369
+ EXPECT_FALSE (testStructuralMatch (t));
370
+ }
371
+
372
+ TEST_F (StructuralEquivalenceCXXMethodTest, Static) {
373
+ auto t = makeNamedDecls (" struct X { void foo(); };" ,
374
+ " struct X { static void foo(); };" , Lang_CXX);
375
+ EXPECT_FALSE (testStructuralMatch (t));
376
+ }
377
+
378
+ TEST_F (StructuralEquivalenceCXXMethodTest, Ref1) {
379
+ auto t = makeNamedDecls (" struct X { void foo(); };" ,
380
+ " struct X { void foo() &&; };" , Lang_CXX11);
381
+ EXPECT_FALSE (testStructuralMatch (t));
382
+ }
383
+
384
+ TEST_F (StructuralEquivalenceCXXMethodTest, Ref2) {
385
+ auto t = makeNamedDecls (" struct X { void foo() &; };" ,
386
+ " struct X { void foo() &&; };" , Lang_CXX11);
387
+ EXPECT_FALSE (testStructuralMatch (t));
388
+ }
389
+
390
+ TEST_F (StructuralEquivalenceCXXMethodTest, AccessSpecifier) {
391
+ auto t = makeDecls<CXXMethodDecl>(
392
+ " struct X { public: void foo(); };" ,
393
+ " struct X { private: void foo(); };" , Lang_CXX,
394
+ cxxMethodDecl (hasName (" foo" )));
395
+ EXPECT_FALSE (testStructuralMatch (t));
396
+ }
397
+
398
+ TEST_F (StructuralEquivalenceCXXMethodTest, Delete) {
399
+ auto t = makeNamedDecls (" struct X { void foo(); };" ,
400
+ " struct X { void foo() = delete; };" , Lang_CXX11);
401
+ EXPECT_FALSE (testStructuralMatch (t));
402
+ }
403
+
404
+ TEST_F (StructuralEquivalenceCXXMethodTest, Constructor) {
405
+ auto t = makeDecls<FunctionDecl>(
406
+ " void foo();" , " struct foo { foo(); };" , Lang_CXX,
407
+ functionDecl (), cxxConstructorDecl ());
408
+ EXPECT_FALSE (testStructuralMatch (t));
409
+ }
410
+
411
+ TEST_F (StructuralEquivalenceCXXMethodTest, ConstructorParam) {
412
+ auto t = makeDecls<CXXConstructorDecl>(" struct X { X(); };" ,
413
+ " struct X { X(int); };" , Lang_CXX,
414
+ cxxConstructorDecl ());
415
+ EXPECT_FALSE (testStructuralMatch (t));
416
+ }
417
+
418
+ TEST_F (StructuralEquivalenceCXXMethodTest, ConstructorExplicit) {
419
+ auto t = makeDecls<CXXConstructorDecl>(" struct X { X(int); };" ,
420
+ " struct X { explicit X(int); };" ,
421
+ Lang_CXX11,
422
+ cxxConstructorDecl ());
423
+ EXPECT_FALSE (testStructuralMatch (t));
424
+ }
425
+
426
+ TEST_F (StructuralEquivalenceCXXMethodTest, ConstructorDefault) {
427
+ auto t = makeDecls<CXXConstructorDecl>(" struct X { X(); };" ,
428
+ " struct X { X() = default; };" ,
429
+ Lang_CXX11,
430
+ cxxConstructorDecl ());
431
+ EXPECT_FALSE (testStructuralMatch (t));
432
+ }
433
+
434
+ TEST_F (StructuralEquivalenceCXXMethodTest, Conversion) {
435
+ auto t = makeDecls<CXXConversionDecl>(" struct X { operator bool(); };" ,
436
+ " struct X { operator char(); };" ,
437
+ Lang_CXX11,
438
+ cxxConversionDecl ());
439
+ EXPECT_FALSE (testStructuralMatch (t));
440
+ }
441
+
442
+ TEST_F (StructuralEquivalenceCXXMethodTest, Operator) {
443
+ auto t = makeDecls<FunctionDecl>(
444
+ " struct X { int operator +(int); };" ,
445
+ " struct X { int operator -(int); };" , Lang_CXX,
446
+ functionDecl (hasOverloadedOperatorName (" +" )),
447
+ functionDecl (hasOverloadedOperatorName (" -" )));
448
+ EXPECT_FALSE (testStructuralMatch (t));
449
+ }
450
+
451
+ TEST_F (StructuralEquivalenceCXXMethodTest, OutOfClass1) {
452
+ auto t = makeDecls<FunctionDecl>(
453
+ " struct X { virtual void f(); }; void X::f() { }" ,
454
+ " struct X { virtual void f() { }; };" ,
455
+ Lang_CXX,
456
+ functionDecl (allOf (hasName (" f" ), isDefinition ())));
457
+ EXPECT_TRUE (testStructuralMatch (t));
458
+ }
459
+
460
+ TEST_F (StructuralEquivalenceCXXMethodTest, OutOfClass2) {
461
+ auto t = makeDecls<FunctionDecl>(
462
+ " struct X { virtual void f(); }; void X::f() { }" ,
463
+ " struct X { void f(); }; void X::f() { }" ,
464
+ Lang_CXX,
465
+ functionDecl (allOf (hasName (" f" ), isDefinition ())));
466
+ EXPECT_FALSE (testStructuralMatch (t));
467
+ }
468
+
469
+ struct StructuralEquivalenceRecordTest : StructuralEquivalenceTest {
470
+ };
471
+
472
+ TEST_F (StructuralEquivalenceRecordTest, Name) {
473
+ auto t = makeDecls<CXXRecordDecl>(
474
+ " struct A{ };" ,
475
+ " struct B{ };" ,
476
+ Lang_CXX,
477
+ cxxRecordDecl ());
478
+ EXPECT_FALSE (testStructuralMatch (t));
479
+ }
480
+
481
+ TEST_F (StructuralEquivalenceRecordTest, Fields) {
482
+ auto t = makeNamedDecls (
483
+ " struct foo{ int x; };" ,
484
+ " struct foo{ char x; };" ,
485
+ Lang_CXX);
486
+ EXPECT_FALSE (testStructuralMatch (t));
487
+ }
488
+
489
+ TEST_F (StructuralEquivalenceRecordTest, DISABLED_Methods) {
490
+ // Currently, methods of a class are not checked at class equivalence.
491
+ auto t = makeNamedDecls (
492
+ " struct foo{ int x(); };" ,
493
+ " struct foo{ char x(); };" ,
494
+ Lang_CXX);
495
+ EXPECT_FALSE (testStructuralMatch (t));
496
+ }
497
+
498
+ TEST_F (StructuralEquivalenceRecordTest, Bases) {
499
+ auto t = makeNamedDecls (
500
+ " struct A{ }; struct foo: A { };" ,
501
+ " struct B{ }; struct foo: B { };" ,
502
+ Lang_CXX);
503
+ EXPECT_FALSE (testStructuralMatch (t));
504
+ }
505
+
506
+ TEST_F (StructuralEquivalenceRecordTest, InheritanceVirtual) {
507
+ auto t = makeNamedDecls (
508
+ " struct A{ }; struct foo: A { };" ,
509
+ " struct A{ }; struct foo: virtual A { };" ,
510
+ Lang_CXX);
511
+ EXPECT_FALSE (testStructuralMatch (t));
512
+ }
513
+
514
+ TEST_F (StructuralEquivalenceRecordTest, DISABLED_InheritanceType) {
515
+ // Access specifier in inheritance is not checked yet.
516
+ auto t = makeNamedDecls (
517
+ " struct A{ }; struct foo: public A { };" ,
518
+ " struct A{ }; struct foo: private A { };" ,
519
+ Lang_CXX);
520
+ EXPECT_FALSE (testStructuralMatch (t));
521
+ }
522
+
523
+ TEST_F (StructuralEquivalenceRecordTest, Match) {
524
+ auto Code = R"(
525
+ struct A{ };
526
+ struct B{ };
527
+ struct foo: A, virtual B {
528
+ void x();
529
+ int a;
530
+ };
531
+ )" ;
532
+ auto t = makeNamedDecls (Code, Code, Lang_CXX);
533
+ EXPECT_TRUE (testStructuralMatch (t));
534
+ }
535
+
536
+ TEST_F (StructuralEquivalenceTest, CompareSameDeclWithMultiple) {
537
+ auto t = makeNamedDecls (
538
+ " struct A{ }; struct B{ }; void foo(A a, A b);" ,
539
+ " struct A{ }; struct B{ }; void foo(A a, B b);" ,
540
+ Lang_CXX);
541
+ EXPECT_FALSE (testStructuralMatch (t));
542
+ }
543
+
206
544
} // end namespace ast_matchers
207
545
} // end namespace clang
0 commit comments