Continue to Site

Welcome to our site!

Electro Tech is an online community (with over 170,000 members) who enjoy talking about and building electronic circuits, projects and gadgets. To participate you need to register. Registration is free. Click here to register now.

  • Welcome to our site! Electro Tech is an online community (with over 170,000 members) who enjoy talking about and building electronic circuits, projects and gadgets. To participate you need to register. Registration is free. Click here to register now.

dsPIC 18F device, problem with interrupt

Status
Not open for further replies.

tzh0013

New Member
I use the comparator 1 module and it's works fine. however, when I set up the comparator interrupt it starts to mess up.
I once used an USART interrupt and changed it to comparator interrupt, I'm a beginner here and I don't know if I didn't change something.
this is the code in my MPLAB




Code:
//**BEGIN INTERRUPT CONTROL**
#pragma code InterruptVectorHigh = 0x08		//interrupt pointer address (0x08 high priority)
void InterruptVectorHigh (void)
{
        _asm						//assembly code starts
        goto InterruptHandlerHigh	//interrupt control
        _endasm						//assembly code ends
}
#pragma code
#pragma interrupt InterruptHandlerHigh		//end interrupt control
void InterruptHandlerHigh()		// Declaration of InterruptHandler
{
        if(PIR2bits.CMIF){
                        intr = 1;
			PIR2bits.CMIF = 0;	//Clear Flag
        }
    INTCONbits.GIE = 1;
    PIE2bits.CMIE = 1;  //Re-enable all interrupts
return;
}

Appreciated for your time
 
Hi,

As I understand it, you do not have to re-enable Global Interrupts within your ISR, it is done automatically when you exit the ISR.

I wouldn't have thought it necessary to re-enable the CMIE either.

Also, there is no need for the return instruction, at the end of the ISR a RETFIE (fast return - if high priority interrupts enabled, or regular return otherwise) is automatically executed.

Always difficult to diagnose a problem when not seeing the ISR in the full context of the entire code.

EOE!
 
Code:
PIE2bits.CMIE = 1;  //Re-enable all interrupts

This should read
Code:
PIE2bits.CMIF = 0;  //Clear interrupt flag

There is no need to set the Global interrupt flag as the Interrupt return does that

Also loose the return statement.... This shouldn't be here... The ISR is a void function and uses a different return type...
 
Really thank you for your time and your information. And also , that's the problem, The ISR is isolated from the program (in my case it's a state machine) but it can still blocking the function of the state machine.

so you are suggesting that i should delete "INTCONbits.GIE = 1;
PIE2bits.CMIE = 1; " and "Return " ?
 
Code:
//**BEGIN INTERRUPT CONTROL**
#pragma code InterruptVectorHigh = 0x08		//interrupt pointer address (0x08 high priority)
void InterruptVectorHigh (void)
{
        _asm						//assembly code starts
        goto InterruptHandlerHigh	//interrupt control
        _endasm						//assembly code ends
}
#pragma code
#pragma interrupt InterruptHandlerHigh		//end interrupt control
void InterruptHandlerHigh()		// Declaration of InterruptHandler
{
        if(PIR2bits.CMIF){
                        intr = 1;
			PIR2bits.CMIF = 0;	//Clear Flag *** You already do it here ***
        }
    

}

Like this..
 
I changed it and it works fine when I isolated the interrupt and the main program. however, it still acting wired when I try to use my varible in the main loop.

Sometimes it works fine and other times, the output pin (RA5 and RC0) are remainning 0 for a really long time and also the comparator output is not working at the same time. after 20-30 sec, it's working again. I already declare the "intr" as volatile as you told me yeaterday. but somehow it's still doesn't help.
Code:
#include <stdio.h>
#include <stdlib.h>
#include <delays.h>
#include <p18f2455.h>
#pragma config FOSC = HS // Oscillator Selection:External oscillator
#pragma config WDT = OFF	// Watchdog Timer
#pragma config LVP = OFF	// Low Voltage ICSP(PIN 6):Disabled


volatile unsigned int intr; 
unsigned int state;

void InterruptHandlerHigh (void);
void main(void)
{

        state = 0;
        intr = 0;
        TRISC = 0;
        TRISAbits.TRISA0 = 1;
        TRISAbits.TRISA1 = 0;
        TRISAbits.TRISA2 = 0;
        TRISAbits.TRISA3 = 1;
        TRISAbits.TRISA4 = 0;
        TRISAbits.TRISA5 = 0;
        
        CMCONbits.CM = 0b001;  // Configure Comparator module 
        
        IPR2bits.CMIP = 1;
        PIE2bits.CMIE = 1;
        INTCONbits.PEIE = 1 ;
        INTCONbits.GIE = 1;
        
        


        while (1)
            switch (state)
            { case (0):
                    PORTAbits.RA5 = 0;
                    PORTCbits.RC0 = 1;
                    Delay10KTCYx(200);
                    if (intr)                    // the only time use the variable 
                    {state = 1;
                    intr = 0;}
                    else {state = 0;
                    intr = 0;}
              break;
              case (1):
                   PORTAbits.RA5 = 0;
                   PORTCbits.RC0 = 0;
                   Delay10KTCYx(200);
                   state = 2;

                  break;
                case (2):
                   PORTAbits.RA5 = 0;
                    PORTCbits.RC0 =1;
                    Delay10KTCYx(200);
                    state = 3;
                    intr = 0;
                    break;
                case (3):
                    PORTAbits.RA5 = 1;
                PORTCbits.RC0 =1;
                Delay10KTCYx(200);
               
                    state = 4;
                       break;

                  case (4):
                      PORTAbits.RA5 = 1;
                PORTCbits.RC0 =0;
                    Delay10KTCYx(200);
                    state = 0;
                    break;
                    default:
                    PORTAbits.RA5 = 1;
                    PORTCbits.RC0 = 0;
                        state = 0;
                       break;}


            }

//**BEGIN INTERRUPT CONTROL**
#pragma code InterruptVectorHigh = 0x08		//interrupt pointer address (0x08 high priority)
void InterruptVectorHigh (void)
{
        _asm						//assembly code starts
        goto InterruptHandlerHigh	//interrupt control
        _endasm						//assembly code ends
}
#pragma code
#pragma interrupt InterruptHandlerHigh		//end interrupt control
void InterruptHandlerHigh()		// Declaration of InterruptHandler
{
        if(PIR2bits.CMIF){
                      intr = 1;
		      PIR2bits.CMIF = 0;	//Clear Flag
        }
      //Re-enable all interrupts

}
 
Status
Not open for further replies.

Latest threads

New Articles From Microcontroller Tips

Back
Top