你的浏览器版本过低,可能导致网站不能正常访问!
为了你能正常使用网站功能,请使用这些浏览器。

【经验分享】STLINK调试程序教程

[复制链接]
STMCU小助手 发布时间:2022-6-10 19:22
01. 概述+ N! f# H! v/ M: J, W- v/ i
在实际的开发过程中,如果程序比较简单就不需要调试程序,但是对于比较复杂的程序,往往需要通过调试来解决bug。串口只能下载代码,并不能实时跟踪调试,而利用调试工具,比如 JLINK、ULINK、STLINK等就可以实时跟踪程序,从而找到你程序中的 bug,使你的开发事半功倍。
  i2 e' e) c& o# y

' ]2 y0 Z6 y- K  c5 ?STLINK 支持 JTAG 和 SWD,同时 STM32F4 也支持 JTAG 和 SWD。所以,我们有 2 种方式可以用来调试,JTAG 调试的时候,占用的 IO 线比较多,而 SWD 调试的时候占用的 IO 线很少,只需要两根即可。& _% a4 S3 M! _2 ?
0 e6 U1 Z% _* d9 O! y5 W

! g: ?' F& z$ X% F; R02. STLINK调试程序' ~* f+ E& `: \/ ?( ~& I
2.1 点击开始调试按钮

3 m: T3 j1 C$ [) I' j' k
4 C2 K8 Z/ {  {2 e3 L9 P
%BIO6FXL$P[8`3%NQRPTPUF.png
! z$ y# a$ W- W* B2 m
1 k' ]) B) D/ u" o编译一下工程。然后点击:(开始/停止仿真按钮),开始仿真(如果开发板的代码没被更新过,则会先更新代码(即下载代码),再仿真,你也可以通过按下载按钮,只下载代码,而不进入仿真。特别注意:开发板上的 B0和 B1 都要设置到 GND,否则代码下载后不会自动运行的!)  F) u' I: J5 ]
- K3 M$ v( M; z4 H3 m: O. R& q

  `0 Z! F9 U" O8 o) o! U2.2 跳转到主函数执行
8 R0 M4 j" d2 o! ^8 i2 S
9 V) c5 h# M( O' c- n+ o
OODEKLTDP67N[E1S2[ZRO%N.png
) e& K- T* `$ p- H# l
# X2 s, W' x# A) K2.3 Debug工具条介绍/ S# Y& k: G; X% T" p

$ R7 ?9 e+ y' V9 v3 \+ ]: U因为我们之前勾选了 Run to main()选项,所以,程序直接就运行到了 main 函数的入口处。另外,此时 MDK 多出了一个工具条,这就是 Debug 工具条,这个工具条在我们仿真的时候是非常有用的,下面简单介绍一下 Debug 工具条相关按钮的功能。; \  J1 J2 U" v% F  ^

5 r6 u7 Z" X( ?2 o; F& Q+ D
% {8 C6 G5 I0 f" @1 z8 j
20200819105104317.png
: A8 X  ~- s! y* O5 @4 h; @
, |: S5 Y9 p9 c( u
复位:其功能等同于硬件上按复位按钮。相当于实现了一次硬复位。按下该按钮之后,代码会重新从头开始执行。
8 h& \4 H) }( u; Y, B; N# a, d+ y' x' g1 [) T2 P! t
执行到断点处:该按钮用来快速执行到断点处,有时候你并不需要观看每步是怎么执行的,而是想快速的执行到程序的某个地方看结果,这个按钮就可以实现这样的功能,前提是你在查看的地方设置了断点。
, n8 B$ ~( R5 ~: v. I" l* R5 X: q) |' Z6 \4 X6 u" D
停止运行:此按钮在程序一直执行的时候会变为有效,通过按该按钮,就可以使程序停止下来,进入到单步调试状态。! c+ k' x1 n' y0 H' M  X( y0 l; P# w

: o" N2 l# J+ Y3 l执行进去:该按钮用来实现执行到某个函数里面去的功能,在没有函数的情况下,是等同于执行过去按钮的。
$ F% P5 C7 ^' z2 f3 ?

4 ]% ^. c: x9 `! \执行过去:在碰到有函数的地方,通过该按钮就可以单步执行过这个函数,而不进入这个函数单步执行。
5 Z% o) Y5 G& j; L
7 N* o. X& D" q9 Z  [
执行出去:该按钮是在进入了函数单步调试的时候,有时候你可能不必再执行该函数的剩余部分了,通过该按钮就直接一步执行完函数余下的部分,并跳出函数,回到函数被调用的位置。+ w' g/ A. z! O2 w) E
% h. v( o0 L5 t5 [7 b
执行到光标处:该按钮可以迅速的使程序运行到光标处,其实是挺像执行到断点处按钮功能,但是两者是有区别的,断点可以有多个,但是光标所在处只有一个。
& X' O, k. V/ B* C! w; ^! |
* b9 A) v7 ~& S; }% N汇编窗口:通过该按钮,就可以查看汇编代码,这对分析程序很有用。
* d* E$ o. `+ J9 t( j+ |& X+ d/ }% _* R' u0 X) E
堆栈局部变量窗口:通过该按钮,显示 Call Stack+Locals 窗口,显示当前函数的局部变量及其值,方便查看。
- B, U" u8 j! @  x
  T  o( K% E4 O  ]! \0 w观察窗口:MDK5 提供 2 个观察窗口(下拉选择),该按钮按下,会弹出一个显示变量的窗口,输入你所想要观察的变量/表达式,即可查看其值,是很常用的一个调试窗口。
+ x5 ~2 Q' F) B* t7 z# f4 C" u0 E4 g+ {  ?0 _
内存查看窗口:MDK5 提供 4 个内存查看窗口(下拉选择),该按钮按下,会弹出一个内存查看窗口,可以在里面输入你要查看的内存地址,然后观察这一片内存的变化情况。是很常用的一个调试窗口8 Y! C& \. v- M

7 S5 J  S+ Z- u串口打印窗口:MDK5 提供 4 个串口打印窗口(下拉选择),该按钮按下,会弹出一个类似串口调试助手界面的窗口,用来显示从串口打印出来的内容。
$ R+ S5 J# N1 i0 `" M5 Q& h& Y3 S3 Q' {2 {9 ~$ h8 p
逻辑分析窗口:该图标下面有 3 个选项(下拉选择),我们一般用第一个,也就是逻辑分析窗口(Logic Analyzer),点击即可调出该窗口,通过 SETUP 按钮新建一些 IO 口,就可以观察这些 IO 口的电平变化情况,以多种形式显示出来,比较直观。# m2 L% }* ?' o+ u5 \1 H; C

8 \' T5 {, G; [3 }6 R系统查看窗口:该按钮可以提供各种外设寄存器的查看窗口(通过下拉选择),选择对应外设,即可调出该外设的相关寄存器表,并显示这些寄存器的值,方便查看设置的是否正确。
$ v! b; P# S- K" W4 S: V8 t% t( F& K: D5 \
Debug 工具条上的其他几个按钮用的比较少,我们这里就不介绍了。以上介绍的是比较常用的,当然也不是每次都用得着这么多,具体看你程序调试的时候有没有必要观看这些东西,来决定要不要看。, `2 j3 e/ E' L8 `* p7 b3 q, u1 x: {

. V8 l( i& T4 j特别注意:串口打印窗口和逻辑分析窗口仅在软件仿真的时候可用,而 MDK5 对 STM32F4的软件仿真,基本上不支持(故本教程直接没有对软件仿真进行介绍了),所以,基本上这两个窗口用不着。但是对 STM32F1 的软件仿真,MDK5 是支持的,在 F1 开发的时候,可以用到。
- l/ L7 U& u3 k" y% u1 Z$ `4 b* C9 h# C( u( [# H  P# v" g

/ ~9 y" U3 g# K% E) K2.4 设置和取消断点

( g3 M! t- x7 k. E. U$ ^6 R  J- y4 s, R8 d" C9 }3 |: h+ @2 }" B8 G
我们把光标放到 test.c 的第22行左侧的灰色区域,然后按下鼠标左键,即可放置一个断点(红色的实心点,也可以通过鼠标右键弹出菜单来加入),再次单击则取消。4 r; B' o2 ~" K; T* J/ F" W

1 D3 v" b' j8 }) J9 i0 O
; T' j) }. N7 [9 ]

" K5 C6 ^( h% H# i, |

& U5 |& w# F0 G, I1 X2.5 点击run执行到断点处
5 k3 D3 I+ n+ Q3 v# F# |8 X! H1 r1 Y% Q$ @  J4 f% E
R231TA{7ZTNZX$WRX[HP3NQ.png 4 U+ F! J4 @6 L" A1 S6 q: M. ?

. u# A! h; B: }5 j; b) v9 @0 g2.6 查看外设信息

( t- O6 o4 h) w
* ?) h5 A+ f" V8 i7 R点击菜单栏的 Peripherals→System Viewer→GPIO→GPIOF。可以看到,有很多外设可以查看,这里我们查看的是GPIOF 的情况。
- H" ^+ u; ^8 F8 x& l% w5 I/ s, d) t! V9 W6 K' O/ d0 C% i/ t
IHWTPD(IF%V2I376$A)H8BO.png 1 t& y) Y2 N9 {' p) `: }

6 j* G: x% x1 `0 t8 j6 o单击 GPIOF后会在 IDE 右侧出现一个如图9 T1 }" t7 E3 r4 b. Z
- C# G8 q& m2 `- p* C/ u
PG{2JRET4FFJ9KX$Z6@7COR.png ; n4 L; x* a+ `8 W7 \- i. q3 t
- B) f0 y4 ^" @2 _; Y; V3 o) y# y
3 x: {. B& n9 t! l( v2 }3 B- V
2.7 执行完初始化
  [6 q  y. [' V5 }2 u4 t2 _, z+ L, y
20200819105226499.png 3 P; ^% o: [" Z- t8 m
* |1 j& H: {: a  a7 I$ d7 }! r
我们可以查看GPIOF 的各个寄存器设置状态,从而判断我们写的代码是否有问题,只有这里的设置正确了之后,才有可能在硬件上正确的执行。同样这样的方法也可以适用于很多其他外设,这个读者慢慢体会吧!这一方法不论是在排错还是在编写代码的时候,都是非常有用的。+ Q* M. m" ?6 \) F& N' y
7 {' G. U- c! X( ]& ~+ [
( a  }5 ^6 I8 Q; g+ p0 S% i
2.8 查看栈信息: [7 u! l4 w. o4 e) h3 u
' Z7 x$ @0 ?' `) H
J%H{{R{8B8LX9~CT(]0QAUO.png + T  m% O8 S1 P
3 p/ [, A. v: j/ {3 u
; }5 ]0 q8 Y/ U7 R, q
赞 收藏 评论0 发布时间:2022-6-10 19:22

举报

0个回答

所属标签

相似技术帖

官网相关资源

关于
我们是谁
投资者关系
意法半导体可持续发展举措
创新与技术
意法半导体官网
联系我们
联系ST分支机构
寻找销售人员和分销渠道
社区
媒体中心
活动与培训
隐私策略
隐私策略
Cookies管理
行使您的权利
官方最新发布
人形机器人运动控制、感知与智能配电
半导体创新技术与应用方向
EE架构与软件定义汽车
12V/48V 汽车智能配电(SPD)
区域控制单元(ZCU)与分区架构
关注我们
st-img 微信公众号
st-img 手机版