diff options
Diffstat (limited to 'clang/lib')
-rw-r--r-- | clang/lib/AST/Expr.cpp | 1 | ||||
-rw-r--r-- | clang/lib/AST/MicrosoftMangle.cpp | 2 | ||||
-rw-r--r-- | clang/lib/AST/Type.cpp | 2 | ||||
-rw-r--r-- | clang/lib/AST/TypePrinter.cpp | 4 | ||||
-rw-r--r-- | clang/lib/Basic/Targets.cpp | 5 | ||||
-rw-r--r-- | clang/lib/CodeGen/CGCall.cpp | 8 | ||||
-rw-r--r-- | clang/lib/Parse/ParseDecl.cpp | 35 | ||||
-rw-r--r-- | clang/lib/Parse/ParseTentative.cpp | 3 | ||||
-rw-r--r-- | clang/lib/Sema/SemaDecl.cpp | 4 | ||||
-rw-r--r-- | clang/lib/Sema/SemaDeclAttr.cpp | 7 | ||||
-rw-r--r-- | clang/lib/Sema/SemaType.cpp | 7 |
11 files changed, 63 insertions, 15 deletions
diff --git a/clang/lib/AST/Expr.cpp b/clang/lib/AST/Expr.cpp index fabcf0c10f5..5020d5a9e29 100644 --- a/clang/lib/AST/Expr.cpp +++ b/clang/lib/AST/Expr.cpp @@ -546,6 +546,7 @@ std::string PredefinedExpr::ComputeName(IdentType IT, const Decl *CurrentDecl) { case CC_X86StdCall: POut << "__stdcall "; break; case CC_X86FastCall: POut << "__fastcall "; break; case CC_X86ThisCall: POut << "__thiscall "; break; + case CC_X86VectorCall: POut << "__vectorcall "; break; // Only bother printing the conventions that MSVC knows about. default: break; } diff --git a/clang/lib/AST/MicrosoftMangle.cpp b/clang/lib/AST/MicrosoftMangle.cpp index 59cf4d091bf..ca16db4cdd0 100644 --- a/clang/lib/AST/MicrosoftMangle.cpp +++ b/clang/lib/AST/MicrosoftMangle.cpp @@ -1687,6 +1687,7 @@ void MicrosoftCXXNameMangler::mangleCallingConvention(const FunctionType *T) { // ::= H # __export __stdcall // ::= I # __fastcall // ::= J # __export __fastcall + // ::= Q # __vectorcall // The 'export' calling conventions are from a bygone era // (*cough*Win16*cough*) when functions were declared for export with // that keyword. (It didn't actually export them, it just made them so @@ -1703,6 +1704,7 @@ void MicrosoftCXXNameMangler::mangleCallingConvention(const FunctionType *T) { case CC_X86ThisCall: Out << 'E'; break; case CC_X86StdCall: Out << 'G'; break; case CC_X86FastCall: Out << 'I'; break; + case CC_X86VectorCall: Out << 'Q'; break; } } void MicrosoftCXXNameMangler::mangleThrowSpecification( diff --git a/clang/lib/AST/Type.cpp b/clang/lib/AST/Type.cpp index 4bf5927f6b3..e9d474a174c 100644 --- a/clang/lib/AST/Type.cpp +++ b/clang/lib/AST/Type.cpp @@ -1578,6 +1578,7 @@ StringRef FunctionType::getNameForCallConv(CallingConv CC) { case CC_X86FastCall: return "fastcall"; case CC_X86ThisCall: return "thiscall"; case CC_X86Pascal: return "pascal"; + case CC_X86VectorCall: return "vectorcall"; case CC_X86_64Win64: return "ms_abi"; case CC_X86_64SysV: return "sysv_abi"; case CC_AAPCS: return "aapcs"; @@ -1913,6 +1914,7 @@ bool AttributedType::isCallingConv() const { case attr_fastcall: case attr_stdcall: case attr_thiscall: + case attr_vectorcall: case attr_pascal: case attr_ms_abi: case attr_sysv_abi: diff --git a/clang/lib/AST/TypePrinter.cpp b/clang/lib/AST/TypePrinter.cpp index 061473eb848..bbd53ed900a 100644 --- a/clang/lib/AST/TypePrinter.cpp +++ b/clang/lib/AST/TypePrinter.cpp @@ -673,6 +673,9 @@ void TypePrinter::printFunctionProtoAfter(const FunctionProtoType *T, case CC_X86ThisCall: OS << " __attribute__((thiscall))"; break; + case CC_X86VectorCall: + OS << " __attribute__((vectorcall))"; + break; case CC_X86Pascal: OS << " __attribute__((pascal))"; break; @@ -1235,6 +1238,7 @@ void TypePrinter::printAttributedAfter(const AttributedType *T, case AttributedType::attr_fastcall: OS << "fastcall"; break; case AttributedType::attr_stdcall: OS << "stdcall"; break; case AttributedType::attr_thiscall: OS << "thiscall"; break; + case AttributedType::attr_vectorcall: OS << "vectorcall"; break; case AttributedType::attr_pascal: OS << "pascal"; break; case AttributedType::attr_ms_abi: OS << "ms_abi"; break; case AttributedType::attr_sysv_abi: OS << "sysv_abi"; break; diff --git a/clang/lib/Basic/Targets.cpp b/clang/lib/Basic/Targets.cpp index 957448a2d49..4604b1cfa0f 100644 --- a/clang/lib/Basic/Targets.cpp +++ b/clang/lib/Basic/Targets.cpp @@ -2095,8 +2095,9 @@ public: // We accept all non-ARM calling conventions return (CC == CC_X86ThisCall || CC == CC_X86FastCall || - CC == CC_X86StdCall || - CC == CC_C || + CC == CC_X86StdCall || + CC == CC_X86VectorCall || + CC == CC_C || CC == CC_X86Pascal || CC == CC_IntelOclBicc) ? CCCR_OK : CCCR_Warning; } diff --git a/clang/lib/CodeGen/CGCall.cpp b/clang/lib/CodeGen/CGCall.cpp index 4c82e90cc0d..ab141d4baeb 100644 --- a/clang/lib/CodeGen/CGCall.cpp +++ b/clang/lib/CodeGen/CGCall.cpp @@ -47,7 +47,10 @@ static unsigned ClangCallConvToLLVMCallConv(CallingConv CC) { case CC_AAPCS: return llvm::CallingConv::ARM_AAPCS; case CC_AAPCS_VFP: return llvm::CallingConv::ARM_AAPCS_VFP; case CC_IntelOclBicc: return llvm::CallingConv::Intel_OCL_BI; - // TODO: add support for CC_X86Pascal to llvm + // TODO: Add support for __pascal to LLVM. + case CC_X86Pascal: return llvm::CallingConv::C; + // TODO: Add support for __vectorcall to LLVM. + case CC_X86VectorCall: return llvm::CallingConv::C; } } @@ -118,6 +121,9 @@ static CallingConv getCallingConventionForDecl(const Decl *D, bool IsWindows) { if (D->hasAttr<ThisCallAttr>()) return CC_X86ThisCall; + if (D->hasAttr<VectorCallAttr>()) + return CC_X86VectorCall; + if (D->hasAttr<PascalAttr>()) return CC_X86Pascal; diff --git a/clang/lib/Parse/ParseDecl.cpp b/clang/lib/Parse/ParseDecl.cpp index eb77b095ed7..054df9f62fa 100644 --- a/clang/lib/Parse/ParseDecl.cpp +++ b/clang/lib/Parse/ParseDecl.cpp @@ -588,15 +588,28 @@ void Parser::ParseMicrosoftDeclSpec(ParsedAttributes &Attrs) { void Parser::ParseMicrosoftTypeAttributes(ParsedAttributes &attrs) { // Treat these like attributes - while (Tok.is(tok::kw___fastcall) || Tok.is(tok::kw___stdcall) || - Tok.is(tok::kw___thiscall) || Tok.is(tok::kw___cdecl) || - Tok.is(tok::kw___ptr64) || Tok.is(tok::kw___w64) || - Tok.is(tok::kw___ptr32) || Tok.is(tok::kw___unaligned) || - Tok.is(tok::kw___sptr) || Tok.is(tok::kw___uptr)) { - IdentifierInfo *AttrName = Tok.getIdentifierInfo(); - SourceLocation AttrNameLoc = ConsumeToken(); - attrs.addNew(AttrName, AttrNameLoc, nullptr, AttrNameLoc, nullptr, 0, - AttributeList::AS_Keyword); + while (true) { + switch (Tok.getKind()) { + case tok::kw___fastcall: + case tok::kw___stdcall: + case tok::kw___thiscall: + case tok::kw___cdecl: + case tok::kw___vectorcall: + case tok::kw___ptr64: + case tok::kw___w64: + case tok::kw___ptr32: + case tok::kw___unaligned: + case tok::kw___sptr: + case tok::kw___uptr: { + IdentifierInfo *AttrName = Tok.getIdentifierInfo(); + SourceLocation AttrNameLoc = ConsumeToken(); + attrs.addNew(AttrName, AttrNameLoc, nullptr, AttrNameLoc, nullptr, 0, + AttributeList::AS_Keyword); + break; + } + default: + return; + } } } @@ -2876,6 +2889,7 @@ void Parser::ParseDeclarationSpecifiers(DeclSpec &DS, case tok::kw___stdcall: case tok::kw___fastcall: case tok::kw___thiscall: + case tok::kw___vectorcall: case tok::kw___unaligned: ParseMicrosoftTypeAttributes(DS.getAttributes()); continue; @@ -4066,6 +4080,7 @@ bool Parser::isTypeSpecifierQualifier() { case tok::kw___stdcall: case tok::kw___fastcall: case tok::kw___thiscall: + case tok::kw___vectorcall: case tok::kw___w64: case tok::kw___ptr64: case tok::kw___ptr32: @@ -4234,6 +4249,7 @@ bool Parser::isDeclarationSpecifier(bool DisambiguatingWithExpression) { case tok::kw___stdcall: case tok::kw___fastcall: case tok::kw___thiscall: + case tok::kw___vectorcall: case tok::kw___w64: case tok::kw___sptr: case tok::kw___uptr: @@ -4457,6 +4473,7 @@ void Parser::ParseTypeQualifierListOpt(DeclSpec &DS, unsigned AttrReqs, case tok::kw___stdcall: case tok::kw___fastcall: case tok::kw___thiscall: + case tok::kw___vectorcall: case tok::kw___unaligned: if (AttrReqs & AR_DeclspecAttributesParsed) { ParseMicrosoftTypeAttributes(DS.getAttributes()); diff --git a/clang/lib/Parse/ParseTentative.cpp b/clang/lib/Parse/ParseTentative.cpp index 4060fab658a..8463138e852 100644 --- a/clang/lib/Parse/ParseTentative.cpp +++ b/clang/lib/Parse/ParseTentative.cpp @@ -837,6 +837,7 @@ Parser::TPResult Parser::TryParseDeclarator(bool mayBeAbstract, Tok.is(tok::kw___stdcall) || Tok.is(tok::kw___fastcall) || Tok.is(tok::kw___thiscall) || + Tok.is(tok::kw___vectorcall) || Tok.is(tok::kw___unaligned)) return TPResult::True; // attributes indicate declaration TPResult TPR = TryParseDeclarator(mayBeAbstract, mayHaveIdentifier); @@ -984,6 +985,7 @@ Parser::isExpressionOrTypeSpecifierSimple(tok::TokenKind Kind) { case tok::kw___stdcall: case tok::kw___fastcall: case tok::kw___thiscall: + case tok::kw___vectorcall: case tok::kw___unaligned: case tok::kw___vector: case tok::kw___pixel: @@ -1254,6 +1256,7 @@ Parser::isCXXDeclarationSpecifier(Parser::TPResult BracedCastResult, case tok::kw___stdcall: case tok::kw___fastcall: case tok::kw___thiscall: + case tok::kw___vectorcall: case tok::kw___w64: case tok::kw___sptr: case tok::kw___uptr: diff --git a/clang/lib/Sema/SemaDecl.cpp b/clang/lib/Sema/SemaDecl.cpp index 1666551d51f..f16ef0cd43c 100644 --- a/clang/lib/Sema/SemaDecl.cpp +++ b/clang/lib/Sema/SemaDecl.cpp @@ -7943,12 +7943,12 @@ bool Sema::CheckFunctionDeclaration(Scope *S, FunctionDecl *NewFD, // Semantic checking for this function declaration (in isolation). - // Diagnose the use of callee-cleanup calls on unprototyped functions. + // Diagnose calling conventions that don't support variadic calls. QualType NewQType = Context.getCanonicalType(NewFD->getType()); const FunctionType *NewType = cast<FunctionType>(NewQType); if (isa<FunctionNoProtoType>(NewType)) { FunctionType::ExtInfo NewTypeInfo = NewType->getExtInfo(); - if (isCalleeCleanup(NewTypeInfo.getCC())) { + if (!supportsVariadicCall(NewTypeInfo.getCC())) { // Windows system headers sometimes accidentally use stdcall without // (void) parameters, so use a default-error warning in this case :-/ int DiagID = NewTypeInfo.getCC() == CC_X86StdCall diff --git a/clang/lib/Sema/SemaDeclAttr.cpp b/clang/lib/Sema/SemaDeclAttr.cpp index d252bdcea56..f6a89d73c5e 100644 --- a/clang/lib/Sema/SemaDeclAttr.cpp +++ b/clang/lib/Sema/SemaDeclAttr.cpp @@ -3226,6 +3226,11 @@ static void handleCallConvAttr(Sema &S, Decl *D, const AttributeList &Attr) { PascalAttr(Attr.getRange(), S.Context, Attr.getAttributeSpellingListIndex())); return; + case AttributeList::AT_VectorCall: + D->addAttr(::new (S.Context) + VectorCallAttr(Attr.getRange(), S.Context, + Attr.getAttributeSpellingListIndex())); + return; case AttributeList::AT_MSABI: D->addAttr(::new (S.Context) MSABIAttr(Attr.getRange(), S.Context, @@ -3288,6 +3293,7 @@ bool Sema::CheckCallingConvAttr(const AttributeList &attr, CallingConv &CC, case AttributeList::AT_StdCall: CC = CC_X86StdCall; break; case AttributeList::AT_ThisCall: CC = CC_X86ThisCall; break; case AttributeList::AT_Pascal: CC = CC_X86Pascal; break; + case AttributeList::AT_VectorCall: CC = CC_X86VectorCall; break; case AttributeList::AT_MSABI: CC = Context.getTargetInfo().getTriple().isOSWindows() ? CC_C : CC_X86_64Win64; @@ -4529,6 +4535,7 @@ static void ProcessDeclAttribute(Sema &S, Scope *scope, Decl *D, case AttributeList::AT_FastCall: case AttributeList::AT_ThisCall: case AttributeList::AT_Pascal: + case AttributeList::AT_VectorCall: case AttributeList::AT_MSABI: case AttributeList::AT_SysVABI: case AttributeList::AT_Pcs: diff --git a/clang/lib/Sema/SemaType.cpp b/clang/lib/Sema/SemaType.cpp index 4b4a7ef5a17..a6f9483ecdc 100644 --- a/clang/lib/Sema/SemaType.cpp +++ b/clang/lib/Sema/SemaType.cpp @@ -107,6 +107,7 @@ static void diagnoseBadTypeAttribute(Sema &S, const AttributeList &attr, case AttributeList::AT_StdCall: \ case AttributeList::AT_ThisCall: \ case AttributeList::AT_Pascal: \ + case AttributeList::AT_VectorCall: \ case AttributeList::AT_MSABI: \ case AttributeList::AT_SysVABI: \ case AttributeList::AT_Regparm: \ @@ -3418,6 +3419,8 @@ static AttributeList::Kind getAttrListKind(AttributedType::Kind kind) { return AttributeList::AT_ThisCall; case AttributedType::attr_pascal: return AttributeList::AT_Pascal; + case AttributedType::attr_vectorcall: + return AttributeList::AT_VectorCall; case AttributedType::attr_pcs: case AttributedType::attr_pcs_vfp: return AttributeList::AT_Pcs; @@ -4434,6 +4437,8 @@ static AttributedType::Kind getCCTypeAttrKind(AttributeList &Attr) { return AttributedType::attr_thiscall; case AttributeList::AT_Pascal: return AttributedType::attr_pascal; + case AttributeList::AT_VectorCall: + return AttributedType::attr_vectorcall; case AttributeList::AT_Pcs: { // The attribute may have had a fixit applied where we treated an // identifier as a string literal. The contents of the string are valid, @@ -4551,7 +4556,7 @@ static bool handleFunctionTypeAttr(TypeProcessingState &state, } // Diagnose use of callee-cleanup calling convention on variadic functions. - if (isCalleeCleanup(CC)) { + if (!supportsVariadicCall(CC)) { const FunctionProtoType *FnP = dyn_cast<FunctionProtoType>(fn); if (FnP && FnP->isVariadic()) { unsigned DiagID = diag::err_cconv_varargs; |