Forum: Mikrocontroller und Digitale Elektronik AT91 -> Interrupt über Taste auslösen (Olimex-EK Board)


von Tobias E. (doenges2)


Lesenswert?

Hallo,

ich probiere gerade so ein bisschen mit meinem neuen Olimex EK Board rum 
(At91Sam7S256) undwoltle unter anderem mal einen IUnterrupt über eine 
Taste auslösen habe das Programm heute auch schon so weit bekommen das 
es aus der while Schleife springt und.........tja dann passiert nichts 
mehr!
Das weiß ich weil die andere LED in der while schleife ein und 
ausgeschaltet wird!

Hat jemand von euch vielleicht eine Idee:

main.c:
--------------------------------------------------
#include "AT91SAM7S256.h"
#include "board.h"
#include "delay.h"
#include "stdlib.h"
#include "string.h"

void button2irqhandler (void);
extern  void LowLevelInit(void);
extern  unsigned enableIRQ(void);
void LowLevelInit();

int main (void)  {

// Set up the LEDs (PA0 - PA3)
  volatile AT91PS_PIO  pPIO = AT91C_BASE_PIOA;      // pointer to PIO 
data structure
  pPIO->PIO_PER = LED_MASK | Button2;          // PIO Enable Register - 
allow PIO to control pins P0 - P2 and pin 19
  pPIO->PIO_OER = LED_MASK;              // PIO Output Enable Register - 
sets pins P0 - P2 to outputs
  pPIO->PIO_SODR = LED_MASK;              // PIO Set Output Data 
Register - turns off the two LEDs

// Select PA20 (pushbutton) to be IRQ function (Peripheral B)
  pPIO->PIO_BSR = Button2;

// Set up the AIC  registers for Button2
  volatile AT91PS_AIC  pAIC = AT91C_BASE_AIC;      // pointer to AIC 
data structure
  pAIC->AIC_IDCR = (1<<AT91C_ID_IRQ0);        // Disable IRQ0 interrupt 
in AIC Interrupt Disable Command Register
  pAIC->AIC_SVR[AT91C_ID_IRQ0] =            // Set the Button2 IRQ0 
handler address in AIC Source
      (unsigned int)button2irqhandler;            // Vector Register[30]
  pAIC->AIC_SMR[AT91C_ID_IRQ0] =            // Set the interrupt source 
type and priority
  (AT91C_AIC_SRCTYPE_INT_HIGH_LEVEL | 0x4 );       // in AIC Source Mode 
Register[30]
  pAIC->AIC_ICCR = (1<<AT91C_ID_IRQ0);         // Clear the IRQ0 
interrupt in AIC Interrupt Clear Command Register
  pAIC->AIC_IDCR = (0<<AT91C_ID_IRQ0);        // Remove disable IRQ0 
interrupt in AIC Interrupt Disable Command Reg
  pAIC->AIC_IECR = (1<<AT91C_ID_IRQ0);         // Enable the IRQ0 
interrupt in AIC Interrupt Enable Command Register
  enableIRQ();

  while (1) {
    Delay(500);
    if  ((pPIO->PIO_ODSR & LED1) == LED1)  {    // read previous state 
of LED1
      pPIO->PIO_CODR = LED1;
    } else {
      pPIO->PIO_SODR = LED1;
    }
  }
}
---------------------------------------------
button2isr.c:
---------------------------------------------
#include "AT91SAM7S256.h"
#include "board.h"

void button2irqhandler (void) {

  volatile AT91PS_TC     pTC = AT91C_BASE_TC0;    // pointer to timer 
channel 0 register structure
  volatile AT91PS_PIO    pPIO = AT91C_BASE_PIOA;    // pointer to PIO 
register structure
  unsigned int       dummy;            // temporary

  dummy = pTC->TC_SR;                  // read TC0 Status Register to 
clear interrupt

  if  ((pPIO->PIO_ODSR & LED2) == LED2) {
    pPIO->PIO_CODR = LED2;              // turn LED2 (DS2) on

  }  else  {
    pPIO->PIO_SODR = LED2;              // turn LED2 (DS2) off

  }
}
------------------------------------------
Hier noch die Funktion enableirq bei der das CPSR folgendermaßen gesetzt 
wird:

unsigned enableIRQ(void)
{
  unsigned _cpsr;

  _cpsr = __get_cpsr();
  __set_cpsr(_cpsr & ~IRQ_MASK);
  return _cpsr;
}

Bitte melde dich an um einen Beitrag zu schreiben. Anmeldung ist kostenlos und dauert nur eine Minute.
Bestehender Account
Schon ein Account bei Google/GoogleMail? Keine Anmeldung erforderlich!
Mit Google-Account einloggen
Noch kein Account? Hier anmelden.