I am having problems with doing an external interrupt using Z8FS021 Zmotion processors. When my external interrupt is trigger, the MCU seems to locks ups. I am not sure what I am doing wrong, but would appreciate any input anyone would have on how to resolved the issue.
Harware Configuration:
Basic Z8FS021A MCU. I am using PA0, PA1, PA2 for lighting LEDs. PA3 is used connected to MOM switch that when pressed, it goes from GND to 3.2V. I am using a pull down resistor on PA3 to ensure that its at 0V. I am also using Timer0 at 2Hz rate to blink an LED and increment a counter. (that part works).
If you could look at my code. I have put into a single file to make it easier to review.
Appreciate any input.
Don
| Code: |
/**********************************************************************************************************
** INTERRUPT DEMO ROUTINE
**
** Purpose: To demonstrate using multiple interrupt, external and timer.
**
** Hardware: Using 3 LED connected to PA0, PA1 and PA2. Use the timer to blink LED3, every 1/2 second
** and every 10 blinks, toggle LED 2. For the external GPIO interrupt, toggle LED1 everytime
** the switch is pressed. (rising edge using a MOM SW connected to Vcc).
**
** Reference: Used examples from Zilog AN0141 and the timer service routine was generated by
** http://projectproto.blogspot.com/2010/07/zilog-z8f64xx-timer-calculator.html
**
** Issues: When the PA3 is trigger from LOW to HIGH, the MCU locks up. Not sure why?
***********************************************************************************************************/
#include <ez8.h>
// DEFINES
#define LED_PORT PAOUT // Set the LED using PAOUT
#define LED_BIT1 0x01 // Define LED_BIT1 as 1st Bit of register
#define LED_OFF1 LED_PORT |= LED_BIT1 // LED OFF - Set Bit High to turn LED OFF
#define LED_ON1 LED_PORT &= ~LED_BIT1 // LED ON - Set big low to turn LED ON
#define LED_TOGGLE1 LED_PORT ^=LED_BIT1 // Toggle the LED
#define LED_BIT2 0x02 // Define LED_BIT2 as 2nd Bit of register
#define LED_OFF2 LED_PORT |= LED_BIT2 // LED OFF - Set Bit High to turn LED OFF
#define LED_ON2 LED_PORT &= ~LED_BIT2 // LED ON - Set big low to turn LED ON
#define LED_TOGGLE2 LED_PORT ^=LED_BIT2 // Toggle the LED
#define LED_BIT3 0x04 // Define LED_BIT3 as 3rd Bit of register
#define LED_OFF3 LED_PORT |= LED_BIT3 // LED OFF - Set Bit High to turn LED OFF
#define LED_ON3 LED_PORT &= ~LED_BIT3 // LED ON - Set big low to turn LED ON
#define LED_TOGGLE3 LED_PORT ^=LED_BIT3 // Toggle the LED
#define DO_ME_FOREVER while(1) // Infinite Look -- Having Fun
// GLOBAL VARIABLES
unsigned int count=0; // Keep track of timer
/**********************************************************************************************************
** TIMER0_ISR()
**
** Timer0 Interrupt Service Routine. Toggle LED 3
**
***********************************************************************************************************/
#pragma interrupt
void TIMER0_ISR(void)
{
//DI(); //disable global interrupt
/* your ISR code here */
LED_TOGGLE3;
count++;
//IRQ0 &= ~0x20; //clear pending interrupt request
//EI(); //enable global interrupt
}
/**********************************************************************************************************
** init_TIMER0()
**
** Timer0 Interrupt Initialization Routine. Set to 2 hz schedule
**
***********************************************************************************************************/
void init_TIMER0(void)
{
T0CTL1 &= ~0x80; //disable Timer
T0CTL1 |= 0x01; //continuous mode
T0CTL1 |= (7)<<3; //prescaler
T0H = 0x00; //initial value is 1
T0L = 0x01;
//expected interrupt rate = 2.00001Hz
T0RH = 168; //reload value
T0RL = 195;
SET_VECTOR(TIMER0, TIMER0_ISR);// interrupt vector
IRQ0ENH |= 0x20; //enable timer interrupt
//IRQ0ENL |= 0x20; //(enable this to make it high priority interrupt)
T0CTL1 |= 0x80; //enable timer
}
/**********************************************************************************************************
** isr_p0ad()
**
** Interrupt Service routing for PA3
**
***********************************************************************************************************/
#pragma interrupt
void isr_p0ad(void) //Interrupt service routine for Port A bit3
{
LED_TOGGLE1;
IRQ1 &= ~0x08; //clear pending interrupt request
}/*isr_p0ad*/
/**********************************************************************************************************
** init_p0ad()
**
** GPIO Initialization Routine for PA3
**
***********************************************************************************************************/
void init_p0ad(void) {
// Set PA 3 as interupt (Pin 9)
SET_VECTOR(P4AD, isr_p0ad); // Set vector for interupt. I assume I can use any vector. Is that correct?
PAADDR = 0x02; //Port A Alternate Function
PACTL &= 0x00; //No Alternate Function
PAADDR = 0x01; //Port A Data Direction
PACTL |= 0x08; //Port A bit 3 is configured as Input
IRQ1ENH &= ~0x08; // Set IRQ1 Bit for the field I want to interupt
IRQ1ENL |= 0x08; // Set IRQ1 Lower bit - Low
IRQES |= 0x08; //Interrupt is rising edge triggered
} /*init_p0ad*/
/**********************************************************************************************************
** MAIN()
**
** Main Routine
**
***********************************************************************************************************/
void main(void)
{
DI(); //disable global interrupt
// SETUP THE LED FOR OUTPUT with OPEN DRAIN.
// Setup the Ouput for GPIO for Drain for PA0, PA1 & PA2
PAADDR = 0x03; // Out-Control PA1 to Open Drain: // 00 - No Function, 01 - Data Direction, 02 - Alt Func, 03-Out Control Open Drain, 04 High enabl,
PACTL |= 0x07; // Set Bit 0,1&2 = 7.
// Set the data direction of the GPIO
PAADDR = 0x01; // Data Direction
PACTL &= ~0x07; // Clear lower three bits for output only
// Turn off Control of PA
PAADDR = 0x00;
// Initialize the Interrupts
init_p0ad(); // PA3 initialize interrupt
init_TIMER0(); //initialize timer
EI(); //enable global interrupt
// Turn LED OFF
LED_OFF1;
LED_OFF2;
LED_OFF3;
DO_ME_FOREVER { // Just a little fun with macros: This is while(1)
if (count>10) {
LED_TOGGLE2; // Toggle 2nd Bit
count=0; // Reset Counter
}
}
}
// End of file
|