Forum: Mikrocontroller und Digitale Elektronik Rechenoperationen Subtraktion


von Steven Z. (stivi)


Lesenswert?

Hallo, habe wiedermal ein paar Probleme.

Ich habe in einem Buch folgendes stehen:

Subtraktion:

ldi r16,K1-K2    ; lädt r16 mit K1-K2

Meine Frage, kann ich K1 und K2 mit einem Register ersetzen!

Funktion:
1. Es soll in K1 eine Konstante stehen und in K2 soll der Wert vom ADC
   übernommen werden!
2. Ergebniss dann in R16!

Vielen Dank!

MFG
Steven

von Nobody (Gast)


Lesenswert?

nein, geht so nicht, denn K1-K2 rechnet der compiler aus und setzt das 
Ergebnis dann ein.

von rene (Gast)


Lesenswert?

ld R16,irgendeinregister
sub R16,irgendeinanderesregister

rene

von Thomas F. (thomas-hn) Benutzerseite


Lesenswert?

In AVR-Assembler nicht.
Dort musst Du z.B. mit "mov r8, Wert" einen Wert in das Register r8 
laden. Dann mit mov den Wert vom ADC holen (korrigiert mich, wenn ich 
den ADC-Wert nicht mit mov bekomme...AFAIK ist es ja aber nur der Inhalt 
von nem Timerregister). Anschließend kannste mit (AFAIK) "sub" die Werte 
subtrahieren und danach wenn benötigt mit "mov" ins benötigte Register 
schieben.

Gruß,

Thomas

von Ronny (Gast)


Lesenswert?

eher:

ldi  Register,Konstante  ODER
mov  Register,Register

von Ronny (Gast)


Lesenswert?

und an Peripherie-Register kommt man mit IN und OUT.

von Werbungverschmäher (Gast)


Lesenswert?

> Meine Frage, kann ich K1 und K2 mit einem Register ersetzen!

Nein. Konstanten sind im Programmcode festgeschrieben (also konstant) 
und lassen sich zur Laufzeit nicht ändern. Da sich Konstanten durch 
Labels ausdrücken lassen (Aliasnamen), können bei einer Zuweisung zu 
einem Register (das Register enthält dann eine Variable) mehrere 
Konstanten vom Assembler zusammengefasst (addiert, subtrahiert, 
multipliziert, dividiert, verORt, verANDet, geshiftet, LOW-isoliert, 
HIGH-isoliert, ...) werden, bevor sie dem Register zugewiesen werden. 
Die Berechnungen erledigt der Präprozessor des Assemblers bevor aus dem 
Quelltext eine ausführbare Datei erstellt wird. In der ausführbaren 
Datei (Maschinencode des Programms) steht dann nur noch das Ergebnis der 
Vorberechnung in Form des Maschinenbefehls, der in einigen seiner Bits 
die (zuzuweisende) Konstante enthält.

Schau Dir mal die Bitmuster der Maschinencodes zu den Befehlen an, die 
mit Konstanten operieren, da gibt es fest definierte Bits für den 
Befehl, variable Bits für das Zielregister und variable Bits für die 
Konstante. Falls Du das in Deinem Buch nicht findest, dann schau mal in 
die Online-Hilfe des AVR-Studios.

MFG

von Ronny (Gast)


Lesenswert?

> Schau Dir mal die Bitmuster der Maschinencodes zu den Befehlen an, die
> mit Konstanten operieren, da gibt es fest definierte Bits für den
> Befehl, variable Bits für das Zielregister und variable Bits für die
> Konstante.

Richtig,die Konstante ist Teil des Maschinenbefehls und liegt genau wie 
der restliche Code (und,falls nicht explizit anders angegeben,auch 
konstant per .DB/.DW abgelegt Daten) im Flash.Das ist ein wichtiges 
Merkmal der AVRs und jeder Havard-Architektur dass Programm und 
Datenbereich strikt getrennt sind.Deshalb gibt es auch unterschiedliche 
Befehle,um Konstanten aus dem Flash (LDI,CPI,SUBI,LPM....) und Variablen 
aus dem SRAM (STS,LDS,LD,ST,...) zu verarbeiten.Um zwischen 
CPU-Allzweckregistern Daten zu verschieben,gibt es dann noch den 
MOV-Befehl.

Zu beachten ist,das eine Lesezugriff auf den Flash(Achtung,Wortweise 
organisiert) andere Daten liefert als ein Lesezugriff aufs SRAM an der 
selbe Addresse:

LPM r0,0x100  ; Byte aus dem Flash von Addresse 100h laden
lds r0,Konstante  ; Byte aus dem SRAM von Addresse 100h laden


Wie die einzelnen Speicherbereiche genau aufgebaut sind,steht im Kapitel 
"AVR-Memories" oder ähnlichem im Datenblatt zu deinem Lieblings-AVR.

Bitte melde dich an um einen Beitrag zu schreiben. Anmeldung ist kostenlos und dauert nur eine Minute.
Bestehender Account
Schon ein Account bei Google/GoogleMail? Keine Anmeldung erforderlich!
Mit Google-Account einloggen
Noch kein Account? Hier anmelden.