blob: e12d22946661337b3f28c1b0476679be7cf5ea8c [file] [log] [blame] [view]
manarabdelaty69bd3262021-04-07 15:58:03 +02001<!---
2# SPDX-FileCopyrightText: 2020 Efabless Corporation
3#
4# Licensed under the Apache License, Version 2.0 (the "License");
5# you may not use this file except in compliance with the License.
6# You may obtain a copy of the License at
7#
8# http://www.apache.org/licenses/LICENSE-2.0
9#
10# Unless required by applicable law or agreed to in writing, software
11# distributed under the License is distributed on an "AS IS" BASIS,
12# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13# See the License for the specific language governing permissions and
14# limitations under the License.
15#
16# SPDX-License-Identifier: Apache-2.0
17-->
18
19# Simulation Environment Setup
20
21There are two options for setting up the simulation environment:
22
23* Pulling a pre-built docker image
24* Installing the dependecies locally
25
26## 1. Docker
27
28There is an available docker setup with the needed tools at [efabless/dockerized-verification-setup](https://github.com/efabless/dockerized-verification-setup)
29
30Run the following to pull the image:
31
32```
33docker pull efabless/dv_setup:latest
34```
35
36## 2. Local Installion (Linux)
37
38You will need to fullfil these dependecies:
39
40* Icarus Verilog (10.2+)
41* RV32I Toolchain
42
43Using apt, you can install Icarus Verilog:
44
45```bash
46sudo apt-get install iverilog
47```
48
49Next, you will need to build the RV32I toolchain. Firstly, export the installation path for the RV32I toolchain,
50
51```bash
52export GCC_PATH=<gcc-installation-path>
53```
54
55Then, run the following:
56
57```bash
58# packages needed:
59sudo apt-get install autoconf automake autotools-dev curl libmpc-dev \
60 libmpfr-dev libgmp-dev gawk build-essential bison flex texinfo \
61 gperf libtool patchutils bc zlib1g-dev git libexpat1-dev
62
63sudo mkdir $GCC_PATH
64sudo chown $USER $GCC_PATH
65
66git clone https://github.com/riscv/riscv-gnu-toolchain riscv-gnu-toolchain-rv32i
67cd riscv-gnu-toolchain-rv32i
68git checkout 411d134
69git submodule update --init --recursive
70
71mkdir build; cd build
72../configure --with-arch=rv32i --prefix=$GCC_PATH
73make -j$(nproc)
74```
75
76# Running Simulation
77
78## Docker
79
80First, you will need to export a number of environment variables:
81
82```bash
83export PDK_PATH=<pdk-location/sky130A>
84export CARAVEL_ROOT=<caravel_root>
85```
86
87Then, run the following command to start the docker container :
88
89```
90docker run -it -v $CARAVEL_ROOT:$CARAVEL_ROOT -v $PDK_PATH:$PDK_PATH -e CARAVEL_ROOT=$CARAVEL_ROOT -e PDK_PATH=$PDK_PATH -u $(id -u $USER):$(id -g $USER) efabless/dv_setup:latest
91```
92
93Then, navigate to the directory where the DV tests reside :
94
95```bash
96cd $CARAVEL_ROOT/verilog/dv/caravel/user_proj_example
97```
98
99Then, follow the instructions at [Both](#both) to run RTL/GL simulation.
100
101## Local
102
103You will need to export these environment variables:
104
105```bash
106export GCC_PATH=<gcc-installation-path>
107export PDK_PATH=<pdk-location/sky130A>
108```
109
110Then, follow the instruction at [Both](#both) to run RTL/GL simulation.
111
112## Both
113
114To run RTL simulation for one of the DV tests,
115
116```bash
117cd <dv-test>
118make
119```
120
121To run gate level simulation for one of the DV tests,
122
123```bash
124cd <dv-test>
125SIM=GL make
126```
127
128# User Project Example DV
129
130The directory includes four tests for the counter user-project example:
131
132### IO Ports Test
133
134* This test is meant to verify that we can configure the pads for the user project area. The firmware configures the lower 8 IO pads in the user space as outputs:
135
136 ```c
137 reg_mprj_io_0 = GPIO_MODE_USER_STD_OUTPUT;
138 reg_mprj_io_1 = GPIO_MODE_USER_STD_OUTPUT;
139 .....
140 reg_mprj_io_7 = GPIO_MODE_USER_STD_OUTPUT;
141 ```
142
143* Then, the firmware applies the pad configuration by enabling the serial transfer on the shift register responsible for configuring the pads and waits till the transfer is done.
144 ```c
145 reg_mprj_xfer = 1;
146 while (reg_mprj_xfer == 1);
147 ```
148
149* The testbench success criteria is that we can observe the counter value on the lower 8 I/O pads. This criteria is checked by the testbench through observing the values on the I/O pads as follows:
150
151 ```verilog
152 wait(mprj_io_0 == 8'h01);
153 wait(mprj_io_0 == 8'h02);
154 wait(mprj_io_0 == 8'h03);
155 ....
156 wait(mprj_io_0 == 8'hFF);
157 ```
158
159* If the testbench fails, it will print a timeout message to the terminal.
160
161### Logic Analyzer Test 1
162
163* This test is meant to verify that we can use the logic analyzer to monitor and write signals in the user project from the management SoC. Firstly, the firmware configures the upper 16 pads as outputs from the managent SoC, applies the configuration by initiating the serial transfer on the shift register, and writes a value on the pads to indicate the end of pad configuration and the start of the test.
164
165 ```c
166 reg_mprj_io_31 = GPIO_MODE_MGMT_STD_OUTPUT;
167 reg_mprj_io_30 = GPIO_MODE_MGMT_STD_OUTPUT;
168 .....
169 reg_mprj_io_16 = GPIO_MODE_MGMT_STD_OUTPUT;
170
171 reg_mprj_xfer = 1;
172 while (reg_mprj_xfer == 1);
173
174 // Flag start of the test
175 reg_mprj_datal = 0xAB400000;
176 ```
177
178 This is done to flag the start/success/end of the simulation by writing a certain value to the I/Os which is then checked by the testbench to know whether the test started/ended/succeeded. For example, the testbench checks on the value of the upper 16 I/Os, if it is equal to `16'hAB40`, then we know that the test started.
179
180 ```verilog
181 wait(checkbits == 16'hAB40);
182 $display("LA Test 1 started");
183 ```
184
185* Then, the firmware configures the logic analyzer (LA) probes `[31:0]` as inputs to the management SoC to monitor the counter value, and configure the logic analyzer probes `[63:32]` as outputs from the management SoC (inputs to the user_proj_example) to set the counter initial value. This is done by writing to the LA probes enable registers.
186
187
188 ```c
189 reg_la0_ena = 0xFFFFFFFF; // [31:0] inputs to mgmt_soc
190 reg_la1_ena = 0x00000000; // [63:32] outputs from mgmt_soc
191 ```
192
193* Then, the firmware writes an initial value to the counter through the LA1 data register. Afte writing the counter value, the LA probes are disabled to prevent the counter write signal from being always set to one.
194
195 ```c
196 reg_la1_data = 0x00000000; // Write zero to count register
197 reg_la1_ena = 0xFFFFFFFF; // Disable probes
198 ```
199
200* The firmware then waits till the count value exceeds 500 and flags the success of the test by writing `0xAB41` to the upper 16 pads. The firmware reads the count value through the logic analyzer probes `[31:0]`
201
202 ```c
203 if (reg_la0_data > 0x1F4) { // Read current count value through LA
204 reg_mprj_datal = 0xAB410000; // Flag success of the test
205 break;
206 }
207 ```
208
209### Logic Analyzer Test 2
210
211* This test is meant to verify that we can drive the clock and reset signals for the user project example through the logic analyzer. In the [user_proj_example](verilog/rtl/user_proj_example.v) RTL, the clock can either be supplied from the `wb_clk_i` or from the logic analyzer through bit `[64]`. Similarly, the reset signal can be supplied from the `wb_rst_i` or through `LA[65]`. The firmware configures the clk and reset LA probes as outputs from the management SoC by writing to the LA2 enable register.
212
213 ```c
214 reg_la2_ena = 0xFFFFFFFC; // Configure LA[64] LA[65] as outputs from the cpu
215 ```
216
217* Then, the firmware supplies both clock reset signals through LA2 data register. First, both are set to one. Then, reset is driven to zero and the clock is toggled for 6 clock cycles.
218
219 ```c
220 reg_la2_data = 0x00000003; // Write one to LA[64] and LA[65]
221 for (i=0; i<11; i=i+1) { // Toggle clk & de-assert reset
222 clk = !clk;
223 reg_la2_data = 0x00000000 | clk;
224 }
225 ```
226* The testbench success criteria is that the firmware reads a count value of five through the LA probes.
227 ```c
228 if (reg_la0_data == 0x05) {
229 reg_mprj_datal = 0xAB610000; // FLag success of the test
230 }
231 ```
232
233### Wishbone Test
234
235* This test is meant to verify that we can read and write to the count register through the wishbone port. The firmware writes a value of `0x2710` to the count register, then reads back the count value after some time. The read and write transactions happen through the management SoC wishbone bus and are initiated by either writing or reading from the user project address on the wishbone bus.