Problemer med brug af Timer med AVR

Mar 17, 2007 30 Replies

Hejsa



Jeg har forsøgt at få svar via programmering.C-nyhedsgruppen, men desværre uden held, så nu prøver jeg her i stedet.



Jeg sidder og leger lidt med AVR-controllere, men har et program, jeg bare ikke kan få til at virke.



Programmet benytter timer0, der tæller til 250 vha. system clock/8. Dette giver en fast tid på 500us. Hver gang Timer 0 laver overflow, vil variablen timecount blive talt 1 op. Når denne er lig 1000, vil den toggle bit 7 på PortA, som dermed blinker ved 1Hz. Problemer er blot. Den lyser konstant, men jeg kan ikke se, hvad der er galt.



Kan nogen ikke hjælpe mig?



#include unsigned int timecount = 0; //global time counter



//Timer 0 overflow ISR interrupt [TIM0_OVF] void timer0_ovf_isr(void) { TCNT0 = 6; // start med at tælle fra 6; Tæl til 250 if(++timecount == 1000) { PORTA = PORTA ^ 0x80; // Toggle bit 7 på PortA timecount = 0; // Clear for de næste 500 us } }



void main(void) { DDRA = 0x80; // Port A bit 7 er output TCCR0 = 0x02; // Sæt Timer0 til clock/8 som clock input TCNT0 = 0x00; // Start Timer med værdien 0 i timer // Timer 0 interrupt initialisering TIMSK = 0x01; // Afmask Timer 0 overflow interrupt // Global aktivering af interrupts #asm("sei") while(1) ; }



Mvh. Tomas

Hedder det mon ikke:

PORTA = PINA ^ 0x80;

Christen

Christen Fihl skrev:

Det gør desværre ingen forskel. Bit 7 er stadig høj konstant

Mvh. Tomas

Tomas . skrev:

Lav et program der toggler benet uden en timer. Så kan ud finde ud af om det er timeren eller toggler det er galt med.

Hilsen Mikkel Lund "Sund fornuft, har aldrig stoppet en tosse" Jokeren i "Mænds ruin"

"Tomas ." skrev i en meddelelse news: snipped-for-privacy@dtext.news.tele.dk...

PORTA = PORTA ^0x80; (eller PORTA ^= 0x80;)

er korrekt, dit problem ligger i erklæringen af din globale variabel. Compileren kan ikke se at variablen bliver anvendt af din mainline kode, så derfor optimeres dens brug i interrupthandleren væk.

Erklær enten variablen volatile eller mere pænt, da du ikke bruger den andre steder, erklær den static som en lokal variabel i funktionen.

Mvh Henrik

Mon ikke, du mener sådan?

#include

//Timer 0 overflow ISR interrupt [TIM0_OVF] void timer0_ovf_isr(void) { static unsigned int timecount = 0; //global time counter TCNT0 = 6; // start med at tælle fra 6; Tæl til 250 if(++timecount == 1000) { PORTA = PINA ^ 0x80; // Toggle bit 7 på PortA timecount = 0; // Clear for de næste

500 us } }

Det har desværre ingen ændring. Den f#¤$$ LED er stadig ON hele tiden :-(

Mvh. Tomas

"Tomas ." skrev i en meddelelse news: snipped-for-privacy@dtext.news.tele.dk...

Du har ikke rettet PINA tilbage til PORTA:

PORTA = PINA ^ 0x80; skal være PORTA = PORTA ^ 0x80;

Mvh Henrik

Henrik [6040] skrev:

counter

PortA

hele

Det var en svipser. Men resultatet er stadig det samme - en konstant lysende LED :-(

Mvh. Tomas

Hejsa,

kan 'timecount' tælles op til 1000??

8-bit processor, eller??

/C

Claus skrev:

Ja da. timecount er defineret som unsigned int og kan derfor indeholde en værdi fra 0 - 65.535.

Jeps. AVR er 8-bit processorer.

Mvh. Tomas

"Tomas ." skrev i en meddelelse news: snipped-for-privacy@dtext.news.tele.dk...

Hvor hurtigt kører krystallet på den der micro?

Mvh Henrik

Henrik [6040] skrev:

Den kører med intern oscillator 4MHz

Mvh. Tomas

Så din compiler håndterer at stable 2 stk. 8-bit registre 'oven på' hinanden??

Kan du osse erklære en long unsigned int på 32 bit på den AVR??

/Claus

Claus skrev:

på'

Det tror jeg næsten. Jeg bruger en bog, der hedder "Embedded C programming and the AVR" som "Lærebog" for mig selv. Det er her eksemplet er fra. Men de er åbenbart ikke helt fejlfri :-(

Mvh. Tomas

rrupt

Mener du ikke:

TIMSK =3D 0x02;

Det er vel bit 1 (v=E6rdi 0x02) du skal s=E6tte? Bit 0 (v=E6rdi 0x01) har vist ingen virkning.

/Thomas

Det er så det man kalder "double-precision" ;)

/Thomas

Hejsa,

I dit sted ville jeg konsultere manualen for den anvendte C-compiler.

/C

Hej Tomas

Jeg har haft samme problem i starten men jeg lavede nogle macro'er der løste problemet:

Eks: if(++timecount == 1000) > { > PORTA = PORTA ^ 0x80; // Toggle bit 7 på PortA > timecount = 0; // Clear for de næste 500 us > } > }

til:

if(++timecount == 1000) > { > tgl(PORTA, 7); // Toggle bit 7 på PortA > timecount = 0; // Clear for de næste 500 us > } > }

/** * @brief Macro for bitmanipulation */ #define sbi(arg, BitNo) (arg |= (1

Henrik [6040] skrev:

, s=E5

den andre

husk at du i hver andet geneml=F8g skal skifte udgangen henholdsvis h=F8j= /lav mvh bamse

Join the Discussion

Have something to add? Share your thoughts — no account required.

Didn't find your answer?

Ask the community — no account required