🧮

The Hex Machine

8-Bit Assembly Trainer

Learn assembly language on a simulated 8-bit CPU. 24 instructions, 256 bytes of memory, 2 registers.

The Environment

Your Workbench

The Assembly Editor

The left side of the screen is your code editor. This is where you type assembly language mnemonics — short abbreviations like LDI, ADD, OUT, and HLT that represent instructions the CPU understands.

Each line holds one instruction. Some instructions need an argument (a number), some don't. The editor highlights your code and shows line numbers so you can track where you are.

The Memory View

The Mem view shows all 256 bytes of the CPU's memory, laid out in a grid. Each cell shows a two-digit hex value (00 to FF). When you assemble your code, you can watch the machine code bytes appear in memory. During execution, the current instruction is highlighted so you can follow along.

Memory addresses run from 00 (top-left) to FF (bottom-right). Your program starts at address 00 and grows upward. Data can be stored anywhere you like.

The Hex Keypad

Below the editor you'll find a hex keypad with keys 0-9 and A-F — the sixteen digits of the hexadecimal number system. Use this for entering hex values directly. There are also letter keys for typing mnemonics.

The Control Buttons

The Hex Converter

A built-in tool that converts between decimal, hexadecimal, and binary. Type a number in any format and see it in all three. Essential while you're learning to think in hex.

Example: type 42 in decimal and see that it's 2A in hex and 00101010 in binary.

The Registers Display

The registers panel shows the current state of the CPU at all times:

In Step mode, watch these values change with each instruction. This is the fastest way to understand what assembly code actually does.


Concepts

Understanding the CPU

What Is a Register?

A register is a tiny piece of memory built directly into the CPU. It's the fastest storage there is — the CPU can read and write registers in a single clock cycle.

The Hex Machine has two general-purpose registers, A and B. Each holds one byte — a number from 0 to 255 (or 00 to FF in hex). Most arithmetic happens in register A (which is why it's sometimes called the accumulator). Register B holds a second value when you need one.

+--------+ +--------+ | A | | B | | 1 byte | | 1 byte | | 00-FF | | 00-FF | +--------+ +--------+ The CPU's two working registers

What Is the Program Counter?

The Program Counter (PC) is a special register that holds the memory address of the next instruction to execute. When the CPU finishes one instruction, it looks at the PC to find the next one.

Normally the PC increments automatically — after executing the instruction at address 00, the PC moves to 01 (or 02, if the instruction was two bytes long). Jump instructions (JMP, JZ, JNZ, JC) change the PC to a completely different address, which is how you create loops and branches.

Memory: [LDI] [05] [OUT] [HLT] ... Address: 00 01 02 03 ^ | PC = 00 (next instruction to execute)

What Is Memory?

The Hex Machine has 256 bytes of memory, addressed from 00 to FF. That's it — your entire world. Your program lives in memory. Your data lives in memory. Everything is just bytes.

Each byte can hold a value from 0 to 255. A byte might be an instruction (like LDI), an argument to an instruction (like the number 05), or data your program stores. The CPU doesn't know the difference — it just executes whatever the PC points to.

Address: 00 01 02 03 04 05 ... FE FF Content: 10 05 20 00 -- -- ... -- -- ^^^^^ ^^^^^ LDI 5 OUT 0 (your program)

What Are Flags?

Flags are single-bit indicators that report what happened during the last operation. The Hex Machine has two flags:

Zero Flag (Z) — set to 1 when the result of an operation is exactly zero. For example, if register A holds 01 and you decrement it (DEC A), the result is 00, so the Zero flag is set. This is how the CPU knows when a countdown reaches zero.

Carry Flag (C) — set to 1 when an arithmetic operation overflows past 255 or underflows below 0. For example, 255 + 1 wraps around to 0 and sets the Carry flag. This is how the CPU detects overflow.

Flags are what make conditional jumps possible. JZ (Jump if Zero) only jumps when the Zero flag is set. JNZ (Jump if Not Zero) only jumps when it's clear. JC (Jump if Carry) only jumps on overflow. Without flags, the CPU could never make decisions.

The Fetch-Execute Cycle

Every CPU in every computer follows the same fundamental loop:

When you use Step mode, you're manually triggering one pass through this cycle. Each tap of Step runs exactly one fetch-decode-execute, then pauses so you can inspect the result.


Reference

Complete Instruction Set

Data Movement

MnemonicArgsDescription
NOPNo operation. Does nothing. Advances PC by 1.
LDA addr1 byteLoad register A from memory address. A = MEM[addr]
LDI val1 byteLoad immediate value into A. A = val
STA addr1 byteStore register A to memory address. MEM[addr] = A
LDB addr1 byteLoad register B from memory address. B = MEM[addr]
LBI val1 byteLoad immediate value into B. B = val
STB addr1 byteStore register B to memory address. MEM[addr] = B
MOV A,BCopy B into A. A = B (B unchanged)

Example: Load and store

LDI 42 ; Load hex 42 (decimal 66) into A STA F0 ; Store A's value to memory address F0 LDA F0 ; Load it back from memory into A

Arithmetic

MnemonicArgsDescription
ADDAdd B to A. A = A + B. Sets Zero and Carry flags.
SUBSubtract B from A. A = A - B. Sets Zero and Carry flags.
INCIncrement A by 1. A = A + 1. Sets Zero flag if result is 00.
DECDecrement A by 1. A = A - 1. Sets Zero flag if result is 00.
ADI val1 byteAdd immediate value to A. A = A + val. Sets flags.

Example: Add two numbers

LDI 03 ; A = 3 LBI 04 ; B = 4 ADD ; A = A + B = 7 OUT ; Display 07

Logic

MnemonicArgsDescription
ANDBitwise AND: A = A AND B
ORBitwise OR: A = A OR B
XORBitwise XOR: A = A XOR B
NOTBitwise NOT: A = NOT A (flips all bits)
SHLShift A left 1 bit. Equivalent to multiply by 2.
SHRShift A right 1 bit. Equivalent to divide by 2.

Example: Bitwise operations

LDI 0F ; A = 00001111 LBI F0 ; B = 11110000 AND ; A = 00000000 (no matching bits) ; Zero flag is set!

Compare & Branch

MnemonicArgsDescription
CMPCompare A and B (A - B) without storing result. Sets flags only.
JMP addr1 byteJump unconditionally. PC = addr.
JZ addr1 byteJump if Zero flag is set. Branch when last result was 0.
JNZ addr1 byteJump if Zero flag is NOT set. Branch when last result was not 0.
JC addr1 byteJump if Carry flag is set. Branch on overflow/underflow.

Example: Conditional branching

LDI 05 ; A = 5 LBI 05 ; B = 5 CMP ; Compare A and B: 5-5=0, Zero flag set JZ 10 ; Jump to address 10 (they're equal!)

I/O & Control

MnemonicArgsDescription
OUTOutput the value in register A to the display.
INPRead input into register A. Pauses for user input.
HLTHalt the CPU. Program stops executing.

Number Systems

Hexadecimal Explained

What Is Hex?

Hexadecimal (hex for short) is a base-16 number system. While decimal uses 10 digits (0-9), hex uses 16: 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, A, B, C, D, E, F.

A = 10, B = 11, C = 12, D = 13, E = 14, F = 15.

Why Do Computers Use Hex?

Computers work in binary (base-2), but binary numbers are long and hard for humans to read. The number 255 in binary is 11111111 — eight digits. In hex, it's just FF — two digits.

Hex is a compact way to represent binary. Each hex digit maps perfectly to exactly 4 binary digits (bits). Two hex digits represent one byte (8 bits). That's why hex is everywhere in low-level computing: it's human-friendly binary.

Hex to Decimal Conversion Table

HexDecimalBinary
00000000000
01100000001
05500000101
0A1000001010
0F1500001111
101600010000
1A2600011010
203200100000
2A4200101010
406401000000
6410001100100
8012810000000
C820011001000
FF25511111111

The Division Trick

To convert a decimal number to hex by hand, divide repeatedly by 16:

Convert 200 to hex: 200 / 16 = 12 remainder 8 12 / 16 = 0 remainder 12 (C) Read remainders bottom to top: C8 So 200 decimal = C8 hex

To go the other direction, multiply each hex digit by its place value:

Convert C8 hex to decimal: C = 12, so 12 x 16 = 192 8 = 8, so 8 x 1 = 8 Total: 192 + 8 = 200

Or just use the built-in Hex Converter. That's what it's there for.


Deep Dive

Hand Assembly

The Paper Worksheet Process

Before assemblers existed, programmers would convert assembly language to machine code by hand on paper. Here's how it works:

Step 1: Write your assembly program with addresses:

Addr Mnemonic Meaning ---- ---------- ------------------------- 00 LDI 05 Load 5 into A 02 OUT Display A 03 DEC Subtract 1 from A 04 JNZ 02 If not zero, jump to 02 06 HLT Stop

Step 2: Look up each mnemonic's hex opcode and write the machine code:

Addr Hex Source ---- ----- ---------- 00 10 05 LDI 05 02 20 OUT 03 15 DEC 04 22 02 JNZ 02 06 FF HLT

Step 3: The final machine code bytes, in order, are:

10 05 20 15 22 02 FF

That's seven bytes. That's your entire program. On the original hardware trainers, you'd toggle these bytes in one at a time using switches. With the Hex Machine, you type the assembly and the assembler does the conversion for you — but understanding the process helps you understand what's really happening.


Tutorials

Step-by-Step Walkthroughs

Tutorial 1: Hello Output

The simplest possible program — load a value and display it.

The code

LDI 42 OUT HLT

What each byte does

LDI 42 — this is two bytes in memory. The first byte is the LDI opcode (which tells the CPU "load the next byte into register A"). The second byte is 42 (the value to load). After this instruction, register A contains 42 (hex) which is 66 in decimal.

OUT — one byte. Tells the CPU to take whatever is in register A and send it to the output display. You'll see "42" appear.

HLT — one byte. Stops the CPU. Without this, the CPU would keep fetching bytes from memory and trying to execute whatever random data is there.

Try it

Type the three lines into the editor. Tap "Asm & Run." You'll see 42 on the output display. Now try changing 42 to FF, or 0A, or 01. Each time, the display shows the new value.

Step through it

Tap "Assemble" (not Asm & Run). Then tap "Step" three times. Watch the PC advance, register A fill with your value, and the output appear. This is the fetch-execute cycle in action.

Tutorial 2: Counting Down

A loop that counts from 5 down to 0, displaying each number.

The code

LDI 05 ; Start with 5 OUT ; Display current value DEC ; Subtract 1 JNZ 02 ; If not zero, go back to OUT OUT ; Display the final 0 HLT ; Stop

How the loop works

The key is the DEC and JNZ pair. DEC subtracts 1 from register A. If the result is not zero, the Zero flag stays clear, and JNZ jumps back to the OUT instruction. When A finally reaches 00, the DEC sets the Zero flag, JNZ sees it, and falls through to the next instruction instead of jumping.

Trace through the execution

Step PC Instruction A Zero Flag ---- -- ----------- -- --------- 1 00 LDI 05 05 0 2 02 OUT 05 0 (displays 05) 3 03 DEC 04 0 4 04 JNZ 02 04 0 (jumps!) 5 02 OUT 04 0 (displays 04) 6 03 DEC 03 0 ... 13 03 DEC 00 1 (Zero flag set!) 14 04 JNZ 02 00 1 (doesn't jump) 15 06 OUT 00 1 (displays 00) 16 07 HLT 00 1 (stop)

Try it

Use Step mode to walk through every iteration. Watch register A count down and the Zero flag flip on the last decrement. Change the starting value from 05 to 0A (that's 10 in decimal) and run it again.

Tutorial 3: Adding Numbers

Use both registers to add two numbers together.

The code

LDI 15 ; Load 15 hex (21 decimal) into A LBI 0A ; Load 0A hex (10 decimal) into B ADD ; A = A + B = 1F hex (31 decimal) OUT ; Display the result HLT

What happens inside the CPU

LDI 15 — puts hex 15 into register A. Register B is still 00.

LBI 0A — puts hex 0A into register B. Now A = 15, B = 0A.

ADD — the CPU adds A and B together (15 + 0A = 1F) and stores the result back in A. The Zero flag is clear (result is not zero). The Carry flag is clear (no overflow — the result fits in one byte).

OUT — displays 1F.

Try some variations

Change the numbers and predict the result before running. Try LDI FF and LBI 01 — what happens when the sum exceeds FF? (Answer: it wraps to 00 and the Carry flag is set.) This is overflow, and it's how the CPU signals that the result didn't fit in one byte.

Using SUB instead

Replace ADD with SUB. Now it computes A - B instead. If B is larger than A, the result wraps around and the Carry flag is set (indicating an underflow / borrow).


Examples

The 10 Example Programs

The Hex Machine comes with 10 built-in example programs. Load any one from the examples menu, step through it, study it, and modify it.


History

The Radio Shack Connection

The Science Fair Microcomputer Trainer

In the early 1980s, Radio Shack sold a remarkable little kit: the Science Fair Microcomputer Trainer (catalog number 28-259). It was a bare circuit board with a simple CPU, 256 bytes of RAM, a hexadecimal keypad, and a row of LED displays.

There was no screen. No keyboard. No operating system. You programmed it by pressing hex keys to enter machine code directly into memory — one byte at a time. You'd press the address, then the data byte, then advance to the next address. When you pressed RUN, the LEDs would blink and the tiny speaker would beep as your program executed.

What It Taught

The Microcomputer Trainer stripped away every abstraction. There was no compiler, no editor, no file system. Just you, raw hex bytes, and a CPU. You had to understand exactly what every byte did because there was nowhere to hide from the machine.

It was frustrating, educational, and deeply satisfying. When your program finally worked — when those LEDs blinked in the pattern you intended — you understood something fundamental about how computers operate. Not as theory, but as physical reality.

The Hex Machine Recreates That Experience

The Hex Machine gives you the same hands-on learning with modern convenience. You get an assembler (so you don't have to look up opcodes by hand), a memory view (instead of squinting at LEDs), and Step mode (instead of guessing what went wrong). But the core experience is the same: a tiny CPU, a small instruction set, 256 bytes of memory, and the joy of making the machine do exactly what you tell it.

Every CPU in every computer and phone works this way at the lowest level. The instructions are more complex, the memory is vastly larger, and there are many more registers — but the fetch-execute cycle, the flags, the jumps, and the logic are all the same concepts you learn here.


Strategy

Tips

← Back to All Games