3 ms·
RISC is also often described as register-register, as opposed to register-memory or stack or accumulator-based. In a pure register-register design, all opcodes
by cbd1984 11y ago
RISC is also often described as register-register, as opposed to register-memory or stack or accumulator-based.
In a pure register-register design, all opcodes which use the ALU only operate on data stored in registers, and only store data to registers. Due to this, the only opcodes which touch RAM in such a design are load and store opcodes, and they only use the simplest addressing modes.
In a register-memory design, ALU-using opcodes can touch RAM as well. This is taken to an extreme in accumulator-based designs, which aren't used much now but were previously very popular: One "main" register which is involved in all (or nearly all) opcodes, maybe a couple index registers to make memory addressing easier, and everything else is in RAM. The 6502 is the prototypical accumulator-based design, with the interesting twist that its zero page (all memory addresses with a high byte of 0x00) is almost as fast as registers, making it practically a machine with 256 one-byte registers.
(Stack machines are fairly self-explanatory. I think they're mostly VMs now, because it's easy to take stack machine code, turn it back into a parse tree, and then compile that to optimized machine code.)
Register-register designs are typically RISC, which implies constant-size opcodes (one machine word per) to save on decoding hardware, pipelining built in from the start (so no or few complicated opcodes which can take an unpredictable number of cycles to complete), and a very Spartan design philosophy, even to the extent of making the pipelining architecturally visible by specifying things like branch delay slots (where the opcode immediately after a taken branch opcode is still executed, because it's already in the pipeline). The idea was that the compiler would make it all invisible to the average programmer.
The "no complex opcodes" thing was sometimes taken to extremes: There's no single-cycle algorithm for integer multiplication or division. MIPS therefore had integer multiplication and division opcodes which executed while the rest of the chip was still executing other opcodes: The code would issue a multiplication, say, and then the next n opcodes would be run while the multiplication hardware was cranking through the math; when it was done, the result would be placed in a pair of special registers, called hi and lo. How many opcodes was n? Dunno, it depended on the inputs to the multiplication opcode. Division worked the same way. I don't remember if reading hi and lo early would stall the pipeline or generate garbage...
However, when you remember that the VAX had an opcode which would evaluate a polynomial of arbitrary degree when given an X value and a variable-length list of coefficients, you can kind of see where the RISC folk were coming from.