§ 2.6. Complete ALU8¶
ALU8 combines the arithmetic, logic, shift/rotate, comparison/select, and flag components into one eight-bit combinational unit. It supports 29 operations, a five-bit opcode, and an explicit carry input. Multiplication and division are not included.
| Component | Description | Structural | Behavioral |
|---|---|---|---|
ALU8ControlDecoder |
Decodes the five-bit opcode into local operation selectors, result-source enables, and an invalid-opcode flag | Yes | Yes |
ALU8ResultSelector |
Combines six enabled result sources into the final eight-bit result | Yes | Yes |
ALU8 |
Integrates the operation units, control decoder, result selector, and flags behind one input/output interface | Yes | Yes |
These columns indicate registered simulator implementations; the simplified C++ examples below are not counted.
The simplified C++ examples describe binary behavior, not the simulator implementation; they omit propagation delays and X/Z handling. The complete ALU example uses the functions from §§2.1–2.5.
2.6.1. ALU8ControlDecoder¶
This block translates the complete ALU opcode into local selectors and result/flag enables. It does not compute operand data.
IO pins¶
| Pin | Direction | Width | Description |
|---|---|---|---|
OP |
Input | 5 | Complete ALU opcode |
LOCAL_OP |
Output | 3 | OP[2:0], used by logic and shift units |
ARITH_OP |
Output | 3 | Arithmetic selector; forced to local SUB = 2 during comparisons |
COMPARE_OP |
Output | 3 | Comparison selector, 0–6 for global opcodes 21–27; otherwise 0 |
ARITHMETIC_ENABLE, LOGIC_ENABLE, SHIFT_ENABLE, COMPARE_ENABLE |
Output | 1 each | Enable the corresponding result source |
PASS_A_ENABLE, PASS_B_ENABLE |
Output | 1 each | Enable operand pass-through |
INVALID_OP |
Output | 1 | Reserved opcode indication |
Behavior¶
For binary OP, arithmetic is enabled for 0–6, logic for 8–14, shifts for 16–20, comparisons for 21–27, and operand pass-through for 28 or 29. At most one result enable is high. CLEAR = 30 and reserved encodings 7, 15, 31 disable every result source; only the reserved encodings set INVALID_OP.
During comparisons, ARITH_OP = 2 requests the shared subtraction, but ARITHMETIC_ENABLE = 0: its intermediate result and flags must not be exposed as the final ALU result and flags. Outside comparisons, ARITH_OP = OP[2:0]. Unused local selectors are not forced to zero except COMPARE_OP.
C++ example¶
#include <cstdint>
#include <stdexcept>
struct ALU8Control {
std::uint8_t LOCAL_OP, ARITH_OP, COMPARE_OP;
bool ARITHMETIC_ENABLE, LOGIC_ENABLE, SHIFT_ENABLE, COMPARE_ENABLE;
bool PASS_A_ENABLE, PASS_B_ENABLE, INVALID_OP;
};
ALU8Control alu8_control_ref(std::uint8_t op) {
if (op > 31) throw std::invalid_argument("OP must fit five bits");
const bool compare = op >= 21 && op <= 27;
return {
static_cast<std::uint8_t>(op & 7),
static_cast<std::uint8_t>(compare ? 2 : op & 7),
static_cast<std::uint8_t>(compare ? op - 21 : 0),
op <= 6, op >= 8 && op <= 14, op >= 16 && op <= 20, compare,
op == 28, op == 29, op == 7 || op == 15 || op == 31
};
}
Unknown inputs and timing¶
Unknown opcode bits follow the decoder and gates. INVALID_OP does not indicate whether all input bits are binary. The block has no clock or stored state; control outputs can change at different propagation times.
Implementation¶
Structural implementation¶
OPERATION_DECODER is a Decoder5to32 with its enable tied high. OR networks combine decoded lines into group enables and the invalid flag. A splitter/joiner forwards the low three bits; three Mux2to1 gates override the arithmetic selector during comparisons. OR networks remap comparison opcodes to local selectors.
Behavioral implementation¶
Behavioral8<ALU8ControlDecoder> calls control. It evaluates all 32 opcode matches with four-state logic, combines them into group enables and INVALID_OP, and constructs the local selectors. LOCAL_OP directly copies OP[2:0], preserving Z as wiring does; the other outputs pass through logic expressions.
The evaluator is defined in ALU8Behavioral.cpp; its value functions are in ALU8ValueModel.hpp. It retains the public pins without functional circuit children. Catalog construction supplies a delay table characterized from the gates; where a delay twin is available and agrees with the computed value, publication can follow the current inputs’ gate-level settling time within that bound, subject to older pending results. The compact evaluator does not reproduce transient gate glitches.
The recorded scenario runs against both implementations in CTest. ALU8FidelityContractTest checks binary/X/Z settled-output equivalence against the structural circuit. The example table uses the default structural run; its checkpoint times need not match the behavioral run.
Examples¶
All 32 recorded rows of ALU8ControlDecoderTest, in checkpoint order. Outputs are test expectations verified against the simulation. Time is the absolute settled checkpoint time in simulator units, not milliseconds or CPU cycles.
Default scenario profile: canonical-default-preview / structural (b9bfd586b0cd37b5). Changing fidelity or the circuit can change these times.
| Checkpointzero-based number · timeline label | Timesimulator units | OPInput · 5 bit |
ARITHMETIC_ENABLEExpected output · 1 bit |
ARITH_OPExpected output · 3 bit |
COMPARE_ENABLEExpected output · 1 bit |
COMPARE_OPExpected output · 3 bit |
INVALID_OPExpected output · 1 bit |
LOCAL_OPExpected output · 3 bit |
LOGIC_ENABLEExpected output · 1 bit |
PASS_A_ENABLEExpected output · 1 bit |
PASS_B_ENABLEExpected output · 1 bit |
SHIFT_ENABLEExpected output · 1 bit |
|---|---|---|---|---|---|---|---|---|---|---|---|---|
#0row-0 | 12 | 0x00 |
1 |
0x0 |
0 |
0x0 |
0 |
0x0 |
0 |
0 |
0 |
0 |
#1row-1 | 19 | 0x01 |
1 |
0x1 |
0 |
0x0 |
0 |
0x1 |
0 |
0 |
0 |
0 |
#2row-2 | 26 | 0x02 |
1 |
0x2 |
0 |
0x0 |
0 |
0x2 |
0 |
0 |
0 |
0 |
#3row-3 | 34 | 0x03 |
1 |
0x3 |
0 |
0x0 |
0 |
0x3 |
0 |
0 |
0 |
0 |
#4row-4 | 45 | 0x04 |
1 |
0x4 |
0 |
0x0 |
0 |
0x4 |
0 |
0 |
0 |
0 |
#5row-5 | 53 | 0x05 |
1 |
0x5 |
0 |
0x0 |
0 |
0x5 |
0 |
0 |
0 |
0 |
#6row-6 | 60 | 0x06 |
1 |
0x6 |
0 |
0x0 |
0 |
0x6 |
0 |
0 |
0 |
0 |
#7row-7 | 67 | 0x07 |
0 |
0x7 |
0 |
0x0 |
1 |
0x7 |
0 |
0 |
0 |
0 |
#8row-8 | 80 | 0x08 |
0 |
0x0 |
0 |
0x0 |
0 |
0x0 |
1 |
0 |
0 |
0 |
#9row-9 | 87 | 0x09 |
0 |
0x1 |
0 |
0x0 |
0 |
0x1 |
1 |
0 |
0 |
0 |
#10row-10 | 94 | 0x0A |
0 |
0x2 |
0 |
0x0 |
0 |
0x2 |
1 |
0 |
0 |
0 |
#11row-11 | 102 | 0x0B |
0 |
0x3 |
0 |
0x0 |
0 |
0x3 |
1 |
0 |
0 |
0 |
#12row-12 | 113 | 0x0C |
0 |
0x4 |
0 |
0x0 |
0 |
0x4 |
1 |
0 |
0 |
0 |
#13row-13 | 121 | 0x0D |
0 |
0x5 |
0 |
0x0 |
0 |
0x5 |
1 |
0 |
0 |
0 |
#14row-14 | 128 | 0x0E |
0 |
0x6 |
0 |
0x0 |
0 |
0x6 |
1 |
0 |
0 |
0 |
#15row-15 | 135 | 0x0F |
0 |
0x7 |
0 |
0x0 |
1 |
0x7 |
0 |
0 |
0 |
0 |
#16row-16 | 146 | 0x10 |
0 |
0x0 |
0 |
0x0 |
0 |
0x0 |
0 |
0 |
0 |
1 |
#17row-17 | 153 | 0x11 |
0 |
0x1 |
0 |
0x0 |
0 |
0x1 |
0 |
0 |
0 |
1 |
#18row-18 | 160 | 0x12 |
0 |
0x2 |
0 |
0x0 |
0 |
0x2 |
0 |
0 |
0 |
1 |
#19row-19 | 168 | 0x13 |
0 |
0x3 |
0 |
0x0 |
0 |
0x3 |
0 |
0 |
0 |
1 |
#20row-20 | 179 | 0x14 |
0 |
0x4 |
0 |
0x0 |
0 |
0x4 |
0 |
0 |
0 |
1 |
#21row-21 | 193 | 0x15 |
0 |
0x2 |
1 |
0x0 |
0 |
0x5 |
0 |
0 |
0 |
0 |
#22row-22 | 208 | 0x16 |
0 |
0x2 |
1 |
0x1 |
0 |
0x6 |
0 |
0 |
0 |
0 |
#23row-23 | 216 | 0x17 |
0 |
0x2 |
1 |
0x2 |
0 |
0x7 |
0 |
0 |
0 |
0 |
#24row-24 | 229 | 0x18 |
0 |
0x2 |
1 |
0x3 |
0 |
0x0 |
0 |
0 |
0 |
0 |
#25row-25 | 237 | 0x19 |
0 |
0x2 |
1 |
0x4 |
0 |
0x1 |
0 |
0 |
0 |
0 |
#26row-26 | 245 | 0x1A |
0 |
0x2 |
1 |
0x5 |
0 |
0x2 |
0 |
0 |
0 |
0 |
#27row-27 | 253 | 0x1B |
0 |
0x2 |
1 |
0x6 |
0 |
0x3 |
0 |
0 |
0 |
0 |
#28row-28 | 267 | 0x1C |
0 |
0x4 |
0 |
0x0 |
0 |
0x4 |
0 |
1 |
0 |
0 |
#29row-29 | 273 | 0x1D |
0 |
0x5 |
0 |
0x0 |
0 |
0x5 |
0 |
0 |
1 |
0 |
#30row-30 | 279 | 0x1E |
0 |
0x6 |
0 |
0x0 |
0 |
0x6 |
0 |
0 |
0 |
0 |
#31row-31 | 285 | 0x1F |
0 |
0x7 |
0 |
0x0 |
1 |
0x7 |
0 |
0 |
0 |
0 |
Scroll within the table for all rows and pins. Buses use hexadecimal; values containing X/Z use MSB-first binary. Inputs show the declared values in effect at each checkpoint, including retained inputs. Sequential tests also replay preparation changes between checkpoints, such as lowering the clock. Use the matching checkpoint label in the simulation below.
Embedded simulation¶
All 32 binary opcodes are recorded, checking every output pin.
Open ALU8ControlDecoder in the simulator
Source and tests¶
- Interface:
ALU8ControlDecoder.hpp - Implementation:
ALU8ControlDecoder.cpp ALU8ControlDecoderTest: 32 recorded rows, exhaustive over binaryOP. Four-state integration cases remain inALU8ContractTest.
2.6.2. ALU8ResultSelector¶
This block combines six enabled data sources into one result bus. Its enable pins are independent; it is not a priority selector.
IO pins¶
| Pin | Direction | Width | Description |
|---|---|---|---|
ARITHMETIC_RESULT, LOGIC_RESULT, SHIFT_RESULT, COMPARE_RESULT |
Input | 8 each | Results from the operation units |
A, B |
Input | 8 each | Operand pass-through sources |
ARITHMETIC_ENABLE, LOGIC_ENABLE, SHIFT_ENABLE, COMPARE_ENABLE |
Input | 1 each | Enable the corresponding unit result |
PASS_A_ENABLE, PASS_B_ENABLE |
Input | 1 each | Enable operand pass-through |
OUT |
Output | 8 | Bitwise OR of the enabled sources |
Behavior¶
Each source is AND-masked by its enable, then the six masked words are OR-combined. With one enable high, OUT is that source. With all enables low, OUT = 0. Multiple enables produce the bitwise OR of those sources, not an error or a priority choice. The integrated decoder only generates zero-hot or one-hot enables for binary opcodes.
C++ example¶
The arrays use this order: arithmetic, logic, shift, comparison, A, B.
#include <array>
#include <cstdint>
std::uint8_t alu8_result_selector_ref(
const std::array<std::uint8_t, 6>& sources,
const std::array<bool, 6>& enables) {
std::uint8_t out = 0;
for (unsigned i = 0; i < sources.size(); ++i)
if (enables[i]) out |= sources[i];
return out;
}
Unknown inputs and timing¶
A low enable masks X/Z data. Active unknown data follows AND/OR gate rules; high impedance is not forwarded as high impedance through these gates. Unknown enables also follow gate rules rather than selecting an arbitrary input. There is no stored state or fixed cycle latency.
Implementation¶
Structural implementation¶
Six eight-bit splitters feed 48 AND gates, followed by 40 OR gates and one output joiner. No operation unit is clock-gated or stopped by these enables.
Behavioral implementation¶
Behavioral8<ALU8ResultSelector> calls select. For each output bit, it AND-masks each of the six source bits with its enable and OR-combines the contributions using four-state logic. Multiple enabled sources are combined, not prioritized; disabled unknown data is masked to zero.
The evaluator is defined in ALU8Behavioral.cpp; its value functions are in ALU8ValueModel.hpp. It retains the public pins without functional circuit children. Catalog construction supplies a delay table characterized from the gates; where a delay twin is available and agrees with the computed value, publication can follow the current inputs’ gate-level settling time within that bound, subject to older pending results. The compact evaluator does not reproduce transient gate glitches.
The recorded scenario runs against both implementations in CTest. ALU8FidelityContractTest checks binary/X/Z settled-output equivalence against the structural circuit. The example table uses the default structural run; its checkpoint times need not match the behavioral run.
Examples¶
All 66 recorded rows of ALU8ResultSelectorTest, in checkpoint order. Outputs are test expectations verified against the simulation. Time is the absolute settled checkpoint time in simulator units, not milliseconds or CPU cycles.
Default scenario profile: canonical-default-preview / structural (860d91a948498bdb). Changing fidelity or the circuit can change these times.
| Checkpointzero-based number · timeline label | Timesimulator units | AInput · 8 bit |
ARITHMETIC_ENABLEInput · 1 bit |
ARITHMETIC_RESULTInput · 8 bit |
BInput · 8 bit |
COMPARE_ENABLEInput · 1 bit |
COMPARE_RESULTInput · 8 bit |
LOGIC_ENABLEInput · 1 bit |
LOGIC_RESULTInput · 8 bit |
PASS_A_ENABLEInput · 1 bit |
PASS_B_ENABLEInput · 1 bit |
SHIFT_ENABLEInput · 1 bit |
SHIFT_RESULTInput · 8 bit |
OUTExpected output · 8 bit |
|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|
#0row-0 | 4 | 0x55 |
0 |
0x81 |
0xAA |
0 |
0x18 |
0 |
0x42 |
0 |
0 |
0 |
0x24 |
0x00 |
#1row-1 | 9 | 0x55 |
1 |
0x81 |
0xAA |
0 |
0x18 |
0 |
0x42 |
0 |
0 |
0 |
0x24 |
0x81 |
#2row-2 | 14 | 0x55 |
0 |
0x81 |
0xAA |
0 |
0x18 |
1 |
0x42 |
0 |
0 |
0 |
0x24 |
0x42 |
#3row-3 | 19 | 0x55 |
1 |
0x81 |
0xAA |
0 |
0x18 |
1 |
0x42 |
0 |
0 |
0 |
0x24 |
0xC3 |
#4row-4 | 24 | 0x55 |
0 |
0x81 |
0xAA |
0 |
0x18 |
0 |
0x42 |
0 |
0 |
1 |
0x24 |
0x24 |
#5row-5 | 29 | 0x55 |
1 |
0x81 |
0xAA |
0 |
0x18 |
0 |
0x42 |
0 |
0 |
1 |
0x24 |
0xA5 |
#6row-6 | 34 | 0x55 |
0 |
0x81 |
0xAA |
0 |
0x18 |
1 |
0x42 |
0 |
0 |
1 |
0x24 |
0x66 |
#7row-7 | 39 | 0x55 |
1 |
0x81 |
0xAA |
0 |
0x18 |
1 |
0x42 |
0 |
0 |
1 |
0x24 |
0xE7 |
#8row-8 | 44 | 0x55 |
0 |
0x81 |
0xAA |
1 |
0x18 |
0 |
0x42 |
0 |
0 |
0 |
0x24 |
0x18 |
#9row-9 | 49 | 0x55 |
1 |
0x81 |
0xAA |
1 |
0x18 |
0 |
0x42 |
0 |
0 |
0 |
0x24 |
0x99 |
#10row-10 | 54 | 0x55 |
0 |
0x81 |
0xAA |
1 |
0x18 |
1 |
0x42 |
0 |
0 |
0 |
0x24 |
0x5A |
#11row-11 | 59 | 0x55 |
1 |
0x81 |
0xAA |
1 |
0x18 |
1 |
0x42 |
0 |
0 |
0 |
0x24 |
0xDB |
#12row-12 | 64 | 0x55 |
0 |
0x81 |
0xAA |
1 |
0x18 |
0 |
0x42 |
0 |
0 |
1 |
0x24 |
0x3C |
#13row-13 | 69 | 0x55 |
1 |
0x81 |
0xAA |
1 |
0x18 |
0 |
0x42 |
0 |
0 |
1 |
0x24 |
0xBD |
#14row-14 | 74 | 0x55 |
0 |
0x81 |
0xAA |
1 |
0x18 |
1 |
0x42 |
0 |
0 |
1 |
0x24 |
0x7E |
#15row-15 | 79 | 0x55 |
1 |
0x81 |
0xAA |
1 |
0x18 |
1 |
0x42 |
0 |
0 |
1 |
0x24 |
0xFF |
#16row-16 | 84 | 0x55 |
0 |
0x81 |
0xAA |
0 |
0x18 |
0 |
0x42 |
1 |
0 |
0 |
0x24 |
0x55 |
#17row-17 | 89 | 0x55 |
1 |
0x81 |
0xAA |
0 |
0x18 |
0 |
0x42 |
1 |
0 |
0 |
0x24 |
0xD5 |
#18row-18 | 94 | 0x55 |
0 |
0x81 |
0xAA |
0 |
0x18 |
1 |
0x42 |
1 |
0 |
0 |
0x24 |
0x57 |
#19row-19 | 99 | 0x55 |
1 |
0x81 |
0xAA |
0 |
0x18 |
1 |
0x42 |
1 |
0 |
0 |
0x24 |
0xD7 |
#20row-20 | 104 | 0x55 |
0 |
0x81 |
0xAA |
0 |
0x18 |
0 |
0x42 |
1 |
0 |
1 |
0x24 |
0x75 |
#21row-21 | 109 | 0x55 |
1 |
0x81 |
0xAA |
0 |
0x18 |
0 |
0x42 |
1 |
0 |
1 |
0x24 |
0xF5 |
#22row-22 | 114 | 0x55 |
0 |
0x81 |
0xAA |
0 |
0x18 |
1 |
0x42 |
1 |
0 |
1 |
0x24 |
0x77 |
#23row-23 | 119 | 0x55 |
1 |
0x81 |
0xAA |
0 |
0x18 |
1 |
0x42 |
1 |
0 |
1 |
0x24 |
0xF7 |
#24row-24 | 124 | 0x55 |
0 |
0x81 |
0xAA |
1 |
0x18 |
0 |
0x42 |
1 |
0 |
0 |
0x24 |
0x5D |
#25row-25 | 129 | 0x55 |
1 |
0x81 |
0xAA |
1 |
0x18 |
0 |
0x42 |
1 |
0 |
0 |
0x24 |
0xDD |
#26row-26 | 134 | 0x55 |
0 |
0x81 |
0xAA |
1 |
0x18 |
1 |
0x42 |
1 |
0 |
0 |
0x24 |
0x5F |
#27row-27 | 139 | 0x55 |
1 |
0x81 |
0xAA |
1 |
0x18 |
1 |
0x42 |
1 |
0 |
0 |
0x24 |
0xDF |
#28row-28 | 144 | 0x55 |
0 |
0x81 |
0xAA |
1 |
0x18 |
0 |
0x42 |
1 |
0 |
1 |
0x24 |
0x7D |
#29row-29 | 149 | 0x55 |
1 |
0x81 |
0xAA |
1 |
0x18 |
0 |
0x42 |
1 |
0 |
1 |
0x24 |
0xFD |
#30row-30 | 154 | 0x55 |
0 |
0x81 |
0xAA |
1 |
0x18 |
1 |
0x42 |
1 |
0 |
1 |
0x24 |
0x7F |
#31row-31 | 159 | 0x55 |
1 |
0x81 |
0xAA |
1 |
0x18 |
1 |
0x42 |
1 |
0 |
1 |
0x24 |
0xFF |
#32row-32 | 164 | 0x55 |
0 |
0x81 |
0xAA |
0 |
0x18 |
0 |
0x42 |
0 |
1 |
0 |
0x24 |
0xAA |
#33row-33 | 169 | 0x55 |
1 |
0x81 |
0xAA |
0 |
0x18 |
0 |
0x42 |
0 |
1 |
0 |
0x24 |
0xAB |
#34row-34 | 174 | 0x55 |
0 |
0x81 |
0xAA |
0 |
0x18 |
1 |
0x42 |
0 |
1 |
0 |
0x24 |
0xEA |
#35row-35 | 179 | 0x55 |
1 |
0x81 |
0xAA |
0 |
0x18 |
1 |
0x42 |
0 |
1 |
0 |
0x24 |
0xEB |
#36row-36 | 184 | 0x55 |
0 |
0x81 |
0xAA |
0 |
0x18 |
0 |
0x42 |
0 |
1 |
1 |
0x24 |
0xAE |
#37row-37 | 189 | 0x55 |
1 |
0x81 |
0xAA |
0 |
0x18 |
0 |
0x42 |
0 |
1 |
1 |
0x24 |
0xAF |
#38row-38 | 194 | 0x55 |
0 |
0x81 |
0xAA |
0 |
0x18 |
1 |
0x42 |
0 |
1 |
1 |
0x24 |
0xEE |
#39row-39 | 199 | 0x55 |
1 |
0x81 |
0xAA |
0 |
0x18 |
1 |
0x42 |
0 |
1 |
1 |
0x24 |
0xEF |
#40row-40 | 204 | 0x55 |
0 |
0x81 |
0xAA |
1 |
0x18 |
0 |
0x42 |
0 |
1 |
0 |
0x24 |
0xBA |
#41row-41 | 209 | 0x55 |
1 |
0x81 |
0xAA |
1 |
0x18 |
0 |
0x42 |
0 |
1 |
0 |
0x24 |
0xBB |
#42row-42 | 214 | 0x55 |
0 |
0x81 |
0xAA |
1 |
0x18 |
1 |
0x42 |
0 |
1 |
0 |
0x24 |
0xFA |
#43row-43 | 219 | 0x55 |
1 |
0x81 |
0xAA |
1 |
0x18 |
1 |
0x42 |
0 |
1 |
0 |
0x24 |
0xFB |
#44row-44 | 224 | 0x55 |
0 |
0x81 |
0xAA |
1 |
0x18 |
0 |
0x42 |
0 |
1 |
1 |
0x24 |
0xBE |
#45row-45 | 229 | 0x55 |
1 |
0x81 |
0xAA |
1 |
0x18 |
0 |
0x42 |
0 |
1 |
1 |
0x24 |
0xBF |
#46row-46 | 234 | 0x55 |
0 |
0x81 |
0xAA |
1 |
0x18 |
1 |
0x42 |
0 |
1 |
1 |
0x24 |
0xFE |
#47row-47 | 239 | 0x55 |
1 |
0x81 |
0xAA |
1 |
0x18 |
1 |
0x42 |
0 |
1 |
1 |
0x24 |
0xFF |
#48row-48 | 244 | 0x55 |
0 |
0x81 |
0xAA |
0 |
0x18 |
0 |
0x42 |
1 |
1 |
0 |
0x24 |
0xFF |
#49row-49 | 249 | 0x55 |
1 |
0x81 |
0xAA |
0 |
0x18 |
0 |
0x42 |
1 |
1 |
0 |
0x24 |
0xFF |
#50row-50 | 254 | 0x55 |
0 |
0x81 |
0xAA |
0 |
0x18 |
1 |
0x42 |
1 |
1 |
0 |
0x24 |
0xFF |
#51row-51 | 259 | 0x55 |
1 |
0x81 |
0xAA |
0 |
0x18 |
1 |
0x42 |
1 |
1 |
0 |
0x24 |
0xFF |
#52row-52 | 264 | 0x55 |
0 |
0x81 |
0xAA |
0 |
0x18 |
0 |
0x42 |
1 |
1 |
1 |
0x24 |
0xFF |
#53row-53 | 269 | 0x55 |
1 |
0x81 |
0xAA |
0 |
0x18 |
0 |
0x42 |
1 |
1 |
1 |
0x24 |
0xFF |
#54row-54 | 274 | 0x55 |
0 |
0x81 |
0xAA |
0 |
0x18 |
1 |
0x42 |
1 |
1 |
1 |
0x24 |
0xFF |
#55row-55 | 279 | 0x55 |
1 |
0x81 |
0xAA |
0 |
0x18 |
1 |
0x42 |
1 |
1 |
1 |
0x24 |
0xFF |
#56row-56 | 284 | 0x55 |
0 |
0x81 |
0xAA |
1 |
0x18 |
0 |
0x42 |
1 |
1 |
0 |
0x24 |
0xFF |
#57row-57 | 289 | 0x55 |
1 |
0x81 |
0xAA |
1 |
0x18 |
0 |
0x42 |
1 |
1 |
0 |
0x24 |
0xFF |
#58row-58 | 294 | 0x55 |
0 |
0x81 |
0xAA |
1 |
0x18 |
1 |
0x42 |
1 |
1 |
0 |
0x24 |
0xFF |
#59row-59 | 299 | 0x55 |
1 |
0x81 |
0xAA |
1 |
0x18 |
1 |
0x42 |
1 |
1 |
0 |
0x24 |
0xFF |
#60row-60 | 304 | 0x55 |
0 |
0x81 |
0xAA |
1 |
0x18 |
0 |
0x42 |
1 |
1 |
1 |
0x24 |
0xFF |
#61row-61 | 309 | 0x55 |
1 |
0x81 |
0xAA |
1 |
0x18 |
0 |
0x42 |
1 |
1 |
1 |
0x24 |
0xFF |
#62row-62 | 314 | 0x55 |
0 |
0x81 |
0xAA |
1 |
0x18 |
1 |
0x42 |
1 |
1 |
1 |
0x24 |
0xFF |
#63row-63 | 319 | 0x55 |
1 |
0x81 |
0xAA |
1 |
0x18 |
1 |
0x42 |
1 |
1 |
1 |
0x24 |
0xFF |
#64row-64 | 324 | 0bXXXXXXXX |
0 |
0bXXXXXXXX |
0bXXXXXXXX |
0 |
0bXXXXXXXX |
0 |
0bXXXXXXXX |
0 |
0 |
0 |
0bXXXXXXXX |
0x00 |
#65row-65 | 327 | 0bZZZZZZZZ |
0 |
0bZZZZZZZZ |
0bZZZZZZZZ |
0 |
0bZZZZZZZZ |
0 |
0bZZZZZZZZ |
0 |
0 |
0 |
0bZZZZZZZZ |
0x00 |
Scroll within the table for all rows and pins. Buses use hexadecimal; values containing X/Z use MSB-first binary. Inputs show the declared values in effect at each checkpoint, including retained inputs. Sequential tests also replay preparation changes between checkpoints, such as lowering the clock. Use the matching checkpoint label in the simulation below.
The binary source words are 81, 42, 24, 18, 55, AA (hex), in the source-array order above; the final two rows use X/Z source words.
Embedded simulation¶
The scenario records all 64 enable combinations with these source words, then two all-disabled cases with every source set to X or Z. It contains 66 rows, not an exhaustive sweep over the six data buses.
Open ALU8ResultSelector in the simulator
Source and tests¶
- Interface:
ALU8ResultSelector.hpp - Implementation:
ALU8ResultSelector.cpp ALU8ResultSelectorTest: 66 recorded rows checking single-source selection, multi-enable OR behavior, and inactive unknown data.
2.6.3. ALU8¶
The caller supplies operands, an operation, and carry input. Opcode decoding, shared subtraction for comparisons, result selection, and flag selection are internal.
IO pins¶
| Pin | Direction | Width | Description |
|---|---|---|---|
A |
Input | 8 | First operand |
B |
Input | 8 | Second operand or shift/rotate distance |
OP |
Input | 5 | Complete ALU opcode |
C_IN |
Input | 1 | Carry/no-borrow input for ADC/SBC; carry source for zero-distance shifts/rotates |
OUT |
Output | 8 | Selected result |
ZERO |
Output | 1 | 1 when OUT is zero |
NEGATIVE |
Output | 1 | Bit 7 of a binary OUT |
CARRY |
Output | 1 | Arithmetic carry/no-borrow or shift/rotate carry; otherwise 0 |
OVERFLOW |
Output | 1 | Signed arithmetic overflow; otherwise 0 |
INVALID_OP |
Output | 1 | A reserved opcode is selected |
There is no clock, start, busy, valid/ready handshake, or stored status register. DIFF, CARRY_IN, and OVERFLOW_IN from CompareSelect8 are not external ALU pins.
Behavior¶
Operands and OUT are eight-bit patterns. Arithmetic wraps modulo 256; signed operations interpret a pattern as two's complement in −128–127. Let \(s(x)\) denote that signed interpretation and \(n=B\mathbin{\&}7\) the effective shift distance.
Opcode map¶
OP |
Operation | OUT |
|---|---|---|
0x00 |
ADD |
A + B |
0x01 |
ADC |
A + B + C_IN |
0x02 |
SUB |
A - B |
0x03 |
SBC |
A - B - (1 - C_IN) |
0x04 |
INC |
A + 1 |
0x05 |
DEC |
A - 1 |
0x06 |
NEG |
0 - A |
0x07 |
Reserved | 0x00; INVALID_OP = 1 |
0x08 |
AND |
A AND B, bitwise |
0x09 |
OR |
A OR B, bitwise |
0x0A |
XOR |
A XOR B, bitwise |
0x0B |
NOT |
Bitwise complement of A |
0x0C |
NAND |
Bitwise complement of A AND B |
0x0D |
NOR |
Bitwise complement of A OR B |
0x0E |
XNOR |
Bitwise complement of A XOR B |
0x0F |
Reserved | 0x00; INVALID_OP = 1 |
0x10 |
SLL |
Shift A left by n, zero fill |
0x11 |
SRL |
Shift A right by n, zero fill |
0x12 |
SRA |
Shift A right by n, sign fill |
0x13 |
ROL |
Rotate A left by n |
0x14 |
ROR |
Rotate A right by n |
0x15 |
EQ |
0x01 if A == B, otherwise 0x00 |
0x16 |
SLTU |
0x01 if unsigned A < B, otherwise 0x00 |
0x17 |
SLT |
0x01 if s(A) < s(B), otherwise 0x00 |
0x18 |
MINU |
Smaller unsigned operand |
0x19 |
MAXU |
Larger unsigned operand |
0x1A |
MINS |
Operand with smaller signed value |
0x1B |
MAXS |
Operand with larger signed value |
0x1C |
PASS_A |
A |
0x1D |
PASS_B |
B |
0x1E |
CLEAR |
0x00; INVALID_OP = 0 |
0x1F |
Reserved | 0x00; INVALID_OP = 1 |
Min/max operations return the original operand pattern, not a predicate or magnitude. Rotations operate on eight bits, not on a nine-bit word containing carry. The full operation details are in arithmetic, logic, shifts and rotations, and comparison and selection.
Flags and ignored inputs¶
ZERO = [OUT == 0] and NEGATIVE = OUT[7] for every binary result, including predicates and reserved operations. A false comparison therefore sets ZERO = 1; a true comparison returns 0x01 and sets ZERO = 0.
| Operation group | CARRY |
OVERFLOW |
|---|---|---|
Arithmetic (0x00–0x06) |
Carry-out for addition; 1 means no borrow for subtraction | Signed result before wrapping is outside −128–127 |
Shift/rotate (0x10–0x14), n > 0 |
Last bit shifted/rotated out | 0 |
Shift/rotate (0x10–0x14), n = 0 |
C_IN |
0 |
| Logic, comparison, min/max, pass, clear, reserved | 0 | 0 |
The arithmetic flag rules for INC, DEC, and NEG are specified in 2.1. In particular, NEG sets carry only for A = 0; this ALU uses the no-borrow convention consistently.
For known opcodes, ignored inputs are isolated from the settled outputs:
Bis ignored byINC,DEC,NEG,NOT, andPASS_A.Ais ignored byPASS_B; both operands are ignored byCLEARand reserved operations.- Shifts and rotations ignore
B[7:3], even when those bits are unknown. C_INis used only byADC,SBC, and zero-distance shifts/rotates. In particular, ordinary subtraction and all comparisons ignore it.
Reserved opcodes produce OUT = 0, ZERO = 1, NEGATIVE = CARRY = OVERFLOW = 0, and INVALID_OP = 1. CLEAR produces the same result and flags except INVALID_OP = 0. For a supported, known opcode, INVALID_OP = 0 even when an operand is unknown or arithmetic overflows.
C++ example¶
This example composes the functions from 2.1, 2.2, 2.3, 2.4, and 2.5. Compile those C++ examples first, in chapter order.
struct ALU8Result {
std::uint8_t OUT;
bool ZERO;
bool NEGATIVE;
bool CARRY;
bool OVERFLOW;
bool INVALID_OP;
};
ALU8Result alu8_ref(
std::uint8_t a, std::uint8_t b, std::uint8_t op, bool c_in) {
const bool arithmetic = op <= 0x06;
const bool logic = op >= 0x08 && op <= 0x0E;
const bool shift = op >= 0x10 && op <= 0x14;
const bool comparison = op >= 0x15 && op <= 0x1B;
const bool transfer = op >= 0x1C && op <= 0x1E;
const bool invalid = !(arithmetic || logic || shift || comparison || transfer);
std::uint8_t out = 0;
bool arith_carry = false, arith_overflow = false, shift_carry = false;
if (arithmetic || comparison) {
const auto local_op = static_cast<std::uint8_t>(comparison ? 2 : op);
const auto r = arithmetic8_ref(a, b, local_op, c_in);
arith_carry = r.CARRY;
arith_overflow = r.OVERFLOW;
out = comparison
? compare_select8_ref(a, b, r.OUT, r.CARRY, r.OVERFLOW,
static_cast<std::uint8_t>(op - 0x15))
: r.OUT;
} else if (logic) {
out = logic8_ref(a, b, static_cast<std::uint8_t>(op - 0x08));
} else if (shift) {
const auto r = shift8_ref(a, b, static_cast<std::uint8_t>(op - 0x10), c_in);
out = r.OUT;
shift_carry = r.CARRY;
} else if (op == 0x1C) {
out = a;
} else if (op == 0x1D) {
out = b;
}
const auto f = flags8_ref(out, arithmetic, shift,
arith_carry, arith_overflow, shift_carry);
return {out, f.ZERO, f.NEGATIVE, f.CARRY, f.OVERFLOW, invalid};
}
op represents a five-bit binary pin. Out-of-range integer arguments also return the invalid-operation result; they are not masked into an unrelated valid opcode. The example skips inactive computations for clarity, whereas the structural circuit can evaluate them and masks their outputs.
Unknown inputs and timing¶
The structural gates determine four-state behavior; the C++ example does not. Known operation selection masks inactive result paths, so unknown data in an unused path does not automatically make OUT unknown. For example, CLEAR and reserved opcodes still produce their defined zero result with unknown data and carry inputs, and AND with an all-zero operand produces zero despite unknown bits in the other operand.
An X/Z bit that affects the selected computation follows its gates' propagation rules. ZERO can be unknown for a partially unknown result with no known 1. A high-impedance operand bit passing through logic is treated as unknown, not preserved as a high-impedance output.
An opcode containing X or Z is not automatically a reserved encoding. Decoder and selection gates determine the outputs; INVALID_OP is not an input-validity checker. The contract test specifically checks that an entirely unknown/high-impedance opcode produces INVALID_OP = X, without asserting a complete output word for that case.
In structural fidelity, all operation paths are combinational and may change while gates settle. There is no fixed instruction-cycle count, atomic result/flag update, or declared worst-case structural ALU8 latency. Recorded checkpoints inspect settled results; intermediate timeline positions can show propagation through the decoder, carry chain, result selector, and flags. Catalog-selected behavioral fidelity uses delays characterized from the gate network. Its delay twin can time the current operation and operands, while the proven per-path table bounds publication when the twin cannot answer. It does not reproduce intermediate gate glitches.
Implementation¶
Structural implementation¶
| Internal component or network | Responsibility |
|---|---|
CONTROL (ALU8ControlDecoder) |
Decode the opcode into local selectors, enables, and the invalid flag |
ARITHMETIC (ArithmeticUnit8) |
Seven arithmetic operations and shared subtraction for comparisons |
LOGIC (LogicUnit8) |
Seven bitwise operations |
SHIFTER (BarrelShifter8) |
Three shifts and two rotations |
COMPARE_SELECT (CompareSelect8) |
Interpret subtraction data/flags and select predicates or operands |
RESULT_SELECT (ALU8ResultSelector) |
Select and assemble the final eight-bit word |
FLAGS (ALU8FlagUnit) |
Derive zero/sign and select carry/overflow |
In the default structural profile there is exactly one AddSub8, containing one Adder8 and eight FullAdder components, in the complete ALU hierarchy. Each of the seven operation units can independently switch between structural and behavioral fidelity. Nested AddSub8, Adder8, and ZeroDetect8 units are also selectable. A structural root with all seven units set to behavioral has eight components; a behavioral root has one. Structural8Builder is only a construction/wiring helper.
The five-bit opcode is translated to each unit's three-bit local selector:
| Selected group | Local operation | Result source |
|---|---|---|
| Arithmetic | OP[2:0] |
ARITHMETIC.OUT |
| Logic | OP[2:0] |
LOGIC.OUT |
| Shift/rotate | OP[2:0] |
SHIFTER.OUT |
| Comparison/min/max | Arithmetic forced to local SUB = 2; comparison remapped to OP - 0x15 |
COMPARE_SELECT.OUT |
PASS_A, PASS_B |
No unit result selected | External A or B |
CLEAR, reserved |
No result source enabled | Zero from the masked result network |
For comparison operations, the same A and B drive both units. ARITHMETIC.OUT, CARRY, and OVERFLOW connect to COMPARE_SELECT.DIFF, CARRY_IN, and OVERFLOW_IN. This makes the comparison inputs consistent without requiring the caller to calculate them or adding a second subtractor. The arithmetic result/flag enable remains low during comparisons, even though the arithmetic unit is computing their intermediate subtraction.
The result network has six sources: arithmetic, logic, shift, comparison, A, and B. For each output bit, six AND gates mask these sources with decoded enables and five OR gates combine them. These enables select outputs; they do not stop inactive units from evaluating. The selected result feeds both OUT and FLAGS.RESULT. The top-level invalid flag comes from its own five-bit decoder, not from the arithmetic unit's local INVALID_OP.
Behavioral implementation¶
Behavioral8<ALU8> calls alu, which composes the four-state control, arithmetic, logic, shift, comparison, result-selection, and flag functions. Comparison inputs come from the same computed subtraction result and flags. Unlike the simplified C++ example, this evaluator computes the operation paths and masks their outputs, preserving the gate expressions' treatment of inactive and unknown inputs.
The evaluator is defined in ALU8Behavioral.cpp; its value functions are in ALU8ValueModel.hpp. It retains the public pins without functional circuit children. Catalog construction supplies a delay table characterized from the gates; where a delay twin is available and agrees with the computed value, publication can follow the current inputs’ gate-level settling time within that bound, subject to older pending results. The compact evaluator does not reproduce transient gate glitches.
The recorded scenario runs against both implementations in CTest. ALU8FidelityContractTest checks binary/X/Z settled-output equivalence against the structural circuit. The example table uses the default structural run; its checkpoint times need not match the behavioral run.
Examples¶
All 70 recorded rows of ALU8Test, in checkpoint order. Outputs are test expectations verified against the simulation. Time is the absolute settled checkpoint time in simulator units, not milliseconds or CPU cycles.
Default scenario profile: canonical-default-preview / structural (e35085b4ea551693). Changing fidelity or the circuit can change these times.
| Checkpointzero-based number · timeline label | Timesimulator units | AInput · 8 bit |
BInput · 8 bit |
C_INInput · 1 bit |
OPInput · 5 bit |
CARRYExpected output · 1 bit |
INVALID_OPExpected output · 1 bit |
NEGATIVEExpected output · 1 bit |
OUTExpected output · 8 bit |
OVERFLOWExpected output · 1 bit |
ZEROExpected output · 1 bit |
|---|---|---|---|---|---|---|---|---|---|---|---|
#0row-0 | 38 | 0x81 |
0x03 |
0 |
0x00 |
0 |
0 |
1 |
0x84 |
0 |
0 |
#1row-1 | 78 | 0x7F |
0x01 |
1 |
0x00 |
0 |
0 |
1 |
0x80 |
1 |
0 |
#2row-2 | 104 | 0x81 |
0x03 |
0 |
0x01 |
0 |
0 |
1 |
0x84 |
0 |
0 |
#3row-3 | 140 | 0x7F |
0x01 |
1 |
0x01 |
0 |
0 |
1 |
0x81 |
1 |
0 |
#4row-4 | 180 | 0x81 |
0x03 |
0 |
0x02 |
1 |
0 |
0 |
0x7E |
1 |
0 |
#5row-5 | 203 | 0x7F |
0x01 |
1 |
0x02 |
1 |
0 |
0 |
0x7E |
0 |
0 |
#6row-6 | 239 | 0x81 |
0x03 |
0 |
0x03 |
1 |
0 |
0 |
0x7D |
1 |
0 |
#7row-7 | 262 | 0x7F |
0x01 |
1 |
0x03 |
1 |
0 |
0 |
0x7E |
0 |
0 |
#8row-8 | 291 | 0x81 |
0x03 |
0 |
0x04 |
0 |
0 |
1 |
0x82 |
0 |
0 |
#9row-9 | 329 | 0x7F |
0x01 |
1 |
0x04 |
0 |
0 |
1 |
0x80 |
1 |
0 |
#10row-10 | 374 | 0x81 |
0x03 |
0 |
0x05 |
1 |
0 |
1 |
0x80 |
0 |
0 |
#11row-11 | 396 | 0x7F |
0x01 |
1 |
0x05 |
1 |
0 |
0 |
0x7E |
0 |
0 |
#12row-12 | 438 | 0x81 |
0x03 |
0 |
0x06 |
0 |
0 |
0 |
0x7F |
0 |
0 |
#13row-13 | 461 | 0x7F |
0x01 |
1 |
0x06 |
0 |
0 |
1 |
0x81 |
0 |
0 |
#14row-14 | 487 | 0x81 |
0x03 |
0 |
0x07 |
0 |
1 |
0 |
0x00 |
0 |
1 |
#15row-15 | 500 | 0x7F |
0x01 |
1 |
0x07 |
0 |
1 |
0 |
0x00 |
0 |
1 |
#16row-16 | 526 | 0x81 |
0x03 |
0 |
0x08 |
0 |
0 |
0 |
0x01 |
0 |
0 |
#17row-17 | 566 | 0x7F |
0x01 |
1 |
0x08 |
0 |
0 |
0 |
0x01 |
0 |
0 |
#18row-18 | 590 | 0x81 |
0x03 |
0 |
0x09 |
0 |
0 |
1 |
0x83 |
0 |
0 |
#19row-19 | 626 | 0x7F |
0x01 |
1 |
0x09 |
0 |
0 |
0 |
0x7F |
0 |
0 |
#20row-20 | 666 | 0x81 |
0x03 |
0 |
0x0A |
0 |
0 |
1 |
0x82 |
0 |
0 |
#21row-21 | 689 | 0x7F |
0x01 |
1 |
0x0A |
0 |
0 |
0 |
0x7E |
0 |
0 |
#22row-22 | 725 | 0x81 |
0x03 |
0 |
0x0B |
0 |
0 |
0 |
0x7E |
0 |
0 |
#23row-23 | 748 | 0x7F |
0x01 |
1 |
0x0B |
0 |
0 |
1 |
0x80 |
0 |
0 |
#24row-24 | 773 | 0x81 |
0x03 |
0 |
0x0C |
0 |
0 |
1 |
0xFE |
0 |
0 |
#25row-25 | 811 | 0x7F |
0x01 |
1 |
0x0C |
0 |
0 |
1 |
0xFE |
0 |
0 |
#26row-26 | 856 | 0x81 |
0x03 |
0 |
0x0D |
0 |
0 |
0 |
0x7C |
0 |
0 |
#27row-27 | 878 | 0x7F |
0x01 |
1 |
0x0D |
0 |
0 |
1 |
0x80 |
0 |
0 |
#28row-28 | 920 | 0x81 |
0x03 |
0 |
0x0E |
0 |
0 |
0 |
0x7D |
0 |
0 |
#29row-29 | 943 | 0x7F |
0x01 |
1 |
0x0E |
0 |
0 |
1 |
0x81 |
0 |
0 |
#30row-30 | 969 | 0x81 |
0x03 |
0 |
0x0F |
0 |
1 |
0 |
0x00 |
0 |
1 |
#31row-31 | 982 | 0x7F |
0x01 |
1 |
0x0F |
0 |
1 |
0 |
0x00 |
0 |
1 |
#32row-32 | 1011 | 0x81 |
0x03 |
0 |
0x10 |
0 |
0 |
0 |
0x08 |
0 |
0 |
#33row-33 | 1051 | 0x7F |
0x01 |
1 |
0x10 |
0 |
0 |
1 |
0xFE |
0 |
0 |
#34row-34 | 1083 | 0x81 |
0x03 |
0 |
0x11 |
0 |
0 |
0 |
0x10 |
0 |
0 |
#35row-35 | 1119 | 0x7F |
0x01 |
1 |
0x11 |
1 |
0 |
0 |
0x3F |
0 |
0 |
#36row-36 | 1159 | 0x81 |
0x03 |
0 |
0x12 |
0 |
0 |
1 |
0xF0 |
0 |
0 |
#37row-37 | 1182 | 0x7F |
0x01 |
1 |
0x12 |
1 |
0 |
0 |
0x3F |
0 |
0 |
#38row-38 | 1218 | 0x81 |
0x03 |
0 |
0x13 |
0 |
0 |
0 |
0x0C |
0 |
0 |
#39row-39 | 1241 | 0x7F |
0x01 |
1 |
0x13 |
0 |
0 |
1 |
0xFE |
0 |
0 |
#40row-40 | 1269 | 0x81 |
0x03 |
0 |
0x14 |
0 |
0 |
0 |
0x30 |
0 |
0 |
#41row-41 | 1307 | 0x7F |
0x01 |
1 |
0x14 |
1 |
0 |
1 |
0xBF |
0 |
0 |
#42row-42 | 1357 | 0x81 |
0x03 |
0 |
0x15 |
0 |
0 |
0 |
0x00 |
0 |
1 |
#43row-43 | 1380 | 0x7F |
0x01 |
1 |
0x15 |
0 |
0 |
0 |
0x00 |
0 |
1 |
#44row-44 | 1429 | 0x81 |
0x03 |
0 |
0x16 |
0 |
0 |
0 |
0x00 |
0 |
1 |
#45row-45 | 1460 | 0x7F |
0x01 |
1 |
0x16 |
0 |
0 |
0 |
0x00 |
0 |
1 |
#46row-46 | 1506 | 0x81 |
0x03 |
0 |
0x17 |
0 |
0 |
0 |
0x01 |
0 |
0 |
#47row-47 | 1538 | 0x7F |
0x01 |
1 |
0x17 |
0 |
0 |
0 |
0x00 |
0 |
1 |
#48row-48 | 1584 | 0x81 |
0x03 |
0 |
0x18 |
0 |
0 |
0 |
0x03 |
0 |
0 |
#49row-49 | 1618 | 0x7F |
0x01 |
1 |
0x18 |
0 |
0 |
0 |
0x01 |
0 |
0 |
#50row-50 | 1654 | 0x81 |
0x03 |
0 |
0x19 |
0 |
0 |
1 |
0x81 |
0 |
0 |
#51row-51 | 1688 | 0x7F |
0x01 |
1 |
0x19 |
0 |
0 |
0 |
0x7F |
0 |
0 |
#52row-52 | 1736 | 0x81 |
0x03 |
0 |
0x1A |
0 |
0 |
1 |
0x81 |
0 |
0 |
#53row-53 | 1771 | 0x7F |
0x01 |
1 |
0x1A |
0 |
0 |
0 |
0x01 |
0 |
0 |
#54row-54 | 1819 | 0x81 |
0x03 |
0 |
0x1B |
0 |
0 |
0 |
0x03 |
0 |
0 |
#55row-55 | 1854 | 0x7F |
0x01 |
1 |
0x1B |
0 |
0 |
0 |
0x7F |
0 |
0 |
#56row-56 | 1887 | 0x81 |
0x03 |
0 |
0x1C |
0 |
0 |
1 |
0x81 |
0 |
0 |
#57row-57 | 1925 | 0x7F |
0x01 |
1 |
0x1C |
0 |
0 |
0 |
0x7F |
0 |
0 |
#58row-58 | 1970 | 0x81 |
0x03 |
0 |
0x1D |
0 |
0 |
0 |
0x03 |
0 |
0 |
#59row-59 | 1992 | 0x7F |
0x01 |
1 |
0x1D |
0 |
0 |
0 |
0x01 |
0 |
0 |
#60row-60 | 2034 | 0x81 |
0x03 |
0 |
0x1E |
0 |
0 |
0 |
0x00 |
0 |
1 |
#61row-61 | 2057 | 0x7F |
0x01 |
1 |
0x1E |
0 |
0 |
0 |
0x00 |
0 |
1 |
#62row-62 | 2083 | 0x81 |
0x03 |
0 |
0x1F |
0 |
1 |
0 |
0x00 |
0 |
1 |
#63row-63 | 2096 | 0x7F |
0x01 |
1 |
0x1F |
0 |
1 |
0 |
0x00 |
0 |
1 |
#64row-64 | 2141 | 0xFF |
0x01 |
0 |
0x00 |
1 |
0 |
0 |
0x00 |
0 |
1 |
#65row-65 | 2181 | 0x00 |
0x00 |
0 |
0x06 |
1 |
0 |
0 |
0x00 |
0 |
1 |
#66row-66 | 2209 | 0x80 |
0x00 |
0 |
0x06 |
0 |
0 |
1 |
0x80 |
1 |
0 |
#67row-67 | 2245 | 0xFF |
0xFF |
0 |
0x03 |
0 |
0 |
1 |
0xFF |
0 |
0 |
#68row-68 | 2275 | 0x81 |
0x00 |
1 |
0x10 |
1 |
0 |
1 |
0x81 |
0 |
0 |
#69row-69 | 2303 | 0x81 |
0x08 |
1 |
0x14 |
1 |
0 |
1 |
0x81 |
0 |
0 |
Scroll within the table for all rows and pins. Buses use hexadecimal; values containing X/Z use MSB-first binary. Inputs show the declared values in effect at each checkpoint, including retained inputs. Sequential tests also replay preparation changes between checkpoints, such as lowering the clock. Use the matching checkpoint label in the simulation below.
The signed comparison and signed-minimum examples return different kinds of data: SLT returns a positive predicate word, while MINS returns the negative operand's original bits. Their NEGATIVE flags follow those output words, not the internal subtraction.
Embedded simulation¶
The alu8 scenario runs ALU8Test: two operand/carry sets for each of the 32 opcodes, followed by six targeted arithmetic and zero-distance shift/rotate cases, for 70 recorded rows. The top level contains exactly seven named blocks. Open the explorer to inspect CONTROL, ARITHMETIC, LOGIC, SHIFTER, COMPARE_SELECT, RESULT_SELECT, or FLAGS; their gates remain expandable and the timeline includes their actual propagation.
Source and tests¶
| Test | Coverage |
|---|---|
ALUHierarchyTest |
Checks the seven named top-level blocks in both ALUs and a single eight-/32-bit full-adder chain. Grouping does not reduce the number of gates. |
ALU8FidelityContractTest |
84,100 settled-output comparisons across all 11 Chapter 2 families, including every four-state zero-detector input, every four-state opcode, and every result-selector enable combination with sampled data. Also checks 13 mixed-fidelity profiles × 256 integrated inputs. These are not exhaustive over the full ALU's four-state input space. |
ALU8Test |
70 recorded binary rows; checks OUT and all five single-bit outputs. This is the embedded scenario. |
ALU8ContractTest: integrated binary checks |
5,184 boundary cases: 32 opcodes × nine A values × nine B values × both carry inputs, plus 2,048 seeded random cases. Checks all outputs against an independent integer oracle. |
ALU8ContractTest: structure and four-state checks |
Checks five-bit OP and exactly one AddSub8, one Adder8, and eight FullAdder instances. Adds 28 targeted X/Z cases for ignored inputs, masked results, partial unknown results, shifts, and unknown opcode indication. The two entirely unknown-opcode cases check only INVALID_OP. |
ALU8ContractTest: standalone sweeps |
262,144 AddSub8 cases and 20,480 valid BarrelShifter8 cases; these are separate lower-level circuits, not that many full-ALU rows. |
ALU8WasmParityTest.mjs |
Compares native and WASM portable topology, timestamps/checkpoint metadata, initial/final states, and expanded ALU topology for the recorded scenarios. This is not an independent arithmetic oracle or an every-timestamp state comparison. |
VisualizerWasmBrowserTest.py |
Checks the chapter embeds, scenario/type/row counts, accessible compact controls, and focus framing in an actual browser. |
The integrated contract sweep contains 7,260 cases, not an exhaustive sweep of all 4,194,304 binary A/B/OP/C_IN combinations. It disables history recording; the embedded simulation contains only the 70 recorded rows.
The component catalog identifies this interface as alu.width8, contract version 2. Its inputs include five-bit OP and C_IN; no four-bit-opcode compatibility mode is part of this contract. The ALU32 and RV32I ALU interfaces are separate contracts.