2
\$\begingroup\$

I'm going to begin the adventure of building an 8-bit homebrew computer.

Right now, I'm considering the instruction set. SAP-1 seems a bit too sparse, so I'm designing my own.

Some facts:

  • My primary goal is to learn. I'll be building this on breadboards.
  • I plan on using 4 bit addresses (so 16 bytes of RAM).
  • The computer will have a 7-segment display for its output.
  • I want to be able to easily write simple math programs (addition, subtraction, multiplication, division). Do I have enough RAM for this?
  • I plan on using an ALU with zero, sign and carry status bits.
  • The system will have two registers for computation (A and B).
  • I'll have additional registers for current instruction and output.
  • Each machine code instruction will use the 4 highest bits for operation codes and the 4 lowest bits for data.

Here is the instruction set I'm thinking about. Does this make sense? Are any of these redundant/unnecessary? Is anything missing?

0000 | NOP | No-op
0001 | LIA | Immediately load data into A register
0010 | LDA | Load contents of memory address into A register 
0011 | STA | Store contents of A register into memory address
0100 | CAB | Copy contents of A register into B register
0101 | CBA | Copy contents of B register into A register
0110 | ADD | Add contents of memory address to A register
0111 | SUB | Subtract contents of memory address from A register
1000 | INC | Increment contents of A register
1001 | DEC | Decrement contents of A register
1010 | JMP | Jump unconditionally
1011 | JEQ | Jump if ALU zero bit is expressed
1100 | JNG | Jump if ALU sign bit (negative) is expressed
1101 | JCA | Jump if ALU carry bit is expressed
1110 | OUT | Copy A register into output register
1111 | HLT | Halt

Also, please let me know of any good resources for instruction set design, or general homebrew computer design.

I'm currently working through The Elements of Computing Systems and Ben Eater's YouTube videos.

\$\endgroup\$
11
  • 4
    \$\begingroup\$ You need some way to store the current (or next) PC. That and a JMP can form a CALL; then you need JUMP (contents of address where you stored it) to RETURN. Stack is a convenient way to handle call/return and a lot of other stuff, but quite a big change to your architecture. \$\endgroup\$
    – user16324
    Commented Jul 19, 2020 at 21:46
  • 1
    \$\begingroup\$ In your INC and DEC instructions you have an op-code but probably no data. If you made the data be "the amount to add" then you could merge the INC and DEC instructions into one instruction that just adds a constant to register A. If the constant happens to be "00000001" its the same as your original "INC" instruction. If the constant happens to be "11111111" (which is two complement -1) then you have the DEC instruction. \$\endgroup\$
    – user4574
    Commented Jul 20, 2020 at 0:13
  • 1
    \$\begingroup\$ You have a HALT instruction. But you also have an unconditional JMP instruction. Whats the difference between HALT and JMP to the current location. HALT doesn't do anything other than make the CPU sit there then you may be able to eliminate it and just use JMP to achieve that function. \$\endgroup\$
    – user4574
    Commented Jul 20, 2020 at 0:16
  • 1
    \$\begingroup\$ I don't see any logical AND, OR, NOT type instructions. A lot of times conditional jumps are based on testing a bit, but you can't do that other than from an add/subtract affecting flags. \$\endgroup\$
    – user4574
    Commented Jul 20, 2020 at 0:20
  • 2
    \$\begingroup\$ I think a better first step would be to do some assembly-language programming on an actual 8-bit microprocessor -- something like a Z80 or 6502 (which are ancient chips, I know). There are kits out there that are based on this class of CPU and are programmable via keypad and 7-segment display (or alphanumeric LCD). Try writing a real application, like a 4-banger calculator -- you'll get a lot of insight into what features of an ISA are useful in different situations. \$\endgroup\$
    – Dave Tweed
    Commented Jul 20, 2020 at 1:26

1 Answer 1

2
\$\begingroup\$

since this is more like feedback: let's have a wiki.

  • You need some way to store the current (or next) PC. That and a JMP can form a CALL; then you need JUMP (contents of address where you stored it) to RETURN. Stack is a convenient way to handle call/return and a lot of other stuff, but quite a big change to your architecture.
  • why do you have fused load+arithmetic ops? Wouldn't a "SUBtract value of register B from register A" be significantly more handy? Otherwise you'd first have to STA to do arithmetic.
  • OUT is a fun operation, but honestly, I'd go the arm route and simply use reserved addresses for that. That is, of course, unless you need all your address space because it's really not that large.
  • integer-to-seven-segment conversion will be pretty complicated using these instructions, if you can't waste a lot of memory space on a lookup table. So, maybe have an instruction to convert a register value to the appropriate output.
  • Instead of the two A->B and B->A copy instructions, I'd go with one copy, and a swap instruction.
  • You have an operation to load 4 bits of an immediate value into an 8 bit registers. How do you set the other bits? Maybe you want a "swap high and low nibble" instruction, or even more versatile, a shift?
\$\endgroup\$
2
  • \$\begingroup\$ Thanks for the feedback! 1. I assume adding an "instruction register" would solve that? 2. Good thinking. Makes a lot more sense. 3. The computer will use 4-bit addresses, so it will have 16 bytes of ram. So an output register would indeed save precious memory. 4. I'll read more about this. 5. Good suggestion, but how do I implement a swap instruction with only two registers? Wouldn't I need a third? 6. Another very good point. What about replacing LDI with LDB (load B from memory)? On second thought, is only 16 bytes of RAM enough to write programs for division and multiplication? \$\endgroup\$
    – Peter
    Commented Jul 19, 2020 at 22:31
  • 1
    \$\begingroup\$ two register swap: a=a^b b=b^a a=a^b but now you have an instruction that hits the ALU 3 times in a row. \$\endgroup\$ Commented Jul 19, 2020 at 23:53

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Not the answer you're looking for? Browse other questions tagged or ask your own question.