整整两天时间,含泪完成。开发过程中主要耗时的是ESP8266发给单片机的数据,在解码的时候有乱码,一直研究原因,浪费了大量时间;一言难尽,同志们引以为戒;千万不要死磕,要学会变通呀。成功之后感觉很简单,但还是担心后续忘记了,这里留个脚印吧,方便日后查看;开始进入正题。
先把配置的过程准备好测试好了参考我的上一篇博文:单击这里打开
配置好之后开始漫长的调试吧!
注意:
1.收发数据都是ASCII码;
2.数据中不要有中文;
3.后续可以采用16进制数据的方式进行解码运算;
4.注意配置优先级,要不然其他定时或串口中断,会导致有的数据没有接到。
由于是开发好的开发板,先是将对应的GPIO引脚引出(我使用的是USART6对应PG9和PG14)使用串口调试工具和软件;进行配置和测试;使用串口USART1进行输出,方便观察;这里千万注意要将ESP8266的CH_PD引脚配置成高电平。
1.将ESP8266的CH_PD引脚配置成高电平。(我的电路板上使用的GPIO引脚是PG12,配置程序如下)
RCC_AHB1PeriphClockCmd(RCC_AHB1Periph_GPIOG, ENABLE);
GPIO_InitStructure.GPIO_Pin = GPIO_Pin_12;
GPIO_InitStructure.GPIO_Mode = GPIO_Mode_OUT;
GPIO_InitStructure.GPIO_OType = GPIO_OType_PP;
GPIO_InitStructure.GPIO_Speed = GPIO_Speed_100MHz;
GPIO_InitStructure.GPIO_PuPd = GPIO_PuPd_NOPULL;
GPIO_Init(GPIOG, &GPIO_InitStructure);
在主程序中调用使用:GPIO_SetBits (GPIOG,GPIO_Pin_12);
2.配置USART6,主要写出来一个u6_Printf方法(区别于USART1的Printf)用于发送数据到ESP8266。
#include "bsp_usart6.h"
#include "stdarg.h"
#include "string.h"
//串口接收缓存区
u8 USART6_RX_BUF[USART6_MAX_RECV_LEN]; //接收缓冲,最大USART3_MAX_RECV_LEN个字节.
u8 USART6_TX_BUF[USART6_MAX_SEND_LEN]; //发送缓冲,最大USART3_MAX_SEND_LEN字节
static void NVIC_Configuration(void)
{
NVIC_InitTypeDef NVIC_InitStructure;
/* Configure one bit for preemption priority */
NVIC_PriorityGroupConfig(NVIC_PriorityGroup_0);
/* 配置中断源 */
NVIC_InitStructure.NVIC_IRQChannel = Wifi_USART_IRQ;
NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority = 1;
NVIC_InitStructure.NVIC_IRQChannelSubPriority = 1;
NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE;
NVIC_Init(&NVIC_InitStructure);
}
void Wifi_USART_Config(void)
{
GPIO_InitTypeDef GPIO_InitStructure;
USART_InitTypeDef USART_InitStructure;
RCC_APB2PeriphClockCmd(Wifi_USART_CLK, ENABLE);
GPIO_PinAFConfig(Wifi_USART_RX_GPIO_PORT,Wifi_USART_RX_SOURCE,Wifi_USART_RX_AF);
GPIO_PinAFConfig(Wifi_USART_TX_GPIO_PORT,Wifi_USART_TX_SOURCE,Wifi_USART_TX_AF);
/* 配置Tx引脚为复用功能 */
GPIO_InitStructure.GPIO_OType = GPIO_OType_PP;
GPIO_InitStructure.GPIO_PuPd = GPIO_PuPd_UP;
GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AF;
GPIO_InitStructure.GPIO_Pin = Wifi_USART_TX_PIN ;
GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
GPIO_Init(Wifi_USART_TX_GPIO_PORT, &GPIO_InitStructure);
/* 配置Rx引脚为复用功能 */
GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AF;
GPIO_InitStructure.GPIO_Pin = Wifi_USART_RX_PIN;
GPIO_Init(Wifi_USART_RX_GPIO_PORT, &GPIO_InitStructure);
/* 配置Wifi_USART 模式 */
USART_InitStructure.USART_BaudRate = Wifi_USART_BAUDRATE;
USART_InitStructure.USART_WordLength = USART_WordLength_8b;
USART_InitStructure.USART_StopBits = USART_StopBits_1;
USART_InitStructure.USART_Parity = USART_Parity_No ;
USART_InitStructure.USART_HardwareFlowControl = USART_HardwareFlowControl_None;
USART_InitStructure.USART_Mode = USART_Mode_Rx | USART_Mode_Tx;
USART_Init(Wifi_USART, &USART_InitStructure);
NVIC_Configuration();
/*配置串口接收中断*/
USART_ITConfig(Wifi_USART, USART_IT_RXNE, ENABLE);
USART_Cmd(Wifi_USART, ENABLE);
}
/***************** 发送一个字符 **********************/
static void Usart_SendByte( USART_TypeDef * pUSARTx, uint8_t ch )
{
/* 发送一个字节数据到USART6 */
USART_SendData(pUSARTx,ch);
/* 等待发送完毕 */
while (USART_GetFlagStatus(pUSARTx, USART_FLAG_TXE) == RESET);
}
/***************** 指定长度的发送字符串 **********************/
void Wifi_Usart_SendStr_length( USART_TypeDef * pUSARTx, uint8_t *str,uint32_t strlen )
{
unsigned int k=0;
do
{
Usart_SendByte( pUSARTx, *(str + k) );
k++;
} while(k < strlen);
}
/***************** 发送字符串 **********************/
void Wifi_Usart_SendString( USART_TypeDef * pUSARTx, uint8_t *str)
{
unsigned int k=0;
do
{
Usart_SendByte( pUSARTx, *(str + k) );
k++;
} while(*(str + k)!='\0');
}
//串口6,printf 函数
//确保一次发送数据不超过USART6_MAX_SEND_LEN字节
void u6_printf(char* fmt,...)
{
u16 i,j;
va_list ap;
va_start(ap,fmt);
vsprintf((char*)USART6_TX_BUF,fmt,ap);
va_end(ap);
i=strlen((const char*)USART6_TX_BUF); //此次发送数据的长度
for(j=0;j<i;j++) //循环发送数据
{
while(USART_GetFlagStatus(Wifi_USART,USART_FLAG_TC)==RESET); //循环发送,直到发送完毕
USART_SendData(Wifi_USART,USART6_TX_BUF[j]);
}
}
3.配置USART6的头文件
```c
#ifndef BSP_USART6_H
#define BSP_USART6_H
#include "stm32f4xx.h"
#include <stdio.h>
#define Wifi_USART USART6
#define Wifi_USART_CLK RCC_APB2Periph_USART6
#define Wifi_USART_RX_GPIO_PORT GPIOG
#define Wifi_USART_RX_GPIO_CLK RCC_AHB1Periph_GPIOG
#define Wifi_USART_RX_PIN GPIO_Pin_9
#define Wifi_USART_RX_AF GPIO_AF_USART6
#define Wifi_USART_RX_SOURCE GPIO_PinSource9
#define Wifi_USART_TX_GPIO_PORT GPIOG
#define Wifi_USART_TX_GPIO_CLK RCC_AHB1Periph_GPIOG
#define Wifi_USART_TX_PIN GPIO_Pin_14
#define Wifi_USART_TX_AF GPIO_AF_USART6
#define Wifi_USART_TX_SOURCE GPIO_PinSource14
#define Wifi_USART_IRQHandler USART6_IRQHandler
#define Wifi_USART_IRQ USART6_IRQn
//串口波特率
#define Wifi_USART_BAUDRATE 115200
#define USART6_MAX_RECV_LEN 600 //最大接收缓存字节数
#define USART6_MAX_SEND_LEN 600 //最大发送缓存字节数
#define USART6_RX_EN 1 //0,不接收;1,接收.
void Wifi_USART_Config(void);
void u6_printf(char* fmt,...) ;
void Wifi_Usart_SendStr_length( USART_TypeDef * pUSARTx, uint8_t *str,uint32_t strlen );
void Wifi_Usart_SendString( USART_TypeDef * pUSARTx, uint8_t *str);
uint8_t* Wifi_Usart_ReciveString(void);
#endif //BSP_USART6_H
4.去配置USART1,配置完后直接主程序开干:注意加延时;
#include "stm32f4xx.h"
#include "bsp_systick.h"
#include "bsp_out.h"
#include "bsp_usart.h"
#include "bsp_usart6.h"
#include "esp8266.h"
#include "string.h"
#define CLOSE_TCP "+++" //关闭TCP连接,退出透传模式
#define AT "AT\r\n"
#define RST "AT+RST\r\n" //软重启模块
#define CWMODE "AT+CWMODE=3\r\n" //设置模式为AP+STA
#define CIFSR "AT+CIFSR\r\n" //查询IP地址
#define UDP_CIPSTART "AT+CIPSTART=\"UDP\",\"192.168.4.2\",11111,2233,0\r\n" //设置为TCP协议传输并指定IP和端口号
#define CIPMODE "AT+CIPMODE=1\r\n" //透传
#define CIPSEND "AT+CIPSEND\r\n" //开始传输
uint8_t ucaRxBuf[256];
int CompareString(uint8_t* chr1,uint8_t* chr2);
uint8_t ucaRxBuf[256];
uint8_t RxEncode[6];
uint8_t RecieveFlag;
int main(void)
{
InitSystick();//Initialization clock
Out_InitGPIO();//Initialization output
Debug_USART_Config();//Initialization RS232
//printf("%s\r\n", "开始进行数据的读取ESP8266");
Wifi_USART_Config();
GPIO_SetBits (GPIOG,GPIO_Pin_12);
Delay_ms(1000);
u6_printf(AT);
Delay_ms(1000);
printf("%s\r\n", ucaRxBuf);
u6_printf(RST);
Delay_ms(1000);
printf("%s\r\n", ucaRxBuf);
u6_printf(CWMODE);
Delay_ms(1000);
printf("%s\r\n", ucaRxBuf);
u6_printf(UDP_CIPSTART);
Delay_ms(1000);
printf("%s\r\n", ucaRxBuf);
u6_printf(CIPMODE);
Delay_ms(1000);
printf("%s\r\n", ucaRxBuf);
u6_printf(CIPSEND);
Delay_ms(1000);
printf("%s\r\n", ucaRxBuf);
RecieveFlag=1;
u6_printf("确认");
Delay_ms(1000);
while(1)
{
Delay_ms(100);
u6_printf("Go");
for(int i=1;i<=12;i++)
{
for(int i=0;i<6;i++)
{
RxEncode[i] = (char)ucaRxBuf[i];
}
printf("%s\r\n", RxEncode);//观察控制指令的当前数据
int sta = strncmp((char*)RxEncode,"0x8001",6);
if(sta==0)
{
Output(i , ON);
Delay_ms(100);
Output(i , OFF);
}
else
{
for(int i=1;i<=12;i++)
{
Output(i , OFF);
}
break;
}
}
}
}
源代码和APP源代码审核中稍后放在这里: