STM32F4--串口通信代码分析

串口接收和发送机理
首先我们要知道的是串口的工作机理,串口是通过数据帧的发送,假定我们使用的如下设置,波特率为9600,8位数据。其它的什么奇偶校验都不用。那么它与PC机之间的通信流程是怎么样的呢?第一,数据帧的大小是10位,包含起始位和结束位,起始位固定为0,结束位固定为1。比如现在PC机要向单片机传递数据,首先单片机检测到数据开始位0,那么单片机开始接受后面的数据,通过移位寄存器,一位一位将数据送入,当8位后,接收到结束标志,这个时候RI置位,单片机进入中断程序,软件置零RI,在最快的时间将SBUF中的值读取了,然后退出中断,等待下一个数据接收完毕,就这样将数据一个一个的传送进来。那么发送又是怎么样的呢?首先单片机将数据发送,然后在最后一位发送完毕后,TI置位,进入中断服务程序,将TI清零,接着发送下一个字节的数据,并且退出中断,等待发送完毕,就这样将数据一位一位发送出去。


 

如下为代码分析

第一段代码:

        GPIO_InitTypeDef   GPIO_Structure;
        USART_InitTypeDef  USART_Structure;
        NVIC_InitTypeDef   NVIC_Structure; 

作用:实例化三组对象,GPIO_InitTypeDef为结构体类型的别名,GPIO_Structure为结构体变量名。GPIO_InitTypeDef相当于模板,根据这个模板可以new出具体的对象。

STM32F4--串口通信代码分析_第1张图片

第二段代码:

        RCC_APB2PeriphClockCmd(RCC_APB2Periph_USART1,ENABLE);//USART1是挂在APB2总线上
        RCC_AHB1PeriphClockCmd(RCC_AHB1Periph_GPIOA,ENABLE);

作用:第一句,使能复用外设(串口1作为内置外设)时钟,相当于打开时钟电路开关。

          第二句,此处用到的引脚是PA9  PA10,GPIOA挂载在AHB1总线上,自然就要使能GPIO时钟。

第三段代码:

        GPIO_PinAFConfig(GPIOA,GPIO_PinSource9,GPIO_AF_USART1);  
        GPIO_PinAFConfig(GPIOA,GPIO_PinSource10,GPIO_AF_USART1);

作用:端口(引脚)复用,串口1 的发送接收引脚是PA9,PA10,当我们把PA9,PA10不用作普通的GPIO口,而把它复用为串口1的发送(TXD)接收(RXD)引脚的时候,叫端口复用

补充一下映射:

     串口1的TX,RX引脚是在PA9,和PA10端口,但是同时它有两个映射端口PB6,PB7。开启重映射,PB6和PB7同样可以使用串口1。

第四段代码:初始化GPIO

        //GPIO初始化
        GPIO_Structure.GPIO_Pin=GPIO_Pin_9|GPIO_Pin_10;//选择引脚 PA9 PA10
        GPIO_Structure.GPIO_Mode=GPIO_Mode_AF;//复用功能
        GPIO_Structure.GPIO_Speed=GPIO_Speed_50MHz;//传输速度
        GPIO_Init(GPIOA,&GPIO_Structure); //按照以上的参数初始化GPIOA

补充说明:以上两段可以用如下一段代码代替

    //USART1_TX   GPIOA.9
  	GPIO_InitStructure.GPIO_Pin = GPIO_Pin_9; //PA.9
 	GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
  	GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AF_PP;	//复用推挽输出
  	GPIO_Init(GPIOA, &GPIO_InitStructure);//初始化GPIOA.9
   
  	//USART1_RX	  GPIOA.10初始化
  	GPIO_InitStructure.GPIO_Pin = GPIO_Pin_10;//PA10
  	GPIO_InitStructure.GPIO_Mode = GPIO_Mode_IN_FLOATING;//浮空输入
  	GPIO_Init(GPIOA, &GPIO_InitStructure);//初始化GPIOA.10  

第五段代码:初始化串口1 

        //USART1串口初始化
        USART_Structure.USART_BaudRate=9600; //波特率 调试助手必须和此参数一致
        USART_Structure.USART_WordLength=USART_WordLength_8b;//字长为8位
        USART_Structure.USART_StopBits=USART_StopBits_1;//停止位为1
        USART_Structure.USART_Parity=USART_Parity_No;//无奇偶校验位
        USART_Structure.USART_HardwareFlowControl=USART_HardwareFlowControl_None;//无硬件数据流控制
        USART_Structure.USART_Mode=USART_Mode_Rx|USART_Mode_Tx; //收发模式
        USART_Init(USART1,&USART_Structure);//按照以上参数初始化USART1串口

第六段:使能串口

        USART_Cmd(USART1,ENABLE);

 作用:打开USART1串口开关,相当于电源开关

第七段:使能或者失能指定的USART1串口中断,开启串口1接受中断的功能

        USART_ITConfig(USART1,USART_IT_RXNE,ENABLE);

第一个参数为使用串口1

第二个参数为中断标志,串口有很多种中断,这里是使用USART_IT_RXNE中断   

第三个参数为使能

第八段:串口1的初始化

        //usart1 的中断初始化
        NVIC_Structure.NVIC_IRQChannel=USART1_IRQn; //stm32f4xx.h开头找
        NVIC_Structure.NVIC_IRQChannelCmd=ENABLE;
        NVIC_Structure.NVIC_IRQChannelPreemptionPriority=1;
        NVIC_Structure.NVIC_IRQChannelSubPriority=1;   
        NVIC_Init(&NVIC_Structure);

你可能感兴趣的:(stm32,单片机,arm)