一、开发板平台简介:
1 O, K9 @/ r9 ?! k4 a; A1 _) g1、开发板资源简介. b( `0 q& J9 G, U. [- H2 g
(1)开发板主芯片型号:STM32L431RCT63 A! g g# F0 |* T$ W, ?8 _
(2)开发板主芯片封装:LQFP-64_10x10x05P
% b2 q& t+ S; b" a3 K% p( m9 Z(3)开发板主芯片内核:ARM® Cortex®-M4
% n/ w$ ?& ]% t& ](4)开发板主芯片主频:80MHz7 g! `7 q) _5 m9 n& Z
(5)开发板主芯片Flash大小:256KB" Q& L* {6 r3 l. a
(6)开发板主芯片RAM大小:64KB
* V$ F% z( `& K1 b
& f: ` [* F: |, k1 L" C, ]
* I; G1 m" o5 j) P/ J
8 f0 `+ ]" ?. \8 ?
6 W( E$ \ [4 n) N( j" I Y) \' G) q$ }9 w
2、LED灯资源$ r) o" q& ]; |
(1) STM32L431RCT6开发板共5个LED灯资源,其中一个红色LED为系统指示灯,指示开发板供电系统是否正常,如供电系统正常,红色LED为上电常亮状态,硬件原理图如下图所示:
/ E4 K, m$ n! N/ f3 r Y% N
. b" J9 G9 K$ U1 |
* B4 L6 w2 [! T( K6 t
# a" S# x+ T7 ~: p4 V1 S% L0 q, x9 o- ]1 q) i( N
(2)其他四个LED灯为黄绿色可控LED,高电平点亮、低电平熄灭,计划用LED常亮验证看门狗的作用,硬件原理图如下图所示:: i8 Q. M( N+ I/ o
- m9 z4 O" i$ B2 t
7 s) h6 w; t7 [
, {% X6 a% z- R8 j. L6 o0 v9 T
3、串口DMA收发工作原理- I+ ?8 \' w7 U2 v' _7 `) `$ p
串口全称为串行通讯接口,即数据在通信线上一次传输一位,按先后一定顺序传输。我们通常所说的单片机串口准确来说应该是串行异步收发传输器(Universal Asynchronous Receiver/Transmitter,UART),使用TTL电平,串口需要RXD、TXD、GND三根线进行通信。
0 b; Y% n# q6 b+ ~$ O: G' n1 D: X! }8 Q t& @4 D
(1)我们选用的STM32L431RCT6开发板串口1已通过USB转TLL串口芯片CH340G引出,使用时,只需要用公对公USB线连接电脑即可(注意也得需要安装CH340G驱动),后期验证试验也可使用该串口作为debug串口。
2 S8 Q+ h; r* E; X. G' L
1 ]0 D! f' ?/ t2 k (2)开发板上的其他串口已通过排针引出,为TTL电平,通信的时候需要注意选择对应的电平模块,如USB转TTL串口模块等。; n9 I# a; Q+ t D
( Y: b0 D. m$ h" Y
TTL转CH340串口,硬件原理图如下所示:
' w a: [6 I; A
% q. q. x0 d6 x
* `" Q# T2 @2 S6 q1 \) X
8 c* q: \. C5 k6 ]- dDMA(Direct Memory Access) :直接存储器存取,是单片机的一个外设,它的主要功能是用来搬数据,但是不需要占用 CPU,即在传输数据的时候, CPU 可以干其他的事情,好像是多线程一样。数据传输支持从外设到存储器或者存储器到存储器,这里的存储器可以是 SRAM 或者是 FLASH。
8 B0 J( p" h" T4 z7 [
( L- U' a8 B; e5 s6 rDMA 控制器包含了 DMA1 和 DMA2,其中 DMA1 有 7 个通道, DMA2 有 5 个通道,这里的通道可以理解为传输数据的一种管道。要注意的是 DMA2 只存在于大容量的单片机中。
3 O0 i9 S! S/ @+ W/ n8 g( E& O$ N7 D) O
5 h' \" \, M6 U1 q! x$ f7 ~, ^. L+ F' ?! l" G8 ]/ x6 Z X
二、串口DMA收发实验过程
/ Z) L0 L& F9 U6 M; p6 |/ J1、新建STM32CubeMX基础工程2 Z4 P+ x! L, Q3 I
(1)打开STM32CubeMX,点击“File”-->"New Project" m$ ]2 l4 }) {/ K$ {
* K; a/ R& E# R4 a
( f- }3 }. o) c$ K" I$ s
1 H! I) v* L) c(2)等待打开主芯片选项界面(大约1分钟时间)。4 e: @6 f( M( Q) M
- B. v ]* R+ i2 S c
! m+ p1 A9 h1 W. w+ ^
( \ U }' B: V(3)昨天搜索框中输入(或选择)所需的主芯片型号(因为我们用的是STM32L431RCT6开发板,所以此处选择STM32L431RC),然后在右下角选择STM32L431RCTx(因为开发板主芯片是STM32L431RCT6),左键双击即可打开新建的项目。
" j/ j. O) p1 j$ k4 \$ @" F% d, @) m4 n- d1 ~# O
; [0 ^4 k, I$ `
4 a3 u( R" `, `
(4)选择时钟源。) B7 Z; z, S3 `9 @* B
( q @- s5 C7 E0 l6 U; a! n
因为开发板上有8M外部时钟,硬件原理图如下所示,所以此处选择使用外部高速时钟(HSE)。
$ X8 u( ], o& l, ?' ?
: @! q4 q3 a: R, R+ k& @# Q3 n7 J1 Q
9 ]/ U/ z" @& N" u/ U. v2 U
, o8 L, a: ]* t/ }7 G0 ]
& q% E$ d9 R: X' g4 v: Z. A 因为我们没有用到外部低速时钟(LSE),此处不做处理,如下图所示。* [4 b& S, D8 g: n5 B9 J% G6 C
- w$ J$ X( |9 A+ @: P
) z9 n, m0 ]: t. O3 ]9 V4 T
2 |$ I1 @5 f4 V2、配置GPIO控制LED
/ ?* w1 W Y7 z+ x8 f(1)查开发板原理图得,LED1、LED2、LED3、LED4的控制引脚分别为:8 V" X, l }- a$ s
LED1——PC0* m, Z6 T K3 ?: Y- c1 D/ q
LED2——PC1
6 V* f# ]! k" w/ FLED3——PC2
. F% \! ?$ P) O9 DLED4——PC3
8 f% T4 l4 N" I$ W$ h! j) s* Z
+ g. @* L1 j6 [3 L(2)配置LED的控制引脚为输出,输出频率、输出方式默认即可。
+ X+ g, N1 T: w
8 q! N+ O7 k! ~" J: x鼠标左键点击PC0,选择“GPIO_Output”,表示设置该引脚为输出模式
. V2 B( l m" c* x; R6 o$ ?/ L鼠标左键点击PC1,选择“GPIO_Output”,表示设置该引脚为输出模式。& ?" S9 i. n3 p0 a* `4 i
鼠标左键点击PC2,选择“GPIO_Output”,表示设置该引脚为输出模式。
+ L8 }8 c* B% z) f" N鼠标左键点击PC3,选择“GPIO_Output”,表示设置该引脚为输出模式。: ^( }6 V" @. o6 w4 g# s0 p
. _, e: ]8 T/ g; ?' J, i
3 I# Q# V: A0 L9 G0 O7 }
' ] s, G4 E; Z" \4 j! p, b
$ Y |5 z# o$ c, @: r, e% }
& K) U5 E8 L1 O" l& u" T$ P% s(3)也根据自己的需求配置GPIO的参数,如输出方式、输出频率、上拉下拉等。因为GPIO控制LED的要求比较低,此处采用默认参数即可,不用修改。
( m; u+ e' c& Z& j4 I' \: l/ O- U) a) j
# G- W6 D2 p J, @
' J' K) m& i1 j3、配置PA9、PA10为串口
) m! u3 D, `8 q* `(1)查原理图得知,串口1使用STM32L431RCT6引脚为PA9-USART1_TX,PA10-USART1_RX,引脚设置如下:
0 R, R* k Y& `, I# v u3 ?; f( S1 H9 \4 Y+ L# @" { C
4 C( s7 `$ e' [9 g" U% r
& G! {, W. {. p2 t( X3 y) g$ `
序号1用来设置串口收发引脚的选择。* B, x* z9 Q# t8 f9 x$ y
序号2-3-4-5-6设置串口参数,如波特率115200、8位、NONE无奇偶校验等。0 t0 X6 w" j6 H4 m
/ G( Q( ~2 z$ z& y
(2)设置NVIC settings 使能接收中断
* l6 m# C- W' `) o* z' J% q' J# q" |( u- R! Q+ S
4 P9 f6 j6 j$ t( Q4 b
5 P) U( g9 ~! a0 O) C) }5 S9 E; O' `3、串口DMA设置 2 k7 P4 g& B$ \; u' H6 \4 S
/ J3 y* n3 ^1 \! J
- l) h0 X; C6 ?& E% f& h1 G; f! l/ B2 ]5 r
(1)根据DMA1通道预览可以得出,我们用的串口1的TX、RX分别为通道4、通道5:& J/ z7 Y5 k/ `# z/ I- ~7 V
点击DMASettings 点击 Add 添加通道2 m- u3 F4 a& p
选择USART_RX USART_TX 传输速率设置为中速- `3 K/ _7 o2 `, O
DMA传输模式为正常模式,即发送一次就结束。
: L g( a" ?! C1 `. ODMA内存地址自增,每次增加一个Byte(字节)
: G' ^8 W2 }0 o, j9 B$ k) H5 [ p3 {# x: w$ e$ G" B% p( T
. j% v6 O- Y" J2 B
+ k+ }( s1 |2 J, } (2)DMA相关参数解析
' b% C) J7 c' L O- uDirction : DMA传输方向有四类2 Q5 u7 j0 k3 } ^' l
外设到内存 Peripheral To Memory$ @& ~2 e0 o9 P J
内存到外设 Memory To Peripheral
3 |! d; ^7 I1 Y! e G内存到内存 Memory To Memory
/ H+ q2 c2 S6 e0 T9 |0 ^" b外设到外设 Peripheral To Peripheral
( d* B( ^7 J2 h% G' X; D# m8 J, [
$ h$ C) |7 y4 i iPriority: DMA通信传输速度有四类
; X7 P1 {; u; L- K2 L2 @0 b5 v: g. E最高优先级 Very Hight
- `. |) T! H1 z( Z" ]高优先级 Hight
: T, V! D$ e1 u$ N% N- a$ S& f1 Q中等优先级 Medium+ q6 v m# W- n" m- l7 ^( ]
低优先级;Low
. t/ E @6 F/ H: O. B
: [6 ?6 Y/ i' S& e1 k. ^8 v" rMode:DMA传输模式有两类
' a- d8 ^0 d- G. P6 U
5 a0 `6 U& L" z9 o e
F/ L* } F' B# v! Q( e7 }
/ D ]% u, M6 dNormal正常模式:当一次DMA数据传输完后,停止DMA传送 ,也就是只传输一次。
, V9 F# u' o% i3 P7 ECircle循环模式:传输完成后又重新开始继续传输,不断循环永不停止。6 [: Y' P9 _6 @ _, }
$ r% z; p" y* @' `Increment Address-DMA指针递增设置:4 A. F, a9 w. z3 {
! ^; V4 B& G6 E& b4 H: L( [
2 Z8 W+ |8 i+ l/ V3 T" I
' n3 w; d2 k& z8 Q2 z0 ^
! k+ u# H5 U5 J4、配置项目工程参数
$ q6 F# x6 \7 Y0 S& B+ T(1)配置时钟树,用于系统内部时钟,以及各个外设时钟等。此处选择外部8M晶振作为主时钟频率,内部最大倍频80MHz。
8 i- \4 X, t8 x# k! ~' F+ }% b, P2 B% T( m$ r* U3 x# \+ e F+ u/ a
+ V+ d: l6 x; C! |) s' B" `* S/ e @+ C) O' O7 v/ M8 ?
(2)完成配置工程。
% S* X: p6 q2 q& T1 k% }* S( @备注:需要注意代码生成过程中的继承关系,如图所示:需要保留开发者自己编写的代码时,请根据配置设置,不然生成代码后会删除自己编写的代码(从这个方面也可以看出开发者备份自己的代码是多么的重要。)- K' [8 X2 A3 k4 j: C N
U- |2 R/ Q) s; A
6 ^5 ?) L+ N0 h* ~5 V" l: R
+ B3 s; ?+ x' v
5 F9 ~; ~* s3 P" Z) d
% {. Y- j0 v. i! x4 } u5 l(3)生成代码。4 A) u* b3 y- R6 ?( f0 ~
& H* ?8 z% e$ R' W& } n备注:使用Generate CODE生成工程代码前,请确保文件路径无中文,否则会生成项目失败。
' \; [( F2 E7 i5 p4 x8 x4 Y) Z: c% g5 i( d$ N
* e$ I0 @+ Q" R: G" b
; s% y; w% G5 l) v5 N$ w$ e& o2 F(4)工程代码生成成功。
* a5 `6 ^1 t1 E0 Q! T; k& k" ^" T2 k* }% k5 i
% [9 I( M$ |$ k" t k& d8 a3 W
" i' S& X' f( W# ]8 @9 C 三、在KEIL 5中编写代码
6 `4 q& Y% ~" f! D) ^' K1、使用KEIL 5(MDK)打开项目工程文件( L( V( _/ j8 `+ ~9 I
源码使用说明:使用前必须把项目工程复制到无中文路径的文件夹下使用。
, e+ B1 l# s+ L# C(1)找到刚才新建工程的存储路径,安装项目名称,打开项目工程.uvprojx。% h& j. g' R* K
8 D1 u) e/ ]# n1 ]7 z5 B( O
, D7 |3 B- `( |8 ^3 F2 b, a5 j+ Z8 ?
2、添加LED指示灯作为系统提示
6 D: |! m; C# F4 _添加每隔100ms,LED1、LED2、LED3、LED4闪烁一次的系统提示,用于提示程序运行正常。
6 s3 n: U r$ \2 s$ Q/ r% G7 U' ?6 |, m
* Z* P- l u/ |- s6 e# y
) i5 K' B( k/ |3 d. C
3、添加HAL库UART DMA 发送函数代码
( W! l1 R' L/ r J H$ Q$ S(1)STM32 HAL函数库的串口DMA相关函数如下:1 y/ S8 T" n5 D! z- ^
- HAL_UART_Transmit();串口发送数据,使用超时管理机制
: K% ^) B( N+ R7 e" A0 M4 U - HAL_UART_Receive();串口接收数据,使用超时管理机制% J4 K+ U6 i& I" h* ~' B4 R3 v
- HAL_UART_Transmit_IT();串口中断模式发送. Q* Z1 k6 s7 I& k4 n( E
- HAL_UART_Receive_IT();串口中断模式接收+ [4 w4 z* @1 G" a* }+ X
- HAL_UART_Transmit_DMA();串口DMA模式发送
! j) N( f0 l2 ?1 y1 t - HAL_UART_Transmit_DMA();串口DMA模式接收. B7 y) ^3 E" [9 l% `, Z! `
- HAL_UART_DMAPause() 暂停串口DMA
- A& ?8 g/ ^, T: Y( u, b* N) z- m/ u - HAL_UART_DMAResume(); 恢复串口DMA# B7 z* Q0 W. U, k7 h; Q
- HAL_UART_DMAStop(); 结束串口DMA
复制代码 0 ?4 h; }# W: w9 g, I. x6 J" F: Q& P
(2)main.c添加串口DMA发送函数相关代码:" t" l0 A, \4 r* Z7 E5 b
- /* Private user code ---------------------------------------------------------*/: d$ _/ Q. r8 ]7 j3 e! Z+ P& S
- /* USER CODE BEGIN 0 */$ s3 j0 J4 X# q r. k1 o
- uart_rx_struct uart_rx_struct_t={0}; //串口接收数组
* ]1 p4 M; Q, @. f' j, Q5 j - /* USER CODE END 0 */
复制代码- int main(void)
$ a* s+ m( E6 F4 h5 ?2 b - {- I$ d) E+ d G1 [
- /* USER CODE BEGIN 1 */
+ l1 _4 y" } p" b. {4 R - uint8_t transmit_str[50]= {"hello world,this is uart dma function!\r\n"};
6 H3 D8 X d$ h' C/ H4 ^ - /* USER CODE END 1 */" z4 W* {7 n/ W5 n
-
' [+ m* I ]5 G9 z2 ^0 I8 o$ f2 ? - /* MCU Configuration--------------------------------------------------------*/6 F3 e5 F F1 J
-
0 L: s0 V, g6 }/ d% q6 E - /* Reset of all peripherals, Initializes the Flash interface and the Systick. */. A8 T0 C2 Q( a% N4 j; q/ J. t
- HAL_Init();
! I l; M1 E! g0 Z5 r/ | -
) u. Q r5 `) @3 I9 j - /* USER CODE BEGIN Init */
% S! g$ R) m1 u9 W& l3 C$ o - $ k- S" {* Q6 y7 G) A9 W( n
- /* USER CODE END Init */, D. H# ]) j! k3 z
- 0 |. J, k8 p' @7 X8 ?* ~, l% J* w
- /* Configure the system clock */
+ e; l( ]1 j& _/ A( F1 G - SystemClock_Config();
9 F0 N9 ~& I! o -
a- u* ?8 C( e8 k' C8 u - /* USER CODE BEGIN SysInit */
h% z, N0 m) j) E$ m% K - # Q3 }) r0 z/ ?* _. y
- /* USER CODE END SysInit */
" _5 u2 V/ {4 ^" E& N7 K1 Z -
5 c$ s- G3 Y* Y% b' U - /* Initialize all configured peripherals */
8 Z4 m* [. z, _# ^% U - MX_GPIO_Init();, F6 y5 B2 x+ K
- MX_DMA_Init();
. \. O' [# a- C/ o - MX_USART1_UART_Init();
& V. ^$ _; i+ \: E+ n - /* USER CODE BEGIN 2 */
1 L* E% E; t! d0 `9 H' B6 _ - HAL_GPIO_WritePin(GPIOC,GPIO_PIN_0,GPIO_PIN_SET); //初始化LED灯,默认点亮
5 {- G% o" D: t. g6 g7 a: Z7 i$ y - HAL_GPIO_WritePin(GPIOC,GPIO_PIN_1,GPIO_PIN_SET); //初始化LED灯,默认点亮& ^. D2 p% e* v5 j) A* c
- HAL_GPIO_WritePin(GPIOC,GPIO_PIN_2,GPIO_PIN_SET); //初始化LED灯,默认点亮$ [4 ~ J2 ]/ n
- HAL_GPIO_WritePin(GPIOC,GPIO_PIN_3,GPIO_PIN_SET); //初始化LED灯,默认点亮; m4 a1 v2 I; h. C- W8 f: m
- HAL_UART_Transmit_DMA(&huart1, (uint8_t*)transmit_str, sizeof(transmit_str)); //
; y) h. |/ O$ _: {( Y. V+ K - HAL_Delay(5);: \3 t: R: ~+ e' r5 Y2 R5 B
- HAL_UART_Receive_DMA(&huart1, uart_rx_struct_t.uart_rx_buf, UART_RX_LEN); // 启动DMA接收# V3 m/ m' a9 J1 c0 k1 O' \
- __HAL_UART_ENABLE_IT(&huart1, UART_IT_IDLE); // 使能空闲中断9 F% h. J3 F9 `/ d, Q
- ( a+ H4 S3 \9 P5 S0 f H2 a
- /* USER CODE END 2 */
. e2 `* p1 J9 e - " O7 V% a! @* w2 Z- U- H
- /* Infinite loop */& R4 v1 e0 I6 M) H1 b/ P6 x
- /* USER CODE BEGIN WHILE */
8 C/ y+ I4 A& @6 T' P - while (1)
2 a8 Q9 G0 a& } - {
' Z! p" g1 D( s% `: E! J8 ] - /* USER CODE END WHILE */2 p9 c4 w& k9 H( k: O+ \
- ) J* d# l$ a6 }; V2 h4 G# S$ t
- /* USER CODE BEGIN 3 */
2 u/ v2 L# P) ] - HAL_Delay(100);
6 d! r8 j) d& p - HAL_GPIO_TogglePin(GPIOC,GPIO_PIN_0); //反转LED点亮熄灭切换* e; H/ t8 k: Z* }" ]8 X6 ~3 T! N
- HAL_GPIO_TogglePin(GPIOC,GPIO_PIN_1); //反转LED点亮熄灭切换* \0 q8 n+ A1 L- P
- HAL_GPIO_TogglePin(GPIOC,GPIO_PIN_2); //反转LED点亮熄灭切换
! S J7 V1 K1 q* S* C! x; H% k+ ` - HAL_GPIO_TogglePin(GPIOC,GPIO_PIN_3); //反转LED点亮熄灭切换
* h) P, }% v$ A% } Z - if(uart_rx_struct_t.uart_rx_flag & 0X80) //DMA接收完成
8 r: [) J) ~7 v9 z& j; i - {# H' s( M" A \. s7 X- g$ c8 H
- HAL_UART_Transmit_DMA(&huart1, uart_rx_struct_t.uart_rx_buf, uart_rx_struct_t.uart_len); // 将接收到的数据发送回去
8 W- }" t! j+ E. J - uart_rx_struct_t.uart_rx_flag = 0;
+ m, h) j% H* @7 ` - }
4 v2 X# r' b% R9 M5 ^ -
% }2 |2 W2 q8 s* y2 ~ - }5 V% y! A& t# m
- /* USER CODE END 3 */
& V0 `# V5 ]: h - }
复制代码
$ S' q# x" V* y% H, N @2 r(3)main.h相关变量声明
, s; k) y6 u% s7 i: t5 V- /* USER CODE BEGIN ET */
% t. z3 n+ B- a9 I# i% ] - #define UART_RX_LEN 1024 // 一次最大接收的数据量
4 A5 |5 o$ }* J+ S7 V' J - typedef struct
* O0 W7 T$ a t3 I2 T - {( E) B+ y) W1 M8 q. y8 p
- uint8_t uart_rx_buf[UART_RX_LEN]; // DMA数据接收缓存数组+ X l2 Q ^4 x5 j E* R' X
- uint16_t uart_len; //DMA数据接收长度
7 d3 U/ x( P5 G c7 C - uint8_t uart_rx_flag; //接收完成标志位# L& |! {. S/ [" C2 G
- }uart_rx_struct;) F5 i7 }. Q8 W' ~
- extern uart_rx_struct uart_rx_struct_t;
9 _! }0 @3 h+ w% F2 e; q$ T -
( }9 L. y- C2 N5 c/ T( t - /* USER CODE END ET */
复制代码
5 k+ \' l- {2 S" w$ R9 p- ]/ r4 d d9 E4、添加HAL库UART DMA 接收函数代码
i2 X8 n7 W" A" j6 P& e(1)DMA接收设置前铺垫知识点:) h2 ]0 Q3 m9 e8 o
STM32的IDLE的中断产生条件:在串口无数据接收的情况下,不会产生,当清除IDLE标志位后,必须有接收到第一个数据后,才开始触发,一但接收的数据断流,没有接收到数据,即产生IDLE中断停止。
2 ]+ s1 C" o* C, o% f9 F$ U6 n h
(2)添加DMA接收处理代码' N8 ?2 z- A# i. ^* l( @9 B
2 b. a- p: l r# a) _stm32f1xx_it.c中添加代码如下:, K; ]- j# x4 R, q, [* ]3 D
- void USART1_IRQHandler(void), E V, a: q8 x) S1 z9 e# I
- {
8 F) i) e* |, I! ]8 z - /* USER CODE BEGIN USART1_IRQn 0 */8 `8 F$ ]. z; m. l8 \
- if(__HAL_UART_GET_FLAG(&huart1, UART_FLAG_IDLE) != RESET) // 空闲中断标记被置位& ~, X e( O+ B
- {
5 \) u) n$ G8 Q, m - __HAL_UART_CLEAR_IDLEFLAG(&huart1); // 清除中断标记" ~; ~4 c& U( ^3 E9 i
- HAL_UART_DMAStop(&huart1); // 停止DMA接收
+ O. X) @1 ^9 [ - uart_rx_struct_t.uart_len = UART_RX_LEN - __HAL_DMA_GET_COUNTER(huart1.hdmarx); // 总数据量减去未接收到的数据量为已经接收到的数据量. U. N% J: `% a( B
- uart_rx_struct_t.uart_rx_buf[uart_rx_struct_t.uart_len] = 0; // 添加结束符
`# \0 z4 }) i5 P; f8 U f - uart_rx_struct_t.uart_rx_flag |= 0x80; // 标记接收结束9 K1 R. { X" u" r/ ?
- HAL_UART_Receive_DMA(&huart1, uart_rx_struct_t.uart_rx_buf, UART_RX_LEN); // 重新启动DMA接收
! r& O" P2 `, T, N3 _- | - }" ], s7 d5 I/ x
- /* USER CODE END USART1_IRQn 0 */' [. X) L& @" L% o5 o# f
- HAL_UART_IRQHandler(&huart1);4 y2 u6 U8 @9 w: i. s
- /* USER CODE BEGIN USART1_IRQn 1 */( p2 `, o/ U0 {( e6 K6 I
-
8 W+ G5 \/ M* ^" r0 G! v - /* USER CODE END USART1_IRQn 1 */$ U6 f' W/ F2 a% `7 `
- }
复制代码 * ~& j+ [" z7 h% W+ t+ M" w
(3)至此,串口DMA收发数据需要添加的代码已经完成。# |1 o6 a* q) q. f; T! E" h
# H$ g$ i3 r5 |5 u5、设置编程仿真下载模式" v; F; O4 m3 d: U' d
(1)选择Options for target ...>>Debug>>J-Link/J-JTRACE Cortex,点击Settings>>选择Port(SW),可以看到搜索成功SW Device,表示芯片可用,可以下载。
( ~. ?8 p) m4 p% M$ a7 M: J, t4 `( [8 o$ t2 D9 N
2 s" b" E& f8 B& V o
/ g- v4 R; ~" B* ?$ s* _5 N5 I z
(2)点击编译,完成后提示“0 error(s),0 warning(s)”。$ O% v% e- I4 L6 M0 v; c
/ H: F5 u0 J$ Q( X) {5 H/ u
& |5 ?+ R; W7 e% G: E: O
3 P/ o5 S# z# g) s* N& v(3)点击Download(或者快捷键F8),即可下载程序。% U6 i8 @2 d( h4 G
7 P/ @2 c, |1 O8 |2 K8 O3 j
! E1 @) F! R6 P2 }: A
1 T/ ^. l, I) o! N6 q" t {$ m: u& ]
(4) 如果下载程序后,没有看到LED1、LED2、LED3、LED4闪烁,可以按下述方式设置一下(Reset and run表示下载后自动复位和重启运行)。或者重新彻底断电再次上电(或按开发板的Reset按键复位MCU即可)。
4 ~9 K% n; [& S. P+ O, I0 x" h+ M3 W! \' e$ `
* w N6 {7 b! T$ d
3 \& A! m1 H- N+ v6、串口DMA收发实验效果展示
' R; B$ g6 v2 D. D' x+ j/ P 程序烧录到开发板后,即可看到LED1、LED2、LED3、LED4初始化后每隔100ms闪烁一次,并且打开串口助手后(串口参数:波特率115200、N、8、1),通过串口助手可以看到,开发板接收到发送的数据转发出来。2 f# R: m) q/ `8 x
$ X# w% Q) t* m, A; R) c& s/ Y
: }/ K+ v, [+ d4 Q' q1 W
; Z& H5 v. Q r( K' Q3 h3 k————————————————
9 C( U6 p: J5 y8 p版权声明:智能小屋ZYXC9 |! O3 g; i+ f( [. |) e
3 S% B: g+ A) A% u5 y. Q2 w( {, k, [% |/ S: A7 Q h/ K
|