aboutsummaryrefslogtreecommitdiff
path: root/lib/Sema/TargetAttributesSema.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'lib/Sema/TargetAttributesSema.cpp')
-rw-r--r--lib/Sema/TargetAttributesSema.cpp136
1 files changed, 74 insertions, 62 deletions
diff --git a/lib/Sema/TargetAttributesSema.cpp b/lib/Sema/TargetAttributesSema.cpp
index 2f7701227da6..45067dee9b8d 100644
--- a/lib/Sema/TargetAttributesSema.cpp
+++ b/lib/Sema/TargetAttributesSema.cpp
@@ -26,21 +26,67 @@ bool TargetAttributesSema::ProcessDeclAttribute(Scope *scope, Decl *D,
return false;
}
+static void HandleARMInterruptAttr(Decl *d,
+ const AttributeList &Attr, Sema &S) {
+ // Check the attribute arguments.
+ if (Attr.getNumArgs() > 1) {
+ S.Diag(Attr.getLoc(), diag::err_attribute_too_many_arguments)
+ << 1;
+ return;
+ }
+
+ StringRef Str;
+ SourceLocation ArgLoc;
+
+ if (Attr.getNumArgs() == 0)
+ Str = "";
+ else if (!S.checkStringLiteralArgumentAttr(Attr, 0, Str, &ArgLoc))
+ return;
+
+ ARMInterruptAttr::InterruptType Kind;
+ if (!ARMInterruptAttr::ConvertStrToInterruptType(Str, Kind)) {
+ S.Diag(Attr.getLoc(), diag::warn_attribute_type_not_supported)
+ << Attr.getName() << Str << ArgLoc;
+ return;
+ }
+
+ unsigned Index = Attr.getAttributeSpellingListIndex();
+ d->addAttr(::new (S.Context)
+ ARMInterruptAttr(Attr.getLoc(), S.Context, Kind, Index));
+}
+
+namespace {
+ class ARMAttributesSema : public TargetAttributesSema {
+ public:
+ ARMAttributesSema() { }
+ bool ProcessDeclAttribute(Scope *scope, Decl *D,
+ const AttributeList &Attr, Sema &S) const {
+ if (Attr.getName()->getName() == "interrupt") {
+ HandleARMInterruptAttr(D, Attr, S);
+ return true;
+ }
+ return false;
+ }
+ };
+}
+
static void HandleMSP430InterruptAttr(Decl *d,
const AttributeList &Attr, Sema &S) {
// Check the attribute arguments.
if (Attr.getNumArgs() != 1) {
- S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 1;
+ S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments)
+ << Attr.getName() << 1;
return;
}
// FIXME: Check for decl - it should be void ()(void).
- Expr *NumParamsExpr = static_cast<Expr *>(Attr.getArg(0));
+ Expr *NumParamsExpr = static_cast<Expr *>(Attr.getArgAsExpr(0));
llvm::APSInt NumParams(32);
if (!NumParamsExpr->isIntegerConstantExpr(NumParams, S.Context)) {
- S.Diag(Attr.getLoc(), diag::err_attribute_argument_not_int)
- << "interrupt" << NumParamsExpr->getSourceRange();
+ S.Diag(Attr.getLoc(), diag::err_attribute_argument_type)
+ << Attr.getName() << AANT_ArgumentIntegerConstant
+ << NumParamsExpr->getSourceRange();
return;
}
@@ -71,61 +117,13 @@ namespace {
};
}
-static void HandleMBlazeInterruptHandlerAttr(Decl *d, const AttributeList &Attr,
- Sema &S) {
- // Check the attribute arguments.
- if (Attr.getNumArgs() != 0) {
- S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 1;
- return;
- }
-
- // FIXME: Check for decl - it should be void ()(void).
-
- d->addAttr(::new (S.Context) MBlazeInterruptHandlerAttr(Attr.getLoc(),
- S.Context));
- d->addAttr(::new (S.Context) UsedAttr(Attr.getLoc(), S.Context));
-}
-
-static void HandleMBlazeSaveVolatilesAttr(Decl *d, const AttributeList &Attr,
- Sema &S) {
- // Check the attribute arguments.
- if (Attr.getNumArgs() != 0) {
- S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 1;
- return;
- }
-
- // FIXME: Check for decl - it should be void ()(void).
-
- d->addAttr(::new (S.Context) MBlazeSaveVolatilesAttr(Attr.getLoc(),
- S.Context));
- d->addAttr(::new (S.Context) UsedAttr(Attr.getLoc(), S.Context));
-}
-
-
-namespace {
- class MBlazeAttributesSema : public TargetAttributesSema {
- public:
- MBlazeAttributesSema() { }
- bool ProcessDeclAttribute(Scope *scope, Decl *D, const AttributeList &Attr,
- Sema &S) const {
- if (Attr.getName()->getName() == "interrupt_handler") {
- HandleMBlazeInterruptHandlerAttr(D, Attr, S);
- return true;
- } else if (Attr.getName()->getName() == "save_volatiles") {
- HandleMBlazeSaveVolatilesAttr(D, Attr, S);
- return true;
- }
- return false;
- }
- };
-}
-
static void HandleX86ForceAlignArgPointerAttr(Decl *D,
const AttributeList& Attr,
Sema &S) {
// Check the attribute arguments.
if (Attr.getNumArgs() != 0) {
- S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 0;
+ S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments)
+ << Attr.getName() << 0;
return;
}
@@ -161,6 +159,15 @@ DLLImportAttr *Sema::mergeDLLImportAttr(Decl *D, SourceRange Range,
if (D->hasAttr<DLLImportAttr>())
return NULL;
+ if (VarDecl *VD = dyn_cast<VarDecl>(D)) {
+ if (VD->hasDefinition()) {
+ // dllimport cannot be applied to definitions.
+ Diag(D->getLocation(), diag::warn_attribute_invalid_on_definition)
+ << "dllimport";
+ return NULL;
+ }
+ }
+
return ::new (Context) DLLImportAttr(Range, Context,
AttrSpellingListIndex);
}
@@ -168,7 +175,8 @@ DLLImportAttr *Sema::mergeDLLImportAttr(Decl *D, SourceRange Range,
static void HandleDLLImportAttr(Decl *D, const AttributeList &Attr, Sema &S) {
// check the attribute arguments.
if (Attr.getNumArgs() != 0) {
- S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 0;
+ S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments)
+ << Attr.getName() << 0;
return;
}
@@ -214,7 +222,8 @@ DLLExportAttr *Sema::mergeDLLExportAttr(Decl *D, SourceRange Range,
static void HandleDLLExportAttr(Decl *D, const AttributeList &Attr, Sema &S) {
// check the attribute arguments.
if (Attr.getNumArgs() != 0) {
- S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 0;
+ S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments)
+ << Attr.getName() << 0;
return;
}
@@ -270,8 +279,9 @@ namespace {
static void HandleMips16Attr(Decl *D, const AttributeList &Attr, Sema &S) {
// check the attribute arguments.
- if (Attr.hasParameterOrArguments()) {
- S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 0;
+ if (Attr.getNumArgs()) {
+ S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments)
+ << Attr.getName() << 0;
return;
}
// Attribute can only be applied to function types.
@@ -286,8 +296,9 @@ static void HandleMips16Attr(Decl *D, const AttributeList &Attr, Sema &S) {
static void HandleNoMips16Attr(Decl *D, const AttributeList &Attr, Sema &S) {
// check the attribute arguments.
- if (Attr.hasParameterOrArguments()) {
- S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 0;
+ if (Attr.getNumArgs()) {
+ S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments)
+ << Attr.getName() << 0;
return;
}
// Attribute can only be applied to function types.
@@ -325,10 +336,11 @@ const TargetAttributesSema &Sema::getTargetAttributesSema() const {
const llvm::Triple &Triple(Context.getTargetInfo().getTriple());
switch (Triple.getArch()) {
+ case llvm::Triple::arm:
+ case llvm::Triple::thumb:
+ return *(TheTargetAttributesSema = new ARMAttributesSema);
case llvm::Triple::msp430:
return *(TheTargetAttributesSema = new MSP430AttributesSema);
- case llvm::Triple::mblaze:
- return *(TheTargetAttributesSema = new MBlazeAttributesSema);
case llvm::Triple::x86:
case llvm::Triple::x86_64:
return *(TheTargetAttributesSema = new X86AttributesSema);