Hallo!
Ich habe auf einem Mega16 mit dem RN-Control Board unter Bascom eine Drehzahlmessung (und Drehgradientenmessung) programmiert (s.u.). Das Programm funktioniert auch soweit. Das einzige Problem ist, dass wenn man den Reset-Taster betätigt, während eine Frequenz am Interrupt anliegt, viel zu große Werte raus kommen, und zwar immer die gleichen, bei der jeweiligen Frequenz. Das geschieht nicht, wenn man Reset betätigt während keine Frequenz anliegt. Nach dem Starten des Programms kann dann die Frequenz verändert werden, was auch richtig angezeigt wird. Teilweise tritt dieser Fehler auch einfach so auf, bei höheren Frequenzen. Und dann kommt man nicht mehr auf einen vernünftigen Wert zurück, ohne die Ferquenz auf Null zu fahren und dann Reset zu drücken.
Sollte der Controller bei einem Reset das Programm nicht von ganz vorne starten?? Wenn das so wäre müsste auch bei anliegender Frequenz ein richtiger Wert angezeigt werden, oder??
Hat jemand ne Idee, wo der Fehler liegen könnte?


Hier mein Programm:
Code:
'###################################################
'LVA_Drehzahlmessung.BAS

'Diese Programm ermittelt über die Signale einer Lichtschranke
'die Drehzahl am Motorenprüfstand 1 des LVA an der Fachhochschule Köln.
'Die ermittelte Drehzahl und der Drehzahlgradient werden an D/A-Wandler gegeben,
'die eine analoge Spannung ausgeben, für die Weiterverarbeitung in der folgenden
'Regelungselektronik.

'Autor: Christian Hungenberg
'#######################################################



$regfile = "m32def.dat"
$framesize = 32
$swstack = 32
$hwstack = 32
$crystal = 16000000                                         'Angabe der Quarzfrequenz
$baud = 9600


Config Int0 = Falling                                       'Der Interrupt wird bei fallendem Flankensignal aktiviert
Config Timer1 = Timer , Prescale = 256                      'Timer 1 (16-bit Timer)


Config Spi = Soft , Din = Pinc.5 , Dout = Portc.1 , Ss = None , Clock = Portc.0       'Konfiguration der Software SPI
Config Portc.2 = Output                                     'Ausgang für CS1
Config Portc.3 = Output                                     'Ausgang für CS2

   Portc.2 = 1                                              'CS1 auf High
   Portc.3 = 1                                              'CS2 auf High

Dim Pointer As Byte                                         'zeigt dei aktuelle Speicherstelle für die Impulse an
Dim Array(24) As Byte                                       '24 Speicherstellen für Impulse
Dim Impulszaehler As Long                                   'Zaehlt die Impulse der Lichtschranke waehrend 10ms (dies ist die Timerzeit)
Dim Impulse As Long                                         'in dieser Variablen werden die gezaehlten Impulse für die Berechnung gespeichert
Dim Drehzahl_alt As Single                                  'zur Berechnung des Gradienten speichtert diese Variable den vorangegangenen Drehzahlwert

Dim Drehzahl_neu As Single                                  'Drehzahl in 1/min, als Dezimalwert
Dim Umdpm1 As Byte
Dim Umdpm2 As Byte
Dim Umdrehungenprominute As Word At Umdpm1 Overlay          'enthaelt den aktuellen Drehzahlwert in 1/min, als ganzzaligen Wert fuer DAC

Dim Drehgradient As Single                                  'für die Berechnung des Gradienten als Dezimalwert
Dim Grad1 As Byte
Dim Grad2 As Byte
Dim Gradient As Word At Grad1 Overlay                       'enthaelt den Drehzahlgradienten in U/s2, als gangzzahligen Wert fuer DAC
Dim I As Integer
Dim Syncro As Byte                                          'synchronisiert die Ausgabe mit der Berechnung


Pointer = 1                                                 'Pointer zeigt auf die erste Speicherstelle
Impulszaehler = 0
Impulse = 0
Drehzahl_neu = 0
Syncro = 0


On Int0 Irq0                                                'bei fallenden Flanken wird der Interrupt ausgeloest und ruft Irq0 auf
Enable Int0

On Timer1 Timer_irq                                         'beim Ueberlaufen des Timers wird die Routine Timer_irq aufgerufen
Enable Timer1

Enable Interrupts



Do
   If Syncro = 1 Then
      Drehzahl_neu = Impulse * 2.5                          'Berechnung der Drehzahl: Imp/(BZ*100)*60    Imp=1; BZ=0,24
      Drehgradient = Drehzahl_neu - Drehzahl_alt            'Berechnung der Drehzahländerung für Gradienten
      Drehgradient = Drehgradient * 10                      'Gradient = Drehzahländerung * Kerwert der Zeiteinheit (1/0,01s)
      Drehzahl_alt = Drehzahl_neu                           'Speichern der neuen Drehzahl als alte fuer naechste Berechnung der Drehzahlaenderung
      Drehzahl_neu = Drehzahl_neu * 0.4096                  'Umrechnung von Drehzahl 0...10.000 auf Binaerzahl 0...4096  (10.000/4096)^-1
      Umdrehungenprominute = Round(drehzahl_neu)

         Portc.2 = 0                                        'CS1 auf LOW
            Spiinit
            Spiout Umdpm2 , 1                               ' Bit 15 - BIT 8
            Spiout Umdpm1 , 1                               ' Bit 7 - BIT 0
         Portc.2 = 1                                        'CS1 auf High

   If Drehgradient > 0 Then
      Drehgradient = Drehgradient * 2.048                   'Umrechnung von Drehzahlgradient 0...2.000 auf Binärzahl 0...4095 (2.000/4096)^-1
      Gradient = Round(drehgradient)
      Else
      Gradient = 0
      End If

         Portc.3 = 0                                        'CS1 auf LOW
            Spiinit
            Spiout Grad2 , 1                                ' Bit 15 - BIT 8
            Spiout Grad1 , 1                                ' Bit 7 - BIT 0
        Portc.3 = 1                                         'CS1 auf High
    'Print Impulse
    'Print Impulszaehler
    'Print Drehzahl_neu

   Syncro = 0
   End If

Loop

End



Irq0:                                                       'Pro Impuls (Markierung auf Scheibe) ein Aufruf
   Incr Impulszaehler
Return




Timer_irq:                                                  'wird beim Ablauf der Berechnungszeit aufgerufen
   Impulse = Impulse + Impulszaehler                        'addiert die Impulse der neuen 10ms
   Impulse = Impulse - Array(pointer)                       'subtrahiert die Impulse der 10ms-Zeiteiheit vor 240ms
   Array(pointer) = Impulszaehler                           'speichert die Impulse der aktuellen 10ms-Zeiteinheit in den aktuellen Speicherplatz
   Impulszaehler = 0                                        'resetet den Impulszaehler

   If Pointer = 24 Then                                     'hier wird der Pointer um den Wert "1" hoch gesetzt, nach 24 fängt er von vorne an
      Pointer = 1
      Else
      Incr Pointer
   End If

   Timer1 = 64911                                           'laed den timer vor, dies definiert die Timerzeit
   Incr Syncro                                              'fuer die Sychronisierung der Ausgabe mit der Berechnung
Return