别把 printf 当万能调试器,但也别只会用它打字
很多从单片机或裸机转岗过来的开发者,对 printf 的认知停留在“串口打印个变量看看值”。一旦遇到中断里偶发的数据错乱、休眠唤醒后设备死机、或者正式量产需要按模块关闭日志,这种朴素打法立刻露怯:要么打印被截断,要么关不掉,要么满屏刷屏找不到关键信息。这门专题课不扯什么从入门到进阶,就解决一件具体事:把嵌入式里最常用的 printf 调试手段,从“能打出字”升级到“可控、可分级、可定位、不丢数据”。适合你已经会基本串口打印、能写点裸机或 RTOS 程序,但遇到复杂故障时打印手段跟不上需求的中级补课。如果你连 UART 初始化、链接脚本都没概念,建议先补外设基础再来。
先补输出重定向与打印缓冲,再碰开关与等级
建议先啃输出重定向这一节,这是后面所有技巧的地基。嵌入式里 printf 默认不走任何地方,你得让它重定向到串口、半主机模式、或者 ITM 之类的接口。理解了 fputc 接管、重定向到多通道,你才能谈后续控制。紧接着重点看打印缓冲问题,这是实战里最容易踩坑的点:为什么在中断里打印会丢字符?为什么系统刚启动时前几条日志没了?多半是缓冲未刷新、栈溢出、或半双工时序冲突。把无缓冲、行缓冲、自定义环形缓冲的取舍搞清楚,再去碰打印开关和等级控制。开关控制解决量产时按文件或模块关闭日志,等级控制解决调试时只看 ERROR 不看 DEBUG。这两块看似简单,但结合宏定义、编译条件、运行时切换去落地,细节不少。至于打印文件名、函数名、行号那段,属于辅助定位的胶水技巧,时间紧可后看,但别跳过——它能在崩溃现场快速锁定是哪个函数哪一行触发的。
学完能干什么,资料怎么练
学完这套,你应该能独立做几件事:第一,给一个新项目搭一套可配置的打印框架,量产版一键关闭调试日志,开发版全开;第二,遇到中断偶发丢数据时,能判断是缓冲问题还是时序问题,并给出修复方案;第三,在崩溃现场用宏定位到具体文件和行号,不用再满代码里加试探打印。配套练习建议这样走:先拿资料里的示例工程,把重定向从串口改成自定义缓冲区输出,观察不同缓冲大小下丢字符的情况;然后给打印加上等级宏,写一段代码同时产生 ERROR 和 DEBUG 信息,验证等级切换是否生效;最后模拟中断高频打印场景,测试缓冲刷新策略。别只看视频不动手,printf 这种东西,看懂和能调对之间差着无数次编译。每节看完,自己复现一遍现象,改参数看输出变化,才算真补上这块缺口。
课程目录
1 输出重定向 (31:42) 2 打印文件名、函数名、行号 (07:42) 3 打印缓冲问题 (11:16) 4 打印开关控制 (09:20) 5 打印等级控制 (15:11)





