-         

Seite 1 von 2 12 LetzteLetzte
Ergebnis 1 bis 10 von 11

Thema: Frequenzanzeige mit Atmega 32 ?

  1. #1
    Benutzer Stammmitglied
    Registriert seit
    18.03.2007
    Ort
    NRW
    Beiträge
    62

    Frequenzanzeige mit Atmega 32 ?

    Anzeige

    Suche Hilfe bei meiner Frequenzanzeige mit dem Atmega 32 !
    Habe einen Taktgenerator mit Bascom erstellt , nun möchte ich die erstellte Frequenz des Taktgenerators auf dem Display darstellen, habe aber das Problem das wenn ich den Takt zähle dieser ja hochgezählt wird , und so auch auf dem Display erscheint, also ich bekomme eine Fortlaufende Anzeige der Zählimpulse.
    Nun möchte ich das die Anzeige aber bevor der Zähler wieder auf Null gesetzt um wieder neu zu zählen als fester Wert für eine bestimmte Zeit auf dem Display stehen bleibt . ( Bin Anfänger und wäre dankbar wenn mir jemand hilft der sich die Mühe macht es mir verständlich zu machen.

    gruß Nase

    Hier den benutzten Code:
    interner 1 Mhz Takt
    '
    ' Display an folgenden Ports
    ' Enable = Port C.4
    ' RS = Port C.5
    ' DB7 = Port C.7
    ' DB6 = Port C.6
    ' DB5 = Port C.3
    ' DB4 = Port C.2
    '
    ' Leds an folgenden Ports
    ' Grün an A.0
    '
    $regfile "m32def.dat" 'Definiert den Atmega als Atmega 32
    $crystal = 1000000 'Gibt die Quarzfrequenz an in Herz
    $hwstack = 32 'Default use 32 for the hardware stack
    $swstack = 10 'Default use 10 for the SW stack
    '-------------------------------------------------------------------------------
    ' Konfiguration fürs Display
    Config Lcd = 16 * 2 'definiert das LCD Display in Art und Größe
    Config Lcdpin = Pin , Db4 = Portc.2 , Db5 = Portc.3 , Db6 = Portc.6 , Db7 = Portc.7 , Rs = Portc.5 , E = Portc.4

    '------------------------------------------------------------------------------
    ' Variablen
    Dim Takt1 As Word
    Dim Takt2 As Word

    '------------------------------------------------------------------------------
    Enable Interrupts

    Portb = &B00011110 ' Pull Up setzen für Pin B1
    Ddra = &B11111111 ' Pin A.7 als Ausgang setzen für blaue Led
    '------------------------------------------------------------------------------
    ' Timer 0
    Config Timer0 = Timer , Prescale = 1024
    Enable Timer0
    On Timer0 Timer_null
    '---------------------------------------
    ' Timer 1
    Config Timer1 = Timer , Prescale = 64
    Enable Timer1
    On Timer1 Timer_eins

    Cls
    '------------------------- H A U P T P R O G R A M M --------------------------
    Do
    Gosub Anzeige

    Waitms 500
    Loop


    '------------------------------ D I S P L A Y - A N Z E I G E -----------------
    Anzeige:
    Cls
    Locate 1 , 1
    Lcd "Takt" ; Takt1
    Waitms 200
    Return
    '--------------------------------- T I M E R - 0 -----------------------------
    Timer_null:
    Toggle Porta.0 ' Led Grün
    If Porta.7 = 1 And Porta.0 = 1 Then Takt1 = Takt1 + 1
    If Porta.7 = 0 Then Takt1 = 0

    Return

    '--------------------------------- T I M E R - 1 ------------------------------
    Timer_eins:
    Toggle Porta.7 ' Led Blau
    Return
    '------------------------------------------------------------------------------

  2. #2
    Moderator Robotik Visionär Avatar von radbruch
    Registriert seit
    27.12.2006
    Ort
    Stuttgart
    Alter
    54
    Beiträge
    5.782
    Blog-Einträge
    8
    So vielleicht?

    Code:
    ' Display an folgenden Ports
    ' Enable = Port C.4
    ' RS = Port C.5
    ' DB7 = Port C.7
    ' DB6 = Port C.6
    ' DB5 = Port C.3
    ' DB4 = Port C.2
    '
    ' Leds an folgenden Ports
    ' Grün an A.0
    '
    $regfile "m32def.dat" 'Definiert den Atmega als Atmega 32
    $crystal = 1000000 'Gibt die Quarzfrequenz an in Herz
    $hwstack = 32 'Default use 32 for the hardware stack
    $swstack = 10 'Default use 10 for the SW stack
    '-------------------------------------------------------------------------------
    ' Konfiguration fürs Display
    Config Lcd = 16 * 2 'definiert das LCD Display in Art und Größe
    Config Lcdpin = Pin , Db4 = Portc.2 , Db5 = Portc.3 , Db6 = Portc.6 , Db7 = Portc.7 , Rs = Portc.5 , E = Portc.4
    
    '------------------------------------------------------------------------------
    ' Variablen
    Dim Takt1 As Word
    Dim Takt2 As Word
    Dim Takt1_temp As Word
    Dim Takt2_temp As Word
    '------------------------------------------------------------------------------
    
    Portb = &B00011110 ' Pull Up setzen für Pin B1
    Ddra = &B11111111 ' Pin A.7 als Ausgang setzen für blaue Led
    '------------------------------------------------------------------------------
    ' Timer 0
    Config Timer0 = Timer , Prescale = 1024
    Enable Timer0
    On Timer0 Timer_null
    '---------------------------------------
    ' Timer 1
    Config Timer1 = Timer , Prescale = 64
    Enable Timer1
    On Timer1 Timer_eins
    
    Enable Interrupts
    
    Cls
    '------------------------- H A U P T P R O G R A M M --------------------------
    Do
    Gosub Anzeige
    
    Waitms 500
    Loop
    
    
    '------------------------------ D I S P L A Y - A N Z E I G E -----------------
    Anzeige:
    
    Disable Interrupts
    Takt1 = Takt1_temp
    Takt1_temp = 0
    Takt2 = Takt2_temp
    Takt2_temp = 0
    Enable Interrupts
    
    Cls
    Locate 1 , 1
    Lcd "Takt1" ; Takt1
    Lcd "Takt2" ; Takt2
    Return
    
    '--------------------------------- T I M E R - 0 -----------------------------
    Timer_null:
    Toggle Porta.0 ' Led Grün
    Takt1_temp = Takt1_temp + 1
    Return
    
    '--------------------------------- T I M E R - 1 ------------------------------
    Timer_eins:
    Toggle Porta.7                                              ' Led Blau
    Takt2_temp = Takt2_temp + 1
    Return
    '------------------------------------------------------------------------------
    (ungetestet)

    Die Zählerstände werden alle 0,5 Sekunden angezeigt und auf null gesetzt. Da jeder Aufruf der Interruptroutinen gezählt wird, sollte das Display so direkt die Frequenz in Hz anzeigen.

    Beim Lesen der 16-Bit Zählerstände werden die Interrupts kurz gesperrt. Das könnte zusammen mit der (Un-)Genauigkeit von Waitms 500 zu einem kleinen Messfehler führen.

    Gruß

    mic

    Atmel’s products are not intended, authorized, or warranted for use
    as components in applications intended to support or sustain life!

  3. #3
    Benutzer Stammmitglied
    Registriert seit
    18.03.2007
    Ort
    NRW
    Beiträge
    62
    Danke für die schnelle Hilfe, hab's ausprobiert, und siehe da die Anzeige steht wirklich, allerdings blinkt die grüne Led ca 3 bis 4 mal in der Sekunde , das Display zeigt unter Takt1 den Wert 10 und unter Takt2 den Wert von 20 an.Genauen Werte werde ich noch einmal nachmessen und dann bekannt geben.


    Hab den Prescaler von Timer 1 von 64 auf 8 verringert, und bekomme immer noch den gleichen Wert bei Takt1 angezeigt, obwohl sich ja die Torzeit dadurch verringert hat.

  4. #4
    Moderator Robotik Visionär Avatar von radbruch
    Registriert seit
    27.12.2006
    Ort
    Stuttgart
    Alter
    54
    Beiträge
    5.782
    Blog-Einträge
    8
    Hallo

    Das war ja klar, dass es nicht auf Anhieb funktioniert ;)

    Der Takt der grünen Led:
    1000000Hz/256/1024 oder etwa 3,81Hz

    Rote Led:
    1000000Hz/256/64 oder etwa 61Hz
    (Rot zu Grün wie 1024 zu 64 oder 61/16=3,8125)

    Der grobe Fehler ist sicher die Zeitmessung mit waitms. Dazu kommen noch die Funktionsaufrufe und die Ausgaben zum LCD. Wissenschaftlicher wäre die Verwendung eines zusätzlichen Timers zum Auslesen der Frequenzzähler:

    Code:
    ' Display an folgenden Ports
    ' Enable = Port C.4
    ' RS = Port C.5
    ' DB7 = Port C.7
    ' DB6 = Port C.6
    ' DB5 = Port C.3
    ' DB4 = Port C.2
    '
    ' Leds an folgenden Ports
    ' Grün an A.0
    '
    $regfile "m32def.dat"                                       'Definiert den Atmega als Atmega 32
    $crystal = 1000000                                          'Gibt die Quarzfrequenz an in Herz
    $hwstack = 32                                               'Default use 32 for the hardware stack
    $swstack = 10                                               'Default use 10 for the SW stack
    '-------------------------------------------------------------------------------
    ' Konfiguration fürs Display
    Config Lcd = 16 * 2                                         'definiert das LCD Display in Art und Größe
    Config Lcdpin = Pin , Db4 = Portc.2 , Db5 = Portc.3 , Db6 = Portc.6 , Db7 = Portc.7 , Rs = Portc.5 , E = Portc.4
    
    '------------------------------------------------------------------------------
    ' Variablen
    Dim Takt1 As Word
    Dim Takt2 As Word
    Dim Takt3 As Word
    Dim Takt1_temp As Word
    Dim Takt2_temp As Word
    '------------------------------------------------------------------------------
    
    Portb = &B00011110                                          ' Pull Up setzen für Pin B1
    Ddra = &B11111111                                           ' Pin A.7 als Ausgang setzen für blaue Led
    '------------------------------------------------------------------------------
    ' Timer 0
    Config Timer0 = Timer , Prescale = 1024
    Enable Timer0
    On Timer0 Timer_null
    '---------------------------------------
    ' Timer 1
    Config Timer1 = Timer , Prescale = 64
    Enable Timer1
    On Timer1 Timer_eins
    '---------------------------------------
    ' Timer 2
    Config Timer2 = Timer , Prescale = 8
    Ocr2 = 6                                                    'nach 250 Zählschritten folgt der Interrupt
    Enable Timer2
    On Timer2 Timer_zwei
    
    Enable Interrupts
    
    Takt3 = 0
    Cls
    '------------------------- H A U P T P R O G R A M M --------------------------
    Do
    Gosub Anzeige
    
    Waitms 300
    Loop
    
    
    '------------------------------ D I S P L A Y - A N Z E I G E -----------------
    Anzeige:
    Cls
    Locate 1 , 1
    Lcd "Takt1: " ; Takt1
    Lcd "Takt2: " ; Takt2
    Return
    
    '--------------------------------- T I M E R - 0 -----------------------------
    Timer_null:
    Toggle Porta.0                                              ' Led Grün
    Takt1_temp = Takt1_temp + 1
    Return
    
    '--------------------------------- T I M E R - 1 ------------------------------
    Timer_eins:
    Toggle Porta.7                                              ' Led Blau
    Takt2_temp = Takt2_temp + 1
    Return
    
    '--------------------------------- T I M E R - 2 ------------------------------
    'Die Werte werden jede 1/2 Sekunde ausgelesen. Das Setup des Timers sieht so aus:
    '1MHz mit Prescaler/8 ergibt 125000 Timertakte pro Sekunde. Das Zählregister startet
    'mit 6, nach 250 Schritten erfolgt der Interrupt. Das ergibt 125000/250=500 Interrupts
    'pro Sekunde.Nach 250 Interrupts werden dann die Werte eingelesen und zurückgesetzt.
    'Die Frequenzkorrektur berücksichtigt auch die Takte, die schon gezählt wurden und
    'entfernt zusätzliche 3 Takte für Laden, Berechnen und Speichern des OCR2-Wertes.
    Timer_zwei:
    Ocr2 = Ocr2 + 9                                             'Frequenzkorrektur (256-6-3)
    If Takt3 < 250 Then
       Takt3 = Takt3 + 1
    Else
       Takt3 = 0
       Takt1 = Takt1_temp                                       'Zähler auslesen und resten
       Takt1_temp = 0
       Takt2 = Takt2_temp
       Takt2_temp = 0
    End If
    Return
    '------------------------------------------------------------------------------
    (ungetestet)

    Ich hoffe, das passt jetzt so in etwa. Ich bin mir nicht sicher, ob OCR2 wirklich mit 6 oder nur mit 5 starten muss.

    Gruß

    mic

    Atmel’s products are not intended, authorized, or warranted for use
    as components in applications intended to support or sustain life!

  5. #5

    .

    Zitat Zitat von radbruch
    Hallo

    Das war ja klar, dass es nicht auf Anhieb funktioniert

    Der Takt der grünen Led:
    1000000Hz/256/1024 oder etwa 3,81Hz

    Rote Led:
    1000000Hz/256/64 oder etwa 61Hz
    (Rot zu Grün wie 1024 zu 64 oder 61/16=3,8125)

    Der grobe Fehler ist sicher die Zeitmessung mit waitms. Dazu kommen noch die Funktionsaufrufe und die Ausgaben zum LCD. Wissenschaftlicher wäre die Verwendung eines zusätzlichen Timers zum Auslesen der Frequenzzähler:

    Code:
    ' Display an folgenden Ports
    ' Enable = Port C.4
    ' RS = Port C.5
    ' DB7 = Port C.7
    ' DB6 = Port C.6
    ' DB5 = Port C.3
    ' DB4 = Port C.2
    '
    ' Leds an folgenden Ports
    ' Grün an A.0
    '
    $regfile "m32def.dat"                                       'Definiert den Atmega als Atmega 32
    $crystal = 1000000                                          'Gibt die Quarzfrequenz an in Herz
    $hwstack = 32                                               'Default use 32 for the hardware stack
    $swstack = 10                                               'Default use 10 for the SW stack
    '-------------------------------------------------------------------------------
    ' Konfiguration fürs Display
    Config Lcd = 16 * 2                                         'definiert das LCD Display in Art und Größe
    Config Lcdpin = Pin , Db4 = Portc.2 , Db5 = Portc.3 , Db6 = Portc.6 , Db7 = Portc.7 , Rs = Portc.5 , E = Portc.4
    
    '------------------------------------------------------------------------------
    ' Variablen
    Dim Takt1 As Word
    Dim Takt2 As Word
    Dim Takt3 As Word
    Dim Takt1_temp As Word
    Dim Takt2_temp As Word
    '------------------------------------------------------------------------------
    
    Portb = &B00011110                                          ' Pull Up setzen für Pin B1
    Ddra = &B11111111                                           ' Pin A.7 als Ausgang setzen für blaue Led
    '------------------------------------------------------------------------------
    ' Timer 0
    Config Timer0 = Timer , Prescale = 1024
    Enable Timer0
    On Timer0 Timer_null
    '---------------------------------------
    ' Timer 1
    Config Timer1 = Timer , Prescale = 64
    Enable Timer1
    On Timer1 Timer_eins
    '---------------------------------------
    ' Timer 2
    Config Timer2 = Timer , Prescale = 8
    Ocr2 = 6                                                    'nach 250 Zählschritten folgt der Interrupt
    Enable Timer2
    On Timer2 Timer_zwei
    
    Enable Interrupts
    
    Takt3 = 0
    Cls
    '------------------------- H A U P T P R O G R A M M --------------------------
    Do
    Gosub Anzeige
    
    Waitms 300
    Loop
    
    
    '------------------------------ D I S P L A Y - A N Z E I G E -----------------
    Anzeige:
    Cls
    Locate 1 , 1
    Lcd "Takt1: " ; Takt1
    Lcd "Takt2: " ; Takt2
    Return
    
    '--------------------------------- T I M E R - 0 -----------------------------
    Timer_null:
    Toggle Porta.0                                              ' Led Grün
    Takt1_temp = Takt1_temp + 1
    Return
    
    '--------------------------------- T I M E R - 1 ------------------------------
    Timer_eins:
    Toggle Porta.7                                              ' Led Blau
    Takt2_temp = Takt2_temp + 1
    Return
    
    '--------------------------------- T I M E R - 2 ------------------------------
    'Die Werte werden jede 1/2 Sekunde ausgelesen. Das Setup des Timers sieht so aus:
    '1MHz mit Prescaler/8 ergibt 125000 Timertakte pro Sekunde. Das Zählregister startet
    'mit 6, nach 250 Schritten erfolgt der Interrupt. Das ergibt 125000/250=500 Interrupts
    'pro Sekunde.Nach 250 Interrupts werden dann die Werte eingelesen und zurückgesetzt.
    'Die Frequenzkorrektur berücksichtigt auch die Takte, die schon gezählt wurden und
    'entfernt zusätzliche 3 Takte für Laden, Berechnen und Speichern des OCR2-Wertes.
    Timer_zwei:
    Ocr2 = Ocr2 + 9                                             'Frequenzkorrektur (256-6-3)
    If Takt3 < 250 Then
       Takt3 = Takt3 + 1
    Else
       Takt3 = 0
       Takt1 = Takt1_temp                                       'Zähler auslesen und resten
       Takt1_temp = 0
       Takt2 = Takt2_temp
       Takt2_temp = 0
    End If
    Return
    '------------------------------------------------------------------------------
    (ungetestet)

    Ich hoffe, das passt jetzt so in etwa. Ich bin mir nicht sicher, ob OCR2 wirklich mit 6 oder nur mit 5 starten muss.

    Gruß

    mic
    Ich glaube da fehlt etwas , kann nicht erkennen wozu Takt3 da ist ?
    Takt3 wird in Zeile 51 auf Null gesetzt , dann noch einmal in den Zeilen 90 bis 93 abgefragt, aber dann nicht mehr benutzt ?????

    Außerdem zeigt mir das Display unter Takt1: den Wert 2
    und unter Takt2: den Wert0 an


    Gruß nase

  6. #6
    Moderator Robotik Visionär Avatar von radbruch
    Registriert seit
    27.12.2006
    Ort
    Stuttgart
    Alter
    54
    Beiträge
    5.782
    Blog-Einträge
    8
    Ojeojeoje. Es ist eben immer schlecht, wenn man es nicht selbst testen kann. Beim Timer2 sollte man schon das Zählregister TCNT2 manipulieren, OCR2 ist hier völlig falsch.

    Takt3 zählt die Aufrufe der Interruptroutine des Timer2. Solange Takt3 kleiner als 250 ist wird es erhöht. Bei 250 sollte eine halbe Sekunde vergangen sein. Es werden dann die Zählerstände von Taktx_temp nach Taktx kopiert und die Taktx_temp gelöscht. Takt3 wird wieder auf null gesetzt und das Spiel beginnt von vorne.

    Code:
    If Takt3 < 250 Then                                         'solange Takt3 kleiner 250
       Takt3 = Takt3 + 1                                        'Takt3 erhöhen
    Else                                                        'die 1/2 Sek. ist vorbei
       Takt3 = 0                                                'Takt3 reseten
       Takt1 = Takt1_temp                                       'Zähler auslesen
       Takt1_temp = 0                                           'und reseten
       Takt2 = Takt2_temp
       Takt2_temp = 0
    End If
    Gleichzeitig werden ca. alle 300ms die aktuellen Werte von Takt1 und 2 am LCD ausgegeben. Der Code mit dem richtigen TCNT2-Register sieht dann so aus:

    Code:
                                         ' Display an folgenden Ports
    ' Enable = Port C.4
    ' RS = Port C.5
    ' DB7 = Port C.7
    ' DB6 = Port C.6
    ' DB5 = Port C.3
    ' DB4 = Port C.2
    '
    ' Leds an folgenden Ports
    ' Grün an A.0
    '
    $regfile "m32def.dat"                                       'Definiert den Atmega als Atmega 32
    $crystal = 1000000                                          'Gibt die Quarzfrequenz an in Herz
    $hwstack = 32                                               'Default use 32 for the hardware stack
    $swstack = 10                                               'Default use 10 for the SW stack
    '-------------------------------------------------------------------------------
    ' Konfiguration fürs Display
    Config Lcd = 16 * 2                                         'definiert das LCD Display in Art und Größe
    Config Lcdpin = Pin , Db4 = Portc.2 , Db5 = Portc.3 , Db6 = Portc.6 , Db7 = Portc.7 , Rs = Portc.5 , E = Portc.4
    
    '------------------------------------------------------------------------------
    ' Variablen
    Dim Takt1 As Word
    Dim Takt2 As Word
    Dim Takt3 As Word
    Dim Takt1_temp As Word
    Dim Takt2_temp As Word
    '------------------------------------------------------------------------------
    
    Portb = &B00011110                                          ' Pull Up setzen für Pin B1
    Ddra = &B11111111                                           ' Pin A.7 als Ausgang setzen für blaue Led
    '------------------------------------------------------------------------------
    ' Timer 0
    Config Timer0 = Timer , Prescale = 1024
    Enable Timer0
    On Timer0 Timer_null
    '---------------------------------------
    ' Timer 1
    Config Timer1 = Timer , Prescale = 64
    Enable Timer1
    On Timer1 Timer_eins
    '---------------------------------------
    ' Timer 2
    Config Timer2 = Timer , Prescale = 8
    Tcnt2 = 6                                                   'nach 250 Zählschritten folgt der Interrupt
    Enable Timer2
    On Timer2 Timer_zwei
    
    Enable Interrupts
    
    Takt3 = 0
    Cls
    '------------------------- H A U P T P R O G R A M M --------------------------
    Do
    Gosub Anzeige
    
    Waitms 300
    Loop
    
    
    '------------------------------ D I S P L A Y - A N Z E I G E -----------------
    Anzeige:
    Cls
    Locate 1 , 1
    Lcd "Takt1: " ; Takt1
    Lcd "Takt2: " ; Takt2
    Return
    
    '--------------------------------- T I M E R - 0 -----------------------------
    Timer_null:
    Toggle Porta.0                                              ' Led Grün
    Takt1_temp = Takt1_temp + 1
    Return
    
    '--------------------------------- T I M E R - 1 ------------------------------
    Timer_eins:
    Toggle Porta.7                                              ' Led Blau
    Takt2_temp = Takt2_temp + 1
    Return
    
    '--------------------------------- T I M E R - 2 ------------------------------
    'Die Werte werden jede 1/2 Sekunde ausgelesen. Das Setup des Timers sieht so aus:
    '1MHz mit Prescaler/8 ergibt 125000 Timertakte pro Sekunde. Das Zählregister startet
    'mit 6, nach 250 Schritten erfolgt der Interrupt. Das ergibt 125000/250=500 Interrupts
    'pro Sekunde.Nach 250 Interrupts werden dann die Werte eingelesen und zurückgesetzt.
    'Die Frequenzkorrektur berücksichtigt auch die Takte, die schon gezählt wurden und
    'entfernt zusätzliche 3 Takte für Laden, Berechnen und Speichern des TCNT2-Wertes.
    Timer_zwei:
    Tcnt2 = Tcnt2 + 9                                           'Frequenzkorrektur (256-6-3)
    If Takt3 < 250 Then                                         'solange Takt3 kleiner 250
       Takt3 = Takt3 + 1                                        'Takt3 erhöhen
    Else                                                        'die 1/2 Sek. vorbei
       Takt3 = 0                                                'Takt3 reseten
       Takt1 = Takt1_temp                                       'Zähler auslesen
       Takt1_temp = 0                                           'und reseten
       Takt2 = Takt2_temp
       Takt2_temp = 0
    End If
    Return
    '------------------------------------------------------------------------------
    Zum Debuggen könnte man im else-Zweig in der Timer2-ISR noch eine Led togglen. Die sollte dann mit 1 Hz blinken.

    Hast du inzwischen die Takte1 und 2 mal nachgemessen? Viele Multimeter können auch Frequenzen messen.

    Gruß

    mic

    Atmel’s products are not intended, authorized, or warranted for use
    as components in applications intended to support or sustain life!

  7. #7
    Ok, hab im Zweig in des Timer2-ISR noch eine Rote Led angeschlossen.

    Hab immer noch eine Anzeige von Takt1=2 und Takt2=0
    [/img]

    Signal1a
    Blaue Led hat 0,12 Hz ( obere Signal)
    Grüne Led hat 1,93 Hz ( untere Signal)

    Signal2a
    Rote Led hat 1,05 Hz
    Miniaturansichten angehängter Grafiken Miniaturansichten angehängter Grafiken signal1a.jpeg   signal2a.jpeg   img_0033_cr.jpg  

  8. #8
    Moderator Robotik Visionär Avatar von radbruch
    Registriert seit
    27.12.2006
    Ort
    Stuttgart
    Alter
    54
    Beiträge
    5.782
    Blog-Einträge
    8
    Hallo

    Timer 1 ist doch ein 16Bit-Timer. Deshalb muss man auch hier das Zählregister in der ISR manipulieren um ein messbares Ergebniss zu erhalten:

    Code:
                                         ' Display an folgenden Ports
    ' Enable = Port C.4
    ' RS = Port C.5
    ' DB7 = Port C.7
    ' DB6 = Port C.6
    ' DB5 = Port C.3
    ' DB4 = Port C.2
    '
    ' Leds an folgenden Ports
    ' Grün an A.0
    '
    $regfile "m32def.dat"                                       'Definiert den Atmega als Atmega 32
    $crystal = 1000000                                          'Gibt die Quarzfrequenz an in Herz
    $hwstack = 32                                               'Default use 32 for the hardware stack
    $swstack = 10                                               'Default use 10 for the SW stack
    '-------------------------------------------------------------------------------
    ' Konfiguration fürs Display
    Config Lcd = 16 * 2                                         'definiert das LCD Display in Art und Größe
    Config Lcdpin = Pin , Db4 = Portc.2 , Db5 = Portc.3 , Db6 = Portc.6 , Db7 = Portc.7 , Rs = Portc.5 , E = Portc.4
    
    '------------------------------------------------------------------------------
    ' Variablen
    Dim Takt1 As Word
    Dim Takt2 As Word
    Dim Takt3 As Word
    Dim Takt1_temp As Word
    Dim Takt2_temp As Word
    '------------------------------------------------------------------------------
    
    Portb = &B00011110                                          ' Pull Up setzen für Pin B1
    Ddra = &B11111111                                           ' Pin A.7 als Ausgang setzen für blaue Led
    '------------------------------------------------------------------------------
    ' Timer 0
    Config Timer0 = Timer , Prescale = 1024
    Enable Timer0
    On Timer0 Timer_null
    '---------------------------------------
    ' Timer 1
    Config Timer1 = Timer , Prescale = 64
    Tcnt1 = 65280                                               '16Bit! 65536-256
    Enable Timer1
    On Timer1 Timer_eins
    '---------------------------------------
    ' Timer 2
    Config Timer2 = Timer , Prescale = 8
    Tcnt2 = 6                                                   'nach 250 Zählschritten folgt der Interrupt
    Enable Timer2
    On Timer2 Timer_zwei
    
    Enable Interrupts
    
    Takt3 = 0
    Cls
    '------------------------- H A U P T P R O G R A M M --------------------------
    Do
    Gosub Anzeige
    
    Waitms 300
    Loop
    
    
    '------------------------------ D I S P L A Y - A N Z E I G E -----------------
    Anzeige:
    Cls
    Locate 1 , 1
    Lcd "Takt1: " ; Takt1
    Lcd "Takt2: " ; Takt2
    Return
    
    '--------------------------------- T I M E R - 0 -----------------------------
    Timer_null:
    Toggle Porta.0                                              ' Led Grün
    Takt1_temp = Takt1_temp + 1
    Return
    
    '--------------------------------- T I M E R - 1 ------------------------------
    Timer_eins:
    Tcnt1 = Tcnt1+65283                                    '16Bit! 65536-256+3
    Toggle Porta.7                                              ' Led Blau
    Takt2_temp = Takt2_temp + 1
    Return
    
    '--------------------------------- T I M E R - 2 ------------------------------
    'Die Werte werden jede 1/2 Sekunde ausgelesen. Das Setup des Timers sieht so aus:
    '1MHz mit Prescaler/8 ergibt 125000 Timertakte pro Sekunde. Das Zählregister startet
    'mit 6, nach 250 Schritten erfolgt der Interrupt. Das ergibt 125000/250=500 Interrupts
    'pro Sekunde.Nach 250 Interrupts werden dann die Werte eingelesen und zurückgesetzt.
    'Die Frequenzkorrektur berücksichtigt auch die Takte, die schon gezählt wurden und
    'entfernt zusätzliche 3 Takte für Laden, Berechnen und Speichern des TCNT2-Wertes.
    Timer_zwei:
    Tcnt2 = Tcnt2 + 9                                           'Frequenzkorrektur (256-6-3)
    If Takt3 < 250 Then                                         'solange Takt3 kleiner 250
       Takt3 = Takt3 + 1                                        'Takt3 erhöhen
    Else                                                        'die 1/2 Sek. vorbei
       Takt3 = 0                                                'Takt3 reseten
       Takt1 = Takt1_temp                                       'Zähler auslesen
       Takt1_temp = 0                                           'und reseten
       Takt2 = Takt2_temp
       Takt2_temp = 0
    End If
    Return
    '------------------------------------------------------------------------------
    Meine Frequenzberechnungen ergeben die Anzahl der ISR-Aufrufe. Die effektive Frequenz an der Led muss man natürlich halbieren.... (nobody is perfect ;)


    Mein Testprogramm für den mit 8MHz getakteten RP6:
    Code:
    $regfile "m32def.dat"                                       'Definiert den Atmega als Atmega 32
    $crystal = 8000000                                          'Gibt die Quarzfrequenz an in Herz
    $hwstack = 32                                               'Default use 32 for the hardware stack
    $swstack = 10                                               'Default use 10 for the SW stack
    $baud = 38400
    '-------------------------------------------------------------------------------
    'Led1 PC4
    'Led2 PC5
    'LED3 PC6
    '------------------------------------------------------------------------------
    ' Variablen
    Dim Takt1 As Word
    Dim Takt2 As Word
    Dim Takt3 As Word
    Dim Takt1_temp As Word
    Dim Takt2_temp As Word
    '------------------------------------------------------------------------------
    
    Ddrc = &B01110000                                           ' PC4-6 sind die Leds
    '------------------------------------------------------------------------------
    ' Timer 0
    Config Timer0 = Timer , Prescale = 1024
    Enable Timer0
    On Timer0 Timer_null
    '---------------------------------------
    ' Timer 1
    Config Timer1 = Timer , Prescale = 64
    Tcnt1 = 65280                                               '16Bit! 65536-256
    Enable Timer1
    On Timer1 Timer_eins
    '---------------------------------------
    ' Timer 2
    Config Timer2 = Timer , Prescale = 64         'RP6 mit 8MHz
    Tcnt2 = 6                                                   'nach 250 Zählschritten folgt der Interrupt
    Enable Timer2
    On Timer2 Timer_zwei
    
    Enable Interrupts
    
    Takt3 = 0
    Cls
    '------------------------- H A U P T P R O G R A M M --------------------------
    Do
    Gosub Anzeige
    
    Waitms 300
    Loop
    
    
    '------------------------------ D I S P L A Y - A N Z E I G E -----------------
    Anzeige:
    Print "Takt1: " ; Takt1
    Print "Takt2: " ; Takt2
    Print
    Return
    
    '--------------------------------- T I M E R - 0 -----------------------------
    Timer_null:
    Toggle Portc.4                                              ' Led 1
    Takt1_temp = Takt1_temp + 1
    Return
    
    '--------------------------------- T I M E R - 1 ------------------------------
    Timer_eins:
    Tcnt1 = Tcnt1+65283                                    '16Bit! 65536-256+3
    Toggle Portc.5                                              ' Led 2
    Takt2_temp = Takt2_temp + 1
    Return
    
    '--------------------------------- T I M E R - 2 ------------------------------
    'Die Werte werden jede 1/2 Sekunde ausgelesen. Das Setup des Timers sieht so aus:
    '1MHz mit Prescaler/8 ergibt 125000 Timertakte pro Sekunde. Das Zählregister startet
    'mit 6, nach 250 Schritten erfolgt der Interrupt. Das ergibt 125000/250=500 Interrupts
    'pro Sekunde.Nach 250 Interrupts werden dann die Werte eingelesen und zurückgesetzt.
    'Die Frequenzkorrektur berücksichtigt auch die Takte, die schon gezählt wurden und
    'entfernt zusätzliche 3 Takte für Laden, Berechnen und Speichern des TCNT2-Wertes.
    Timer_zwei:
    Tcnt2 = Tcnt2 + 9                                           'Frequenzkorrektur (256-6-3)
    If Takt3 < 250 Then                                         'solange Takt3 kleiner 250
       Takt3 = Takt3 + 1                                        'Takt3 erhöhen
    Else                                                        'die 1/2 Sek. vorbei
       Toggle Portc.6                                           ' Led 3
       Takt3 = 0                                                'Takt3 reseten
       Takt1 = Takt1_temp                                       'Zähler auslesen
       Takt1_temp = 0                                           'und reseten
       Takt2 = Takt2_temp
       Takt2_temp = 0
    End If
    Return
    '------------------------------------------------------------------------------
    Die Ausgabe:
    Code:
    Takt1: 15
    Takt2: 244
    
    Takt1: 15
    Takt2: 244
    
    Takt1: 15
    Takt2: 245
    
    Takt1: 15
    Takt2: 245
    Gruß

    mic

    Atmel’s products are not intended, authorized, or warranted for use
    as components in applications intended to support or sustain life!

  9. #9
    Benutzer Stammmitglied
    Registriert seit
    18.03.2007
    Ort
    NRW
    Beiträge
    62
    Hab dein Testprogramm getestet, bzw, versucht zu testen , bekam beim Comilieren gleich folgende Fehlermeldungen:

    Zeile 40 Assignment error TCNT 1:0
    Zeile 79 Invalid Datatype [0007]
    Zeile 79 Interrupt needs return

    Um nochmal zum eigentlichen Thema zurück zu kommen, es geht mir nicht um die Genauigkeit der Anzeige, zumindest jetzt noch nicht , evtl wenn ich mal weiter bin.
    Es geht mir in der Hauptsache darum eine Stabile Anzeige auf dem Display zu erhalten.

    gruß Nase

  10. #10
    Moderator Robotik Visionär Avatar von radbruch
    Registriert seit
    27.12.2006
    Ort
    Stuttgart
    Alter
    54
    Beiträge
    5.782
    Blog-Einträge
    8
    Hallo

    Seltsam, mein Bascom (Demo 1.11.9.8) schluckt das anstandslos. TCNT2 funktioniert bei dir ja auch. Hier eine Variante in der TCNT1 durch TIMER1 ersetzt ist:

    Code:
    ' Display an folgenden Ports
    ' Enable = Port C.4
    ' RS = Port C.5
    ' DB7 = Port C.7
    ' DB6 = Port C.6
    ' DB5 = Port C.3
    ' DB4 = Port C.2
    '
    ' Leds an folgenden Ports
    ' Grün an A.0
    '
    $regfile "m32def.dat"                                       'Definiert den Atmega als Atmega 32
    $crystal = 1000000                                          'Gibt die Quarzfrequenz an in Herz
    $hwstack = 32                                               'Default use 32 for the hardware stack
    $swstack = 10                                               'Default use 10 for the SW stack
    '-------------------------------------------------------------------------------
    ' Konfiguration fürs Display
    Config Lcd = 16 * 2                                         'definiert das LCD Display in Art und Größe
    Config Lcdpin = Pin , Db4 = Portc.2 , Db5 = Portc.3 , Db6 = Portc.6 , Db7 = Portc.7 , Rs = Portc.5 , E = Portc.4
    
    '------------------------------------------------------------------------------
    ' Variablen
    Dim Takt1 As Word
    Dim Takt2 As Word
    Dim Takt3 As Word
    Dim Takt1_temp As Word
    Dim Takt2_temp As Word
    '------------------------------------------------------------------------------
    
    Portb = &B00011110                                          ' Pull Up setzen für Pin B1
    Ddra = &B11111111                                           ' Pin A.7 als Ausgang setzen für blaue Led
    '------------------------------------------------------------------------------
    ' Timer 0
    Config Timer0 = Timer , Prescale = 1024
    Enable Timer0
    On Timer0 Timer_null
    '---------------------------------------
    ' Timer 1
    Config Timer1 = Timer , Prescale = 64
    Timer1 = 65280                                             '16Bit! 65536-256
    Enable Timer1
    On Timer1 Timer_eins
    '---------------------------------------
    ' Timer 2
    Config Timer2 = Timer , Prescale = 8
    Tcnt2 = 6                                                   'nach 250 Zählschritten folgt der Interrupt
    Enable Timer2
    On Timer2 Timer_zwei
    
    Enable Interrupts
    
    Takt3 = 0
    Cls
    '------------------------- H A U P T P R O G R A M M --------------------------
    Do
    Gosub Anzeige
    
    Waitms 300
    Loop
    
    
    '------------------------------ D I S P L A Y - A N Z E I G E -----------------
    Anzeige:
    Cls
    Locate 1 , 1
    Lcd "Takt1:" ; Takt1
    Lcd "Takt2:" ; Takt2
    Return
    
    '--------------------------------- T I M E R - 0 -----------------------------
    Timer_null:
    Toggle Porta.0                                              ' Led Grün
    Takt1_temp = Takt1_temp + 1
    Return
    
    '--------------------------------- T I M E R - 1 ------------------------------
    Timer_eins:
    Timer1 = Timer1 + 65283                                     '16Bit! 65536-256+3
    Toggle Porta.7                                              ' Led Blau
    Takt2_temp = Takt2_temp + 1
    Return
    
    '--------------------------------- T I M E R - 2 ------------------------------
    'Die Werte werden jede 1/2 Sekunde ausgelesen. Das Setup des Timers sieht so aus:
    '1MHz mit Prescaler/8 ergibt 125000 Timertakte pro Sekunde. Das Zählregister startet
    'mit 6, nach 250 Schritten erfolgt der Interrupt. Das ergibt 125000/250=500 Interrupts
    'pro Sekunde.Nach 250 Interrupts werden dann die Werte eingelesen und zurückgesetzt.
    'Die Frequenzkorrektur berücksichtigt auch die Takte, die schon gezählt wurden und
    'entfernt zusätzliche 3 Takte für Laden, Berechnen und Speichern des TCNT2-Wertes.
    Timer_zwei:
    Tcnt2 = Tcnt2 + 9                                           'Frequenzkorrektur (256-6-3)
    If Takt3 < 250 Then                                         'solange Takt3 kleiner 250
       Takt3 = Takt3 + 1                                        'Takt3 erhöhen
    Else                                                        'die 1/2 Sek. vorbei
       Takt3 = 0                                                'Takt3 reseten
       Takt1 = Takt1_temp                                       'Zähler auslesen
       Takt1_temp = 0                                           'und reseten
       Takt2 = Takt2_temp
       Takt2_temp = 0
    End If
    Return
    '------------------------------------------------------------------------------
    Ich bin halt leider nicht so sehr der Bascom-Profi :(

    Gruß

    mic

    Atmel’s products are not intended, authorized, or warranted for use
    as components in applications intended to support or sustain life!

Seite 1 von 2 12 LetzteLetzte

Berechtigungen

  • Neue Themen erstellen: Nein
  • Themen beantworten: Nein
  • Anhänge hochladen: Nein
  • Beiträge bearbeiten: Nein
  •