Sida 1 av 1
interrupt problem PIC18f458 *LÖST*
Postat: 20 maj 2008, 18:36:50
av slatte
Jag är helt ny på 18f serien och som jag förstår det så använder man inte interruppt rutinen på samma sätt här. utan man har 2 st en hög och en låg prioritets interrupt? men jag lyckas inte få det att fungera har försökt att läsa mig till det och har provat en massa, men får det verkligen inte att fungera.
använder Mplab med c18 kompilatorn
Här är min kod se om ni kan säga vad jag gör för fel. säkert massor
Kod: Markera allt
#include <p18f458.h>
#pragma config OSC = XT, OSCS = OFF
#pragma config PWRT = ON, BOR = OFF
#pragma config WDT = OFF
#pragma config STVR = ON, LVP = OFF
#pragma interruptlow interrupt_low
#pragma interrupt interrupt_high
void init (void){
TRISA = 0; //PORTA out
TRISB = 0; //PORTB out
PORTA = 0;
PORTB = 0;
T0CON = 0b11000000;
INTCON = 0b10100000;
INTCONbits.T0IF = 0;
TMR0L = 0b00000000;
TMR0H = 0b00000000;
INTCON2bits.TMR0IP = 1;
}
void interrupt_high(){
static char temp = 0;
if (temp < 10)
PORTB = 0b11111111;
else if(temp < 20)
PORTB = 0b00000000;
else
temp = 0;
INTCONbits.T0IF = 0;
TMR0L = 0b00000000;
TMR0H = 0b00000000;
}
void interrupt_low(){
}
void main (void){
init();
while (1){
}
}
Postat: 20 maj 2008, 19:33:25
av sodjan
> utan man har 2 st en hög och en låg prioritets interrupt?
Om man vill och behöver !
I 99 fall av 100 behöver man det inte och det är *mycket*
enklare at köra "som vanligt" med 1 interrupt prio-nivå.
Postat: 20 maj 2008, 19:44:20
av bos
Till att börja med skulle du ju kunna berätta vad som är det förväntade resultatet, och vad som händer. Det går att med hjälp av din kod utröna vad som händer med PORTB, men du skriver inte om det händer något här.
Oavsett vilket så är din interrupt konstig. Du testar "temp" för olika värden, men inte någonstans inkrementeras denna variabel. Den är noll hela tiden.
Postat: 20 maj 2008, 19:59:45
av slatte
hmm har inte kollat så mycket på funktionen i interruptet ännu tack vare att jag inte får den att gå in i interruptet. Gjorde lite ändringar hitta var man stängde av prioitets interruptet nu;-). hela funktionen är bara att initiera och sedan gå till while satsen som är en evighetsloop och när timern0 går overflow ska den gå in i interrupt. Typ så var det tängt att det ska fungera.
När jag stegar igenom händer något annat. När TMR0IF (alltså då jag vill att den ska hoppa till interrupt rutinen) sätts så hoppar den in i filen c018i.c av någon anledning som jag inte förstår och där händer en del grejer som t.ex att den nollställer GIE
Kod: Markera allt
#include <p18f458.h>
#pragma config OSC = XT, OSCS = OFF
#pragma config PWRT = ON, BOR = OFF
#pragma config WDT = OFF
#pragma config STVR = ON, LVP = OFF
void init (void){
TRISA = 0; //PORTA out
TRISB = 0; //PORTB out
PORTA = 0;
PORTB = 0;
T0CON = 0b11000000; // TIMER0 med prescaler 1:2 och intern CLK
INTCON = 0b10100000; // 1= GIE; 0= IPEN; 1= TMR0IE; 0= INT0IE;
// 0= RBIE; 0= TMR0IF; 0= INT0IF; 0= RBIF
INTCONbits.T0IF = 0; //nollar TIMER0 interrupt flag
TMR0L = 0; //nollar TMR0
TMR0H = 0;
INTCON2bits.TMR0IP = 1; //TMR0IP Overflow interrupt priority bit
RCONbits.IPEN = 0; //disable priority interrupt
}
void interrupt(){
static char temp = 0; //VAD SOM GÖRS I INTERRUPTET ÄR INTE
//SÅ VIKTIGT JAG VILL BARA VETA VARFÖR
//DEN INTE GÅR IN I INTERRUPTET
if (temp < 10){
PORTB = 0b11111111;
temp++;
{
else if(temp < 20){
PORTB = 0b00000000;
temp++;
}
else
temp = 0;
INTCONbits.T0IF = 0; //nollar flaggan
TMR0L = 0b00000000; //nollar TMR0
TMR0H = 0b00000000; //behöver nog inte nolla denna egetligen men gör det för säkerhets skull
}
void main (void){
init();
while (1){
}
}
Postat: 20 maj 2008, 20:30:14
av Micke_s
Har inte PIC18F458 och massa andra äldre kiseluppsättningar massa skumma effekter när man använder olika prioriteringsordningar på interrupten?
Postat: 20 maj 2008, 20:33:56
av sodjan
Dels är det nu avstängt, dels så borde kompilatorn känna till det.
> och där händer en del grejer som t.ex att den nollställer GIE
Lite konstigt, GIE sköts av processorn (d.v.s hårdvaran) automatiskt.
D.v.s när interruptet inträffar och när man (eller kompilatorn) gör RETFIE.
Aja, jag vet inte hur det fungerar i C...
Postat: 20 maj 2008, 20:36:58
av slatte
ingen aning! men jag tror att jag har satt den funktionen som disable i vilket fall genom
Kod: Markera allt
RCONbits.IPEN = 0; //disable priority interrupt
Men hittar ni något jag känner att jag inte har alls koll på detta så att det kan vara något jätte basic fel med för den delen
EDIT: bah får snart börja med assembler igen

fast det lär väll inte hjälpa
Postat: 20 maj 2008, 20:38:36
av bos
Jag ser inte att du sätter GIE någonstans.
Postat: 20 maj 2008, 20:40:32
av slatte
Kod: Markera allt
INTCON = 0b10100000; // 1= GIE; 0= IPEN; 1= TMR0IE; 0= INT0IE;
// 0= RBIE; 0= TMR0IF; 0= INT0IF; 0= RBIF

Postat: 20 maj 2008, 21:45:04
av bos
När jag bytte till C så slutade jag använda den typen av deklarationer när det gäller konfigurationsflaggor, så det var därför jag missade det. Jag använder istället GIE = 1; T0IE = 1, osv.
Nåväl. Du har fortfarande inte ändrat koden i din interrupt, så den kommer bara att sätta PORTB till -1 en enda gång. Du vill nog lägga till en temp += 1 nånstans.
Har du byggt upp en krets kring cpu:n, eller kör du bara i simulator? Om det senare, sätt en breakpoint i interrupten.
Postat: 20 maj 2008, 22:03:17
av slatte
Jag kör bara simulator! och angående deklarationen är det nog snyggare att göra som du gör

ändrade lite i interrupt rutinen med, inte för att det kommer göra någon nytta om den inte hoppar in i funktionen

Postat: 20 maj 2008, 22:49:43
av BER
Tror att detta saknas...
Kod: Markera allt
#pragma code HIGH_INTERRUPT_VECTOR = 0x208
void high_ISR (void)
{
_asm
goto interrupt_high
_endasm
}
#pragma code
#pragma interrupt_high
void interrupt(){
...
}
Kontrollera med databladet att 0x208 stämmer för din PIC
Postat: 20 maj 2008, 22:51:39
av slatte
Gött!! ska genast undersöka detta danke danke!!
Postat: 20 maj 2008, 23:02:21
av BER
Skall du lägga ut något på portpinnarna skall du anväda "LAT" registren om jag minns rätt.
Postat: 20 maj 2008, 23:10:10
av slatte
gött nu fungerar det gjorde lite ändringar men du löste problemet danke danke!! Du gjorde mig glad har suttit och klurat på det ett tag. jag läste lite om portarna och hittade något om LAT får kolla nogrannare på det. såhär fick jag det att fungera:
Kod: Markera allt
#include <p18f458.h>
#pragma config OSC = XT, OSCS = OFF
#pragma config PWRT = ON, BOR = OFF
#pragma config WDT = OFF
#pragma config STVR = ON, LVP = OFF
#pragma code high_vector = 0x0008
void interrupt_1(void);
void interrupt_at_high_vector(void)
{
_asm GOTO interrupt_1 _endasm
}
#pragma code
#pragma interrupt interrupt_1
void init (void){
TRISA = 0; //PORTA out
TRISB = 0; //PORTB out
PORTA = 0;
PORTB = 0;
T0CON = 0b11000000; // TIMER0 med prescaler 1:2 och intern CLK
INTCON = 0b10100000; // 1= GIE; 0= IPEN; 1= TMR0IE; 0= INT0IE;
// 0= RBIE; 0= TMR0IF; 0= INT0IF; 0= RBIF
INTCONbits.T0IF = 0; //nollar TIMER0 interrupt flag
TMR0L = 0; //nollar TMR0
TMR0H = 0;
INTCON2bits.TMR0IP = 1; //TMR0IP Overflow interrupt priority bit
RCONbits.IPEN = 0; //disable priority interrupt
}
void interrupt_1(){
static char temp = 0;
if (temp < 10){
PORTB = 0b11111111;
temp++;
}
else if(temp < 20){
PORTB = 0b00000000;
temp++;
}
else
temp = 0;
INTCONbits.T0IF = 0; //nollar flaggan
TMR0L = 0b00000000; //nollar TMR0
TMR0H = 0b00000000; //behöver nog inte nolla denna egetligen men gör det för säkerhets skull
}
void main (void){
init();
while (1){
}
}
Äntligen kan man fortsätta leka
