Table of Contents

Arithmetische Grundschaltungen mit FPGA und VHDL

Zurück zur Themenübersicht

Aufgabenstellung

Zahlen werden addiert und in Hexadezimaldarstellung auf den 7-Segmentanzeigen dargestellt. Die Zahlen werden vom Zweierkomplement in eine Betrags- Vorzeichendarstellung gewandelt und so verständlich angezeigt.

Vorbereitung

VHDL toplevel top_hex

In der Datei top_hex.vhd ist die höchste Hierarchie (toplevel) auf dem FPGA mit den Eingängen SW und den Ausgängen LEDR, HEX0, HEX1, HEX2, HEX3 dargestellt.

Abb. 1: Toplevel top_hex

Die HEXn Ausgänge steuern 7-Segmentanzeigen wie in Abbildung 2 an. Jedes einzelne Segment ist aus einer Leuchtdiode aufgebaut und kann einzeln ein- und ausgeschaltet werden. Zusammen bilden sie eine Darstellung einer Ziffer oder eines Buchstabens. Es gibt vier 7-Segmentanzeigen auf dem Altera Board.

Abb. 2: 7-Segmentanzeige mit den Namen der Segmente

Die Zuordnung ist HEXn[6..0] = GFEDCBA. Dabei ist Logik negativ, d.h. wenn ein Segment mit '0' angesteuert wird, dann leuchtet es. Mit “1111110” wird also das oberste Segment “A” leuchten und alle anderen Segmente sind aus.

In top_hex werden die Schalter SW[9..5] und SW[4..0] jeweils als Zahlen interpretiert und addiert. Das Ergebnis der Addition wird in mit einer Schaltung “bin2seg” in eine Ansteuerung für eine 7-Segmentanzeige umgewandelt. So können an den Schaltern zwei Summanden festgelegt werden. Das Additionsergebnis wird als Hexadezimalzahl an HEX1 und HEX0 angezeigt.

Arithmetische Operationen mit Package ieee.numeric_std

In top_hex werden die Signale sa, sb und sum als Arrays vom Typ “signed” angelegt. Dieser ist ähnlich wie “std_ulogic_vector”, aber für diesen Typen sind arithmetische Operationen wie die Addition definiert.

architecture rtl of top_hex is
  signal sa : signed(4 downto 0);
  signal sb : signed(4 downto 0);
  signal sum : signed(4 downto 0);
begin
sa <= signed(SW(4 downto 0));
sb <= signed(SW(9 downto 5));
sum <= sa + sb;
...

Signale vom Typ “std_ulogic_vector” muss man bei der Zuweisung nach “signed” Typwandeln (casten). Zurück geht der Typecast analog. Mit diesem Code baut man einen 5-Bit Addierer.

Weiter unten im Code wird der Vergleich “sa > -1” gemacht. “sa” ist vom Typ signed und die Konstante “-1” ist vom Typ integer. Solche arithmetischen Vergleiche sind im numeric_std Paket für die Typen “signed” und “unsigned” definiert. Das Ergebnis des Vergleichs wird dann im conditional signal assignment für HEX2 verwendet.

HEX2 <= "1111111" when sa > -1 else "0000000";

Wenn die Zahl an den Schaltern SW[4..0] größer als -1 ist, dann bleiben alle Segmente von HEX2 aus. Ansonsten werden alle Segmente eingeschaltet.

Instantiierung von bin2seg

In top_hex ist die Schaltung “bin2seg” aus der Datei bin2hex.vhd zweimal instantiiert.

Abb. 3: bin2seg erzeugt die Ansteuerung einer 7-Segmentanzeige als Hexadezimalzahl

Wie in Abbildung 3 dargestellt, hat “bin2seg” einen 4 Bit breiten Eingang “bin_i” und einen 7 Bit breiten Ausgang “seg_o”. Diese Schaltung wandelt eine binäre 4 Bit vorzeichenlose Zahl, die an dem Eingang “bin_i” anliegt, in eine Ansteuerung für eine 7-Segmentanzeige um. Die Zahl wird dort als Hexadezimalzahl dargestellt.

bin2seg_i0: entity work.bin2seg
 port map(
    bin_i => std_ulogic_vector(sum(3 downto 0)),
    seg_o => HEX0
);

Der Codeteil aus “top_hex.vhd” instantiiert die Schaltung bin2seg. Die Instanz hat den Namen “bin2seg_i0”. Der Eingang “bin_i” wird (mit einem Typecast von “signed” nach “std_ulogic_vector”) an das Signal “sum” angeschlossen. Der Ausgang “seg_o” wird mit dem Ausgangsport des Toplevels “HEX0” verbunden.

bin2seg_i1: entity work.bin2seg
 port map(
    bin_i => "000" & std_ulogic(sum(4)),
    seg_o => HEX1
);

Mit diesem Code wird die zweite Instanz “bin2seg_i1” instantiiert und angeschlossen. Das fünfte Bit aus dem Ergebnis der Addition wird zunächst in “std_ulogic” gecastet. Dann werden links drei Nullen angehängt und das Ergebnis wird mit dem Eingang “bin_i” verbunden. Der Ausgang seg_o wird mit der 7-Segmentanzeige “HEX1” verbunden. Mit jeder 7-Segmentanzeige können im Hexadezimalsystem 4 Bit als Ziffern 0-F dargestellt werden. Bei 5 Bit braucht man eine zweite HEX Ziffer. Auf HEX1 werden also die Ziffern 0 und 1 dargestellt, weil bin_i entweder “0000” oder “0001” ist.

Aufgaben

HEX3 und HEX2

Erweitern Sie den Code, damit auch an HEX3 und HEX2 die Summe als Hexadezimalwert dargestellt wird.

+ und - Anzeige

Die Schalter SW[4..0] und SW[9..5] repräsentieren Zahlen im Zweierkomplement. Die Anzeige funktioniert aber als vorzeichenlose Zahl im Hexadezimalformat. Wandeln Sie die Schaltung so ab, dass die Anzeige in der üblichen Form aus dem Dezimalsystem erfolgt. Auf HEX0 soll der Betrag erscheinen. Auf HEX1 soll entweder nichts oder ein Minuszeichen erscheinen.

Zahlenbereich

Bei einer Darstellung im Zweierkomplement geht der Zahlenbereich von -16 bis +15. Die -16 lässt sich aber in der 4 Bit Betragsdarstellung nicht darstellen. Modifizieren Sie die Schaltung so, dass bei dem Ergebnis von -16 bei der Addition statt eines Minuszeichens an HEX1 ein “F” dargestellt wird.

Labor

Stellen Sie im Labor Ihre Ergebnisse vor