how to implement this in a logic circuit, etc.
In the normal flow of execution, an instruction gets fetched into the instruction register IR,
then is decoded by the control unit into a big bundle of individual control wires,
which then controls the datapath of the processor.
If I were you, I would design the control path "backwards" from that process:
First design the datapath.
Then make a list of all the control signals that are needed to specify how data flows through that datapath.
The ALU needs some control signals to tell it whether to add, subtract, etc.
The program counter section needs control signals to tell it whether the program counter gets reloaded with an incremented version of the previous value, or with some completely different branch value.
Then for each assembly-language instruction mnemonic, figure out what sequence of pulses on each control signal line are required to implement that instruction.
If you are lucky, many of those control signals can be "directly decoded" from the instruction register.
The remaining control signals are generated by the control unit, which is implemented as a Moore machine or a Mealy machine.
If you have a Princeton architecture -- your processor normally pulls instructions from the same single-ported memory used to read and write data --
then you are forced to have at least LOAD and STORE take multiple cycles to execute.
Perhaps the conceptually simplest and most general-purpose approach
is to implement the control unit with a very wide control store ROM
holding the microprogram,
with a pipeline register that latches all the output bits of that ROM
every clock cycle.
Every time a new new opcode is fetched from main memory, typically the high bits of the microPC are loaded with the opcode, and the low bits of the microPC reset to zero.
The "Microprocessor Design: Design steps" goes into much more detail.
Please help improve the current rough draft of the "Microprocessor Design" book to make it easier for the next person to design a processor.
typical 8-bit CPUs
... using 8-bit instructions ...
With very rare exceptions, every instruction set I've ever seen proposed (much less even simulated or actually implemented) uses more than 8 bits for at least some instructions.
All the "8-bit CPUs" I've ever seen (6800, 6502, Zilog Z80, 8080, 68HC11, Microchip PIC, Atmel AVR, etc.; as well as some unique homebrew processors and a bunch of "paper-only" ideas that have not yet been implemented) have at least some instructions that are more than 8 bits long.
For practically all of those CPUs, the first byte of the instruction has the complete opcode, and from that byte the decoder in the CPU can figure out exactly how long the instruction is.
Often NOP and RETURN are one-byte instructions.
Often BRANCH is a multi-byte instruction -- one byte for the opcode, followed by however many bytes are required to fill the program counter PC.
I think it is unlikely that the person who gave you those specifications for an 8-bit machine really intended you to work under the additional heavy burden of also limiting the maximum length of every instruction, including the non-opcode bits, to 8 bits.
And so you can probably skip the next section.
What if every instruction were exactly 8 bits wide?
I think limiting the maximum instruction length to 8 bits (or even shorter!)
is a fascinating idea.
It makes some parts of the processor simpler, at the cost of making other things much more difficult to implement and test.
... instructions, and there will be 9 or 10 of them. ...
A processor with at least 9 instructions requires at least 4 bits to fully distinguish those instructions -- the opcode bits.
For loading/storing/branch if zero/branch if not zero, I need one bit
for the single register and 4 bits for the address
Plus at least 2 bits to need to distinguish between those 4 different operations.
Plus at least 1 more bit to indicate whether it's one of these 4 instructions or some other instruction entirely.
That implies that loading/storing/branch if zero/branch if not zero instructions have this format:
3 bit opcode + 1 bit source/destination register select + 4 bit address = 8 bits.
That's a total of 8 bits, so it just barely fits.
If you really need 2 bits of register select for other instructions (I'm not sure that you do), you are forced to use a different format for those instructions, perhaps
3 bit opcode + 1 bit source/destination register select + 1 bit source register + 2 function bits + 1 unused bit = 8 bits.
Typically the same machine-language opcode is used for several different ALU operations.
The function bits select which particular operation -- add, subtract, or some other ALU operation.