Übungsblatt 1: Funktion der PC-Register und einfache PC-Assemblerbefehle

Im heutigen Labor werden wir uns etwas näher mit den Allzweckregistern und dem Flag-Register des PC beschäftigen und uns mit einigen grundlegenden Assemblerbefehlen vertraut machen.

Aufgabe 1: Jasmin kennenlernen

Zu diesem Zweck werden wir die Assemblerentwicklungsumgebung Jasmin einsetzen. Jasmin wurde in Java geschrieben und ist sowohl unter Windows, als auch auf dem Mac lauffähig.

Jasmin erlaubt das interaktive Editieren, Ausführen und Visualisieren von Assemblerbefehlen und -programmen, ohne dass ein expliziter Übersetzungsvorgang ("assembly") in Maschinensprache erforderlich ist.

Step/ Schritttaste
Resettaste
Abb.1: Buttons

Starten Sie zunächst Jasmin und legen Sie ein neues Dokument an. Auf der linken Seite blendet Jasmin die gegenwärtigen Registerinhalte ein. Hier finden sie die 32-Bit-Allzweckregister EAX bis EDX, die auch als arithmetische Register bezeichnet werden, und das Flag-Register ("flags") in Form seiner wichtigsten Kontrollbits (Abb. 2).

Abb.2: Flag-Register

Tippen Sie den Befehl mov ax,100 in Zeile 0 ein und führen Sie diesen als Einzelbefehl durch Drücken der Schritttaste (s. Abb. 1) aus. Der grüne Balken springt dabei eine Zeile weiter und markiert so die als nächstes auszuführende Befehlszeile. Durch wiederholtes Drücken der Schritttaste kann ein Programm Befehl für Befehl durchlaufen werden.

Abb.3: Jasmin Oberfläche

Das Resultat jedes Programmbefehls können Sie an Hand der Registerwerte studieren.

Wie Sie in Abbildung 3 sehen, interpretiert Jasmin die 100 als Dezimalzahl. Diese wird durch den MOV-Befehl in das Akkumulatorregister AX geschrieben. Da der Zahlenwert in ein Byte passt, landet dieser im unteren Byte AL des Registers AX. Um die genaue Belegung der Registerbytes einsehen zu können, müssen Sie auf den Button ... links neben dem Register klicken, damit die Registeransicht expandiert wird.

Wenn Sie nun auf hex und bin klicken, können Sie den Hexadezimal- und Binärwert der Dezimalzahl 100 sehen. Mit +-dec und dec schalten Sie zwischen der vorzeichenbehafteten und vorzeichenlosen dezimalen Zahlendarstellung um.

Durch Drücken der Resettaste (s. Abb. 1) ist es möglich, wieder an den Anfang eines Programms zu springen. Dabei werden alle Register auf 0 zurückgesetzt.

Ändern Sie den Befehl in Zeile 0 ab zu mov ax,-100. Drücken Sie danach die Resettaste und führen Sie den Befehl erneut aus. Expandieren Sie dann die Registeransicht und schalten Sie zwischen bin, +-dec und dec um, um die Unterschiede zwischen den verschiedenen Darstellungen zu sehen.


Aufgabe 2: Allzweckregister

Neben Dezimalzahlen können Sie durch ein nachgestelltes h, z. B. 100h, oder durch ein vorangestelltes 0x, z. B. 0x100, auch Hexadezimalzahlen, durch ein nachgestelltes b Dualzahlen und schließlich durch ein nachgestelltes o Oktalzahlen eingeben.

  1. Probieren Sie dies an Hand der Zahl 100 aus. Je nach gewählten Zahlensystem erscheint die 100 dann als solche, wenn Sie nach der Eingabe den jeweiligen Reiter des Zahlensystems wählen.

    Zusätzlich zu Kleinbuchstaben sind bei Jasmin auch Großbuchstaben bei der Zahlensystemmarkierung erlaubt. Bei Hexadezimalzahlen funktionieren die nachgestellten Buchstaben allerdings nur bei Zahlen, die keine Buchstaben enthalten. Es geht also z. B. 0xFFFF, aber nicht FFFFh.

  2. Versuchen Sie den Wert 100000 in das Register AX zu schreiben. Was passiert nun?

  3. Wie können Sie den Wert 100000 in das Akkumulatorregister schreiben?

  4. Als nächstes werden wir einen einfachen Zähler programmieren. Kopieren Sie den folgenden Code in Jasmin, aktivieren Sie die Binäransicht "bin" und führen Sie das Programm aus. Der Befehl inc inkrementiert den Inhalt des angegebenen Registers, d. h. erhöht den Registerwert um 1. Mit jedem inc wird hier also der Wert des Akkumulatorregisters um 1 erhöht. Jedes zweite Inkrementieren führt dabei zu einem Übertrag in die nächsthöhere Stelle, d. h. nach links, da das Dualsystem nur die beiden Ziffern 0 und 1 kennt.

    mov ax,0
    inc ax ; addiere 1 zu ax
    inc ax
    inc ax
    inc ax
    inc ax
    inc ax
    inc ax
    inc ax
    inc ax
    inc ax
    inc ax
  5. Aktivieren Sie danach die Dezimalansicht "dec" und führen Sie das Programm erneut aus. Hier entsteht beim Programmdurchlauf nur ein einzelner Übertrag in die nächsthöhere Stelle, da das Dezimalsystem 9 Ziffern kennt.

  6. Probieren Sie nun den Assemblerbefehl zur Multiplikation aus. Unabhängig vom gewählten Zahlensystem funktioniert der Stellenübertrag immer gleich. Wird z. B. 11 mit 100 multipliziert, so ist das Resultat eine Verschiebung um zwei Stellen nach links zu 1100, egal ob im Dezimalsystem oder in irgendeinem anderen Zahlensystem. Kopieren und starten Sie den folgenden Code, um dies zu überprüfen:

    mov ax,11
    mov bx,100
    mul bx
    
    mov ax,11h
    mov bx,100h
    mul bx
    
    mov ax,11b
    mov bx,100b
    mul bx

    Wenn Sie den zum jeweiligen Zahlensystem gehörenden Reiter wählen, werden Sie sehen, dass das Ergebnis immer das gleiche ist.

  7. Zu welcher Klasse von Befehlen gehören inc und mul?

  8. Laden Sie nun den Dezimalwert 1000 in das AX-Register und multiplizieren Sie diesen danach mit dem Dezimalwert 35. Das Ergebnis 35000 sollte im AX-Register angezeigt werden. Multiplizieren Sie dieses Ergebnis danach mit dem Dezimalwert 3. Stellen Sie einen Unterschied hinsichtlich der Darstellung des Ergebnisses fest? Falls ja: welchen?
    Schalten Sie die Hexadezimalansicht der Registerwerte ein und starten Sie zum Vergleich den Taschenrechner des Windowssystems (Start > Alle Programme > Zubehör > Rechner) und schalten Sie die Ansicht für Programmierer ein (Ansicht > Programmierer). Geben Sie 105000 ein und schalten Sie auch hier mit Hex die hexadezimale Darstellung ein. Vergleichen Sie das Ergebnis mit den Inhalten der Allzweckregister.

  9. Wiederholen Sie die Multiplikationen mit den 32-Bit-Registern. Was passiert nun und warum?

  10. Als nächstes wenden wir uns der Division zu. Teilen Sie 1000 im AX-Register durch 35 im BX-Register. Wie wird die Lösung dargestellt und warum ist dies so?

  11. Teilen Sie danach 1000 im AX-Register durch 35 im BL-Register. Wie wird die Lösung dargestellt und warum ist dies so?

  12. Teilen Sie schließlich 1000 im AX-Register durch 35 im BH-Register. Gibt es hier einen Unterschied zur Lösung der vorherigen Aufgabe?


Aufgabe 3: Flag-Register

Das wichtigste Instrument zur Kontrolle des Ablaufs arithmetischer Operationen ist das Flag-Register, da mit seiner Hilfe, z. B. bei arithmetischen Operationen, Zahlenbereichsüberläufe und auch -wechsel festgestellt werden können. Dies werden wir nun an Hand einiger Beispiele ausprobieren.

Die Bits bzw. Flags des Flag-Registers sind in die beiden Gruppen der Control Flags ("Steuerzeichen") und Status Flags ("Zustandszeichen") aufgeteilt. Mit Hilfe der Steuerzeichen kann der Rechner in bestimmte Betriebsmodi überführt werden. Zu den Steuerzeichen gehört beispielsweise das Interrupt-Flag, welches bei Aktivierung die schrittweise Ausführung eines Programms erlaubt. Steuerzeichen werden explizit aktiviert oder deaktiviert und behalten bis zur nächsten Änderung ihren Wert.

Zustandszeichen hingegen ändern sich laufend als Folge der gerade durchgeführten Operation. Zu den wichtigsten Zustandszeichen bzw. Status Flags gehören Carry, Overflow, Sign und Zero.

  1. Geben Sie in Jasmin den folgenden Code ein:

    mov ax,0xFFFF
    add ax,1

    Ausführen des mov-Befehls setzt zunächst alle Bits des AX-Registers auf 1 (warum?). Die Flags im Flag-Register bleiben davon unberührt. Der nachfolgende Befehl hat dann eine Reihe von Änderungen zur Folge. Zunächst werden alle Bits von AX auf 0 gesetzt, da die Summe nicht mehr in das AX-Register passt. Es wäre ein 17. Bit erforderlich, um den letzten Übertrag aufzunehmen. Dieses 17. Bit existiert nicht in AX. Es existiert aber in gewisser Weise schon: in Form des Carry-Flags im Statusregister. Der letzte Übertrag wandert also in das Carry-Bit des Statusregisters. Deswegen ist dieses nach der zweiten Operation gesetzt. Daneben sind allerdings noch zwei weitere Bits gesetzt: das Zero-Bit und das Parity-Bit. Das Zero-Bit ist auf 1 gesetzt, weil der Inhalt des AX-Registers nun gleich 0 ist. Das gesetzte Parity-Bit zeigt hingegen an, dass der Inhalt des AX-Registers nun eine gerade Parität besitzt (wann besaß ein Binärwort gerade Parität?).

  2. Führen Sie noch einmal schrittweise den Code des einfachen Zählers aus und betrachten Sie dabei die Änderungen des Parity-Bits.

  3. Führen Sie auch den folgenden Code aus. Schalten Sie zuvor in die expandierte Ansicht des AX-Registers (Button ...) und die bin-Darstellung. Betrachten Sie bei der Ausführung den Registerinhalt und das Zero-Bit:

    mov ax,0xFFFC
    inc al
    inc al
    inc al
    inc al
    inc al
    inc al

    Das Zero-Bit wird offenbar auch dann auf 1 gesetzt, wenn nur ein Teil des Registers den Wert 0 enthält, sofern die vorhergehende Operation sich nur auf einen Teil des Registers bezog.

  4. Welchen Wert wird das Zero-Bit nach folgender Operation besitzen: sub ax,ax?

  5. Bei dem Beispiel

    mov ax,0xFFFF
    add ax,1

    sahen Sie, dass ein Übertrag entstand, der im Carry-Flag landete, da er im AX-Register keinen Platz mehr fand. Das gesetzte Carry-Flag signalisierte also, dass ein Übertrag aus der größten Stelle entstanden und die Rechnung damit ungültig war. Es stellt sich nun die Frage, wie groß Überträge ganz allgemein werden können? Tatsächlich ist es so, dass ein Übertrag in die nächsthöhere Stelle nie mehr als 1 sein kann, unabhängig von der Größe der addierten Zahlen und vom gewählten Zahlensystem. Es ist also immer eine 1, die in die nächsthöhere Stelle oder eventuell in das Carry-Bit rutscht, selbst dann, wenn maximal mögliche Zahlenwerte, wie z. B. 999+999, addiert werden.

    Probieren Sie die folgenden Codesegmente aus, um dies zu bestätigen:

    mov ax,999
    mov bx,999
    add ax,bx
    
    mov ax,0xFFF
    mov bx,0xFFF
    add ax,bx
    
    mov ax,1111111b
    mov bx,1111111b
    add ax,bx

    Schalten Sie dazu in die zum jeweiligen Zahlensystem passende Ansicht.


Aufgabe 4: Polynomauswertung

Programmieren Sie in Jasmin das in der Vorlesung behandelte Beispiel zur Polynomauswertung. Wenn Sie alles richtig gemacht haben, sollte das im AX-Register angezeigte dezimale Ergebnis 342 lauten.