Sei sulla pagina 1di 30

Table of Contents

1.0 Introduction to Project..........................................................................................................2


1.1 Introduction to Phase Two................................................................................................3

2.0 Yoda’s Memory Organisation...............................................................................................5

3.0 Instruction Set of Yoda.........................................................................................................7


3.1 Length of Instruction Set..................................................................................................8

4.0 Instruction Set Processor.......................................................................................................9


4.1 ALU................................................................................................................................10
4.2 Data RAM.......................................................................................................................11
4.3 W Register & Status Register.........................................................................................11
4.4 Pointer.............................................................................................................................12

5.0 Instruction Cycle Processor................................................................................................13


5.1 Program Memory............................................................................................................14
5.2 IR and PC Registers........................................................................................................14
5.3 Stack................................................................................................................................15
5.4 INC Blocks......................................................................................................................17

6.0 Integrating the Processor & Development of Controller....................................................18

7.0 Testing Yoda.......................................................................................................................22


7.1 Testing the Data Transfer Instructions............................................................................24
7.2 Testing Arithmetic & Logic Instructions........................................................................25
7.3 Testing Instruction Cycle Operations.............................................................................26
7.4 Testing the Pointer..........................................................................................................28

8.0 Conclusion..........................................................................................................................29
8.1 Suggestions for Further Work.........................................................................................30

9.0 Group Details......................................................................................................................31

10.0 File Locations....................................................................................................................31


1.0 Introduction to Project
The system design project module aims to design a system called Cyclops.
Cyclops is a fire truck whose functions are fully controlled via a standard personal
computer (PC).

Basic functions such as driving the fire truck, squirting water from the hose
and capturing images/video from the mounted camera are to be coordinated with an
on-board electronic system consisting of a custom built micro-controller together with
some peripherals. Separate motors are used for the real wheel drive, steering and
the pump.

Instructions and status information are exchanged between the PC and


Cyclops via a Universal Serial Bus (USB) interface. Figure 1 below illustrates the
chassis of Cyclops.
Hose
Hose

Pump
Pump

Camera
Camera

Front
Front Wheels
Wheels
Rear
Rear Wheels
Wheels

Figure 1: Chassis of Cyclops

The objective of the project is to design both the electronic control system and
a Graphical User Interface (GUI) for the PC. The electronic control system was to be
designed in two phases.

Phase one consisted the design of an I2C interface which was to be the
camera control interface and the pulse width modulators (PWM) for the driving the
motors.

The objective of phase two was to design the microcontroller (nicknamed


Yoda), the video interface between Yoda and the camera and also the USB interface
between Yoda and the PC.

Ultimately, the design of the GUI and integration and interfacing is to be


performed in phase three.
1.1 Introduction to Phase Two

Phase two as mentioned involves the design of:

 Yoda – the microcontroller for Cyclops


 Video Interface – To transfer image/video from camera to Yoda/PC
 USB Interface – for exchanging information between the PC and Yoda

The above units were to be designed, implemented and fully tested for phase
two.

Most functions of Yoda involve handling and transferring of data so the


microcontroller has to be streamlined for this. Yoda also requires the functionality to
control all of its peripherals.

Yoda itself is to be programmed whenever the user selects/adjusts different


settings from the GUI. Programs will be transferred via the USB interface to program
memory of Yoda.

The video interface is to be used for transferring image/video information from


the mounted camera to Yoda.

The USB interface links the whole electronic system with the PC GUI. This
interface should be meet the video streaming data rate and also be able to transfer
control/status information as well as transfer program instructions to Yoda whenever
necessary.
2.0 Yoda’s Memory Organisation
Yoda is a logistics based controller so it was designed to perform data transfer
operations efficiently. Usually, this involves the data transfer between two peripheral
units within the system. Therefore, the data memory organisation of Yoda was
chosen to have a linear address space so that the peripherals can be mapped into
the data memory of Yoda. This was expected to facilitate the transfer of data. Figure
2 below shows the data memory map intended to be used for Yoda.

Address Memory Content


0x00 I2C Tx Register
0x01 I2C Rx Register
0x02 I2C Ctrl Register
0x03 I2C Stat Register
0x04 FSR
0x05 INDF
0x06 PWM1 Register
……. …………
0x0A PWM5 Register
0x0B Video Memory 1
0x0A Video Memory 2
…… …….
0x8B Video Memory 128
0x8C USB Reg1
0x8B USB Reg 2
…… ………
0xCC USB Reg 64
0xCD General Purpose
0xCC General Purpose
……. ………
0xFF General Purpose

Figure 2: Data Memory Map (8x256)

As can be seen from Figure 2, Yoda consists of only one page of data
memory which is 8-bits wide and 256 levels deep. The I2C unit was allocated four
registers and the 5 PWM units were allocated a register (for setting the desired pulse
width) each as shown. Since the Video and the USB units were not designed,
sufficient memory locations (i.e. 128) were allocated to the Video and (64 to the) USB
units. The rest of the memory space consisted of 33 general purpose registers which
can be used to hold constants or variables as desired by the end-user.

The FSR (File Select Register) and the INDF (Indirect File Register) serve to
function as a pointer. FSR holds the address the pointer is pointing to while the
contents of the pointer can be accessed via INDF. This simple pointer can be used
for simple indexing operations and will be desirable when dealing with video streams
for example.
The program memory was designed to be a RAM block of 8x256. The memory
depth was more that sufficient and the full program memory will rarely be used.
However, extra memory was included to allow for a worst case scenario. Figure 3
below illustrates the program memory map for Yoda:

Address Description
0x00 Reset Vector
0x01 Instruction
0x02 Instruction
……. ………
0xFE Instruction
0xFF Interrupt Vector
Figure 3: Program Memory Map

As can be seen from above, the reset vector is set to the first address of
program RAM. This allows the program to flow naturally from top to bottom since a
device reset or the burning of a new program will force the program counter to reset
to 0.

It was decided that there should be a single interrupt vector for the controller
and this interrupt vector address was assigned to the last memory location. Normal
program instructions are highly unlikely to be stored in this location. Usually, a “goto”
statement will be placed in this location to divert the program to an interrupt service
routine located elsewhere in the program.
3.0 Instruction Set of Yoda
An instruction set was designed to provide Yoda with the basic
functions that it was expected to perform. Table 1 details the instruction set:
Encoding Mnemonic Operand 1 Operand 2 D Description
0x00 NOP X X X No operation
0x01 MOVLW Literal X X W=Literal
0x02 MOVWF Addr X X F(addr)=W
0x03 MOVFW Addr X X W=F(addr)
0x04 MOVLF Literal Addr X F(addr)=Literal
0x05 MOVFF Addr1 Addr2 X F(addr2)=F(addr1)
0x06 ADDWF Addr X 1 W=F(addr)+W (D=0)
0 F(addr)=F(addr)+W (D=1)
0x07 ADDLW Literal X X W=Literal + W
0x08 SUBWF Addr X 1 W=F(addr) - W (D=0)
0 F(addr)=F(addr) - W (D=1)
0x09 SUBLW Literal X X W=Literal - W
0x0A INCF Addr X 1 W=F(addr) + 1 (D=0)
0 F(addr)=F(addr) + 1(D=1)
0x0B DECF Addr X 1 W=F(address) - 1 (D=0)
0 F(addr)=F(addr) - 1(D=1)
0x0C ANDWF Addr X 1 W=W & F(addr) (D=0)
0 F(addr)=F(addr) & W (D=1)
0x0D ANDLW Literal X X W=W & Literal
0x0E ORWF Addr X 1 W=W OR F(addr) (D=0)
0 F(addr)=F(addr) OR W (D=1)
0x0F ORLW Literal X X W=W OR Literal
0x10 XORWF Addr X 1 W=W XOR F(addr) (D=0)
0 F(addr)=F(addr) XOR W (D=1)
0x11 XORLW Literal X X W=W XOR Literal
0x12 RESET X X X Reset program counter
0x13 BTFSS Addr Bit Location X Skip next instruction if bit in
F(Addr) is set
0x14 BTFSC Addr Bit Location X Skip next instruction if bit in
F(Addr) is clear
0x15 BSF Addr Bit Location X Set bit in F(addr)
0x16 BCF Addr Bit Location X Clear bit it F(addr)
0x17 RRF Addr X X Rotate F(addr) to right once
0x18 RLF Addr X X Rotate F(addr) to left once
0x19 GOTO Addr X X Goto Addr in program memory
0x1A CALL Addr X X Call subroutine at Addr
0x1B RET X X X Return from subroutine
Table 1: Instruction Set Summary

Note that ‘W’ in the above corresponds to the working register (which is the
only accumulator in Yoda) and F denotes a file register and Addr denotes an
address referring to either a data or program memory location. The “Bit Location”
stated in Table 1 denotes the position of the bit to be set/cleared or tested. Also, ‘D’
above denotes the destination and is only a 1-bit field. Clearing D to 0 usually returns
the result to W whereas setting it to 1 returns the result to a file register.

3.1 Length of Instruction Set

The instruction set consists of 27 instructions. Therefore, these were encoded


with 5 bits. Each of the operands was chosen to be 8-bits wide so that for example all
the 256 memory locations in program/data memory can be accessed and also literals
up to 256 can be used. Finally, the destination bit (d-bit) is only 1-bit wide. Combining
all these fields together produces a 22-bit instruction as shown in Figure 4 below:

Op-Code Operand 1 Operand 2 D

5-Bits 8-Bits 8-Bits 1-Bit

22-Bit Field

Figure 4: Instruction Field Length


4.0 Instruction Set Processor
The instruction set processor enables the microcontroller to process data
oriented instructions. The instruction set processor for Yoda was derived by
analysing the instruction set given in Table 1. The final instruction set processor unit
is detailed in Figure 5 below.

Figure 5: Instruction Set Processor

The entire datapath illustrated above is 8-bits wide except for the ALU control
signals, the Data RAM Write_En bit and the Jump signal which is also 1-bit wide. The
following subsections will detail the functions of each of the functional blocks in
Figure 5.
4.1 ALU

The function of the ALU is to perform all the arithmetic and logic operations.
The ALU has two data input ports, namely input A and input B. Input A is always the
contents of the W register (accumulator) while input B can either be contents of a
memory location or a literal as shown in Figure 5. The Mode signal to the ALU
defines the operation to be performed on the data from inputs A and B. Note that the
arithmetic operations are all unsigned and unprotected against overflow. Therefore,
these events must be checked in software. Table 2 below summarises the different
modes of the ALU:

ALU Mode Operation Performed


0 O/P= A and B
1 O/P= A or B
2 O/P= A xor B
3 O/P= A + B
4 O/P= B – A
5 O/P= B/2 (rotated to right)
6 O/P= 2*B (rotated to left)
7 O/P= B(Bit_Location)=0
8 O/P= B(Bit_Location)=1
9 O/P= B + 1
10 O/P= B – 1
11 Jump=B(Bit_Location)
12 Jump=not(B(Bit_Location))
Table 2: Modes supported by the ALU

The VHDL code used to implement this is illustrated in Figure 6 below:

Figure 6: VHDL architecture entry for ALU unit


4.2 Data RAM

The data RAM block shown in Figure 5 was an 8x256 memory block. Memory
mapping of the peripherals was not carried out at this stage of the design. The
primary aim was to implement a fully working processor before performing the
memory mappings to peripherals.

The data RAM was selected to be two-port RAM since this allows
simultaneous read and write capability which is necessary for fast data transfers (1
cycle as opposed to 2) and this is desired for a logistics processor. This meant that
the RAM itself would have a separate read and write address.

For present purposes, peripheral mapping was excluded and the following
VHDL entry was used to implement this RAM block:

Figure 7: VHDL entry for data RAM block

4.3 W Register & Status Register

The W register (working register) serves as an accumulator. One of the two


inputs to the ALU is always this register (input A). This register is usually used to hold
intermediate results of the ALU between operations.

The Status register is also an 8-bit register which holds primarily two important
bits: the C_bit and the Z_bit. The C_bit is set whenever there is an overflow from the
ALU as a result of an arithmetic operation and the Z_bit is set if the result is zero.
Checking for zero is important especially when implementing loops (such as for loop)
and the status register will enable this. The C_bit can be used to check for overflow
in software since the ALU arithmetic is unprotected from overflows.
4.4 Pointer

A pointer was introduced into the system via the FSR (File Select Register)
and INDF register. These registers were memory mapped into data RAM as shown
below in Figure 8:

Address Description
0x04 FSR
0x05 INDF
Figure 8: Position of FSR and INDF in Data RAM

The FSR held the address of the pointer while the contents of the pointer can
be accessed via the INDF register. A pointer is a desirable asset to most
microprocessors and it enables software to index through a set of repetitive
operations on a consecutive sequence of memory locations.

Referring to Figure 5, the FSR can be loaded a new address via the datapath.
The Address Assignment block is simply an address comparator enabling the FSR to
be loaded if address location 0x04 is written to as shown below in Figure 9. This
effectively maps the FSR to the data memory and consequently, the memory location
0x04 in data memory is also saves the same data.

Whenever the pointer is used to access a memory location, the INDF register
will be read. When address 0x05 is read, the Address Assignment (Address
Comparator) block selects the read address to the Data Memory to be the address
value in FSR. This enables the contents of the pointer to be read. Similarly, if the
write address is 0x05, the Address Comparator block selects the write address to the
data memory as the contents of the FSR. This allows the contents of the pointer to
be written to. Figure 9 below provides an insight to the implementation of the pointer.

Figure 9: Implementation of a pointer using FSR


5.0 Instruction Cycle Processor
The instruction cycle processor is responsible for handling the flow of the
program. Therefore, it must also be able to cater for jumps and/or function calls or
returns. Yoda’s instruction cycle processor was given the following functionality:

 Be able to sequentially execute a program


 Be able to make unconditional jumps
 Be able to perform function calls and returns

The simplified block diagram in Figure 10 below details the design of the
instruction cycle processor.

Figure 10: Instruction Cycle Processor

As can be seen, the instruction width as explained is 22 bits while the


addressing lines are 8 bits wide. The subsections which follow details each important
block illustrated in Figure 10 above.
5.1 Program Memory

Program memory was chosen to be 22-bits wide and 256 levels deep. The
depth of the memory is sufficient to accommodate 256 lines of code which is suitable
for this application.

The program memory should also be programmed whenever the user


changes the configuration from the PC GUI. This programming capability is added by
having both a data read and data write ports. While the Enable_Programming signal
is not asserted, the program memory operates in normal mode. In this mode, the
program memory is read and the instructions are executed by the system. When
there is a rising edge on the enable_programming signal, the data at the input to the
memory will be written to the current address location. This can be used to program
the whole memory sequentially. Figure 11 below shows the implementation of the
program memory using VHDL:

Figure 11: VHDL implementation of Program RAM

5.2 IR and PC Registers

The IR (instruction) register is a 22 bit wide register with a clock and load
input. This register retains instructions from program memory so that the instruction
decoder can identify and process the instructions. The output from the IR register is
separated into the opcode (5-bits wide), operand 1 (8 bits wide), operand 2 (8 bits
wide) and D (1 bit wide). The controller FSM (Finite State Machine) would use the
opcode to determine the operation to perform while both operands and D will be used
by the datapath unit (which includes both the Instruction Cycle Processor and the
Instruction Set Processor).

The PC (program counter) register holds the address of the next instruction to
be executed. During normal program flow, the PC is incremented while during jump
or call operations, the PC value may change randomly depending on the destination
of the jump.
5.3 Stack

A stack is not necessary if the program is guaranteed to flow sequentially


without any branching. However, this is only feasible for very simple routines. It is a
standard practice in programming to structure the program efficiently and elegantly
so that code minimisation can be achieved. Repetitive routines can be written once
as functions and these can be called whenever desired within the main program.
When a function is called, the main program will divert and execute the function
before resuming. This ability to divert from the current process and later return to
where the program left is provided by the stack.

Whenever a function call is made, the stack records the value of the PC
register. This is done via a push operation. When the function returns, the stack
returns the recorded value into the PC register so that the main process can be
resumed. The stack is ‘popped’ this way via a pull operation. There is also possibility
to have a function call within another function. This requires a total of two memory
locations within the stack to record the two return locations. Therefore, the maximum
number of consecutive function calls allowed without pulling from the stack is equal
to the depth of the stack.

In a simple application such as this project, the use of functions will be limited.
Therefore, it is anticipated that a 4 level stack should be sufficient. This allows a
maximum of 4 consecutive function calls to be performed without need for popping
the stack. However, if this is exceeded, the stack will overflow and the processor will
fail to return to the correct address.

The stack was implemented in two stages. First, a simple 8-bit wide 4 level
deep memory with data in and data out ports was generated. The address input to
the memory (called the stack pointer) determines where data is read or written. The
following code shows how this stack memory was implemented in VHDL:

Figure 12: VHDL code for implementing Stack Memory


Secondly, a stack counter was implemented as an FSM to count the stack
pointer up/down depending on a push/pull operation. In a push operation, the stack
counter first increments the stack pointer so that this points to a vacant memory
location. Then the stack memory will record the return address. During a pull
operation, the current pointer value is not changed. The content of the corresponding
memory location is produced by the stack memory. If a further pull operation is
performed, then the pointer is decremented and the content of the new memory
location is read. The stack counter FSM is shown in Figure 13 below:

Figure 13: Stack counter implantation

Ultimately, these two functional units were combined to give a complete


functional stack unit. This is depicted in Figure 14 below:

Figure 14: Complete Stack Unit

As can be seen in Figure 14, the clock to the stack_core (stack memory) is
inverted. This is to assure that the stack pointer has enough time to increment before
a new address is registered into the stack.
5.4 INC Blocks

The INC blocks in Figure 10 represent simple incrementers. This allows the
PC value to be incremented (for normal program flow) or allow the program to jump
one instruction forward (during btfss or btfsc commands).
6.0 Integrating the Processor & Development of Controller
The instruction cycle and instruction set processor were combined to a single
controller unit as shown below. This controller was responsible for generating all the
control signals (shown below) when necessary.

Dest

Figure 15: Competed Yoda

The two multiplexers in Figure 15 are used to divert operand 1 and operand 2
values into the rd_address (read address of RAM),wr_address (write address of
RAM), or literal_val (literal input) as necessary when carrying out the various
instructions. These two multiplexers are controlled by the control unit as shown.

Note that the ‘Dest’ signal shown above is the ‘D’ bit extracted from the
instruction word, i.e. bit 0 of the instruction word.

As can be seen, there are only three signals entering Yoda. This includes the
system clock, program data and a program enable signal. The program data line can
be used to “burn” the program memory of Yoda with a new set of commands. The
Prog_En signal must be toggled to indicate that a new program requires to be
written.

Finally, the controller FSM had to be developed to be able to deliver the


control signals shown above. Firstly, the control unit should be able to fetch and
decode the instruction. To accomplish this, the controller requires communicating
with the instruction cycle processor. Then the controller must be able to generate the
necessary control signals to the datapath unit to execute the decoded instruction.
The next two pages will outline the state of the control signals during the execution of
each instruction in the instruction set.
6.1 Control Signals Related to Data Processing
6.2 Control Signals Relating to Program Flow
The two previous pages outlined the control signal states used to execute all
the instructions. Figure 16 below is the implementation of this using an FSM
approach. This FSM essentially fetches an instruction from program memory (by
controlling the instruction cycle processor), then decodes this instruction and
executes the instruction by setting the relevant control signals to the datapath unit.
Figure 16 below provides an overview of Yoda’s controller FSM:

Figure 16: Controller FSM of Yoda

The green state above represents the start state where all control signals are
cleared. This is followed by the fetch state which loads the PC and the IR registers
with the appropriate values. The next state is the decode state. The states that are
positioned in a circle represent instructions from the instruction set and depending on
the value of IR (the op-code) the FSM will select one of these states to execute.
Within each of these states will be the control signals necessary to execute that
instruction. Once executed, the FSM will return to start and will process the next
instruction.

The three states at the top left cornet in Figure 16 are entered when the
device is in programming mode. Here, the PC is reset to 0 and is counted up to 255.
During each clock cycle a new instruction will be recorded into program memory.
Once the 255 memory locations are written, the FSM resets again and returns to the
start state to resume normal operation.

The call operation as shown in Figure 16 was implemented by two states. The
call state pushes the PC value into stack. Then the goto state is executed and the PC
is forced to jump to the specified value.

The entire details of the control signalling in the FSM are not provided here
due to the shear size of this FSM. For more detailed information, the reader is
referred to section 10 of the report where the project files are attached.
7.0 Testing Yoda
Each unit was tested independently before integrating all of these to form
Yoda. Note that at this stage, peripheral mapping had not included. This section
presents the final phase of testing of Yoda.

The test bench was used as a interface to “burn” different programs into the
program memory of Yoda. After programming has finished, the test bench only
generate a clock to Yoda. After programming, Yoda is configured to automatically
reset and execute the instructions. These results can be observed from the signal
display window to confirm Yoda’s functionality.

At this stage of testing, it is most convenient to use a test bench to generate


the required signals. The finalised Yoda block had three ports: clock,
program_data_in and program_enable. Yoda was tested by first programming it with
a known set of instructions and by observing the outputs. This enabled the testing of
all the instructions as well as the capability to program Yoda.

To simplify the entry of instruction into the test bench the corresponding op-
codes were assigned to the instruction names using the following statements:

The encodings in the test bench shown above enabled the desired instruction
to be written using the instruction name as opposed to its op-code. This simplified the
task.
The same was done to encode memory locations and file registers as shown
below:

The declarations given above enabled the test bench to be prepared without
ambiguity since the instruction and the operands can now be selected from the list of
constants above and can be concatenated to give almost any combination as
desired.

The following subsections will describe the different tests performed on Yoda
to fully test all of its functionality.
7.1 Testing the Data Transfer Instructions

The following data transfer instructions were tested with this test procedure:

1. Movlw – W=Literal
2. Movwf – F(address)=W
3. Movfw – W=F(address)
4. Movlf – F(address)=Literal
5. Movff – F(address1)=F(address2)

All of these instructions were tested together through the test bench listed in
Appendix one. The program written in the test bench is summarised in the Table 3
below. The test bench ‘burnt’ this program into the program memory of the Yoda and
became idle. This allowed us to observe how Yoda executed the instructions written
to its program memory.

Instruction No. Instruction To Be Executed Action Performed


0 Movlw “50” W=50
1 Movwf “0” F(0)=50
2 Movlf “127”,”1” F(1)=127
3 Movfw “1” W=F(1)=127
4 Movff “1”,”2” F(2)=F(1)=127
Table 3: Program used to test the data transfer instructions

The results obtained for the program are shown in Figure 18 below. As can be
seen, the all the data transfer instructions work as expected and in one clock cycle.

A B C D E

Figure 18: Results for data transfer tests

The different points labelled above in Figure 17 are detailed below:

A- W is loaded with a value of 50


B- F(0) is loaded the contents of W so F(0)=50
C- F(1) is loaded a literal of 127 so F(1)=127
D- The content of F(1) is loaded into W so W=127
E- The content of F(1) is copied to F(2) so F(2)=127

From Figure 18 and its interpretation from the points labelled above confirms
that the program was executed correctly. Therefore, the data transfer tests were
successfully performed. Yoda behaved as expected and carried out the program
written to its instruction memory.
7.2 Testing Arithmetic & Logic Instructions

The objective of this test process is to confirm that the arithmetic and logic
based instructions are carried out successfully by Yoda. This test will be performed
on the following instructions:

1) Addwf 2) Sublw 3) Incf 4) BSF 5) RRF

Note that since all the arithmetic and logic operations are carried out by the
ALU block, testing only the instructions shown above is fairly adequate to confirm
that all arithmetic operations will be performed properly.

Similar to the previous tests, a new test bench was prepared to test the
instructions above. As before, the test bench will burn these instructions into the
program memory and become idle (only generating a clock signal). After
programming, Yoda will auto-reset and begin executing the program sequentially.
The results can then be analysed through the simulator. The table below lists the
program used for this test. The full test bench is listed in Appendix two.

Instruction Instruction To Action Performed Expected


No. Be Executed Result
0 Movlf “4”,”0” F(0)=4 F(0)=4
1 RRF “0”,’0’ W=F(0)/2 W=2
2 addwf “0”,’1’ F(0)=W+F(0) F(0)=6
3 Sublw “127” W=127-W W=125
4 Bsf “0”,”0” F(0)=F(0) or “00000001” F(0)=7
Table 4: Program used to test arithmetic and logic operations

The results obtained are summarised in the Figure 19 below.


A B C D E

Figure 19: Results of arithmetic & logic operations test

The events at the different points in Figure 18 above are explained below:

A – F(0)=4 occurs at this point


B – The RRF command updates W with the right-rotated value of F(0) here
C – The addwf instruction executes and the result of 6 is written to F(0) at this point
D – The sublw instruction is performed and the result of 125 is put into W
E – The first bit in F(0) is set in this operation so F(0) now is updated to 7 here.

As can be observed from the above interpretation, the program was executed
by Yoda correctly so this test was completely successful.
7.3 Testing Instruction Cycle Operations

This section aims to confirm the instruction cycle operations. These operations
are all involved with the control of program flow. The following instructions are tested
in this test process:

1. Btfss
2. Goto
3. Call
4. return

As before, a new test bench was prepared to test the instructions above. This
is provided in Appendix 3. Table 5 below summarises the sequence of the program
to be executed by Yoda.

Instruction Instruction To Action Performed Expected Result


No. Be Executed
0 Goto “3” PC=3 PC=3
1 Movlf “10”,”0” F(0)=10 F(0)=10
2 Return Return from subroutine PC=6
3 Movlf “127”,”0” F(0)=127 F(0)=127
4 Btfss “0”, “5” Skip next instruction if bit Next instruction is
5 in F(0) is set skipped (i.e.PC=6)
5 Nop - -
6 Call “1” PC=1 PC=1
Table 5: Program used to test Instruction Cycle Operations

The instructions are listed below in order of execution as expected:

1) Instruction No. 0 is processed and the PC jumps to address 3


2) Instruction No. 3 is processed and F(0)=127
3) Instruction No. 4 is processed and since F(0)’s bit 5 is set, the next instruction
is skipped so PC=6.
4) Instruction No. 6 is processed so PC=1
5) Instruction No. 1 is processed so F(0)=10
6) Instruction No. 2 is processed so PC=7
Figure 20 below illustrates the results obtained. Since the length of the
simulation is longer, the continuous waveforms were split into the two figures below.

A
A B
B C
C

D
D EE FF

Figure 20: Results of Instruction Cycle operations test

The important changes occurring at the points labelled above are explained
below:

A- The goto instruction updates the contents of PC to 3 as expected


B- Instruction at address 3 (movlf ‘127’,’0’) is executed so F(0)=127
C- The BTFSS instruction performs a ‘skip’ operation as expected so PC=6
D- The call instruction results in PC=1 as expected
E- Instruction at address 1(movlf ‘10’,’0’) is executed so F(0)=10
F- The return command sets PC to 7 as expected

The above results confirm that the instruction cycle operations are functional.
The test was successful and the testing of all the features of the instruction set is
nearly complete. The next section will test the last feature which is the pointer.
7.4 Testing the Pointer

The pointer is a useful feature in Yoda and therefore must be fully tested. The
program outlined in Table 6 below details the program used to test the pointer. The
full listing of the test bench for this is given is Appendix 4. Note again that the FSR
register (whose address is 0x04) sets the address of the pointer while the INDF
register (whose address is 0x05) is the contents of the pointer.

Instruction Instruction To Action Performed Expected Result


No. Be Executed
0 Movlf “0”,”4” FSR=0 FSR=0
1 Movlf “127”,”5” F(FSR)=127 F(0)=127
2 INCF “4”,’1’ FSR=FSR+1 FSR=1
3 Movlf “127”,”5” F(FSR)=127 F(1)=127
Table 6: Program used to test pointer

Figure 21 below shows the results obtained. The points labelled in Figure 20
are explained below:

A B C D

Figure 21: Results of pointer test

A- FSR register (with address 0x04) is loaded with the value 0. therefore, the
pointer now points to memory location 0
B- The contents of the pointer is written a value of 127 so F(0)=127
C- The FSR is incremented so that the pointer points to F(1)
D- F(1) is set to 127 through the pointer

The pointer test was successful as can be seen. With this final test, it can be
said that most of Yoda’s functionality has be tested thoroughly and it can be
confirmed that the instruction set has be successfully implemented.
8.0 Conclusion
The microcontroller for Cyclops (called Yoda) was designed and thoroughly
tested for phase two of this project. The design was started with the preparation of a
suitable instruction set. The instruction set consisted of a total of 27 instructions
including data transfer, arithmetic and logic and branching instructions.

Data transfer instructions enabled transfer of data between any two memory
locations or between the accumulator (W register) and any memory location within
one clock cycle. This was important since Yoda is a data transfer oriented processor
so it is necessary to have fast data transfers.

The instruction set also provided some simple arithmetic operations such as
addition and subtraction. However, overflow saturation or rounding was not added to
this since this complexity was not necessary for the application. Multiplication and
division by 2 was also incorporated into the design as these were relatively simple to
implement.

Bit test commands (BTFSS/BTFSC) allowed decisions to be made depending


on the state of a bit in a memory location. For example, the BTFSS (bit test file
register skip if set) will skip the next instruction if the bit in interest in the memory
location is set. This together with the goto/call instructions can be used in software to
perform “if” statements. The call statement on its own can be used to perform simple
function calls. This is possible due to the implementation of a 4 level stack.

The width of each instruction was 22 bits. The op-code was 5 bits, operands 1
and 2 are 8 bits each and the destination bit was 1-bit wide. This meant that the
program memory had to be 22 bits wide. The depth of the program memory was
chosen to be 256 so that any program for this simple application can be
accommodated.

The datapath was 8-bits wide. Therefore, the data memory also had to be 8
bits wide. The data memory was chosen to be 256 levels deep so that there were
sufficient registers available to perform even the most demanding task in Cyclops.
The data RAM was chosen to be a two port RAM so to speed up data transfers
between the RAM and the ALU/accumulator/RAM. Two port RAMs can be read and
written simultaneously so all arithmetic operations on memory locations can be
performed in only one instruction cycle as oppose to two. Also memory – memory
transfers can occur in one clock cycle. These benefits are a necessity for Yoda since
it should be able to process video, which requires fast processing speed.

A simple pointer was implemented by using two registers, namely the FSR
and INDF. The FSR register holds the address of the pointer while the INDF register
represents the contents of the pointer. Writing to INDF modifies the contents of the
pointer. Having a pointer in Yoda is also desired. A pointer can be used for example
to index through a pixel stream.

A 4-level stack was added to Yoda so that function calls can be used in
software. This allowed a maximum of 4 nested function calls to be performed without
the danger of stack overflow. For this application, a 4 level stack was sufficient.
The full details of the controller FSM was not included in the report due to its
shear size. The FSM was responsible for asserting the various control signals for the
datapath unit.

The various tests performed on Yoda confirmed that the microcontroller


operates properly. Tests were carried out on most of the instructions and tested
nearly every feature of the design. All the test results were successful as was shown
in the testing section. Testing proved to be a difficult task. However, the definition of
constants representing the various opcode in the test bench made the task simpler.

Phase 2 provided the opportunity to learn about the various design


considerations in implementing a customised microprocessor. It also enabled VHDL
concepts to be strengthened and also highlighted the importance of VHDL in
modelling and simulating complex designs.

8.1 Suggestions for Further Work

Phase three was involved with the design of the microprocessor and this has
been mostly completed. However there still remains the mapping of the various
peripherals to data memory. This task was not performed at this stage since all the
peripherals were not implemented. The USB interface and the video processor unit
were yet to be designed.

The Video processing block and the USB interface must then be designed and
implemented. Then the peripherals must be mapped to Yoda’s memory space. Then
a GUI must be designed to communicate with the electronics system in Cyclops. The
GUI must be able to reconfigure the program memory in Yoda so that Cyclops can
be controlled in real time.
9.0 Group Details
This task was tackled by a team of three: Thant Sin, Uthayateban Logarajah
and Lakshman Athukorala. The designs were brainstormed together as a group and
other members of the class were also consulted. It was decided that each member
implement the proposed designs individually so as to gain experience with the design
software. Any disagreements or problems faced during simulations were resolved
thereafter.

Designs were drafted with FPGA Advantage 5.0 software package which was
available to each group member on their personal computers. Although the later 7.2
version was available, due to the various problems encountered and the
sluggishness of the virtual machines, version 5.0 was preferred.

10.0 File Locations


The library files containing Yoda and the I2C module are located at the
following addresses:

CD Drive:\SystemDesignProject\I2C

CD Drive:\SystemDesignProject\Yoda

Note that the designs were implemented in FPGA Advantage version 5.0 and
some components may need to be re-compiled before simulations can be started.

Potrebbero piacerti anche