# Stephen Smith's Blog

Musings on Machine Learning…

with one comment

# Introduction

Last time, I talked about getting a minimal RISC-V CPU up and running on my Basys FPGA development board. In this article, we’ll connect up the seven segment displays as memory mapped I/O and write a simple RISC-V Assembly Language program to count on the display.

# Connecting the Seven Segment Display

To support the four seven segment displays, I took the code from the book “FPGA Programming for Beginners” by Frank Bruno, and connected it to the RISC-V CPU from the book “Digital Design and Computer Architecture: RISC-V Edition” by Sarah L. Harris and David Harris. This turned out to be quite easy. Just needed to add a case statement in soc.sv where if the address is 0x100 then it goes to the seven segment display routine. I chose the rather low address 0x100 since that fits in an immediate argument saving additional code.

`  always @(negedge clk_25)    begin        if(MemWrite) begin            case(DataAdr)                16'h100: encoded = WriteData;            endcase            led[7:0] = WriteData[7:0];              led[15:8] = DataAdr[7:0];        end    end`

To test this, I needed to write a RISC-V Assembly Language program, only using the instructions that my mini RISC-V CPU supports.

# Writing RISC-V Assembly Language

I wrote the simple program:

```# Simple program to count on the 7-segment display
addi x2, x0, 0     #initialize counter to 0
sw x2, (x3)        # save to the display
addi x4, x0, 0x7ff # delay loop counter
sll x4, x4, x6     # shift left 9 bits
addi x5, x0, 1     # will subtract from x4
loop: sub x4, x4, x5     # decrement counter
beq x4, x0, next   # loop done, proceed
beq x4, x4, loop   # repeat loop
next: beq x2, x2, main   # jump back to loop forever```

The first version of this didn’t have the delay loop, so was simpler. With this nice Assembly Language source code, I needed a way to assemble it. I googled and found RARS (Risc-V Assembler and Runtime Simulator). RARS compiled the program fine and I could copy the compiled programs to the instruction memory in the SoC source code.

When I first ran the program, it was way too fast and the seven segment display just showed all eights (all segments lit up). So I added a delay loop, but due to the limited instruction set, I could only loop 0x7ff times, this slowed it down so the high order LED counted. I needed a way to create bigger numbers, so I implemented the SLL (shift logical left) instruction, which was easy to add to the ALU. I could have loaded a larger number from memory or could have written an outer loop to have two nested loops, but chose this instead. With this all done it works fairly well.

# Utilization

Below is the utilization report for the hardware resources being used. Notice that with this simple CPU implementation that we are using a small percentage of the available resources. Hence, we have a lot of headroom to keep developing this simple CPU/computer.

`+----------------------------+------+-------+------------+-----------+-------+|          Site Type         | Used | Fixed | Prohibited | Available | Util% |+----------------------------+------+-------+------------+-----------+-------+| Slice LUTs*                |  347 |     0 |          0 |     20800 |  1.67 ||   LUT as Logic             |  299 |     0 |          0 |     20800 |  1.44 ||   LUT as Memory            |   48 |     0 |          0 |      9600 |  0.50 ||     LUT as Distributed RAM |   48 |     0 |            |           |       ||     LUT as Shift Register  |    0 |     0 |            |           |       || Slice Registers            |   93 |     0 |          0 |     41600 |  0.22 ||   Register as Flip Flop    |   93 |     0 |          0 |     41600 |  0.22 ||   Register as Latch        |    0 |     0 |          0 |     41600 |  0.00 || F7 Muxes                   |    2 |     0 |          0 |     16300 |  0.01 || F8 Muxes                   |    1 |     0 |          0 |      8150 |  0.01 |+----------------------------+------+-------+------------+-----------+-------+`

# Summary

Developing a CPU is a lot of work, but a lot of fun. It’s amazing that with a low cost FPGA development board you can design a CPU and start building a computer around it. This was a small increment in my RISC-V CPU, but nice to see that the tools are quite easy to work with to accomplish my goal.

Written by smist08

March 8, 2023 at 6:41 pm

### One Response

1. […] Last time, we assembled a small RISC-V program to run on my FPGA RISC-V core running on a Digilent Basys3 development board. To do this we used RARS, which is a quite good Assembler, Debugger, Simulator for RISC-V; in this article I thought I’d point out some other tools available from the official RISC-V github page, including the full GNU C toolchain. […]

This site uses Akismet to reduce spam. Learn how your comment data is processed.