Вопрос

I am trying to write some code for an msp430g2452 mcu. It should cycle through a few modes of led's being on or off using an interrupt and a switch statement. I am only just beginning to learn to code, c and python :) so I am unsure of what is going wrong.

As far as I can tell everything is working alright except I am not capturing the interrupt on p1.3 which is a button on my launchpad emulation/development board. If I debug using code composer studio 5 and I pause the emulation, I then change the bit for P1IFG.3 and resume the emulation the correct chain of events takes place. So it would seem to me the issue is capturing that switch edge.

If anyone has any ideas as to what is going on here I would very much appreciate it. mcu datasheet for those who are interested. And the code I am using to follow:

#include <msp430g2452.h>

#define button BIT3 // set button to p1.3
#define grnLED BIT6 // set green led to p1.6
#define redLED BIT0 // set red led to p1.0

volatile unsigned int stateID = 0; // declare and clear stateID

void main(void) {
WDTCTL = WDTPW | WDTHOLD;     // Stop watchdog timer

P1DIR |= (grnLED + redLED); // set bit0 and bit6 to output, led's
P1OUT &= ~(grnLED + redLED); // both led's off

P1IE |= button; // enable interrupts on button
P1REN |= button; // enable pull-up resistor on button
P1IFG &= ~button; // flag for button off

_EINT(); // enable interrupts

// loop forever
while (1){
      switch(stateID){ //switch based on state of stateID
      case 1:
      {
              P1OUT = grnLED; //turn green led on
              break;
      }
      case 2:
      {
              P1OUT = redLED; //turn red led on
              break;
      }
      case 3:
      {
              P1OUT = (grnLED + redLED); // turn both led's on
              break;
      }
      case 4:
      {
              stateID = 0; // reset stateID
              break;
      }
      default:
      {
              P1OUT &= ~(grnLED + redLED); // turn both led's off again
              break;

      }
      }
}
}

// interrupt handler
#pragma vector=PORT1_VECTOR
__interrupt void Port_1 (void){
  _DINT(); // disable interrupts to avoid nesting
  stateID=(stateID+1); // increment stateID
  P1IFG &= ~button; // clear interrupt flag on button
  _EINT(); // re-enable interrupts
}

here is the fixed code

#include <msp430g2553.h>

/* written by: rob j loranger
* date: april  2013
*
* this program should emulate a typical headlamp operation,
* from a power off state one button press should turn on the lamp in mode one.
* each successive press should cycle through modes until it returns to an off state
*
* main.c
*/

#define button BIT3 // set button to p1.3
#define grnLED BIT6 // set green led to p1.6
#define redLED BIT0 // set red led to p1.0

volatile unsigned int stateID = 0; // declare and clear stateID


void main(void) {
WDTCTL = WDTPW | WDTHOLD;     // Stop watchdog timer

P1DIR |= (grnLED + redLED); // set bit0 and bit6 to output, led's
P1OUT &= ~(grnLED + redLED); // both led's off
P1OUT |= button; // set button to output


/* i set button to an output and i set the edge high 
*  for the interrupt as well.
*/


P1IE |= button; // enable interrupts on button
P1IES |= button; // set edge high
P1REN |= button; // enable pull-up resistor on button
P1IFG &= ~button; // flag for button off

_EINT(); // enable interrupts


/* i then made some changes to my loop to prevent the output 
*  state on button from being changed
*/

// loop forever
while (1){
      switch(stateID){ //switch based on state of stateID
      case 1:
      {
              P1OUT |= grnLED; //turn green led on
              break;
      }
      case 2:
      {
              P1OUT &= ~grnLED; // turn green led off
              P1OUT |= redLED; //turn red led on
              break;
      }
      case 3:
      {
              P1OUT |= grnLED; // turn green led on, both are on now
              break;
      }
      case 4:
      {
              stateID = 0; // reset stateID
              break;
      }
      default:
      {
              P1OUT &= ~(grnLED + redLED); // turn both led's off again
              break;

      }
      }
}
}

// interrupt handler
#pragma vector=PORT1_VECTOR
__interrupt void Port_1 (void){
  _DINT(); // disable interrupts to avoid nesting
  stateID=(stateID+1); // increment stateID
  P1IFG &= ~button; // clear interrupt flag on button
  _EINT(); // re-enable interrupts
}
Это было полезно?

Решение

This datasheet may be of more use, specifically section 8.

I'd suggest that you look into either ensuring the pin is really configured as IO (P1SEL.x P1SEL2.x both = 0), or checking the "Interrupt Edge Select" (P1IES.x) settings.

Good luck!

Лицензировано под: CC-BY-SA с атрибуция
Не связан с StackOverflow
scroll top