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

基于STM32常用库函数经验分享

[复制链接]
攻城狮Melo 发布时间:2023-3-26 16:13
 1.GPIO初始化
% |* ^% ]& A* O8 B1 A  用法:% u. a0 b- y( B! j: B3 w
  1.   voidGPIO_Configuration(void)# M5 k% U# l7 ~. c5 z: q
  2.   {5 K. j! n/ [$ o' T- Z' f$ ]/ h
  3.   GPIO_InitTypeDefGPIO_InitStructure;//GPIO状态恢复默认参数
    + |6 g2 D6 v/ \/ I
  4.   GPIO_InitStructure.GPIO_Pin=GPIO_Pin_标号|GPIO_Pin_标号;; ^; n% r- X3 K: T8 y0 x0 a/ _
  5.   //管脚位置定义,标号可以是NONE、ALL、0至15。
    1 ?( U8 M8 K7 Q5 }
  6.   GPIO_InitStructure.GPIO_Speed=GPIO_Speed_50MHz;//最高输出速度为50MHz& L2 I$ X+ n1 q1 l* p' Y9 {2 {
  7.   GPIO_InitStructure.GPIO_Mode=GPIO_Mode_Out_PP;//推挽输出! n$ \  Z. y; ]; j7 A( f- w$ B
  8.   GPIO_Init(GPIOC,&GPIO_InitStructure);//C组GPIO初始化# I- j0 p+ b% W, Z" v! t
  9.   /*注:以上四行代码为一组,每组GPIO属性必须相同,默认的GPIO参数为:ALL,2MHz,FLATING。如果其中任意一行与前一组相应设置相同,那么那一行可以省略,由此推论如果前面已经将此行参数设定为默认参数(包括使用GPIO_InitTypeDefGPIO_InitStructure代码),本组应用也是默认参数的话,那么也可以省略。以下重复这个过程直到所有应用的管脚全部被定义完毕。*/3 @8 s: V) {/ R; g
  10.   }
复制代码
* m' X3 d4 G  R& [8 \: H; I
  GPIO基础应用:向管脚置1||0
& v. k$ X4 W, R* k( P% i
  1.   GPIO_SetBits(GPIOC,GPIO_Pin_1);//置1, U+ w# c/ @7 |; m
  2.   GPIO_ResetBits(GPIOC,GPIO_Pin_1);//置0
复制代码

: h5 w; Q+ Z8 ?% I" z+ }6 z5 _  2.RCC:单片机时钟管理。0 l! y8 E# R. S4 E5 N3 o8 O7 ]
  管理外部、内部和外设的时钟,设置、打开和关闭这些时钟。
0 A: W. I2 H1 Y# Q- D  用法:- _, G3 }% [, F, c

4 j' ^2 a) ~; x* `) x% F  函数初始化( o8 [/ i4 l4 V; V) f
  1.   voidRCC_Configuration(void)//时钟初始化函数
    ' \9 `& a" `% D, T( ~; e
  2.   {
    / [8 Z2 C+ e9 M- O$ Y, h
  3.   ErrorStatusHSEStartUpStatus;//等待时钟的稳定. H' n6 H8 C3 @- a3 `1 ?1 J1 E
  4.   RCC_DeInit();//时钟管理重置$ U; p7 |' V8 {# G9 x4 v" Q9 i& b
  5.   RCC_HSEConfig(RCC_HSE_ON);//打开外部晶振HSEStartUpStatus=RCC_WaitForHSEStartUp();//等待外部晶振就绪
    - I: g& l) n  Z5 }9 O% ]7 ]% C
  6.   if(HSEStartUpStatus==SUCCESS)
    6 Q6 A; Y. Y/ j/ u+ H2 j# K) d
  7.   {% o9 P. t, G0 s
  8.   FLASH_PrefetchBufferCmd(FLASH_PrefetchBuffer_Enable);//flash读取缓冲,加速; g" b3 x% l) a3 U1 q
  9.   FLASH_SetLatency(FLASH_Latency_2);//flash操作的延时
    ) K- u9 Y/ a) f$ ]% Z
  10.   RCC_HCLKConfig(RCC_SYSCLK_Div1);//AHB使用系统时钟
    ' z3 a0 g& h/ Z
  11.   RCC_PCLK2Config(RCC_HCLK_Div2);//APB2(高速)为HCLK的一半! [) e5 O& I( Q- B
  12.   RCC_PCLK1Config(RCC_HCLK_Div2);//APB1(低速)为HCLK的一半
    . P) {) N# \  Z: f3 ]
  13.   /*注:AHB主要负责外部存储器时钟。APB2负责AD,I/O,高级TIM,串口1。APB1负
    . B% c5 B, O2 _. T; z; m
  14.   责DA,USB,SPI,I2C,CAN,串口2345,普通TIM。*/+ G0 c+ z7 E: ^8 O( O2 Q
  15.   RCC_PLLConfig(RCC_PLLSource_HSE_Div1,RCC_PLLMul_9);/ B% o% U# d# ]
  16.   //PLLCLK=8MHz*9=72MHz5 W: S7 p$ q4 F0 `9 i
  17.   RCC_PLLCmd(ENABLE);//启动PLL
      I. q# q! ~) R8 V- ]7 `
  18.   while(RCC_GetFlagStatus(RCC_FLAG_PLLRDY)==RESET){}//等待PLL启动- f# _8 `8 Z( f) O5 L! ]1 q, z
  19.   RCC_SYSCLKConfig(RCC_SYSCLKSource_PLLCLK);//将PLL设置为系统时钟源
    / @2 ^1 b' m) z* p7 x2 C: g
  20.   while(RCC_GetSYSCLKSource()!=0x08){}//等待系统时钟源的启动' W  y& F' x  z0 d( s% Z: f
  21.   }
    4 d- d1 D3 _2 w" p: s
  22.   RCC_AHBPeriphClockCmd(ABP2设备1|ABP2设备2|,ENABLE);//启动AHP设备
    2 i# S" L0 Q$ R9 N$ u3 o5 F0 V
  23.   RCC_APB2PeriphClockCmd(ABP2设备1|ABP2设备2|,ENABLE);//启动ABP2设备
    $ h( }7 e& j  b6 n/ r# k4 V/ _" u/ E
  24.   RCC_APB1PeriphClockCmd(ABP2设备1|ABP2设备2|,ENABLE);//启动ABP1设备
    # X+ d) Y& X  X; D. a
  25.   }
复制代码
" S9 w- V. g" G! y+ Z+ y: ^0 e
  3.NVIC:系统中断管理。
# G  O3 j$ ?; y8 G) v
  管理系统内部的中断,负责打开和关闭中断。7 S+ @  I+ a5 n* C' ?

" t: J: k3 I! W1 @( j  基础应用1,中断的初始化函数,包括设置中断向量表位置,和开启所需的中断两部分。
; {, S7 t. x% b$ ~
# j8 v8 s6 h) b: M- l$ J3 j3 D  用法:! F2 b" X" `: E' I' d1 b% M
  1.   voidNVIC_Configuration(void). D" {" a* P/ I+ B
  2.   {( b* N8 o5 e# S. r& O) `% S
  3.   NVIC_InitTypeDefNVIC_InitStructure;//中断管理恢复默认参数
      k0 N7 C0 W5 ^* s" C& O7 b+ D
  4.   #ifdefVECT_TAB_RAM+ q4 N' T' Y6 t  }7 \$ c/ X4 V$ H
  5.   /*如果C/C++CompilerPreprocessorDefinedsymbols中的定义了VECT_TAB_RAM(见程序库更改内容的表格)*/* q2 n9 E' T1 H0 M; f
  6.   NVIC_SetVectorTable(NVIC_VectTab_RAM,0x0);//则在RAM调试, \. G3 v3 W& B5 [' A. |
  7.   #else//如果没有定义VECT_TAB_RAM
    " i- A8 o( Q4 a- B9 s1 A" l5 g) z
  8.   NVIC_SetVectorTable(NVIC_VectTab_FLASH,0x0);//则在Flash里调试
    , _& V+ S' H% ]7 A: S  J6 G0 g
  9.   #endif//结束判断语句
    % a4 ]5 E; ]' ^0 M+ g+ e9 q
  10.   /*以下为中断的开启过程,不是所有程序必须的。*/, I2 a. s& ?& ]4 }
  11.   NVIC_PriorityGroupConfig(NVIC_PriorityGroup_2);//设置NVIC优先级分组,方式。
    : Z- h  B' V; J2 x8 t
  12.   NVIC_InitStructure.NVIC_IRQChannel=中断通道名;//开中断,中断名称见函数库
    2 r7 w, |0 O7 K& A5 J3 i$ Y
  13.   NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority=0;//抢占优先级4 x$ s! y% @  B. f, N  \2 q4 m
  14.   NVIC_InitStructure.NVIC_IRQChannelSubPriority=0;//响应优先级# K3 ^* P3 O9 `! @: |
  15.   NVIC_InitStructure.NVIC_IRQChannelCmd=ENABLE;//启动此通道的中断
    1 s+ w2 _% v% e; r; S" j
  16.   NVIC_Init(&NVIC_InitStructure);//中断初始化" M; q# J7 j. _- M2 P; v
  17.   }
复制代码

. L. U0 v) e" V! ~- v; ~- k8 I+ G- V  注:一共16个优先级,分为抢占式和响应式。两种优先级所占的数量由此代码确定,NVIC_PriorityGroup_x可以是0、1、2、3、4,分别代表抢占优先级有1、2、4、8、16个和响应优先级有16、8、4、2、1个。规定两种优先级的数量后,所有的中断级别必须在其中选择,抢占级别高的会打断其他中断优先执行,而响应级别高的会在其他中断执行完优先执行。5 ~& O: J; Q+ O/ q* d1 U

) H. V  c8 O6 ]- U* U- G0 H

5 F& V* y! }$ h; B+ q1 G  s8 X  4.FLASH:芯片内部存储器flash操作函数* C& x( i  C$ F7 X" Q( @: E
/ S$ s; K+ K+ J- U
  对芯片内部flash进行操作的函数,包括读取,状态,擦除,写入等等,可以允许程序去操作flash上的数据。
2 }! Y, F4 j& W. b8 z" t/ _- Y' F6 I9 b+ M' @% S5 P+ l/ Z
  基础应用1,FLASH时序延迟几个周期,等待总线同步操作。推荐按照单片机系统运行频率,0—24MHz时,取Latency=0;24—48MHz时,取Latency=1;48~72MHz时,取Latency=2。所有程序中必须的
, S6 ~! X  N$ ^2 {; `( T
/ i: v" v/ ?0 n* K) C  用法:, i, U2 v1 W/ E9 \
  1.   FLASH_SetLatency(FLASH_Latency_2);
复制代码

1 W/ k; S' z, }8 \) n! b  位置:RCC初始化子函数里面,时钟起振之后。, D' y* ~$ w+ @; E6 e& {& q
* ~8 ^, P& k6 @/ B' |
  基础应用2,开启FLASH预读缓冲功能,加速FLASH的读取。所有程序中必须的用法:
4 r& A/ w4 @; f% I" h1 i) [2 ~* B
  1.   FLASH_PrefetchBufferCmd(FLASH_PrefetchBuffer_Enable);
复制代码

, I* u; N% m4 L/ Z. n  位置:RCC初始化子函数里面,时钟起振之后。
/ ]% y. b% W& b4 L( r" F
* p  V4 W: O# k$ I$ {$ C

4 k" \1 g: Z  \/ Z  F. L  5.LIB:调试所有外设初始化的函数。* S1 ?4 k+ F6 ]) c- i& ?
  所有外设在调试的时候,EWRAM需要从这个函数里面获得调试所需信息的地址或者指针之类的信息。8 K0 z7 s" k( ?1 H) n

/ b+ l6 \! S/ w; J* U  基础应用1,只有一个函数debug。所有程序中必须的。
" u8 X9 `& n4 V! C; c% t( ~

7 d% E( Q: h! K! R  z  O1 H  用法:9 X, m9 R; d0 v4 _" S% \
  1.   #ifdefDEBUG5 f: y2 F- ^5 F# ]! j) o# p; ^
  2.   debug();$ s1 E9 v4 Z$ u1 U& X& w
  3.   #endif
复制代码
" T- Q  {& F! b  x9 y
  位置:main函数开头,声明变量之后。) a! v& k; D9 B" g6 n
" Y2 z: m5 [# F7 _) {* j+ [7 J$ g4 p5 `
( G' G& ~# C7 E8 }# q8 v
  6.EXTI:外部设备中断函数, K) F. c. Y9 i3 |% w: m8 t% ?
  外部设备通过引脚给出的硬件中断,也可以产生软件中断,19个上升、下降或都触发。EXTI0~EXTI15连接到管脚,EXTI线16连接到PVD(VDD监视),EXTI线17连接到RTC(闹钟),EXTI线18连接到USB(唤醒)。基础应用1,设定外部中断初始化函数。按需求,不是必须代码。用法:- y8 g+ @: D0 K& T9 A
  1.   voidEXTI_Configuration(void)
    8 v6 \' M& J+ }3 H; `" z; t6 s
  2.   {
    : n$ o2 t# F( d3 e7 R
  3.   EXTI_InitTypeDefEXTI_InitStructure;//外部设备中断恢复默认参数, [5 N/ }! |8 ?, m  j8 U
  4.   EXTI_InitStructure.EXTI_Line=通道1|通道2;
    / {; X+ n% I0 L* `" H( K
  5.   //设定所需产生外部中断的通道,一共19个。
    + Z6 n# t; Q0 E
  6.   EXTI_InitStructure.EXTI_Mode=EXTI_Mode_Interrupt;//产生中断
    $ j( X" R4 Y" v* t" N3 z
  7.   EXTI_InitStructure.EXTI_Trigger=EXTI_Trigger_Falling;
    6 q' n2 U! {6 X; _
  8.   //上升下降沿都触发. ]# m' [3 p1 A: Y7 z! m; W5 z  c
  9.   EXTI_InitStructure.EXTI_LineCmd=ENABLE;//启动中断的接收) v0 j0 t  w9 k/ K/ d% \
  10.   EXTI_Init(&EXTI_InitStructure);//外部设备中断启动
    $ M7 ]& R( [9 {  @$ K. }
  11.   }
复制代码
9 _* l5 O( W2 q* b
  7.systic:系统定时器
$ U! r: v0 w$ [$ r4 H  可以输出和利用系统时钟的计数、状态。8 W2 _" V4 H2 b5 Q, J: n$ V% g. j
  1.   vu32TimingDelay;//全局变量声明' A* j* c4 R& M3 b3 _0 m
  2.   voidSysTick_Configuration(void)//初始化函数
    % I- E) _% G4 U% z# v. U8 j& P
  3.   {' K/ G! q+ z: U+ h
  4.   SysTick_CLKSourceConfig(SysTick_CLKSource_HCLK_Div8);//设置SysTick时钟源1 o9 X% \, ^' q; V& R4 x# N) ^! |/ c
  5.   NVIC_SystemHandlerPriorityConfig(SystemHandler_SysTick,2,0);4 ?$ u, j. g' ^
  6.   //设置指定的系统Handler优先级
    ; I4 t1 M' `! o! a
  7.   SysTick_SetReload(9000); /*设置SysTick重装载值72M为基础9000--1ms
    $ ?& T( D3 t# {/ T* w( Q
  8.   SysTick_ITConfig(ENABLE);//使能或者失能SysTick中断
    # R/ e& w1 h9 q4 l  H; e! \% q
  9.   }, z5 R' i8 m: G, I# g$ g0 U
  10.   voidDelay_nms(u32nTime)//精确延时函数
    5 U7 p3 U! d, |) x
  11.   {
    7 f- x: w3 I5 ]
  12.   SysTick_CounterCmd(SysTick_Counter_Enable);//使能SysTick计数器
    ) j5 v" A# U/ G- L
  13.   TimingDelay=nTime;
    / e8 a6 k' S0 d/ u( B% R! e' q/ _3 J
  14.   while(TimingDelay!=0);
    8 f6 g- k/ T# k3 D0 q3 A$ e
  15.   SysTick_CounterCmd(SysTick_Counter_Disable);//失能SysTick计数器  n0 u+ R) J$ }) P+ }. f
  16.   SysTick_CounterCmd(SysTick_Counter_Clear);//清除计数器值为0
    5 `# `4 Z; S7 ?  X6 n
  17.   }# y! w( x# D: _  X  l8 F: L
  18.   voidSysTick_Handler(void)//中断
    4 F- p7 x) J7 `$ u3 ^( Y( f" A
  19.   {
    : I$ [$ j% c' A% S1 K' s
  20.   if(TimingDelay)
    1 H$ t" Z; B  d" t. U
  21.   TimingDelay--;8 I: q* _/ a1 y6 j% \4 p# x  k
  22.   }
    1 k, e  i  u& G0 r* i% k  R7 ]3 k
  23.   voidUSART_Configuration(void)//串口初始化函数
    2 e( p; _+ g0 W0 a1 P! a0 r
  24.   {
    6 n9 ]' m+ y- P3 h
  25.   USART_InitTypeDefUSART_InitStructure;//串口设置恢复默认参数USART_InitStructure.USART_BaudRate=9600;//波特率9600
    ) ^  M$ F8 k6 O1 _/ G6 ]
  26.   USART_InitStructure.USART_WordLength=USART_WordLength_8b;//字长8位
    - D/ S) `1 v. Z+ v& R3 r- d
  27.   USART_InitStructure.USART_StopBits=USART_StopBits_1;//1位停止字节
      i' [$ I; X* C2 z+ M  O5 z
  28.   USART_InitStructure.USART_Parity=USART_Parity_No;//无奇偶校验USART_InitStructure.USART_HardwareFlowControl=USART_HardwareFloControl_None;//无流控制USART_InitStructure.USART_Mode=USART_Mode_Rx|USART_Mode_Tx;//打开Rx接收和Tx发送功能
    ! }8 M- t2 `4 _# [7 w* ]1 G3 ]
  29.   USART_Init(USART1,&USART_InitStructure);//初始化/ x: B/ u+ q/ S  |
  30.   USART_Cmd(USART1,ENABLE);//启动串口
    ! o- `" |9 m: |) M0 G* N) Q
  31.   }
复制代码
( N9 f  e8 E* ]

7 K) j0 V8 L' P# l$ ]  RCC中打开相应串口
4 \7 K" `; I+ @# Z0 I0 G# o
  1.   RCC_APB2PeriphClockCmd(RCC_APB2Periph_USART1,ENABLE);
复制代码

2 x7 K9 x6 d# p- H5 Y, j0 }) Y  GPIO里面设定相应串口管脚模式
' \: a! _, v7 {3 M4 b9 a- V
  1.   //串口1的管脚初始化
    5 q6 @" C$ P1 h( x( B' [
  2.   GPIO_InitStructure.GPIO_Pin=GPIO_Pin_9;//管脚9" ^4 w' L' E2 p" O8 m, n& k7 p
  3.   GPIO_InitStructure.GPIO_Mode=GPIO_Mode_AF_PP;//复用推挽输出GPIO_Init(GPIOA,&GPIO_InitStructure);//TX初始化GPIO_InitStructure.GPIO_Pin=GPIO_Pin_10;//管脚106 m& b, p) L& _1 z2 Z4 O
  4.   GPIO_InitStructure.GPIO_Mode=GPIO_Mode_IN_FLOATING;//浮空输GPIO_Init(GPIOA,&GPIO_InitStructure);//RX初始化
复制代码

  l+ d; f; _& N- m- g  8.注意事项
) B& g, k9 v! H3 q5 t  a)Lib注意事项:; S4 J6 z- J4 j+ I' l+ T
  属于Lib的Debug函数的调用,应该放在main函数最开始,不要改变其位置。2 H* i  Z2 H1 f
$ D; P& a8 m" J
  b)RCC注意事项:& j/ Z5 w+ M5 m) m- Y3 L
  Flash优化处理可以不做,但是两句也不难也不用改参数……& v8 G0 c! _. y- b4 [' w; m* N. x& }
  根据需要开启设备时钟可以节省电能8 |" S; v' k/ r6 F  _* A; Z7 F
  时钟频率需要根据实际情况设置参数
, X- M$ e' a, i1 U) o$ U2 ^* B# }5 G/ r) y/ _8 s. \( ]/ [
  c)NVIC注意事项
5 z( X* d+ L7 Q  注意理解占先优先级和响应优先级的分组的概念3 d2 x" [6 V: L" ~1 y6 Q& [
2 G+ ]9 X# ^  H4 d5 [
  d)GPIO注意事项
3 k5 U& @! c: D( v) _  K  注意以后的过程中收集不同管脚应用对应的频率和模式的设置。
! L& S' u8 C2 X: O4 o# N  作为高低电平的I/O,所需设置:RCC初始化里面打开RCC_APB2+ ^5 S+ B: Y4 n1 |% _# V
  PeriphClockCmd(RCC_APB2Periph_GPIOA);GPIO里面管脚设定:IO输出(50MHz,Out_PP);IO输入(50MHz,IPU);
+ k/ B! U) I0 I3 q- ^
! z1 W5 U! Y" ?2 T- B- ]: j  e)USART注意事项:* m! p# u- h3 ?3 {1 l) S; B
  发动和接受都需要配合标志等待。
: `' E$ A6 z8 H$ G& \( u  只能对一个字节操作,对字符串等大量数据操作需要写函数
6 G: j3 R' M' T! n  C& H! h  使用串口所需设置:RCC初始化里面打开RCC_APB2PeriphClockCmd
% w! T2 K& w" }. e5 k  (RCC_APB2Periph_USARTx);GPIO里面管脚设定:串口RX(50Hz,IN_FLOATING);串口TX(50Hz,AF_PP);8 L2 K! x! @" ?3 \( z
————————————————
3 }2 m" F8 w/ D& W  M版权声明:被大佬糊弄的只会点灯的小菜鸡4 }$ j- P! Z3 c# m
如有侵权请联系删除! P1 W4 y6 S4 E7 o

9 @  L+ U, d$ y$ g$ J* Q  x
/ s1 N9 m$ `9 h6 ~/ X( Q' n
赞 收藏 评论0 发布时间:2023-3-26 16:13

举报

0个回答

所属标签

相似技术帖

官网相关资源

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