Hi,
I am trying to write a code on the launchpad msp430g2553, which would simulate the output of several simple logic gates.
I have connected 2 push buttons as inputs to pins P1.3 and P1.7 and 4 LEDs as outputs to P1.0, P1.4, P1.5, and P1.6.
2 of the LEDs are representing the "truth" and "false" of the truth table and the other 2 are just to indicate that a push button has been pressed (1 for each).
At first I did it with polling with 6 diferrent logic gates in switch cases and it is working just fine.
#include <msp430g2553.h> #include <stdlib.h> void main(void) { WDTCTL = WDTPW + WDTHOLD; // Stop watchdog timer P1DIR |= 0x71; // Set P1.0, P1.4, P1.5, and P1.6 to output direction, 1 is output P1OUT &= ~0x71; // Set all the LED off P1DIR &= ~0x88; // Port 1 P1.3 and P1.7 (push buttons) as input, 0 is input P1SEL &= ~0x88; // Select Port 1 P1.3 and P1.7 (push buttons), 0 selects // P1REN |= 0x88; // Enable Port 1 P1.3 (push button) pull-up resistor srand (time(NULL)); // Initialise random seed long random= rand() % 6 + 1; // generate random number from 1 to 6 while(1){ if( (P1IN & 0x08) == 0x08) // if Push button at P1.3 is pressed P1OUT |= 0x40; // Set LED at 1.6 ON when button down else P1OUT &= ~0x40; // Set LED at 1.6 OFF if ((P1IN & 0x80) == 0x80) // if Push button at P1.7 is pressed P1OUT |= 0x01; // Set LED at 1.0 ON when button down else P1OUT &= ~0x01; // Set LED at 1.6 OFF switch(random){ case 1: //logic "AND" if ((P1IN & 0x88) == 0x88) //if both push buttons are pressed { P1OUT |= 0x10; // Set "TRUE" LED at 1.4 ON P1OUT &= ~0x20; // Set "FALSE" LED at 1.5 OFF } else{ P1OUT |= 0x20; // Set "FALSE" LED at 1.5 ON P1OUT &= ~0x10; // Set "TRUE" LED at 1.5 OFF } break; case 2: //logic "OR" if (((P1IN & 0x88) == 0x88) || ((P1IN & 0x80) == 0x80) || ((P1IN & 0x08) == 0x08) ) { P1OUT |= 0x10; P1OUT &= ~0x20; } else{ P1OUT |= 0x20; P1OUT &= ~0x10; } break; case 3: //logic "XNOR" if (((P1IN & 0x88) == 0x88) || ((P1IN & 0x80) == 0x80) || ((P1IN & 0x08) == 0x08) ) { P1OUT |= 0x20; P1OUT &= ~0x10; } else{ P1OUT |= 0x10; P1OUT &= ~0x20; } break; case 4: //logic "XOR" if ((P1IN & 0x88) == 0x88) { P1OUT |= 0x20; P1OUT &= ~0x10; } else if ((P1IN & 0x80) == 0x80){ P1OUT |= 0x10; P1OUT &= ~0x20; } else if ((P1IN & 0x08) == 0x08){ P1OUT |= 0x10; P1OUT &= ~0x20; } else{ P1OUT |= 0x20; P1OUT &= ~0x10; } break; case 5: //logic "NAND" { if ((P1IN & 0x88) == 0x88) { P1OUT |= 0x20; P1OUT &= ~0x10; } else{ P1OUT |= 0x10; // Set green LED off when button up P1OUT &= ~0x20; } break; case 6: //logic "XNOR" if ((P1IN & 0x88) == 0x88) { P1OUT |= 0x10; P1OUT &= ~0x20; } else if ((P1IN & 0x80) == 0x80){ P1OUT |= 0x20; P1OUT &= ~0x10; } else if ((P1IN & 0x08) == 0x08) { P1OUT |= 0x20; P1OUT &= ~0x10; } else{ P1OUT |= 0x10; P1OUT &= ~0x20; } break; default: P1OUT &= ~0x71; } } }
But now I am trying to do it with interrupts and I get problems while pressing both buttons at the same time (simulating 2 inputs of ´1´ and ´1´). for pressing one of the buttons I used this code and it works:
#pragma vector=PORT1_VECTOR __interrupt void Port_1(void) { if(P1IFG & BUTTON){ P1OUT ^= LED1; // P1.6 = toggle P1IFG &= ~BUTTON; // P1.3 IFG cleared P1IES ^= BUTTON; // toggle the interrupt edge, }
But when I want to set the "truth" LED on while pressing both buttons at the same time it does not work
if ((P1IFG & BUTTON1)&&(P1IFG & BUTTON)){ P1OUT ^= LED2; P1IFG &= ~(BUTTON + BUTTON1); P1IES ^= (BUTTON + BUTTON1); }
I have stopped coding when I realized that I got it wrong,so the code is not complete, but eventually I want to code it so it functions exactly as the first polling code.
#include <msp430x20x2.h> #define LED0 BIT0 #define LED1 BIT6 #define LED2 BIT4 #define BUTTON BIT3 #define BUTTON1 BIT7 int main(void) { WDTCTL = WDTPW + WDTHOLD; // Stop watchdog timer P1DIR |= (LED0 + LED1 + LED2); P1OUT &= ~(LED0 + LED1 + LED2); P1IE |= (BUTTON + BUTTON1); // P1.3 and P1.7 interrupt enabled P1IFG &= ~(BUTTON + BUTTON1); // P1.3 and P1.7 IFG cleared __enable_interrupt(); // enable all interrupts for(;;) {} } // Port 1 interrupt service routine #pragma vector=PORT1_VECTOR __interrupt void Port_1(void) { if(P1IFG & BUTTON){ P1OUT ^= LED1; // P1.6 = toggle P1IFG &= ~BUTTON; // P1.3 IFG cleared P1IES ^= BUTTON; // toggle the interrupt edge, // the interrupt vector will be called // when P1.3 goes from HitoLow as well as // LowtoHigh } if(P1IFG & BUTTON1){ P1OUT ^= LED0; // P1.0 = toggle P1IFG &= ~BUTTON1; // P1.7 IFG cleared P1IES ^= BUTTON1; // toggle the interrupt edge, // the interrupt vector will be called // when P1.3 goes from HitoLow as well as // LowtoHigh } if ((P1IFG & BUTTON1)&&(P1IFG & BUTTON)){ P1OUT ^= LED2; P1IFG &= ~(BUTTON + BUTTON1); P1IES ^= (BUTTON + BUTTON1); } }
I am new to msp430 and to microcontrollers and I understand that there is a problem with how I handle the interrupts (the ISR reads only 1 interrupt at a time??) but can't figure out how to fix it.
any help would be much appreciated
Many thanks,
Shahar