wg2993 发表于 2025-3-23 23:21:34

15W4K48S4+ESP8266实现通信时遇到问题

需求:用15W4K48S4+ESP8266与服务器通信。
问题:程序烧录成功后,拔掉电源,接上esp826601s,接通电源,led不闪烁,在路由器中找不到此设备(esp8266),感觉芯片没有向esp8266发送at相关指令
预期:接esp8266并通电后,led会根据通信情况闪烁(通信OK闪2次,失败闪烁5次,出现错误闪10次),并在路由中能找到此设备
硬件:
    程序烧录电路图:
      

       usb-ttl:3.3v供电,通过串口1烧录程序。tx接收芯片的rx(p3.0),rx接芯片的tx(p3.1)。
       程序烧录是成功的:

      
   连接esp8266的电路图:
      
       esp8266与芯片的串口2进行通信。tx接到芯片的P1.0(第9脚引),rx接到芯片的P1.1(第10引脚)
程序:
   
#include <STC15.H>
#include <intrins.h>
#include <string.h>

#define FOSC 30000000L    // 主频设为30MHz
#define BAUD 115200         // 波特率115200
#define SIZE 12

#define NONE_PARITY   0       //无校验
#define ODD_PARITY      1       //奇校验
#define EVEN_PARITY   2       //偶校验
#define MARK_PARITY   3       //标记校验
#define SPACE_PARITY    4       //空白校验
#define PARITYBIT NONE_PARITY   //定义校验位

typedef unsigned char BYTE;
typedef unsigned int WORD;

char buffer;
char AT_OK_Flag = 0; //OK返回值的标志位
bit busy;

void delay_ms(unsigned int ms);
void SendData(BYTE dat);
void UART2_SendString(char *s);
void Receive();

/************ UART1配置(P3.0/RxD1, P3.1/TxD1) ************/
void UART1_Init(void)
{
    P3M1 &= ~0x03; P3M0 &= ~0x03; // P3.0/P3.1设为准双向模式
      
    P_SW1 |= 0x00;                // 串口1使用默认的3.0和3.1
   
      SCON = 0x50;      // 8位数据,可变波特率
    AUXR |= 0x40;       // Timer1时钟为FOSC
    AUXR &= 0xFE;       // UART1选择Timer1为波特率发生器
    TMOD &= 0x0F;       // Timer1设为16位自动重载
      TL1 = 0xBF;                        // 波特率115200(当FOSC=30MHz)
      TH1 = 0xFF;
    TR1 = 1;            // 启动Timer1
    ES = 1;             // 使能UART1中断
}

/************ UART2配置(P1.6/RxD2, P1.7/TxD2) ************/
void UART2_Init(void)
{
    P_SW2 |= 0x00;       // 将UART2切换到P1.0(RxD2)和P1.1(TxD2)
   
    S2CON = 0x50;      // 8位数据,可变波特率
      
      T2L = (65536 - (FOSC/4/BAUD));   //设置波特率重装值
    T2H = (65536 - (FOSC/4/BAUD))>>8;
    AUXR = 0x14;                //T2为1T模式, 并启动定时器2
    IE2 = 0x01;               //使能串口2中断
}

/************ 中断服务函数 ************/
void UART1_ISR() interrupt 4
{
    if (RI)
    {
      RI = 0;          // 清除接收中断标志
      // 处理接收数据:SBUF为接收到的字节
               
    }
    if (TI)
    {
      TI = 0;          // 清除发送中断标志
      // 发送完成处理
    }
}

void UART2_ISR() interrupt 8
{
    if (S2CON & 0x01)    // 检测接收中断标志S2RI
    {
      S2CON &= ~0x01;// 清除S2RI
      // 处理接收数据:S2BUF为接收到的字节
                Receive();
    }
    if (S2CON & 0x02)    // 检测发送中断标志S2TI
    {
      S2CON &= ~0x02;// 清除S2TI
      // 发送完成处理
    }
}

/************ ESP826601s初始化函数 ************/
void ESP8266_Init(){
      // 发送AT指令配置ESP8266
    UART2_SendString("AT+RST\r\n");      // 重启模块
      delay_ms(3000);   
      UART2_SendString("AT+UART=115200,8,1,0,0\r\n");      // 设置波特率
    delay_ms(1000);
    UART2_SendString("AT+CWMODE=1\r\n"); // 设置为STA模式
    delay_ms(1000);
    UART2_SendString("AT+CWJAP=\"Route-1302\",\"wg.89702993\"\r\n"); // 连接WiFi
    delay_ms(3000);
    UART2_SendString("AT+CIPSTART=\"TCP\",\"192.168.3.5\",8080\r\n"); // 连接服务器
    delay_ms(3000);
      UART2_SendString("AT+CIPMODE=1\r\n"); // 设置透传
    delay_ms(1000);
      UART2_SendString("AT+CIPSEND\r\n");
      delay_ms(1000);
}

/************ 主函数 ************/
void main()
{
      P00 = 1;
      
      P0M0 = 0x00;
    P0M1 = 0x00;
    P1M0 = 0x00;
    P1M1 = 0x00;
    P2M0 = 0x00;
    P2M1 = 0x00;
    P3M0 = 0x00;
    P3M1 = 0x00;
    P4M0 = 0x00;
    P4M1 = 0x00;
    P5M0 = 0x00;
    P5M1 = 0x00;
    P6M0 = 0x00;
    P6M1 = 0x00;
    P7M0 = 0x00;
    P7M1 = 0x00;

    EA = 1;             // 全局中断使能
      
    UART1_Init();
    UART2_Init();
      ESP8266_Init();
   
    while (1);
}

/************ 延时函数:以毫秒为单位 ************/
void delay_ms(unsigned int ms)      //@30.000MHz
{
      unsigned char data i, j;

      i = 30;
      j = 43;
      while(ms--){
                do
                {
                        while (--j);
                } while (--i);
      }
}

/************ 接收信息 ************/
void Receive(){
      static int i=0; //静态变量,被初始化一次
      int n = 0;

      char tmp = SBUF;
      if(tmp == 'W' || tmp == 'O' || tmp == 'F' || tmp=='L' || tmp == 'E' || tmp == "?"){
                i = 0;
      }
      buffer = tmp;
      //连接服务器等OK返回值指令的判断
      if(buffer == 'O' && buffer == 'K'){
                AT_OK_Flag = 1;
                memset(buffer,'\0',SIZE);
                for(n = 0; n < 2; n++){
                        P00 = 0;
                        delay_ms(200);
                        P00 = 1;
                        delay_ms(200);
                }
      }
      //联网失败出现FAIL字样捕获
      if(buffer == 'F' && buffer == 'A'){
                for(n = 0; n < 5; n++){
                        P00 = 0;
                        delay_ms(200);
                        P00 = 1;
                        delay_ms(200);
                }
                memset(buffer,'\0',SIZE);
      }
      if(buffer=='E' && buffer =='R'){
                for(n = 0; n < 10; n++){
                        P00 = 0;
                        delay_ms(200);
                        P00 = 1;
                        delay_ms(200);
                }
                memset(buffer,'\0',SIZE);
      }
/*      if(buffer=='0' || buffer =='?'){
                for(i=0; i<5; i++){
                        P00 = 0;
                        delay_ms(1000);
                        P00 = 1;
                        delay_ms(1000);
                }
                memset(buffer,'\0',SIZE);
      }
      if(buffer == 'L' && buffer == '1'){
                P00 = 0;
                memset(buffer,'\0',SIZE);
      }
      if(buffer == 'L' && buffer == '0'){
                P00 = 1;
                memset(buffer,'\0',SIZE);
      }      
*/
}

/*----------------------------
发送串口数据
----------------------------*/
void SendData(BYTE dat)
{
    while (busy);               //等待前面的数据发送完成
    ACC = dat;                  //获取校验位P (PSW.0)
    if (P)                      //根据P来设置校验位
    {
#if (PARITYBIT == ODD_PARITY)
      S2CON &= ~S2TB8;      //设置校验位为0
#elif (PARITYBIT == EVEN_PARITY)
      S2CON |= S2TB8;         //设置校验位为1
#endif
    }
    else
    {
#if (PARITYBIT == ODD_PARITY)
      S2CON |= S2TB8;         //设置校验位为1
#elif (PARITYBIT == EVEN_PARITY)
      S2CON &= ~S2TB8;      //设置校验位为0
#endif
    }
    busy = 1;
    S2BUF = ACC;                //写数据到UART2数据寄存器
}

/*----------------------------
发送字符串
----------------------------*/
void UART2_SendString(char *s)
{
    while (*s)                  //检测字符串结束标志
    {
      SendData(*s++);         //发送当前字符
    }
}
我想过好些办法都未解决,请各位大能帮忙看看,谢谢

国芯人工智能 发表于 2025-3-23 23:23:00

针对您在使用STC15W4K48S4与ESP8266进行通信时遇到的问题,以下是一些可能的原因和解决方案:

1. 硬件连接检查
首先,确保ESP8266与STC15W4K48S4的硬件连接正确。根据您的描述,ESP8266的TX应连接到STC15W4K48S4的P1.0,RX应连接到P1.1。请仔细检查这些连接是否正确,并确保没有虚焊或短路现象。

2. 电源供应
ESP8266的工作电压为3.3V,确保您为ESP8266提供了稳定的3.3V电源。如果电源不稳定或电压不足,ESP8266可能无法正常工作。您可以使用电压表测量ESP8266的VCC引脚,确保其在3.3V左右。

3. 串口配置
确保STC15W4K48S4的串口2配置正确。您需要设置正确的波特率、数据位、停止位和校验位。ESP8266默认的AT指令波特率为115200,因此您需要将STC15W4K48S4的串口2配置为相同的波特率。

4. AT指令发送
在程序中,您需要确保STC15W4K48S4通过串口2向ESP8266发送AT指令。以下是一个简单的示例代码,展示如何发送AT指令并接收响应:

c
include
include
include

define ESP8266RX P10
define ESP8266TX P11

void UART2Init(void) {
    SCON2 = 0x50; // 8位数据, 1位停止位, 无校验位
    AUXR |= 0x04; // 定时器1作为波特率发生器
    T2L = 0xE8;   // 波特率115200
    T2H = 0xFF;
    AUXR |= 0x10; // 启动定时器2
}

void UART2SendByte(unsigned char dat) {
    SBUF2 = dat;
    while (!TI2);
    TI2 = 0;
}

void UART2SendString(char s) {
    while (s) {
      UART2SendByte(s++);
    }
}

unsigned char UART2ReceiveByte(void) {
    while (!RI2);
    RI2 = 0;
    return SBUF2;
}

void main(void) {
    UART2Init();
    UART2SendString("AT\r\n"); // 发送AT指令
    while (1) {
      unsigned char response = UART2ReceiveByte();
      // 处理ESP8266的响应
    }
}

5. 调试与日志
建议您使用调试工具或串口助手来监控STC15W4K48S4与ESP8266之间的通信。通过查看实际的AT指令发送和ESP8266的响应,可以更好地定位问题。

6. 固件更新
如果ESP8266的固件版本较旧,可能会导致AT指令无法正常工作。您可以尝试更新ESP8266的固件到最新版本。

7. 路由器配置
确保您的路由器允许新设备接入,并且没有启用MAC地址过滤等安全措施,这些可能会阻止ESP8266连接到网络。

通过以上步骤,您应该能够解决STC15W4K48S4与ESP8266通信中的问题。如果问题仍然存在,建议进一步检查硬件和软件配置,或寻求更专业的支持。

[本文内容由国芯人工智能辅助生成,仅供参考]

ercircle 发表于 2025-3-24 08:27:31

这种需求一般先分开调试,
1.串口工具连接串口2是否有报文输出
2.用串口工具给esp8266发这些AT指令是否能正常工作
3.才是组合联调

ercircle 发表于 2025-3-24 08:43:13

代码里的问题:
1.AT发送这里语法问题,字符串拼接里面有"应该用\",否则编译报错
    UART2_SendString("AT+CWJAP=\"Route-1302\",\"wg.89702993\"\r\n"); // 连接WiFi
    delay_ms(3000);
    UART2_SendString("AT+CIPSTART=\"TCP\",\"192.168.3.5\",8080\r\n"); // 连接服务器

2.串口2发送中断里没有及时清除busy状态,只能能出去一个字符
void UART2_ISR() interrupt 8
{
    if (S2CON & 0x01)    // 检测接收中断标志S2RI
    {
      S2CON &= ~0x01;// 清除S2RI
      // 处理接收数据:S2BUF为接收到的字节
                Receive();
    }
    if (S2CON & 0x02)    // 检测发送中断标志S2TI
    {
      S2CON &= ~0x02;// 清除S2TI
                        busy = 0;
      // 发送完成处理
    }
}

wg2993 发表于 2025-3-24 23:51:23

ercircle 发表于 2025-3-24 08:43
代码里的问题:
1.AT发送这里语法问题,字符串拼接里面有"应该用\",否则编译报错
    UART2_SendString("A ...

谢谢你提供的思路。引号\"原本是有的,复制出来不知怎样就没了。busy的问题已改。现通过芯片的uart2发送的内容如下:
AT+RST
AT+UART=115200,8,1,0,0
AT+CWMODE=1
AT+CWJAP="Route-1302","12345678"
AT+CIPSTART="TCP","192.168.3.5",8080
AT+CIPMODE=1
AT+CIPSEND

将esp826601s连接到芯片的uart2上,不停地闪烁蓝光,路由器中看到不此设备

wg2993 发表于 2025-3-24 23:52:39

国芯人工智能 发表于 2025-3-23 23:23
针对您在使用STC15W4K48S4与ESP8266进行通信时遇到的问题,以下是一些可能的原因和解决方案:

1. 硬件连接 ...

谢谢哦

ercircle 发表于 2025-3-25 08:56:05

wg2993 发表于 2025-3-24 23:51
谢谢你提供的思路。引号\"原本是有的,复制出来不知怎样就没了。busy的问题已改。现通过芯片的uart2发送 ...

直接用串口工具连接esp8266逐条测试AT指令是否正确执行

wg2993 发表于 2025-3-25 23:05:12

ercircle 发表于 2025-3-25 08:56
直接用串口工具连接esp8266逐条测试AT指令是否正确执行

直接用串口工具连接esp8266逐条测试AT指令是能正确执行的,但将esp826601s与芯片连接就不行了

ercircle 发表于 2025-3-25 23:09:49

wg2993 发表于 2025-3-25 23:05
直接用串口工具连接esp8266逐条测试AT指令是能正确执行的,但将esp826601s与芯片连接就不行了 ...

一个串口和ESP8266通讯,用另一个串口将回复内容传到电脑上,和正常报文对比下,一步一步排查
页: [1]
查看完整版本: 15W4K48S4+ESP8266实现通信时遇到问题