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

【经验分享】STM32H7 RL-USB移植(MDK AC5)

[复制链接]
STMCU小助手 发布时间:2021-12-30 14:01
4.1   初学者重要提示9 g; r3 U: P8 F* c
  学习RL-USB移植前,务必保证已经熟练掌握了RTX5内核的移植
4 z6 ]4 z# }- P2 T! m  STM32H7使用MDK RTE环境添加RTX5和RL-USB,需要强制运行一次STM32CubeMX,因为H7已经没有配套RTE经典添加方式,而STM32F4是支持经典方式的,所以无需运行STM32CubeMX,详情可以看我们STM32F4开发板对应的RL-USB教程。' Y; V7 d2 [) R, {
  本章配套例子使用STM32内部RAM模拟一个U盘,使用的MicroUSB接口。
7 Y# n* m3 D) Y8 w# h4.2   移植RL-USB整体说明' A* X4 F% Q+ e& j$ o
移植之前,有必要对移植过程有个整体的认识:; F! G+ m2 Y- G9 n0 s8 D$ a% w7 a
9 w: \$ C/ X* B0 u
  第1步,准备一个RTX5工程模板。
' l. o) Z2 K; v7 D# w  第2步,移植RL-USB。
5 ~, I+ a5 V# `7 _2 n$ e  移植RL-USB是采用MDK的RTE环境直接添加。当前H7芯片使用RTX5强制运行STM32CubeMX,所以需要大家提前安装好STM32CubeMX V6.0或者以上版本。
, C" p6 R* Z  [# _9 R5 g* o  第3步,处理HAL库时间基准,MPU配置等。
. r8 B/ d( E( O+ ]! [4 V  第4步,创建应用。6 G7 y  w' T  c; ~. w
总的来说,这4步就可以完成移植,下面将STM32H7的移植步骤和注意事项为大家做个说明。
; A; G) e: |4 q0 [2 ]# ?4 m( o5 ]* B, C
4.3   了解RL-USB模板框架设计
5 u$ n* W, W! l
移植RL-USB前,我们优先了解下移植好的RL-USB内核模板,方面大家后面移植:& M3 k- {/ D* H1 }8 X7 d7 u0 e
3 T' O! i) m$ A
9c6a4f191f47051f48c46fad67830cf5.png

- U3 K4 A2 ?* W; c
5 ]4 N9 B* b  n) k- V框图如下:
8 h% `1 \" E; |: o9 l' Y4 v& r, c* T+ e
5d53a3abf7c75f1cb8292dc449988f1a.png

+ p2 ~0 j, M! M0 ]4 k% o9 j: P' U" T. Z) n& |( ~3 f7 c
4.4   第1步,安装指定的MDK软件包
. ?( w- w* w7 e5 \
移植新版RL-USB需要大家下载当前最新的MDK软件包版本(如果有最新版,推荐大家用最新版):6 o  \: G/ f1 a1 a! R. M! [- L
3 v5 U* I/ [- d) O2 T- e8 g
  CMSIS 软件包使用当前最新的:V5.7.0; w4 ?; D- j. `5 g3 {9 d
  STM32H7使用当前最新的:V2.6.0
! M8 u" x. `$ r& k8 L  STM32F4使用当前最新的:V2.15.0. f1 T9 W& o. l3 P
  STM32CubeMX使用当前最新的:V6.0.x
$ ~3 s- N' Q" F, K; r; L  ARM_Compiler使用当前最新的:V1.6.39 \& z9 k7 m  F1 {4 g) w
  RTX5中间件使用当前最新的:V7.12( D9 z' D2 z- J

3 J7 x9 V0 u5 g/ ~' G
& b7 X5 w( e5 o. O9 w不管以后MDK的软件包版本如何升级,当前的软件包版本和以后的新版是可以同时安装的,也就是说可以安装多个不同版本,在这里可以选择指定版本:
8 B- U+ T9 [  V. h! N3 j# H 7264b6fa8f70af9cae9f03812878d357.png . s$ e, x4 r) d5 C. T# D  ]
9 w( P$ M1 i. `- W1 f7 r
0 N6 W" ?& d4 N0 h. u7 O, ]
4.5   第2步,准备一个工程模板
; U( z5 b, F; r. t: K' n7 D
首先准备好一个简单的裸机工程模板,已经为大家做好:V7-4001_RTX5 Kernal Template,准备好的工程模板如下图所示(大家也可以制作其它任意的工程模板,不限制):
, j8 f- l. U9 D6 c: i8 ]0 \+ y- m6 \1 l- @& q; g  c8 I( \
74269e50c64ab536eeb86097f3884ec3.png
4 f& U7 ~& h- s9 i: ~
* s- k6 O+ O3 V9 T3 r
4.6   第3步,添加RL-USB并配置

0 @% `; k6 o  H. w! f! t看这部分内容前,务必保证已经熟练掌握了RTX5教程移植章节的添加方法。8 p# g3 p5 X% o* r) O

" j/ p. W$ s' S: P7 i4.6.1      RL-USB相关文件和驱动4 R( _$ u% {( t
CMSIS-Driver分组中添加USB Device驱动:
' i5 M$ e- E  \- [# j$ C8 e- `* u3 a+ U6 `* X! L6 [) p/ y
ea12a66af6e60e048bf1b9b81e9aa08a.png
* ?( I3 d1 x' U7 I

- [; g2 S% P) Y! o+ C添加USB驱动:( p) o( M& n5 U. |$ Y
6 ?3 Q$ z' ?% A( x
b683b1361cf7de9821e95e9473212e41.png

* T) F5 V5 h, |  _9 q
; c6 z" A# X8 A$ Z/ z添加RL-USB并配置:
1 \+ o6 Y' d5 J6 s1 b
! q# V  Q/ f1 |5 a' ~% @  q! o
4d32bb88eee575ba6da2871d56a1ffde.png

; f. c: t: G/ O: h" S/ Y4 E1 e9 v5 t% Q9 ~: F
我们需要的都已经添加好,效果如下:
( U3 z; {, Q, Z: O( ~
/ h! A0 e6 }* J: W
6ce0595add222d31f90d93e116cad4f9.png
) H8 |: q9 H) @" d! J
" D" S' I6 @# Q8 Z) H( ^
红色方框里面驱动要隔离出来,隔离后的效果如下(隔离方法看RTX5教程移植章节):
% i& o# W' _- m6 P/ j: ^1 G1 @& q4 Y1 B. t
f4cf0f77d674b6a83289142025e72131.png

* C7 p+ ^; K6 r) Q8 O, O5 A
: t" p  D6 J0 {+ _; f4.6.2      重新添加被隔离的CMSIS-Driver文件
/ d' ]" T4 |+ [0 I
将我们提供的程序模板中制作好的RL-ARM文件夹复制粘贴到大家准备好的工程模板中。. B/ D& N5 d1 G  ~  x' T
9 ~  G2 E0 r- g" t1 k$ j3 V" |/ j  j
52112e844aee805fc01a6d40cddc00a7.png

& c) r9 b) d8 J! _6 L: e" F5 V8 `# }" z; c8 y
RL-ARM文件夹中有如下七个文件夹,其中只有RL-USB文件夹里面有文件
  |5 u8 I! C) y
" Q' Y' p. E' p6 e& K. P- I
7039175ef77263dc5dc73a486e83950f.png
5 J, Q& b, h+ O4 w  Z3 ?( r: D
; a- P8 I3 D. a9 ]: \
内容如下,这些文件是来自MDK安装目录:0 ~# }1 r+ D  s6 H% f

6 D7 Z1 a: E, |
17b8ba3a04288a0e29d94e7ad5f45325.png
% V( G7 i8 d$ j# _: ^/ k' ?
* j0 E  J- W/ K; b
然后将用到的两个文件添加进来:) Y, t; Y, n, L2 M: |! r

. M; Y5 o0 Z3 ]! u6 P
9ad9fcc23d96b8aec42538dff0552a2f.png
. _+ j9 v# d% J  v# r
, B' C& p( ?) x- j: c) \
4.6.3      重新添加被隔离的HAL库USB文件6 d# D5 k# |- r" z+ o, V" P
文件stm32h7xx_hal_pcd.c,stm32h7xx_hal_pcd_ex.c和stm32h7xx_ll_usb.c被隔离出来了,我们单独在分组HAL_Driver里面添加。除了这三个文件,同时将两个pwr文件也添加进来:- `# }$ j. ^, B
" g1 W7 S# E) g3 N$ s- O
48241523bce89ad84d2851afef1384e2.png

' |' u+ B' C2 q* ^0 F
4 r7 r) N8 q7 n4.6.4      RL-USB配置: n1 F+ N5 w( b5 b: {! r
添加完毕RL-USB所需的文件后,就是配置RL-USB,具体每个配置所代表的含义,会在后面章节专为大家讲解。
- [4 R5 f! [: ?6 C, p! B) q# l( @6 ~5 ]. ^
+ n4 c6 C+ g$ o6 g  j7 W5 d, vUSBD_Config_0.c文件配置:
; S' v0 E6 e8 i9 y8 k
/ C: Y- }* I' n
c5dcc4510924d2ff0e75092f7d4ca9fe.png

: l, ?4 w% b3 h! X0 [0 u7 b
, B8 ^6 M+ K( c3 D; h& i注意这个文件里面还有一个RL-USB内核线程的优先级配置,当前是将其配置为:6 u9 p. {7 y+ r. \$ J; n6 n

- h# A/ h; U1 ]0 ^7 o! V$ A& wosPriorityAboveNormal:& }6 N+ T3 ?$ X3 }
0 d1 d+ g+ }. _0 H1 n; {& c. k) v
f62a8fad5d1ce978c1730b2ad87955e0.png
  J" w( S4 P, o" q: C
: Q) {  h" G& H/ x
USBD_Config_MSC_0.h文件的配置如下:
+ `/ t5 v7 r0 |* X7 x+ Q% z" L$ r' R$ X' e
1cffb6b1fa60821b7a7ab7900f7f40a4.png

3 ?$ N: P1 ^) B7 \- b2 n% t0 ^- s. Y8 s/ ]" ~8 y9 ^
这个文件里面有一个USB MSC任务的优先级配置,当前是将其配置为:osPriorityAboveNormal。
4 S9 t" ]1 n6 z# s0 e1 `$ X0 N' k& t7 `- W8 J4 B# g. A
fafa76af25304dc853509d2c4dc839f8.png
$ @$ ~9 o  l0 ?

! A* s7 C  I) s: V* a: `4.7   第4步,强制运行一次CubeMX配置USB
& |9 [4 k6 L' P" q$ t  Y" d我们这里要强行运行一次STM32CubeMX来自动使能RL-USB的相关宏定义,并配置USB接口使用到的两个引脚PA11和PA12。: f( r; F( E+ z7 z: b4 J5 G
, C( {# p4 F5 M: ~
打开RTE环境,点击如下按钮:% c1 i( q, H7 W
2 o; y  \# f: G" @( a
6d97a5c7ce435822748232a4fe1b0e64.png
# {- W# e/ ?* s8 z5 ^

( ^" c! N* w1 @+ _$ p, i- l$ j弹出的STM32CubeMX配置如下:
2 u3 `7 Z0 L$ ]$ C% a' N& m9 c/ B1 Z- \* S$ q1 F7 Y
2f47e57c5008dce25c2c00afe900142c.png
$ q9 J5 F/ R$ `9 ?

( M) l# B- L8 J  f; Q/ I' \修改位置1:用于选择仅使用设备。* ~( N5 g( a6 T9 T
. {3 `" u( Y8 h  C  \8 F9 Y
修改位置2:用于使能USB FS中断。然后点击“GENERATE CODE”
8 }6 b2 z: \$ G5 s) `4 P% t" ?' B) c! {0 ^; S8 n+ R! n% C
2259b40b2cc2d5b5819f6ac79dd22c3e.png

( V+ B/ J$ g' i* D1 K. ?' |& y3 ]' G, ]9 t
然后弹出如下对话框,点击Close即可,然后关闭STM32CubeMX。
' }, i. f! }4 }" ~4 [, `' H7 D- N1 Y9 G
17f991df1ea61c9ffd2dbb4c7216da25.png
" u7 S5 f' _1 p( |

8 g$ N( V6 g+ l& b重新回到MDK,会有一个对话框,点击“是”即可:
' h8 f5 e7 I  i+ Q, q
( r& G. v9 n. u# l; u- {; Q
292e9c0668f8c166995f17f5d58cc2f8.png
9 W' m& s- F; f% u2 ^( I: x

! F' @4 f& }% j  K配置后,就可以看到stm32h7xx_hal_msp.c文件里面对USB引脚做了配置。+ ?( a" ?# c/ \/ w+ p) x2 d
; z! ]8 T( C4 p# D4 W$ E" S
db9b1da83c41e9807da4cae3b2618f11.png
, r& s, M0 w( Z

4 a. |* P4 D; |6 x4.8   第5步,修改文件USBD_STM32H7xx.C3 @4 v! Y/ J4 S; U
这个文件开头的头文件顺序要修改,否则编译会出错,原始的顺序如下:, v7 n+ l' d3 B3 S( h* w. ^
8 s) _) e! @0 E5 [
  1. #include "OTG_STM32H7xx.h"3 Q- w- [- l* \& j, f
  2. #include "USBD_STM32H7xx.h"
    6 W, b0 p2 w* R# N# o  ]0 b

  3. 8 q7 W5 V; Z% \5 v
  4. #include "stm32h7xx.h"
复制代码
$ q9 o/ P- g+ d7 F) E
修改后的顺序如下:1 U+ z" l$ ?* ]" H& j

4 H3 D8 g% ~  ?& A6 ^/ o
  1. #include "stm32h7xx.h") `+ x9 P# r; l( v$ Z& Y0 T5 P6 H8 t

  2. 7 f' \. p( }- m" i3 c- D0 p, l
  3. #include "OTG_STM32H7xx.h"7 g2 g. `: ]: \' F
  4. #include "USBD_STM32H7xx.h"
复制代码
, c# z# y6 u& }+ l5 w$ j7 C
4.9   第6步,修改文件stm32h7xx_hal_msp.c
$ m; q1 J% \3 |5 X需要在这个文件开头添加一个变量PCD_HandleTypeDef hpcd_USB_OTG_FS,此贴变量会被USB的CMSIS Driver文件所调用。最好将其放在如下位置,防止重新调用STM32CubeMX时将清除掉:
1 r8 b. k8 J9 U, {  c# E" x5 `  P1 e8 Q
5d9cadc09f4b5d106e20e496c919908e.png
5 q2 k2 e8 M0 q: A7 \" t

$ \: F/ U/ \5 c4.10 第7步,修改文件includes
' a9 H- K; E( |) ^添加USB头文件:#include "rl_usb.h"
% k( F9 Q* Y4 g6 F
# U% N$ C9 T# U4 A#ifndef  __INCLUDES_H__5 _+ I6 X: `; j) y6 Z' Z5 q
#define  __INCLUDES_H__
3 ?0 h0 b7 r, v- M- r
! v. y3 h! p' U/ X; Z/*) B8 _8 l$ ~5 L$ v* F& x  Z
*********************************************************************************************************
& {6 d$ g$ W8 R*                                         标准库
: O' D! q7 m7 _7 u( k7 A( o% M$ A- w*********************************************************************************************************1 O  U) x, ^3 X
*/7 T: B) |; H) H% s$ _9 d% W7 N; j
#include  <stdarg.h>& d! l  o7 K; D! {+ {0 u$ T" o' J
#include  <stdio.h>
; M9 Q- W' Q6 K#include  <stdlib.h>
; l6 V7 _/ f( w1 [5 f#include  <math.h>" b9 B7 ~8 E" M4 p' w
1 \+ W4 W4 Z  A2 p$ B
& X7 O  H2 t9 h6 \4 t4 f2 D
/*
( l4 ^* T# `2 h" r*********************************************************************************************************
0 e, k6 ]4 \7 F% `" {4 |6 o*                                         其它库
5 R! d: j. T) t5 h- ]! `*********************************************************************************************************( B) L8 @7 {$ Z* H3 G! k
*/
, m  f0 k" F4 V" v) c8 o% z! t7 x5 }! b0 j9 F" o

( W$ Q+ |" r3 s0 S/*
3 w5 _# |: x( z! C2 s* V*********************************************************************************************************& }7 |, L+ {. N9 J
*                                           OS和系统库- \( E) z- n. K9 B9 o8 \
*********************************************************************************************************
3 z7 v4 P8 |/ [7 p*/
3 r$ d) B0 `2 @- G* i; c/ e#include "cmsis_os2.h") b6 l- D1 d: g0 b
#include "rl_usb.h"
) [- ?6 M2 k( I% ]) ]& v. g6 Q& h" `# V) i3 _
/*$ R3 p/ w% z4 H! s8 Y( w2 d
*********************************************************************************************************8 R2 |: p6 Q, y9 d1 C  k
*                                           宏定义, {5 B: U1 w" ~9 |& T
*********************************************************************************************************
  V, n- P! G1 t& d7 J*/1 I2 k8 d% y1 N( f

. p# O: v" N8 |  a# W  j0 d, x1 F- H! l: A7 g+ J4 D* D* z8 h& @

7 F3 B( j8 o! \5 V/*
7 y. {9 D- u! b) o' h; o*********************************************************************************************************1 o/ d, v8 A  Z1 D) I. F( w
*                                        APP / BSP
. o* @, Z- e5 k" I8 L*********************************************************************************************************
( z7 h5 r" ]5 U! Q*/" C: I9 u; K+ S- ^# E2 ~$ x1 k% |
#include "bsp.h"  n% ?- I$ O  F8 g- }! X& _

2 q8 t1 n" X3 e. k* o9 C5 f2 g
. g/ Y! |( ]& q; {- s# j
/*
! l+ n" e9 r0 K1 t' h% Z9 q2 Q*********************************************************************************************************
4 Q6 b. s$ }% _3 |* o! ^4 D  D*                                          变量和函数) }4 D- m, q  P. d' Z% G" U2 \
*********************************************************************************************************( o8 g  V" J  Y; n* x8 F
*/' H6 m( O+ ~* g8 N3 F2 H5 M
/* 方便RTOS里面使用 */
: v! h+ E0 p) e% ?' P! Q6 cextern void SysTick_ISR(void);
1 P" o% t! n7 }! W  `
( z& M2 i' F( f#define bsp_ProPer1ms  SysTick_ISR
: {- M. b/ P- b& \7 w. B. ~. W. O& w" o
#endif
1 y1 j" ]; Z$ N& U6 f
0 m" u5 P* t/ b9 e2 p/***************************** 安富莱电子 www.armfly.com (END OF FILE) *********************************/3 [! n8 ^6 ~8 q# k" Q
4.11 第8步,添加两个应用文件
: j8 H' D9 I8 q0 Y+ u为了验证移植的USB是否成功,我们这里使用内部RAM模拟一个U盘。需要添加的两个文件在MDK安装目录里面。方便起见,大家可以直接从本章配套例子里面复制粘贴(这两个文件位于User文件夹),添加后的效果如下:4 v( O! m/ }; _; D

" d6 Q! \+ T  [! F
0ff85fc9774973eb80c1dbfa6653222d.png
8 ]6 ~$ y; G; o4 S4 X2 F

0 c5 T+ w1 L( m9 i% O1 l" q& D" ~6 b4.12 第9步,添加头文件路径" y. {& \9 W4 h6 u' r: S% f9 v- J
添加头文件路径:6 a. L# \, \3 Y! l" L+ _
7 i1 Y+ f& B" l" V0 ^
3d601bebf02ab97843fdaf69cbe84a46.png
/ \6 y1 y* c; g  u  B
, p) w% q( c2 u$ C4 @( }& {
4.13 第10步,创建应用任务(重要,注意启动任务); I. v6 S! I; L
应用程序比较简单,大家可以直接复制本章教程配置例子的main.c文件中的内容到自己工程里面测试。主要创建了如下几个任务:
4 q# }9 [+ h: }
7 N. B+ F5 i; E, R% \& y& J% aAppTaskUserIF任务   : 按键消息处理。
; U  I) j1 q9 h/ z3 J. v) J" `# f+ B1 t% B3 s4 S2 g4 b$ c9 U
AppTaskLED任务      : LED闪烁。
) S" F7 y% _3 P, ^: W) J
  I9 |, {% ]3 w& @7 J# R* Z3 hAppTaskMsgPro任务   : 消息处理,暂未使用。5 \4 p% `- x6 D# |

* n' A, b" u2 J( x8 ZAppTaskStart任务    : 启动任务,也是最高优先级任务,这里实现按键扫描。
% T$ Z6 o6 Y: }$ R* P( i9 K" |2 O; x- v
osRtxTimerThread任务: 定时器任务,暂未使用。
$ X" M4 m0 `+ U* j. K% R" M( L! W
任务栈大小和任务控制块定义如下:4 @+ k0 i6 \; U* _) P/ Y

: m2 \6 g! n! O5 C+ e
  1. /*
    8 O$ }% I& f0 ~! p
  2. **********************************************************************************************************
    & K8 Y2 {' u" @8 u' D& v3 W
  3.                                              变量
    ; S& x1 j0 P/ G2 O7 u. c1 K
  4. **********************************************************************************************************
    8 o) ~1 t  S# }( I+ l) j
  5. */
    1 k* X2 |! L6 y
  6. /* 任务的属性设置 */
    * E" {/ F2 h  T3 L# ^$ b# s
  7. const osThreadAttr_t ThreadStart_Attr =
    3 |6 i7 z- R+ @% k0 A* r- N) Y
  8. {
    + x& r. I2 D# I4 Q
  9.     /* 未使用 */) U3 k% T/ ^* ^2 p# E0 g
  10. //    .cb_mem = &worker_thread_tcb_1,
    9 j+ E+ M' E/ R, c6 r7 _6 p
  11. //    .cb_size = sizeof(worker_thread_tcb_1),
    ' P/ v5 V2 `/ m8 i
  12. //    .stack_mem = &worker_thread_stk_1[0],2 X  }$ D% G+ u& w" P6 h
  13. //    .stack_size = sizeof(worker_thread_stk_1),
    0 _5 M7 `- g- S
  14. //    .priority = osPriorityAboveNormal,
    8 W' o! O1 ?$ v# S6 V
  15. //    .tz_module = 0( r; K/ S5 \  l$ i5 z4 h. t. C

  16. - [' M6 l, b. ]$ a! v# T
  17.     .name = "osRtxStartThread",
    ' T% p8 w4 b: e- v/ n% \
  18.     .attr_bits = osThreadDetached,
    " r" E9 {# D' |" P1 I
  19.     .priority = osPriorityNormal4,' ~1 A7 ~% Q% I% {" c+ g2 P# S  ^
  20.     .stack_size = 2048,' ~: o7 j& E9 S; W3 E
  21. };
    # |2 x$ q* j. I' J+ a
  22. 8 @, Z% {  c0 y+ Q
  23. const osThreadAttr_t ThreadMsgPro_Attr =
    # j! j1 V2 w0 H8 ?
  24. {; s3 G9 v' T7 t) m+ m+ X
  25.     .name = "osRtxMsgProThread",
    3 \3 W1 E' ^6 D# u( o: i/ j) G& U
  26.     .attr_bits = osThreadDetached, 2 `8 |* \3 s; c4 U/ I' [
  27.     .priority = osPriorityNormal3,9 G/ k' N& N3 S$ E0 I' c3 q
  28.     .stack_size = 1024,
    ' @0 e$ h8 K0 B' B  p/ f( G
  29. };( A' f. Z# ]  b0 }3 Q: a9 i5 y
  30. 2 m2 [6 I0 l! j1 h. a+ r
  31. const osThreadAttr_t ThreadLED_Attr =
    1 E, H1 ~* W/ a4 P2 W4 K4 M
  32. {
    0 C( V. q5 e8 D4 _. o
  33.     .name = "osRtxLEDThread",
    ' O0 Q& R& Z3 b7 q1 F
  34.     .attr_bits = osThreadDetached,   q" y' n. x$ M
  35.     .priority = osPriorityNormal2,
    " h" H  X9 K$ e9 w0 {
  36.     .stack_size = 512,( P- `7 C# n- E0 F. W! h
  37. };
    # g; d5 W7 v2 _+ N0 K( e. r7 H* R
  38. . u" T* Q' L! O, t5 F( o" s. Y
  39. const osThreadAttr_t ThreadUserIF_Attr = 5 O) a* m7 b- I
  40. {3 s6 u2 r$ J* W  L
  41.     .name = "osRtxThreadUserIF",
      e+ b- M" V- `, f) n: n, A
  42.     .attr_bits = osThreadDetached,
    , H( j8 y6 D: c
  43.     .priority = osPriorityNormal1,8 W5 M+ W/ }7 ~  J
  44.     .stack_size = 1024,, k3 {0 ]" R7 d) b0 G0 {) g
  45. };
复制代码
8 p. R/ s3 A& z2 r; V- |
任务创建:+ |8 v  a: n8 c  i2 j0 Q& s7 x
, M8 y/ @9 t* E3 k" W0 g3 b
  1. /*
    3 w: z' E; t) S+ @
  2. *********************************************************************************************************
    : F- x& Q/ |% ~% Z
  3. *    函 数 名: main+ H  P% j8 c4 `( c$ W4 b
  4. *    功能说明: 标准c程序入口。2 ~# H3 i1 n5 L
  5. *    形    参: 无, M, i( u2 o& u% A+ l
  6. *    返 回 值: 无
    " V% }# R( u/ E# ~2 N, h# g
  7. *********************************************************************************************************
    3 \# K5 }1 Q3 q, U! ~; ~  h7 t
  8. */
    4 Q/ j" s) _1 ~, w* `8 k5 f( T
  9. int main (void)
    + v8 l! W. H+ t6 w" B& A' V  w7 z8 K. {
  10. {    2 L9 [6 I; z" }( H. P  x# k
  11.     /* HAL库,MPU,Cache,时钟等系统初始化 */' B2 _, \: ]& e
  12.     System_Init();
    ; l( A* c( E) k& g
  13. % C3 Q7 @1 c  u
  14.     /* 内核开启前关闭HAL的时间基准 */  q) p7 n3 ^* E0 _3 l" a" S8 e* s
  15.     HAL_SuspendTick();
    ' w6 p2 I  ]7 e( _! [
  16. * U, a7 }; C8 G8 |
  17.     /* 内核初始化 */
    ; L" h0 T2 C4 X+ w3 j
  18.     osKernelInitialize();                                  3 ^9 Z& w0 S& w) Y3 Y5 W/ D

  19. 0 L* _% C  L3 E5 a1 ]3 Q
  20.     /* 创建启动任务 */
    9 z8 {9 `# S% M3 A) W. M; g
  21.     ThreadIdStart = osThreadNew(AppTaskStart, NULL, &ThreadStart_Attr);  
    ) u* P3 T  y+ y' o8 _

  22. * ~, D# C. S/ U/ U' `! U1 L
  23.     /* 开启多任务 */
    / z4 a: }% `' r9 t" s# \
  24.     osKernelStart();
      F" X0 g, F- W$ B

  25. ; g- k# i* p* O( n7 T0 ]5 A. U) P
  26.     while(1);
    ( ]6 W+ T( B4 m- p
  27. }2 _9 n) ~9 e  S6 Y# @  R- e2 `

  28. * ~0 D/ i% d' g- r7 Y
  29. /*) h+ \' k# P! K$ C5 Q- L& s2 r7 |
  30. *********************************************************************************************************3 v+ }0 R" Q- Z" w" h2 f
  31. *    函 数 名: AppTaskCreate
    , \/ X$ s0 B& O* U6 i2 |
  32. *    功能说明: 创建应用任务' D* Z9 R9 m9 u4 E- m
  33. *    形    参: 无
    + c  u! j% s4 a3 s$ D
  34. *    返 回 值: 无
    + C4 r* t& D9 t  [- S- }
  35. *********************************************************************************************************
    5 z/ V; g1 d6 d$ r7 n
  36. */7 [4 w+ F8 e; C  T
  37. static void AppTaskCreate (void)( _# @2 I( G0 r. X
  38. {
    ! s$ v& ?. A' b: c" P; x5 q
  39.     ThreadIdTaskMsgPro = osThreadNew(AppTaskMsgPro, NULL, &ThreadMsgPro_Attr);  
    ( C; c* v6 M% Y; |* O9 t
  40.     ThreadIdTaskLED = osThreadNew(AppTaskLED, NULL, &ThreadLED_Attr);    e& }2 a( r1 `0 b( f: X/ V4 T( @
  41.     ThreadIdTaskUserIF = osThreadNew(AppTaskUserIF, NULL, &ThreadUserIF_Attr);  . p2 f) U: o$ F
  42. }
复制代码

. Q' u+ W" e) E+ z% e5 s这里我们重点看下启动任务,主要做了五个工作:
1 X; o) V4 F; n1 @! Z' f  I3 Q$ H0 R8 J6 v
  外设初始化bsp_Init。
( z* n, {5 s9 L. i- X5 G  D0 l& Q. s  任务创建AppTaskCreate。
/ r" F" V; r% l0 r  初始化USB并连接电脑。5 A  M9 L+ z; O; }- E
  需要周期性处理的程序bsp_ProPer1ms,对应裸机工程调用的SysTick_ISR。这个的实现非常重要,这样之前裸机里面使用的API,就可以直接在RTX5里面直接调用。9 R7 P7 F8 e5 A# s2 Z
  1. /*( n: ]! U# s5 ]7 w: w; }* @& ~
  2. *********************************************************************************************************0 t" g' j4 z9 \4 r* y" F& q7 \
  3. *    函 数 名: AppTaskStart* W" S4 o* i% }9 M1 T6 K1 u
  4. *    功能说明: 启动任务,这里用作BSP驱动包处理。
    3 s+ o9 m+ k. A4 ^# @. d
  5. *    形    参: 无) C, Q5 M( x5 K* g: K" c% G5 J
  6. *    返 回 值: 无0 o4 l! i' a, |4 h. |1 ?$ Y
  7. *   优 先 级: osPriorityHigh4  
    8 A* D2 v( Y& z, @( e  o7 H
  8. *********************************************************************************************************
    ! o6 [2 q- _0 a
  9. */
    " G1 Z$ E2 I2 c  @! f7 j* t. h
  10. void AppTaskStart(void *argument)
    ) m0 X* F! O# u+ @9 O8 c/ @$ y
  11. {$ O; q) j7 Q/ u! H
  12.     const uint16_t usFrequency = 1; /* 延迟周期 */$ W9 R- b" x* }$ A
  13.     uint32_t tick;
    7 F1 A' C5 e# s; ~+ Z! ^) k
  14. . [0 |# u6 v* s' J' a/ k: W; A
  15.     /* 初始化外设 *// F# `& _- `2 {! M! U/ b& z
  16.     HAL_ResumeTick();
    , X' P, {- x+ r! \) A
  17.     bsp_Init();
    . W( O# B0 B3 t3 g' `
  18. % }+ ^% [' l# B
  19.     /* 创建任务 */
    7 n& Z0 u* v$ C  a% k: f) q& C3 u
  20.     AppTaskCreate();
    6 r+ I  J7 R6 ?, q6 _% s: F5 P
  21.   d2 Y$ ]& m) N2 W9 [1 s
  22.     USBD_Initialize(0U);  /* 初始化USB设备 */
    # X: U1 ^2 x2 L3 x. e( i- C# d
  23.     USBD_Connect   (0U);  /* USB设备连接 */
      H5 |4 b8 k: }7 Q6 t1 \5 p- D

  24. 9 @0 P' x) K6 p6 D% {+ B
  25.     /* 获取当前时间 */
    2 K% N$ G' j4 q- \/ c& T
  26.     tick = osKernelGetTickCount(); . P" ?3 I6 ~& l9 U8 l# N3 g) ~
  27. + l5 d/ ~1 O# _% U) o
  28.     while(1)
    % n$ N" {; Y8 G. P; n6 U2 B
  29.     {' I% ~! X6 B4 g
  30.         /* 需要周期性处理的程序,对应裸机工程调用的SysTick_ISR */
    7 a8 d- ?! t. _7 a
  31.         bsp_ProPer1ms();  s* `6 x1 L. G$ x5 u5 W8 S
  32. ' _9 m; M9 t; ]
  33.         /* 相对延迟 */
    , h9 |* u8 Q5 {% P8 B( v" g
  34.         tick += usFrequency;                          
    , U6 D% ^2 Q3 {
  35.         osDelayUntil(tick);3 _! `* M7 y2 S& i
  36.     }8 g) w& W, L$ \1 j4 z3 V- C
  37. }
复制代码

  x% U6 {/ x) ^0 I! c- M& u4.14 常见移植错误总结. Z: s; f- _4 @1 W, L
  编译后提示如下错误:8 u4 f- k0 a: i0 e
error: 'Driver_USBD.h' file not found
, S3 u. Y* O" L
; A, ~. J2 ?5 ~解决办法是将新版 CMSIS 软件包里面 Driver 文件夹全部复制到自己所创建工程里面的 CMSIS文件夹下,并添加路径:+ s7 |6 a" K; k9 t( ]; f

4 y( T3 k3 T1 x. R) H& {
d32a6c67848ac92bf4c29e0fbf5ef220.png
. {8 u! N- o- _+ ^

* Z- k0 v1 g/ C3 ], R  提示如下错误1 P5 `& J( T  y# b% M. b  K
unknown type name 'HAL_StatusTypeDef'' g8 d! j( L  a2 b  M: s% I
. n+ @  B$ k& J* g) f7 b
解决办法:本章4.8小节。
( Z2 t  j# K6 e2 I. g/ {
. W* ~$ }* n+ {  X( D" U4.15 使用的MicroUSB接口并注意跳线帽设置
) H) R1 _! ^" J% t本周教程移植的例子使用内部RAM模拟了一个U盘,效果如下:  J, K( W; f  p6 n

2 G4 v2 `# v) M' L# P& A. K# r" t
9c04c38f56dbbfd80201520f1e84223e.png
* u) [. Q5 B2 G1 F8 o
5 o* s3 t0 x" M3 I& T
注意使用的是MicroUSB接口:
, K4 h/ {5 X( {8 m8 m" g$ k
% w9 _; N9 k, R7 ~2 g/ z
374a9b3f00b1d0e7cd589a59b3fe699a.png
! Z. U" H/ c, G
: ]- n8 u8 V# u$ [
注意板子左下角跳线帽的设置:
- n$ l' M9 ~/ l+ g' _. o, S* ]/ t$ A- \* r/ Y
f13c6739f82641308861da50db97c44a.png

- S8 F3 @5 N  R, T* J' b# k' {% r+ q* |! Y$ l
这里是用于选择CAN1 TX使用PB9或者PA12引脚,CAN1 RX使用PB8或者PA11引脚。大家这里可以什么都不接,或者CAN1 TX通过跳线帽短接PA12,CAN1 RX通过跳线帽短接PA11。切记不可以短接到PA12和PA11引脚上,USB要使用这两个引脚。0 l  U1 D6 X% ]( i# \* u* q

$ u. [& t5 C, P4.16 实验例程) V$ x- m! u" a) ]" b
本章节配套了如下几个例子供大家移植参考:# T( R5 g* A  P4 W  ?- D) @

7 b5 i5 m" w" p( l4 x  V7-4001_RTX5 Kernal Template8 z- R3 W$ v$ P- f3 c! f
2 c' }7 v! ?+ x! J" s4 u0 Y) j+ c9 g
RTX5内核模板。7 B/ `. F1 T, T+ i: Z% X' \( q

7 {& I0 i) Q. b* m- I4 s- a. x  V7-4002_RL-USB Template, O% {; D) ]0 F, _- D' b2 }

) S9 U  H) P* o' x; r  nRL-USB工程内核模板,使用内部RAM模拟了一个U盘。' ]6 t6 {" k. x7 ]! E# v

9 s5 ?% h1 W. p2 p% s" O5 dMDK进入调试状态后,选择周期更新:
9 G2 ^0 a5 [5 Y2 ]* x8 c' M- ?8 b$ z* P+ j
dca8f2e82304e411670c3194cde12230.png

0 [. S9 G3 e- x3 J1 {( x8 E1 W; a; N/ l' D  J+ j( L0 M/ u' `
然后打开调试组件,注意和RTX4的调试组件位置不同:1 s  Q% T1 i+ T( P# P3 \' W  ^

" v1 ~9 m% ~0 F4 }# H6 F
9daa841c2ebfbe6204c5bb95355e5707.png

. r8 ~+ t! [4 \8 N$ Z  l7 ~" ?( r; |) a: p4 F' Z* t
然后点击MDK的全速运行,
2 v' f- m' s2 p. a& A3 c$ E3 u$ i
3 U+ i# w% Q/ v; D1 {. E- ]' q
1d57a73648e5313c246a089fc2a85ac5.png

; v2 g; F; L& H, o3 H. s( G% q
# M- e4 T* [, ~3 _, `, j3 M: x至此,就可以动态实时查看RL-USB的运行状态:( Y) v# }5 |/ w2 N; K% d' O# Q6 x

+ B  m9 _- N2 R
1e9d6ebcc79d1df8a4302d0c846080e0.png

! \* [' y. f2 E2 z! Q
( Y# f7 z0 b% O0 `6 L- G4.17 总结

) ?+ [  k" r  f本章节为大家讲解了RL-USB 在MDK AC5上的移植方法,移植涉及到的知识点比较多,初学的话,建议实际动手操作一遍。
) e/ \0 q$ ?$ s) N/ n8 s+ s
3 l% a1 ?4 I; Y' E) `" w. M: Q5 J+ ]
" d, j1 s2 o( L, b2 V" I2 O
3 _  ^! S. w4 C7 {( N
( j# u3 d4 b1 N5 y$ l5 M
收藏 评论1 发布时间:2021-12-30 14:01

举报

1个回答
STMWoodData 回答时间:2021-12-30 14:28:14

好好学习

关于意法半导体
我们是谁
投资者关系
意法半导体可持续发展举措
创新和工艺
招聘信息
联系我们
联系ST分支机构
寻找销售人员和分销渠道
社区
媒体中心
活动与培训
隐私策略
隐私策略
Cookies管理
行使您的权利
关注我们
st-img 微信公众号
st-img 手机版