Index: lib/AST/MicrosoftMangle.cpp =================================================================== --- lib/AST/MicrosoftMangle.cpp +++ lib/AST/MicrosoftMangle.cpp @@ -13,6 +13,7 @@ #include "clang/AST/Mangle.h" #include "clang/AST/ASTContext.h" +#include "clang/AST/ASTLambda.h" #include "clang/AST/Attr.h" #include "clang/AST/CXXInheritance.h" #include "clang/AST/CharUnits.h" @@ -1549,9 +1550,38 @@ Out << '@'; } else { QualType ResultType = Proto->getReturnType(); + bool AlreadyMangledReturnType = false; if (ResultType->isVoidType()) ResultType = ResultType.getUnqualifiedType(); - mangleType(ResultType, Range, QMM_Result); + else if (ResultType->getContainedAutoType()) { + if (ResultType->isRecordType()) { + CXXRecordDecl *RD = ResultType->getAsCXXRecordDecl(); + // Is this type defined within the function/lambda itself and + // deduced as the return type? i.e + // auto fun() { struct M{}; return M{}; } + // If so, prevent infinite recursion, by mangling this here as a temporary fix me. + if (FunctionDecl *FD = dyn_cast(RD->getDeclContext())) { + while (FD) { + FD = FD->getFirstDecl(); + if (FD == D) { + Out << '?'; + mangleQualifiers(ResultType.getLocalQualifiers(), false); + mangleSourceName(""); + AlreadyMangledReturnType = true; + break; + } + FD = dyn_cast(getLambdaAwareParentOfDeclContext(FD)); + } + } + } else if (ResultType->isUndeducedType()) { + Out << '?'; + mangleQualifiers(ResultType.getLocalQualifiers(), false); + mangleSourceName(""); + AlreadyMangledReturnType = true; + } + } + if (!AlreadyMangledReturnType) + mangleType(ResultType, Range, QMM_Result); } // ::= X # void