Zur Übersicht - INFO - Neueste 50 Beiträge - Neuer Beitrag - Suchen - Zum C-Control-I-Forum - Zum C-Control-II-Forum

Re: LCD_WriteText() lässt die Uhr langsamer laufen Kategorie: Programmierung C (von PeterS - 13.05.2007 22:53)
Als Antwort auf LCD_WriteText() lässt die Uhr langsamer laufen von Hannes - 10.05.2007 13:43

> Es ist ein ziemlicher Scheissfehler, wenn man ein Messprogramm laufen lässt und am Ende feststellt,
> dass einem 30min abgehen. Den Zeitaufwand um den Fehler zu finden, brauch ich wohl nicht
> erwähnen.
>
> Zum Fehler:
> Die Funktion LCD_WriteText() lässt die Echtzeituhr langsamer laufen, ca. 33sec pro Stunde, wenn die
> Funkt. jede Sekunde aufgerufen wird.
> Was treibt die Funktion mit Timer2, der ja nur für die Systemzeit zuständig ist???

Ich hab mir das ganze angesehen, kann aber nicht erkennen, wieso die LCD Ausgabe soviel Zeit verbrauchen
soll. Geht die Uhr soviel genauer, wenn die LCD Ausgabe nicht drin ist? Den Timer2 stören die LCD
Funktionen nicht, das hab ich geprĂĽft.

Man mu� sich ganz klar sein, Quarze gehörige Abweichungen haben können. Die 33sek pro Stunde sind
zuviel, aber eine Minute in 12 Sd. ist durchaus normal.

Ich bin mit der Konstruktion der Interpreter Interruptroutine selbst nicht ganz glĂĽcklich, es wird zuviel
Interpreterzeit damit verschwendet. Ich werde innerhalb der nächsten 7 Tage eine Zusatzfunktion
in den Interpreter einbauen, die eine einfache Uhr mit dem 10ms Interrupt direkt in Assembler macht.
Man kann dann eine Anfangszeit setzen, und später die aktuelle Uhrzeit abfragen. Die Ungenauigkeit
des Quarzes kann dies aber nicht ausbĂĽgeln. In dem Fall empfehle ich eine I2C Echtzeituhr.

Gruss Peter


>
>
> Anbei das Demoprogramm LCD-Uhr, die Funkt. LCD_Ausgabe() am Schluss habe ich eingefĂĽgt um
> den Fehler zu reproduzieren.
>
>
>
>
>
>
>
> // LCD_Uhr_1: LCD-Uhr  (Anzeigeformat "13:47:24")
> // LED1 blinkt mit 1Hz
> // erforderliche Library: IntFunc_Lib.cc, LCD_Lib.cc
>
> // Auf dem Display wird eine LCD-Uhr im Anzeigenformat "13:47:24" dargestellt.
> // Zeitbasis 10ms Interrupt mit Zeitkorrektur
>
> byte cnt1;                                  // globale Variablendeklaration
> byte Sekunde, Minute, Stunde;               // globale Variablendeklaration
>
> //------------------------------------------------------------------------------
> // Zeichenausgabe
> //
> void Write2Digits(byte pos,byte val)
> {
>     char num[3];
>
>     LCD_CursorPos(pos);                     // LCD Cursor positionieren
>     Str_WriteWord(val,10,num,0,2);          // Zahl mit Basis 10, Offset 0, 2 stellig in String schreiben
>     LCD_WriteText(num);                     // String ausgeben
> }
>
> //------------------------------------------------------------------------------
> // Ausgabeformat der Uhr festlegen
> //
> void Display_Time(void)
> {
>     Write2Digits(0,Stunde);                 // Stunde
>     LCD_WriteChar(':');
>     Write2Digits(3,Minute);                 // Minute
>     LCD_WriteChar(':');
>     Write2Digits(6,Sekunde);                // Sekunde
> }
>
> //------------------------------------------------------------------------------
> // Zeitberechnung
> //
> void RTC(void)
> {
>     cnt1++;                                 // 10ms Zähler erhöhen
>     if (cnt1==50)
>     {
>         Port_WriteBit(PORT_LED1,PORT_OFF);  // LED1 ausschalten
>     }
>     if (cnt1==100)
>     {
>         Port_WriteBit(PORT_LED1,PORT_ON);   // LED1 einschalten
>         Display_Time();                     // Funktionsaufruf: Display_Time
>
>         LCD_Ausgabe();
>
>         Sekunde++;
>         if (Sekunde==60)
>         {
>             Sekunde=0;
>             Minute++;
>             if (Minute==60)
>             {
>                 Minute=0;
>                 Stunde++;
>                 if (Stunde==24) Stunde=0;
>             }
>         }
>         cnt1=0;
>     }
> }
>
> //------------------------------------------------------------------------------
> // Interrupt alle 10ms
> //
> void INT_10ms(void)
> {
>     int irqcnt;
>
>     RTC();                                  // Funktionsaufrauf: RTC
>     irqcnt=Irq_GetCount(INT_TIM2COMP);      // Interrupt Request Counter
> }
>
> //------------------------------------------------------------------------------
> // Hauptprogramm
> //
> void main(void)
> {
>     LCD_Init();                             // Display initialisieren
>     LCD_ClearLCD();                         // Display löschen
>     LCD_CursorOff();                        // Display Cursur ausschalten
>
>     cnt1=0;
>
>     Port_DataDirBit(PORT_LED1,PORT_OUT);    // LED1 auf Ausgabe vorbereiten
>     Port_WriteBit(PORT_LED1,PORT_OFF);      // LED1 ausschalten
>     Sekunde=00;                           // Startzeit festlegen z.B. 12:25:00
>     Minute=00;
>     Stunde=00;
>     Irq_SetVect(INT_TIM2COMP,INT_10ms);     // Interrupt Service Routine definieren
>     while (1);                              // Endlosschleife, hier können weitere
>                                             // Anweisungen stehen
> }
>
>
>
> //-------------------------------------------------------------------------------------
> void LCD_Ausgabe(void)                      // wird jede Sekunde aufgerufen
> {
>     char text[10];
>     text="ABCDEFGH";
>     LCD_CursorPos(0x40);                    // Verzögert die RTC
>     LCD_WriteText(text);
>
>
> }


    Antwort schreiben


Antworten:

Re: LCD_WriteText() lässt die Uhr langsamer laufen (von Hannes - 14.05.2007 8:09)
    Re: LCD_WriteText() lässt die Uhr langsamer laufen (von Mike - 13.08.2007 14:31)