diff options
author | David Majnemer <david.majnemer@gmail.com> | 2014-02-06 10:59:19 +0000 |
---|---|---|
committer | David Majnemer <david.majnemer@gmail.com> | 2014-02-06 10:59:19 +0000 |
commit | 763584dc645151f2c9810f6d0fbd29118a44a659 (patch) | |
tree | 613c44affbff3b73de3a500dac997d6b4d3c65a9 /clang/lib/AST/MicrosoftMangle.cpp | |
parent | efbcf4943c268b6e5d6cf093b3560d989d4bddec (diff) | |
download | bcm5719-llvm-763584dc645151f2c9810f6d0fbd29118a44a659.tar.gz bcm5719-llvm-763584dc645151f2c9810f6d0fbd29118a44a659.zip |
MS ABI: Tweak pointer-to-member mangling/inheritance model selection
Properly determine the inheritance model when dealing with nullptr:
- If a nullptr template argument is being checked against
pointer-to-member parameter, nail down an inheritance model.
N.B. We will chose an inheritance model even if we won't ultimately
choose the template to instantiate! Cooky, right?
- Null pointer-to-datamembers have a virtual base table offset of -1,
not zero. Previously, we chose an offset of 0.
llvm-svn: 200920
Diffstat (limited to 'clang/lib/AST/MicrosoftMangle.cpp')
-rw-r--r-- | clang/lib/AST/MicrosoftMangle.cpp | 55 |
1 files changed, 24 insertions, 31 deletions
diff --git a/clang/lib/AST/MicrosoftMangle.cpp b/clang/lib/AST/MicrosoftMangle.cpp index 8563f2e2911..f02dfc72ee9 100644 --- a/clang/lib/AST/MicrosoftMangle.cpp +++ b/clang/lib/AST/MicrosoftMangle.cpp @@ -383,43 +383,38 @@ void MicrosoftCXXNameMangler::mangleMemberDataPointer(const CXXRecordDecl *RD, // ::= $F <number> <number> // ::= $G <number> <number> <number> - int64_t FO = 0; + int64_t FieldOffset; + int64_t VBTableOffset; MSInheritanceAttr::Spelling IM = RD->getMSInheritanceModel(); if (FD) { - FO = getASTContext().getFieldOffset(FD); - assert(FO % getASTContext().getCharWidth() == 0 && + FieldOffset = getASTContext().getFieldOffset(FD); + assert(FieldOffset % getASTContext().getCharWidth() == 0 && "cannot take address of bitfield"); - FO /= getASTContext().getCharWidth(); - } else if (!RD->nullFieldOffsetIsZero()) { - FO = -1; + FieldOffset /= getASTContext().getCharWidth(); + + VBTableOffset = 0; + } else { + FieldOffset = RD->nullFieldOffsetIsZero() ? 0 : -1; + + VBTableOffset = -1; } + char Code = '\0'; switch (IM) { - case MSInheritanceAttr::Keyword_single_inheritance: - case MSInheritanceAttr::Keyword_multiple_inheritance: { - // If we only have a single field, it's just an integer literal. - llvm::APSInt Val(64, /*isUnsigned=*/false); - Val = FO; - mangleIntegerLiteral(Val, /*IsBoolean=*/false); - break; + case MSInheritanceAttr::Keyword_single_inheritance: Code = '0'; break; + case MSInheritanceAttr::Keyword_multiple_inheritance: Code = '0'; break; + case MSInheritanceAttr::Keyword_virtual_inheritance: Code = 'F'; break; + case MSInheritanceAttr::Keyword_unspecified_inheritance: Code = 'G'; break; } - // Otherwise, we have an aggregate, but all adjusting fields should be zero, - // because we don't allow casts (even implicit) in the context of a template - // argument. - case MSInheritanceAttr::Keyword_virtual_inheritance: - Out << "$F"; - mangleNumber(FO); - mangleNumber(0); - break; + Out << '$' << Code; - case MSInheritanceAttr::Keyword_unspecified_inheritance: - Out << "$G"; - mangleNumber(FO); - mangleNumber(0); + mangleNumber(FieldOffset); + + if (MSInheritanceAttr::hasVBPtrOffsetField(IM)) mangleNumber(0); - break; - } + if (MSInheritanceAttr::hasVBTableOffsetField(IM)) + mangleNumber(VBTableOffset); } void @@ -455,9 +450,7 @@ MicrosoftCXXNameMangler::mangleMemberFunctionPointer(const CXXRecordDecl *RD, // thunk. uint64_t NVOffset = 0; uint64_t VBTableOffset = 0; - if (!MD) { - mangleNumber(0); - } else if (MD->isVirtual()) { + if (MD->isVirtual()) { MicrosoftVTableContext *VTContext = cast<MicrosoftVTableContext>(getASTContext().getVTableContext()); const MicrosoftVTableContext::MethodVFTableLocation &ML = @@ -1110,7 +1103,7 @@ void MicrosoftCXXNameMangler::mangleTemplateArg(const TemplateDecl *TD, case TemplateArgument::NullPtr: { QualType T = TA.getNullPtrType(); if (const MemberPointerType *MPT = T->getAs<MemberPointerType>()) { - const CXXRecordDecl *RD = MPT->getClass()->getAsCXXRecordDecl(); + const CXXRecordDecl *RD = MPT->getMostRecentCXXRecordDecl(); if (MPT->isMemberFunctionPointerType()) mangleMemberFunctionPointer(RD, 0); else |