Professional Documents
Culture Documents
Problem
A maple syrup factory in Vermont has a problem. They have a holding tank that stores their
product that overflows from time-to-time. When this happens, an operator in a remote monitoring room
is sent to clean up the mess. They have asked you group to implement an “Annunciator” system to
monitor the holding tank and report its status to the operator in the monitoring room. The system has
two objectives, to notify the operator when the tank is near full (so they can manually turn off the fill
valve), then to notify the operator when the tank has over flown (so they can be sent to clean it up).
There are 4 input to the system. There are two level switches in the tank, full level alarm (FLA)
and overflow level alarm (OLA). On the Annunciator box in the control room, there are two momentary
push buttons, acknowledge (ACK) and test (TST).
On the Annunciator box, there are 3 outputs from the system, a green ok indicator, a yellow full
indicator and a red overflow indicator. The system has 6 states as shown in Figure 7.
E310 Pinout
(from “HiFive1 getting started v1.0.2”
Bitfield (GPIO Offset)
Bitfield or GPIO Offset is a bit number in 32-bit sequence that corresponds to a pin. For example,
student wants to enable input for pin 2. First, the student needs to figure out the GPIO offset of pin 2 which
is 18 in this case. The binary 32-bit number with 18th offset bit enabled is below.
0000 0000 0000 0100 0000 0000 0000 0000 which equals to 0x00040000 in hexadecimal(0x4000).
The hexadecimal number is called a “mask” for pin 2. Now when mask is acquired it can be stored to
corresponding memory location which activates the input. In E310’s case its base GPIO address of
0x10012000 plus input_en offset of 0x04 which gives memory location of 0x10012004. The mask for pin
2 can be stored into input_en offset by the following assembly commands:
Li t0, 0x10012000 load GPIO base address into t0
Li t1, 0x04 load input_en offset to t1
Li t2, 0x4000 load pin 2 mask to t2
Sw t2, t1(t0) store t2 into the address provided by t0 plus the offset of t1
Getting input from pin 2 is a similar procedure. First you load the value stored at input_val offset
into a register. In order to determine if pin 2 is in the high state student must AND the mask and newly
stored input_val, when the result of the AND operation is 0x0 the pin is low, otherwise its high.
Often it is desirable to enable input or output to many pins at the same time. In that case simple
additions of all the masks can be done, since no 1s overlap the result will be a bitmap that covers all the
desired pins.
Procedure:
Use the same file setup as in Lab 2 Part 2 (test before proceeding)
1. Select the GPIO’s to be used for the inputs and outputs. Use recommended pins. Modify
setupGPIO.S to enable selected pins for input or output. In setupGPIO.S delete
sw t1, GPIO_OUTPUT_XOR(t0)
2. On the solderless breadboard, wire 2 pushbuttons and 2 of the DIP stitches to the 4 GPIO’s
selected as the inputs in a pull-up resistor configuration with one side of the switch to the GPIO
and the other side to ground.
3. On the solderless breadboard, wire the 3 outputs to the anodes of the red yellow and green
LED’s. Tie the cathodes of the LED to ground though 200 ohm resistors.
4. Modify code of checkBot.S to accept mask for a pin (ex. int checkBot(int PIN)). The parameter
will be passed onto the register a0. Before proceeding any further, test this new functionality.
5. In setLED.S, change the first line after ledOn: to or t1, t1, a0.
6. Add code to main.c to handle the states of the Annunciator state machine. When returning value
from checkBot(int PIN) do not forget to invert it, since the pullup function is on, pins are in
active low state which is not intuitive. (ex TST = !checkBot(PIN_2);)
8. After fully testing the program, demonstrate it to the course instructor for credit.