CSE 371/372
Lab 2

Due:  Friday, February 18 at the close of lab (just hand your writeup to a TA).
You are to do this lab alone

In this lab you will create some of the arithmetic and logical components of your R372 processor. Specifically, you will create a 16-bit ALU (complete with carry lookahead adder) and a 16-bit arithmetic/logical left/right barrel shifter. Again, you will use structural Verilog only. As you should be somewhat more familiar with Verilog and the tracing/debugging tools you should be able to finish the assignment more quickly than you finished the previous one. Still, don't procrastinate. The number of machines is limited as is TA time (you will still have to do demonstrations). Get started early.

Exercise 0: 16-bit MUXes (0 points)

Since both the ALU and the barrel shifter will internally contain multiple 16-bit functions, each will require an N-to-1 16-bit MUX. As we saw (or will see in class), there are two ways to implement a mux. One way uses a two-level AND/OR network. The other uses tri-state buffers. In this lab, we will use two-level digital logic.

1. Create a 1-bit 2-to-1 MUX component muxh_2to1_1. The component will have three inputs. sh is a "one hot" (i.e., 2-bit) encoding of the selector. a and b are one bit inputs. o is a one bit output. Combine 16 of these components to create a 16-bit 2-to-1 MUX (muxh_2to1_16).

2. Create a 1-bit 4-to-1 MUX component muxh_4to1_1 with inputs sh (4-bit "one hot" encoded selector), a, b, c, and d, and output o. Combine 16 of these components to create a 16-bit 4-to-1 MUX muxh_4to1_16.

2. Create a 1-bit 5-to-1 MUX component muxh_5to1_1 with inputs sh (8-bit "one hot" encoded selector), a, b, c, d, and e, and output o. Since there are 8 selector combinations and only 5 inputs, the selection function is non-obvious. Implement your selection function as 0:a, 1:a, 2:X, 3:X, 4:b, 5:c, 6:d, 7:e. X means "don't care". Combine 16 of these components to create a 16-bit 5-to-1 MUX muxh_5to1_16.

There is no need to turn in anything for this part of the assignment.

Exercise 1: 16-bit ALU (50 points)

For this exercise, you will create a 16-bit ALU alu_16. The ALU has a 3-bit control input aluop, two 16-bit data inputs, a and b, a 16-bit data output o, and a 1-bit output cout, which is the carry out of the adder. The ALU performs the following functions for each value of aluop:

You should try to create this ALU efficiently and reuse as many calculations as possible. For instance, use a single adder to implement both addition and subtraction, use the fact that subtraction already requires the negation of the second input and reuse the negation circuit, use the fact that carry lookahead already requires the computation of A & B and A | B to avoid duplicating those gates as well. See lecture slides for this.

Break this task down into a series of components. First the easy ones.

Now, the more challenging ones.

Finally, create the component alu_16 using the components you have already created for this lab and any you have created for the previous lab.

Turn in schematics only for the components cla_4 and cla_16 and alu_16 and a functional simulation output showing each one of the ALU functions. For the logical functions, use 00FF and 0F0F as the values for A and B, respectively. For both addition and subtraction, use the following combinations of A and B to show that your design works properly on positive and negative numbers: 000F and 000F, FFF0 and FFF0, 000F and FF00, and FF00 and 000F. Demonstrate your design to the TA.

Exercise 2: 16-bit Barrel Shifter (20 points)

For this exercise, you will create a 16-bit barrel shifter bshift_16. The shifter has a 2-bit control input shop, a 4-bit control input shamt, a 16-bit data input a, and a 16-bit data output o. The output of the shifter for each value of shop is:

Use the 16-bit 4-to-1 MUX from exercise 0 and the barrel design shown to create this component. Note, there are several ways to do this. You could create three different barrel shifters using 2-to-1 MUXes at each level of the barrel. You would then use a 4-to-1 MUX (with one duplicated input) to select between the at the end. A cleaner and more efficient implementation would use four copies of the 4-to-1 MUX to select between the three kinds of shifts and no shift at all at each "stage" of a single barrel. Do the second.

Turn in a schematic for bshift_16 (you don't need schmatics for the muxes and individual shifters) and a functional simulation showing each one of your shifts. Use the following combinations for values for A and SHAMT for each kind of shift: 0FF0 and 4, 0FF0 and 9, F00F and 4, F00F and 9. Demonstrate your design to the TA.

Exercise 4: 16-bit Incrementer (20 points)

A useful circuit in a processor is an incrementer, an adder which can only add one variable and one fixed constant (usually, this constant is a power of two). There are two ways to implement an incrementer. The first is to use a general-purpose adder and hardwire one of the inputs. The second is to optimize the adder knowing what one of the inputs is going to be. This is the smarter way. For this exercise, you will build a 16-bit two-level carry-lookahead +1 incrementer inc1_16. Use a carry-lookahead design, but think about how the carry-lookahead circuitry (claopt_4 and claopt_16 could be optimized if you knew that b was always 0 and cin was always 1.)

Turn in your schematics for claopt_4, claopt_16 and inc1_16 and a functional simulation showing an increment for each of the following inputs: 0000, 0FF0, 00FF, FF00, and FFFF. Demonstrate your design to the TA.