Timer1 Läuft nicht richtig

Gast #285104
Lesenswert?
• ▲
▼
Hallo Leute,

ich baue eine Uhr die Relativ genau gehen soll.
Mit dem Sourcecode ist eine Sekunde leider 16 Sekunden lang ;-(
Was mache ich falsch?
Benutze einen ATINY2313-20PU mit 16 Mhz extern Quarz.

Danke für die hilfe

Hier der Sourcecode:




#include <main.h>
#include <lcd.c>


 uint8_t second=0;
 uint8_t secled=0;
 uint8_t minute=0;
 uint8_t hour=0;

SIGNAL (SIG_OVERFLOW1)
{
   second ++;
   if(second == 60)
   {
      second = 0;
      minute ++;
   };
   if(minute == 60)
   {
      minute = 0;
      hour ++;
   };
   if(hour == 24)
   {
      hour = 0;
   };

};

//Hauptprogramm
int main (void)
{

  DDRD  = 0x00; /* alle Pins von Port D als Eingang */
  PORTD = 0xff; /* interne Pull-Ups an allen Port-Pins aktivieren */

  //Initzialisierung des LCD - Displays
  LCD_Init();
  LCD_Print(1,0,"Clock");

   OCR1AL = 0x09;
   OCR1AH = 0x3d;
   TCNT1L = 0xf7;
   TCNT1H = 0xc2;
   TCCR1B |= (1<<CS10)|(1<<CS12); //1024
   TIMSK |= (1 << TOIE1);
   sei();

  unsigned char count;
  //Hauptprogramm läuft ständig in einer schleife
  while (1)
    {
    /*       if ( !(PIND & (1<<PIND4)) ) {
           count++;
         {
         if ( !(PIND & (1<<PIND5)) ) {
           count--;
         { */
        LCD_Print(0,1,"Time: %i:%i:%i",hour,minute,second);
    }
return (1);
};
Gast #285108
Lesenswert?
• ▲
▼
Ich denke es muss so aussehen:

volatile uint8_t second=0;

Du musst alle Variablen die in einem Interrupt geändert werden mit
"volatile" deklarieren.

Sonst fällt mir noch das ein:

SIGNAL (SIG_OVERFLOW1)
{
  // Am ende von dem Signal diesen code plazieren
  // timer = overflow - cpufreq / prescaler
  TCNT1    = 0        - F_CPU   / 1024;
}

Feadi
Gast #285109
Lesenswert?
• ▲
▼
Ich verstehe nicht warum bei mir 1 Sekunde 10 Sekunde dauert :-(

Wie kann ich nachprüfen mit wieviel Mhz der AVR läuft? Kann man das
irgendwie messen das man 100% sicher ist?

Hab das so gemacht:

#include <main.h>
#include <lcd.c>
//#include <avr/delay.h>


 volatile uint8_t second=0;
 volatile uint8_t minute=0;
 volatile uint8_t hour=0;

SIGNAL (SIG_OVERFLOW1)
{
   second ++;
   if(second == 60)
   {
      second = 0;
      minute ++;
   };
   if(minute == 60)
   {
      minute = 0;
      hour ++;
   };
   if(hour == 24)
   {
      hour = 0;
   };
   TCNT1    = 0        - F_CPU   / 1024;
};

//Hauptprogramm
int main (void)
{

  DDRD  = 0x00; /* alle Pins von Port D als Eingang */
  PORTD = 0xff; /* interne Pull-Ups an allen Port-Pins aktivieren */

  //Initzialisierung des LCD - Displays
  LCD_Init();
  LCD_Print(1,0,"Clock");

    OCR1AL = 0x09;
    OCR1AH = 0x3d;
    TCNT1L = 0xf7;
    TCNT1H = 0xc2;
    TCCR1B |= (1<<CS10)|(1<<CS12); //1024
    TIMSK |= (1 << TOIE1);
    sei();

  unsigned char count;
  //Hauptprogramm läuft ständig in einer schleife
  while (1)
    {
        LCD_Print(0,1,"Time: %i:%i:%i",hour,minute,second);
        //_delay_ms(100);
    }
return (1);
};





main.h


#ifndef MAIN_H
 #define MAIN_H

#include <stdio.h>
#include <stdlib.h>
#include <avr/io.h>
#include <avr/interrupt.h>
#include <avr/signal.h>

#include "lcd.h"

#define SYSCLK  16000000  //Quarz Frequenz in Hz
#define F_CPU 16000000

extern int main (void);

#endif //_MAIN_H_
Gast #285114
Lesenswert?
• ▲
▼
OCR1AL = 0x09;
OCR1AH = 0x3d;

TCCR1B |= (1<<CTC1)|(1<<CS10)|(1<<CS12); //1024
TIMSK |= (1 << TOIE1);
sei();

Initialisiere den Timer mal so. Die letzte Zeile (TCNT1=0....)in der
ISR lass weg. Den Rest aus der ISR kannst du später verlegen wenn es
mal grundsätzlich klappt.
Mit dem selben Takt kannst du auch das LCD ansteuern.
Gast #285115
Lesenswert?
• ▲
▼
Der hat irgendwie probleme mit CTC1:

Compiling: main.c
avr-gcc -c -mmcu=attiny2313 -I. -g -Os -funsigned-char
-funsigned-bitfields -fpack-struct -fshort-enums -Wall
-Wstrict-prototypes -Wa,-adhlns=main.lst  -std=gnu99 main.c -o main.o
main.c:19: warning: `SIG_OVERFLOW1' appears to be a misspelled signal
handler
main.c: In function `main':
main.c:52: error: `CTC1' undeclared (first use in this function)
main.c:52: error: (Each undeclared identifier is reported only once
main.c:52: error: for each function it appears in.)

Antwort schreiben

Hinweis: der ursprüngliche Beitrag ist mehr als 6 Monate alt. Bitte hier nur auf die ursprüngliche Frage antworten, für neue Fragen einen neuen Beitrag erstellen.

Formatierung
  • [c]C-Code[/c]
  • [code]Code in anderen Sprachen, ASCII-Zeichnungen[/code]
  • [math]Formel in LaTeX-Syntax[/math]
  • [[Titel]] – Link zu einem Artikel
  • Verweis auf einen anderen Beitrag: Rechtsklick auf dessen Beitrags-ID (#8078628), „Adresse kopieren“, in den Text einfügen

Mehr zur Formatierung

Längeren Sourcecode als Anhang, nicht in den Text. JPG nur für Fotos und Scans; Zeichnungen und Screenshots als PNG oder GIF. Siehe Bildformate.

Schon registriert? Anmelden

Wird nicht angezeigt. Wir schicken dir einen Link; sobald du damit bestätigst, erscheint dein Beitrag.

Mit dem Abschicken legst du einen kostenlosen Account an und erkennst die Nutzungsbedingungen und die Datenschutzerklärung an.