We are trying to set up a button interrupt on port Ra.5 on the 16f688 chip to light a led, this is the first time that we have worked with the innterrupt command, any suggestions? Will post the program that we have so far if necessary.
Printable View
We are trying to set up a button interrupt on port Ra.5 on the 16f688 chip to light a led, this is the first time that we have worked with the innterrupt command, any suggestions? Will post the program that we have so far if necessary.
Here is the code, If i will help at all.Code:Trisa = 32
Trisc = 0
ioca=%10000000
a Var porta
c var portc
t1 var word
t1=200
start:
on interrupt goto buttonpressed
INTCON = %10000000
one:
gosub left:
goto one:
buttonpressed:
gosub All_on:
goto buttonpressed:
resume
''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''
'SUBROUTINES
left:
a=4:c=36
pause t1
a=0: c=0
pause t1
return
all_on:
a=7:c=63
pause t1
return
Got a few problems there ...
For Interrupt on change with RA5, you need to set bit 5 of the IOCA register. You have bit 7 set.Then the PortA change interrupt needs to be enabled (RAIE)...Code:ioca=%00100000
In the interrupt handler (buttonpressed), you MUST read PORTA to end the mismatch condition, and clear the interrupt flag before exiting the handler. And it must exit the handler. You have a continuous loop in there, remove the goto.Code:INTCON = %10001000
Keep in mind that you will get an interrupt on both the Press and Release of the button. You will eventually need to change the interrupt handler to determine which Edge occurred.Code:buttonpressed:
gosub All_on:
dummy = PORTA ; clear mismatch condition
INTCON.0 = 0 ; reset interrupt flag
resume
RA5 is also a main oscillator pin. I assume you are using the internal oscillator .. just checking.
You should turn off the Analog functions when using Digital signals.And disable the comparators.Code:ANSEL = 0
Code:CMCON0 = 7
What do you mean by this?Quote:
dummy = PORTA
Also we are trying to make the button, when pressesd, toggle between two subroutines, Exe: one press is the first one, then when you press it again it will go to the next program.
ps: yes we are using the internal oscillator
You'll need to have a BYTE variableAt this point the variable isn't used for anything.Code:dummy VAR BYTE
But by simply reading PORTA, it resets the Latches used to detect the change on the Port.
Without clearing the "Mismatch" condition, there's no way to reset the interrupt flag.
So as soon as you RESUME from the interrupt handler, it would jump right back into the interrupt again.
<br>
This is the code we have now and it still isn't working, the only thing it is doing is stopping the program where it is, What is wrong?Code:Trisa = 32
Trisc = 0
a Var porta:c var portc
x var word:t1 var word
dummy var byte
x=0
t1=200
ANSEL = 0
ioca=%00100000
CMCON0 = 7
start:
on interrupt goto buttonpressed
INTCON = %10001000
one:
gosub left
goto one
buttonpressed:
gosub All_on
dummy=porta ; clear mismatch condition
INTCON.0 = 0 ; reset interrupt flag
resume
''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''
'SUBROUTINES
left:
a=4:c=36
pause t1
a=0: c=0
pause t1
return
all_on:
a=7:c=63
pause t1
return
Add DISABLE/ENABLE around the interrupt handler, and any subroutines called from the handler.
Without them, the interrupt handler will continuously interrupt itself.
Code:DISABLE
buttonpressed:
gosub All_on
dummy=porta ; clear mismatch condition
INTCON.0 = 0 ; reset interrupt flag
resume
ENABLE
...
DISABLE
all_on:
a=7:c=63
pause t1
return
ENABLE
thank you for all of your help, but is there a way to make it so that when you press the button it loops one program continously then, when pressed again goes to another program?
Untested but worth a try:
Code:Button_Flag VAR BIT
DUMMY VAR BYTE
Trisa = 32
Trisc = 0
a Var porta:c var portc
x var word:t1 var word
x=0
t1=200
ANSEL = 0
ioca=%00100000
CMCON0 = 7
start:
on interrupt goto buttonpressed
INTCON = %10001000
DISABLE
buttonpressed:
IF Button_Flag = 1 THEN
gosub All_on
ELSE
gosub LEFT
endif
dummy=porta ; clear mismatch condition
INTCON.0 = 0 ; reset interrupt flag
resume
ENABLE
'...
DISABLE
all_on:
a=7:c=63
Button_Flag = 1
pause t1
return
ENABLE
DISABLE
LEFT:
A=4 : c=36:
Button_Flag = 0
pause t1
a=0: c=0
pause t1
return
ENABLE
We finally got it working! Thanks for all of your help, it was greatly appreciated.Code:Trisa = 32
Trisc = 0
a Var porta:c var portc
x var word:x1 var word:x2 var word: x3 var word:t1 var word:
dummy var byte
t1=200
ANSEL = 0
ioca=%00100000
CMCON0 = 7
start:
on interrupt goto flag
INTCON = %10001000
one:
gosub left
goto one
two:
gosub all_on
goto two
''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''
'SUBROUTINES
disable
flag:
x=1+x
x1=x//2
if x1=0 then
x2=1+x2
x3=x2//2
branch x3,[one_reset,two_reset]
endif
dummy=porta ; clear mismatch condition
INTCON.0 = 0 ; reset interrupt flag
resume
enable
disable
left:
a=4:c=36
pause t1
a=0: c=0
pause t1
return
enable
disable
all_on:
a=7:c=63
pause 100
return
enable
one_reset:
x=0
goto one
two_reset:
x=0
goto two