forked from OSchip/llvm-project
Rvalue references for *this: add name mangling for ref-qualifiers,
using rules that I just made up this morning. This encoding has now been proposed to the Itanium C++ ABI group for inclusion, but of course it's still possible that the mangling will change. llvm-svn: 124296
This commit is contained in:
parent
54e462ac6e
commit
f3ea1ed1ad
|
@ -1096,6 +1096,20 @@ public:
|
|||
return getType()->getAs<FunctionProtoType>()->getTypeQuals();
|
||||
}
|
||||
|
||||
/// \brief Retrieve the ref-qualifier associated with this method.
|
||||
///
|
||||
/// In the following example, \c f() has an lvalue ref-qualifier, \c g()
|
||||
/// has an rvalue ref-qualifier, and \c h() has no ref-qualifier.
|
||||
/// \code
|
||||
/// struct X {
|
||||
/// void f() &;
|
||||
/// void g() &&;
|
||||
/// void h();
|
||||
/// };
|
||||
RefQualifierKind getRefQualifier() const {
|
||||
return getType()->getAs<FunctionProtoType>()->getRefQualifier();
|
||||
}
|
||||
|
||||
bool hasInlineBody() const;
|
||||
|
||||
// Implement isa/cast/dyncast/etc.
|
||||
|
|
|
@ -228,6 +228,7 @@ private:
|
|||
void mangleTemplatePrefix(TemplateName Template);
|
||||
void mangleOperatorName(OverloadedOperatorKind OO, unsigned Arity);
|
||||
void mangleQualifiers(Qualifiers Quals);
|
||||
void mangleRefQualifier(RefQualifierKind RefQualifier);
|
||||
|
||||
void mangleObjCMethodName(const ObjCMethodDecl *MD);
|
||||
|
||||
|
@ -817,13 +818,17 @@ void CXXNameMangler::mangleSourceName(const IdentifierInfo *II) {
|
|||
void CXXNameMangler::mangleNestedName(const NamedDecl *ND,
|
||||
const DeclContext *DC,
|
||||
bool NoFunction) {
|
||||
// <nested-name> ::= N [<CV-qualifiers>] <prefix> <unqualified-name> E
|
||||
// ::= N [<CV-qualifiers>] <template-prefix> <template-args> E
|
||||
// <nested-name>
|
||||
// ::= N [<CV-qualifiers>] [<ref-qualifier>] <prefix> <unqualified-name> E
|
||||
// ::= N [<CV-qualifiers>] [<ref-qualifier>] <template-prefix>
|
||||
// <template-args> E
|
||||
|
||||
Out << 'N';
|
||||
if (const CXXMethodDecl *Method = dyn_cast<CXXMethodDecl>(ND))
|
||||
if (const CXXMethodDecl *Method = dyn_cast<CXXMethodDecl>(ND)) {
|
||||
mangleQualifiers(Qualifiers::fromCVRMask(Method->getTypeQualifiers()));
|
||||
|
||||
mangleRefQualifier(Method->getRefQualifier());
|
||||
}
|
||||
|
||||
// Check if we have a template.
|
||||
const TemplateArgumentList *TemplateArgs = 0;
|
||||
if (const TemplateDecl *TD = isTemplate(ND, TemplateArgs)) {
|
||||
|
@ -1162,6 +1167,24 @@ void CXXNameMangler::mangleQualifiers(Qualifiers Quals) {
|
|||
// FIXME: For now, just drop all extension qualifiers on the floor.
|
||||
}
|
||||
|
||||
void CXXNameMangler::mangleRefQualifier(RefQualifierKind RefQualifier) {
|
||||
// <ref-qualifier> ::= R # lvalue reference
|
||||
// ::= O # rvalue-reference
|
||||
// Proposal to Itanium C++ ABI list on 1/26/11
|
||||
switch (RefQualifier) {
|
||||
case RQ_None:
|
||||
break;
|
||||
|
||||
case RQ_LValue:
|
||||
Out << 'R';
|
||||
break;
|
||||
|
||||
case RQ_RValue:
|
||||
Out << 'O';
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
void CXXNameMangler::mangleObjCMethodName(const ObjCMethodDecl *MD) {
|
||||
llvm::SmallString<64> Buffer;
|
||||
Context.mangleObjCMethodName(MD, Buffer);
|
||||
|
@ -1364,6 +1387,7 @@ void CXXNameMangler::mangleType(const MemberPointerType *T) {
|
|||
QualType PointeeType = T->getPointeeType();
|
||||
if (const FunctionProtoType *FPT = dyn_cast<FunctionProtoType>(PointeeType)) {
|
||||
mangleQualifiers(Qualifiers::fromCVRMask(FPT->getTypeQuals()));
|
||||
mangleRefQualifier(FPT->getRefQualifier());
|
||||
mangleType(FPT);
|
||||
|
||||
// Itanium C++ ABI 5.1.8:
|
||||
|
|
|
@ -0,0 +1,16 @@
|
|||
// RUN: %clang_cc1 -std=c++0x -triple x86_64-apple-darwin10 -emit-llvm -o - %s | FileCheck %s
|
||||
struct X {
|
||||
int f() &;
|
||||
int g() &&;
|
||||
int h() const &&;
|
||||
};
|
||||
|
||||
// CHECK: define i32 @_ZNR1X1fEv
|
||||
int X::f() & { return 0; }
|
||||
// CHECK: define i32 @_ZNO1X1gEv
|
||||
int X::g() && { return 0; }
|
||||
// CHECK: define i32 @_ZNKO1X1hEv
|
||||
int X::h() const && { return 0; }
|
||||
|
||||
// CHECK: define void @_Z1fM1XRFivEMS_OFivEMS_KOFivE
|
||||
void f(int (X::*)() &, int (X::*)() &&, int (X::*)() const&&) { }
|
Loading…
Reference in New Issue