www.mikrocontroller.net

Forum: Mikrocontroller und Digitale Elektronik Rückkehr nach Befehl BRTS o. BRTC?


Autor: Thomas O. (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Hallo,

ich habe ein kleines Programm geschrieben das die 8 Bits eines
Registers nacheinander an einen Port ausgeben soll. Also R17 ist z.b.
00000001 dann soll es halt 7 mal low und 1mal high die Verzögerung
erfolgt mittels Schleife. Ich habe aber ein Problem und zwar kann ich
nach einen Aufruf einer Routine nicht mehr zur urspünglichen
Programmstelle zurückspringen. Da die Routine ja nicht mit rcall
aufgerufen wurde komme ich mit ret nicht zurück sondern lande auf
init:

Habe mal das asm-File mitgeschickt. Wäre klasse wenn mir jemand sagen
könnte wie ich nach einem brts Aufruf wieder auf den darauf folgenden
Befehl(brtc) komme.

Autor: Thomas O. (Gast)
Datum:
Angehängte Dateien:

Bewertung
0 lesenswert
nicht lesenswert
Hallo,

ups hab das ams-File vergessen

Autor: Christof Krüger (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Mit brts springst du einfach irgendwo hin und speicherst vor dem Sprung
NICHT, wo du vorher warst. Hab ich das richtig verstanden? Und jetzt
willst du an die vorherige Stelle zurück? Wie soll das gehen, wenn du
dir das vorher nicht gespeichert hast?

Folgendes könntest du stattdessen machen:

          brts highcall  ;zum "rcall high" sprinten
          rcall low      ;ansonsten low "callen"
          rjmp weiter    ;low ausgeführt, nächsten befehl überspringen
highcall: rcall high     ;high "callen"
weiter: ...

In den unterprogrammen low und high benutzt du dann am Ende ret.
Wenn bei "brts highcall" nicht gesprungen wurde, kannst du beim
nächsten Befehl davon ausgehen, dass T nicht gesetzt ist, daher
brauchst du kein zusätzliches brtc benutzen.

Ganz davon abgesehen, dass man den ganzen Code viel effektiver
schreiben könnte. Stell dir vor, ein Register wäre nicht nur 8 Bit
sondern ganze 32 Bit breit. Würdest du dann 32 Mal fast das gleiche
schreiben?
Eine Anregung: Benutze eine Schleife und shifte das Register immer um 1
nach links. Das "herausgeshiftete" Bit geht nicht verloren, sondern
wird im Status-Register gespeichert. An welcher Stelle genau steht dann
in der ASM-Hilfe vom AVR-Studio.

Viel Spass noch!

Autor: Thomas O. (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Hallo,

danke für die Antwort,. Mir ist schon klar das dieser Code sehr
uneffektiv ist( vor allem für mich) der Assembler macht da schon
bestimmt was ordentliches draus. War auch garnicht mein Problem. Mir
war ja auch klar das ret nicht funktioniert ohne rcall Aufruf. Habs
einfach mal drin gelassen damit man sieht von wo ich wieder
zurückwill.

Deine Problemlösung hab ich ja auch schon probiert. Aber ich habe dann
das gleiche Problem und zwar bewirkt dann das ret das ich hier wieder
bei der Aufrufroutine lande und nicht nach auf den BRTC Befehl.

Test7:
bst temp2,7 ; Store bit 7 of r15 in T Flag
brts recallhigh; Branch if T Flag set
brtc lowhigh

rcallhigh:
rcall xyz

xyz:
xxxxx
xxxxx
xxxxx
ret

Autor: Christof Krüger (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Du hast jetzt meine Problemlösung aber nicht 1:1 übernommen. Warum
willst du das T-Bit nochmal testen, auch wenn du es in deinem
Unterprogramm nicht änderst?

So wie du es jetzt geschrieben hast wird im Fall, dass T gesetzt ist
folgendes passieren:
brts rcallhigh wird anschlagen und zum befehl rcall xyz führen. Nach
dem ret im Unterprogramm wird NACH "rcall xyz" fortgefahren.

Im Fall, dass T NICHT gesetzt ist passiert folgendes:
"brts rcallhigh" schlägt NICHT an, "brtc lowhigh" jedoch schon und
an dem Punkt weiss ich nicht, was du mit dem Beispiel willst, da du
nirgends lowhigh als Label deklariert hast ;)

Hier nochmal mein Beispiel:


          brts highcall  ;zum "rcall high" sprinten
          rcall low      ;ansonsten low "callen"
          rjmp weiter    ;low ausgeführt, nächsten befehl überspringen
highcall: rcall high     ;high "callen"
weiter:   ...

Beim ersten Befehl wird geprüft ob T geseztzt ist. Wenn ja, dann wird
zu highcall gesprungen und dort wird mit rcall zu high gesprungen. Ist
das Unterprogramm "high" fertig, geht es nach dem rcall weiter, also
dort wo das Label "weiter" deklariert ist. Im Fall, dass T nicht
gesetzt ist, wird beim ersten Befehl nicht gesprungen. An dieser Stelle
wissen wir, dass wir nicht gesprungen sind, also dass T nicht gesetzt
ist. Daher rufen wir "low" mit rcall auf. Wenn "low" fertig ist und
"ret" benutzt gehts nach dem rcall weiter, also beim dritten Befehl,
nämlich "rjmp weiter". Dieser Befehl ist dazu gut, da ansonsten der
nächste Befehl wieder "rcall high" wäre, aber das wollen wir ja
nicht, daher überspringen wir diesen Aufruf quasi.
Ich hoffe, du verstehst jetzt die Funktionsweise.

Autor: Thomas O. (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Hallo,

ok jetzt hab ichs verstanden. Werde das jetzt ausprobieren, danke
nochmal.

Autor: crazy horse (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
und der Assembler macht gar nichts dran, der übersetzt es so wie es da
steht (wenn er es kann) - selbstständige Optimierungen gibts da nicht.

Autor: ...HanneS... (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Stimmt.

Der Assembler macht aus jedem Befehl exakt einen Maschinenbefehl. Ob
diese logisch angeordnet sind, ist Sache des Programmierers. Um das zu
ergründen, ist die Simulation im AVR-Studio sehr gut geeignet.
Besonders bei solch kleinen Programmen kann man per Einzelschritt
logische Fehler sehr schnell aufspüren. Dabei sollte man sich im
Workspace (linke Seite) das Statusregister und die benutzten I/Os
anzeigen lassen und im Memory-Fenster (unten rechts) den Inhalt der
Register. Und die F11-Taste sollte man erst wieder betätigen, wenn man
vorhersagen kann, was als nächstes passieren wird. Passiert das
Vorhergesagte, dann ist es gut, passiert etwas Anderes, dann hat man
irgendwo einen Denkfehler gemacht. Dann hilft die Hilfe zu den
ASM-Befehlen weiter.

Übrigens ist ein Programmablaufplan (Papier & Bleistift) recht
hilfreich, solche logischen Fehler wie im vorgestellten Programm zu
erkennen.

Gruß...
...HanneS...

Autor: Thomas O. (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Hallo,

ok danke, war also ne Fehlannahme von mir das ja was beim Assamblieren
optimiert wird. Vielleicht ist es bei x86er Assembler so. Dachte das
mal irgendwo gelesen zu haben.

Autor: Andi (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Kein ASM-Compiler optimiert oder verändert irgend was an den
Maschinen-Befehlen.
Das machen nur C-Compiler oder andere Hochsprachen aber in der
logischen Abfolge verändert keiner was.
BRTS und BRTC prüfen einfach ob das T-Bit in SREG gesetzt (1) oder
gelöscht (0) ist und verzweigen (springen) dann zu ner anderen Stelle
wenn die Prüfung zutrifft.
In Deinem Fall mit einem Aufruf eines Unterprogrammes wenn T-Bit
gesetzt oder gelöscht ist mußt Du anders rum denken.

 BRTC  nohigh1    ;Ist Zustand (T-Bit) low (0)?
 rcall high       ;Wenn nicht, also high, dann zu high callen.
nohigh1:
 BRTS  nolow1     ;Ist Zustand (T-Bit) high (1)?
 rcall low        ;Wenn nicht, also low, dann zu low callen.
nolow1:
 .....

Man überspringt durch das Prüfen des Gegenteiles den RCALL.

geht auch ohne dem T-Bit sofern das Register mit dem zu prüfenden Bit
eines von R16 - R31 ist.
Mit SBRS Rr,n und SBRC Rr,n (Skip if Bit in Register is Set/Clear)
überspringt man den nächsten Befehl wenn eine Bit-Prüfung zutrifft.

 SBRC  temp2,6    ;Ist Bit 6 low (0)?
                  ;Wenn ja, dann RCALL überspringen.
 rcall high       ;Wenn nicht, also high, dann zu high callen.
 SBRS  temp2,6    ;Ist Bit 6 high (1)?
                  ;Wenn ja, dann RCALL überspringen.
 rcall low        ;Wenn nicht, also low, dann zu low callen.
 .....

Mit SBRS und SBRC erspart man sich die zusätzlichen Marken im Prog.

Gruß
Andi

Autor: ...HanneS... (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Es gibt keine ASM-Compiler, das sind Assembler (im Gegensatz zu
Hochsprachen-Compilern)...

Das Einsparen von Marken / Labels bringt nix, da diese keine Ressourcen
verbrauchen. Sie dienen nur dazu, einen (bedingten) relativen Sprung zu
berechnen. Im eigentlichen Maschinensprachebefehl steht dann nur die
Sprungdifferenz, die zum PC (Programm-Counter) addiert wird.

...HanneS...

Autor: Andi (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Das ein Label keine Resourcen braucht ist schon klar.
Sollte nur verdeutlichen, das SBRS und SBRC den nächsten Befehl nach
zutreffender Bit-Prüfung sowieso überspringen.
Das mit dem "ASM-Compiler" ist halt in vieler Munde obwohl es das
nicht ist und irgend wie auch zu mir rübergerutscht.
Es wird Assembliert (gebaut, erstellt) und nicht Compiliert
(umgewandelt).
Man, Du mußt aber auch alles zerlegen.

Gruß
Andi

Autor: ...HanneS... (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Hi Andi...

Ach so, ist wohl so wie mit der "String-Taste" am PC... ;-))

Mach dir nix draus, nimms mit Humor, mach ich doch auch immer, auch
wenns manchmal nicht so aussieht.

Beste Grüße...
...HanneS...

Autor: m.merten (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Dann muß ich meinen Senf aber auch dazu geben :-)
Marken bzw. Labels verbrauchen sehr wohl Resourcen, zwar nicht im
Programmspeicher der µc, aber in der Symboltabelle des Assemblers
und machen diese ggf. unnötig groß und unübersichtlich.

Autor: Tobi (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
das stört den assembler aber herzlich wenig wenn er nun 20 symbole mehr
zu verarbeiten hat oder nicht. übersichtlichkeit kennen computer nun
auch noch nicht - so weit ist die ki forschung noch nicht :)
und auf einem aktuellen pc dürfte das irgendwo im kaum messbaren
bereich länger dauern

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.