Skip to content
This repository was archived by the owner on Jul 6, 2023. It is now read-only.

Commit b525b1d

Browse files
committed
feat: Final RV64 CPU with MMU and kernel
1 parent b77d285 commit b525b1d

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

85 files changed

+24762
-706
lines changed

.gitignore

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,6 @@
11
.DS_Store
22

33
src/core.vvp
4-
src/dump.vcd
4+
src/dump.vcd
5+
6+
src/dut_changes.txt

README.md

Lines changed: 9 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -6,7 +6,9 @@
66
77
## 实验进度
88

9-
系统贯通课程会逐步实现一个 RISC-V 五级流水线 CPU,并实现异常处理、分支预测、Cache 等功能。本 repo 通过分支、tag 等来记录实验进度,保存各阶段成果。
9+
系统贯通课程会逐步实现一个 RISC-V 五级流水线 CPU,并实现异常处理、分支预测、Cache、MMU 等功能,并在其上运行自己编写的简易 kernel。
10+
11+
本 repo 通过分支、tag 等来记录实验进度,保存各阶段成果。
1012

1113
- [x] 系统 Ⅰ lab5-1/lab5-2:单周期 CPU
1214
- [x] extra:单周期 CPU with 特权指令/异常处理
@@ -18,6 +20,12 @@
1820
- 使用了提供的实验框架而非自己的,就不放在 repo 里了
1921
- [x] 系统 Ⅲ lab2:流水线 CPU with Cache
2022
- 使用了提供的实验框架而非自己的,就不放在 repo 里了
23+
- [x] 系统 Ⅲ lab Xpart:软硬件贯通实验,主要部分是实现 MMU 以及调试 kernel
24+
- RV64IZicsr 全部指令(除去 fence ebreak wfi)
25+
- 包含 Supervisor 和 User 两个特权级
26+
- 实现了 Bare 和 Sv39 两种分页模式
27+
- 支持串口输出
28+
- 展示 slides 在:[slides.tonycrane.cc/sys3-xpart-pre](https://slides.tonycrane.cc/sys3-xpart-pre/)
2129

2230
## 实验环境
2331

src/CPU.v

Lines changed: 158 additions & 238 deletions
Large diffs are not rendered by default.

src/Core.v

Lines changed: 32 additions & 19 deletions
Original file line numberDiff line numberDiff line change
@@ -6,19 +6,25 @@ module Core (
66
input wire step,
77
input wire debug_mode,
88
input wire [4:0] debug_reg_addr, // register address
9-
output wire [31:0] chip_debug_out0,
10-
output wire [31:0] chip_debug_out1,
11-
output wire [31:0] chip_debug_out2,
12-
output wire [31:0] chip_debug_out3
9+
output wire [63:0] chip_debug_out0,
10+
output wire [63:0] chip_debug_out1,
11+
output wire [63:0] chip_debug_out2,
12+
output wire [63:0] chip_debug_out3,
13+
output wire [7:0] sim_uart_char_out,
14+
output wire sim_uart_char_valid
1315
);
1416
wire rst, mem_write, mem_clk, cpu_clk;
15-
wire [31:0] inst, core_data_in, addr_out, core_data_out, pc_out;
17+
wire [31:0] inst;
18+
wire [63:0] core_data_in, addr_out, core_data_out, pc_out;
1619
reg [31:0] clk_div;
17-
wire [31:0] debug_reg;
20+
wire [63:0] debug_reg;
21+
wire [63:0] satp;
22+
wire stall, mem_read;
23+
wire [2:0] width;
1824

1925
assign rst = ~aresetn;
2026

21-
CPU cpu(
27+
CPU cpu (
2228
.clk(cpu_clk),
2329
.rst(rst),
2430
.inst(inst),
@@ -27,8 +33,12 @@ module Core (
2733
.data_out(core_data_out), // data to data memory
2834
.pc_out(pc_out), // connect to instruction memory
2935
.mem_write(mem_write),
36+
.mem_read(mem_read),
3037
.debug_reg_addr(debug_reg_addr),
31-
.debug_reg(debug_reg)
38+
.debug_reg(debug_reg),
39+
.satp(satp),
40+
.data_width(width),
41+
.stall(stall)
3242
);
3343

3444
always @(posedge clk) begin
@@ -38,21 +48,24 @@ module Core (
3848
assign mem_clk = ~clk_div[0];
3949
assign cpu_clk = debug_mode ? clk_div[0] : step;
4050

41-
ROM rom_unit (
42-
.address(pc_out / 4),
43-
.out(inst)
44-
);
45-
46-
RAM ram_unit (
47-
.clk(mem_clk),
48-
.we(mem_write),
49-
.address(addr_out / 4),
51+
MMU mmu (
52+
.clk(mem_clk), .rst(rst),
53+
.inst_addr(pc_out),
54+
.data_addr(addr_out),
5055
.write_data(core_data_out),
51-
.read_data(core_data_in)
56+
.mem_write(mem_write),
57+
.mem_read(mem_read),
58+
.width(width),
59+
.satp(satp),
60+
.inst_out(inst),
61+
.read_data(core_data_in),
62+
.stall_pipeline(stall),
63+
.sim_uart_char_out(sim_uart_char_out),
64+
.sim_uart_char_valid(sim_uart_char_valid)
5265
);
5366

5467
assign chip_debug_out0 = pc_out;
5568
assign chip_debug_out1 = addr_out;
56-
assign chip_debug_out2 = inst;
69+
assign chip_debug_out2 = {32'b0, inst};
5770
assign chip_debug_out3 = debug_reg;
5871
endmodule

src/CoreSim.v

Lines changed: 10 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -2,23 +2,28 @@
22

33
module CoreSim;
44
reg clk, rst;
5-
Core core(
5+
Core core (
66
.clk(clk),
77
.aresetn(~rst),
88
.step(1'b0),
99
.debug_mode(1'b1),
1010
.debug_reg_addr(5'b0)
1111
);
1212

13-
initial begin
14-
$dumpvars(0, CoreSim);
15-
#700000 $finish;
16-
end
13+
// initial begin
14+
// $dumpvars(0, CoreSim);
15+
// // #700000 $finish;
16+
// // #2000 $finish;
17+
// // #1000000000 $finish;
18+
// end
1719

1820
initial begin
1921
clk = 0;
2022
rst = 1;
2123
#2 rst = 0;
2224
end
2325
always #1 clk = ~clk;
26+
// always #5000000 begin
27+
// $display("pc: %h", core.cpu.MEM_WB_pc);
28+
// end
2429
endmodule

src/MMUSim.v

Lines changed: 35 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,35 @@
1+
`timescale 1ns / 1ps
2+
3+
module MMUSim;
4+
reg clk, rst;
5+
wire [31:0] inst_out;
6+
wire [63:0] read_data;
7+
wire stall_pipeline;
8+
9+
MMU mmu (
10+
.clk(clk), .rst(rst),
11+
.inst_addr(64'hffffffe000200000),
12+
.data_addr(64'hffffffe00020b000),
13+
// .data_addr(64'h800),
14+
.write_data(64'h0000000000000000),
15+
.mem_write(1'b0),
16+
.mem_read(1'b1),
17+
.width(3'b011),
18+
.satp(64'h8000000000080202),
19+
.inst_out(inst_out),
20+
.read_data(read_data),
21+
.stall_pipeline(stall_pipeline)
22+
);
23+
24+
initial begin
25+
$dumpvars(0, MMUSim);
26+
#200 $finish;
27+
end
28+
29+
initial begin
30+
clk = 0;
31+
rst = 1;
32+
#2 rst = 0;
33+
end
34+
always #1 clk = ~clk;
35+
endmodule

src/Makefile

Lines changed: 15 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -6,13 +6,27 @@ all: compile simulate
66

77
compile:
88
iverilog -o core.vvp -y . \
9-
-y components -y memory -y utils \
9+
-y components -y utils \
1010
-I headers \
1111
CoreSim.v
1212

1313
simulate:
1414
vvp -n core.vvp
15+
16+
open:
1517
$(GTKWAVE) dump.vcd wave.gtkw
1618

19+
mmu: compile-mmu simulate-mmu
20+
21+
compile-mmu:
22+
iverilog -o core.vvp -y . \
23+
-y components -y utils \
24+
-I headers \
25+
MMUSim.v
26+
27+
simulate-mmu:
28+
vvp -n core.vvp
29+
$(GTKWAVE) dump.vcd wave_mmu.gtkw
30+
1731
clean:
1832
rm -f core.vvp dump.vcd

src/Top.sv

Lines changed: 44 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -10,30 +10,44 @@ module Top(
1010
output [ 2:0] rgb1,
1111
output [ 2:0] rgb2,
1212
output [ 7:0] num_csn,
13-
output [ 7:0] num_an
13+
output [ 7:0] num_an,
14+
output UART_TXD
1415
);
1516
logic aresetn;
1617
logic step;
1718

18-
logic [31:0] chip_debug_out0;
19-
logic [31:0] chip_debug_out1;
20-
logic [31:0] chip_debug_out2;
21-
logic [31:0] chip_debug_out3;
19+
logic [63:0] chip_debug_out0;
20+
logic [63:0] chip_debug_out1;
21+
logic [63:0] chip_debug_out2;
22+
logic [63:0] chip_debug_out3;
23+
24+
logic [7:0] uart_data, sim_uart_char;
25+
logic uart_send, uart_ready, sim_uart_char_valid;
26+
logic [31:0] clk_div;
27+
logic clk_cpu;
28+
29+
always @(posedge clk) begin
30+
if (!resetn) clk_div <= 0;
31+
else clk_div <= clk_div + 1;
32+
end
33+
assign clk_cpu = clk_div[3];
2234

2335
Core chip_inst(
24-
.clk(clk),
36+
.clk(clk_cpu),
2537
.aresetn(aresetn),
2638
.step(step),
2739
.debug_mode(switch[15]),
2840
.debug_reg_addr(switch[11:7]),
2941
.chip_debug_out0(chip_debug_out0),
3042
.chip_debug_out1(chip_debug_out1),
3143
.chip_debug_out2(chip_debug_out2),
32-
.chip_debug_out3(chip_debug_out3)
44+
.chip_debug_out3(chip_debug_out3),
45+
.sim_uart_char_out(sim_uart_char),
46+
.sim_uart_char_valid(sim_uart_char_valid),
3347
);
3448

3549
IO_Manager io_manager_inst(
36-
.clk(clk),
50+
.clk(clk_cpu),
3751
.resetn(resetn),
3852

3953
// to chip
@@ -54,9 +68,27 @@ module Top(
5468
.debug1({16'b0, switch[15:0]}),
5569
.debug2({12'b0, 3'b0, button[4], 3'b0, button[3], 3'b0, button[2], 3'b0, button[1], 3'b0, button[0]}),
5670
.debug3(32'h12345678),
57-
.debug4(chip_debug_out0),
58-
.debug5(chip_debug_out1),
59-
.debug6(chip_debug_out2),
60-
.debug7(chip_debug_out3)
71+
.debug4(chip_debug_out0[31:0]),
72+
.debug5(chip_debug_out1[31:0]),
73+
.debug6(chip_debug_out2[31:0]),
74+
.debug7(chip_debug_out3[31:0])
75+
);
76+
77+
UART_TX_CTRL uart_tx_ctrl (
78+
.SEND(uart_send),
79+
.DATA(uart_data),
80+
.CLK(clk),
81+
.READY(uart_ready),
82+
.UART_TX(UART_TXD)
83+
);
84+
85+
uart_buffer UART_BUFF (
86+
.clk(clk_cpu),
87+
.rst(~aresetn),
88+
.ready(uart_ready),
89+
.sim_uart_char_valid(sim_uart_char_valid),
90+
.sim_uart_char(sim_uart_char),
91+
.send(uart_send),
92+
.datao(uart_data)
6193
);
6294
endmodule
File renamed without changes.

0 commit comments

Comments
 (0)