1 //===--- ASTStructuralEquivalence.cpp - -------------------------*- C++ -*-===// 2 // 3 // The LLVM Compiler Infrastructure 4 // 5 // This file is distributed under the University of Illinois Open Source 6 // License. See LICENSE.TXT for details. 7 // 8 //===----------------------------------------------------------------------===// 9 // 10 // This file implement StructuralEquivalenceContext class and helper functions 11 // for layout matching. 12 // 13 //===----------------------------------------------------------------------===// 14 15 #include "clang/AST/ASTStructuralEquivalence.h" 16 #include "clang/AST/ASTContext.h" 17 #include "clang/AST/ASTDiagnostic.h" 18 #include "clang/AST/ASTImporter.h" 19 #include "clang/AST/DeclCXX.h" 20 #include "clang/AST/DeclObjC.h" 21 #include "clang/AST/DeclVisitor.h" 22 #include "clang/AST/StmtVisitor.h" 23 #include "clang/AST/TypeVisitor.h" 24 #include "clang/Basic/SourceManager.h" 25 26 namespace { 27 28 using namespace clang; 29 30 static bool IsStructurallyEquivalent(StructuralEquivalenceContext &Context, 31 QualType T1, QualType T2); 32 static bool IsStructurallyEquivalent(StructuralEquivalenceContext &Context, 33 Decl *D1, Decl *D2); 34 static bool IsStructurallyEquivalent(StructuralEquivalenceContext &Context, 35 const TemplateArgument &Arg1, 36 const TemplateArgument &Arg2); 37 38 /// Determine structural equivalence of two expressions. 39 static bool IsStructurallyEquivalent(StructuralEquivalenceContext &Context, 40 Expr *E1, Expr *E2) { 41 if (!E1 || !E2) 42 return E1 == E2; 43 44 // FIXME: Actually perform a structural comparison! 45 return true; 46 } 47 48 /// Determine whether two identifiers are equivalent. 49 static bool IsStructurallyEquivalent(const IdentifierInfo *Name1, 50 const IdentifierInfo *Name2) { 51 if (!Name1 || !Name2) 52 return Name1 == Name2; 53 54 return Name1->getName() == Name2->getName(); 55 } 56 57 /// Determine whether two nested-name-specifiers are equivalent. 58 static bool IsStructurallyEquivalent(StructuralEquivalenceContext &Context, 59 NestedNameSpecifier *NNS1, 60 NestedNameSpecifier *NNS2) { 61 if (NNS1->getKind() != NNS2->getKind()) 62 return false; 63 64 NestedNameSpecifier *Prefix1 = NNS1->getPrefix(), 65 *Prefix2 = NNS2->getPrefix(); 66 if ((bool)Prefix1 != (bool)Prefix2) 67 return false; 68 69 if (Prefix1) 70 if (!IsStructurallyEquivalent(Context, Prefix1, Prefix2)) 71 return false; 72 73 switch (NNS1->getKind()) { 74 case NestedNameSpecifier::Identifier: 75 return IsStructurallyEquivalent(NNS1->getAsIdentifier(), 76 NNS2->getAsIdentifier()); 77 case NestedNameSpecifier::Namespace: 78 return IsStructurallyEquivalent(Context, NNS1->getAsNamespace(), 79 NNS2->getAsNamespace()); 80 case NestedNameSpecifier::NamespaceAlias: 81 return IsStructurallyEquivalent(Context, NNS1->getAsNamespaceAlias(), 82 NNS2->getAsNamespaceAlias()); 83 case NestedNameSpecifier::TypeSpec: 84 case NestedNameSpecifier::TypeSpecWithTemplate: 85 return IsStructurallyEquivalent(Context, QualType(NNS1->getAsType(), 0), 86 QualType(NNS2->getAsType(), 0)); 87 case NestedNameSpecifier::Global: 88 return true; 89 case NestedNameSpecifier::Super: 90 return IsStructurallyEquivalent(Context, NNS1->getAsRecordDecl(), 91 NNS2->getAsRecordDecl()); 92 } 93 return false; 94 } 95 96 static bool IsStructurallyEquivalent(StructuralEquivalenceContext &Context, 97 const TemplateName &N1, 98 const TemplateName &N2) { 99 if (N1.getKind() != N2.getKind()) 100 return false; 101 switch (N1.getKind()) { 102 case TemplateName::Template: 103 return IsStructurallyEquivalent(Context, N1.getAsTemplateDecl(), 104 N2.getAsTemplateDecl()); 105 106 case TemplateName::OverloadedTemplate: { 107 OverloadedTemplateStorage *OS1 = N1.getAsOverloadedTemplate(), 108 *OS2 = N2.getAsOverloadedTemplate(); 109 OverloadedTemplateStorage::iterator I1 = OS1->begin(), I2 = OS2->begin(), 110 E1 = OS1->end(), E2 = OS2->end(); 111 for (; I1 != E1 && I2 != E2; ++I1, ++I2) 112 if (!IsStructurallyEquivalent(Context, *I1, *I2)) 113 return false; 114 return I1 == E1 && I2 == E2; 115 } 116 117 case TemplateName::QualifiedTemplate: { 118 QualifiedTemplateName *QN1 = N1.getAsQualifiedTemplateName(), 119 *QN2 = N2.getAsQualifiedTemplateName(); 120 return IsStructurallyEquivalent(Context, QN1->getDecl(), QN2->getDecl()) && 121 IsStructurallyEquivalent(Context, QN1->getQualifier(), 122 QN2->getQualifier()); 123 } 124 125 case TemplateName::DependentTemplate: { 126 DependentTemplateName *DN1 = N1.getAsDependentTemplateName(), 127 *DN2 = N2.getAsDependentTemplateName(); 128 if (!IsStructurallyEquivalent(Context, DN1->getQualifier(), 129 DN2->getQualifier())) 130 return false; 131 if (DN1->isIdentifier() && DN2->isIdentifier()) 132 return IsStructurallyEquivalent(DN1->getIdentifier(), 133 DN2->getIdentifier()); 134 else if (DN1->isOverloadedOperator() && DN2->isOverloadedOperator()) 135 return DN1->getOperator() == DN2->getOperator(); 136 return false; 137 } 138 139 case TemplateName::SubstTemplateTemplateParm: { 140 SubstTemplateTemplateParmStorage *TS1 = N1.getAsSubstTemplateTemplateParm(), 141 *TS2 = N2.getAsSubstTemplateTemplateParm(); 142 return IsStructurallyEquivalent(Context, TS1->getParameter(), 143 TS2->getParameter()) && 144 IsStructurallyEquivalent(Context, TS1->getReplacement(), 145 TS2->getReplacement()); 146 } 147 case TemplateName::SubstTemplateTemplateParmPack: { 148 SubstTemplateTemplateParmPackStorage 149 *P1 = N1.getAsSubstTemplateTemplateParmPack(), 150 *P2 = N2.getAsSubstTemplateTemplateParmPack(); 151 return IsStructurallyEquivalent(Context, P1->getArgumentPack(), 152 P2->getArgumentPack()) && 153 IsStructurallyEquivalent(Context, P1->getParameterPack(), 154 P2->getParameterPack()); 155 } 156 } 157 return false; 158 } 159 160 /// Determine whether two template arguments are equivalent. 161 static bool IsStructurallyEquivalent(StructuralEquivalenceContext &Context, 162 const TemplateArgument &Arg1, 163 const TemplateArgument &Arg2) { 164 if (Arg1.getKind() != Arg2.getKind()) 165 return false; 166 167 switch (Arg1.getKind()) { 168 case TemplateArgument::Null: 169 return true; 170 171 case TemplateArgument::Type: 172 return Context.IsStructurallyEquivalent(Arg1.getAsType(), Arg2.getAsType()); 173 174 case TemplateArgument::Integral: 175 if (!Context.IsStructurallyEquivalent(Arg1.getIntegralType(), 176 Arg2.getIntegralType())) 177 return false; 178 179 return llvm::APSInt::isSameValue(Arg1.getAsIntegral(), 180 Arg2.getAsIntegral()); 181 182 case TemplateArgument::Declaration: 183 return Context.IsStructurallyEquivalent(Arg1.getAsDecl(), Arg2.getAsDecl()); 184 185 case TemplateArgument::NullPtr: 186 return true; // FIXME: Is this correct? 187 188 case TemplateArgument::Template: 189 return IsStructurallyEquivalent(Context, Arg1.getAsTemplate(), 190 Arg2.getAsTemplate()); 191 192 case TemplateArgument::TemplateExpansion: 193 return IsStructurallyEquivalent(Context, 194 Arg1.getAsTemplateOrTemplatePattern(), 195 Arg2.getAsTemplateOrTemplatePattern()); 196 197 case TemplateArgument::Expression: 198 return IsStructurallyEquivalent(Context, Arg1.getAsExpr(), 199 Arg2.getAsExpr()); 200 201 case TemplateArgument::Pack: 202 if (Arg1.pack_size() != Arg2.pack_size()) 203 return false; 204 205 for (unsigned I = 0, N = Arg1.pack_size(); I != N; ++I) 206 if (!IsStructurallyEquivalent(Context, Arg1.pack_begin()[I], 207 Arg2.pack_begin()[I])) 208 return false; 209 210 return true; 211 } 212 213 llvm_unreachable("Invalid template argument kind"); 214 } 215 216 /// Determine structural equivalence for the common part of array 217 /// types. 218 static bool IsArrayStructurallyEquivalent(StructuralEquivalenceContext &Context, 219 const ArrayType *Array1, 220 const ArrayType *Array2) { 221 if (!IsStructurallyEquivalent(Context, Array1->getElementType(), 222 Array2->getElementType())) 223 return false; 224 if (Array1->getSizeModifier() != Array2->getSizeModifier()) 225 return false; 226 if (Array1->getIndexTypeQualifiers() != Array2->getIndexTypeQualifiers()) 227 return false; 228 229 return true; 230 } 231 232 /// Determine structural equivalence of two types. 233 static bool IsStructurallyEquivalent(StructuralEquivalenceContext &Context, 234 QualType T1, QualType T2) { 235 if (T1.isNull() || T2.isNull()) 236 return T1.isNull() && T2.isNull(); 237 238 if (!Context.StrictTypeSpelling) { 239 // We aren't being strict about token-to-token equivalence of types, 240 // so map down to the canonical type. 241 T1 = Context.FromCtx.getCanonicalType(T1); 242 T2 = Context.ToCtx.getCanonicalType(T2); 243 } 244 245 if (T1.getQualifiers() != T2.getQualifiers()) 246 return false; 247 248 Type::TypeClass TC = T1->getTypeClass(); 249 250 if (T1->getTypeClass() != T2->getTypeClass()) { 251 // Compare function types with prototypes vs. without prototypes as if 252 // both did not have prototypes. 253 if (T1->getTypeClass() == Type::FunctionProto && 254 T2->getTypeClass() == Type::FunctionNoProto) 255 TC = Type::FunctionNoProto; 256 else if (T1->getTypeClass() == Type::FunctionNoProto && 257 T2->getTypeClass() == Type::FunctionProto) 258 TC = Type::FunctionNoProto; 259 else 260 return false; 261 } 262 263 switch (TC) { 264 case Type::Builtin: 265 // FIXME: Deal with Char_S/Char_U. 266 if (cast<BuiltinType>(T1)->getKind() != cast<BuiltinType>(T2)->getKind()) 267 return false; 268 break; 269 270 case Type::Complex: 271 if (!IsStructurallyEquivalent(Context, 272 cast<ComplexType>(T1)->getElementType(), 273 cast<ComplexType>(T2)->getElementType())) 274 return false; 275 break; 276 277 case Type::Adjusted: 278 case Type::Decayed: 279 if (!IsStructurallyEquivalent(Context, 280 cast<AdjustedType>(T1)->getOriginalType(), 281 cast<AdjustedType>(T2)->getOriginalType())) 282 return false; 283 break; 284 285 case Type::Pointer: 286 if (!IsStructurallyEquivalent(Context, 287 cast<PointerType>(T1)->getPointeeType(), 288 cast<PointerType>(T2)->getPointeeType())) 289 return false; 290 break; 291 292 case Type::BlockPointer: 293 if (!IsStructurallyEquivalent(Context, 294 cast<BlockPointerType>(T1)->getPointeeType(), 295 cast<BlockPointerType>(T2)->getPointeeType())) 296 return false; 297 break; 298 299 case Type::LValueReference: 300 case Type::RValueReference: { 301 const ReferenceType *Ref1 = cast<ReferenceType>(T1); 302 const ReferenceType *Ref2 = cast<ReferenceType>(T2); 303 if (Ref1->isSpelledAsLValue() != Ref2->isSpelledAsLValue()) 304 return false; 305 if (Ref1->isInnerRef() != Ref2->isInnerRef()) 306 return false; 307 if (!IsStructurallyEquivalent(Context, Ref1->getPointeeTypeAsWritten(), 308 Ref2->getPointeeTypeAsWritten())) 309 return false; 310 break; 311 } 312 313 case Type::MemberPointer: { 314 const MemberPointerType *MemPtr1 = cast<MemberPointerType>(T1); 315 const MemberPointerType *MemPtr2 = cast<MemberPointerType>(T2); 316 if (!IsStructurallyEquivalent(Context, MemPtr1->getPointeeType(), 317 MemPtr2->getPointeeType())) 318 return false; 319 if (!IsStructurallyEquivalent(Context, QualType(MemPtr1->getClass(), 0), 320 QualType(MemPtr2->getClass(), 0))) 321 return false; 322 break; 323 } 324 325 case Type::ConstantArray: { 326 const ConstantArrayType *Array1 = cast<ConstantArrayType>(T1); 327 const ConstantArrayType *Array2 = cast<ConstantArrayType>(T2); 328 if (!llvm::APInt::isSameValue(Array1->getSize(), Array2->getSize())) 329 return false; 330 331 if (!IsArrayStructurallyEquivalent(Context, Array1, Array2)) 332 return false; 333 break; 334 } 335 336 case Type::IncompleteArray: 337 if (!IsArrayStructurallyEquivalent(Context, cast<ArrayType>(T1), 338 cast<ArrayType>(T2))) 339 return false; 340 break; 341 342 case Type::VariableArray: { 343 const VariableArrayType *Array1 = cast<VariableArrayType>(T1); 344 const VariableArrayType *Array2 = cast<VariableArrayType>(T2); 345 if (!IsStructurallyEquivalent(Context, Array1->getSizeExpr(), 346 Array2->getSizeExpr())) 347 return false; 348 349 if (!IsArrayStructurallyEquivalent(Context, Array1, Array2)) 350 return false; 351 352 break; 353 } 354 355 case Type::DependentSizedArray: { 356 const DependentSizedArrayType *Array1 = cast<DependentSizedArrayType>(T1); 357 const DependentSizedArrayType *Array2 = cast<DependentSizedArrayType>(T2); 358 if (!IsStructurallyEquivalent(Context, Array1->getSizeExpr(), 359 Array2->getSizeExpr())) 360 return false; 361 362 if (!IsArrayStructurallyEquivalent(Context, Array1, Array2)) 363 return false; 364 365 break; 366 } 367 368 case Type::DependentSizedExtVector: { 369 const DependentSizedExtVectorType *Vec1 = 370 cast<DependentSizedExtVectorType>(T1); 371 const DependentSizedExtVectorType *Vec2 = 372 cast<DependentSizedExtVectorType>(T2); 373 if (!IsStructurallyEquivalent(Context, Vec1->getSizeExpr(), 374 Vec2->getSizeExpr())) 375 return false; 376 if (!IsStructurallyEquivalent(Context, Vec1->getElementType(), 377 Vec2->getElementType())) 378 return false; 379 break; 380 } 381 382 case Type::Vector: 383 case Type::ExtVector: { 384 const VectorType *Vec1 = cast<VectorType>(T1); 385 const VectorType *Vec2 = cast<VectorType>(T2); 386 if (!IsStructurallyEquivalent(Context, Vec1->getElementType(), 387 Vec2->getElementType())) 388 return false; 389 if (Vec1->getNumElements() != Vec2->getNumElements()) 390 return false; 391 if (Vec1->getVectorKind() != Vec2->getVectorKind()) 392 return false; 393 break; 394 } 395 396 case Type::FunctionProto: { 397 const FunctionProtoType *Proto1 = cast<FunctionProtoType>(T1); 398 const FunctionProtoType *Proto2 = cast<FunctionProtoType>(T2); 399 if (Proto1->getNumParams() != Proto2->getNumParams()) 400 return false; 401 for (unsigned I = 0, N = Proto1->getNumParams(); I != N; ++I) { 402 if (!IsStructurallyEquivalent(Context, Proto1->getParamType(I), 403 Proto2->getParamType(I))) 404 return false; 405 } 406 if (Proto1->isVariadic() != Proto2->isVariadic()) 407 return false; 408 if (Proto1->getExceptionSpecType() != Proto2->getExceptionSpecType()) 409 return false; 410 if (Proto1->getExceptionSpecType() == EST_Dynamic) { 411 if (Proto1->getNumExceptions() != Proto2->getNumExceptions()) 412 return false; 413 for (unsigned I = 0, N = Proto1->getNumExceptions(); I != N; ++I) { 414 if (!IsStructurallyEquivalent(Context, Proto1->getExceptionType(I), 415 Proto2->getExceptionType(I))) 416 return false; 417 } 418 } else if (Proto1->getExceptionSpecType() == EST_ComputedNoexcept) { 419 if (!IsStructurallyEquivalent(Context, Proto1->getNoexceptExpr(), 420 Proto2->getNoexceptExpr())) 421 return false; 422 } 423 if (Proto1->getTypeQuals() != Proto2->getTypeQuals()) 424 return false; 425 426 // Fall through to check the bits common with FunctionNoProtoType. 427 } 428 429 case Type::FunctionNoProto: { 430 const FunctionType *Function1 = cast<FunctionType>(T1); 431 const FunctionType *Function2 = cast<FunctionType>(T2); 432 if (!IsStructurallyEquivalent(Context, Function1->getReturnType(), 433 Function2->getReturnType())) 434 return false; 435 if (Function1->getExtInfo() != Function2->getExtInfo()) 436 return false; 437 break; 438 } 439 440 case Type::UnresolvedUsing: 441 if (!IsStructurallyEquivalent(Context, 442 cast<UnresolvedUsingType>(T1)->getDecl(), 443 cast<UnresolvedUsingType>(T2)->getDecl())) 444 return false; 445 446 break; 447 448 case Type::Attributed: 449 if (!IsStructurallyEquivalent(Context, 450 cast<AttributedType>(T1)->getModifiedType(), 451 cast<AttributedType>(T2)->getModifiedType())) 452 return false; 453 if (!IsStructurallyEquivalent( 454 Context, cast<AttributedType>(T1)->getEquivalentType(), 455 cast<AttributedType>(T2)->getEquivalentType())) 456 return false; 457 break; 458 459 case Type::Paren: 460 if (!IsStructurallyEquivalent(Context, cast<ParenType>(T1)->getInnerType(), 461 cast<ParenType>(T2)->getInnerType())) 462 return false; 463 break; 464 465 case Type::Typedef: 466 if (!IsStructurallyEquivalent(Context, cast<TypedefType>(T1)->getDecl(), 467 cast<TypedefType>(T2)->getDecl())) 468 return false; 469 break; 470 471 case Type::TypeOfExpr: 472 if (!IsStructurallyEquivalent( 473 Context, cast<TypeOfExprType>(T1)->getUnderlyingExpr(), 474 cast<TypeOfExprType>(T2)->getUnderlyingExpr())) 475 return false; 476 break; 477 478 case Type::TypeOf: 479 if (!IsStructurallyEquivalent(Context, 480 cast<TypeOfType>(T1)->getUnderlyingType(), 481 cast<TypeOfType>(T2)->getUnderlyingType())) 482 return false; 483 break; 484 485 case Type::UnaryTransform: 486 if (!IsStructurallyEquivalent( 487 Context, cast<UnaryTransformType>(T1)->getUnderlyingType(), 488 cast<UnaryTransformType>(T1)->getUnderlyingType())) 489 return false; 490 break; 491 492 case Type::Decltype: 493 if (!IsStructurallyEquivalent(Context, 494 cast<DecltypeType>(T1)->getUnderlyingExpr(), 495 cast<DecltypeType>(T2)->getUnderlyingExpr())) 496 return false; 497 break; 498 499 case Type::Auto: 500 if (!IsStructurallyEquivalent(Context, cast<AutoType>(T1)->getDeducedType(), 501 cast<AutoType>(T2)->getDeducedType())) 502 return false; 503 break; 504 505 case Type::DeducedTemplateSpecialization: { 506 auto *DT1 = cast<DeducedTemplateSpecializationType>(T1); 507 auto *DT2 = cast<DeducedTemplateSpecializationType>(T2); 508 if (!IsStructurallyEquivalent(Context, DT1->getTemplateName(), 509 DT2->getTemplateName())) 510 return false; 511 if (!IsStructurallyEquivalent(Context, DT1->getDeducedType(), 512 DT2->getDeducedType())) 513 return false; 514 break; 515 } 516 517 case Type::Record: 518 case Type::Enum: 519 if (!IsStructurallyEquivalent(Context, cast<TagType>(T1)->getDecl(), 520 cast<TagType>(T2)->getDecl())) 521 return false; 522 break; 523 524 case Type::TemplateTypeParm: { 525 const TemplateTypeParmType *Parm1 = cast<TemplateTypeParmType>(T1); 526 const TemplateTypeParmType *Parm2 = cast<TemplateTypeParmType>(T2); 527 if (Parm1->getDepth() != Parm2->getDepth()) 528 return false; 529 if (Parm1->getIndex() != Parm2->getIndex()) 530 return false; 531 if (Parm1->isParameterPack() != Parm2->isParameterPack()) 532 return false; 533 534 // Names of template type parameters are never significant. 535 break; 536 } 537 538 case Type::SubstTemplateTypeParm: { 539 const SubstTemplateTypeParmType *Subst1 = 540 cast<SubstTemplateTypeParmType>(T1); 541 const SubstTemplateTypeParmType *Subst2 = 542 cast<SubstTemplateTypeParmType>(T2); 543 if (!IsStructurallyEquivalent(Context, 544 QualType(Subst1->getReplacedParameter(), 0), 545 QualType(Subst2->getReplacedParameter(), 0))) 546 return false; 547 if (!IsStructurallyEquivalent(Context, Subst1->getReplacementType(), 548 Subst2->getReplacementType())) 549 return false; 550 break; 551 } 552 553 case Type::SubstTemplateTypeParmPack: { 554 const SubstTemplateTypeParmPackType *Subst1 = 555 cast<SubstTemplateTypeParmPackType>(T1); 556 const SubstTemplateTypeParmPackType *Subst2 = 557 cast<SubstTemplateTypeParmPackType>(T2); 558 if (!IsStructurallyEquivalent(Context, 559 QualType(Subst1->getReplacedParameter(), 0), 560 QualType(Subst2->getReplacedParameter(), 0))) 561 return false; 562 if (!IsStructurallyEquivalent(Context, Subst1->getArgumentPack(), 563 Subst2->getArgumentPack())) 564 return false; 565 break; 566 } 567 case Type::TemplateSpecialization: { 568 const TemplateSpecializationType *Spec1 = 569 cast<TemplateSpecializationType>(T1); 570 const TemplateSpecializationType *Spec2 = 571 cast<TemplateSpecializationType>(T2); 572 if (!IsStructurallyEquivalent(Context, Spec1->getTemplateName(), 573 Spec2->getTemplateName())) 574 return false; 575 if (Spec1->getNumArgs() != Spec2->getNumArgs()) 576 return false; 577 for (unsigned I = 0, N = Spec1->getNumArgs(); I != N; ++I) { 578 if (!IsStructurallyEquivalent(Context, Spec1->getArg(I), 579 Spec2->getArg(I))) 580 return false; 581 } 582 break; 583 } 584 585 case Type::Elaborated: { 586 const ElaboratedType *Elab1 = cast<ElaboratedType>(T1); 587 const ElaboratedType *Elab2 = cast<ElaboratedType>(T2); 588 // CHECKME: what if a keyword is ETK_None or ETK_typename ? 589 if (Elab1->getKeyword() != Elab2->getKeyword()) 590 return false; 591 if (!IsStructurallyEquivalent(Context, Elab1->getQualifier(), 592 Elab2->getQualifier())) 593 return false; 594 if (!IsStructurallyEquivalent(Context, Elab1->getNamedType(), 595 Elab2->getNamedType())) 596 return false; 597 break; 598 } 599 600 case Type::InjectedClassName: { 601 const InjectedClassNameType *Inj1 = cast<InjectedClassNameType>(T1); 602 const InjectedClassNameType *Inj2 = cast<InjectedClassNameType>(T2); 603 if (!IsStructurallyEquivalent(Context, 604 Inj1->getInjectedSpecializationType(), 605 Inj2->getInjectedSpecializationType())) 606 return false; 607 break; 608 } 609 610 case Type::DependentName: { 611 const DependentNameType *Typename1 = cast<DependentNameType>(T1); 612 const DependentNameType *Typename2 = cast<DependentNameType>(T2); 613 if (!IsStructurallyEquivalent(Context, Typename1->getQualifier(), 614 Typename2->getQualifier())) 615 return false; 616 if (!IsStructurallyEquivalent(Typename1->getIdentifier(), 617 Typename2->getIdentifier())) 618 return false; 619 620 break; 621 } 622 623 case Type::DependentTemplateSpecialization: { 624 const DependentTemplateSpecializationType *Spec1 = 625 cast<DependentTemplateSpecializationType>(T1); 626 const DependentTemplateSpecializationType *Spec2 = 627 cast<DependentTemplateSpecializationType>(T2); 628 if (!IsStructurallyEquivalent(Context, Spec1->getQualifier(), 629 Spec2->getQualifier())) 630 return false; 631 if (!IsStructurallyEquivalent(Spec1->getIdentifier(), 632 Spec2->getIdentifier())) 633 return false; 634 if (Spec1->getNumArgs() != Spec2->getNumArgs()) 635 return false; 636 for (unsigned I = 0, N = Spec1->getNumArgs(); I != N; ++I) { 637 if (!IsStructurallyEquivalent(Context, Spec1->getArg(I), 638 Spec2->getArg(I))) 639 return false; 640 } 641 break; 642 } 643 644 case Type::PackExpansion: 645 if (!IsStructurallyEquivalent(Context, 646 cast<PackExpansionType>(T1)->getPattern(), 647 cast<PackExpansionType>(T2)->getPattern())) 648 return false; 649 break; 650 651 case Type::ObjCInterface: { 652 const ObjCInterfaceType *Iface1 = cast<ObjCInterfaceType>(T1); 653 const ObjCInterfaceType *Iface2 = cast<ObjCInterfaceType>(T2); 654 if (!IsStructurallyEquivalent(Context, Iface1->getDecl(), 655 Iface2->getDecl())) 656 return false; 657 break; 658 } 659 660 case Type::ObjCTypeParam: { 661 const ObjCTypeParamType *Obj1 = cast<ObjCTypeParamType>(T1); 662 const ObjCTypeParamType *Obj2 = cast<ObjCTypeParamType>(T2); 663 if (!IsStructurallyEquivalent(Context, Obj1->getDecl(), Obj2->getDecl())) 664 return false; 665 666 if (Obj1->getNumProtocols() != Obj2->getNumProtocols()) 667 return false; 668 for (unsigned I = 0, N = Obj1->getNumProtocols(); I != N; ++I) { 669 if (!IsStructurallyEquivalent(Context, Obj1->getProtocol(I), 670 Obj2->getProtocol(I))) 671 return false; 672 } 673 break; 674 } 675 case Type::ObjCObject: { 676 const ObjCObjectType *Obj1 = cast<ObjCObjectType>(T1); 677 const ObjCObjectType *Obj2 = cast<ObjCObjectType>(T2); 678 if (!IsStructurallyEquivalent(Context, Obj1->getBaseType(), 679 Obj2->getBaseType())) 680 return false; 681 if (Obj1->getNumProtocols() != Obj2->getNumProtocols()) 682 return false; 683 for (unsigned I = 0, N = Obj1->getNumProtocols(); I != N; ++I) { 684 if (!IsStructurallyEquivalent(Context, Obj1->getProtocol(I), 685 Obj2->getProtocol(I))) 686 return false; 687 } 688 break; 689 } 690 691 case Type::ObjCObjectPointer: { 692 const ObjCObjectPointerType *Ptr1 = cast<ObjCObjectPointerType>(T1); 693 const ObjCObjectPointerType *Ptr2 = cast<ObjCObjectPointerType>(T2); 694 if (!IsStructurallyEquivalent(Context, Ptr1->getPointeeType(), 695 Ptr2->getPointeeType())) 696 return false; 697 break; 698 } 699 700 case Type::Atomic: { 701 if (!IsStructurallyEquivalent(Context, cast<AtomicType>(T1)->getValueType(), 702 cast<AtomicType>(T2)->getValueType())) 703 return false; 704 break; 705 } 706 707 case Type::Pipe: { 708 if (!IsStructurallyEquivalent(Context, cast<PipeType>(T1)->getElementType(), 709 cast<PipeType>(T2)->getElementType())) 710 return false; 711 break; 712 } 713 714 } // end switch 715 716 return true; 717 } 718 719 /// Determine structural equivalence of two fields. 720 static bool IsStructurallyEquivalent(StructuralEquivalenceContext &Context, 721 FieldDecl *Field1, FieldDecl *Field2) { 722 RecordDecl *Owner2 = cast<RecordDecl>(Field2->getDeclContext()); 723 724 // For anonymous structs/unions, match up the anonymous struct/union type 725 // declarations directly, so that we don't go off searching for anonymous 726 // types 727 if (Field1->isAnonymousStructOrUnion() && 728 Field2->isAnonymousStructOrUnion()) { 729 RecordDecl *D1 = Field1->getType()->castAs<RecordType>()->getDecl(); 730 RecordDecl *D2 = Field2->getType()->castAs<RecordType>()->getDecl(); 731 return IsStructurallyEquivalent(Context, D1, D2); 732 } 733 734 // Check for equivalent field names. 735 IdentifierInfo *Name1 = Field1->getIdentifier(); 736 IdentifierInfo *Name2 = Field2->getIdentifier(); 737 if (!::IsStructurallyEquivalent(Name1, Name2)) 738 return false; 739 740 if (!IsStructurallyEquivalent(Context, Field1->getType(), 741 Field2->getType())) { 742 if (Context.Complain) { 743 Context.Diag2(Owner2->getLocation(), diag::warn_odr_tag_type_inconsistent) 744 << Context.ToCtx.getTypeDeclType(Owner2); 745 Context.Diag2(Field2->getLocation(), diag::note_odr_field) 746 << Field2->getDeclName() << Field2->getType(); 747 Context.Diag1(Field1->getLocation(), diag::note_odr_field) 748 << Field1->getDeclName() << Field1->getType(); 749 } 750 return false; 751 } 752 753 if (Field1->isBitField() != Field2->isBitField()) { 754 if (Context.Complain) { 755 Context.Diag2(Owner2->getLocation(), diag::warn_odr_tag_type_inconsistent) 756 << Context.ToCtx.getTypeDeclType(Owner2); 757 if (Field1->isBitField()) { 758 Context.Diag1(Field1->getLocation(), diag::note_odr_bit_field) 759 << Field1->getDeclName() << Field1->getType() 760 << Field1->getBitWidthValue(Context.FromCtx); 761 Context.Diag2(Field2->getLocation(), diag::note_odr_not_bit_field) 762 << Field2->getDeclName(); 763 } else { 764 Context.Diag2(Field2->getLocation(), diag::note_odr_bit_field) 765 << Field2->getDeclName() << Field2->getType() 766 << Field2->getBitWidthValue(Context.ToCtx); 767 Context.Diag1(Field1->getLocation(), diag::note_odr_not_bit_field) 768 << Field1->getDeclName(); 769 } 770 } 771 return false; 772 } 773 774 if (Field1->isBitField()) { 775 // Make sure that the bit-fields are the same length. 776 unsigned Bits1 = Field1->getBitWidthValue(Context.FromCtx); 777 unsigned Bits2 = Field2->getBitWidthValue(Context.ToCtx); 778 779 if (Bits1 != Bits2) { 780 if (Context.Complain) { 781 Context.Diag2(Owner2->getLocation(), 782 diag::warn_odr_tag_type_inconsistent) 783 << Context.ToCtx.getTypeDeclType(Owner2); 784 Context.Diag2(Field2->getLocation(), diag::note_odr_bit_field) 785 << Field2->getDeclName() << Field2->getType() << Bits2; 786 Context.Diag1(Field1->getLocation(), diag::note_odr_bit_field) 787 << Field1->getDeclName() << Field1->getType() << Bits1; 788 } 789 return false; 790 } 791 } 792 793 return true; 794 } 795 796 /// Determine structural equivalence of two records. 797 static bool IsStructurallyEquivalent(StructuralEquivalenceContext &Context, 798 RecordDecl *D1, RecordDecl *D2) { 799 if (D1->isUnion() != D2->isUnion()) { 800 if (Context.Complain) { 801 Context.Diag2(D2->getLocation(), diag::warn_odr_tag_type_inconsistent) 802 << Context.ToCtx.getTypeDeclType(D2); 803 Context.Diag1(D1->getLocation(), diag::note_odr_tag_kind_here) 804 << D1->getDeclName() << (unsigned)D1->getTagKind(); 805 } 806 return false; 807 } 808 809 if (D1->isAnonymousStructOrUnion() && D2->isAnonymousStructOrUnion()) { 810 // If both anonymous structs/unions are in a record context, make sure 811 // they occur in the same location in the context records. 812 if (Optional<unsigned> Index1 = 813 StructuralEquivalenceContext::findUntaggedStructOrUnionIndex(D1)) { 814 if (Optional<unsigned> Index2 = 815 StructuralEquivalenceContext::findUntaggedStructOrUnionIndex( 816 D2)) { 817 if (*Index1 != *Index2) 818 return false; 819 } 820 } 821 } 822 823 // If both declarations are class template specializations, we know 824 // the ODR applies, so check the template and template arguments. 825 ClassTemplateSpecializationDecl *Spec1 = 826 dyn_cast<ClassTemplateSpecializationDecl>(D1); 827 ClassTemplateSpecializationDecl *Spec2 = 828 dyn_cast<ClassTemplateSpecializationDecl>(D2); 829 if (Spec1 && Spec2) { 830 // Check that the specialized templates are the same. 831 if (!IsStructurallyEquivalent(Context, Spec1->getSpecializedTemplate(), 832 Spec2->getSpecializedTemplate())) 833 return false; 834 835 // Check that the template arguments are the same. 836 if (Spec1->getTemplateArgs().size() != Spec2->getTemplateArgs().size()) 837 return false; 838 839 for (unsigned I = 0, N = Spec1->getTemplateArgs().size(); I != N; ++I) 840 if (!IsStructurallyEquivalent(Context, Spec1->getTemplateArgs().get(I), 841 Spec2->getTemplateArgs().get(I))) 842 return false; 843 } 844 // If one is a class template specialization and the other is not, these 845 // structures are different. 846 else if (Spec1 || Spec2) 847 return false; 848 849 // Compare the definitions of these two records. If either or both are 850 // incomplete, we assume that they are equivalent. 851 D1 = D1->getDefinition(); 852 D2 = D2->getDefinition(); 853 if (!D1 || !D2) 854 return true; 855 856 if (CXXRecordDecl *D1CXX = dyn_cast<CXXRecordDecl>(D1)) { 857 if (CXXRecordDecl *D2CXX = dyn_cast<CXXRecordDecl>(D2)) { 858 if (D1CXX->hasExternalLexicalStorage() && 859 !D1CXX->isCompleteDefinition()) { 860 D1CXX->getASTContext().getExternalSource()->CompleteType(D1CXX); 861 } 862 863 if (D1CXX->getNumBases() != D2CXX->getNumBases()) { 864 if (Context.Complain) { 865 Context.Diag2(D2->getLocation(), diag::warn_odr_tag_type_inconsistent) 866 << Context.ToCtx.getTypeDeclType(D2); 867 Context.Diag2(D2->getLocation(), diag::note_odr_number_of_bases) 868 << D2CXX->getNumBases(); 869 Context.Diag1(D1->getLocation(), diag::note_odr_number_of_bases) 870 << D1CXX->getNumBases(); 871 } 872 return false; 873 } 874 875 // Check the base classes. 876 for (CXXRecordDecl::base_class_iterator Base1 = D1CXX->bases_begin(), 877 BaseEnd1 = D1CXX->bases_end(), 878 Base2 = D2CXX->bases_begin(); 879 Base1 != BaseEnd1; ++Base1, ++Base2) { 880 if (!IsStructurallyEquivalent(Context, Base1->getType(), 881 Base2->getType())) { 882 if (Context.Complain) { 883 Context.Diag2(D2->getLocation(), 884 diag::warn_odr_tag_type_inconsistent) 885 << Context.ToCtx.getTypeDeclType(D2); 886 Context.Diag2(Base2->getLocStart(), diag::note_odr_base) 887 << Base2->getType() << Base2->getSourceRange(); 888 Context.Diag1(Base1->getLocStart(), diag::note_odr_base) 889 << Base1->getType() << Base1->getSourceRange(); 890 } 891 return false; 892 } 893 894 // Check virtual vs. non-virtual inheritance mismatch. 895 if (Base1->isVirtual() != Base2->isVirtual()) { 896 if (Context.Complain) { 897 Context.Diag2(D2->getLocation(), 898 diag::warn_odr_tag_type_inconsistent) 899 << Context.ToCtx.getTypeDeclType(D2); 900 Context.Diag2(Base2->getLocStart(), diag::note_odr_virtual_base) 901 << Base2->isVirtual() << Base2->getSourceRange(); 902 Context.Diag1(Base1->getLocStart(), diag::note_odr_base) 903 << Base1->isVirtual() << Base1->getSourceRange(); 904 } 905 return false; 906 } 907 } 908 } else if (D1CXX->getNumBases() > 0) { 909 if (Context.Complain) { 910 Context.Diag2(D2->getLocation(), diag::warn_odr_tag_type_inconsistent) 911 << Context.ToCtx.getTypeDeclType(D2); 912 const CXXBaseSpecifier *Base1 = D1CXX->bases_begin(); 913 Context.Diag1(Base1->getLocStart(), diag::note_odr_base) 914 << Base1->getType() << Base1->getSourceRange(); 915 Context.Diag2(D2->getLocation(), diag::note_odr_missing_base); 916 } 917 return false; 918 } 919 } 920 921 // Check the fields for consistency. 922 RecordDecl::field_iterator Field2 = D2->field_begin(), 923 Field2End = D2->field_end(); 924 for (RecordDecl::field_iterator Field1 = D1->field_begin(), 925 Field1End = D1->field_end(); 926 Field1 != Field1End; ++Field1, ++Field2) { 927 if (Field2 == Field2End) { 928 if (Context.Complain) { 929 Context.Diag2(D2->getLocation(), diag::warn_odr_tag_type_inconsistent) 930 << Context.ToCtx.getTypeDeclType(D2); 931 Context.Diag1(Field1->getLocation(), diag::note_odr_field) 932 << Field1->getDeclName() << Field1->getType(); 933 Context.Diag2(D2->getLocation(), diag::note_odr_missing_field); 934 } 935 return false; 936 } 937 938 if (!IsStructurallyEquivalent(Context, *Field1, *Field2)) 939 return false; 940 } 941 942 if (Field2 != Field2End) { 943 if (Context.Complain) { 944 Context.Diag2(D2->getLocation(), diag::warn_odr_tag_type_inconsistent) 945 << Context.ToCtx.getTypeDeclType(D2); 946 Context.Diag2(Field2->getLocation(), diag::note_odr_field) 947 << Field2->getDeclName() << Field2->getType(); 948 Context.Diag1(D1->getLocation(), diag::note_odr_missing_field); 949 } 950 return false; 951 } 952 953 return true; 954 } 955 956 /// Determine structural equivalence of two enums. 957 static bool IsStructurallyEquivalent(StructuralEquivalenceContext &Context, 958 EnumDecl *D1, EnumDecl *D2) { 959 EnumDecl::enumerator_iterator EC2 = D2->enumerator_begin(), 960 EC2End = D2->enumerator_end(); 961 for (EnumDecl::enumerator_iterator EC1 = D1->enumerator_begin(), 962 EC1End = D1->enumerator_end(); 963 EC1 != EC1End; ++EC1, ++EC2) { 964 if (EC2 == EC2End) { 965 if (Context.Complain) { 966 Context.Diag2(D2->getLocation(), diag::warn_odr_tag_type_inconsistent) 967 << Context.ToCtx.getTypeDeclType(D2); 968 Context.Diag1(EC1->getLocation(), diag::note_odr_enumerator) 969 << EC1->getDeclName() << EC1->getInitVal().toString(10); 970 Context.Diag2(D2->getLocation(), diag::note_odr_missing_enumerator); 971 } 972 return false; 973 } 974 975 llvm::APSInt Val1 = EC1->getInitVal(); 976 llvm::APSInt Val2 = EC2->getInitVal(); 977 if (!llvm::APSInt::isSameValue(Val1, Val2) || 978 !IsStructurallyEquivalent(EC1->getIdentifier(), EC2->getIdentifier())) { 979 if (Context.Complain) { 980 Context.Diag2(D2->getLocation(), diag::warn_odr_tag_type_inconsistent) 981 << Context.ToCtx.getTypeDeclType(D2); 982 Context.Diag2(EC2->getLocation(), diag::note_odr_enumerator) 983 << EC2->getDeclName() << EC2->getInitVal().toString(10); 984 Context.Diag1(EC1->getLocation(), diag::note_odr_enumerator) 985 << EC1->getDeclName() << EC1->getInitVal().toString(10); 986 } 987 return false; 988 } 989 } 990 991 if (EC2 != EC2End) { 992 if (Context.Complain) { 993 Context.Diag2(D2->getLocation(), diag::warn_odr_tag_type_inconsistent) 994 << Context.ToCtx.getTypeDeclType(D2); 995 Context.Diag2(EC2->getLocation(), diag::note_odr_enumerator) 996 << EC2->getDeclName() << EC2->getInitVal().toString(10); 997 Context.Diag1(D1->getLocation(), diag::note_odr_missing_enumerator); 998 } 999 return false; 1000 } 1001 1002 return true; 1003 } 1004 1005 static bool IsStructurallyEquivalent(StructuralEquivalenceContext &Context, 1006 TemplateParameterList *Params1, 1007 TemplateParameterList *Params2) { 1008 if (Params1->size() != Params2->size()) { 1009 if (Context.Complain) { 1010 Context.Diag2(Params2->getTemplateLoc(), 1011 diag::err_odr_different_num_template_parameters) 1012 << Params1->size() << Params2->size(); 1013 Context.Diag1(Params1->getTemplateLoc(), 1014 diag::note_odr_template_parameter_list); 1015 } 1016 return false; 1017 } 1018 1019 for (unsigned I = 0, N = Params1->size(); I != N; ++I) { 1020 if (Params1->getParam(I)->getKind() != Params2->getParam(I)->getKind()) { 1021 if (Context.Complain) { 1022 Context.Diag2(Params2->getParam(I)->getLocation(), 1023 diag::err_odr_different_template_parameter_kind); 1024 Context.Diag1(Params1->getParam(I)->getLocation(), 1025 diag::note_odr_template_parameter_here); 1026 } 1027 return false; 1028 } 1029 1030 if (!Context.IsStructurallyEquivalent(Params1->getParam(I), 1031 Params2->getParam(I))) { 1032 1033 return false; 1034 } 1035 } 1036 1037 return true; 1038 } 1039 1040 static bool IsStructurallyEquivalent(StructuralEquivalenceContext &Context, 1041 TemplateTypeParmDecl *D1, 1042 TemplateTypeParmDecl *D2) { 1043 if (D1->isParameterPack() != D2->isParameterPack()) { 1044 if (Context.Complain) { 1045 Context.Diag2(D2->getLocation(), diag::err_odr_parameter_pack_non_pack) 1046 << D2->isParameterPack(); 1047 Context.Diag1(D1->getLocation(), diag::note_odr_parameter_pack_non_pack) 1048 << D1->isParameterPack(); 1049 } 1050 return false; 1051 } 1052 1053 return true; 1054 } 1055 1056 static bool IsStructurallyEquivalent(StructuralEquivalenceContext &Context, 1057 NonTypeTemplateParmDecl *D1, 1058 NonTypeTemplateParmDecl *D2) { 1059 if (D1->isParameterPack() != D2->isParameterPack()) { 1060 if (Context.Complain) { 1061 Context.Diag2(D2->getLocation(), diag::err_odr_parameter_pack_non_pack) 1062 << D2->isParameterPack(); 1063 Context.Diag1(D1->getLocation(), diag::note_odr_parameter_pack_non_pack) 1064 << D1->isParameterPack(); 1065 } 1066 return false; 1067 } 1068 1069 // Check types. 1070 if (!Context.IsStructurallyEquivalent(D1->getType(), D2->getType())) { 1071 if (Context.Complain) { 1072 Context.Diag2(D2->getLocation(), 1073 diag::err_odr_non_type_parameter_type_inconsistent) 1074 << D2->getType() << D1->getType(); 1075 Context.Diag1(D1->getLocation(), diag::note_odr_value_here) 1076 << D1->getType(); 1077 } 1078 return false; 1079 } 1080 1081 return true; 1082 } 1083 1084 static bool IsStructurallyEquivalent(StructuralEquivalenceContext &Context, 1085 TemplateTemplateParmDecl *D1, 1086 TemplateTemplateParmDecl *D2) { 1087 if (D1->isParameterPack() != D2->isParameterPack()) { 1088 if (Context.Complain) { 1089 Context.Diag2(D2->getLocation(), diag::err_odr_parameter_pack_non_pack) 1090 << D2->isParameterPack(); 1091 Context.Diag1(D1->getLocation(), diag::note_odr_parameter_pack_non_pack) 1092 << D1->isParameterPack(); 1093 } 1094 return false; 1095 } 1096 1097 // Check template parameter lists. 1098 return IsStructurallyEquivalent(Context, D1->getTemplateParameters(), 1099 D2->getTemplateParameters()); 1100 } 1101 1102 static bool IsStructurallyEquivalent(StructuralEquivalenceContext &Context, 1103 ClassTemplateDecl *D1, 1104 ClassTemplateDecl *D2) { 1105 // Check template parameters. 1106 if (!IsStructurallyEquivalent(Context, D1->getTemplateParameters(), 1107 D2->getTemplateParameters())) 1108 return false; 1109 1110 // Check the templated declaration. 1111 return Context.IsStructurallyEquivalent(D1->getTemplatedDecl(), 1112 D2->getTemplatedDecl()); 1113 } 1114 1115 /// Determine structural equivalence of two declarations. 1116 static bool IsStructurallyEquivalent(StructuralEquivalenceContext &Context, 1117 Decl *D1, Decl *D2) { 1118 // FIXME: Check for known structural equivalences via a callback of some sort. 1119 1120 // Check whether we already know that these two declarations are not 1121 // structurally equivalent. 1122 if (Context.NonEquivalentDecls.count( 1123 std::make_pair(D1->getCanonicalDecl(), D2->getCanonicalDecl()))) 1124 return false; 1125 1126 // Determine whether we've already produced a tentative equivalence for D1. 1127 Decl *&EquivToD1 = Context.TentativeEquivalences[D1->getCanonicalDecl()]; 1128 if (EquivToD1) 1129 return EquivToD1 == D2->getCanonicalDecl(); 1130 1131 // Produce a tentative equivalence D1 <-> D2, which will be checked later. 1132 EquivToD1 = D2->getCanonicalDecl(); 1133 Context.DeclsToCheck.push_back(D1->getCanonicalDecl()); 1134 return true; 1135 } 1136 } // namespace 1137 1138 namespace clang { 1139 1140 DiagnosticBuilder StructuralEquivalenceContext::Diag1(SourceLocation Loc, 1141 unsigned DiagID) { 1142 assert(Complain && "Not allowed to complain"); 1143 if (LastDiagFromC2) 1144 FromCtx.getDiagnostics().notePriorDiagnosticFrom(ToCtx.getDiagnostics()); 1145 LastDiagFromC2 = false; 1146 return FromCtx.getDiagnostics().Report(Loc, DiagID); 1147 } 1148 1149 DiagnosticBuilder StructuralEquivalenceContext::Diag2(SourceLocation Loc, 1150 unsigned DiagID) { 1151 assert(Complain && "Not allowed to complain"); 1152 if (!LastDiagFromC2) 1153 ToCtx.getDiagnostics().notePriorDiagnosticFrom(FromCtx.getDiagnostics()); 1154 LastDiagFromC2 = true; 1155 return ToCtx.getDiagnostics().Report(Loc, DiagID); 1156 } 1157 1158 Optional<unsigned> 1159 StructuralEquivalenceContext::findUntaggedStructOrUnionIndex(RecordDecl *Anon) { 1160 ASTContext &Context = Anon->getASTContext(); 1161 QualType AnonTy = Context.getRecordType(Anon); 1162 1163 RecordDecl *Owner = dyn_cast<RecordDecl>(Anon->getDeclContext()); 1164 if (!Owner) 1165 return None; 1166 1167 unsigned Index = 0; 1168 for (const auto *D : Owner->noload_decls()) { 1169 const auto *F = dyn_cast<FieldDecl>(D); 1170 if (!F) 1171 continue; 1172 1173 if (F->isAnonymousStructOrUnion()) { 1174 if (Context.hasSameType(F->getType(), AnonTy)) 1175 break; 1176 ++Index; 1177 continue; 1178 } 1179 1180 // If the field looks like this: 1181 // struct { ... } A; 1182 QualType FieldType = F->getType(); 1183 if (const auto *RecType = dyn_cast<RecordType>(FieldType)) { 1184 const RecordDecl *RecDecl = RecType->getDecl(); 1185 if (RecDecl->getDeclContext() == Owner && !RecDecl->getIdentifier()) { 1186 if (Context.hasSameType(FieldType, AnonTy)) 1187 break; 1188 ++Index; 1189 continue; 1190 } 1191 } 1192 } 1193 1194 return Index; 1195 } 1196 1197 bool StructuralEquivalenceContext::IsStructurallyEquivalent(Decl *D1, 1198 Decl *D2) { 1199 if (!::IsStructurallyEquivalent(*this, D1, D2)) 1200 return false; 1201 1202 return !Finish(); 1203 } 1204 1205 bool StructuralEquivalenceContext::IsStructurallyEquivalent(QualType T1, 1206 QualType T2) { 1207 if (!::IsStructurallyEquivalent(*this, T1, T2)) 1208 return false; 1209 1210 return !Finish(); 1211 } 1212 1213 bool StructuralEquivalenceContext::Finish() { 1214 while (!DeclsToCheck.empty()) { 1215 // Check the next declaration. 1216 Decl *D1 = DeclsToCheck.front(); 1217 DeclsToCheck.pop_front(); 1218 1219 Decl *D2 = TentativeEquivalences[D1]; 1220 assert(D2 && "Unrecorded tentative equivalence?"); 1221 1222 bool Equivalent = true; 1223 1224 // FIXME: Switch on all declaration kinds. For now, we're just going to 1225 // check the obvious ones. 1226 if (RecordDecl *Record1 = dyn_cast<RecordDecl>(D1)) { 1227 if (RecordDecl *Record2 = dyn_cast<RecordDecl>(D2)) { 1228 // Check for equivalent structure names. 1229 IdentifierInfo *Name1 = Record1->getIdentifier(); 1230 if (!Name1 && Record1->getTypedefNameForAnonDecl()) 1231 Name1 = Record1->getTypedefNameForAnonDecl()->getIdentifier(); 1232 IdentifierInfo *Name2 = Record2->getIdentifier(); 1233 if (!Name2 && Record2->getTypedefNameForAnonDecl()) 1234 Name2 = Record2->getTypedefNameForAnonDecl()->getIdentifier(); 1235 if (!::IsStructurallyEquivalent(Name1, Name2) || 1236 !::IsStructurallyEquivalent(*this, Record1, Record2)) 1237 Equivalent = false; 1238 } else { 1239 // Record/non-record mismatch. 1240 Equivalent = false; 1241 } 1242 } else if (EnumDecl *Enum1 = dyn_cast<EnumDecl>(D1)) { 1243 if (EnumDecl *Enum2 = dyn_cast<EnumDecl>(D2)) { 1244 // Check for equivalent enum names. 1245 IdentifierInfo *Name1 = Enum1->getIdentifier(); 1246 if (!Name1 && Enum1->getTypedefNameForAnonDecl()) 1247 Name1 = Enum1->getTypedefNameForAnonDecl()->getIdentifier(); 1248 IdentifierInfo *Name2 = Enum2->getIdentifier(); 1249 if (!Name2 && Enum2->getTypedefNameForAnonDecl()) 1250 Name2 = Enum2->getTypedefNameForAnonDecl()->getIdentifier(); 1251 if (!::IsStructurallyEquivalent(Name1, Name2) || 1252 !::IsStructurallyEquivalent(*this, Enum1, Enum2)) 1253 Equivalent = false; 1254 } else { 1255 // Enum/non-enum mismatch 1256 Equivalent = false; 1257 } 1258 } else if (TypedefNameDecl *Typedef1 = dyn_cast<TypedefNameDecl>(D1)) { 1259 if (TypedefNameDecl *Typedef2 = dyn_cast<TypedefNameDecl>(D2)) { 1260 if (!::IsStructurallyEquivalent(Typedef1->getIdentifier(), 1261 Typedef2->getIdentifier()) || 1262 !::IsStructurallyEquivalent(*this, Typedef1->getUnderlyingType(), 1263 Typedef2->getUnderlyingType())) 1264 Equivalent = false; 1265 } else { 1266 // Typedef/non-typedef mismatch. 1267 Equivalent = false; 1268 } 1269 } else if (ClassTemplateDecl *ClassTemplate1 = 1270 dyn_cast<ClassTemplateDecl>(D1)) { 1271 if (ClassTemplateDecl *ClassTemplate2 = dyn_cast<ClassTemplateDecl>(D2)) { 1272 if (!::IsStructurallyEquivalent(ClassTemplate1->getIdentifier(), 1273 ClassTemplate2->getIdentifier()) || 1274 !::IsStructurallyEquivalent(*this, ClassTemplate1, ClassTemplate2)) 1275 Equivalent = false; 1276 } else { 1277 // Class template/non-class-template mismatch. 1278 Equivalent = false; 1279 } 1280 } else if (TemplateTypeParmDecl *TTP1 = 1281 dyn_cast<TemplateTypeParmDecl>(D1)) { 1282 if (TemplateTypeParmDecl *TTP2 = dyn_cast<TemplateTypeParmDecl>(D2)) { 1283 if (!::IsStructurallyEquivalent(*this, TTP1, TTP2)) 1284 Equivalent = false; 1285 } else { 1286 // Kind mismatch. 1287 Equivalent = false; 1288 } 1289 } else if (NonTypeTemplateParmDecl *NTTP1 = 1290 dyn_cast<NonTypeTemplateParmDecl>(D1)) { 1291 if (NonTypeTemplateParmDecl *NTTP2 = 1292 dyn_cast<NonTypeTemplateParmDecl>(D2)) { 1293 if (!::IsStructurallyEquivalent(*this, NTTP1, NTTP2)) 1294 Equivalent = false; 1295 } else { 1296 // Kind mismatch. 1297 Equivalent = false; 1298 } 1299 } else if (TemplateTemplateParmDecl *TTP1 = 1300 dyn_cast<TemplateTemplateParmDecl>(D1)) { 1301 if (TemplateTemplateParmDecl *TTP2 = 1302 dyn_cast<TemplateTemplateParmDecl>(D2)) { 1303 if (!::IsStructurallyEquivalent(*this, TTP1, TTP2)) 1304 Equivalent = false; 1305 } else { 1306 // Kind mismatch. 1307 Equivalent = false; 1308 } 1309 } 1310 1311 if (!Equivalent) { 1312 // Note that these two declarations are not equivalent (and we already 1313 // know about it). 1314 NonEquivalentDecls.insert( 1315 std::make_pair(D1->getCanonicalDecl(), D2->getCanonicalDecl())); 1316 return true; 1317 } 1318 // FIXME: Check other declaration kinds! 1319 } 1320 1321 return false; 1322 } 1323 } // namespace clang 1324