郞性人生

导航

在状态机中设置超时

1.用枚举类型生成一个状态机;

2.当状态机为过程状态机,最终需要到达某个确定的状态,而中间状态需要设计状态超时时要对整个状态机进行超时设计;

eg.

1.AT指令操作WiFi模块;

//WIFI状态机状态定义
typedef enum _WIFI_STATUS
{
    WIFI_DISCONNECT,
    WIFI_RESET_OK,
    WIFI_AT_OK,
    WIFI_CWMODE_OK,
    WIFI_CWDHCP_OK,
    WIFI_CIPSTA_OK,
    WIFI_CWJAP_OK,
    WIFI_CIPMUX_OK,
    WIFI_CIPSTART_OK,
    WIFI_CIPMODE_OK,
    WIFI_CIPSEND_OK,
    WIFI_EXIT_AT,
} eWIFI_STATUS_T;


static void wifi_send(void)
{
    static uint8_t  repeat_send = 0;

    //状态机超时计数
    if (WIFI_STATUS != WIFI_CIPSEND_OK)
    {
        repeat_send+=1;
    }
    if (repeat_send>15)
    {
        repeat_send = 0;
        WIFI_STATUS = WIFI_EXIT_AT;
    }
    //状态机状态处理
    switch(WIFI_STATUS)
    {

    case    WIFI_DISCONNECT:
        WIFISend_str("AT+RST\r\n");
        vTaskDelay(5000);
        WIFI_STATUS = WIFI_RESET_OK;
        break;
    case    WIFI_RESET_OK:
        xTimerChangePeriod( xTimers[5], (200), portMAX_DELAY );
        WIFISend_str("AT\r\n");
        vTaskDelay(500);
        break;
    case    WIFI_AT_OK:
        WIFISend_str("AT+CWMODE=1\r\n");
        vTaskDelay(500);
        break;
    case    WIFI_CWMODE_OK:
        WIFISend_str("AT+CWDHCP=1,0\r\n");
        vTaskDelay(500);
        break;
    case    WIFI_CWDHCP_OK:
        WIFISend_str((uint8_t *)AT_CIPSTA);
        vTaskDelay(500);
        break;
    case    WIFI_CIPSTA_OK:
        WIFISend_str((uint8_t *)AT_CWJAP);
        vTaskDelay(10000);
        break;
    case   WIFI_CWJAP_OK:
        WIFISend_str("AT+CIPMUX=0\r\n");
        vTaskDelay(500);
        break;
    case    WIFI_CIPMUX_OK:
        WIFISend_str("AT+CIPSTART=\"TCP\",\"mqtt.zsp-tech.com\",1883\r\n");
        vTaskDelay(15000);
        break;
    case    WIFI_CIPSTART_OK:
        WIFISend_str("AT+CIPMODE=1\r\n");
        vTaskDelay(500);
        break;
    case    WIFI_CIPMODE_OK:
        WIFISend_str("AT+CIPSEND\r\n");
        vTaskDelay(500);
        break;
    case    WIFI_CIPSEND_OK:
        PortMQTTSend();
        break;
    case    WIFI_EXIT_AT:
        repeat_send = 0;
        WIFISend_str("+++");
        vTaskDelay(1500);
        WIFISend_str("+++");
        vTaskDelay(1500);
        WIFISend_str("AT+CIPCLOSE\r\n");
        vTaskDelay(1500);
        MQTTStatus = PORT_MQTT_DISCONNECT;
        xTimerChangePeriod( xTimers[5], (200), portMAX_DELAY );
        WIFI_STATUS = WIFI_DISCONNECT;
        break;
    }
}
View Code

2.AT指令操作GPRS模块:

//GPRS 状态定义
typedef enum _GPRS_STATUS
{
    GPRS_DISCONNECT,
    GPRS_RESET_OK,
    GPRS_OK,
    GPRS_HEART_OK,
    GPRS_SRVHEART_OK,
    GPRS_INDE_OK,
    GPRS_UDPM_OK,
    GPRS_DELAY_OK,
    GPRS_DATA_T_OK,
    GPRS_CONNECT,
    GPRS_EXIT_AT,
} eGPRS_STATUS_T;


static void gprs_send(void)
{
    uint8_t static GPRS_DATA_T_OK_count = 0;
    //状态计数
    if (GPRS_STATUS != GPRS_CONNECT)
    {
        GPRS_DATA_T_OK_count++;
    }
    //超时处理
    if (GPRS_DATA_T_OK_count>15)
    {
        GPRS_STATUS = GPRS_EXIT_AT;
        GPRS_DATA_T_OK_count = 0;
    }
    //状态处理
    switch(GPRS_STATUS)
    {
    case    GPRS_DISCONNECT:
        MQTTStatus = PORT_MQTT_DISCONNECT;
        GPRS_UART_RS485Send_str("+++");
        vTaskDelay(500);
        GPRS_UART_RS485Send_str("AT^RESET\r\n");
        vTaskDelay(20000);
        break;
    case    GPRS_RESET_OK:
        xTimerChangePeriod( xTimers[5], (200), portMAX_DELAY );
        GPRS_UART_RS485Send_str("AT\r\n");
        vTaskDelay(500);
        break;
    case    GPRS_OK:
        GPRS_UART_RS485Send_str("AT^HEART=0\r\n");
        break;
    case     GPRS_HEART_OK:
        GPRS_UART_RS485Send_str("AT^SRVHEART=60\r\n");
        break;
    case GPRS_SRVHEART_OK:
        GPRS_UART_RS485Send_str("AT^INDE=1\r\n");
        vTaskDelay(500);
        break;
    case    GPRS_INDE_OK:
        GPRS_UART_RS485Send_str("AT^UDPM=0\r\n");
        vTaskDelay(500);
        break;
    case    GPRS_UDPM_OK:
        GPRS_UART_RS485Send_str("AT^DELAY=0=0\r\n");
        vTaskDelay(500);
        break;
    case    GPRS_DELAY_OK:
        GPRS_UART_RS485Send_str((uint8_t *)MQTTServer);
        vTaskDelay(500);
        break;
    case    GPRS_DATA_T_OK:
        GPRS_UART_RS485Send_str("AT^GPRS\r\n");
        vTaskDelay(15000);
        break;
    case    GPRS_CONNECT:    //GPRS与服务器建立TCP连接成功
        PortMQTTSend();
        break;
    case GPRS_EXIT_AT:
        GPRS_DATA_T_OK_count = 0;
        GPRS_UART_RS485Send_str("+++");
        vTaskDelay(1100);
        GPRS_UART_RS485Send_str("+++");
        vTaskDelay(1100);
        GPRS_STATUS = GPRS_DISCONNECT;
        break;
    }
    if(GPRS_STATUS != GPRS_CONNECT)
    {
        DEBUG_printf("GPRS_STATUS = %d\n", GPRS_STATUS);
    }
}
View Code

 

posted on 2019-02-27 11:52  郞性人生  阅读(732)  评论(0)    收藏  举报