Teams should turn in only a single solution, listing the team members.
(It wouldn't be much of a stretch to guess that this model of doing homeworks is a harbinger of things to come.)
O:\nt\courses\cse378\smok\SMOK
.
There are two - SMOK.exe
and SMOKTrace.exe
.
The latter comes up with a window into which each component writes a line of trace information each cycle; the former does not
have that window. (This is a performance issue - tracing takes a lot more time than simulating. That matters only (if ever)
once you have a working machine and want to run some application on it as fast as possible, though.)
Start menu shortcuts are being set up on the lab machines, but there continue to be problems. The easiest thing to do is to
create shortcuts on your desktop, linking either to the .exe
files.
while (A != 0) { Product = Product + B; A = A - 1; }You can download an example of a machine that implements this algorithm from here. Download this model, load it into SMOK, and experiment with it. What is the cost of this machine? How many cycles are required to multiply two relatively large numbers (say 0x1234 by 0xABCD)?
while (A != 0) { if (A % 2 == 1) // If A is odd Product = Product + B; B = B << 1; // Multiply B by two A = A >> 1; // Divide A by two }Checking for oddness is easy in a binary representation. Just look at the low order bit. Doubling and halving numbers is easily accomplished by shifting left or right, respectively.
What is the cost of this new machine? How many cycles are required to multiply two numbers?
ssi-0.smok
and
ssi-0.smokmem
. The former is the SMOK model from class
that implements SSI-0, the latter the
sample SSI-0 program
from lecture expressed in a file that can be loaded by SMOK into the memory component of the SSI-0 model.
Run SMOK and read the model (.smok) file. (The model is set up to load memory with the contents of the .smokmem file.) Single-step through the model and make sure you understand how it works. Edit the .smokmem file to run a different program.
SSI-3 is/has:
Format | 31:24 | 23:16 | 15:8 | 7:0 |
Register | opcode | dest reg # | src0 reg # | src1 reg # |
Immediate | opcode | dest reg # | 16-bit signed immediate | |
Load | opcode | dest reg # | src addr reg # | Unused |
Store | opcode | Unused | dest addr reg # | src reg # |
Branch | opcode | target addr | src0 reg# | src1 reg # |
Opcode | Operation | Example | Meaning |
---|---|---|---|
00100000 (0x20) | ADD | 0x20020205 | Reg[2] = Reg[2] + Reg[5] |
01100000 (0x60) | IMM | 0x60020001 | Reg[2] = 1 |
00010001 (0x11) | BNE | 0x11130501 | If (Reg[5] != Reg[1]) PC = 0x4C |
10100100 (0xA4) | LOAD | 0xA4050400 | Reg[5] = Mem[Reg[4]] |
00001000 (0x08) | STORE | 0x08000203 | Mem[Reg[2]] = Reg[3] |
ADD adds to register operands and places the result into a register. IMM takes an 16-bit immediate operand from the instruction, sign-extends it to 32-bits, and places that value into a register. BNE compares two registers, and possibly sets the PC to the 8-bit immediate target address in the instruction shifted left two bits. (Because all instructions are 4-bytes long, and because the architecture insists that instructions be word aligned, the lowest-order two bits of all instruction addresses must be 00. So, we don't store those two bits in the instruction.) LOAD reads memory at an address specified by the contents of a register, and places the result into another register. STORE takes a value (from the register file) and stores it at an address specified by another register.
Registers in the Simple Machine are defined to be 32 bits wide. LOADs/STOREs operate on 32-bit words to/from memory. All instructions are encoded as 32-bit values. The high order eight bits (bits 31 through 24) specify the opcode, as shown in the table. Bits 23-16 specify a register number to write (if the instruction does so) OR a target value for the PC if the instruction is a branch. Bits 15-8 specify a register number to read. Bits 7-0 specify either an immediate value to load into a register, or a second register to read.
Your machine will implement the fetch-increment-execute loop: it fetches the instruction specified by the PC, increments the PC to point to the next instruction, and performs the operation specified by the instruction just fetched. The "steps" happen in parallel in the implementation.
Designing the datapath and control is totally up to you, but here are some hints:
anyoldname.smokmem
with this format:
// Comment line <starting address in decimal> <word1 in hex> <word2 in hex> ... <wordN in hex>For example:
// My first program 0 6001000A 60020010 20030201Puts the immediate value 0x000A into register 1, the immediate value 0x0010 into register 2 and then adds the contents of register 1 and register 2 and places the result into register 3. Double clicking the memory component will allow you to load a file like the above into memory.
Add the STOP instruction to the ISA. STOP should have an opcode of zero, and cause your machine to stop executing. Modify your machine to handle this instruction. (You may just wire a HALT component to the appropriate place.)
Write an SSI-3 program that multiplies two numbers by repeated addition (as in Exercise 0, above). It should read the first number from memory location 100, the second number from memory location 104, and store the product into memory location 108. When it is finished, it should STOP. We recommend writing the program in "assembly" code, hand-simulating it, and then hand-assembling it into machine code.
The SMOK system provides you with some important metrics that you should keep in mind. The first is the cycle time of your machine and the second is the "cost", which is a measure of how many transistors your components would consume. The person(s) who get the lowest cycle time and cost will receive a special prize!
Please: