Vai al contenuto
PLC Forum


Interrupt Timer Con Dspic30 - Non riesco a farlo andare


Neway

Messaggi consigliati

Ho cercato nel forum ma non ho trovato niente in proposito. Premetto che ho letto bene e più volte reference manual e datasheet, ma non sono riuscito a venire a capo della questione.

Per fare la prova vorrei far lampeggiare un led grazie a continui interrupt da parte del timer1. Ho messo un secondo led sulla porta D che lampeggia giusto per capire che il pic è vivo. Nel seguente programma il filo logico di inizializzazione interrupt è questo:

1) Elevo la priorità degli interrupt da timer1 a 7 (la massima possibile)

2) Pulisco l'interrupt flag del timer1

3) Abilito l'interrupt da timer 1

4) Attivo il timer1

Però l'interrupt non funziona. Potreste dirmi dove sbaglio? Ecco il codice scritto in MikroC per dsPIC.

Grazie

void Timer1Int() org 0x001A {
  T1IF_bit = 0;          //clear TMR1 interrupt flag
  TMR1 = 7958;           //reset initial value of timer
  PORTC = ~ PORTC;        //invert led state
}

void main() {
  TRISC = 0;             //portC output
  TRISD = 0;             //portD output
  TMR1 = 7958;           //initial value for timer
  IPC0 = 0xFFFF;         //interrupt prioriry for TMR1 = 7 (the highest possible)
  T1IF_bit = 0;          //clear TMR1 interrupt flag
  T1IE_bit = 1;          //enable TMR1 interrupt
  T1CON = 0b1010000000110000;  //prescaler 1:256 and start timer1
  
  while (1) {                //endless loop. Waiting for timer1 interrupt
       delay_ms (500);       //flash the led
       portd = ~ portd;
    }
  }

Link al commento
Condividi su altri siti


I dsPIC hanno gli interrupt vector, e non c'è bisogno di andare a controllare quale dei bit di flag è a 1. La routine di interrupt è univocamente legata al TIMER 1 attraverso la direttiva org 0x1A. E' così anche in tutti gli esempi che ho visto.

Link al commento
Condividi su altri siti

Guarda che è cosa comune per tutti i micro che dispongono di interrupt smile.gif

Io non uso microC. Per i dsPIC ho usato sempre e solo il compilatore "C" della Microcihip quindi non so se è sufficiente quello che hai scritto.

ORG 0x1A significa origine dall'indirizzo 0x1A. E' una direttiva per stabilire un indirizzo assoluto.

Verifica se ci entra in quella locazione. Se non ci entra, come presumo, hai sbagliato il restart dell'interrupt. smile.gif

Link al commento
Condividi su altri siti

Sul manuale del mikroC è scritto di utilizzare ORG e l'indirizzo del corrispettivo interrupt vector.

Ho appena visto sul sito della mikroelektronica che è possibile importare in MPLAB il codice scritto in mikroC per poi fare il debug hardware (ho il pickit 2). Potrebbe essere di grande aiuto per capire cosa succede.

Un'altra informazione. Come faccio ad accorgermi che è scattata una trap senza il debug hardware?

Link al commento
Condividi su altri siti

Si fa alzare un'uscita, questa verrà riabbassata esclusivamente su comando esterno.

Nel caso a cui si riferisce la tua discussione ci sono praticamente due possibilità:

1 - Il programma non entra mai nella sub di interrupt

2 - Il cambio di stato è troppo veloce per essere percepito. Prova ad inserire un secondo contatore nella sub. Ad ogni ingrsso decrementi il contatore, quando si azzera il contatore cambi di stato l'uscita e ricarichi il contatore. In questo modo allunghi a piacimento il periodo e sei sicuro di vedere il cambio di stato.

Link al commento
Condividi su altri siti

Ora funzione, ma rimane un fitto mistero.

A dire il vero un errore c'era, ovvero andava definito il valore di overflow del timer con

PR1 = valore;

ma non era questo il problema.

Il problema era la frequenza di clock, ovvero, lasciando il codice per com'era settando l'oscillatore a 25Mhz (e anche il compilatore ovviamente) l'interrupt ha cominciato a funzionare.

Sottolineo che a 59 Mhz il dsPIC oscillava correttamente visto che eseguiva il lampeggio di un led con delay software.

Dove può stare il problema?

Link al commento
Condividi su altri siti

Non conoscendo il compilatore della MikroC non mi sento di azzardare ipotesi.

Rimangono sempre valide le due ipoitesi del messaggio precedente. Anche se la seconda mi sembra meno probabile perchè la frequenza si praticamente solo dimezzata.

Potrbbe dipendere anche dalla definizione di over flow del timer, dipende da come lavora il compilatore.

Avere misteir non è mai bello. Ti consiglierei di riportare il clock a 59MHz ed eseguire un debugger corretto facendo accendere il led e comandandone lo spegnimentop da comando esterno Hw. Così sei sicuro che entri nella sub ed esegui correttamente il tutto.

Link al commento
Condividi su altri siti

Si, e in ogni caso avevo provato a dare nella routine di interrupt il solo spegnimento di un led acceso all'avvio. Sicuramente il micro non entra nella routine.

In realtà in questo caso il compilatore fa poco e niente perché il tutto avviene settando manualmente i singoli bit.

Ho fatto la prova con l'oscillatore interno settato a 7,37Mhz e anche così incredibilmente non funziona l'interrupt da timer. Funziona soltanto a 25 Mhz blink.gif

Potrebbe trattarsi di qualche problema legato a componentistica esterna? Il PIC è su una basetta per prototipi ed è alimentato tramite il PICkit2. Ho aggiunto anche un condensatore da 1mF tra positivo e negativo.

Grazie per l'aiuto.

Link al commento
Condividi su altri siti

Non sarebbe logico, a meno di condizioni aprticolarissime che impediscono le oscillazioni al di fuori dei 25 MHz.

Sarebbe comunque utile, per poter avanzare ipotesi più significative, conoscere le condizioni al contorno.

Prima di tutto l'esatto tipo di dsPIC, poi che tipo di risuonature impieghi: quarzo, risuonatore ceramico, RC; anche lo schema del circuito della basetta di test non guasterebbe.

Link al commento
Condividi su altri siti

Il dsPIC è un 30F3012, utilizzo l'oscillatore RC interno (Fast RC oscillator a 7.37Mhz) collegato al moltiplicatore.

Lo schema è il più semplice del mondo, cioè il solo dsPIC con collegati:

Alimentazione con condensatore da 1 mF e due led (tramite resistenze) sui pin 7 e 10.

Una foto però rende meglio la disposizione sulla basetta per prototipi. In queste condizioni però non ho mai avuto problemi con tutti gli altri progetti (fatti con PIC a 8 bit)

user posted image

Link al commento
Condividi su altri siti

Non ho mai usato questo dsPIC, ma altri della stessa serie, 30F3013 p.e..

Io ho sempre usato un quarzo esterno. Leggo il datasheet per capire che non ci siano problemi particolari per quel dsPIC.

Link al commento
Condividi su altri siti

  • 2 weeks later...

Non si finisce mai di imparare.

Riassumendo: Il pic funzionava normalmente usando l'oscillatore interno settato a FRC con PLL 4x (28,48Mhz), ma appena cambiavo frequenza o usavo un oscillatore esterno (quarzo) non andavano gli interrupt.

E' bastato mettere un condensatore da 10 nF tra positivo e negativo per risolvere il problema.

Link al commento
Condividi su altri siti

Forse hai problemi di layout. Fai attenzione. Potresti aver rispolto questo problema, ma potrebbero capitartene altri in futuro. Mettere condensatori come pezze, secondo la mia (purtroppo lunga) esperienza quasi mai è risolutivo. sad.gif

Link al commento
Condividi su altri siti

Crea un account o accedi per commentare

Devi essere un utente per poter lasciare un commento

Crea un account

Registrati per un nuovo account nella nostra comunità. è facile!

Registra un nuovo account

Accedi

Hai già un account? Accedi qui.

Accedi ora
×
×
  • Crea nuovo/a...