1. 为什么我们需要Keil Debug串口调试?
很多刚开始玩单片机,尤其是用STM32这类ARM芯片的朋友,可能都有过这样的经历:程序烧录进去,灯不亮,电机不转,屏幕没反应。这时候你心里肯定在打鼓:“我的代码逻辑到底对不对?变量现在是什么值?程序跑到哪一步卡住了?” 如果只靠“烧录-看现象-猜问题-改代码-再烧录”这个循环,调试效率会非常低,简直像是在黑箱里摸鱼。
这时候,Keil MDK的Debug调试功能就是你的“透视眼”。它允许你在代码运行时,暂停程序(设置断点),查看和修改内存、寄存器的值,单步执行观察程序流。但这还不够,很多时候我们需要程序在全速运行时,也能把一些内部状态、传感器数据、算法中间结果实时地打印出来,方便我们分析。比如,一个PID控制程序,你想看看计算过程中的误差、积分项、输出值是怎么变化的,总不能每步都暂停吧?这就需要用到我们今天要深入聊的串口调试。
你可能用过printf重定向到串口,然后接一个USB转TTL模块,在电脑上用串口助手看数据。这方法很经典,但每次都要连接硬件,如果你的板子不在手边,或者想快速验证一段逻辑,就显得有点麻烦。而Keil Debug环境里,其实内置了两种更“软”的串口调试方式:Debug窗口输出和虚拟串口通信。前者可以直接在Keil的调试界面里开个窗口看打印信息,后者则能模拟出一个真实的COM口,让你可以用任何串口助手软件(甚至是你自己写的上位机)来接收数据,完全不需要物理连接。
我刚开始用的时候也觉得有点绕,但一旦配置好,你会发现调试效率提升了好几个档次。下面,我就把自己踩过坑、验证过的方法,从最基础的配置开始,一步步分享给你,保证小白也能跟着做出来。
2. 准备工作:你的工程和代码需要做什么?
在动手配置那些炫酷的调试功能之前,我们得先把地基打好。这个地基就是你的Keil工程和一段能够通过串口发送数据的代码。别担心,这很简单。
首先,确保你有一个正常编译的Keil MDK工程。芯片型号根据你自己的来,我这里以最常见的STM32F103系列为例。接着,我们需要一段核心代码:一个不依赖硬件串口外设的打印函数。为什么这么说?因为Debug窗口和虚拟串口都是Keil仿真器在模拟串口行为,数据流并不经过芯片上的USART模块,所以我们需要使用Keil提供的标准库函数来发送数据。
这个函数通常长这样:
#include <stdio.h>
// 重写fputc函数,这是printf函数最终调用的底层输出函数
int fputc(int ch, FILE *f)
{
// 将字符发送到Keil Debugger的调试窗口
// 这是关键函数,它把数据送到了调试器,而不是硬件TX引脚
ITM_SendChar(ch);
return ch;
}
这里的 ITM_SendChar 函数是ARM Cortex-M内核中ITM(Instrumentation Trace Macrocell)模块的功能,它专门用于在调试时向主机(也就是你的电脑上的Keil软件)发送数据。你需要在工程里包含ARM CMSIS相关的头文件(通常Keil新建工程时会自动添加),这个函数才能用。
写好这个函数之后,你就可以在代码的任何地方愉快地使用 printf 了,就像在电脑上编程一样:
int main(void)
{
SystemInit(); // 系统初始化
printf("系统启动成功!\n"); // 这行字将会发送到调试器
int sens


242

被折叠的 条评论
为什么被折叠?



