mikrocontroller.net

Forum: Mikrocontroller und Digitale Elektronik Seltsamer Stackpointer


Autor: Peter X. (vielfrass)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Habe mir bei ATtiny84 mal den Stackpointerwert ausgeben lassen, bekomme 
607 dezimal.

Mein Programm hat eine Menge PUSH und POP und RCALL und RET drin, 
funktioniert ansonsten, obwohl ich
1. den Stackpointer zu initialisieren vergessen habe
2. der ATtiny84 laut Datenblatt nur 512 Byte RAM hat.

Warum 607 und nicht 511?

Autor: Hannes Lux (hannes)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Peter X. wrote:
> Habe mir bei ATtiny84 mal den Stackpointerwert ausgeben lassen, bekomme
> 607 dezimal.

Dann steht er noch auf RAMEND...

>
> Mein Programm hat eine Menge PUSH und POP und RCALL und RET drin,
> funktioniert ansonsten, obwohl ich
> 1. den Stackpointer zu initialisieren vergessen habe

Datenblatt Seite 11 Absatz 4.6.1 zeigt die Register SPL und SPH und 
zeigt auch als Startwert (Initial Value) RAMEND an. Man braucht den SP 
bei diesem AVR also nicht mehr per Hand initialisieren, das macht die 
Reset-Hardware bereits.

> 2. der ATtiny84 laut Datenblatt nur 512 Byte RAM hat.

Richtig. Und wo beginnt der SRAM?

>
> Warum 607 und nicht 511?

96 + 511 = 607 oder?

...

Autor: 3357 (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Der pointer ist natuerlich 16 bit SPL:SPH, wobei alle bit oberhalb 9 
abgeschnitten werden.

Autor: Hannes Lux (hannes)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
3357 wrote:
> Der pointer ist natuerlich 16 bit SPL:SPH, wobei alle bit oberhalb 9
> abgeschnitten werden.

Kannst Du das bitte mal genauer erklären?

;-)

...

Autor: spess53 (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Hi

>Datenblatt Seite 11 Absatz 4.6.1 zeigt die Register SPL und SPH und
>zeigt auch als Startwert (Initial Value) RAMEND an. Man braucht den SP
>bei diesem AVR also nicht mehr per Hand initialisieren, das macht die
>Reset-Hardware bereits.

Aber Vorsicht, das gilt nicht für alle AVRs.

MfG Spess

Autor: Hannes Lux (hannes)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
spess53 wrote:
> Hi
>
>>Datenblatt Seite 11 Absatz 4.6.1 zeigt die Register SPL und SPH und
>>zeigt auch als Startwert (Initial Value) RAMEND an. Man braucht den SP
>>bei diesem AVR also nicht mehr per Hand initialisieren, das macht die
>>Reset-Hardware bereits.
>
> Aber Vorsicht, das gilt nicht für alle AVRs.

Ich weiß, bei meinem letzten Tiny24-Projekt (vor einer Woche) wusste ich 
das auch noch nicht und habe den SP schön brav von Hand initialisiert. 
Ich bin auch erst durch Vielfraß' Frage auf die Idee gekommen, im 
Datenblatt nachzuschaun. ;-)

>
> MfG Spess

Bit- & Bytebruch, Hannes

Autor: spess53 (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Hi

@Hannes: Wenn man nicht mit jedem Byte geizen muss, ist das auch kein 
Beinbruch.

MfG Spess

Autor: Peter X. (vielfrass)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Habe mal was getestet:
Lasse mir in einer Endlosschleife den Stackpointer ausgeben.
Bei jedem Schleifendurchlauf wird der Stackpointer durch ein "POP" ohne 
dazugehöriges "PUSH" um 1 erhöht. Anzeige der Werte über Hyperterminal 
mit 115200 Baud. Witzigerweise stürzt das Programm erst ab, wenn der 
Stackpointer 1023 erreicht hat.
Big_loop:
  IN  Zahl_l,SPL
  IN  Zahl_h,SPH
  RCALL  Zahl_ausgeben
  POP  ACC  ;Nur zu Testzwecken!!!!!!!!!!!!!!!!!!!

  ldi      ACC,13   ;CR
  rcall    RS232_putchar
  ldi      ACC,10   ;LF
  rcall    RS232_putchar
  
  ldi  ACC,20
  rcall  Delay
  rjmp  Big_loop
Warum?

Autor: Hannes Lux (hannes)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Hi Vielfrass...

Der Stack wächst nach unten (zu kleineren Adressen). Sein Startwert ist 
RAMEND, also das Ende vom RAM. Probleme gibt es, wenn der Stackpointer 
auf so geringe Adressen zeigt, dass der Stack Variablen, I/O-Register 
oder gar CPU-Register überschreibt.

Du kannst den Stackpointer zwar über das RAM-Ende hinaus erhöhen, dort 
ist aber kein RAM und sonst auch nix. Die Adressierung greift daher erst 
beim Überschreiten des gesamten adressierbaren Bereiches, also wenn der 
Wertebereich (durch Bitbreite des SPH:SPL bestimmt) überschritten ist 
und damit die oberen Bits wirkungslos sind und die unteren (wirksamen) 
Bits auf die CPU-Register zeigen.

Du solltest Dir den verfügbaren Adressbereich nochmal genau ansehen, ehe 
Du weitere Experimente machst, ansonsten ziehst Du falsche Schlüsse. 
Experimente sind zwar eine feine Sache, doch ohne Verständnis der 
Zusammenhänge bringen sie nicht viel. Und Vieles lässt sich im Vorfeld 
durch das Lesen der Datenblätter ermitteln, z.B. auch die Organisation 
des Speichers und seiner Adressbereiche.

...

Autor: crazy horse (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
also ich habe solche Spielchen früher auch schon mal gemacht, und 
teilweise war da wirklich mehr Speicher da als angegeben. Speziell ging 
es um den 4414 und 8515, RAM und EEPROM. Das sah so aus, als ob der 4414 
die Resteverwertung von teildefekten 8515 war, aber auch nicht 
durchgängig.

Autor: Hannes Lux (hannes)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Mir scheint, dass jeder AVR-Typ ein Versuchskarnickel ist, bei dem 
irgendein Feature für zukünftigen Serien-Einsatz getestet wird.

Ich bin allerdings noch nicht auf die Idee gekommen, nach Teilen zu 
suchen, die es laut Datenblatt gar nicht gibt... (Nein, ich bin kein 
wandelndes Datenblatt, aber ich betreibe das nur zum Hobby und kann mir 
die Zeit nehmen, Datenblätter zu lesen...)

...

Autor: Peter X. (vielfrass)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Habe mir das Datenblatt des ATtiny84 eben noch mal angesehen.
Der Bereich der 32 Register geht von
0x0000 bis 0x001F
Die 64 IO-Register gehen von
0x0020 bis 0x005F
Die 512 Byte das RAM's gehen von
0x0060 bis 0x025F

0x025F = 607 dezimal.

Was zwischen
0x0260 und 0x03FF ist, habe ich im Datenblatt bisher noch nicht finden 
können. Habe mich nur gewundert, das mein Programm trotz mehrerer 
Unterprogramme, die selber wieder Unterprogramme aufrufen nicht 
abstürzt, wenn der Stackpointer auf Adressen oberhalb 0x025F zeigt.

"Versuch macht klug"

Autor: Jochen Müller (taschenbuch)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Wobei ich persönlich das automatische Initialisieren des Stackpointers 
für einen witzlosen Gimmick halte. Ich käme niemals auf die Idee den 
Stackinit am Programmanfang weg zu lassen. Alleine schon wegen der 
Probleme, wenn das Programm mal auf einen anderen AVR portiert werden 
soll (der dann eben nicht automatisch initialisiert...).
Auch initialisiere ich JEDEN Portpin auf definierte Werte, auch wenn lt. 
Datenblatt der Port nach einem Reset schon auf dem-und-dem Wert stehen 
soll.
Gleiches gilt für mich für jede andere AVR-Peripherie.
Irgendwie fühle ich mich sonst nicht richtig wohl.

Jochen Müller

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.