www.mikrocontroller.net

Forum: Mikrocontroller und Digitale Elektronik HW-Stack wird in Subroutine voll bis Prog. abstürzt


Autor: Axel Krüger (axel)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
huhu : )

Ich komme nicht weiter : ((


Ich habe 4 ineinander verschachtelte Subroutinen.

In der 4. Subroutine inkrementiere bzw. dekrementiere ich eine Variable 
(welche ich ganz am Anfang normal deklariert habe) mittels 2 Taster.

Als ich den HW-Stack auf 32 hatte, konnte ich ca. 15 mal einen Taster 
betätigen (egal welchen), bis das Programm abstürzt.

Dann habe ich den HW-Stack auf 64 erhöht - jetzt kann ich ca. 30 x eine 
Taste drücken, bis das Programm abstürzt...


Habt ihr eine Idee, wie ich das umgehen kann, dass er den HW Stack damit 
vollstopft?

Achso, ich habe schon versucht irgendwie mit byval und byref zum 
erstenmal herumzuexperimentieren, aber da seh ich nicht durch.. (( Zumal 
"mein" Bascom garnicht "byref" kennt, wenn ich byval damit ersetze....

gruss
Axel

Autor: pfft. (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Der Fehler ist in Zeile 42. Mach die weg, und gut ist.

Autor: Klaus (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Der Fehler ist in Zeile 42!

Autor: spess53 (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Hi

Einhellige Meinung. Schließe mich an.

Erzähl erstmal worum es geht, Cotroller etc. Programm wäre durchaus 
hilfreich.

MfG Spess

Autor: Nez (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Komisch. Der Fehler ist schon wieder in Zeile 42. Ob das Zufall ist?

Autor: Helmut Lenzen (helmi1)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Man sollte mal einen Editor schreiben der grundsaetzlich Zeile 42 
auslaesst. So koennte man sich manchen Fehler ersparen.

Autor: Peter Dannegger (peda)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Axel Krüger schrieb:
> Ich habe 4 ineinander verschachtelte Subroutinen.

Subroutinen dürfen sich nicht gegenseitig aufrufen (unendliche 
Rekursion). Du mußt immer mit Return zum Aufrufer zurückkehren.


Peter

Autor: Axel Krüger (axel)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Hallo! Ganz am Ende ist die Routine:
$regfile = "m8def.dat"                                      'ATMEGA8-Deklarationen

$crystal = 8233333
$baud = 9600


'############################################################################################################

'START Variablen----------------------------------------------------------------
Dim C1 As Word
Dim C2 As Word

Dim C4 As Word
Dim C5 As Word

Dim C3 As Word

Dim Tastenfeld As Word
Dim Tastenfeld_zaehler As Byte
Dim Tastenwert_ug As Word
Dim Tastenwert_og As Word







Dim Ubatterie As Long
Dim Ubatterie_formatiert As Long
Dim Ubatterie_str2 As String * 5

Dim Ubatterie_aktueller_wert As Word



Dim Idc1 As Long
Dim X As Word


Dim Watt As Long

Dim L As Word
Dim Var1 As Single
Dim Var2 As Word
Dim Var3 As Word

Dim Var11 As String * 5
Dim Var12 As String * 5


'ENDE Variablen----------------------------------------------------------------

'############################################################################################################

'Config Timer0 = Timer , Prescale = 64                       'Timerperiode = 1Sekunde
'On Timer0 Overflow_timer0
'Enable Timer0
'Enable Interrupts

Config Portb = Output
Config Portc = Input
Config Portd = Output

Config Adc = Single , Prescaler = 128 , Reference = Avcc
'Set Sfior.adhsm

Config Lcdpin = Pin , Db4 = Portd.5 , Db5 = Portd.6 , Db6 = Portd.7 , Db7 = Portb.0 , E = Portb.7 , Rs = Portb.6
Config Lcd = 20 * 4
Waitms 2000
Initlcd

Declare Sub Lcd_out
Declare Sub Tastenabfrage
Declare Sub Hauptmenue
Declare Sub Konfig_sensoren
Declare Sub Konfig_dcsensoren
Declare Sub Maxampere



Declare Sub Tastenabfrage_schleife
Declare Sub Tastenabfrage_schleife2


Call Lcd_out

Start Adc

'############################################################################################################


'START DO-LOOP Hauptschleife----------------------------------------------------
Do

Waitms 300                                                  'Wartezeit; spдter durch Timer ersetzen

'START Batterie Spannung / Versorgungsspannung----------------------------------
C1 = Getadc(0)                                              '"Get" Versorgungsspannung
'---------------------------------------------------------
'Routine welche das stдndige Schwanken der Werte verhindert

'Dieses dient dazu, dass Flackern der "letzten" LED, im Falle das die Drehzahl zwischen 2 LED hin und
'her "pendelt", zu unterbinden. Dazu dient variable C2 als Ausgabevariable. C1 ist der eigentliche,
'berechnete Wert. Wenn C1 mehr als eine LED gegenьber C2 zunimmt, dann wird C2 C1- 1 angeglichen.
'Ist C2 = C1 oder um eins niedriger, dann behдlt C2 seinen Wert. Im Falle dass C1 niedriger ist,
'wird C2 C1 gleichgesetzt. Sollte dann sofort C1 um eins grцЯer werden, wird dieses nicht einbezogen.

If C2 < C1 Then
   C3 = C1 - C2
   If C3 > 1 Then                                           'Bei Differenz grцЯer eins C2 = C1 - 1
      C2 = C1 - 1
   End If

   Goto Weiter
End If

If C2 > C1 Then
   C2 = C1
End If

Weiter:

Ubatterie = C2
'---------------------------------------------------------


Ubatterie = Ubatterie * 1500                                'Dreisatz => 1500 (/10 mV) * Getadc(0) / 512 = UBatterie in mV/10
Ubatterie = Ubatterie / 512                                 ' = UBatterie
Var1 = Ubatterie
Var2 = Round(var1)                                          'auf einer Stelle nach dem Komma runden
Var11 = Str(var2)
Ubatterie_str2 = Mid(var11 , 1 , 2)
Ubatterie_str2 = Ubatterie_str2 + ","
Ubatterie_str2 = Ubatterie_str2 + Mid(var11 , 3 , 2)


Locate 1 , 13
Lcd Ubatterie_str2 ; "V "
'-------------------------------------------------------------------------------




'START DC1 Sensor---------------------------------------------------------------
C4 = Getadc(1)
'---------------------------------------------------------
'Routine welche das stдndige Schwanken der Werte verhindert

'Dieses dient dazu, dass Flackern der "letzten" LED, im Falle das die Drehzahl zwischen 2 LED hin und
'her "pendelt", zu unterbinden. Dazu dient variable C2 als Ausgabevariable. C1 ist der eigentliche,
'berechnete Wert. Wenn C1 mehr als eine LED gegenьber C2 zunimmt, dann wird C2 C1- 1 angeglichen.
'Ist C2 = C1 oder um eins niedriger, dann behдlt C2 seinen Wert. Im Falle dass C1 niedriger ist,
'wird C2 C1 gleichgesetzt. Sollte dann sofort C1 um eins grцЯer werden, wird dieses nicht einbezogen.

If C5 < C4 Then
   C3 = C4 - C5
   If C3 > 1 Then                                           'Bei Differenz grцЯer eins C2 = C1 - 1
      C5 = C4 - 1
   End If

   Goto Weiter2
End If

If C5 > C4 Then
   C5 = C4
End If

Weiter2:

Idc1 = C5
'---------------------------------------------------------


Locate 2 , 13
Lcd Idc1
'-------------------------------------------------------------------------------





Locate 4 , 1
Lcd Tastenfeld ; " counts  "



'Tastenfeldabfrage fьr Aufruf Hauptmenue----------------------------------------
Tastenwert_ug = 199                                         'Tastenwert muss ca. bei 205 liegen
Tastenwert_og = 211
Call Tastenabfrage                                          'Aufruf Sub_Tastenabfrage

'3mal abfragen zur Fehlervermeidung
If Tastenfeld_zaehler = 3 Then                              'nach 3-maliger Abfrage Hauptmenue anrufen
   Tastenfeld_zaehler = 0
   Call Hauptmenue
   Call Lcd_out                                             'wenn do-loop beendet wird dann Ausgangsbildschirm laden
End If
'-------------------------------------------------------------------------------


Loop
End

'############################################################################################################

'Ausgangsbildschirm-------------------------------------------------------------
Sub Lcd_out

   Cls

   Locate 1 , 1
   Lcd "U-Batterie: "

   Locate 2 , 1
   Lcd "I-DC1: "

   Locate 3 , 1
   Lcd "Leistung: "

   Cursor Off

End Sub
'-------------------------------------------------------------------------------


'Hauptmenь----------------------------------------------------------------------
Sub Hauptmenue

   Cls

   Locate 1 , 1
   Lcd "Hauptmenue: "

   Locate 2 , 1
   Lcd "Konfig. Sensoren (1)"                               '206

   Locate 3 , 1
   Lcd "Funktion1 "

   Locate 4 , 1
   Lcd "Funktion4 "

   Locate 4 , 17                                            '811
   Lcd "EXIT"

   Waitms 1000


Call Tastenabfrage_schleife

   Cls

   If Var3 = 4 Then

   Var3 = 0

   End If

   If Var3 = 3 Then

   Var3 = 0

      'Exit Sub
   End If

   If Var3 = 2 Then

   End If

   If Var3 = 1 Then
       Call Konfig_sensoren
       Var3 = 0
   End If

End Sub
'-------------------------------------------------------------------------------


'Tastenabfrage (Prьfung ob der Wert den Wert xxx entspricht)--------------------
Sub Tastenabfrage

   Tastenfeld = Getadc(3)

   If Tastenfeld_zaehler > 0 Then                           'Wenn Taste vorzeitig losgelassen wird, dann Rьckstellung des Zaehlers
      Tastenfeld_zaehler = Tastenfeld_zaehler - 1
   End If

   If Tastenfeld < Tastenwert_og Then
      If Tastenfeld > Tastenwert_ug Then
         Tastenfeld_zaehler = Tastenfeld_zaehler + 2
      End If
   End If

End Sub
'-------------------------------------------------------------------------------


'Tastenabfrage beendet wenn eine Taste gedrьckt wurde---------------------------
Sub Tastenabfrage_schleife

Var3 = 0

Do

Tastenfeld = Getadc(3)


'Taste1
Tastenwert_ug = 199
Tastenwert_og = 211
Var2 = 1
Call Tastenabfrage_schleife2

'Taste2
Tastenwert_ug = 402
Tastenwert_og = 415
Var2 = 2
Call Tastenabfrage_schleife2

'Taste3
Tastenwert_ug = 605
Tastenwert_og = 615
Var2 = 3
Call Tastenabfrage_schleife2

'Taste4
Tastenwert_ug = 805
Tastenwert_og = 816
Var2 = 4
Call Tastenabfrage_schleife2

   If Var3 > 0 Then                                         'zum letzten Menь gehen
         Exit Do
   End If

Loop


End Sub
'-------------------------------------------------------------------------------


Sub Tastenabfrage_schleife2

If Tastenfeld < Tastenwert_og Then
      If Tastenfeld > Tastenwert_ug Then
         If Var3 = Var2 Then                                'Taste(var3) "sicher" gedrьckt
            Exit Sub
         End If

            Var3 = Var2
      End If
End If



End Sub
'---------------------


Sub Konfig_sensoren

Cls

   Locate 1 , 1
   Lcd "Konfig. Sensoren:"

   Locate 2 , 1
   Lcd "DC-Sensoren(1)"                                     '206

   Locate 3 , 1
   Lcd "AC-Sensoren(2)"

   Locate 4 , 1
   Lcd "F4 "

   Locate 4 , 17                                            '811
   Lcd "back"

   Waitms 1000


Call Tastenabfrage_schleife

   Cls

   If Var3 = 4 Then
      Call Hauptmenue
      Var3 = 0
   End If

   If Var3 = 3 Then

   End If

   If Var3 = 2 Then

   End If

   If Var3 = 1 Then
   Call Konfig_dcsensoren
   Var3 = 0

   End If



End Sub

'---------


Sub Konfig_dcsensoren


Var11 = Str(l)

Cls

   Locate 1 , 1
   Lcd "Konfig. DC-Sensoren:"

   Locate 2 , 1
   Lcd "DC-1 (1)"                                           '206

   Locate 3 , 1
   Lcd "DC-2 (2)"

   Locate 4 , 1
   Lcd "F4 " ; Var11

   Locate 4 , 17                                            '811
   Lcd "back"

   Waitms 1000


Call Tastenabfrage_schleife

   Cls

   If Var3 = 4 Then
      Call Konfig_sensoren
      Var3 = 0
   End If

   If Var3 = 3 Then
      Locate 1 , 1
   Lcd "Taste 3 gedrueckt"
   Var3 = 0
   Waitms 5000
      'Exit Sub
   End If

   If Var3 = 2 Then
      Locate 1 , 1
   Lcd "Taste 2 gedrueckt"
   Var3 = 0
   Waitms 5000
      'Exit Sub
   End If

   If Var3 = 1 Then
 Call Maxampere
   Var3 = 0

   End If


End Sub

'-------------------------


Sub Maxampere






Cls

   Locate 1 , 1
   Lcd "Konfig. DC-1:"

   Locate 2 , 1
   Lcd "I-Maximal = " ; X ; " A"                            '206

   Locate 3 , 1
   Lcd "F3"

   Locate 4 , 1
   Lcd "F4"

   Locate 4 , 17                                            '811
   Lcd "back"


Waitms 500


Call Tastenabfrage_schleife

   Cls

   If Var3 = 4 Then
      Call Konfig_dcsensoren
      Var3 = 0
   End If

   If Var3 = 3 Then
      Locate 1 , 1
   Lcd "Taste 3 gedrueckt"
   Var3 = 0
   Waitms 5000
      'Exit Sub
   End If

   If Var3 = 2 Then
     If X > 29 Then
      X = X - 30
     End If
   Var3 = 0
   Call Maxampere
   End If

   If Var3 = 1 Then
        If X < 871 Then
      X = X + 30
     End If
   Var3 = 0
   Call Maxampere
   End If




End Sub

Autor: Axel Krüger (axel)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
kann das sein, weil sich die sub "maxampere" selbst wieder aufruft? :S

Autor: holger (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
>kann das sein, weil sich die sub "maxampere" selbst wieder aufruft? :S

Ja. Der Stack läuft über.

Autor: Axel Krüger (axel)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
rotwerd  .... ich habe 2 Stunden gegrübelt und eben beim 
runterscrollen ist mir das aufgefallen :/

Autor: Benedikt K. (benedikt) (Moderator)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Seit wann hat ein ATmega8 einen Hardware Stack?

Autor: Tom (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
> Seit wann hat ein ATmega8 einen Hardware Stack?

Mit Basic ist alles möglich!

Autor: Magnus Müller (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Benedikt K. schrieb:
> Seit wann hat ein ATmega8 einen Hardware Stack?

Den hat er sich vermutlich selbst in den Die rein dotiert ;)

Chip-Modding rulez     lol

Autor: A. K. (prx)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Nicht jeder Compiler verwendet nur einen Stack. Mancher trennt 
Return-Stack (HW) vom handgemachten Stack für Variablen und Parameter. 
Bei AVRs verkürzt das Funktions-Prolog/Epilog deutlich.

Autor: Tom (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
> Nicht jeder Compiler verwendet nur einen Stack. Mancher trennt
> Return-Stack (HW) vom handgemachten Stack für Variablen und Parameter.

Trotzdem ist es kein Hardwarestack. Return-Stack wird ja auch 
sinnvollerweise mit (HW) abgekürzt.

Antwort schreiben

Die Angabe einer E-Mail-Adresse ist freiwillig. Wenn Sie automatisch per E-Mail über Antworten auf Ihren Beitrag informiert werden möchten, melden Sie sich bitte an.

Wichtige Regeln - erst lesen, dann posten!

  • Groß- und Kleinschreibung verwenden
  • Längeren Sourcecode nicht im Text einfügen, sondern als Dateianhang

Formatierung (mehr Informationen...)

  • [c]C-Code[/c]
  • [avrasm]AVR-Assembler-Code[/avrasm]
  • [code]Code in anderen Sprachen, ASCII-Zeichnungen[/code]
  • [math]Formel in LaTeX-Syntax[/math]
  • [[Titel]] - Link zu Artikel
  • Verweis auf anderen Beitrag einfügen: Rechtsklick auf Beitragstitel,
    "Adresse kopieren", und in den Text einfügen




Bild automatisch verkleinern, falls nötig
Bitte das JPG-Format nur für Fotos und Scans verwenden!
Zeichnungen und Screenshots im PNG- oder
GIF-Format hochladen. Siehe Bildformate.
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.

Mit dem Abschicken bestätigst du, die Nutzungsbedingungen anzuerkennen.