3 / 24 · Übung
Praktikum: Referenzmodell einer Acht-Bit-ALU
Prüfen Sie ADD, SUB, AND, XOR, Übertrag und Entlehnung in einem eigenständigen Programm.
Lektionen sind frei lesbar. Schreibe dich ein, um deinen Fortschritt zu speichern.
Die numerischen Verhaltensregeln ausführbar machen
Dieses Praktikum modelliert eine kombinatorische ALU mit ganzen Zahlen in JavaScript. Die Operanden reichen von 0 bis 255, die Operationen von 0 bis 3. Die Ausgabe y passt stets in acht Bits. Das Flag steht für den ADD-Übertrag oder die SUB-Entlehnung und ist bei logischen Operationen Null. In dieser Schnittstelle ist die Entlehnung eins, wenn a kleiner als b ist. Andere Architekturen können Subtraktionsflags anders definieren; unsere Festlegung ist ausdrücklich.
Erstellen Sie einen lokalen Ordner oder legen Sie in Digital Design Studio manuell ein leeres Projekt an und fügen Sie alu-model.mjs hinzu. Speichern Sie die folgende Datei. Wechseln Sie in einem Terminal mit installiertem Node.js in den Ordner und führen Sie node alu-model.mjs aus. Das Bearbeiten einer Datei in DDS und das Ausführen von JavaScript sind getrennte Aktionen. Es sind weder eine Paketinstallation noch eine automatische Importfunktion erforderlich.
import assert from 'node:assert/strict';
function alu(a, b, op) {
if (op === 0) {
const wide = a + b;
return { y: wide & 255, flag: Number(wide > 255) };
}
if (op === 1) return { y: (a - b) & 255, flag: Number(a < b) };
if (op === 2) return { y: a & b, flag: 0 };
if (op === 3) return { y: a ^ b, flag: 0 };
throw new RangeError('operation');
}
assert.deepEqual(alu(250, 10, 0), { y: 4, flag: 1 });
assert.deepEqual(alu(3, 5, 1), { y: 254, flag: 1 });
assert.deepEqual(alu(170, 204, 2), { y: 136, flag: 0 });
assert.deepEqual(alu(170, 204, 3), { y: 102, flag: 0 });
let checks = 0;
for (let a = 0; a < 256; a++) {
for (let b = 0; b < 256; b++) {
const add = alu(a, b, 0), sub = alu(a, b, 1);
assert.equal(add.y + 256 * add.flag, a + b);
assert.equal(sub.y - 256 * sub.flag, a - b);
assert.equal(alu(a, b, 2).y | alu(a, b, 3).y, a | b);
checks += 3;
}
}
console.log(`ALU PASS: ${checks} identities`);Für 250+10 rekonstruieren y=4 und carry=1 den Wert 260. Für 3-5 rekonstruieren y=254 und borrow=1 den Wert -2. Die Binärdarstellung von 170 lautet 10101010, die von 204 lautet 11001100: AND ergibt 136 und XOR ergibt 102. Die Schleife durchläuft alle 65536 Operandenpaare und prüft pro Paar drei Identitäten. Ein erfolgreicher Lauf meldet 196608 Prüfungen.
Verwenden Sie im Referenzmodell ein anderes Verfahren als im RTL. Wenn die Hardware den Übertrag aus einem Neun-Bit-Addierer gewinnt, prüft dieses Modell den mathematischen Wertebereich. Dadurch werden gemeinsame Implementierungsfehler reduziert. Diese Prüfungen untersuchen keine HDL-X/Z-Werte, Signallaufzeiten oder Taktverhalten. Verwenden Sie die Testvektoren bei der RTL-Implementierung erneut in einem Simulator. Vergleichen Sie immer die Flags ebenso wie die Daten; korrekte umlaufende Ergebnisbits können ein falsches Grenzflag verdecken.
Selbst ausprobieren
Welche numerische Identität schlägt fehl, wenn SUB immer flag=0 liefert? Prüfen Sie a=0, b=1 von Hand und stellen Sie die Implementierung wieder her.
Erklärung lesen
y ist 255. Mit flag=0 ergibt y-256×flag den Wert 255 statt -1, daher schlägt die Rekonstruktion der Subtraktion fehl. Mit borrow=1 gilt 255-256=-1. Eine alleinige Prüfung von y würde diesen Fehler übersehen.