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

【经验分享】基于STM32使用HAL库硬件SPI驱动WK2124一拖四SPI转四路串口芯片

[复制链接]
STMCU小助手 发布时间:2022-4-9 22:59
STM32基础工程生成
* u8 B$ [1 m% g- x6 P首先使用STM32CUBEMX生成STM32的基础工程,配置时钟到72M主频:
, R. v+ c% i) b9 ]; W2 ~) H' Z9 m
* m! n: O, j* E: P$ b2 i, X 20210712163230798.png 2 k) l6 {3 d* N5 i7 A0 \) O& K

6 |; a( F8 ]( `1 C配置SPI前,首先查看WK2124的芯片手册,手册里面说明了WK2124的SPI最高支持到10M并且使用SPI模式0,SPI的模式0就是时钟空闲电平为低电平且在第一个时钟延采样:# X0 |7 |/ A# W' X# }

2 x4 T6 Q2 N+ ?' g9 w1 D 9W47%D}PLND[Y8HO8C05BXS.png # L2 M0 L6 v, {7 O; Z
* v( v# N- O4 Q* a6 ~
所以STM32CUBEMX需要这样配置:8 |2 t, d: N' J( r. b0 P( K

6 N/ t" H! B, d4 C  r W]TW7XP@HG4%Q1V_Q{{B.png & O' P3 c- ~+ s$ F& B

  p' \/ O* F* JIO配置:* n8 y* a* B& p0 l: z% U* b
WK2124的硬件复位引脚,这个引脚最好接上,使用STM32的IO进行控制
% n5 z) c  Q& G& R5 \# E6 ZWK2124的片选引脚
! j+ A$ `, K& {9 F, x8 \/ N4 q如果用WK2124的中断,那么还需要配置一个IO为外部中断
+ ?8 h/ B+ _0 }( w- r, X2 x, hWK2124驱动代码

* V( n: i% w0 h* l; [- X8 y' w$ |代码已经测试通过无问题,贴一下:
* J/ h7 ~) W) E; E7 R4 j3 w6 V, M+ v0 v- K. h* G7 _8 L
头文件0 F6 ]( E+ C9 N1 H2 I+ Y) l
  1. /*3 L4 f" W9 d* ~
  2. * wk2xxx.h
    # i$ P( D7 D" H( Y- W5 R( @
  3. *
    7 Y+ C  V& X+ V$ Q
  4. *  Created on: Jun 17, 2021
    6 C% |! {& _1 N: K/ t3 f1 g4 t/ y
  5. *      Author: hello
    . k- @7 J+ r, W& H- D0 v  A
  6. */! x8 n9 e8 `& b8 E7 e/ e9 K9 j

  7. / O5 }' R# P2 N
  8. #ifndef SRC_WK2XXX_H_& [2 I- w8 \& ~# `
  9. #define SRC_WK2XXX_H_
    , k6 y& K1 h: g* ^$ @* Q
  10. / `1 A" p5 M  F2 G2 \! {1 e* c
  11. #include "main.h"
    4 b5 M3 o3 W/ u$ c, y: h" Q' b3 M& K

  12. % z6 Q% a  ]/ }7 p
  13. & e! ?5 |- ~: A: b" ~
  14. #define         WK2XXX_GENA     0X00
    $ f: J% q& T; }& u! ]; i8 T3 J! z/ \
  15. #define         WK2XXX_GRST     0X01% s' w( d; a0 u. @5 f% Z
  16. #define                WK2XXX_GMUT     0X02! {/ ~7 [) f- D) f( t8 ?4 T. l, ?
  17. #define         WK2XXX_GIER     0X10
    , H+ |+ d  Q9 M
  18. #define         WK2XXX_GIFR     0X11* K4 K2 Y$ O8 L2 b; _
  19. #define         WK2XXX_GPDIR    0X21
    , j" P. T4 n& X* X. [
  20. #define         WK2XXX_GPDAT    0X313 G: r! Z( @" L9 z% N! k. m: |
  21. //wkxxxx  slave uarts  rigister address defines
    6 N+ J6 J  Z0 {6 C; S

  22. # P0 A  Z% H6 `# l+ V! O# l
  23. #define         WK2XXX_SPAGE    0X03
    * [; ^) f) z# F" p& X6 q4 Z4 c
  24. //PAGE0
    ! u5 f! v, V, w/ [8 I5 S) t
  25. #define         WK2XXX_SCR      0X04- A) D4 V$ D4 k- B
  26. #define         WK2XXX_LCR      0X05
    - Y/ \: ~/ F: L$ D. L8 u. c1 @
  27. #define         WK2XXX_FCR      0X06) b1 T/ r) z# w3 o
  28. #define         WK2XXX_SIER     0X07* ^7 W# B0 n/ h: i+ }2 c8 [
  29. #define         WK2XXX_SIFR     0X088 U  m: D8 b1 L% _
  30. #define         WK2XXX_TFCNT    0X09
    + g2 K* v/ S. e; U  `
  31. #define         WK2XXX_RFCNT    0X0A2 L& R2 s/ ^3 n5 _# W6 a
  32. #define         WK2XXX_FSR      0X0B! E1 K/ T" J. b( x
  33. #define         WK2XXX_LSR      0X0C
    . R/ w  X! F  ^# Y; X
  34. #define         WK2XXX_FDAT     0X0D
    3 ^* ^/ r9 d5 [0 p1 Q5 E
  35. #define         WK2XXX_FWCR     0X0E
    9 S3 P% l% ?: M3 U7 M7 Q
  36. #define         WK2XXX_RS485    0X0F/ D5 p  s6 z# p, i* q
  37. //PAGE1
    ) I) ]/ P5 d; p1 j5 x( J
  38. #define         WK2XXX_BAUD1    0X041 {: l: y) X  |1 l& ^: R/ ~
  39. #define         WK2XXX_BAUD0    0X05) Z1 k$ m5 C" E
  40. #define         WK2XXX_PRES     0X064 q) _& q* j, z9 d$ b" p* t
  41. #define         WK2XXX_RFTL     0X07
    8 q) H7 ?5 n' p
  42. #define         WK2XXX_TFTL     0X08  u" o8 L' M0 p0 i$ I$ h0 h2 i' C
  43. #define         WK2XXX_FWTH     0X09
    ! _/ t: J$ _4 Y4 p1 J
  44. #define         WK2XXX_FWTL     0X0A1 q% p5 @# M& i" u) z7 X, s
  45. #define         WK2XXX_XON1     0X0B  l4 v, q- F0 T5 H" K1 A4 ?
  46. #define         WK2XXX_XOFF1    0X0C
    9 c+ d& ?8 I2 F% L
  47. #define         WK2XXX_SADR     0X0D
    + g9 h7 B5 q- c1 v( x
  48. #define         WK2XXX_SAEN     0X0E
      l) n8 k. ]* S  u; K4 ?
  49. #define         WK2XXX_RTSDLY   0X0F( O  N+ u3 d4 r. t0 Y( L4 J
  50. # v  Y  z' E% m
  51. //WK串口扩展芯片的寄存器的位定义
    6 b* D$ a& M& [/ ]: ?7 d
  52. //wkxxx register bit defines' B8 D" A& B( h4 h
  53. // GENA0 z( F' _# z( d: H
  54. #define         WK2XXX_UT4EN        0x08
    , I  G, U/ `1 k+ r7 k, h9 z
  55. #define         WK2XXX_UT3EN        0x04
    , Q5 \) }2 a* S6 V3 r8 j( Z5 O
  56. #define         WK2XXX_UT2EN        0x02
    + Y' V( @: y: A5 ^9 G% Y
  57. #define         WK2XXX_UT1EN        0x01
    % o. k' r9 e* N# q: D" F4 |* D
  58. //GRST
    4 X7 S( L# F* \1 {% j: D
  59. #define         WK2XXX_UT4SLEEP        0x80. h) h: S8 [0 y0 [- n8 E
  60. #define         WK2XXX_UT3SLEEP        0x40
    7 A0 M: Q3 S8 _; r/ A2 `
  61. #define         WK2XXX_UT2SLEEP        0x20/ j1 T1 _% ^/ H7 c$ X
  62. #define         WK2XXX_UT1SLEEP        0x105 k3 |+ c5 e1 F6 w; C; f$ X
  63. #define         WK2XXX_UT4RST        0x08
    & j5 W, @' Z: J& _7 U3 X
  64. #define         WK2XXX_UT3RST        0x047 u- y( t; {, Y& u0 C. x+ J  x+ M$ E
  65. #define         WK2XXX_UT2RST        0x02' i2 k+ p! k. B' Y% o
  66. #define         WK2XXX_UT1RST        0x01
    $ s4 _4 T: A; M  N6 J
  67. //GIER3 _3 X5 j3 A& Q' y& h9 j# y# k, X/ k
  68. #define         WK2XXX_UT4IE        0x08
    ! W! s1 P7 ~4 E1 H; V; f
  69. #define         WK2XXX_UT3IE        0x04) P0 P8 a& ~1 w
  70. #define         WK2XXX_UT2IE        0x02
    ) r3 t" N& |2 T
  71. #define         WK2XXX_UT1IE        0x01! p8 K3 O) @3 A4 s! P2 F
  72. //GIFR
    0 K. p- Q8 K2 v( T! G5 h: |
  73. #define         WK2XXX_UT4INT        0x08
    % V2 E4 ~9 Z+ G5 a# e# M
  74. #define         WK2XXX_UT3INT        0x04/ c1 d, y' C& _4 f1 N8 f* t( Q6 _
  75. #define         WK2XXX_UT2INT        0x02
    ( z& n5 @1 O0 O; G" M
  76. #define         WK2XXX_UT1INT        0x01; o5 ]# k! u9 N1 g& P: d5 S2 q; T* P
  77. //SPAGE
    & _! H  `/ q  \
  78. #define         WK2XXX_SPAGE0          0x00
    2 V8 Z7 d8 u+ L- ?2 d
  79. #define         WK2XXX_SPAGE1   0x01
    & t  H, [1 W9 z# ]% \
  80. //SCR5 k) f3 q! \1 N8 j
  81. #define         WK2XXX_SLEEPEN        0x04
    2 ^5 f' t5 N6 O6 F2 E1 @7 e# z
  82. #define         WK2XXX_TXEN     0x02/ _8 R4 }) U' Q. d) T9 F
  83. #define         WK2XXX_RXEN     0x01
    7 f6 J5 s4 q: _8 h4 @
  84. //LCR
      B' Z/ n# c5 x' C$ {. x
  85. #define         WK2XXX_BREAK          0x207 J% g7 y' \, @+ _/ r1 Y$ ^7 N% t
  86. #define         WK2XXX_IREN     0x10+ X) W* `( c' J' d5 a, s; k
  87. #define         WK2XXX_PAEN     0x08, [3 J; i- E2 K2 n& v- I( L# ]+ ^
  88. #define         WK2XXX_PAM1     0x046 [& b- k. t3 I3 L; E" D
  89. #define         WK2XXX_PAM0     0x023 n8 \, ^" @: X  O$ w2 K
  90. #define         WK2XXX_STPL     0x01
    0 P9 b- J9 R6 L
  91. //FCR& q/ W* h) i' ?% R$ m9 a1 ]
  92. //SIER9 T# u% R! B& I) W
  93. #define         WK2XXX_FERR_IEN      0x80
    + c6 r. C& w0 h4 B! H
  94. #define         WK2XXX_CTS_IEN       0x40
    # L) z+ @6 o% P4 q/ C! J+ o) Z9 p
  95. #define         WK2XXX_RTS_IEN       0x202 ~; t; @. ]* v( p, e9 C8 _
  96. #define         WK2XXX_XOFF_IEN      0x108 t' D0 y% r! p! z
  97. #define         WK2XXX_TFEMPTY_IEN   0x08& E$ P8 v; M$ ~4 c1 B- U; n1 ~
  98. #define         WK2XXX_TFTRIG_IEN    0x04$ f1 @: D  M* e
  99. #define         WK2XXX_RXOUT_IEN     0x02. m- M7 K: k1 ]$ U1 H7 ^2 d; I% V
  100. #define         WK2XXX_RFTRIG_IEN    0x01
    / N" N( y. p4 q( i1 b; m4 b
  101. //SIFR& y  o$ A# a1 p) t9 w
  102. #define         WK2XXX_FERR_INT      0x80
    3 W& `  V! Y* t9 ?
  103. #define         WK2XXX_CTS_INT       0x40# H! x& @) O3 n7 Q
  104. #define         WK2XXX_RTS_INT       0x20
    ( r! B; Z  w$ M+ h! h- {3 l- v
  105. #define         WK2XXX_XOFF_INT      0x107 N. n: p; J) u! u# [$ Y
  106. #define         WK2XXX_TFEMPTY_INT   0x080 [6 T0 I7 V$ q: X
  107. #define         WK2XXX_TFTRIG_INT    0x04" r# |; C" ^3 d" m$ z4 ?
  108. #define         WK2XXX_RXOVT_INT     0x02/ _7 X- }; C' m5 F4 W% ^. _' @
  109. #define         WK2XXX_RFTRIG_INT    0x013 R: Q! ~* g; \* {. ?* w) Z
  110. $ s2 Y9 N6 t- w9 C
  111. , E- `% I& `; b, C
  112. //TFCNT
    7 u2 g% T1 w7 q
  113. //RFCNT
    $ D9 w6 Y. j  W' n
  114. //FSR
    1 }% r) z+ C; q2 G
  115. #define         WK2XXX_RFOE     0x80
    ; f$ l0 @# g6 a  X
  116. #define         WK2XXX_RFBI     0x40
    ' q, Q4 z/ a( C$ d  G
  117. #define         WK2XXX_RFFE     0x20& w' v, \5 A3 p% e6 ~
  118. #define         WK2XXX_RFPE     0x10% x/ K" w+ ]/ ?: |" A. F
  119. #define         WK2XXX_RDAT     0x08
    / K/ c& ]! ^' d0 M. b  y
  120. #define         WK2XXX_TDAT     0x046 U0 r4 q0 Q0 w+ j) Q
  121. #define         WK2XXX_TFULL    0x02
    - B, P2 S1 Z1 w. Q
  122. #define         WK2XXX_TBUSY    0x01
    / d1 h, M; e: l& Y- [
  123. //LSR
    * l% }" _6 ~, j% }# c
  124. #define         WK2XXX_OE       0x08
    ; t$ f/ a$ x' M% e
  125. #define         WK2XXX_BI       0x04
    . D$ P- C. P0 K% j7 x% f
  126. #define         WK2XXX_FE       0x02
    ) U* C3 k' b2 Q2 [
  127. #define         WK2XXX_PE       0x01
    . a: u& o) G' Y& @' d
  128. //FWCR3 \2 Q/ L" K% H3 ]

  129. 4 [: T- s" I, V9 z+ C6 X! |
  130. uint16_t WK_PortSendData(uint8_t port, const void* buf, uint16_t len);
    . m7 X, O. s( @+ h: W# M3 ?
  131. uint16_t WK_PortRecvData(uint8_t port, void* buf, uint16_t len);
    3 S2 \9 l- b# X6 y
  132. void WK_PortInit(uint8_t port, uint32_t fosc, uint32_t baudrate);
    1 Q9 x! v2 B+ [, o
  133. void WK_IRQHandler(void);7 }. X5 T. D& g; ^3 B. i  z
  134. void WK_Rst(void);& C# F8 L- p5 F" N, p) R

  135. 8 k/ _9 o0 {$ r* x- F5 M
  136. #endif /* SRC_WK2XXX_H_ */
复制代码

8 a+ N0 ~- r, Q5 V7 B" Y源文件
% T7 m  `+ [% h/ B( u$ j# B  [8 q
  1. /*9 H8 ?! G6 p$ N0 I9 T
  2. * wk2xxx.c% F% l/ \$ ?' N* Y1 [
  3. *
    & P/ @$ P, h4 G0 T. {
  4. *  Created on: Jun 17, 2021
    0 m4 p4 E# ]6 b  K* u
  5. *      Author: hello3 l. p' @7 s6 b$ P% Z
  6. */
    + d$ `2 o) ^+ k0 x; g- S! R

  7. ; M; _( \  G' P9 J5 Z: o/ L
  8. #include "wk2xxx.h"
      o; {! h5 }# n8 a# x
  9. #include "spi.h"3 x3 @- A1 @) B6 ^# {% ^
  10. 1 S/ m+ b, }& M  u6 i9 t

  11. % C, p4 I- p; }' v/ f# p! [# A
  12. //
    % i' Q8 [; A4 }- W4 b
  13. ///
    * H. V" v2 j( S- q  [
  14. ///                            移植修改区域2 \7 R/ d. [) e( ?' \% Y: y! H
  15. ///4 e7 I4 g. M3 }+ l8 h6 t* H
  16. /// h5 P5 P7 \% m

  17. " B" t; `" }4 h: V
  18. /// HAL库SPI句柄6 |+ W' i0 z/ x
  19. #define WK_SPI_Handle (&hspi2)
    $ C1 z- m) m  q; m

  20. * _4 [- [% ]+ ~) }# K0 u# \
  21. // 拉低RST引脚
    * x2 u) d8 n, z
  22. #define WK_GPIO_RST_L()    HAL_GPIO_WritePin(WK2124_RST1_GPIO_Port, WK2124_RST1_Pin, GPIO_PIN_RESET)
      t: T! B7 U6 n  `
  23. + A+ y3 M. r* Z. k/ c* c1 Y4 W/ M
  24. // 拉高RST引脚& U5 N9 b% x& {+ V# X. E
  25. #define WK_GPIO_RST_H()    HAL_GPIO_WritePin(WK2124_RST1_GPIO_Port, WK2124_RST1_Pin, GPIO_PIN_SET)6 h, E" s. B' I, i% J# @

  26. 2 b; d! H' l1 o" u9 B
  27. // 片选引脚拉低
    , r* W" k6 x2 T. L, I
  28. #define WK_GPIO_SEL_L()    HAL_GPIO_WritePin(WK2124_CS1_GPIO_Port, WK2124_CS1_Pin, GPIO_PIN_RESET)
    7 J2 A7 w9 r, f5 ~  I; V
  29. 5 `! Y% z& A3 z' u5 S
  30. // 片选引脚拉高/ N8 A1 _7 C- O7 B
  31. #define WK_GPIO_SEL_H()    HAL_GPIO_WritePin(WK2124_CS1_GPIO_Port, WK2124_CS1_Pin, GPIO_PIN_SET)5 x3 u2 z2 W4 [/ d
  32. ( Z& x0 [3 s, r% D* Z# i% @

  33. ) m( a& v2 h2 q9 X" j
  34. static void wk_delay_ms(uint32_t nms)" U# w3 z4 F5 }, M
  35. {! ~! J& [- I* w2 g
  36.         HAL_Delay(nms);4 ?& b" ]) S& b8 E4 h% ^. V
  37. }! \( x' y/ |/ F+ C

  38. 5 S- P0 V0 n7 d6 R" x; X$ W) O& C
  39. static uint8_t WK_SPI_ReadWriteByte(uint8_t TxData)- Z" H2 F, s: x4 w
  40. {
    9 w, }( A! [! k4 g, i
  41.         uint8_t RxData = 0X00;% G7 [5 Z5 o  \, X: R; q
  42.         if (HAL_SPI_TransmitReceive(WK_SPI_Handle, &TxData, &RxData, 1, 10) != HAL_OK)( e5 l, \, }" f: V
  43.         {
    2 L. \) B/ X3 {8 {
  44.                 RxData = 0XFF;* y7 Y( x1 T7 C+ F
  45.         }
    ' u) D. ~& S( n6 H
  46.         return RxData;
    ! V9 U6 }- y9 A. `7 ~
  47. }
    % R2 g  F" d+ S; S6 A$ x2 x4 |* a
  48. ' U! d; J$ [2 @1 y8 C

  49. / \8 l: D( R* d+ J7 L, B

  50. % U! P2 @, B$ f, w

  51. ( b/ E8 |1 G# b: N7 x
  52. //
    - {8 V+ g; J% Z7 O, y( S7 U
  53. //// R9 {& }1 r" N# n  G' g
  54. ///                            驱动程序代码/ L* a' F) L9 r* z
  55. ///; {7 N3 ^" _: m4 y
  56. //2 ]) U: _; V9 ]/ u0 B& }# B& X

  57. 7 L) o* P* ?0 Z4 ^0 N1 {5 i

  58. % ^2 W+ }* t) T0 M. r
  59. 7 D3 d7 G" K0 f' V
  60. /// 硬件复位(拉低复位引脚最低10毫秒进行复位)7 r8 W" H& Q; c; @1 O
  61. void WK_Rst(void)! c+ w& T& i& f# Y9 k4 m: g
  62. {3 T; O0 @# q6 y: b
  63.         WK_GPIO_RST_L();
    1 W- k2 }" b1 G0 g
  64.         wk_delay_ms(50);7 \5 d( E/ i& l: C* ^  M
  65.         WK_GPIO_RST_H();1 v9 z* I5 D& o% n( D
  66.         wk_delay_ms(50);, g4 W! c$ E# T8 N8 @# H. w
  67. }: h( g" D; v" R9 m8 D  D& v

  68. ! A/ C3 @7 U5 g  l) c! p
  69. void WK_WriteGReg(uint8_t reg, uint8_t value)
    & P- K( \2 {( C: r8 P* e
  70. {, z) n  l; N  w
  71.         WK_GPIO_SEL_L();6 M) n' D7 [* a  L7 z8 H" ~9 V
  72.         WK_SPI_ReadWriteByte(reg);
    : o+ B9 B! @. o, q
  73.         WK_SPI_ReadWriteByte(value);0 u3 F+ ]# Y; }
  74.         WK_GPIO_SEL_H();
    $ w; k  E9 b6 W
  75. }
    8 S  O; G) d8 T8 B0 b
  76. & q" h0 k5 |" a2 q' a5 u: `, z
  77. uint8_t WK_ReadGReg(uint8_t reg)
    ' r+ ^( F4 g' v( p6 i
  78. {
    - s1 p) I9 O$ v  R0 z8 r5 w
  79.         uint8_t value = 0X00;
    ( x! o: H  |8 a+ `, ]
  80.         WK_GPIO_SEL_L();4 Z6 J# R- h  S# C( q% `. z
  81.         WK_SPI_ReadWriteByte(0X40 | reg);
    ( I, M, O' l' j6 o% \
  82.         value = WK_SPI_ReadWriteByte(0X00);
    ! e+ U4 K" `4 d1 p5 i
  83.         WK_GPIO_SEL_H();" x  ]2 I9 |. i6 p7 ]
  84.         return value;' ^  C9 E; P7 e
  85. }
    # [; j, j- r; V, E7 F: U

  86. 5 `6 z9 i5 K; I' `+ J4 T: v; b
  87. void WK_WriteSReg(uint8_t port, uint8_t reg, uint8_t value)
    : _' g5 R$ x6 W( B/ _. W
  88. {
    ; z9 r; Y/ X0 E
  89.         WK_GPIO_SEL_L();
    ( f- x2 S! f  J4 B  }- R
  90.         WK_SPI_ReadWriteByte(((port - 1) << 4) | reg);
    & v; D5 ~: I  @+ j! m8 v
  91.         WK_SPI_ReadWriteByte(value);
    5 ?' U  e6 l: Y) t9 ]% ]7 @
  92.         WK_GPIO_SEL_H();
    ) C5 x5 }0 g+ H* w" W& ^  C
  93. }
    * J  ]8 l, v. l- v( E
  94.   a+ X! v% z: d% b  h
  95. uint8_t WK_ReadSReg(uint8_t port, uint8_t reg)
    3 z& o1 Z/ P2 h3 g) g
  96. {; _3 v. `9 j: a8 S/ L  D5 x: E4 h
  97.         uint8_t value = 0X00;
    8 V* O# \* Y* d' C7 E8 W
  98.         WK_GPIO_SEL_L();
    6 z$ m* W3 n! h6 @& v
  99.         WK_SPI_ReadWriteByte(0X40 | ((port - 1) << 4) | reg);% B6 {  X4 M, a) I: e
  100.         value = WK_SPI_ReadWriteByte(0X00);+ A/ P. m, O! {- n
  101.         WK_GPIO_SEL_H();
    ( ^9 u4 }0 r* }- U
  102.         return value;7 y9 J$ j* {8 c6 M" _/ n3 u
  103. }
    " O! f% i7 O; w( l
  104. # y3 ]& V0 ?+ S- K2 ?' L
  105. void WK_WriteFIFO(uint8_t port, const void* buf, uint16_t len)
    ' K( l# F/ [  T, m( t
  106. {
    . g3 e2 f; p4 e: h. @+ [- ]9 R" g% ]
  107.         const uint8_t* p = (const uint8_t *)buf;8 g& A! v, L" e
  108.         WK_GPIO_SEL_L();
    ! E6 B! C3 T5 |. J8 S5 U
  109.         WK_SPI_ReadWriteByte(0X80 | ((port - 1) << 4));
    % b% r1 j* |, w
  110.         while (len--)- x! W( l5 j: m$ M" N
  111.         {
    * J; }8 p& Z$ W& d6 |! `! Q4 u, E
  112.                 WK_SPI_ReadWriteByte(*p++);. b( S9 r/ E# e7 j* q5 [3 E
  113.         }
    , F. K5 V9 Y0 y; K3 M
  114.         WK_GPIO_SEL_H();
    # L: K  u. g" J/ M* U) E7 J
  115. }" [6 W- t8 }4 v2 s1 q# b

  116. 3 u' s' k9 Y8 R! V! d! E
  117. void WK_ReadFIFO(uint8_t port, void* buf, uint16_t len)0 i2 L  u! U4 G) i* G  b- ~5 g
  118. {
    5 s: v0 T+ n+ m" b: `6 g1 v
  119.         uint8_t* p = (uint8_t *)buf;( q  M8 o# @" |" G* @9 R9 z
  120.         WK_GPIO_SEL_L();
    1 v, \0 f5 N% I
  121.         WK_SPI_ReadWriteByte(0XC0 | ((port - 1) << 4));$ X& F) x0 D3 O4 T0 p* T0 r3 H
  122.         while (len--)
    6 G  w. N0 b; i
  123.         {
    1 A5 Q$ z/ b8 y9 M/ d6 n
  124.                 *p++ = WK_SPI_ReadWriteByte(0X00);6 o6 ?) B# j! a( u" r! @
  125.         }
    - G$ _+ A" Y' e1 ~: m1 y
  126.         WK_GPIO_SEL_H();6 J) t9 n& c+ }$ l: w" o
  127. }  }9 |+ U; ^9 z/ ~! j

  128. 6 V5 v) ?& y; C, _( R
  129. void WK_PortCalcBaudrate(uint32_t fosc, uint32_t baudrate, uint8_t* BAUD0, uint8_t* BAUD1, uint8_t* PRES)' v$ G% X* f7 x1 x% \7 a
  130. {
    2 l" V3 j, c! I" t3 ?
  131.         float value = (float)fosc / (float)(baudrate << 4);
    ) K+ w5 @# E3 l3 M# G3 c( f
  132.         *BAUD0 = (((uint32_t)value) - 1) & 0XFF;: W9 Y3 w9 w/ O4 o5 ]
  133.         *BAUD1 = ((((uint32_t)value) - 1) >> 8) & 0XFF;
    % @" Q* ~- [) T& e  \0 Y
  134.         *PRES  = ((uint32_t)(value * 10)) % 10;( A% V1 P) ^2 q% ]2 h
  135. }4 I: |6 h! ~6 C. Q5 l5 N! n
  136. $ J/ h! ]% L! A$ A8 w$ A
  137. uint16_t WK_PortSendData(uint8_t port, const void* buf, uint16_t len)  {9 V' m/ O4 C# M* a
  138. {
    % P6 L# A$ I  p  Q9 j- s
  139.         uint8_t  state = 0;
    , w( g7 ?% {: ^4 |) t: Z
  140.         uint16_t nsend = 0;! y8 N* S6 a! M7 d
  141.         state = WK_ReadSReg(port, WK2XXX_FSR);
    % T! d' e8 @. u% d" L
  142.         if (state & WK2XXX_TFULL)                    // 发送FIFO满0 @# n1 Y1 O) F! `9 l5 D: p# f7 ^
  143.         {" G. N* ?+ O( k
  144.                 nsend = 0;
    , m! l7 t9 |9 t
  145.         } else
    % H$ J# ^& |6 n% g
  146.         {5 E8 n# S+ ]) m' |
  147.                 state = WK_ReadSReg(port, WK2XXX_TFCNT); // 读取发送FIFO已用空间
    ) K5 u! s$ L2 O0 E4 y
  148.                 nsend = 256 - state;3 s5 Y+ F" K2 M' W; D
  149.                 nsend = nsend >= len ? len : nsend;+ f$ H3 e9 k. S( |  J
  150.                 WK_WriteFIFO(port, buf, nsend);          // 将待发送的数据写入FIFO( |; [# w! B9 H7 [* ~
  151.         }5 q+ H1 f5 u+ z- k6 d
  152.         return nsend;                                // 返回实际发送成功的数据量( _% s0 L8 O9 K6 y$ t
  153. }
    ! a: @( K; W' x1 {0 O, J3 Q

  154. " g4 x; b; J7 S4 v
  155. uint16_t WK_PortRecvData(uint8_t port, void* buf, uint16_t len)+ L7 f8 V3 B- q' _/ w( A0 A
  156. {
    4 _# V/ d4 Y& a  N: n4 K
  157.         uint8_t state = 0;
    3 U! j4 l. R. k5 m. S, ~/ E' W- e
  158.         uint8_t nread = 0;( b$ V1 X3 @+ c: t, s: `" b, k  n
  159.         state = WK_ReadSReg(port, WK2XXX_FSR);
    / I0 g- n" Y7 h, w5 k$ H
  160.         if (state & WK2XXX_RDAT)                      // 接收FIFO非空
    ( ]; k" y$ p/ h" n& k  }, e
  161.         {
    $ k8 J6 F; `) R0 @, i7 q
  162.                 nread = WK_ReadSReg(port, WK2XXX_RFCNT);  // 查询FIFO中的数据量
    7 O$ h" h. c$ F4 c
  163.                 nread = len >= nread ? nread : len;
    1 c; t: t- O. a6 S1 }
  164.                 WK_ReadFIFO(port, buf, nread);            // 读取FIFO中的数据" O0 g- F; a1 L7 h8 f) \
  165.         }
    2 b  f+ N4 _9 n, L
  166.         return nread;                                 // 返回实际读取到的数据量
    ; E; v9 H8 d* g8 @2 }
  167. }. b0 Z$ C& v/ t8 A2 k* \

  168. " T, O$ t1 r& m; q1 i
  169. void WK_PortInit(uint8_t port, uint32_t fosc, uint32_t baudrate)+ r( u: c5 U+ K+ H
  170. {
    ( D% x2 Z% P: |5 B' W
  171.         uint8_t BAUD0 = 0, BAUD1 = 0, PRES = 0, value = 0, ret = 0;
    5 N% E$ z& `  r6 n  }
  172. / s6 Z: b; X$ |( p+ U. ]
  173.         //* I1 Y0 S, ^/ [: h4 |  P, o
  174.         // 使能子串口时钟( y4 v* g' k7 M8 l9 s! N7 J
  175.         //( [6 v% }8 T  |8 W8 l  E
  176.         value = WK_ReadGReg(WK2XXX_GENA);  D9 t* d1 t' w( }& S
  177.         value |= (1 << (port - 1));" ~! Y& B0 ^) K6 n$ j6 z7 J, C* l1 V, J
  178.         WK_WriteGReg(WK2XXX_GENA, value);1 o: K1 ^  W9 h+ m7 O, r9 U6 o1 u8 H% T
  179.         ret = WK_ReadGReg(WK2XXX_GENA);
    ( Q$ T% K: n# m7 L

  180. . {" @$ r6 {) t
  181.         /// f2 ]! ]" J: u  B
  182.         // 软件复位子串口9 L- U2 L/ U$ B# I/ \1 I
  183.         //. {3 t4 k: _6 w3 U
  184.         value = WK_ReadGReg(WK2XXX_GRST);6 O- K* a6 S( @) k: r$ _
  185.         value |= (1 << (port - 1));
    8 _$ s$ W4 E0 z0 |- p
  186.         WK_WriteGReg(WK2XXX_GRST, value);  ~$ I6 q- w# }4 b) v: U( L
  187.         ret = WK_ReadGReg(WK2XXX_GRST);$ v7 z; t' l; Q8 j0 p) H: P4 Y

  188. ( X8 V1 E- g7 Y1 v
  189.         //; P; t0 z+ c1 X7 F" m5 r; w
  190.         // 使能子串口总中断
    . u' E- ]# q4 S6 I8 R3 F/ ~
  191.         //! a$ g. x# H2 S( ]& a
  192.         value = WK_ReadGReg(WK2XXX_GIER);
    * A4 |" N7 d  ?& N2 I
  193.         value |= (1 << (port - 1));
    & s/ V/ i0 W* {( A1 W6 k$ m$ h- p
  194.         WK_WriteGReg(WK2XXX_GIER, value);
    : j4 A% C/ e+ l& I9 [
  195.         ret = WK_ReadGReg(WK2XXX_GIER);1 v& R0 [) R7 v) n2 M  T" p  r% H
  196. # G- E3 i3 _! g1 a! U! M5 B: X+ k
  197.         //  j3 B* K; w% R2 M
  198.         // 使能子串口FIFO相关中断
    ( W* U; h( r4 k1 k. w. V, @
  199.         //
    2 ?" _6 R0 ^5 X3 `  z. c
  200.         value = WK_ReadSReg(port, WK2XXX_SIER);
    . x; l$ @) x) R/ M6 R7 P" e3 k
  201.         value |= WK2XXX_RFTRIG_IEN;                  // 接收FIFO触点中断
    & ^3 F2 D7 i! J/ [$ Y# v  A# L
  202. //        value |= WK2XXX_TFTRIG_IEN;                  // 发送FIFO触点中断. |, ?' o# l2 \0 ^2 Z
  203. //        value |= WK2XXX_RXOUT_IEN;                   // 接收FIFO超时中断* q0 [. E0 E7 z6 m7 w
  204.         WK_WriteSReg(port, WK2XXX_SIER, value);. }9 b5 Z( D; L8 C# w/ e
  205.         ret = WK_ReadSReg(port, WK2XXX_SIER);) k, y; D3 G) t4 ~  T3 C5 E
  206. 7 ^7 R5 T3 l4 d! x+ D$ t
  207.         //2 D! R9 i* ~6 @  y' a8 B
  208.         // 设置FCR寄存器
    8 y* s- ?/ @& c( f" d3 s2 S3 P
  209.         //
    7 `  s5 t4 g' |# b4 u, t5 r0 `* w
  210.         value = 0;) B1 ^5 V% J  x+ [9 x1 u1 _
  211.         value |= (1 << 0);  // 复位接收FIFO
    , N0 m" z! g# p" n4 ?( e
  212.         value |= (1 << 1);  // 复位发送FIFO( J2 g# G+ l! f0 d1 N
  213.         value |= (1 << 2);  // 使能接收FIFO(这一步必须)
    # E7 B! i1 P0 g) g8 F8 ^5 \
  214.         value |= (1 << 3);  // 使能发送FIFO(这一步必须)
      p$ c% F- S( s* N! D5 B& f
  215.         value |= (0 << 4);  // 设置接收FIFO触点固定为8字节7 |2 @. \8 H+ N! t4 }
  216.         value |= (0 << 6);  // 设置发送FIFO触点固定为8字节
    6 k: q9 f, d! O
  217.         WK_WriteSReg(port, WK2XXX_FCR, value);" B7 _$ T. W' f1 e
  218.         ret = WK_ReadSReg(port, WK2XXX_FCR);
    0 [9 X1 v8 l) I# q4 ]+ h

  219. # E8 Q0 ]4 f' L7 {: e  P
  220.         //
    3 [' Q- A  \$ R9 O/ W* `2 Y
  221.         // 切换到page1设置中断触点和波特率
    , j' Q6 {& ~; j0 \
  222.         //
    6 F# k: S. Z; J  x
  223.         WK_WriteSReg(port, WK2XXX_SPAGE, 1);6 {* [/ q. h: |1 g  T
  224.         ret = WK_ReadSReg(port, WK2XXX_SPAGE);
    : E6 E  y3 D( |7 b6 \5 l! b

  225. 2 K0 d5 S+ t6 r/ C4 {
  226.         WK_WriteSReg(port, WK2XXX_RFTL, 10);      // 设置接收触点为10个字节
    + F3 L/ r4 [3 W
  227.         ret = WK_ReadSReg(port, WK2XXX_RFTL);6 m- Q" `- I0 z6 H( e
  228. 1 `+ l* o0 d( k( E: N8 c
  229.         WK_WriteSReg(port, WK2XXX_TFTL, 10);      // 设置发送触点为10个字节+ M% J: d1 w/ L! w9 ?
  230.         ret = WK_ReadSReg(port, WK2XXX_TFTL);
    4 n! A4 E+ Q9 V: m) m% Y
  231. / L1 t+ \+ F( u9 l% m- n. X1 \) ~
  232.         WK_PortCalcBaudrate(fosc, baudrate, &BAUD0, &BAUD1, &PRES);  // 计算波特率
    - x% e9 ^! B( _) M; ~. N

  233. % `! m* o/ t, k; X: p% S, @" F2 r
  234.         WK_WriteSReg(port, WK2XXX_BAUD1, BAUD1);  // 设置BAUD1
    1 ]8 C/ Y0 X* N4 B$ W+ p/ c
  235.         ret = WK_ReadSReg(port, WK2XXX_BAUD1);% u$ r/ X: H2 H* |  S; X

  236. " {6 F# e  v/ \9 K3 N
  237.         WK_WriteSReg(port, WK2XXX_BAUD0, BAUD0);  // 设置BAUD0
    5 J% b5 h3 I" D6 T3 H: k- t. d3 O
  238.         ret = WK_ReadSReg(port, WK2XXX_BAUD0);
    / p% n9 g2 \0 y- w( w

  239. 1 e2 j: l+ C) P/ l& V' c* @" @+ M8 v
  240.         WK_WriteSReg(port, WK2XXX_PRES, PRES);    // 设置PRES: |1 Q0 W7 R5 l& C* S- S( l+ D; T
  241.         ret = WK_ReadSReg(port, WK2XXX_PRES);
    . V, f! B4 g3 U. b1 J9 ^) c

  242.   r6 e2 {/ H' Y! ], I+ p9 v
  243.         //
    ' o. D% v* U$ G7 s: k' @
  244.         // 切换回page0
    8 q- T3 }; c  D! k6 r$ n
  245.         //0 D3 j: E8 g5 y5 N- X+ ~
  246.         WK_WriteSReg(port, WK2XXX_SPAGE, 0);) v7 P9 M+ Q) ~( Y8 f' ]1 H
  247.         ret = WK_ReadSReg(port, WK2XXX_SPAGE);. S* l% J+ d6 }# Z- b3 X7 c" s0 j
  248. 8 @) a$ m1 b9 Z7 b, @3 b8 C
  249.         //% r/ E6 f* Z0 k
  250.         // 使能子串口收发7 i8 |2 |" N8 r& m* s
  251.         //
    8 d3 E! O6 Q6 N9 K- F. J
  252.         value = WK_ReadSReg(port, WK2XXX_SCR);
    # {. e5 N6 n$ [3 I' l
  253.         value |= WK2XXX_TXEN;
    ! O; Z, i: ]+ \5 G
  254.         value |= WK2XXX_RXEN;
    * d4 G% n6 g. f5 Y; o( g
  255.         WK_WriteSReg(port, WK2XXX_SCR, value);  p# g# G- G! B  ]9 |% g  |6 W
  256.         ret = WK_ReadSReg(port, WK2XXX_SCR);
    ! @- v4 i/ r8 ~* w
  257. }3 J0 u$ G" `* x, U; T8 j
  258. . @% h9 j6 `2 n3 S6 |0 [7 d

  259. 6 u; W1 }0 G+ i9 r+ B
  260. // 如果irq引脚接入了单片机的外部中断引脚,将该函数放入外部中断处理函数内。+ R' o$ k" N6 g
  261. // 对于WK2124所开启的中断可以这么处理:1 r3 w! E1 `* D( c" `" ?0 w
  262. void WK_IRQHandler(void)
    9 [: `# ^8 E4 L
  263. {
    ( _( g. f# u$ o8 }! ~, `* b
  264.         int i = 0;
    / t+ u  k" i' I
  265.         uint8_t GIFR = 0, SIFR = 0;" w! M. S0 C5 X: y  Q' l0 d
  266. ) D$ E" W; X$ `# F
  267.         // 读取子串口全局中断寄存器) u6 J8 _9 u! r% [6 C% l# y4 y0 u
  268.         GIFR = WK_ReadGReg(WK2XXX_GIFR);' w, u! m$ k( S! _

  269. 6 ?! ^; b: J: |
  270.         // 查询4个子串口是否发生中断
      \( O6 B# G' T& q, \
  271.         for (i = 0; i < 4; i++)! i) q7 A/ X5 p! X
  272.         {
    * @* i# y$ m  o# }  o) \) ~! i
  273.                 if ((GIFR >> i) & 0X01)6 b$ u! \. i. N7 z# E
  274.                 {
    3 C- n7 K5 v/ x6 r- m1 C7 C
  275.                         SIFR = WK_ReadSReg((i + 1), WK2XXX_SIFR);! n# H: `2 {% N$ C. Z' E, c3 _) Y  T

  276. % o  Y- Q$ V9 g8 a
  277.                         // 有接收FIFO触点中断1 ]6 l8 ~* R' S" l
  278.                         if (SIFR & WK2XXX_RFTRIG_INT)
    ) p; ~5 [2 x) D8 v( g9 Z
  279.                         {5 ]6 S' Z2 F) p9 D9 c, _
  280.                                 // 调用WK_PortRecvData接收数据
    8 `5 {& L4 x  k6 t) r
  281.                         }2 m0 F9 E! Z( W8 s0 S' I
  282. + g0 D3 M9 V0 {* j. [8 \
  283.                         // 有接收FIFO超时中断# |& {. T+ X0 A6 h
  284.                         if (SIFR & WK2XXX_RXOVT_INT)( K9 x/ O7 u7 B+ X# A3 c
  285.                         {
    ; e& E1 v  }, K, T8 Y
  286. ' A5 C- e& Z. s( n& L3 m
  287.                         }% O$ G* n3 d! m4 N6 N, B

  288. ) M! s4 b7 b. P. o: Q, B& ^$ m: R
  289.                         // 有发送FIFO触点中断$ y$ V8 e0 @4 P2 M1 H# {
  290.                         if (SIFR & WK2XXX_TFTRIG_INT)7 a' T% Q4 x& q* z
  291.                         {- N. G7 f2 j" s- g

  292.   _9 u& v$ f; B% {
  293.                         }
    1 e6 R/ r1 z4 S

  294. * ?) S, N, K7 e: o0 n
  295.                         // 有发送FIFO空中断5 H6 {5 R+ J$ C0 m
  296.                         if (SIFR & WK2XXX_TFEMPTY_INT); W. L; ~' i) g$ a; W
  297.                         {
    ( y  }0 g* ~  r6 p: M

  298. " m  `- J. ^9 e' |  i6 O
  299.                         }
    ! m+ N; C: j9 L# n! x) \
  300. . H5 O3 z  |: }9 [& J. b$ J+ O
  301.                         // 有接收FIFO数据错误中断
    1 l) U' O  @# Q- o& S- ?3 p$ n; G
  302.                         if (SIFR & WK2XXX_FERR_INT)
    5 Q2 Z, I9 N( P
  303.                         {2 e9 ?9 P6 g% m: {/ H3 O

  304. 4 T2 F, u" i. O' J1 y0 A4 f
  305.                         }* N6 T! `* v: y6 M# M  i) w5 a8 q( `
  306.                 }
    4 v" `- l. A9 ?& L3 k, s3 b! P: }
  307.         }
    3 }7 y. I+ x+ _0 z; p$ @# i* L; C3 c
  308. }
    4 e3 E6 Q* F1 \
  309. 6 |/ G8 s1 o, U% y" q/ b
  310. /*
    & B" E. R( ~  N2 I2 P
  311. 1 d# u% Y/ s* ^+ ~: d
  312. int main()9 K, g+ V2 l! W' R4 e2 H! v
  313. {
    ( F$ P' V8 t+ N. H2 ?/ y' b2 d
  314.         int nrecv = 0;
    . J+ j8 {! J, \. R+ C
  315.         uint8_t buffer[256];
    7 s- S, M4 l; S/ L1 ^3 K! m) ^, B
  316.         
    0 x" W% r: H; }7 B6 p" p$ G" ~" j
  317.         // 硬件复位一下
    # \: ?  x0 U8 W# w! J; t" g
  318.         WK_Rst();0 @3 u& z$ f/ q' u7 t$ s- m# g4 d
  319.         
    . f9 j, i5 ^  t, W. n
  320.         // 初始化四个端口
    3 a! N8 [7 V5 Z7 f4 n& `( X
  321.         WK_PortInit(1, 11059200, 9600);  // WK2124晶振我用的是11.0592MHz的,这个值根据实际进行修改% o5 E5 ?/ H: ]) \; f% I: ~
  322.         WK_PortInit(2, 11059200, 9600);- K6 T. U  k. O, q  {. _5 H4 K' ^
  323.         WK_PortInit(3, 11059200, 9600);
    * P2 N0 }6 t  O+ H) q
  324.         WK_PortInit(4, 11059200, 9600);' Q; S- D6 I! n, R: I
  325.         
    6 Q0 o  P* |$ l2 W2 A  B
  326.         // 发送数据
    / y. \6 w7 p; o3 W: d9 V
  327.         WK_PortSendData(1, "helloworld\r\n", 12);, D) [' }7 I, w( j( O
  328.         WK_PortSendData(2, "helloworld\r\n", 12);
    ! {$ c" a' z% W5 w# O
  329.         WK_PortSendData(3, "helloworld\r\n", 12);
    , x# d/ m% S( I8 b8 h4 j! f1 Q; i: O6 T
  330.         WK_PortSendData(4, "helloworld\r\n", 12);$ _$ p$ a& l7 _( S3 ?
  331.         3 L% B% v0 `$ h0 L6 G- g
  332.         // 接收数据,轮训方式; p+ X# V: J$ |5 \* G
  333.         nrecv = WK_PortRecvData(1, buffer, sizeof(buffer));. s/ G% P7 Z  E1 u
  334.         & l0 N8 W  T1 ?
  335.         if(nrecv != 0)) B' h1 M6 v2 N2 M$ A! w9 f
  336.         {# k. a3 s8 a+ i. a% o
  337.                 // 处理数据
    1 l+ j. D7 Y: P( S5 g1 x! Z* ^' _
  338.         }
    - s3 p& Z# M- T7 d: l6 o- g
  339.         
    1 K3 {3 `  I. F9 A+ y1 w- o& P+ |, F
  340. }# H. B' @  g8 H8 T' J" J- x
  341. 1 [$ M& m2 a$ a% e' r7 _7 b2 y
  342. *// U5 |, Q' R  M- V# f( }' q  x" K7 v

  343. - a+ n6 b7 Y* o6 c) q5 w3 ?
  344. ! T% _. X& o7 ?/ }6 b
  345. 1 J9 v( N& k7 p! T  X. ?

  346. 6 `; B- M) U$ j' x
  347. 1 Z0 x7 j# G5 W! Q# k8 V' E
  348. % j; i1 {  w9 l5 _
复制代码
5 [3 t/ ?0 M3 d, H4 w

, T( X2 G# v/ ]) T$ f- X6 i7 F/ Z
收藏 评论0 发布时间:2022-4-9 22:59

举报

0个回答

所属标签

相似分享

官网相关资源

关于
我们是谁
投资者关系
意法半导体可持续发展举措
创新与技术
意法半导体官网
联系我们
联系ST分支机构
寻找销售人员和分销渠道
社区
媒体中心
活动与培训
隐私策略
隐私策略
Cookies管理
行使您的权利
官方最新发布
STM32N6 AI生态系统
STM32MCU,MPU高性能GUI
ST ACEPACK电源模块
意法半导体生物传感器
STM32Cube扩展软件包
关注我们
st-img 微信公众号
st-img 手机版