diff --git a/README.assets/DongshanPI-D1s-V2TopFuction.png b/README.assets/DongshanPI-D1s-V2TopFuction.png deleted file mode 100644 index ffd83105b1f376af6a0ae6dc5566c1683a0a7fc8..0000000000000000000000000000000000000000 Binary files a/README.assets/DongshanPI-D1s-V2TopFuction.png and /dev/null differ diff --git a/README.assets/git_day1.png b/README.assets/git_day1.png deleted file mode 100644 index 0b5269344fc1d0127201889ebff0cf0afbc27860..0000000000000000000000000000000000000000 Binary files a/README.assets/git_day1.png and /dev/null differ diff --git a/README.assets/image-20221230183307481.png b/README.assets/image-20221230183307481.png deleted file mode 100644 index 32ae018f6c41304773d135054e25430b20392d42..0000000000000000000000000000000000000000 Binary files a/README.assets/image-20221230183307481.png and /dev/null differ diff --git a/README.assets/image-20221230183836681.png b/README.assets/image-20221230183836681.png deleted file mode 100644 index df53c681a4012500bce5956c4497bc7aa038763b..0000000000000000000000000000000000000000 Binary files a/README.assets/image-20221230183836681.png and /dev/null differ diff --git a/README.assets/image-20221230185133821.png b/README.assets/image-20221230185133821.png deleted file mode 100644 index 36943493ef90d4b016cd92acead0d446acfcd1f0..0000000000000000000000000000000000000000 Binary files a/README.assets/image-20221230185133821.png and /dev/null differ diff --git a/README.assets/image-20230206160858602.png b/README.assets/image-20230206160858602.png deleted file mode 100644 index ecf3308399e5b4523a7559f146e0837b50727af5..0000000000000000000000000000000000000000 Binary files a/README.assets/image-20230206160858602.png and /dev/null differ diff --git a/README.assets/image-20230206162126447.png b/README.assets/image-20230206162126447.png deleted file mode 100644 index e102ea48ca87ac6f92abff67604f2dc9609eddef..0000000000000000000000000000000000000000 Binary files a/README.assets/image-20230206162126447.png and /dev/null differ diff --git a/README.assets/image-20230206162745308.png b/README.assets/image-20230206162745308.png deleted file mode 100644 index 97e079190b0fdd435b35b944119262bc294ac87d..0000000000000000000000000000000000000000 Binary files a/README.assets/image-20230206162745308.png and /dev/null differ diff --git a/README.assets/image-20230206163356032.png b/README.assets/image-20230206163356032.png deleted file mode 100644 index ca46f54f88b1a10d22cadad02938d087f3fc0f28..0000000000000000000000000000000000000000 Binary files a/README.assets/image-20230206163356032.png and /dev/null differ diff --git a/README.assets/image-20230206163444439.png b/README.assets/image-20230206163444439.png deleted file mode 100644 index 9160c84246866e386b64dffaddccc21d07c77c79..0000000000000000000000000000000000000000 Binary files a/README.assets/image-20230206163444439.png and /dev/null differ diff --git a/README.assets/image-20230206164624420.png b/README.assets/image-20230206164624420.png deleted file mode 100644 index dcf2678354251f5774c0102ca074da02bd6ca20f..0000000000000000000000000000000000000000 Binary files a/README.assets/image-20230206164624420.png and /dev/null differ diff --git a/README.assets/image-20230206164841521.png b/README.assets/image-20230206164841521.png deleted file mode 100644 index 5542e4bae81b48a9e608a69e111b0c3d6ef485a3..0000000000000000000000000000000000000000 Binary files a/README.assets/image-20230206164841521.png and /dev/null differ diff --git a/README.assets/image-20230206165026922.png b/README.assets/image-20230206165026922.png deleted file mode 100644 index c5c653d6f4980878499e021f901998517012728f..0000000000000000000000000000000000000000 Binary files a/README.assets/image-20230206165026922.png and /dev/null differ diff --git a/README.assets/image-20230206174701108.png b/README.assets/image-20230206174701108.png deleted file mode 100644 index 12d7152ccb85fc3bfc360ebc1f20ca2117589de1..0000000000000000000000000000000000000000 Binary files a/README.assets/image-20230206174701108.png and /dev/null differ diff --git a/README.assets/image-20230206174810855.png b/README.assets/image-20230206174810855.png deleted file mode 100644 index 5cb35bf05c64c6d6fe53bb0393a224e94aa1cdbd..0000000000000000000000000000000000000000 Binary files a/README.assets/image-20230206174810855.png and /dev/null differ diff --git a/README.assets/image-20230206174957082.png b/README.assets/image-20230206174957082.png deleted file mode 100644 index 0881a7fd8bd2a07552a64dfee70a902312ead3c9..0000000000000000000000000000000000000000 Binary files a/README.assets/image-20230206174957082.png and /dev/null differ diff --git a/README.assets/image-20230206175015091.png b/README.assets/image-20230206175015091.png deleted file mode 100644 index 26a92d2cd07eaae106b0db7f04402b568f8e06f6..0000000000000000000000000000000000000000 Binary files a/README.assets/image-20230206175015091.png and /dev/null differ diff --git a/README.assets/image-20230206175153041.png b/README.assets/image-20230206175153041.png deleted file mode 100644 index 1bcf89c136f85cb3cab285a01445cfa60ff3288b..0000000000000000000000000000000000000000 Binary files a/README.assets/image-20230206175153041.png and /dev/null differ diff --git a/README.assets/image-20230206182706010.png b/README.assets/image-20230206182706010.png deleted file mode 100644 index 46c5c054719461caebbda1a511cf1048e7a7e905..0000000000000000000000000000000000000000 Binary files a/README.assets/image-20230206182706010.png and /dev/null differ diff --git a/README.assets/zadig.png b/README.assets/zadig.png deleted file mode 100644 index 10083fa43609734b98ea6984899df511f7fda1be..0000000000000000000000000000000000000000 Binary files a/README.assets/zadig.png and /dev/null differ diff --git a/README.md b/README.md index aec7d974595cec5c19324c64dab407d047883808..5f885d23fbd66160a7396f54671b9adb6c24dab0 100644 --- a/README.md +++ b/README.md @@ -1,127 +1,629 @@ -# 《RISC-V体系结构编程与实践》for DongshanPI-D1s +[toc] -本分支提供基于DongShanPI D1s开发板验证过的《RISC-V体系结构编程与实践》实验参考代码,由韦东山团队提供技术支持。 -DongShanPI D1s开发板购买方式如下: -[DongShanPI D1s + RISC-V图书套餐 购买链接](https://item.taobao.com/item.htm?&id=695941169493) -实验环境: -1. 主机硬件平台: DongshanPI-D1s开发板主板 -2. 主机操作系统:Windows10/ubuntu -3. GCC版本:9(riscv64-linux-gnu-gcc) -4. GDB版本:gdb-multiarch。 +# 第1章 环境搭建 -![](README.assets/DongshanPI-D1s-V2TopFuction.png) +## 1.1 开发板介绍 -## 配置windows下开发环境 +张天飞老师编写的《RISC-V体系结构编程与实践》,里面的源码是基于QEMU模拟器的,可以认为它是一款虚拟的开发板。如果需要在真实开发板上学习,可以使用百问网的DongshanPI-D1S开发板。 -### 安装Git Bash +DongshanPI-D1S是百问网推出的一款基于RISC-V 架构的学习裸机、RTOS的最小开发板。集成CKLink调试器,支持OTG烧录、GDB调试、串口打印,并将主芯片所有的信号全部引出,其中左右两侧兼容了树莓派的电源信号定义,可以很方便扩展模块。 -进入 **05_开发配套工具** 先安装 `Git-2.39.1-64-bit.exe` +D1S是全志公司针对智能解码市场推出的高性价比AIoT芯片,它使用阿里平头哥的64bit RISC-V架构的C906处理器,内置了64M DDR2,支持FreeRTOS、RT-Thread等RTOS,也支持Linux系统。同时集成了大量自研的音视频编解码相关IP,可以支持H.265、H.264、MPEG-1/2/4、JPEG等全格式视频解码,支持ADC、DAC、12S、PCM、DMIC、OWA等多种音频接口,可以广泛应用于智能家居面板、智能商显、工业控制、车载等产品。 -在Windows下,Git名为msysGit,从 [https://gitforwindows.org](https://gitforwindows.org/) 上下载安装文件,双击安装即可,安装选项很多,使用默认选项即可。 如果下载慢,可以在百度上搜:Git-2.28.0-64-bit.exe,自行下载。 +![](pic/D1s_pic_1.png) -对于Windows或Linux,它们的命令行用法相似,对于Windows,进入Git命令行的方法是在 `开始->所有程序->Git` 下启动 Git Bash。 Git Bash的命令用法跟Linux完全一样,比如cd、ls等命令。 -安装完成后可以参考下图来打开 git bash工具 -![](README.assets/git_day1.png) +板子资料:http://download.100ask.net/boards/Allwinner/D1s/index.html -### 安装Cklink驱动软件 +购买地址:https://item.taobao.com/item.htm?id=688098912622 -进入 **05_开发配套工具\CKLinkServer** 安装windows下`T-Head-DebugServer-windows-V5.16.6-20221102-1510.zip` 直接进行解压缩安装。 -连接开发板另一条TypeC线至开发板 Cklink 接口此时设备管理器会多出来一个 Cklink-lite的设备。 -此时我们长按开发板上的 **FEL按键** ,同时按一下 **RESET按键** 开发板就会自动进入调试模式。 +## 1.2 下载资料 -这时打开 T-HeadDebugServer会自动显示设备的CPU 信息以及GDB端口连接地址。 +资料分两部分:开发板通用资料、《RISC-V体系结构编程与实践》的D1S源码。前者比较庞大,放在百度网盘;后者放在书籍配套的GITEE网站。 -![image-20230206160858602](README.assets/image-20230206160858602.png) + +开发板通用资料: +打开http://download.100ask.net/boards/Allwinner/D1s/index.html,可以看到“D1s课程配套通用资料”对应的百度网盘地址,请自行下载。本课程主要使用下图所示的软件: -### 安装交叉编译工具链 + -进入到 **05_开发配套工具\toolchain** 目录,解压缩 `Xuantie-900-gcc-elf-newlib-mingw-V2.6.1-20220906.tar.gz` -解压缩完成后进入到 如下图红框所示这个目录 ,记住这个路径的完整目录(尽量不要包含中文) 然后将其 添加至系统的 Path环境变量内。 -![image-20230206162126447](README.assets/image-20230206162126447.png) +《RISC-V体系结构编程与实践》的D1S源码: +打开https://gitee.com/weidongshan/riscv_programming_practice,登录后按如下界面操作: +![](pic/D1s_pic_3.png) -![image-20230206162745308](README.assets/image-20230206162745308.png) -### 配置make工具 -进入 **05_开发配套工具\Make** 目录内,双击 `make-3.81.exe`开始安装,安装时请注意一下安装所在路径,等待安装完成后 我们需要将此路径添加至系统环境变量里面。 +点击“克隆/下载”按钮之后,如下点击“下载ZIP”即可: -![image-20230206174701108](README.assets/image-20230206174701108.png) +![](pic/D1s_pic_4.png) -添加完成后如下图所示,之后我们可以通过git bash命令进行验证。 +如果你没有点击“下载ZIP”,而是使用GIT命令来下载,那么下载成功后还需要执行如下命令: -![image-20230206174810855](README.assets/image-20230206174810855.png) +``` +git checkout DongShanPI_D1 +``` -### 配置Xfel工具 -进入 **05_开发配套工具\xfel目录内**,复制完整的路径,将其单独添加到 windows 环境变量内。 -![image-20230206163444439](README.assets/image-20230206163444439.png) +## 1.3 安装软件 -在windows下使用xfel烧录工具之前,我们需要先连接一条 Typec线至开发板OTG接口 连接成功后后,长按 **FEL按键** 此时按一下 **RESET按键** 开发板就会进入烧录模式,如果之前安装过 全志的usb烧写驱动,电脑的设备管理器会出来一个 usb device设备,表明已经进入烧写模式成功。如果你的电脑没有安装驱动,会提示一个 位置设备 https://dongshanpi.com/DongshanNezhaSTU/03-QuickStart/#usb 那么请参考这篇文章安装一下驱动。 +需要安装如下5个软件,它们都位于网盘资料“开发板通用资料\05_开发配套工具\”目录下: -![image-20221230183307481](README.assets/image-20221230183307481.png) +① “Git\Git-2.39.1-64-bit.exe”:我们把它当做命令行,不能使用Windows自带的DOS命令行、Powershell(在里面无法执行make命令) -连接成功后,我们进入到 **05_开发配套工具\xfel\Drivers** 目录下,参考下图安装一下 **WinUSB**驱动,就可以使用xfel识别到设备了。 +② “make\make-3.81.exe”:make工具 -![zadig](README.assets/zadig.png) +③ “toolchain\Xuantie-900-gcc-elf-newlib-mingw-V2.6.1-gdbtui-20230210.tar.gz”:这是Windows版本的交叉编译工具,并且支持TUI +④ “CKLinkServer\T-Head-DebugServer-windows-V5.16.6-20221102-1510.zip”:这是调试服务软件 +⑤ “xfe\xfe.exe”:烧写工具 -### 验证工具配置 + -打开git bash界面 来依次验证工具是否正常。 +### 1.3.1 Git Bash -* 验证xfel烧录工具 +双击“开发板通用资料\05_开发配套工具\Git\Git-2.39.1-64-bit.exe”即可安装。 -先连接一条 Typec线至开发板OTG接口 连接成功后后,长按 **FEL按键** 此时按一下 **RESET按键** 开发板就会进入烧录模式,此时在 git bash终端里面 输入 `xfel.exe version`命令就可以识别到芯片的详细信息。 +启动Git Bash有两种方法: -![image-20230206164624420](README.assets/image-20230206164624420.png) +① 点击“开始->Git->Git Bash” +② 在文件浏览器进入某个目录后,在空白处点击右键弹出菜单后选择“Git Bash Here” +在Git Bash中各种命令的用法跟Linux完全一样,比如也有“cd”、“ls”、“rm”等命令。在Git Bash中,对路径的表示方法也跟Linux一样,比如D盘下的abc子目录使用“/d/abc”表示,而不是“D:\abc”。 -* 验证 交叉编译工具链 +在Git Bash中使用命令简单示范如下: -在 git bash输入` riscv64-unknown-elf-gcc -v ` 既可看到详细的工具链参数输出,表示已经配置成功 +![](pic/D1s_pic_5.png) -![image-20230206164841521](README.assets/image-20230206164841521.png) -* 验证make 命令 -在git bash输入`make -v`命令,如果可以显示出来版本,就表示已经可以使用。 +### 1.3.2 make -![image-20230206175015091](README.assets/image-20230206175015091.png) +双击“开发板通用资料\05_开发配套工具\make\make-3.81.exe”即可安装。安装时,要记住安装的路径,需要把安装路径下的bin目录放入环境变量Path里。 +![](pic/D1s_pic_6.png) +如下图把“C:\Program Files (x86)\GnuWin32\bin”添加进环境变量Path: -## 编译烧写程序 +![](pic/D1s_pic_7.png) -如下图为开发板的功能示意图,我们需要先将 配套的typec线 一根插至 黑色序号3. OTG烧录接口,用于进行供电和烧录系统操作。 +验证:启动Git Bash后执行“make -v”命令,如下图所示。 -![DongshanPI-D1s-V2TopFuction](README.assets/DongshanPI-D1s-V2TopFuction.png) +![](pic/D1s_pic_8.png) -首先进入到源码目录 **riscv_programming_practice-for-dongshan\chapter_2\benos** 在当前目录下,鼠标右键,点击 `git bash Here` -![image-20230206175153041](README.assets/image-20230206175153041.png) -在源码目录下 执行` make clean`清理缓存,之后执行`make`命令开始编译,编译完成后,可以执行` make burn`来自动烧录镜像到开发板内,可以看到如下图所示。 +### 1.3.3 交叉工具链 -注意:烧录开发板之前需要先将两根 typec线全都连接至开发板上,然后 长按 **FEL按键** 短按一下**RESET键** 进入烧录模式,之后就可以执行上述烧录步骤了,烧录完成后,可以使用串口工具 打开 Cklinke自带的 串口设备,波特率 115200 就可以看到程序的输出信息。 +把“开发板通用资料\05_开发配套工具\toolchain\Xuantie-900-gcc-elf-newlib-mingw-V2.6.1-gdbtui-20230210.tar.gz”解压即可,注意路径名不要有中文。 -![image-20230206182706010](README.assets/image-20230206182706010.png) +解压后要确认如下目录里的文件不是0字节: -## 使用GDB 调试 +![](pic/D1s_pic_9.png) + +使用有些解压工具比如banzip可能会得到0字节的文件,建议使用7-Zip解压。 + +解压成功后,可以看到“riscv64-unknown-elf-gcc.exe”文件,如下图所示: + +![](pic/D1s_pic_10.png) + +需要把“riscv64-unknown-elf-gcc.exe”文件所在目录放入Path环境变量里,具体方法可以参考《1.3.2 make》。结果如下图所示: + +![](pic/D1s_pic_11.png) + + + +验证:启动Git Bash后执行“riscv64-unknown-elf-gcc -v”命令,如下图所示(Git Bash支持命令补全功能,输入“risc”后按TAB键会自动补全命令)。 + +![](pic/D1s_pic_12.png) + + + +### 1.3.4 调试服务软件 + +先解压文件:“开发板通用资料\05_开发配套工具\CKLinkServer\T-Head-DebugServer-windows-V5.16.6-20221102-1510.zip”。 + +再双击里面的“setup.exe”即可安装。 + + + +### 1.3.5 烧写工具 + +把“开发板通用资料\05_开发配套工具\xfel”目录复制到其他非中文路径即可。 + +还需要把“xfel.exe”文件所在目录放入Path环境变量里,具体方法可以参考《1.3.2 make》。结果如下图所示: + +![](pic/D1s_pic_13.png) + + + +验证:启动Git Bash后执行“xfel --help”命令,如下图所示。 + +![](pic/D1s_pic_14.png) + + + +## 1.4 安装驱动 + +DongshanPI-D1S开发板各接口如下图所示: + +![](pic/D1s_pic_15.png) + +D1S自身支持USB-OTG烧录(对应上面的接口“3.OTG烧录接口”),这需要安装对应的驱动程序。 + +DongshanPI-D1S开发板集成了CKLink调试器(对应上面的接口“4.调试&串口接口”),它有2个功能:调试、USB串口,需要安装2个驱动程序。 + + + +### 1.4.1 OTG烧录驱动程序 + +使用USB线连接开发板的“3.OTG烧录接口”到电脑后,先按住“2.烧录模式按键”不松开,然后按下、松开“5.系统复位按键”,最后松开“2.烧录模式按键”,开发板就会进入烧录模式。 + +第一次使用烧录模式时,要先安装驱动程序,先运行程序“开发板通用资料\05_开发配套工具\xfel\Drivers\zadig-2.7.exe”,然后如下图操作: + +![](pic/D1s_pic_16.png) + + + +注意:上图的第4步里,按钮内容可能是“Install Driver”、“Replace Driver”或“Reinstall Driver”,都一样点击。 + + + + + +验证:安装好驱动程序后,使用按钮让板子进入烧录模式,然后在Git Bash中执行命令,可以检测到设备: + +![](pic/D1s_pic_17.png) + +如果没找到设备,可以多次尝试: + +① 使用按钮让开发板进入烧录模式 + +② 重新安装驱动、甚至重启电脑 + +③ 插到电脑的其他USB口 + + + +### 1.4.2 USB串口和调试器 + +使用USB线连接开发板的“4.调试&串口接口”到电脑后,它会自动安装2个驱动程序,打开设备管理器可以看到如下设备: + +![](pic/D1s_pic_18.png) + + + + + +# 第2章 体验第一个程序 + +## 2.1 编译烧录运行 + +### 2.1.1 编译 + +先进入源码目录,打开Git Bash,如下图操作: + +![](pic/D1s_pic_19.png) + +然后在Git Bash中执行“make”命令,可以生成benos_payload.bin文件,如下图所示: + +![](pic/D1s_pic_20.png) + + + +### 2.1.2 烧录运行 + +使用2条USB线,分别连接开发板的“3.OTG烧录接口”、“4.调试&串口接口”,使用串口工具打开串口,波特率设为115200,8个数据位,1个停止位,不使用流量控制。 + +烧录方法如下: + +① 先让开发板进入烧录模式: + +方法为:先按住“2.烧录模式按键”不松开,然后按下、松开“5.系统复位按键”,最后松开“2.烧录模式按键”。 + +② 然后在Git Bash开执行“make burn”命令 + +如下图所示: + +![](pic/D1s_pic_21.png) + +烧写成功后,按下、松开“5.系统复位按键”即可启动程序,可以在串口看到输出信息: + +![](pic/D1s_pic_22.png) + + + +## 2.2 调试 + +### 2.2.1 GDB常用命令 + +使用GDB调试时,涉及两个软件: + +① 在Git Bash中运行的“riscv64-unknown-elf-gdb”:它发出各类调试命令,比如连接调试服务软件(T-HeadDebugServer)、单步运行、查看变量等等 + +② T-HeadDebugServer:它就是“调试服务软件”,负责接收、处理各类调试命令 + + + +常见的命令如下表所示: + +| **命令** | **简写形式** | **说明** | +| ----------------- | ------------ | ------------------------------------------------------------ | +| target | | 连接调试服务器,比如: target remote 127.0.0.1:1025 | +| run | r | 运行程序 | +| continue | c、cont | 继续运行 | +| break | b | 设置断点,比如: b sbi_main.c:121 b sbi_main b \*0x20000 | +| delete | d | 删除断点 | +| disable | dis | 禁用断点 | +| info breakpoints | info b | 显示断点信息 | +| next | n | 执行下一行 | +| nexti | ni | 执行下一行(以汇编代码为单位) | +| step | s | 一次执行一行,包括函数内部 | +| setpi | si | 执行下一行 | +| list | l | 显示函数或行 | +| print | p | 显示表达式,比如: print a print $pc // 打印寄存器 print \*0x20000//打印内存 print /x a // 16进制打印 | +| x | | 显示内存内容,比如: x 0x20000 x /x 0x20000 //16进制 | +| info registers | infor r | 打印所有寄存器的值 | +| set | | 设置变量,比如: set var a=1 set \*(unsigned int \*)0x28000 = 0x55555555 set var $pc=0x22000 | +| finish | | 运行到函数结束 | +| help | h | 显示帮助一览 | +| backtrace | bt、where | 显示 backtrace | +| symbol-file | | 加载符号表,比如 symbol-file benos.elf | + + + +### 2.2.2 benos_payload程序组成 + +《RISC-V体系结构编程与实践》中的代码分为两部分: + +① mysbi.elf:运行于M模式的底层软件,提供各种系统服务 + +② benos.elf:运行于S模式的应用软件 + +benos_payload是这两部分程序的组合: + + + + + + + +### 2.2.2 benos_payload程序组成 + +《RISC-V体系结构编程与实践》中的代码分为两部分: + +① mysbi.elf:运行于M模式的底层软件,提供各种系统服务 + +② benos.elf:运行于S模式的应用软件 + +benos_payload是这两部分程序的组合: + +``` +benos_payload.elf = mysbi.elf + benos.elf +benos_payload.bin = mysbi.bin + benos.bin +``` + +烧写、运行benos_payload.bin时,会先运行mysbi程序,mysbi再启动benos。调试benos_payload.elf时,我们可以先调试mysbi,等benos启动后再调试benos。 + + + +### 2.2.3 调试准备工作 + +首先,启动CKLink的调试功能,方法为:把下图中蓝色箭头所指的拨码开关上的薄膜撕开,把所有拨码开关拨向左边(USB接口那边): + +![](pic/D1s_pic_23.png) + +然后,启动调试服务软件“T-HeadDebugServer”,它会自动检测到芯片,如下图所示: + +![](pic/D1s_pic_24.png) + +如果没有上图所示信息,有多种可能: + +① 没有自动识别: + +可以手动识别,如下图所示: + +![](pic/D1s_pic_25.png) + +② 板子上的程序有Bug,导致板子死机了:可以让板子先进入烧录模式,再按照步骤①操作 + +③ 提示1025端口被占用:运行任务管理器,把所有“T-HeadDebugServer”杀掉,再重新运行“T-HeadDebugServer” + + + +当“T-HeadDebugServer”识别出芯片后,就可以调试程序了,有2种方式: + +① 使用命令行模式调试 + +② 使用TUI模式调试 + + + +### 2.2.4 命令行调试示例 + +当“T-HeadDebugServer”识别出芯片后,就可以在Git Bash里执行“riscv64-unknown-elf-gdb benos_payload.elf”来调试程序了。 + +示例如下: + +``` +weidongshan@DESKTOP-TP8DH2I MINGW64 /d/abc/riscv_programming_practice/chapter_2/benos (DongShanPI_D1) +$ riscv64-unknown-elf-gdb benos_payload.elf +Reading symbols from benos_payload.elf... +(gdb) target remote 127.0.0.1:1025 // 连接调试服务软件 +Remote debugging using 127.0.0.1:1025 +0x000000000000a22a in ?? () +(gdb) load // 加载benos_payload.elf +Loading section .text.boot, size 0x44 lma 0x20000 + section progress: 100.0%, total progress: 0.38% +Loading section .text, size 0x538 lma 0x20044 + section progress: 100.0%, total progress: 7.81% +Loading section .rodata, size 0xc0 lma 0x2057c + section progress: 100.0%, total progress: 8.88% +Loading section .data, size 0x1000 lma 0x21000 + section progress: 100.0%, total progress: 31.66% +Loading section .payload, size 0x3000 lma 0x22000 + section progress: 100.0%, total progress: 100.00% +Start address 0x0000000000020000, load size 17980 +Transfer rate: 209 KB/sec, 1997 bytes/write. +(gdb) x /x 0x20000 // 检查0x20000是否被正确写入, +// 我们调试程序时可能因为上次的死机导致无法load +// 这时可以让板子进入烧录模式,再重新连接、重新加载 +0x20000 : 0x0300006f +(gdb) b sbi_main // 设置断点为sbi_main函数 +Breakpoint 1 at 0x204bc: file sbi/sbi_main.c, line 80. +(gdb) c // 执行 +Continuing. + +Breakpoint 1, sbi_main () at sbi/sbi_main.c:80 +80 sbi_set_pmp(0, 0, -1UL, PMP_RWX); +(gdb) n // 下一步 +84 val = read_csr(mstatus); +(gdb) b sbi_main.c:102 // 设置断点为sbi_main.c的102行 +Breakpoint 2 at 0x20564: file sbi/sbi_main.c, line 102. +(gdb) info b // 查看所有断点 +Num Type Disp Enb Address What +1 breakpoint keep y 0x00000000000204bc in sbi_main + at sbi/sbi_main.c:80 + breakpoint already hit 1 time +2 breakpoint keep y 0x0000000000020564 in sbi_main + at sbi/sbi_main.c:102 +(gdb) i b // 查看所有断点,简写的命令 +Num Type Disp Enb Address What +1 breakpoint keep y 0x00000000000204bc in sbi_main + at sbi/sbi_main.c:80 + breakpoint already hit 1 time +2 breakpoint keep y 0x0000000000020564 in sbi_main + at sbi/sbi_main.c:102 +(gdb) c // 继续执行 +Continuing. + +Breakpoint 2, sbi_main () at sbi/sbi_main.c:102 // 碰到断点了 +// 执行完下一句代码就会跳到benos程序 +102 asm volatile("mret"); +(gdb) si // 单步执行并进入函数,每次执行一条汇编语句 +0x0000000000022000 in payload_bin () // 现在要执行另一个程序benos了 +(gdb) symbol-file benos.elf // 读取benos.elf的符号表,否则你调试时无法知道函数、代码等信息 +Load new symbol table from "benos.elf"? (y or n) [answered Y; input not from terminal] +Reading symbols from benos.elf... +Error in re-setting breakpoint 1: Function "sbi_main" not defined. +Error in re-setting breakpoint 2: No source file named sbi_main.c. +(gdb) si // 单步执行并进入函数,每次执行一条汇编语句 +9 la sp, stacks_start +(gdb) b kernel_main // 设置断点为kernel_main函数 +Breakpoint 3 at 0x22020: file src/kernel.c, line 6. +(gdb) c // 继续执行 +Continuing. + +Breakpoint 3, kernel_main () at src/kernel.c:6 +6 sys_clock_init(); +(gdb) i r // 列出所有寄存器的值 +ra 0x204d0 0x204d0 +sp 0x24ff0 0x24ff0 +gp 0x0 0x0 +tp 0x0 0x0 +t0 0x1000 4096 +t1 0xfffffffffffff000 -4096 +t2 0x109 265 +fp 0xa00000900 0xa00000900 +s1 0x0 0 +a0 0x0 0 +a1 0x1f 31 +a2 0xffffffffffffffff -1 +a3 0x0 0 +a4 0xa00000100 42949673216 +a5 0x0 0 +a6 0x80 128 +a7 0x1c0 448 +s2 0x375bff17 928775959 +s3 0xff32dec 267595244 +s4 0x2eebeffb 787214331 +s5 0xffffffffffdf9ffd -2121731 +s6 0x355077ff 894466047 +s7 0xffffffffef7eeee9 -276893975 +s8 0x27034 159796 +s9 0xffffffffe6376ff3 -432574477 +s10 0xffffffffb9d37bfc -1177322500 +s11 0x78b47e70 2025094768 +t3 0x1 1 +t4 0xefe8 61416 +t5 0x8001 32769 +t6 0x0 0 +pc 0x22020 0x22020 +(gdb) l // 列出代码 +1 #include "clock.h" +2 #include "uart.h" +3 +4 void kernel_main(void) +5 { +6 sys_clock_init(); +7 uart_init(); +8 +9 while (1) { +10 uart_send_string("Welcome RISC-V!\r\n"); +(gdb) l +11 ; +12 } +13 } +(gdb) c // 继续执行 +Continuing. + +Program received signal SIGINT, Interrupt. // 按Ctrl+C停止程序 +read32 (addr=38797436) at include/io.h:23 +23 } +(gdb) quit // 退出调试 +``` + + + +上述调试过程中,用到的命令都有注释,摘抄如下: + +``` +$ riscv64-unknown-elf-gdb benos_payload.elf // 开始调试 +(gdb) target remote 127.0.0.1:1025 // 连接调试服务软件 +(gdb) load // 加载benos_payload.elf +(gdb) x /x 0x20000 // 检查0x20000是否被正确写入, +// 我们调试程序时可能因为上次的死机导致无法load +// 这时可以让板子进入烧录模式,再重新连接、重新加载 +(gdb) b sbi_main // 设置断点为sbi_main函数 +(gdb) c // 执行 +(gdb) n // 下一步 +(gdb) b sbi_main.c:102 // 设置断点为sbi_main.c的102行 +(gdb) info b // 查看所有断点 +(gdb) i b // 查看所有断点,简写的命令 +(gdb) c // 继续执行 +(gdb) si // 单步执行并进入函数,每次执行一条汇编语句 +(gdb) symbol-file benos.elf // 读取benos.elf的符号表,否则你调试时无法知道函数、代码等信息 +(gdb) si // 单步执行并进入函数,每次执行一条汇编语句 +(gdb) b kernel_main // 设置断点为kernel_main函数 +(gdb) c // 继续执行 +(gdb) i r // 列出所有寄存器的值 +(gdb) l // 列出代码 +(gdb) l +(gdb) c // 继续执行 +Program received signal SIGINT, Interrupt. // 按Ctrl+C停止程序 +(gdb) quit // 退出调试 +``` + + + +benos_payload.elf是2个程序的组合,调试的要点在于: + +① 调试第1个程序时,默认从benos_payload.elf里得到符号表 + +② 执行到第2个程序时,需要使用“symbol-file benos.elf”命令读取benos.elf的符号表,否则你调试时无法知道函数、代码等信息。 + +③ 怎么知道执行到了第2个程序?可以在sbi_main.c里如下红框代码处设置断点(比如“b sbi_main.c:102”),执行到断点后,再执行“si”命令就开始运行第2个程序了: + +![](pic/D1s_pic_26.png) + + + +### 2.2.5 TUI调试示例 + +当“T-HeadDebugServer”识别出芯片后,就可以在Powershell里执行“riscv64-unknown-elf-gdb -tui benos_payload.elf”来调试程序了。 + +注意:在Git Bash中无法使用TUI功能,需要使用Powershell。 + + + +先启动Powershell:进入源码目录后,按住shift键同时点击鼠标右键,在弹出的菜单里启动Powershell,如下图所示: + +![](pic/D1s_pic_27.png) + +在Powershell窗口,执行如下命令即可开始调试: + +``` +riscv64-unknown-elf-gdb -tui benos_payload.elf +``` + + + +执行上述命令后,可以得到如下界面(源码窗口里的汉字是乱码,暂时无法解决): + +![](pic/D1s_pic_28.png) + + + +使用TUI的便利在于可以方便地观看源码、反汇编码、寄存器,显示这些信息的窗口被称为layout。使用以下命令可以显示这些layout: + +① layout src:显示源码窗口 + +② layout asm:显示汇编窗口 + +③ layout regs:在之前的窗口上再显示寄存器窗口 + +④ layout split:显示源码、汇编窗口 + +⑤ layout next:显示下一个layout + +⑥ layout prev:显示上一个layout + +能输入各类GDB命令的窗口是“命令窗口”,它总是显示的。 + + + +要同时显示源码和寄存器,可以执行如下2个命令: + +``` +layout src +layout regs +``` + + + +要同时显示反汇编码和寄存器,可以执行如下2个命令: + +``` +layout asm +layout regs +``` + + + +要同时显示源码和反汇编码,可以执行如下命令: + +``` +layout split +``` + + + +使用TUI模式时,只是方便我们观看源码、反汇编码、寄存器,具体操作还是在命令窗口输入GDB命令,请参考《2.2.4 命令行调试示例》。 + + + +### 2.2.6 gdb脚本 + +如果不想每次执行“riscv64-unknown-elf-gdb benos_payload.elf”或“riscv64-unknown-elf-gdb -tui benos_payload.elf”后,都手工执行以下命令来连接调试服务软件: + +``` +(gdb) target remote 127.0.0.1:1025 // 连接调试服务软件 +``` + + + +可以把这些命令写入一个名为“.gdbinit”的文件里,注意这个文件名的第1个字符是“.”,它表示在Linux系统下它是一个隐藏文件。在Windows的文件浏览器里我们可以看见它,但是在Git Bash里执行“ls”命令看不到它,需要执行“ls -a”命令才能看见。 + +你可以在“.gdbinit”里放入更多命令,下面是一个例子: + +``` +target remote 127.0.0.1:1025 +load +b sbi_main.c:102 +``` diff --git a/README.pdf b/README.pdf deleted file mode 100644 index b537e3bf681443dbf5bf1e299ea0d6b82d264b3f..0000000000000000000000000000000000000000 Binary files a/README.pdf and /dev/null differ diff --git a/README_EN.md b/README_EN.md new file mode 100644 index 0000000000000000000000000000000000000000..0841fbce3a7e9d8cf968e56d3adacaceb24f59aa --- /dev/null +++ b/README_EN.md @@ -0,0 +1,547 @@ +[toc] + +## Chapter 1 Environment Construction + +## 1.1 Introduction to development board + +The source code in "RISC-V Architecture Programming and Practice" written by Zhang Tianfei is based on QEMU simulator, which can be regarded as a virtual development board. If you need to learn on the real development board, you can use the DongshanPI-D1S development board of Baiwen. + +DongshanPI-D1S is the smallest development board for learning bare metal and RTOS based on RISC-V architecture launched by Baiwen. The integrated CKLink debugger supports OTG burning, GDB debugging, serial port printing, and exports all the signals of the main chip. The left and right sides are compatible with the power signal definition of raspberry pie, which makes it easy to expand the module. + +D1S is an AIoT chip with high performance-price ratio launched by Quanzhi for the intelligent decoding market. It uses the C906 processor with 64bit RISC-V architecture of Alibaba Pingtou, and has 64M DDR2 built in. It supports FreeRTOS, RT-Thread and other RTOS, as well as Linux system. At the same time, it integrates a large number of self-developed audio and video codec-related IPs, which can support H.265, H.264, MPEG-1/2/4, JPEG and other full-format video decoding, and supports multiple audio interfaces such as ADC, DAC, 12S, PCM, DMIC, OWA, and can be widely used in smart home panel, smart business display, industrial control, car and other products. + +![](pic/D1s_pic_1.png) + + + +Board data:http://download.100ask.net/boards/Allwinner/D1s/index.html + +Purchase address:https://item.taobao.com/item.htm?id=688098912622 + + + +## 1.2 Download materials + +The data is divided into two parts: general data of development board and D1S source code of RISC-V Architecture Programming and Practice. The former is relatively large, which is placed on Baidu Netdisk; The latter is placed on the GITEE website supporting the book. + + + +General information of development board: +open http://download.100ask.net/boards/Allwinner/D1s/index.html , you can see the Baidu network disk address corresponding to "D1s course supporting general materials", please download it yourself. This course mainly uses the software shown below: + + + + + +D1S source code of RISC-V Architecture Programming and Practice: +open https://gitee.com/weidongshan/riscv_programming_practice After logging in, press the following interface to operate: + +![](pic/D1s_pic_3.png) + + + +After clicking the "Clone/Download" button, click "Download ZIP" as follows: + +![](pic/D1s_pic_4.png) + +If you do not click "Download ZIP" but use the GIT command to download, you need to execute the following command after the download is successful: + +``` +git checkout DongShanPI_D1 +``` + + + + + +## 1.3 安装软件 + +The following five software needs to be installed, which are all located in the directory of "Development Board General Data 05_Development Kit " of the network disk data: +① "Git Git-2.39.1-64-bit. exe": We regard it as a command line. We can't use the DOS command line and Powershell that comes with Windows (you can't execute the make command in it) +② "Make make-3.81. exe": make tool +③ "Toolchain Xuantie-900-gcc-elf-newlib-mingw-V2.6.1-gdbtui-20230210. tar. gz": This is a cross-compilation tool for Windows version and supports TUI +④ "CKLinkServer T-Head-DebugServer-windows-V5.16.6-20221102-1510. zip": This is the debugging service software +⑤ "Xfe xfe. exe": burning tool + + + +### 1.3.1 Git Bash + +Double-click "Development Board General Data 05_Development Kit Git Git-2.39.1-64-bit.exe" to install it. +There are two ways to start Git Bash: +① Click "Start ->Git ->Git Bash" +② After entering a directory in the file browser, right-click in the blank space and select "Git Bash Here" +The usage of various commands in Git Bash is exactly the same as that in Linux, such as "cd", "ls", and "rm". In Git Bash, the path is also represented in the same way as in Linux. For example, the abc subdirectory under disk D is represented by "/d/abc" instead of "D: abc". +A simple example of using commands in Git Bash is as follows: + +![](pic/D1s_pic_5.png) + + + +### 1.3.2 make + +Double-click "Development Board General Data 05_Development Kit make make-3.81.exe" to install it. When installing, remember the installation path. You need to put the bin directory under the installation path into the environment variable Path. + +![](pic/D1s_pic_6.png) + +Add "C: Program Files (x86) GnuWin32 bin" to the environment variable Path as shown below: + +![](pic/D1s_pic_7.png) + +Verification: After starting Git Bash, execute the "make - v" command, as shown in the following figure. + +![](pic/D1s_pic_8.png) + + + +### 1.3.3 cross tool chain + +Unpack the "Development Board General Data 05_Development Kit toolchain Xuantie-900-gcc-elf-newlib-mingw-V2.6.1-gdbtui-20230210. tar. gz", and note that the path name does not contain Chinese. +After decompression, make sure that the file in the following directory is not 0 bytes: + +![](pic/D1s_pic_9.png) + +Using some decompression tools, such as banzip, may result in 0 bytes of files. It is recommended to use 7-Zip for decompression. +After decompression, you can see the "riscv64-unknown-elf-gcc.exe" file, as shown in the following figure: + +![](pic/D1s_pic_10.png) + +You need to put the directory where the "riscv64-unknown-elf-gcc.exe" file is located into the Path environment variable. Please refer to 1.3.2 Make for details. The results are as follows: + +![](pic/D1s_pic_11.png) + + + +Verification: After starting Git Bash, execute the "riscv64-unknown-elf-gcc - v" command, as shown in the following figure (Git Bash supports the command completion function, and pressing TAB after entering "risc" will automatically complete the command). + +![](pic/D1s_pic_12.png) + + + +### 1.3.4 commissioning service software + +First extract the file: "Development Board General Data 05_Development Kit CKLinkServer T-Head-DebugServer-windows-V5.16.6-20221102-1510. zip". +Double-click "setup. exe" inside to install. + + + +### 1.3.5 burn tool + +Copy the "Development Board General Data 05_Development Kit xfel" directory to other non-Chinese paths. +You also need to put the directory where the "xfel. exe" file is located into the Path environment variable. Please refer to 1.3.2 Make for details. The results are as follows: + +![](pic/D1s_pic_13.png) + + + +Verification: After starting Git Bash, execute the "xfel -- help" command, as shown in the following figure. + +![](pic/D1s_pic_14.png) + + + +## 1.4 Installing driver + +The interfaces of DongshanPI-D1S development board are shown in the following figure: + +![](pic/D1s_pic_15.png) + +D1S itself supports USB-OTG burning (corresponding to the above interface "3. OTG burning interface"), which requires the installation of the corresponding driver. +The DongshanPI-D1S development board integrates the CKLink debugger (corresponding to the above interface "4. Debugging&Serial Port Interface"). It has two functions: debugging and USB serial port. Two drivers need to be installed. + + + + + +### 1.4.1 OTG burning driver + +After connecting the "3. OTG burning interface" of the development board with the USB cable to the computer, first press and hold the "2. Burning mode key" without releasing it, then press and release the "5. System reset key", and finally release the "2. Burning mode key", and the development board will enter the burning mode. +When using burn mode for the first time, install the driver first, run the program "Development Board General Data 05_ Development Kit xfel Drivers zadig-2.7. exe", and then operate as follows: + +![](pic/D1s_pic_16.png) + +Note: In step 4 of the above figure, the button content may be "Install Driver", "Replace Driver" or "Reinstall Driver", which are all clicked the same way. + + Verification: After installing the driver, use the button to put the board into burning mode, and then execute the command in Git Bash to detect the device: + +![](pic/D1s_pic_17.png) + +If the device is not found, you can try several times: +① Use the button to put the development board into burning mode +② Reinstall the driver or even restart the computer +③ Plug into other USB ports of the computer + + + +### 1.4.2 USB serial port and debugger + +After connecting the "4. Debugging&Serial Port Interface" of the development board with USB cable to the computer, it will automatically install 2 drivers. Open the device manager to see the following devices: + +![](pic/D1s_pic_18.png) + + + +#Chapter 2 Experience the first procedure +##2.1 Compile, burn and run +###2.1.1 Compilation + + + +## Chapter 2 Experience the first procedure + +### 2.1 Compile, burn and run + +### 2.1.1 Compilation + +​ Enter the source directory first and open Git Bash, as shown in the following figure: + +![](pic/D1s_pic_19.png) + +Then execute the "make" command in Git Bash to generate benos_ The payload.bin file is shown in the following figure: + +![](pic/D1s_pic_20.png) + + + +### 2.1.2 Burning operation + +Use two USB cables to connect "3. OTG burning interface" and "4. Debugging&serial port interface" of the development board respectively. Use the serial port tool to open the serial port. The baud rate is set to 115200,8 data bits and 1 stop bit, without using flow control. +The burning method is as follows: +① Let the development board enter the burning mode first: +The method is: first press and hold "2. Burn mode key" without releasing, then press and release "5. System reset key", and finally release "2. Burn mode key". +② Then execute the "make burn" command in Git Bash +As shown in the figure below: + +![](pic/D1s_pic_21.png) + +After the burning is successful, press and release the "5. System reset button" to start the program. You can see the output information on the serial port: + +![](pic/D1s_pic_22.png) + + + +## 2.2 debugging + +### 2.2.1 GDB Common Commands + +When using GDB debugging, two software are involved: +① "Riscv64-unknown-elf-gdb" running in Git Bash: it issues various debugging commands, such as connecting debugging service software (T-HeadDebugServer), single-step running, viewing variables, etc +② T-HeadDebugServer: it is the "debugging service software", responsible for receiving and processing various debugging commands +Common commands are shown in the following table: + +| Commands | **Abbreviated form** | **Description** | +| ----------------- | -------------------- | ------------------------------------------------------------ | +| target | | Connect to the debugging server, for example: target remote 127.0.0.1:1025 | +| run | r | Run program | +| continue | c、cont | Continue to run | +| break | b | Set breakpoints, such as: b sbi_main.c:121 b sbi_main b \*0x20000 | +| delete | d | Remove Breakpoint | +| disable | dis | Disable breakpoints | +| info breakpoints | info b | Display breakpoint information | +| next | n | Execute next line | +| nexti | ni | Execute the next line (in assembly code) | +| step | s | Execute one line at a time, including the function | +| setpi | si | Execute next line | +| list | l | Show functions or rows | +| print | p | Display the expression, such as: print a print $pc//print register print * 0x20000//print memory print/x a//hexadecimal print | +| x | | Display memory contents, such as: x 0x20000 x/x 0x20000//hexadecimal | +| info registers | infor r | Print the value of all registers | +| set | | Design variables, such as: #set was a=1 \* (unsigned int \*)0x28000 = 0x55555555 > set was $pc=0x22000 | +| finish | | Run to the end of the function | +| help | h | Show help at a glance | +| backtrace | bt、where | Show backtrace | +| symbol-file | | Load the symbol table, such as symbol-file benes.elf | + + + +### 2.2.2 benos_ Payload program composition + +The code in RISC-V Architecture Programming and Practice is divided into two parts: +① Mysbi.elf: the underlying software running in M mode, providing various system services +② Benos.elf: application software running in S mode +benos_ Payload is a combination of these two parts of programs: + +``` +benos_payload.elf = mysbi.elf + benos.elf +benos_payload.bin = mysbi.bin + benos.bin +``` + +Burn and run benos_ When payload.bin, the mysbi program will be run first, and then mysbi will start benos. Debug benos_ When payload.elf, we can debug mysbi first, and then debug benos after benos is started. + + + +### 2.2.3 Commissioning preparation + +First, start the debugging function of CKLink by tearing the film on the dial switch indicated by the blue arrow in the figure below and turning all dial switches to the left (USB interface side): + +![](pic/D1s_pic_23.png) + +Then, start the debugging service software "T-HeadDebugServer", which will automatically detect the chip, as shown in the following figure: + +![](pic/D1s_pic_24.png) + +If there is no information shown above, there are many possibilities: +① No automatic recognition: +It can be identified manually, as shown in the figure below: + +![](pic/D1s_pic_25.png) + +② The program on the board has a bug, which causes the board to crash: you can let the board enter the burning mode first, and then follow step ① +③ Prompt 1025 port is occupied: run the task manager, kill all "T-HeadDebugServers", and then run "T-HeadDebugServer" again +After "T-HeadDebugServer" identifies the chip, you can debug the program in two ways: +① Debugging using command line mode +② Debug using TUI mode + + + +### 2.2.4 Command line debugging example + +After "T-HeadDebugServer" identifies the chip, it can execute "riscv64-unknown-elf-gdb benos_payload. elf" in Git Bash to debug the program. +Examples are as follows: + +``` +weidongshan@DESKTOP-TP8DH2I MINGW64 /d/abc/riscv_programming_practice/chapter_2/benos (DongShanPI_D1) +$ riscv64-unknown-elf-gdb benos_payload.elf +Reading symbols from benos_payload.elf... +(gdb) target remote 127.0.0.1:1025 //Connect debugging service software +Remote debugging using 127.0.0.1:1025 +0x000000000000a22a in ?? () +(gdb) load // load benos_payload.elf +Loading section .text.boot, size 0x44 lma 0x20000 + section progress: 100.0%, total progress: 0.38% +Loading section .text, size 0x538 lma 0x20044 + section progress: 100.0%, total progress: 7.81% +Loading section .rodata, size 0xc0 lma 0x2057c + section progress: 100.0%, total progress: 8.88% +Loading section .data, size 0x1000 lma 0x21000 + section progress: 100.0%, total progress: 31.66% +Loading section .payload, size 0x3000 lma 0x22000 + section progress: 100.0%, total progress: 100.00% +Start address 0x0000000000020000, load size 17980 +Transfer rate: 209 KB/sec, 1997 bytes/write. +(gdb) x /x 0x20000 // Check whether 0x20000 is written correctly, +// When we debug the program, we may not be able to load because of the last crash +// At this time, you can put the board into burning mode, and then reconnect and reload it +0x20000 : 0x0300006f +(gdb) b sbi_main // Set breakpoint to sbi_ Main function +Breakpoint 1 at 0x204bc: file sbi/sbi_main.c, line 80. +(gdb) c // implement +Continuing. + +Breakpoint 1, sbi_main () at sbi/sbi_main.c:80 +80 sbi_set_pmp(0, 0, -1UL, PMP_RWX); +(gdb) n // next step +84 val = read_csr(mstatus); +(gdb) b sbi_main.c:102 // Set breakpoint to sbi_ Line 102 of main. c +Breakpoint 2 at 0x20564: file sbi/sbi_main.c, line 102. +(gdb) info b // View all breakpoints +Num Type Disp Enb Address What +1 breakpoint keep y 0x00000000000204bc in sbi_main + at sbi/sbi_main.c:80 + breakpoint already hit 1 time +2 breakpoint keep y 0x0000000000020564 in sbi_main + at sbi/sbi_main.c:102 +(gdb) i b // View all breakpoints, abbreviated commands +Num Type Disp Enb Address What +1 breakpoint keep y 0x00000000000204bc in sbi_main + at sbi/sbi_main.c:80 + breakpoint already hit 1 time +2 breakpoint keep y 0x0000000000020564 in sbi_main + at sbi/sbi_main.c:102 +(gdb) c // Continue execution +Continuing. + +Breakpoint 2, sbi_main () at sbi/sbi_main.c:102 // I hit a breakpoint +// After executing the next sentence of code, you will jump to the benos program +102 asm volatile("mret"); +(gdb) si // Step into the function and execute one assembly statement at a time +0x0000000000022000 in payload_bin () // Now we need to execute another program, benos +(gdb) symbol-file benos.elf // Read the symbol table of benos.elf, otherwise you cannot know the function, code and other information when debugging +Load new symbol table from "benos.elf"? (y or n) [answered Y; input not from terminal] +Reading symbols from benos.elf... +Error in re-setting breakpoint 1: Function "sbi_main" not defined. +Error in re-setting breakpoint 2: No source file named sbi_main.c. +(gdb) si // Step into the function and execute one assembly statement at a time +9 la sp, stacks_start +(gdb) b kernel_main // Set breakpoint to kernel_ Main function +Breakpoint 3 at 0x22020: file src/kernel.c, line 6. +(gdb) c // Continue execution +Continuing. + +Breakpoint 3, kernel_main () at src/kernel.c:6 +6 sys_clock_init(); +(gdb) i r // List the values of all registers +ra 0x204d0 0x204d0 +sp 0x24ff0 0x24ff0 +gp 0x0 0x0 +tp 0x0 0x0 +t0 0x1000 4096 +t1 0xfffffffffffff000 -4096 +t2 0x109 265 +fp 0xa00000900 0xa00000900 +s1 0x0 0 +a0 0x0 0 +a1 0x1f 31 +a2 0xffffffffffffffff -1 +a3 0x0 0 +a4 0xa00000100 42949673216 +a5 0x0 0 +a6 0x80 128 +a7 0x1c0 448 +s2 0x375bff17 928775959 +s3 0xff32dec 267595244 +s4 0x2eebeffb 787214331 +s5 0xffffffffffdf9ffd -2121731 +s6 0x355077ff 894466047 +s7 0xffffffffef7eeee9 -276893975 +s8 0x27034 159796 +s9 0xffffffffe6376ff3 -432574477 +s10 0xffffffffb9d37bfc -1177322500 +s11 0x78b47e70 2025094768 +t3 0x1 1 +t4 0xefe8 61416 +t5 0x8001 32769 +t6 0x0 0 +pc 0x22020 0x22020 +(gdb) l // List Codes +1 #include "clock.h" +2 #include "uart.h" +3 +4 void kernel_main(void) +5 { +6 sys_clock_init(); +7 uart_init(); +8 +9 while (1) { +10 uart_send_string("Welcome RISC-V!\r\n"); +(gdb) l +11 ; +12 } +13 } +(gdb) c // Continue execution +Continuing. + +Program received signal SIGINT, Interrupt. // Press Ctrl+C to stop the program +read32 (addr=38797436) at include/io.h:23 +23 } +(gdb) quit // Exit debugging +``` + + + +The commands used in the above debugging process have comments, excerpts are as follows: + +``` +$ riscv64-unknown-elf-gdb benos_payload.elf // Start debugging +(gdb) target remote 127.0.0.1:1025 // Connect debugging service software +(gdb) load // Load benos_ payload.elf +(gdb) x /x 0x20000 // Check whether 0x20000 is written correctly, +// When we debug the program, we may not be able to load because of the last crash +// At this time, you can put the board into burning mode, and then reconnect and reload it +(gdb) b sbi_main // Set breakpoint to sbi_main function +(gdb) c // implement +(gdb) n // next step +(gdb) b sbi_main.c:102 // Set breakpoint to Line 102 of sbi_main. c +(gdb) info b // View all breakpoints +(gdb) i b // View all breakpoints, abbreviated commands +(gdb) c // Continue execution +(gdb) si // Step into the function and execute one assembly statement at a time +(gdb) symbol-file benos.elf // Read the symbol table of benos.elf, otherwise you cannot know the function, code and other information when debugging +(gdb) si // Step into the function and execute one assembly statement at a time +(gdb) b kernel_main // Set breakpoint to kernel_main function +(gdb) c // Continue execution +(gdb) i r // List the values of all registers +(gdb) l // List Codes +(gdb) l +(gdb) c // Continue execution +Program received signal SIGINT, Interrupt. // Press Ctrl+C to stop the program +(gdb) quit // Exit debugging +``` + + + +benos_ Payload.elf is a combination of two programs. The key points of debugging are: +① When debugging the first program, the default is from benos_ Get the symbol table in payload.elf +② When executing the second program, you need to use the "symbol file benos. elf" command to read the symbol table of benos. elf, otherwise you cannot know the function, code and other information when debugging. +③ How do I know that the second program has been executed? Can be found in sbi_ Set breakpoints (such as "b sbi_main. c: 102") at the following red box code in main. c. After the breakpoint is executed, execute the "si" command to start the second program: + +![](pic/D1s_pic_26.png) + + + +### 2.2.5 TUI debugging example + +After "T-HeadDebugServer" identifies the chip, it can execute "riscv64-unknown-elf-gdb - tui benos_payload. elf" in Powershell to debug the program. +Note: TUI function cannot be used in Git Bash. Powershell is required. +Start Powershell first: After entering the source code directory, press and hold the shift key while clicking the right mouse button to start Powershell in the pop-up menu, as shown in the following figure: + +![](pic/D1s_pic_27.png) + +In the Powershell window, execute the following command to start debugging: + +``` +riscv64-unknown-elf-gdb -tui benos_payload.elf +``` + + After executing the above command, you can get the following interface (the Chinese characters in the source code window are garbled and cannot be solved temporarily): + +![](pic/D1s_pic_28.png) + + + +The convenience of using TUI is that you can easily view the source code, reverse sink code, and register. The window that displays these information is called layout. Use the following command to display these layouts: +① Layout src: display the source code window +② Layout asm: display the assembly window +③ Layout regs: display the register window again on the previous window +④ Layout split: display source code and assembly window +⑤ Layout next: display the next layout +⑥ Layout prev: display the previous layout +The window that can input various GDB commands is the "command window", which is always displayed. +To display the source code and registers at the same time, you can execute the following two commands: + +``` +layout src +layout regs +``` + + + +To display the reverse sink code and register at the same time, you can execute the following two commands: + +``` +layout asm +layout regs +``` + + + +To display the source code and the reverse exchange code at the same time, you can execute the following command: + +``` +layout split +``` + + + +When using the TUI mode, it is only convenient for us to view the source code, reverse sink code, and register. For specific operation, please enter the GDB command in the command window. Please refer to 2.2.4 Command Line Debugging Example. + + + +### 2.2.6 gdb script + +If you don't want to execute "riscv64-unknown-elf-gdb benos_payload. elf" or "riscv64-unknown-elf-gdb - ui benos_payload. elf" each time, you should manually execute the following command to connect the debugging service software: +``` +(gdb) target remote 127.0.0.1:1025//Connect debugging service software +``` + + + +You can write these commands to a file named ". gdbinit". Note that the first character of the file name is ".", which means it is a hidden file under Linux system. We can see it in the Windows file browser, but we can't see it in Git Bash by executing the "ls" command. We need to execute the "ls - a" command to see it. +You can put more commands in ". gdbinit". Here is an example: + +``` +target remote 127.0.0.1:1025 +load +b sbi_main.c:102 +``` + diff --git a/pic/D1s_pic_1.png b/pic/D1s_pic_1.png new file mode 100644 index 0000000000000000000000000000000000000000..ab79eb137c0b8b04c6ea3c1f189dd86a64506c1c Binary files /dev/null and b/pic/D1s_pic_1.png differ diff --git a/pic/D1s_pic_10.png b/pic/D1s_pic_10.png new file mode 100644 index 0000000000000000000000000000000000000000..5d2fa1324f8819bda4317e425e1c0d2ab02ab822 Binary files /dev/null and b/pic/D1s_pic_10.png differ diff --git a/pic/D1s_pic_11.png b/pic/D1s_pic_11.png new file mode 100644 index 0000000000000000000000000000000000000000..1eff70809b456c84084f7e0841dda9010c0a13ca Binary files /dev/null and b/pic/D1s_pic_11.png differ diff --git a/pic/D1s_pic_12.png b/pic/D1s_pic_12.png new file mode 100644 index 0000000000000000000000000000000000000000..f0b1fee6df73d1f01735b9185e45d1c960d5865a Binary files /dev/null and b/pic/D1s_pic_12.png differ diff --git a/pic/D1s_pic_13.png b/pic/D1s_pic_13.png new file mode 100644 index 0000000000000000000000000000000000000000..a4c661a7f69bdd4ce2f7eabc83197ad5d17a586b Binary files /dev/null and b/pic/D1s_pic_13.png differ diff --git a/pic/D1s_pic_14.png b/pic/D1s_pic_14.png new file mode 100644 index 0000000000000000000000000000000000000000..0576863dc5d872602985fb396cf4ab5de6c39af9 Binary files /dev/null and b/pic/D1s_pic_14.png differ diff --git a/pic/D1s_pic_15.png b/pic/D1s_pic_15.png new file mode 100644 index 0000000000000000000000000000000000000000..f81d9a8055cb21a67ce8c8f3089f9ffbb1ca25ad Binary files /dev/null and b/pic/D1s_pic_15.png differ diff --git a/pic/D1s_pic_16.png b/pic/D1s_pic_16.png new file mode 100644 index 0000000000000000000000000000000000000000..3b21624ed67feb87383a6306307ef68a414af783 Binary files /dev/null and b/pic/D1s_pic_16.png differ diff --git a/pic/D1s_pic_17.png b/pic/D1s_pic_17.png new file mode 100644 index 0000000000000000000000000000000000000000..a86f2270f8083279b88b6a1ab8cb39bffe45a0fe Binary files /dev/null and b/pic/D1s_pic_17.png differ diff --git a/pic/D1s_pic_18.png b/pic/D1s_pic_18.png new file mode 100644 index 0000000000000000000000000000000000000000..72cab304223aecc85a222930235e952c5e40054c Binary files /dev/null and b/pic/D1s_pic_18.png differ diff --git a/pic/D1s_pic_19.png b/pic/D1s_pic_19.png new file mode 100644 index 0000000000000000000000000000000000000000..f38ff6e790c320b3faa1ee6d08e6c5539992f930 Binary files /dev/null and b/pic/D1s_pic_19.png differ diff --git a/pic/D1s_pic_2.png b/pic/D1s_pic_2.png new file mode 100644 index 0000000000000000000000000000000000000000..5dddbb4703aa07092d11c08c3ab6aff863d7e3c4 Binary files /dev/null and b/pic/D1s_pic_2.png differ diff --git a/pic/D1s_pic_20.png b/pic/D1s_pic_20.png new file mode 100644 index 0000000000000000000000000000000000000000..059de76954796941ab6ac1c2a3bc95c556ea9617 Binary files /dev/null and b/pic/D1s_pic_20.png differ diff --git a/pic/D1s_pic_21.png b/pic/D1s_pic_21.png new file mode 100644 index 0000000000000000000000000000000000000000..53760a7260bf77675da4cc29f30b06a8e2095fd8 Binary files /dev/null and b/pic/D1s_pic_21.png differ diff --git a/pic/D1s_pic_22.png b/pic/D1s_pic_22.png new file mode 100644 index 0000000000000000000000000000000000000000..dcbff80c7c29b9e43f7d091303a2bc2526c7dd1d Binary files /dev/null and b/pic/D1s_pic_22.png differ diff --git a/pic/D1s_pic_23.png b/pic/D1s_pic_23.png new file mode 100644 index 0000000000000000000000000000000000000000..51a6dbee093a8fad09c843d8513b9a472091fb2a Binary files /dev/null and b/pic/D1s_pic_23.png differ diff --git a/pic/D1s_pic_24.png b/pic/D1s_pic_24.png new file mode 100644 index 0000000000000000000000000000000000000000..d7f2c94ea390229f5b7fffbcf2897b4ff78bf5e9 Binary files /dev/null and b/pic/D1s_pic_24.png differ diff --git a/pic/D1s_pic_25.png b/pic/D1s_pic_25.png new file mode 100644 index 0000000000000000000000000000000000000000..a54dc57a9270b59fff1c157aac6eaadca382f714 Binary files /dev/null and b/pic/D1s_pic_25.png differ diff --git a/pic/D1s_pic_26.png b/pic/D1s_pic_26.png new file mode 100644 index 0000000000000000000000000000000000000000..39e84d52214cdd01b850737e151e839620e1703a Binary files /dev/null and b/pic/D1s_pic_26.png differ diff --git a/pic/D1s_pic_27.png b/pic/D1s_pic_27.png new file mode 100644 index 0000000000000000000000000000000000000000..3085db182bccbfb3a426245d5dfbf928bdd6a4a8 Binary files /dev/null and b/pic/D1s_pic_27.png differ diff --git a/pic/D1s_pic_28.png b/pic/D1s_pic_28.png new file mode 100644 index 0000000000000000000000000000000000000000..11dd7a22d6850cab63547f53beca817f68071ccb Binary files /dev/null and b/pic/D1s_pic_28.png differ diff --git a/pic/D1s_pic_3.png b/pic/D1s_pic_3.png new file mode 100644 index 0000000000000000000000000000000000000000..35f69a848638771391b7e225df4ef67cbaf38622 Binary files /dev/null and b/pic/D1s_pic_3.png differ diff --git a/pic/D1s_pic_4.png b/pic/D1s_pic_4.png new file mode 100644 index 0000000000000000000000000000000000000000..eb830fa7194163201ecab4a73452cf734fdaae64 Binary files /dev/null and b/pic/D1s_pic_4.png differ diff --git a/pic/D1s_pic_5.png b/pic/D1s_pic_5.png new file mode 100644 index 0000000000000000000000000000000000000000..1feb9d5244272655cd3e1b72da916959f5d272ff Binary files /dev/null and b/pic/D1s_pic_5.png differ diff --git a/pic/D1s_pic_6.png b/pic/D1s_pic_6.png new file mode 100644 index 0000000000000000000000000000000000000000..92f3e9f8b229fc208d9f6d2ba33ae56b3559b4da Binary files /dev/null and b/pic/D1s_pic_6.png differ diff --git a/pic/D1s_pic_7.png b/pic/D1s_pic_7.png new file mode 100644 index 0000000000000000000000000000000000000000..8317bdbdae5103f7e70f72e085d4ac59972d6996 Binary files /dev/null and b/pic/D1s_pic_7.png differ diff --git a/pic/D1s_pic_8.png b/pic/D1s_pic_8.png new file mode 100644 index 0000000000000000000000000000000000000000..be7149a8d084a3bd898cf1afe9b21ec00c928640 Binary files /dev/null and b/pic/D1s_pic_8.png differ diff --git a/pic/D1s_pic_9.png b/pic/D1s_pic_9.png new file mode 100644 index 0000000000000000000000000000000000000000..19ffcf57d08c113b517e8d6159e7b3b05fef1f0e Binary files /dev/null and b/pic/D1s_pic_9.png differ