Skip to content

Commit 3aa00ad

Browse files
Update p4-lab1.md
1 parent 4acc8a7 commit 3aa00ad

File tree

1 file changed

+47
-15
lines changed

1 file changed

+47
-15
lines changed

lec2/p4-lab1.md

Lines changed: 47 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -384,6 +384,9 @@ qemu-system-riscv64 \
384384
-device loader,file=target/riscv64gc-unknown-none-elf/release/os.bin,addr=0x80200000 \
385385
-s -S
386386
```
387+
<!---s:启动GDB服务器在默认端口上进行监听。这允许开发者使用GNU调试器(GDB)连接到虚拟机以进行调试。
388+
-S:在CPU执行第一条指令前暂停虚拟机。这对于调试非常有用,因为它允许开发人员在任何代码执行之前先连接GDB,并设置断点或检查初始状态。
389+
-->
387390

388391
```
389392
riscv64-unknown-elf-gdb \
@@ -393,7 +396,10 @@ riscv64-unknown-elf-gdb \
393396
[GDB output]
394397
0x0000000000001000 in ?? ()
395398
```
396-
399+
<!---加载指定的可执行文件。
400+
设置GDB的架构为RISC-V 64位
401+
指定GDB连接到一个远程目标,
402+
-->
397403

398404
---
399405
提纲
@@ -417,35 +423,61 @@ riscv64-unknown-elf-gdb \
417423
![bg right:60% 90%](figs/function-call.png)
418424

419425

426+
420427
---
421428
#### call/return伪指令
422-
423429
伪指令 | 基本指令 | 含义 |
424430
:----------------|:-----------|:----------|
425-
ret | jalr x0, x1, 0 (jalr rd, rs1, imm) | 函数返回
426-
call offset | auipc x6, offset[31:12]; jalr x1, x6, offset[11:0] | 函数调用
431+
call offset | auipc x6, offset[31:12]; jalr x1, x6, offset[11:0] | 调用
432+
ret | jalr x0, x1, 0 | 返回
433+
434+
435+
函数调用核心机制:
436+
- 在函数调用时,通过 call 伪指令保存返回地址并实现跳转;
437+
- 在函数返回时,通过 ret 伪指令回到跳转之前的下一条指令继续执行
438+
439+
440+
---
441+
#### call/return伪指令
442+
443+
伪指令 | 基本指令 | 含义 |
444+
:----------|:-----------|:----------|
445+
call offset | auipc x6, offset[31:12]; jalr x1, x6, offset[11:0]| 调用
446+
ret| jalr x0, x1, 0 (jalr rd, rs1, imm)|返回
447+
448+
449+
* auipc(add upper immediate to pc)被用来构建 PC 相对的地址,使用的是 U 型立即数。 auipc将 offset 的高 20 位(即 offset[31:12])与当前 PC 相加,并将结果存储到寄存器 x6 中。
450+
* jalr x1, x6, offset[11:0] 将 x6 中的基址与 offset 的低 12 位(即 offset[11:0])相加,得到完整的跳转地址。
451+
* 同时,把下一条指令的地址(即 PC + 4)存入 x1 寄存器。
452+
453+
<!--auipc 以低 12 位补 0,高 20 位是 U 型立即数的方式形成 32 位偏移量,然后和 PC 相加,最后把结果保存在寄存器 x6。
454+
455+
456+
jalr 跳转到rs1+imm地址,并在rd寄存器中存储返回地址
457+
-->
427458

428-
auipc(add upper immediate to pc)被用来构建 PC 相对的地址,使用的是 U 型立即数。 auipc 以低 12 位补 0,高 20 位是 U 型立即数的方式形成 32 位偏移量,然后和 PC 相加,最后把结果保存在寄存器 x1。
459+
460+
---
461+
#### call/return伪指令
462+
463+
伪指令 | 基本指令 | 含义 |
464+
:----------|:-----------|:----------|
465+
call offset | auipc x6, offset[31:12]; jalr x1, x6, offset[11:0]| 调用
466+
ret| jalr x0, x1, 0 (jalr rd, rs1, imm)|返回
467+
468+
469+
* 伪指令 ret (jalr x0, x1, 0) 翻译为 jalr x0, 0(x1),含义为跳转到寄存器 ra(即x1)保存的返回地址。
429470

430471
---
431472

432473
#### 函数调用跳转指令
433474
![w:1000](figs/fun-call-in-rv.png)
434475

435-
伪指令 ret 翻译为 jalr x0, 0(x1),含义为跳转到寄存器 ra(即x1)保存的地址。
476+
<!--伪指令 ret 翻译为 jalr x0, 0(x1),含义为跳转到寄存器 ra(即x1)保存的地址。-->
436477
*[快速入门RISC-V汇编的文档](https://github.com/riscv-non-isa/riscv-asm-manual/blob/master/riscv-asm.md)*
437478

438479

439-
---
440-
#### call/return伪指令
441-
伪指令 | 基本指令 | 含义 |
442-
:----------------|:-----------|:----------|
443-
ret | jalr x0, x1, 0 | 函数返回
444-
call offset | auipc x6, offset[31:12]; jalr x1, x6, offset[11:0] | 函数调用
445480

446-
函数调用核心机制:
447-
- 在函数调用时,通过 call 伪指令保存返回地址并实现跳转;
448-
- 在函数返回时,通过 ret 伪指令回到跳转之前的下一条指令继续执行
449481

450482

451483
---

0 commit comments

Comments
 (0)