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

【经验分享】STM32F0系列开发之串口的使用

[复制链接]
STMCU小助手 发布时间:2021-11-22 22:03
写在前面
( a+ z% J; `4 `+ \芯片型号:stm32f030c8t6
  I5 l$ Z* z; @6 C说明:便宜,用量大
9 A% M; r7 E, s# z要点说明:初始化、主函数调用串口接收callback、串口接收空闲中断,串口接收中断0 s+ B$ O7 m( ^9 o# j+ {9 d4 g& k
这种API封装方式可以拓展到其他单片机,但需要注意单片机是否支持接收空闲中断) k4 p# Z5 A  z- ^# L1 g1 X; ]- t
本文注意介绍空闲中断的应用,这样就不用在定时器中计时来检测接收超时中断了
  g% R' ^8 _# b% |# \1 w" M: J
" Z# w1 n" |7 C4 b4 S  i6 J# h- P  }' T  s一、应用
! F' w! j; x+ l9 F$ L1 D7 T外部定义串口接收回调
  _6 S, y, {2 j3 T  A6 ~/ V当串口数据接收完成后,在该回调中处理串口数据即可
  g3 i  u, R$ [; [7 W# e
  1. void Uart_recvCallBack(void *buf, int len): S& p3 `7 d  _( }2 u
  2. {# z4 \* a/ q& Q: l: ~" D8 }
  3. 4 F4 p+ e" w3 B( w8 }
  4. }
复制代码

; ^( w) T  d3 Z8 K# [- y外部初始化串口) W+ x: J* c( Z. k
  1. myUart_initialize(115200,
    / h; u) F6 t; J: ]9 d
  2.                                         USART_WordLength_8b,+ P' M& _) Z9 Z* w7 q& }7 ]
  3.                                         USART_StopBits_1,
    7 P2 F& W5 G' `* k! h1 c
  4.                                         USART_Parity_No,. o8 P3 t6 o  E, `
  5.                                         Uart_recvCallBack);
复制代码

% E) L9 s8 k8 v1 K  d  ?6 ~+ R/ G二、源码
  o7 N1 V2 C9 c6 Z! QmyUart.h. o/ B9 ?# X- V" M6 L6 k8 W% @
  1. #ifndef __myUart_H) u, z  Y0 u( c9 v$ Y
  2. #define        __myUart_H
    , g" ?/ P8 E& _5 P

  3. . u2 E& ^* j- w; H
  4. #include "stm32f0xx.h"0 U5 ^1 j" `  W8 H1 E$ \
  5. #include "stm32f0xx_usart.h", f; f5 d9 v) x4 Z( H" m9 ~6 {
  6. #include "stm32f0xx_gpio.h"
    : T  ]8 ]0 ?. L1 {. o
  7. #include "stm32f0xx_rcc.h"
    ' x; t2 O1 G9 _6 T
  8. #include "stm32f0xx_misc.h"
    ; E% o+ r3 z% M  D

  9. 0 H' T5 y* Q: x4 v( {' @0 t
  10. #define USART_REC_LEN                          200          //定义最大接收字节数4 t/ k3 |, R& ]- I

  11. / `; q4 r& }* b/ f8 f# ~2 @* E- U( g+ y' H
  12. typedef void (*myUart_cb)(void *buf, int len);; P9 Q$ a2 F. k
  13. 7 g! q$ F: b: S- Q. R! e) |* Y) S
  14. void myUart_initialize(   uint32_t USART_BaudRate,
    ; X4 |# ?: J- G9 L: C7 V! D
  15.                                                         uint32_t USART_WordLength,
    0 L8 c9 C$ s2 ~) @: M
  16.                                                         uint32_t USART_StopBits,0 e# O6 M% o* x) f2 u1 x% ~" L
  17.                                                         uint32_t USART_Parity,, M7 q/ x9 p0 E" f4 R
  18.                                                         myUart_cb cb);
    6 g/ A- F5 N% |4 ?
  19. void myUart_setBaudRate(uint32_t USART_BaudRate);8 b* {# g# y4 O3 }  u
  20. void myUart_sendByte(uint8_t byte);" M$ a1 B, G3 t8 a1 O7 N
  21. void myUart_sendBytes(uint8_t *Buffer, uint32_t Length);
    % d$ w$ z2 A. \$ d
  22. uint8_t myUart_recvByte(void);/ a3 a) i& y, n' R; Q' R. N0 M
  23. int fputc(int ch, FILE *f);7 G& W. D4 u: N6 e8 _$ }, X) y

  24. ; ]! K- |0 l( P+ r5 y" ]
  25. #endif /* __UART_H */+ T' C- H' j1 I3 `, b- C; P* _
复制代码

5 g& ~4 c3 H$ r: [9 }) E" YmyUart.c
, p+ g4 Z# s8 R: N6 L
  1. #include "myUart.h"
    4 T8 \) K  ?2 y. S' p

  2. 2 e. s! e. s. V
  3. #define PUTCHAR_PROTOTYPE int fputc(int ch, FILE *f)
    0 b) W" B- M6 e( x

  4. ' ?8 ^$ E( F4 E( {1 N0 N
  5. uint8_t USART_RX_BUF[USART_REC_LEN];     //接收缓冲,最大USART_REC_LEN个字节.9 q- w: h* w) p, X
  6. uint16_t USART_RX_count = 0;       //接收状态标记               
    ! I2 q. z3 K1 {& m
  7. myUart_cb myUart_callBack;
    9 `! Q; g6 c8 @8 d8 a( [3 t9 P/ c5 l& G
  8. /* Private functions ---------------------------------------------------------*/3 q: b' C0 j9 E

  9. 2 v4 Q( L3 B* _) t
  10. USART_InitTypeDef USART_InitStructure;. g% f" i& O3 o2 j; D1 i
  11. / f1 K  @4 ?8 K
  12. void myUart_initialize(   uint32_t USART_BaudRate,% B4 ?1 N3 P* C; A* t8 l8 ?6 Q
  13.                                                         uint32_t USART_WordLength,- }6 H  ?+ v; W' w1 c- q
  14.                                                         uint32_t USART_StopBits,
    6 K" E: j: k7 _1 a3 R, C
  15.                                                         uint32_t USART_Parity,
    1 g: {( _( i4 Y; _- J3 |5 I
  16.                                                         myUart_cb cb)
    7 X. D' q7 Z) _- u, \7 g6 _
  17. {  
    ) h5 }- N! n4 k! |5 f# c

  18. 5 @6 D# R) |$ ^% s+ n
  19.         GPIO_InitTypeDef  GPIO_InitStructure;
    : ^6 J, l$ ~" A2 G+ X) p
  20.         NVIC_InitTypeDef NVIC_InitStructure;. r7 S6 U5 u" d% r; u7 v5 U* ]" L
  21. 7 r) d' v( h. |6 C6 ?
  22.         RCC_APB2PeriphClockCmd(RCC_APB2Periph_USART1, ENABLE );
    8 [" o+ H/ A6 K6 _# @8 i
  23. / W, a  G: Z. ~! }3 \9 E9 M: ^; `
  24.         GPIO_PinAFConfig(GPIOA,GPIO_PinSource9,GPIO_AF_1);
    0 ?8 U! i8 M+ U! ~7 W
  25.         GPIO_PinAFConfig(GPIOA,GPIO_PinSource10,GPIO_AF_1);        8 R4 f! h1 o8 g5 ^) T( |$ q
  26.         /*+ ~) w5 H0 t: E0 z( W2 S! ?
  27.         *  USART1_TX -> PA9 , USART1_RX ->        PA10
    9 u2 {2 Z, K. L1 X
  28.         */                                
    3 k( O& W! d4 @" Y, n% \
  29.         GPIO_InitStructure.GPIO_Pin = GPIO_Pin_9|GPIO_Pin_10;                 
    : ^) t- ^8 m$ m" G- m0 }
  30.         GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AF;
    ( Z5 Q9 L) k. V9 B* ^+ V) f2 E# Q( ?
  31.         GPIO_InitStructure.GPIO_OType = GPIO_OType_PP;
    , ]8 D) Q4 W$ A0 j1 n4 B8 J
  32.         GPIO_InitStructure.GPIO_PuPd = GPIO_PuPd_UP;- |1 a5 t. N: ]. z
  33.         GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz; ( e. B( W: i: F6 J( u
  34.         GPIO_Init(GPIOA, &GPIO_InitStructure);        
    " Z2 b" t- u7 r. Q" Y" T8 O

  35. & U0 D( n- L2 D3 \
  36.         //Usart1 NVIC 配置
    + S1 |% ~5 e" F3 }" l
  37.         NVIC_InitStructure.NVIC_IRQChannel = USART1_IRQn;
    % d. d/ m8 f( Z. j3 `
  38.         NVIC_InitStructure.NVIC_IRQChannelPriority=1 ;//抢占优先级3) F: k) c4 B9 t+ y* l, B
  39.         NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE;                        //IRQ通道使能6 E0 s, V* R( }& F
  40.         NVIC_Init(&NVIC_InitStructure);        //根据指定的参数初始化VIC寄存器
    5 R% V  E2 c- z, q, R

  41. : @4 ~/ P9 i3 i7 w) w% L/ @
  42.         USART_InitStructure.USART_BaudRate = USART_BaudRate;//设置串口波特率+ I9 Q5 E* Y( j! G% ]6 o; {
  43.         USART_InitStructure.USART_WordLength = USART_WordLength;//设置数据位
    ' E4 F! ]" s8 @3 V0 ]
  44.         USART_InitStructure.USART_StopBits = USART_StopBits;//设置停止位% g' C) X9 N* d, O3 b% }* Y
  45.         USART_InitStructure.USART_Parity = USART_Parity;//设置效验位
    # K4 G! P2 F/ q
  46.         USART_InitStructure.USART_HardwareFlowControl = USART_HardwareFlowControl_None;//设置流控制
    0 I9 K- `& L" J/ `3 h
  47.         USART_InitStructure.USART_Mode = USART_Mode_Rx | USART_Mode_Tx;//设置工作模式
    + G+ V3 F7 f# P8 e- o
  48.         USART_Init(USART1, &USART_InitStructure); //配置入结构体
    6 g  T7 o4 l; N  ]9 \* q

  49. 9 S$ O; m& X3 v. v  k+ ~
  50.         USART_ITConfig(USART1, USART_IT_RXNE, ENABLE);//开启串口接受中断/ v2 O, A! b, o
  51.         USART_ITConfig(USART1, USART_IT_IDLE, ENABLE);//开启串口接受超时中断
    . D, b" N% H  k' g; a1 r7 W
  52.         USART_Cmd(USART1, ENABLE);//使能串口1
    $ Y' v$ a( Y$ G- }1 }7 H

  53.   r  w5 b9 z& d* O' N
  54.         myUart_callBack = cb;
    8 _4 O. \/ k, d$ {/ ]
  55. }                        ' E5 @% o) C# n7 h: o9 U
  56. void myUart_setBaudRate(uint32_t USART_BaudRate); s& [/ S2 h: b# J( V5 i
  57. {
    9 b8 a5 S6 @5 Q% F( ]- [
  58.         USART_ITConfig(USART1, USART_IT_RXNE, DISABLE);4 ?5 k- \6 g0 j8 s
  59.         USART_ITConfig(USART1, USART_IT_IDLE, DISABLE);9 ]3 O+ S  z0 w1 ^5 h5 S
  60.         USART_Cmd(USART1, DISABLE);
    , J; `; s. p: p8 i5 Q

  61. 5 j6 }+ t7 F& _7 Y+ K; y
  62.         USART_InitStructure.USART_BaudRate = USART_BaudRate;//设置串口波特率6 D) i, U- r; R) H' S: K  @; @; t
  63.         USART_Init(USART1, &USART_InitStructure); //配置入结构体7 X. X3 Z( T9 V9 a% P7 B* J

  64. 0 Z0 F0 r  Q+ ~* I
  65.         USART_ITConfig(USART1, USART_IT_RXNE, ENABLE);//开启串口接收中断) ^9 [3 i6 Q" A' S. x4 F
  66.         USART_ITConfig(USART1, USART_IT_IDLE, ENABLE);//开启串口接收超时中断. g, F( q& N# J% a0 C
  67.         USART_Cmd(USART1, ENABLE);//使能串口1: V5 A3 u  E) g6 w$ _
  68. }
    ) O7 p+ A! m  |1 p5 U1 V
  69. void myUart_sendByte(uint8_t byte) //发送1字节数据
    2 ]% b$ W6 f2 d( b* I7 X  H
  70. {3 w/ n( [6 u" _. P& m2 T0 m
  71. while(!((USART1->ISR)&(1<<7)));
    # w. S$ X% Y5 R5 I- |
  72. USART1->TDR=byte;        
      J& e1 x8 ^+ B! X; D
  73. }                1 T7 M- z3 A+ D* Z7 G. `- h( g

  74. * G, C  R: u* l2 n, f  w. y5 L; b
  75. void myUart_sendBytes(uint8_t *Buffer, uint32_t Length)
    ! b# e8 T/ |& ~; g7 ^: \  k1 z- B
  76. {  d. }: q/ ^. r* M5 V6 `
  77.         while(Length != 0)
    / N! X) a! g/ m% \: j  X2 N
  78.         {+ @9 b  }' t  c& ?
  79.                 while(!((USART1->ISR)&(1<<7)));//等待发送完' J3 [& b0 G# _* T" v* Y% B
  80.                 USART1->TDR= *Buffer;+ ?) s; a& N* `! |
  81.                 Buffer++;
    7 G2 ~" M; n; {! X
  82.                 Length--;
    " L$ d/ J8 h' \- e( M2 q" G$ ^$ s, ]
  83.         }
    2 S+ O* H) b4 q7 G' Q1 x
  84. }
    $ r6 l! V/ a- h# c' Y# E
  85. , R1 F: M9 ?7 A. W) L" P0 s
  86. uint8_t myUart_recvByte(void)& ^% m4 F0 l; s5 C6 ~
  87. {        
    9 O" [4 B9 [$ x" S. p4 }+ J/ B
  88.         while(!(USART1->ISR & (1<<5)));//等待接收到数据/ s9 i9 j7 y2 k7 s# `
  89.         return(USART1->RDR);                         //读出数据
    % ]6 v8 W9 X2 X9 i8 p9 b
  90. }, ^* Z# a) v9 t9 N$ |9 B

  91.   R/ g8 T$ g7 V. Y& O
  92. 0 O9 \& [5 k" f8 h8 z
  93. PUTCHAR_PROTOTYPE + N: ~& A' @  ]
  94. {7 l7 ], J  J5 c  ~
  95. /* 将Printf内容发往串口 */
    7 \, e" K! l* n$ [
  96.   USART_SendData(USART1,(uint8_t)  ch);
    * o1 A: Y1 e2 Q
  97.   while (USART_GetFlagStatus(USART1, USART_FLAG_TXE) == RESET)
    ( e( n% q( N5 e
  98.         {}
    $ t# o3 @0 ]1 ?) @3 `

  99. 0 i; ^: N4 x* i2 |+ S
  100.   return (ch);
    - B% L4 c- H% r0 C8 J- O, r
  101. }
    $ g6 M& U# M4 r+ r- P5 Q

  102. 5 {3 e, ^* W; w+ v4 U' x  |9 @' m
  103. void USART1_IRQHandler(void)                        //串口1中断服务程序6 T$ c4 S& M7 R: n
  104. {6 X/ r5 F8 X: F3 L1 E1 C
  105.         uint8_t Res;6 s3 }' v' Z2 }1 n9 z

  106. : r! C* ]' M8 U9 V: p6 Q3 O
  107.         if(USART_GetITStatus(USART1, USART_IT_IDLE) != RESET)% K+ u/ R* D( O7 |1 s! @- i' Z6 o
  108.         {# S! ~  t6 l. V' ~
  109.                 USART_ClearITPendingBit(USART1, USART_IT_IDLE);//USART_IT_IDLE需要手动清除
    ; ~- ?# ]0 X$ O; q1 b: [
  110.                 if (USART_RX_count)0 [9 h: g, t! h# b
  111.                 {" `1 L4 v7 C& t
  112.                         if (myUart_callBack)
    6 ?6 x) X/ \( h
  113.                         {) C( `* f! I1 u  j3 M8 T! j
  114.                                 myUart_callBack(USART_RX_BUF, USART_RX_count);4 `0 g+ h% w# _- ^) T
  115.                         }& f8 Z! M7 A) y& L1 d
  116.                 }
    4 u: l7 E4 d2 C! F' _
  117.                 USART_RX_count = 0;7 v, E: ~' F- n! c9 N# K: [
  118.         }1 {( q5 i4 ?6 n+ Q3 w
  119.         if(USART_GetITStatus(USART1, USART_IT_RXNE) != RESET)  //接收中断1 I* h/ x) `! ?3 z" A
  120.         {
    7 _: C3 D( B2 X4 d* Z+ f* P
  121.                 USART_RX_BUF[USART_RX_count] = USART_ReceiveData(USART1);        //读取接收到的数据,自动清除USART_IT_RXNE中断标志; q2 Q6 e. V" O) Z# H- S% q" m
  122.                 USART_RX_count ++;+ \7 Z5 \) H# Q7 E+ X7 Y( x  f
  123.         }
    2 i" j, O5 N6 E6 O/ d+ D
  124. } ' a' L& u3 u1 |# h0 o9 _
  125. 1 h1 z7 n9 s' i# n1 f: }
复制代码

' T% ], N: w2 f9 m6 n- h
收藏 评论0 发布时间:2021-11-22 22:03

举报

0个回答

所属标签

相似分享

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