# 国民技术车规MCU N32A455开发板测评 - 2 - uart串口通讯+mqtt初连百度智能云
>你好!这边之前通过阿里智能云社区中的帖子搞过关于stm32f103c8t6连接到百度智能云不过没有很好的记录下来,这次通过这次机会将其完整的记录下来。
编程软件keil5 串口调试工具usb转ttl 串口上位机sscom
## STEP one:
>我们首先需要完成的是关于串口的发送以及中断接收
#### 1.串口的初始化
```c
/**
*
@brief Configures the different system clocks.
*/
void RCC_Configuration(void)
{
/* Enable GPIO clock */
GPIO_APBxClkCmd(USARTx_GPIO_CLK | RCC_APB2_PERIPH_AFIO, ENABLE);
/* Enable USARTy and USARTz Clock */
USART_APBxClkCmd(USARTx_CLK, ENABLE);
}
```
>APB2 外设时钟使能寄存器的操作
USARTx_GPIO_CLK所定义的内容是
RCC_APB2_PERIPH_AFIO所定义的内容是
通过查询数据手册可以得知这时钟的第一步是使能GPIO端的A时钟与AFIO时钟
第二步是初始化usart时钟
```c
void GPIO_Configuration(void)
{
GPIO_InitType GPIO_InitStructure;//定义引脚初始化结构体
/* Configure USARTy Rx as input floating */
GPIO_InitStructure.Pin = USARTx_RxPin;//Pa10
GPIO_InitStructure.GPIO_Mode = GPIO_Mode_IN_FLOATING;
GPIO_InitPeripheral(USARTy_GPIO, &GPIO_InitStructure);
/* Configure USARTy Tx as alternate function push-pull */
GPIO_InitStructure.Pin = USARTx_TxPin;//Pa9
GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
GPIO_InitStructure.GPIO_Mode= GPIO_Mode_AF_PP;
GPIO_InitPeripheral(USARTy_GPIO, &GPIO_InitStructure);
}
```
其中IO的配置在代码中是由GPIO_ModeType这个结构体表示的:
```c
typedef enum
{
GPIO_Mode_AIN = 0x0,//模拟模式 0000
GPIO_Mode_IN_FLOATING = 0x04,//浮空输入0100
GPIO_Mode_IPD = 0x28,//下拉输入1000 0
GPIO_Mode_IPU = 0x48,//上拉输入1000 1
GPIO_Mode_Out_OD = 0x14,//开漏输出
GPIO_Mode_Out_PP = 0x10,//推挽输出
GPIO_Mode_AF_OD = 0x1C,//复用开漏输出
GPIO_Mode_AF_PP = 0x18//复用推挽输出
} GPIO_ModeType;
```
在通过查询手册可知PA9是串口一的TX采用复用推挽输出PA10是串口的RX采用的是浮空输入
```c
/* USARTy and USARTz configuration ------------------------------------------------------*/
USART_InitStructure.BaudRate = 115200;//串口工作速率设置后期与PC端串口调试工具调试的时候需要对上这个波特率
USART_InitStructure.WordLength = USART_WL_8B;//发送与接收的数据位数
USART_InitStructure.StopBits = USART_STPB_1;//停止位
USART_InitStructure.Parity = USART_PE_NO;//奇偶校验位
USART_InitStructure.HardwareFlowControl = USART_HFCTRL_NONE;//是否开启硬件流控制
USART_InitStructure.Mode = USART_MODE_RX | USART_MODE_TX;//接收模式开启参数
/* Configure USARTx */
USART_Init(USARTx, &USART_InitStructure);//将所有参数进行输入进行初始化
```
串口接收中断的初始化
```c
void NVIC_Configuration(void)
{
NVIC_InitType NVIC_InitStructure;
/* Configure the NVIC Preemption Priority Bits */
NVIC_PriorityGroupConfig(NVIC_PriorityGroup_0);//设置0bit抢占优先级4bit优先级为首要优先级
/* Enable the USARTy Interrupt */
NVIC_InitStructure.NVIC_IRQChannel = USARTx_IRQn;
NVIC_InitStructure.NVIC_IRQChannelSubPriority = 0;
NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE;
NVIC_Init(&NVIC_InitStructure);
}
```
#### 2.串口的发送与接收
发送,通过重写串口发送函数
//串口1发送的重写
```c
//串口1发送的重写
void Usart1_SendByte(u8 val)
{
USART_SendData(USART1, (uint8_t)val);
while (USART_GetFlagStatus(USART1, USART_FLAG_TXDE) == RESET);
}
void Usart1_SendBuf(u8 *buf,u8 len)
{
while(len--) Usart1_SendByte(*buf++);
}
void Usart1_SendString(char *str)
{
while(*str) Usart1_SendByte(*str++);
}
```
在while函数中调用结果如下
中断函数中进行中断接收
```c
void USARTx_IRQHandler(void)
{
if (USART_GetIntStatus(USART1, USART_INT_RXDNE) != RESET)
{
rxbuf[RxCounter1++] = USART_ReceiveData(USART1);
if(rxbuf[RxCounter1] == 0x02 && rxbuf[RxCounter1-1] == 0x20)
{
mqtt_flag = 1;
}
rxarray[RxCounter1-1] = rxbuf[RxCounter1-1];
}
if(RxCounter1 == 200)
{
RxCounter1 = 0;
}
// if (RxCounter1 == 100)
// {
// /* Disable the USARTy Receive interrupt */
// USART_ConfigInt(USART1, USART_INT_RXDNE, DISABLE);
// }
}
```
结果如下图
## STEP tow:
```c
//连接热点
u8 wifi_state = 0;
void Wifi_Init(void)
{
while(wifi_state < 3)
{
wifi_state = 0;
if(_net.Init(rxbuf,sizeof(rxbuf),txbuf,sizeof(txbuf))!=0)//如果初始化返回为0的话说明esp8266没有连接好
{
wifi_state++;
}
if(_net.ConnectAP(WIFI_NAME,WIFI_PASSWD)!=0)//连接热点
{
wifi_state++;
}
if(_net.ConnectServer("TCP",MQTT_BROKERADDRESS,1883)!=0)//构建TCP通讯线路
{
wifi_state++;
}
}
}
u8 mqtt_state = 0;
void Mqtt_Init(void)
{
while(mqtt_state < 2)
{
mqtt_state = 0;
_mqtt.Init(rxbuf,sizeof(rxbuf),txbuf,sizeof(txbuf));
if(_mqtt.Connect(
MQTT_CLIENTID,//ClientID
MQTT_USARNAME,//Username
MQTT_PASSWD //Password
) != 0)
{
mqtt_state++;
}
if(_mqtt.SubscribeTopic(MQTT_SUBSCRIBE_TOPIC,0,1) != 0)
{
mqtt_state++;
}
}
}
```