当前位置: 首页 > news >正文

基于HAL库实现CAN通信RS485通信WIFI模块和4G模块的AT指令和TCP透传

1.基于HAL库实现CAN通信

        Controller Area Network,控制器局域网,是市场上应用最广泛的现场总线之一。下面我们来看看基于HAL库实现CAN总线通信的配置和程序:

void CANFilter_Init(void)//can过滤器初始化
{CAN_FilterTypeDef sFilterConfig;sFilterConfig.FilterBank = 0;                       //CAN过滤器编号,范围0-27sFilterConfig.FilterMode = CAN_FILTERMODE_IDMASK;   //CAN过滤器模式,掩码模式或列表模式sFilterConfig.FilterScale = CAN_FILTERSCALE_32BIT;  //CAN过滤器尺度,16位或32位sFilterConfig.FilterIdHigh = 0x000 << 5;            //32位下,存储要过滤ID的高16位sFilterConfig.FilterIdLow = 0x0000;                 //32位下,存储要过滤ID的低16位sFilterConfig.FilterMaskIdHigh = 0x0000;            //掩码模式下,存储的是掩码sFilterConfig.FilterMaskIdLow = 0x0000;sFilterConfig.FilterFIFOAssignment = 0; //报文通过过滤器的匹配后,存储到哪个FIFOsFilterConfig.FilterActivation = ENABLE;            //激活过滤器sFilterConfig.SlaveStartFilterBank = 0;if (HAL_CAN_ConfigFilter(&hcan, &sFilterConfig) != HAL_OK){Error_Handler();}
}void CAN_Start_Init(void)//can开始初始化
{if (HAL_CAN_Start(&hcan) != HAL_OK){Error_Handler();}/* 3. Enable CAN RX Interrupt */if (HAL_CAN_ActivateNotification(&hcan, CAN_IT_RX_FIFO0_MSG_PENDING) != HAL_OK) {Error_Handler();}
}uint8_t RX_Message[8] = {0}; // 接收消息的数组
CAN_RxHeaderTypeDef RX_Header; // 接收数据包头
void HAL_CAN_RxFifo0MsgPendingCallback(CAN_HandleTypeDef *hcan)
{if(hcan->Instance == CAN1){if( HAL_CAN_GetRxMessage(hcan,CAN_RX_FIFO0,&RX_Header,RX_Message) == HAL_OK){printf("%#x:",RX_Header.StdId);HAL_UART_Transmit(&huart1,RX_Message,8,HAL_MAX_DELAY);}}
}void CAN_Test(void)
{uint8_t TX_Message[8]={1,2,3,4,5,6,7,8}; //can发送数据缓冲区uint32_t pTxMailbox;CAN_TxHeaderTypeDef TX_Header;TX_Header.IDE = CAN_ID_STD;              //标准帧 TX_Header.StdId = 0x12;                  //id号TX_Header.RTR = CAN_RTR_DATA;            //数据帧TX_Header.DLC = 8;                       //字节数if(HAL_CAN_AddTxMessage(&hcan, &TX_Header,TX_Message, &pTxMailbox) != HAL_OK){Error_Handler();}HAL_Delay(5000);
}

我们通过配置CAN过滤器和在CAN初始化函数中对两个函数是否完成的读取来处理错误确保CAN总线的通信正常实现。在Test函数中通过配置帧格式来进行can的发送。

2.基于HAL库实现RS485通信

        我们使用的是通过串口转485芯片来实现在硬件上485通信。具体实现看下面的配置和程序:

void HAL_UART_RxHalfCpltCallback(UART_HandleTypeDef *huart)
{if(huart->Instance == USART1){uint8_t Length = DMA_BUF_SIZE/2 - RX1_Offset;HAL_GPIO_WritePin(RS485_RW_GPIO_Port,RS485_RW_Pin,GPIO_PIN_SET);     //将控制rs485的发送接收引脚的GPIO口置高,启用发送模式HAL_UART_Transmit(&huart2,RX1_Buf+RX1_Offset,Length,HAL_MAX_DELAY);  //将串口1接收的数据通过串口2发送出去,在硬件上再转化为485通信发送出去HAL_GPIO_WritePin(RS485_RW_GPIO_Port,RS485_RW_Pin,GPIO_PIN_RESET);   //再将控制rs485的发送接收引脚的GPIO口置低,回到默认的接收模式//printf("HLength=%d\n",Length);RX1_Offset+=Length;}else if(huart->Instance == USART2){uint8_t Length = DMA_BUF_SIZE/2 - RX2_Offset;HAL_UART_Transmit(&huart1,RX2_Buf+RX2_Offset,Length,HAL_MAX_DELAY);  //将串口2接收的数据(即通过rs485通信接收到数据后,再通过转化芯片转换到串口2接收后的数据)//printf("HLength=%d\n",Length);                                     //通过串口1发送出去RX2_Offset+=Length;}
}//DMA接收满中断
void HAL_UART_RxCpltCallback(UART_HandleTypeDef *huart)
{if(huart->Instance == USART1){uint8_t Length = DMA_BUF_SIZE - RX1_Offset;HAL_GPIO_WritePin(RS485_RW_GPIO_Port,RS485_RW_Pin,GPIO_PIN_SET);     //将控制rs485的发送接收引脚的GPIO口置高,启用发送模式HAL_UART_Transmit(&huart2,RX1_Buf+RX1_Offset,Length,HAL_MAX_DELAY);  //将串口1接收的数据通过串口2发送出去,在硬件上再转化为485通信发送出去HAL_GPIO_WritePin(RS485_RW_GPIO_Port,RS485_RW_Pin,GPIO_PIN_RESET);   //再将控制rs485的发送接收引脚的GPIO口置低,回到默认的接收模式//printf("CLength=%d\n",Length);RX1_Offset = 0;}else if(huart->Instance == USART2){uint8_t Length = DMA_BUF_SIZE - RX2_Offset;HAL_UART_Transmit(&huart1,RX2_Buf+RX2_Offset,Length,HAL_MAX_DELAY);  //将串口2接收的数据(即通过rs485通信接收到数据后,再通过转化芯片转换到串口2接收后的数据)//printf("HLength=%d\n",Length);                                     //通过串口1发送出去RX2_Offset = 0;}
}void USER_UART_IRQHandler(UART_HandleTypeDef *huart)
{if(huart->Instance == USART1){//用来消除噪声对传输数据的影响if((__HAL_UART_GET_FLAG(huart, UART_FLAG_FE) ||__HAL_UART_GET_FLAG(huart, UART_FLAG_NE) )== SET ) //判断是否是帧错误或者噪音中断{__HAL_UART_CLEAR_FLAG(huart, UART_FLAG_FE);__HAL_UART_CLEAR_FLAG(huart, UART_FLAG_NE);huart->ErrorCode &= HAL_UART_ERROR_FE; // 清除错误标志位huart->ErrorCode &= HAL_UART_ERROR_NE; // 清除错误标志位HAL_UART_DMAStop(huart); // 关闭DMAHAL_UART_Receive_DMA(huart,RX1_Buf,DMA_BUF_SIZE);// 重新启动DMA}if(__HAL_UART_GET_FLAG(huart,UART_FLAG_IDLE)!=RESET)   //判断是否发生空闲中断{__HAL_UART_CLEAR_IDLEFLAG(huart);                    //清空空闲中断标志位 uint8_t Length = DMA_BUF_SIZE - __HAL_DMA_GET_COUNTER(&hdma_usart1_rx) - RX1_Offset;   //接收到的数据的长度HAL_GPIO_WritePin(RS485_RW_GPIO_Port,RS485_RW_Pin,GPIO_PIN_SET);     //将控制rs485的发送接收引脚的GPIO口置高,启用发送模式HAL_UART_Transmit(&huart2,RX1_Buf+RX1_Offset,Length,HAL_MAX_DELAY);HAL_GPIO_WritePin(RS485_RW_GPIO_Port,RS485_RW_Pin,GPIO_PIN_RESET);   //再将控制rs485的发送接收引脚的GPIO口置低,回到默认的接收模式RX1_Offset += Length;//printf("ILength=%d\n",Length);}}if(huart->Instance == USART1){//用来消除噪声对传输数据的影响if((__HAL_UART_GET_FLAG(huart, UART_FLAG_FE) ||__HAL_UART_GET_FLAG(huart, UART_FLAG_NE) )== SET ) //判断是否是帧错误或者噪音中断{__HAL_UART_CLEAR_FLAG(huart, UART_FLAG_FE);__HAL_UART_CLEAR_FLAG(huart, UART_FLAG_NE);huart->ErrorCode &= HAL_UART_ERROR_FE; // 清除错误标志位huart->ErrorCode &= HAL_UART_ERROR_NE; // 清除错误标志位HAL_UART_DMAStop(huart); // 关闭DMAHAL_UART_Receive_DMA(huart,RX1_Buf,DMA_BUF_SIZE);// 重新启动DMA}if(__HAL_UART_GET_FLAG(huart,UART_FLAG_IDLE)!=RESET)   //判断是否发生空闲中断{__HAL_UART_CLEAR_IDLEFLAG(huart);                    //清空空闲中断标志位 uint8_t Length = DMA_BUF_SIZE - __HAL_DMA_GET_COUNTER(&hdma_usart1_rx) - RX1_Offset;   //接收到的数据的长度HAL_GPIO_WritePin(RS485_RW_GPIO_Port,RS485_RW_Pin,GPIO_PIN_SET);     //将控制rs485的发送接收引脚的GPIO口置高,启用发送模式HAL_UART_Transmit(&huart2,RX1_Buf+RX1_Offset,Length,HAL_MAX_DELAY);HAL_GPIO_WritePin(RS485_RW_GPIO_Port,RS485_RW_Pin,GPIO_PIN_RESET);   //再将控制rs485的发送接收引脚的GPIO口置低,回到默认的接收模式RX1_Offset += Length;//printf("ILength=%d\n",Length);}}
}

采用的是MCU通过串口将数据发出,通过串口转485芯片实现485通信,485接收到的数据则通过485转串口芯片来与MCU通信。

3.基于HAL库实现wifi模块tcp透传

        我们采用串口给wifi模块发送AT指令来使wifi模块进入透传模式,wifi模块返回给我们的数据用循环队列作为接收缓冲区来接收。我们先来看循环队列的相关程序:

#ifndef __FIFO_H
#define __FIFO_H#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <stdint.h>#define NSize 256typedef struct
{uint8_t data[NSize]; // 用数组作为队列的储存空间int32_t front;       // 指示队头位置int32_t rear;        // 指示队尾位置
} sequeue_t;
extern sequeue_t QUART3;int8_t Queue_Init(sequeue_t *q);
uint16_t Queue_Size(sequeue_t *q);
int8_t Queue_IsEmpty(sequeue_t *q);
int8_t Enqueue(sequeue_t *q, uint8_t value);
int8_t Dequeue(sequeue_t *q, uint8_t *pvalue);
int8_t Enqueue_Bytes(sequeue_t *q, uint8_t *pvalue, uint32_t Size);
#endif#include "fifo.h"
#include <stdlib.h>// 循环队列关于满和空的理解
// 空 : 队头和队尾相等就是空
// 满 : 数组元素个数减一/** 为区别空队和满队,满队元素个数比数组元素个数少一个。* 满队 队尾+1 == 队头 ,数组空了一个元素, 因此满队比数组少一个元素*/sequeue_t QUART3; // 单片机中尽量不使用malloc函数,
int8_t Queue_Init(sequeue_t *q)
{q->front = q->rear = NSize - 1; // 指向数组的最后一个元素 , 原因入队队尾加, 出队队头加memset(q->data, 0, NSize);return 0;
}uint16_t Queue_Size(sequeue_t *q)
{if (q->rear >= q->front){return q->rear - q->front;}else{return NSize - q->front + q->rear;}
}// 空队 队头等于队尾
int8_t Queue_IsEmpty(sequeue_t *q)
{return (q->front == q->rear);
}int Queue_IsFull(sequeue_t *q)
{// 队尾 +1 == 队头 , 就是满队// 任何一个一个数对N求余 , 这个数的范围是  0 - N-1return ((q->rear + 1) % NSize == q->front);
}// 入队  , 队尾加
int8_t Enqueue(sequeue_t *q, uint8_t value)
{if (Queue_IsFull(q)){printf("queue is full\n");return -1;}q->rear = (q->rear + 1) % NSize; // 数组下标的移动范围 0 到N-1q->data[q->rear] = value;return 0;
}// 出队 , 队头加
int8_t Dequeue(sequeue_t *q, uint8_t *pvalue)
{if (Queue_IsEmpty(q)){// printf("empty\n");return -1;}q->front = (q->front + 1) % NSize; // 数组下标的移动范围 0 到N-1*pvalue = q->data[q->front];return 0;
}int8_t Enqueue_Bytes(sequeue_t *q, uint8_t *pvalue, uint32_t Size)
{for (uint16_t i = 0; i < Size; i++, pvalue++){if (Enqueue(q, *pvalue) < 0){return -1;}}return 0;
}

可见对于循环队列的使用是较为简单的,主要实现的就是判断空满,入队出队操作。下面我们来看实现WiFi模块tcp透传的程序:

#ifndef __WIFI4G_H
#define __WIFI4G_H
#include <stdint.h>
#include "main.h"
#include "fifo.h"enum
{WIFI4G_NOT = 0, // Not foundWIFI4G_OK,WIFI4G_ERROR
};extern __IO uint8_t WIFI4G_CMD_Status; // OK状态标志位extern uint8_t Parse_Substr[];uint8_t Test_WIFI4G_CMD_Status(uint32_t Timeout);
uint8_t WIFI4G_Parse_Queue(sequeue_t *sq);
uint8_t ESP8266_Connect_WIFI(void);
void ESP8266_Init(void);
void ESP8266_Test(void);#endif#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <stdint.h>#include "stm32f1xx_it.h"
#include "wifi4g.h"
#include "main.h"
#include "usart.h"
#include "oled.h"
#include "gpio.h"
#include "fifo.h"#pragma diag_suppress 870__IO uint8_t WIFI4G_CMD_Status = 0;	   // 命令执行结果的状态标志位
__IO uint8_t WIFI4G_TouChuan_Flag = 0; // 透传标志uint8_t Parse_Substr[32] = {0}; // 用来判断指令成功的状态uint8_t Test_WIFI4G_CMD_Status(uint32_t Timeout)
{while (WIFI4G_CMD_Status == WIFI4G_NOT) // 没找到继续找{if ((Timeout--) == 0)return WIFI4G_NOT; // 超时时间到 , 函数返回HAL_Delay(1);}return WIFI4G_CMD_Status;
}// 这里要使用一个全局变量 Parse_Substr, 表示要解析的数组
uint8_t RecvBuf[NSize] = {0};
uint8_t WIFI4G_Parse_Queue(sequeue_t *sq)
{// memset(RecvBuf,0,NSize);// 把队列中的数据导出到数组内, 便于进行搜索if (sq != NULL){int32_t i = 0;while (!Queue_IsEmpty(sq)){Dequeue(sq, RecvBuf + i);HAL_UART_Transmit(&huart1,RecvBuf+i, 1,1000); //  把收到的数据进行转发i++;}RecvBuf[i] = 0;}// printf("RecvBuf:%s\n",RecvBuf);if (strstr((const char *)RecvBuf, (const char *)Parse_Substr) != NULL) // 找到单词 返回单词的位置{// printf("found Parse_Substr:%s\n",Parse_Substr);return WIFI4G_OK; // 找到 指令返回OK}else if (strstr((const char *)RecvBuf, (const char *)"ERROR\r\n") != NULL){// printf("found Parse_Substr:%s\n","ERROR");return WIFI4G_ERROR; // 找到指令返回ERROR}else{// printf("not found Parse_Substr:%s\n",Parse_Substr);return WIFI4G_NOT; // 没找到返回假}
}void ESP8266_Init(void)
{if (ESP8266_Connect_WIFI() == SET){printf("WIFI已链接 \n");}
}uint8_t ESP8266_Connect_WIFI(void)
{uint8_t buf[64] = {0};uint8_t ret;printf("******************************************\n");strcpy((char *)Parse_Substr, "OK\r\n");WIFI4G_CMD_Status = WIFI4G_NOT; // 初始化标志位strcpy((char *)buf, "AT+CWMODE=1\r\n"); // 设置无线网卡模式HAL_UART_Transmit(&huart3, buf, strlen((char *)buf), 1000);if (Test_WIFI4G_CMD_Status(1000) == WIFI4G_ERROR){OLED_ShowStr(112, 2, (unsigned char *)"--", 2); // 测试8*16字符return RESET;									// 指令执行失败}// 链接WIFI,成功后立即返回, 失败后使用SmartConfig 配置新的WIFIprintf("******************************************\n");strcpy((char *)buf, "AT+CWJAP\r\n"); // 接至上次 Wi-Fi 配置中的 APstrcpy((char *)Parse_Substr, "OK\r\n");WIFI4G_CMD_Status = WIFI4G_NOT; // 初始化标志位HAL_UART_Transmit(&huart3, buf, strlen((char *)buf), 1000);// 找到指定的字符, wifi链接成功, 超时时间20秒ret = Test_WIFI4G_CMD_Status(20 * 1000);if (ret == WIFI4G_OK){OLED_ShowStr(0, 2, (unsigned char *)"WIFI          OK", 2); // 测试8*16字符return SET;													// wifi 链接成功,函数返回}else if (ret == WIFI4G_NOT) // 指令执行无结果{return RESET;}else // ERROR{// 执行到这里, WIFI链接失败,需要重新配置新的WIFIprintf("******************************************\n");OLED_ShowStr(112, 2, (unsigned char *)"--", 2); // 测试8*16字符printf("没有链接wifi,需要链接wifi,请打开airkiss小程序 \r\n");strcpy((char *)Parse_Substr, "smartconfig connected wifi\r\n");WIFI4G_CMD_Status = WIFI4G_NOT; // 初始化标志位// 手机热点设置为WPA2 ,AT命令使用 AT+CWSTARTSMART=3,3strcpy((char *)buf, "AT+CWSTARTSMART=3,3\r\n");OLED_ShowStr(0, 2, (unsigned char *)"AT+CWSTARTSMART", 2); // 测试8*16字符HAL_UART_Transmit(&huart3, buf, strlen((char *)buf), 1000);// 找到指定的字符,超时时间200秒 ,ret = Test_WIFI4G_CMD_Status(200 * 1000);printf("ret=%d\n", ret);if (ret == WIFI4G_OK) // 链接上wifi{OLED_ShowStr(0, 2, (unsigned char *)"WIFI          OK", 2); // 测试8*16字符printf("关闭smartconfig\r\n");// 关闭 smartconfigstrcpy((char *)Parse_Substr, "OK\r\n");strcpy((char *)buf, "AT+CWSTOPSMART\r\n");OLED_ShowStr(0, 2, (unsigned char *)"AT+CWSTOPSMART", 2); // 测试8*16字符HAL_UART_Transmit(&huart3, buf, strlen((char *)buf), 1000);if (Test_WIFI4G_CMD_Status(1000) == WIFI4G_ERROR){OLED_ShowStr(112, 2, (unsigned char *)"--", 2); // 测试8*16字符return RESET;									// 指令执行失败}OLED_ShowStr(0, 2, (unsigned char *)"WIFI          OK", 2); // 测试8*16字符return SET;													// wifi 链接成功,函数返回}}return SET;
}
uint8_t ESP8266_Connect_TCPServer(void)
{uint8_t buf[64] = {0};WIFI4G_CMD_Status = WIFI4G_NOT;			// 初始化标志位strcpy((char *)buf, "AT+CIPMUX=0\r\n"); // 单链接HAL_UART_Transmit(&huart3, buf, strlen((char *)buf), 1000);OLED_ShowStr(0, 4, (unsigned char *)"AT+CIPMUX", 2); // 测试8*16字符if (Test_WIFI4G_CMD_Status(1000) == WIFI4G_ERROR){OLED_ShowStr(0, 4, (unsigned char *)"TouChuan...   --", 2); // 测试8*16字符return RESET;												// 等待OK返回}WIFI4G_CMD_Status = WIFI4G_NOT;			 // 初始化标志位strcpy((char *)buf, "AT+CIPMODE=1\r\n"); // 设置透传模式HAL_UART_Transmit(&huart3, buf, strlen((char *)buf), 1000);OLED_ShowStr(0, 4, (unsigned char *)"AT+CIPMODE=1", 2); // 测试8*16字符if (Test_WIFI4G_CMD_Status(1000) == WIFI4G_ERROR){OLED_ShowStr(0, 4, (unsigned char *)"TouChuan...   --", 2); // 测试8*16字符return RESET;												// 等待OK返回}WIFI4G_CMD_Status = WIFI4G_NOT; // 初始化标志位// strcpy((char *)buf,"AT+CIPSTART=\"TCP\",\"172.20.10.11\",8000\r\n");strcpy((char *)buf, "AT+CIPSTART=\"TCP\",\"192.168.5.187\",8000\r\n");HAL_UART_Transmit(&huart3, buf, strlen((char *)buf), 1000);OLED_ShowStr(0, 4, (unsigned char *)"AT+CIPSTART", 2); // 测试8*16字符// 找到指定的字符, wifi链接成功, 超时时间20秒uint8_t ret = Test_WIFI4G_CMD_Status(20 * 1000);if (ret == WIFI4G_OK) // 连接到服务器{strcpy((char *)buf, "AT+CIPSEND\r\n"); // 发送数据 , 开启透传HAL_UART_Transmit(&huart3, buf, strlen((char *)buf), 1000);OLED_ShowStr(0, 4, (unsigned char *)"TouChuan...   OK", 2); // 测试8*16字符OLED_ShowStr(0, 6, (unsigned char *)"Exit TouChuan --", 2); // 测试8*16字符WIFI4G_TouChuan_Flag = 1; //  设置透传标志return SET;}else // ERROR  没有连接到服务器,需要重新连接{OLED_ShowStr(0, 6, (unsigned char *)"TouChuan --", 2); // 测试8*16字符return RESET;}
}void ESP8266_Disconnect(void)
{uint8_t buf[64] = {0};WIFI4G_CMD_Status = WIFI4G_NOT; // 初始化标志位strcpy((char *)buf, "+++");HAL_UART_Transmit(&huart3, buf, strlen((const char *)buf), 1000);OLED_ShowStr(0, 6, (unsigned char *)"+++         ", 2); // 测试8*16字符HAL_Delay(100);OLED_ShowStr(0, 6, (unsigned char *)"Exit TouChuan", 2); // 测试8*16字符printf("Exit TouChuan\n");strcpy((char *)buf, "AT+CIPCLOSE\r\n"); // 关闭连接HAL_UART_Transmit(&huart3, buf, strlen((char *)buf), 1000);WIFI4G_CMD_Status = WIFI4G_NOT; // 初始化标志位if (Test_WIFI4G_CMD_Status(1000) == WIFI4G_ERROR){OLED_ShowStr(0, 6, (unsigned char *)"Exit TouChuan --", 2); // 测试8*16字符return;														// 等待OK返回}OLED_ShowStr(0, 6, (unsigned char *)"Exit TouChuan OK", 2); // 测试8*16字符OLED_ShowStr(0, 4, (unsigned char *)"TouChuan...   --", 2); // 测试8*16字符// 防止在透传模式下再次按下OK 按键, 做一个标志WIFI4G_TouChuan_Flag = 0; // 退出透传模式
}void ESP8266_Test(void)
{if (Key_Value == KEY_OK) // OK 按键 连接服务器{Key_Value = 0;if (WIFI4G_TouChuan_Flag == 0) // 在非透传模式下连接设置透传{ESP8266_Connect_TCPServer();}}else if (Key_Value == KEY_ESC) // ESC按键 退出透传并断开连接{Key_Value = 0;ESP8266_Disconnect();}HAL_Delay(200);
}

大体上的程序实现就是通过串口发送AT指令给wifi模块来控制wifi模块执行相应的命令,然后接收wifi模块给我们返回的字符串也就是信息来判断是否那个发送的指令是否成功执行或没有成执行。

4.基于HAL库实现4G模块tcp透传

        4G模块也是常用的无线通信模块,下面我们来看实现tcp透传的程序:

uint8_t ML307_Connect_TCPServer(void)
{uint8_t buf[64]={0};/*******************************************************/WIFI4G_CMD_Status = WIFI4G_NOT ; // 初始化标志位strcpy((char *)Parse_Substr,"OK\r\n"); // 检查网络连接是否成功strcpy((char *)buf,"AT+DTUTASK=\"1\",\"10\"\r\n");HAL_UART_Transmit(&huart3,buf,strlen((char *)buf),1000);if(Test_WIFI4G_CMD_Status(10*1000) == WIFI4G_ERROR) {return RESET; // 等待OK返回}/*******************************************************/WIFI4G_CMD_Status = WIFI4G_NOT ; // 初始化标志位strcpy((char *)Parse_Substr,"OK\r\n"); // 检查网络连接是否成功strcpy((char *)buf,"AT+SOCK=1,1,\"8.135.10.183\",31160,0\r\n"); // 设置透传模式HAL_UART_Transmit(&huart3,buf,strlen((char *)buf),1000);if(Test_WIFI4G_CMD_Status(1000) == WIFI4G_ERROR) {return RESET ; // 等待OK返回}/*******************************************************/WIFI4G_CMD_Status = WIFI4G_NOT ; // 初始化标志位strcpy((char *)Parse_Substr,"OK\r\n"); // 检查网络连接是否成功strcpy((char *)buf,"AT+REST\r\n"); // 设置透传模式HAL_UART_Transmit(&huart3,buf,strlen((char *)buf),1000);if(Test_WIFI4G_CMD_Status(1000) == WIFI4G_ERROR) {return RESET ; // 等待OK返回}/*******************************************************/OLED_ShowStr(0,4,(unsigned char *)"TouChuan... OK",2);//测试8*16字符WIFI4G_TouChuan_Flag = 1 ; // 设置透传标志return SET;
}void ML307_Test(void)
{if(Key_Value == KEY_OK) // OK 按键 连接服务器{Key_Value = 0 ;if(WIFI4G_TouChuan_Flag == 0) // 在非透传模式下连接设置透传{printf("ML307_Connect_Server()\n");ML307_Connect_TCPServer();}else{printf("TCPServer Connected\n");}}HAL_Delay(200);
}

与wifi模块相同4g模块也是采用的串口来使MCU与4g模块间进行通信,采用的也是对应的AT指令集。

http://www.dtcms.com/a/585652.html

相关文章:

  • 采购网站有哪些东莞百度推广优化排名
  • 黄石网站设计公司网站都必须要备案吗
  • 36.华为云计算类服务实践
  • 长沙网站制作合作商网站更改文章标题
  • 【赵渝强老师】使用Helm简化Kubernetes(K8s)应用的部署和管理
  • 网页设计与制作教程期末考试东莞网络优化公司排名
  • docker打包,启动java程序
  • Debian 13 安装 Kubernetes 最新版 并使用 containerd 运行时
  • 通过操作地址,来进行STM32的写入GPIO端口值
  • 压力测试详解
  • 网站 怎么备案佛山营销型网站设计
  • 网站关键字被百度收录外链群发
  • Qt点击信号全解析:QTreeWidget交互指南
  • C++ 头文件:语言功能的 “模块化工具箱”(第三章)
  • 系统架构设计师学习大纲目录
  • 网站建设百度推广说词网站服务器在本地是指
  • Highcharts 3D图:深入解析与实际应用
  • 全景图制作工具( 10 种)
  • 虚拟位置映射(标签鸽
  • Pytorch 学习之Transforms
  • 中国建设银行网站的社保板块在哪里徐州专业网站制作公司
  • 免费建立移动网站吗模拟百度搜索词进入网站
  • Windows 如何安装 Chocolatey
  • 江苏高端网站建设一个网站怎么赚钱
  • 鸿蒙 ArkTS 入门教程:小白实战 List 列表开发(详解 @State, ForEach, @Builder)
  • Redis_8_List
  • excel VBA应用
  • 第十六章 SDN与NFV概述
  • C++ STL:阅读list源码|list类模拟|优化构造|优化const迭代器|优化迭代器模板|附源码
  • 《uni-app跨平台开发完全指南》- 05 - 基础组件使用