12 KiB
12 KiB
ARM Befehle
ARM 7
- Architektur: ARM v4T, Prozessor ARM7 TDMI
- 1994 rausgekommen
- 12-70 MHz, 0,889 DMIPS/MHz
- RISC, Load-Store-Architektur
- 3-stufige Pipeline
- Instruction Set
- ARM 32 bit oder Thumb
- 3-Adress-Befehle
- Little Endian als Standard
ARM-Datenpfad
ARM7-ALU
ARM7-Pipeline für ALU-Befehle
- Latenz
- 3 Zyklen
- Durchsatz
- 1 Befehl je Zyklus
Multi-cycle Execution
- Execute benötigt einen Takt für simple Instruktionen
- Bei Speicherzugriff mind. 2 Takte
- Adress Berechnung
- Speicherzugriff
Load/Store Befehle Hazard in Von-Neumann
ARM Registerstruktur
Statusflags
- N (Negative)
- Das Ergebnis der ALU ist negativ (Bit 31=1)
- Z (Zero)
- Das Ergebnis der ALU ist Null (Bit 0..31 = 0)
- C (Carry)
- Bei arithmetischer Operation wird C auf Carry-Out der ALU gesetzt
- Sonst auf Carry-Out des Shifters bzw. ohne Shift Operation bleibt C erhalten
- V (Overflow)
- Wenn Zahlensystem geändert wird
- Wenn mit unsigned gerechnet wird ist V ohne Interesse
Current Program Status Register (CPSR)
- T-Bit
- T = 0
- Prozessor in Arm State
- T = 1
- Prozessor in Thumb State
- T = 0
- Interrupt Disable Bit
- I = 1, disables IRQ
- F = 1, disables FIQ
- Mode Bits
- Spezifizieren Prozessor Mode
Übersetzungstabelle Assembler - Binärcode
Thumb Befehlsatz
- zusätzlicher Befehlssatz
- 16 Bit
- Intern werden sie auf 32 Bit erweitert
- Programme verbrauchen nur halben Speicher
- weniger Register stehen zur Verfügung
- Während Programmausführung kann zwischen ARM-32 und Thumb gewechselt werden
- Programme verbrauchen nur halben Speicher
- Thumb-2 ist ein gemischter 16/32 Bit Befehlssatz
- Prozessor ARM7TDMI unterstützt sowohl ARM als auch Thumb
ARM Befehlssatz
- Drei Befehlstypen
- zur Datenverarbeitung (bspw. Addition)
- Ablaufsteuerung (bspw. Verzweigungen)
- Befehle zur Adressierung
- Groß-Kleinschreibung wird ignoriert
ARM-Befehle: MOV
- MOV ist ein Datentransferbefehl
- Kopiert Daten in ein Register
- Beispiele
- mov r0, r1 @Inhalt von R1 wird nach R0 kopiert
- mov r1, #0 @Zahl 0 wird nach R1 kopiert
- mov pc, lr @PC wird auf LR gesetzt
- Variante:
- mvn r1, r2
- Wendet zusätzlich zu mov ein EOR auf Inhalt von r2 an
- mvn r1, r2
ARM-Befehle: ADD
- Die arithmetischen Befehle der ARM Prozessoren sind 3-Register-Befehle
- Alle Operanden sind 32Bit
- Das Ergebnis ist 32 Bit
- 3 Operanden: 2 als Input, 1 als Ergebnis
- Beispiel
- ADD r0, r0, r3 @R0 = R0 + R3
ARM-Befehle: SUB
- ARM-Prozessoren implementieren keine Subtraktion
- Addition mit 2er Komplement
- Beispiel
- SUB r0, r0, r3 @R0 = R0 - R3 = R0 + (-R3)
ARM-Befehle: CMP
- Befehl vergleicht zwei Werte auf Gleichheit und setzt Statusflags entsprechend
- CMP r0, #5 @r0 == r5?
- Dazu wird folgende Berechnung (r0=3) ausgeführt
- CMP r0, #5 @r0-5 = 3-5 ausgeführt
- MOV r1, #5
- SUBS r1, r0, r1
- CMP r0, #5 @r0-5 = 3-5 ausgeführt
- Folgende Statusflags werden gesetzt
ARM-Befehle: -S
- Setzen des Statusregisters bei arithmetischen und logischen Befehlen
- Bedingungsbits des Statusregisters werden nur bei Test-/Compare-Befehlen automatisch gesetzt
- Alle anderen Befehle müssen explizit setzen
- Beispiel
- add r0, r0, r3 @lässt Statusregister unverändert
- subs r0, r0, #1 @schreibt alle Flags NZCV
ARM-Befehle: - {cond}
- Jeder Befehl kann bedingt ausgeführt werden
- Bedingung (bezogen auf vorher gesetzte Werte des Statusregisters) als Ergänzung an den Befehl angehängt
- Beispiel
- CMP r0, #5
- ADDNE r1, r1, r0
- SUBNE r1, r1, r2
- if (r0 != 5) {r1 = r1+r0-r2}
- NE = not equal
- Bezogen auf die vorherigen Werte des Statusregisters
Bedingte Ausführung von Befehlen
Signed/unsigned
carry set / higher same
- Beispiel:
- CMP r0, r1 @berechnet R0-R1, also R0 + (-R1) und setzt NZCV
- JCS sprungziel @springt zur Marke "sprungziel", wenn CS erfüllt ist
- Bedeutung: Wenn unsigned >= dann C gesetzt
- R0 = 3,R1 = 2 (nur 4-Bit Darstellung)
- R0 = 0011 2k = 1110
- Berechnet: 0011 + 1110 = 3 + (-2) = 0001
- C = 1
- R0 = 2, R1 = 3 (nur 4-Bit Darstellung)
- R0 = 0010 R1 = 0011
- Berechnet: 0010 + 1101 = 2 + (-3) = 1111
- C = 0
Bedingte Ausführung LT (Less than)
- Beispiel
- CMP R0, R1 @berechnet R0-R1 und setzt NZCV
- JLT sprungziel @springt zur Marke "sprungziel", wenn CS erfüllt ist
- Bedeutung: wenn signed < dann N ungleich V
- Beispiel 1
- R0 = 3, R1 = 4 (nur 8 Bit)
- R0 = 00000011 R1 = 00000100
- Berechnet: 00000011 + 11111100 = 3 + (-4) = 11111111
- N = 1, V = 0
- Beispiel 2
- R0 = -127, R1 = 2
- R 0 = 10000001 R1 = 00000010
- Berechnet: 10000001 + 11111110 = -127 + (-2) = 127 (?)
- N = 0, V = 1
ARM-Befehle: Der Barrel Shifter
LSL: Logical Shift Left = Arithmetic Shift Left (ASL)
LSR: Logical Shift Right
ASR: Arithmetic Shift Right
ROR: Rotate Right
RRX: Rotate Right Extended
Multiplikation mit einer Konstanten
- mit 2^x oder als 2^x +-1 darstellen lassen
- können in einem Zyklus durchgeführt werden
- Beispiel: Mul mit 5
- ADD r0, r1, r1, LSL #2
- Durch Zusammensetzen mehrerer Instruktionen können auch komplexere Multiplikationen durchgeführt werden
- Beispiel: Mul 10
- ADD r0, r1, r1, LSL #2
- LSL r0, r0, #1 @mov r0, r0, LSL#1
- Beispiel Mul mit 119 = 17·7 = (16+1)·(8-1)
- ADD r2, r3, r3, LSL #4 @r2 = r3·17
- RSB r2, r3, r2, LSL #3 @r2 = r2·7
- Beispiel: Mul 10
UAL (Unified Assembler Language)
- gemeinsamer Syntax für ARM32 und Thumb
- gleicher Code für beide Modi
- Falls Befehl nicht umgesetzt werden kann
- Assembler gibt Fehlermeldung aus
- Beispiel 1
- vorher
- Thumb: AND R0, R1
- ARM: AND, R0, R0, R1
- Jetzt: AND R0, R0, R1
- vorher
- Beispiel 2
- vorher
- Thumb: LSL R0, R1, #2
- ARM: MOV R0, R1, LSL #2
- Jetzt: LSL R0, R1, #2
- vorher
Arithmetische und logische Befehle
Binärcodierung arithmetischer und logischer Befehle
Assembler Format
-
Arithmetische und logische Befehle haben eins der beiden logischen Formate
- <op>{<cond>}{S} -> Rd, Rn, #<32-Bit-Immidiate>
- <op>{<cond>}{S} -> Rd, Rn, Rm, {<shift>}
-
Rd: Destination
-
Rn: Operand 1
-
Rm: Operand 2
-
Beispiel:
- ADD r0, r1, r2
- ADD r0, r2, #4
- MOV r0, r1
- ADDGTS r0, r1, r2, LSR r3
Operand 2 als Konstante (Immidiate)
- Befehlsformat für Datenverarbeitungsbefehle reserviert 12 Bits für Operand 2
- ergäbe einen Wertebereich von max 2^12 = 4096
- oder aufgeteilt in Wertebereiche mit 8 Bits (0-255)
- Diese 8 Bits können (links) rotiert werden
- gerade Anzahl von Positionen (0, 2, 4, ..., 30)
- Ergibt weitaus größere Abdeckung des Zahlenbereichs
- Einige Konstanten müssen dennoch vom Speicher geladen werden
- oder in einem Register konstruieren
Operand 2 als Konstante
- Wertebereich
-
0-255 [0-0xff] 256, 260, 264, ..., 1020 [0x100-0x3fc, step 4, 0x40-0xff ror 30] 1024, 1040, 1056, ..., 4080 [0x400-0xff0, step 16, 0x40-0xff ror 28] 4096,4160, 4224,..,16320 [0x1000-0x3fc0, step 64, 0x40-0xff ror 26]
-
- Beispiel MOV-Befehl
- MOV r0, #0xFF000000 @MOV r0, #0xFF, 8
- Beispiel MVN: erzeuge das bitweise 1er-Komplement
- MOV r0, #0xFFFFFFFF @umgesetzt zu MVN r0,#0
- Falls benötigte Konstante nicht erzeugt werden kann
- Assembler erzeugt Fehlermeldung
Multiplikation
Befehle zur Ablaufsteuerung
Sprungbefehle (Branch)
- dienen dazu den Kontrollfluss von Programmen zu kontrollieren
- in Kombination mit Vergleichsbefehlen
- können alle wichtigen Anweisungen (if, else, while, for, switch) darstellen
- Ziel ist immer eine Marke (Label)
- Assembler erzeugt Sprungadresse
- Beispiel
-
CMP R0, #0 BNE Marke 1 ... ... Marke 1: MOV R5, #5
Sprungbefehle
Unterprogramme (Branch-with-Link)
- Der Befehl BL führt einen Sprung aus
- speichert die Rücksprungadresse im Link-Register r14(LR)
- Weitere Subroutinen müssen r14(LR) im Speicher sichern
- bspw. auf Stack und bei Rückkehr in r15(PC) wieder herstellen
- Arbeitsregister können ebenfalls gesichert werden
- wenn Unterprogramm diese benötigt
- Übergabe von Parametern nach APCS-Standard
- Beispiel
Sprungbefehle mit Mode-Wechsel (32Bit Thumb)
- BX Rn Branch and Exchange
- Als Argument erhält der Befehl eine Registeradresse
- Inhalt wird in PC kopiert
- Falls ungerade → Wechsel in Thumbmode
- Falls gerade → Wechsel in ARM-Mode
- Inhalt wird in PC kopiert
- Befehl BX LR ist Standardbefehl um Unterprogramme zu verlassen
- Rücksprungadresse steht noch im Linkregister
- Als Argument erhält der Befehl eine Registeradresse
- BXL Label - Branch and Link with Exchange
- Standardbefehl zum Aufruf von Unterprogrammen
- wird in Programmen mit gemischtem 32-Bit/Thumb Code genutzt
- BLX Rn
- Führt Modewechsel durch
- Speichert nächste Adresse im Linkregister
Unterprogrammaufruf mit Modewechsel
Befehle zur Ablaufsteuerung - Beispiele
- Befehle MOV PC, Rd, ist nach Einführung des Thumb Befehlssatzes nicht mehr empfohlen
- Lässt direkten Zugriff auf PC nicht zu
- Stattdessen BX, BLX
- Alle Sprungbefehle können bedingt ausgeführt werden
- Offset der Sprungbefehle bis zu 32 MByte
- FÜr größere Sprünge muss Zieladresse erst in ein Register geladen werden
Assembler-Format der Sprungbefehle
APCS (ARM Procedure Calling Standard)
- Standard definiert wie Funktionen geschrieben werden sollen
- können unabhängig geschrieben, compiliert, assembliert uns später gelinkt werden
- Umfasst auch andere Programmiersprachen wie C
- Definiert sind
- Anforderungen an aufrufende/aufgerufene Funktionen
- Einschränkungen bei der Nutzung von Registern durch Funktionen
- Daten- und Stacklayout und Konventionen
- C/C++ Language Bindings, shared libs, reentrant code, etc.
Parameterübergabe an Funktionen
- Funktionsaufruf:
- Result = fct(ARG1, ARG2, ARG3, ARG4)
- Parameter 1-4 in Register r0-r3 übergeben
- Rückgabewert von Funktionen steht im Register r0 oder r0/r1
- Result = fct(ARG1, ARG2, ARG3, ARG4)
- Verwendung von Registern in der Funktion
- r0-r3 und IP = Scratch Register
- dürfen im Unterprogramm zerstört werden
- Informationen in r4-r10, fp, sp dürfen nicht zerstört werden
- Inhalt von lr wird zur Rückkehr ins aufrufende Programm benötigt
- r0-r3 und IP = Scratch Register