uiint 发表于 2024-10-31 20:20

Keil常用的调试操作

一、软件调试使用1.1 基本调试操作      上文已经说过在线调试和模拟调试的配置过程,但无论是在线还是模拟调试,调试技巧工具的使用都是一样的。
点击红色d,进入调试
https://i-blog.csdnimg.cn/blog_migrate/26f5348ae310e42c7e15cf501cd08e07.png
可以发现,多出了一个工具条,这就是 Debug 工具条,这个工具条在我们仿真的时候是非
常有用的,下面简单介绍一下 Debug 工具条相关按钮的功能。Debug 工具条部分按钮的功能如
图:
https://i-blog.csdnimg.cn/blog_migrate/0b04357acba526f3a90151cbca0e4222.png
复位(Reset):其功能等同于硬件上按复位按钮。相当于实现了一次硬复位。按下该按钮之后,代码会重新从头开始执行。
https://i-blog.csdnimg.cn/blog_migrate/5f2da685f831fadda05acf8ca682d63a.png
执行到断点处(Run):该按钮用来快速执行到断点处,有时候你并不需要观看每步是怎么执行的,而是想快速的执行到程序的某个地方看结果,这个按钮就可以实现这样的功能,前提是你在查
看的地方设置了断点。
https://i-blog.csdnimg.cn/blog_migrate/9e1cba87cf012fa5da779a8439662ea7.png
挂起(Stop):此按钮在程序一直执行的时候会变为有效,通过按该按钮,就可以使程序停止下来,进入到单步调试状态。
https://i-blog.csdnimg.cn/blog_migrate/7ab706c8831c672ec4d8632beba438ba.png
单步调试(Step):根据当前调试的窗口的语言,执行单条语句。如果遇到函数,则会进入函数内部。该按钮用来实现执行到某个函数里面去的功能,在没有函数的情况下,是等同于执行过去按钮的。
https://i-blog.csdnimg.cn/blog_migrate/505654f1add024df8636c1261b766a2d.png
单步跳过调试(Step Over):如果是在C语言窗口中,则是按单条语句执行,与单步调试不同的是,遇到函数不会进入函数内部,而是直接全速运行函数,并跳到下一条语句。在碰到有函数的地方,通过该按钮就可以单步执行过这个函数,而不进入这个函数单步执行。
https://i-blog.csdnimg.cn/blog_migrate/cf20286cc9947beb0a424fa9bef3445f.png
单步返回调试(Step Out):如果是在C语言窗口中,则是直接全速运行当前函数后面所有内容,直到函数返回上一级。该按钮是在进入了函数单步调试的时候,有时候你可能不必再执行该函数的剩余部分了,通过该按钮就直接一步执行完函数余下的部分,并跳出函数,回到函数被调用的置。
https://i-blog.csdnimg.cn/blog_migrate/57379d5dbd7270bce6db7faac4151b4c.png
执行到光标处(Step Run to Cursor Line):该按钮可以迅速的使程序运行到光标处,其实是挺像执行到断点处按钮功能,但是两者是有区别的,断点可以有多个,但是光标所在处只有一个。
https://i-blog.csdnimg.cn/blog_migrate/98a21510057fd26480560030f1fa1fb7.png
插入/移除断点:如果当前光标所在行未有断点,则插入断点(前提是当前行可以插入,如果无法插入会显示一个感叹号),在有断点的情况下则是移除断点。插入断点后,当前行前面会有个红圆表示断点位置。也可以通过直接点击红圆位置进行插入/移除断点的操作。另一种断点方式,是通过指令来控制,当然也可以使用Keil提供的界面化操作,设置某个变量读或写时触发断点。不过目前貌似有部分芯片不支持这种操作。注:断点最多只能打7个。
https://i-blog.csdnimg.cn/blog_migrate/dbfeab9f575c489ebe8f0f1604699505.png
使能/禁止断点:开启或禁止当前光标所在行的断点。禁止后红圆变成白圆。
https://i-blog.csdnimg.cn/blog_migrate/11a7be8c477155ecc9886e3725e6ea87.png
禁止所有断点:禁止当前所有的断点。
https://i-blog.csdnimg.cn/blog_migrate/9a7a4aacd5ab088fae3dc1294f7c5578.png
删除所有断点:删除所有断点。
https://i-blog.csdnimg.cn/blog_migrate/364727647a277c5296dc159f3df98cf0.png
1.2 调试窗口https://i-blog.csdnimg.cn/blog_migrate/38d6fdf8450cb9b4f508a4d8cc954bc9.png
汇编窗口:通过该按钮,就可以查看汇编代码,这对分析程序很有用。
观看变量/堆栈局部变量窗口:该按钮按下,会弹出一个显示变量的窗口,在里面可以查看各种你想要看的变量值,也是很常用的一个调试窗口。
观察窗口:watch窗口,可以看到你想看的变量。
内存查看窗口:该按钮按下,会弹出一个内存查看窗口,可以在里面输入你要查看的内存
地址,然后观察这一片内存的变化情况。是很常用的一个调试窗口。
串口打印窗口:该按钮按下,会弹出一个类似串口调试助手界面的窗口,用来显示从串口
打印出来的内容。
逻辑分析窗口:按下该按钮会弹出一个逻辑分析窗口,通过 SETUP 按钮新建一些 IO 口,
就可以观察这些 IO 口的电平变化情况,以多种形式显示出来,比较直观。
系统查看窗口:这个窗口用于查看当前单片机外设及内核寄存器的值,在调试外设底层时经常会使用到。

[*]变量查看窗口——watch1,watch2
https://i-blog.csdnimg.cn/blog_migrate/b9ac2e1dd29fe4b1d7168a6ea554c604.png
      通过"View->Watch Windows->Watch1、Watch2"可以选择打开Watch窗口,也可以在工具栏
这里打开。再点击一次则可以关闭。
      通过选中一个变量(一定要选中变量,而不是光变放在变量那里),右键添加入对应的Watch窗口,可以追踪查看当前变量的变化状态。注意,只有全局变量可以全程监视,临时变量只有在进入当前函数中才可监视到其数据,用static关键词修饰的变量无法监视。
      如果当前变量没有实时更新,则需要点击"View->Periodic Window Update"将其勾选上。
https://i-blog.csdnimg.cn/blog_migrate/d805f03e82e00500d3fc79e91aaf070c.png
      在 "Watch" 窗口中,可以查看当前变量名称、值、数据类型,如果当前变量类型为结构体,则可以以对应的结构形式进行展开查看。
https://i-blog.csdnimg.cn/blog_migrate/30e1f44ebaf4d6910c5f14679fd52a62.png

[*]内存查看窗口——Memory
       https://i-blog.csdnimg.cn/blog_migrate/bcea0ad5dd08724f7562daf8ef654995.png
      通过"View->Memory Windows->Memory1/2/3/4"打开Memory窗口,也可以通过工具栏这个图标打开。打开的状态下再按一次则可关闭。
      在Memory窗口中输入想要查看内存的起始地址里的数据,另外右上角的锁可以把当前界面锁定下来。
https://i-blog.csdnimg.cn/blog_migrate/fcbe08eba30e80cc5c90177fcc022793.png
      另外如果查看的是Ram的地址,那其中的数据也可以直接通过此窗口进行修改。
https://i-blog.csdnimg.cn/blog_migrate/a906cc79e1f1d576e4037feb9b51972f.png

[*] 系统视窗——System Viewer Windows(这个根据不同芯片会有不同的展示)
      https://i-blog.csdnimg.cn/blog_migrate/a44d65ef53c35f7f2bf6de873b0edc45.png
      可以在"Peripherals"选项栏中选择"System Viewer"系统视窗中对应的外设,选择"Core Peripherals"则是内核调试窗口。另外系统视窗也可以通过工具栏中,这个位置打开。
      这个窗口用于查看当前单片机外设及内核寄存器的值,在调试外设底层时经常会使用到。
      在这个窗口中可以直接修改外设寄存器的值,当然部分只读寄存器是无法修改的,有些则是需要在特定条件下才可以设置生效,具体就得看对应的芯片手册里寄存器的说明了。
但我的Keil软件中无法显示这个视图,并且通过修改系统试图,调试时,点击打开系统视图发生了闪退的现象,目前能想到的原因是:重新安装Keil,安装最新版本。
https://i-blog.csdnimg.cn/blog_migrate/b1a0b9fa1398f762ec5271f173096a0e.png
若Keil软件的System Viewer中没有,可以在这里点击 Use Custom File,添加SRF后缀的文件,这个文件在芯片包里。添加后,确实有了系统视图,但会出现闪退的现象。
https://i-blog.csdnimg.cn/blog_migrate/5e74b43ace7f3bfafd56ae27e5ed5d50.png

[*]调度关系窗口——Call Stack Window
[*]寄存器窗口——Register Window
[*]反汇编调试窗口——Disassembly Window
[*]命令窗口——Command Window
[*]函数地址表——Symbols Window
[*]跟踪窗口——Trace Windows
[*]以上不常用的窗口介绍,详情:不常用调试窗口介绍


[*]串口调试窗口——Serial Windows
https://i-blog.csdnimg.cn/blog_migrate/634170eda1c223b2cc8ea9abc4f7191a.png
该窗口在"View->Serial Windows"中打开,也可以在工具栏这个位置打开。
https://i-blog.csdnimg.cn/blog_migrate/1ea521d4d79fa0a754995148dd58bb64.png

[*] 逻辑分析窗口——Analysis Windows
https://i-blog.csdnimg.cn/blog_migrate/1015668f17be8fc1cb519ad6ca94485d.png
该窗口在"View->Analysis Windows"中打开,也可以在工具栏这个位置打开。
https://i-blog.csdnimg.cn/blog_migrate/aca5e0913a4ae880d19e8ab3e2280325.png
二、注意事项1、有时候在watch窗口中,变量值不会刷新,这时候就需要查看一下"View->Periodic Window Update"是否已勾选,如果没勾选,变量只有在第一次添加或停止调试时才会刷新。另外当窗口里一次性加载了一个很大的数组,当展开数组时,变量刷新也会变得很慢,并且软件会变卡顿。
2、当选择了非0级优化时,调试可能会变得困难,具体表现在断点调试。比如现在下面的代码,代码优化的关系,有可能把case0、1、2里的return 1都合并成一行,导致运行调试时,无论当前程序进入了哪个分支,使用断点时都只会进其中一个。所以当开启代码优化等级后,需要注意断点调试将变得不可信。另外优化编译后,有部分代码也将无法打断点(被优化的代码)。
switch (xx){      case 0:      {                do_something0();                return 1;      }      case 1:      {                do_something1();                return 1;      }      case 2:      {                do_something2();                return 1;      }      default:      {                return 0;      }}此时应该去看汇编的实现,其执行顺序与汇编一致。
3、目前发现有部分工程在一些电脑上调试时,打断点后在删除断点之前退出调试,会导致Keil崩溃,只能结束进程重启,可能是你的工程中有中文名字。
4、当开启内部看门狗并且未打开调试关看门狗功能时,停止运行一段时间后会复位。
5、在全速运行时,有时打断点会无效,取消断点也无效,貌似是Keil本身的问题。

yangjiaxu 发表于 2025-1-23 17:15

不错不错,keil要是把调试工具插件都用明白了也不容易

地瓜patch 发表于 2025-2-27 12:33

仿真,窗口,变量等等

bestwell 发表于 2025-3-9 18:57

在Keil中,可以通过点击工具栏上的“Debug”按钮或按下快捷键(如Ctrl+F5)进入调试模式。在调试模式下,可以使用各种调试工具和功能来检查和调试程序。

loutin 发表于 2025-3-9 20:52

打开Watch窗口(View -> Watch Windows -> Watch1/Watch2),可以查看和监视变量的值。
在Watch窗口中,可以查看变量的名称、值和数据类型。如果变量是结构体,可以展开查看其成员。

primojones 发表于 2025-3-9 21:45

单步跳过(Step Over):点击调试工具栏中的 “Step Over” 按钮,或使用快捷键 F10。程序会执行当前行代码,并跳转到下一行,不会进入函数内部。如果当前行调用了函数,会将函数当作一个整体执行完,然后停在下一行。
单步进入(Step Into):点击 “Step Into” 按钮,或使用快捷键 F11。当遇到函数调用时,会进入函数内部,逐行执行函数中的代码。
单步跳出(Step Out):当在函数内部调试时,点击 “Step Out” 按钮,或使用快捷键 Shift+F11,程序会继续执行直到从当前函数返回,停在调用该函数的下一行代码处。

dspmana 发表于 2025-3-10 10:05

查看程序的汇编代码,有助于深入理解程序的底层执行过程和优化代码性能。

alvpeg 发表于 2025-3-10 13:06

可以开启或禁止当前光标所在行的断点。禁止断点后,程序在运行到该位置时不会暂停执行。

beacherblack 发表于 2025-3-10 16:10

直接在代码编辑器的左侧边栏点击对应行号旁的空白处即可设置或移除断点。你也可以右击选择"Toggle Breakpoint"来完成此操作。

kkzz 发表于 2025-3-11 13:11

单步执行:点击 “Step Over” 按钮或按下 F10 键,程序将逐行执行,遇到函数调用时,会将函数作为一个整体执行完,然后停在下一条语句。
进入函数:使用 “Step Into” 按钮或 F11 键,当程序执行到函数调用时,会进入函数内部,逐行执行函数中的代码。
跳出函数:当在函数内部调试时,点击 “Step Out” 按钮或按下 Shift+F11 组合键,程序将执行完当前函数的剩余部分,并返回到调用该函数的下一条语句。

hudi008 发表于 2025-3-11 15:09

查看寄存器:在调试模式下,打开 “Registers” 窗口,可查看 CPU 寄存器的当前值,包括通用寄存器、程序计数器(PC)、状态寄存器等。
修改寄存器:在 “Registers” 窗口中,可以直接双击寄存器的值进行修改,也可以右键点击寄存器,选择 “Modify” 选项来修改寄存器的值,用于模拟特定的硬件状态或测试某些功能。

adolphcocker 发表于 2025-3-11 17:03

点击工具栏上的“Debug”按钮或按下F5键启动调试会话。

tifmill 发表于 2025-3-11 20:04

在程序执行过程中实时查看变量的值,帮助分析程序的逻辑和数据流向。

1988020566 发表于 2025-3-12 15:05

在使用系统视窗和寄存器窗口时,应谨慎修改外设寄存器和内核寄存器的值,以避免对程序造成不可预测的影响。

yorkbarney 发表于 2025-3-12 16:48

通过选中一个变量并右键添加入对应的Watch窗口,可以追踪查看当前变量的变化状态。这有助于实时监视变量的值,以便在调试过程中及时发现问题。

hilahope 发表于 2025-3-12 18:31

在代码编辑区域,点击行号可以设置或取消断点。当程序运行到断点时,将会暂停执行,等待用户进行下一步操作。断点有助于在特定位置暂停程序执行,以便检查变量的值或程序的行为。

sesefadou 发表于 2025-3-12 20:36

全速运行(F5):让程序以全速运行,可以在特定位置设置断点,让程序运行到断点位置。
停止运行:在程序全速运行时,点击停止运行按钮可以让程序停止。

ccook11 发表于 2025-3-12 22:18

打开串口打印窗口(View -> Serial Windows -> UART1/UART2),可以查看从串口打印出来的内容。

lihuami 发表于 2025-3-14 10:31

在调试时,可以打开 “Disassembly” 窗口,查看程序的反汇编代码。这对于深入理解程序的执行过程、分析汇编级别的代码逻辑以及优化程序性能非常有帮助。

deliahouse887 发表于 2025-3-14 12:14

断点(Breakpoints)​
​用途:暂停程序执行,观察当前状态。
​普通断点:在代码行左侧单击设置,程序执行到该行时停止。
​条件断点:右键断点 → ​Condition,设置触发条件(如i > 100)。
​数据断点:监视特定内存地址或变量的值变化(如&counter),当值变化时触发中断。
​指令断点:在汇编级别设置断点(适用于底层调试)。
页: [1] 2 3
查看完整版本: Keil常用的调试操作