r294402 - [AVR] Add support for the 'interrupt' and 'naked' attributes

Dylan McKay via cfe-commits cfe-commits at lists.llvm.org
Tue Feb 7 21:09:27 PST 2017


Author: dylanmckay
Date: Tue Feb  7 23:09:26 2017
New Revision: 294402

URL: http://llvm.org/viewvc/llvm-project?rev=294402&view=rev
Log:
[AVR] Add support for the 'interrupt' and 'naked' attributes

Summary:
This teaches clang how to parse and lower the 'interrupt' and 'naked'
attributes.

This allows interrupt signal handlers to be written.

Reviewers: aaron.ballman

Subscribers: malcolm.parsons, cfe-commits

Differential Revision: https://reviews.llvm.org/D28451

Added:
    cfe/trunk/test/CodeGen/avr/attributes/
    cfe/trunk/test/CodeGen/avr/attributes/interrupt.c
    cfe/trunk/test/CodeGen/avr/attributes/signal.c
    cfe/trunk/test/Sema/avr-interrupt-attr.c
    cfe/trunk/test/Sema/avr-signal-attr.c
Modified:
    cfe/trunk/include/clang/Basic/Attr.td
    cfe/trunk/include/clang/Basic/AttrDocs.td
    cfe/trunk/lib/CodeGen/TargetInfo.cpp
    cfe/trunk/lib/Sema/SemaDeclAttr.cpp

Modified: cfe/trunk/include/clang/Basic/Attr.td
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/include/clang/Basic/Attr.td?rev=294402&r1=294401&r2=294402&view=diff
==============================================================================
--- cfe/trunk/include/clang/Basic/Attr.td (original)
+++ cfe/trunk/include/clang/Basic/Attr.td Tue Feb  7 23:09:26 2017
@@ -258,6 +258,7 @@ class TargetArch<list<string> arches> {
   list<string> CXXABIs;
 }
 def TargetARM : TargetArch<["arm", "thumb", "armeb", "thumbeb"]>;
+def TargetAVR : TargetArch<["avr"]>;
 def TargetMips : TargetArch<["mips", "mipsel"]>;
 def TargetMSP430 : TargetArch<["msp430"]>;
 def TargetX86 : TargetArch<["x86"]>;
@@ -480,6 +481,19 @@ def ARMInterrupt : InheritableAttr, Targ
   let Documentation = [ARMInterruptDocs];
 }
 
+def AVRInterrupt : InheritableAttr, TargetSpecificAttr<TargetAVR> {
+  let Spellings = [GNU<"interrupt">];
+  let Subjects = SubjectList<[Function]>;
+  let ParseKind = "Interrupt";
+  let Documentation = [AVRInterruptDocs];
+}
+
+def AVRSignal : InheritableAttr, TargetSpecificAttr<TargetAVR> {
+  let Spellings = [GNU<"signal">];
+  let Subjects = SubjectList<[Function]>;
+  let Documentation = [AVRSignalDocs];
+}
+
 def AsmLabel : InheritableAttr {
   let Spellings = [Keyword<"asm">, Keyword<"__asm__">];
   let Args = [StringArgument<"Label">];

Modified: cfe/trunk/include/clang/Basic/AttrDocs.td
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/include/clang/Basic/AttrDocs.td?rev=294402&r1=294401&r2=294402&view=diff
==============================================================================
--- cfe/trunk/include/clang/Basic/AttrDocs.td (original)
+++ cfe/trunk/include/clang/Basic/AttrDocs.td Tue Feb  7 23:09:26 2017
@@ -1182,6 +1182,33 @@ The semantics are as follows:
   }];
 }
 
+def AVRInterruptDocs : Documentation {
+  let Category = DocCatFunction;
+  let Content = [{
+Clang supports the GNU style ``__attribute__((interrupt))`` attribute on
+AVR targets. This attribute may be attached to a function definition and instructs
+the backend to generate appropriate function entry/exit code so that it can be used
+directly as an interrupt service routine.
+
+On the AVR, the hardware globally disables interrupts when an interrupt is executed.
+The first instruction of an interrupt handler declared with this attribute is a SEI
+instruction to re-enable interrupts. See also the signal attribute that
+does not insert a SEI instruction.
+  }];
+}
+
+def AVRSignalDocs : Documentation {
+  let Category = DocCatFunction;
+  let Content = [{
+Clang supports the GNU style ``__attribute__((signal))`` attribute on
+AVR targets. This attribute may be attached to a function definition and instructs
+the backend to generate appropriate function entry/exit code so that it can be used
+directly as an interrupt service routine.
+
+Interrupt handler functions defined with the signal attribute do not re-enable interrupts.
+}];
+}
+
 def TargetDocs : Documentation {
   let Category = DocCatFunction;
   let Content = [{

Modified: cfe/trunk/lib/CodeGen/TargetInfo.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/CodeGen/TargetInfo.cpp?rev=294402&r1=294401&r2=294402&view=diff
==============================================================================
--- cfe/trunk/lib/CodeGen/TargetInfo.cpp (original)
+++ cfe/trunk/lib/CodeGen/TargetInfo.cpp Tue Feb  7 23:09:26 2017
@@ -6900,6 +6900,31 @@ MIPSTargetCodeGenInfo::initDwarfEHRegSiz
 }
 
 //===----------------------------------------------------------------------===//
+// AVR ABI Implementation.
+//===----------------------------------------------------------------------===//
+
+namespace {
+class AVRTargetCodeGenInfo : public TargetCodeGenInfo {
+public:
+  AVRTargetCodeGenInfo(CodeGenTypes &CGT)
+    : TargetCodeGenInfo(new DefaultABIInfo(CGT)) { }
+
+  void setTargetAttributes(const Decl *D, llvm::GlobalValue *GV,
+                           CodeGen::CodeGenModule &CGM) const override {
+    const auto *FD = dyn_cast_or_null<FunctionDecl>(D);
+    if (!FD) return;
+    auto *Fn = cast<llvm::Function>(GV);
+
+    if (FD->getAttr<AVRInterruptAttr>())
+      Fn->addFnAttr("interrupt");
+
+    if (FD->getAttr<AVRSignalAttr>())
+      Fn->addFnAttr("signal");
+  }
+};
+}
+
+//===----------------------------------------------------------------------===//
 // TCE ABI Implementation (see http://tce.cs.tut.fi). Uses mostly the defaults.
 // Currently subclassed only to implement custom OpenCL C function attribute
 // handling.
@@ -8402,6 +8427,9 @@ const TargetCodeGenInfo &CodeGenModule::
   case llvm::Triple::mips64el:
     return SetCGInfo(new MIPSTargetCodeGenInfo(Types, false));
 
+  case llvm::Triple::avr:
+    return SetCGInfo(new AVRTargetCodeGenInfo(Types));
+
   case llvm::Triple::aarch64:
   case llvm::Triple::aarch64_be: {
     AArch64ABIInfo::ABIKind Kind = AArch64ABIInfo::AAPCS;

Modified: cfe/trunk/lib/Sema/SemaDeclAttr.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Sema/SemaDeclAttr.cpp?rev=294402&r1=294401&r2=294402&view=diff
==============================================================================
--- cfe/trunk/lib/Sema/SemaDeclAttr.cpp (original)
+++ cfe/trunk/lib/Sema/SemaDeclAttr.cpp Tue Feb  7 23:09:26 2017
@@ -5126,6 +5126,32 @@ static void handleAnyX86InterruptAttr(Se
   D->addAttr(UsedAttr::CreateImplicit(S.Context));
 }
 
+static void handleAVRInterruptAttr(Sema &S, Decl *D, const AttributeList &Attr) {
+  if (!isFunctionOrMethod(D)) {
+    S.Diag(D->getLocation(), diag::warn_attribute_wrong_decl_type)
+        << "'interrupt'" << ExpectedFunction;
+    return;
+  }
+
+  if (!checkAttributeNumArgs(S, Attr, 0))
+    return;
+
+  handleSimpleAttribute<AVRInterruptAttr>(S, D, Attr);
+}
+
+static void handleAVRSignalAttr(Sema &S, Decl *D, const AttributeList &Attr) {
+  if (!isFunctionOrMethod(D)) {
+    S.Diag(D->getLocation(), diag::warn_attribute_wrong_decl_type)
+        << "'signal'" << ExpectedFunction;
+    return;
+  }
+
+  if (!checkAttributeNumArgs(S, Attr, 0))
+    return;
+
+  handleSimpleAttribute<AVRSignalAttr>(S, D, Attr);
+}
+
 static void handleInterruptAttr(Sema &S, Decl *D, const AttributeList &Attr) {
   // Dispatch the interrupt attribute based on the current target.
   switch (S.Context.getTargetInfo().getTriple().getArch()) {
@@ -5140,6 +5166,9 @@ static void handleInterruptAttr(Sema &S,
   case llvm::Triple::x86_64:
     handleAnyX86InterruptAttr(S, D, Attr);
     break;
+  case llvm::Triple::avr:
+    handleAVRInterruptAttr(S, D, Attr);
+    break;
   default:
     handleARMInterruptAttr(S, D, Attr);
     break;
@@ -5700,6 +5729,9 @@ static void ProcessDeclAttribute(Sema &S
   case AttributeList::AT_AMDGPUNumVGPR:
     handleAMDGPUNumVGPRAttr(S, D, Attr);
     break;
+  case AttributeList::AT_AVRSignal:
+    handleAVRSignalAttr(S, D, Attr);
+    break;
   case AttributeList::AT_IBAction:
     handleSimpleAttribute<IBActionAttr>(S, D, Attr);
     break;

Added: cfe/trunk/test/CodeGen/avr/attributes/interrupt.c
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/test/CodeGen/avr/attributes/interrupt.c?rev=294402&view=auto
==============================================================================
--- cfe/trunk/test/CodeGen/avr/attributes/interrupt.c (added)
+++ cfe/trunk/test/CodeGen/avr/attributes/interrupt.c Tue Feb  7 23:09:26 2017
@@ -0,0 +1,6 @@
+// RUN: %clang_cc1 -triple avr-unknown-unknown -emit-llvm %s -o - | FileCheck %s
+
+// CHECK: define void @foo() #0
+__attribute__((interrupt)) void foo(void) { }
+
+// CHECK: attributes #0 = {{{.*interrupt.*}}}

Added: cfe/trunk/test/CodeGen/avr/attributes/signal.c
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/test/CodeGen/avr/attributes/signal.c?rev=294402&view=auto
==============================================================================
--- cfe/trunk/test/CodeGen/avr/attributes/signal.c (added)
+++ cfe/trunk/test/CodeGen/avr/attributes/signal.c Tue Feb  7 23:09:26 2017
@@ -0,0 +1,6 @@
+// RUN: %clang_cc1 -triple avr-unknown-unknown -emit-llvm %s -o - | FileCheck %s
+
+// CHECK: define void @foo() #0
+__attribute__((signal)) void foo(void) { }
+
+// CHECK: attributes #0 = {{{.*signal.*}}}

Added: cfe/trunk/test/Sema/avr-interrupt-attr.c
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/test/Sema/avr-interrupt-attr.c?rev=294402&view=auto
==============================================================================
--- cfe/trunk/test/Sema/avr-interrupt-attr.c (added)
+++ cfe/trunk/test/Sema/avr-interrupt-attr.c Tue Feb  7 23:09:26 2017
@@ -0,0 +1,8 @@
+// RUN: %clang_cc1 %s -triple avr-unknown-unknown -verify -fsyntax-only
+struct a { int b; };
+
+struct a test __attribute__((interrupt)); // expected-warning {{'interrupt' attribute only applies to functions}}
+
+__attribute__((interrupt(12))) void foo(void) { } // expected-error {{'interrupt' attribute takes no arguments}}
+
+__attribute__((interrupt)) void food() {}

Added: cfe/trunk/test/Sema/avr-signal-attr.c
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/test/Sema/avr-signal-attr.c?rev=294402&view=auto
==============================================================================
--- cfe/trunk/test/Sema/avr-signal-attr.c (added)
+++ cfe/trunk/test/Sema/avr-signal-attr.c Tue Feb  7 23:09:26 2017
@@ -0,0 +1,8 @@
+// RUN: %clang_cc1 %s -triple avr-unknown-unknown -verify -fsyntax-only
+struct a { int b; };
+
+struct a test __attribute__((signal)); // expected-warning {{'signal' attribute only applies to functions}}
+
+__attribute__((signal(12))) void foo(void) { } // expected-error {{'signal' attribute takes no arguments}}
+
+__attribute__((signal)) void food() {}




More information about the cfe-commits mailing list