#include "bsp_ml307r.h" #include "at_chat.h" #include "at_port.h" #include "bsp_uart.h" #include "log.h" #include "stdio.h" #include "CONFIG.h" #include "SLEEP.h" #undef LOG_ENABLE #define LOG_ENABLE 1 #define ML307_PERIODIC_EVT (0x0001 << 0) #define ML307_TIMEOUT_EVT (0x0001 << 1) static tmosTaskID ml307_task_id = INVALID_TASK_ID; static tmosTaskID ml307_timeout_task_id = INVALID_TASK_ID; at_obj_t *ml307r_obj; uint8_t databuf[5] = {0x01,0xaa,0x12,0xde,0x39}; void At_Debug(const char *fmt, ...) { va_list args; va_start(args, fmt); vprintf(fmt, args); va_end(args); } void Ml307_Delay_Ms(uint16_t ms) { DelayMs(ms); } void Ml307_Delay_us(uint16_t us) { DelayUs(us); } static const at_adapter_t at_adapter = { .write = BSP_Uart1_Send_Data, .read = BSP_Uart1_Receive_Data, .debug = At_Debug, .recv_bufsize = 512, //256 .urc_bufsize = 512 }; //模块准备就绪 static int URC_Module_Ready_Cb(at_urc_info_t *info) { logDebug("module ready complete\r\n"); return 0; } /** * @brief urc订阅表 */ static const urc_item_t urc_table[] = { {.prefix = "+CPIN: READY", .endmark = '\n', .handler = URC_Module_Ready_Cb},//模块准备就绪 }; static void Ml307_Power_On(void) { #define ML307_POWER_ON_TIME 3 GPIOB_SetBits(ML307_PWR_PIN); Ml307_Delay_Ms(ML307_POWER_ON_TIME * 1000); GPIOB_ResetBits(ML307_PWR_PIN); } static void Ml307_Power_Off(void) { #define M307_POWER_OFF_TIME 4 GPIOB_SetBits(ML307_PWR_PIN); Ml307_Delay_Ms(M307_POWER_OFF_TIME * 1000); GPIOB_ResetBits(ML307_PWR_PIN); Ml307_Delay_Ms(100); } int Ml307r_Gpio_Init(void) { GPIOB_SetBits(ENABLE_3_8_V); GPIOB_ModeCfg(ENABLE_3_8_V, GPIO_ModeOut_PP_5mA); GPIOB_ResetBits(ML307_RST_PIN); GPIOB_ModeCfg(ML307_RST_PIN, GPIO_ModeOut_PP_5mA); GPIOB_ModeCfg(USIM_DECT_PIN, GPIO_ModeIN_Floating); GPIOB_ModeCfg(ML307_PWR_PIN, GPIO_ModeOut_PP_5mA); return 0; } // 停止4G通信,停止轮询任务 void BSP_Stop_ML307_Task(void) { if (ml307_task_id != INVALID_TASK_ID) { tmos_stop_task(ml307_task_id, ML307_PERIODIC_EVT); Ml307_Power_Off(); BSP_RequestSleep(); logDebug("4G module polling stopped\n"); } } static int Module_Read_State(at_env_t *e) { switch (e->state) { case 0: e->obj->adap->debug("Check if the Module is ready\r\n"); e->println(e, "AT"); e->reset_timer(e); e->state++; break; case 1: if (e->contains(e, "OK")) { e->recvclr(e); e->finish(e, AT_RESP_OK); e->obj->adap->debug("Module is ready\r\n"); // BSP_Stop_ML307_Task(); } if (e->is_timeout(e, 5000)) { e->state--; if (++e->i > 3) { e->obj->adap->debug("Module error\r\n"); e->finish(e, AT_RESP_ERROR); // BSP_Stop_ML307_Task(); } } break; } return 0; } static void BSP_Read_Module(void) { at_do_work(ml307r_obj, NULL, Module_Read_State); // 重启后生效 } /** * @brief 命令响应处理程序 */ static void simcom_init_callback(at_response_t *r) { printf("SIM800C Init %s!\r\n",r->code == AT_RESP_OK ? "ok" : "error"); } /* * @brief 模块初始化 */ static void simcom_init(void) { at_attr_t attr; static const char *cmds[] = { "AT+GSN=1", "AT+CIMI", "AT+MCCID", "AT+CPIN?", "AT+CEREG?", "AT+CSQ", NULL, }; at_attr_deinit(&attr); attr.cb = simcom_init_callback; //设置命令回调 at_send_multiline(ml307r_obj, &attr, cmds); } /* * @brief 创建设备 * @return */ static int BSP_Module_Connect_CtWing_Handle(at_env_t *e) { switch (e->state) { case 0: logDebug("create device...\r\n"); e->println(e, "AT+MIPOPEN=0,\"TCP\",\"112.125.89.8\",45950,,1"); // 8.135.10.183,32994 e->reset_timer(e); e->state++; break; case 1: if (e->contains(e, "CONNECT")) { logDebug("create device complete\r\n"); e->finish(e, AT_RESP_OK); BSP_ML307_StartTimeoutTimer(); } else if (e->is_timeout(e, 5000)) { e->state--; if (++e->i > 3) { logDebug("create device error\r\n"); e->finish(e, AT_RESP_ERROR); } } break; default: break; } return 0; } //连接服务器 static void BSP_Module_Connect_CtWing(void) { at_do_work(ml307r_obj, NULL, BSP_Module_Connect_CtWing_Handle);//创建设备 } static int Module_Restart_Work(at_env_t *e) { switch (e->state) { case 0: logDebug("restart module...\r\n"); e->println(e, "AT+CFUN=1,1");//重启模块 e->reset_timer(e); e->state++; break; case 1: if (e->contains(e, "OK")) { logDebug("restart module complete\r\n"); e->reset_timer(e); e->state++; } if (e->is_timeout(e, 5000)) { e->state--; if (++e->i > 3) { logDebug("Module restart error\r\n"); e->finish(e, AT_RESP_ERROR); } } break; case 2: logDebug("Check if the Module is ready\r\n"); e->println(e, "AT"); e->reset_timer(e); e->state++; break; case 3: if (e->contains(e, "OK")) { e->recvclr(e); e->finish(e, AT_RESP_OK); logDebug("Module is ready\r\n"); } if (e->is_timeout(e, 5000)) { e->state--; if (++e->i > 3) { logDebug("Module error\r\n"); e->finish(e, AT_RESP_ERROR); } } break; } return 0; } //重启模块 static void BSP_Restart_Module(void) { at_do_work(ml307r_obj, NULL, Module_Restart_Work);//重启后生效 } void Ml307r_Loop(void) { at_obj_process(ml307r_obj); } __HIGH_CODE __attribute__((noinline)) uint16_t Ml307r_Handle(uint8_t task_id, uint16_t events) { if (events & ML307_PERIODIC_EVT) { Ml307r_Loop(); tmos_start_task(ml307_task_id, ML307_PERIODIC_EVT, MS1_TO_SYSTEM_TIME(200)); //5 return (events ^ ML307_PERIODIC_EVT); } return 0; } //向服务器发送数据 void BSP_Module_Send_Data(uint8_t* data, uint8_t len) { at_attr_t attr; at_send_data(ml307r_obj, &attr, data, len); } // 断电保护数据上报 void BSP_Module_Emergency_Send(uint8_t* data, uint8_t len) { if (ml307_task_id != INVALID_TASK_ID) { GPIOB_SetBits(ENABLE_3_8_V); // 确保3.8V供电正常 BSP_Read_Module(); // 确保模块在工作状态 at_attr_t attr; at_send_data(ml307r_obj, &attr, data, len); Ml307_Power_Off(); logDebug("Power failure protection data has been sent\n"); } else { BSP_Ml307r_Init(); // 如果模块未初始化,先初始化 logDebug("4G initialization\n"); at_attr_t attr; at_send_data(ml307r_obj, &attr, data, len); Ml307_Power_Off(); logDebug("Power failure protection data has been sent\n"); } } void BSP_Ml307r_Init(void) { Ml307r_Gpio_Init(); Ml307_Power_On(); BSP_UART1_Init(); ml307r_obj = at_obj_create(&at_adapter);//Create AT communication object at_obj_set_urc(ml307r_obj, urc_table, sizeof(urc_table) / sizeof(urc_table[0])); ml307_task_id = TMOS_ProcessEventRegister(Ml307r_Handle); tmos_set_event(ml307_task_id, ML307_PERIODIC_EVT); // 初始化超时任务 BSP_ML307_SetActive(); logDebug("BSP_Read_Module\n"); BSP_Read_Module(); logDebug("simcom_init\n"); simcom_init(); logDebug("BSP_Module_Connect_CtWing\n"); BSP_Module_Connect_CtWing(); logDebug("BSP_Module_Send_Data\n"); // BSP_Module_Send_Data(databuf, 5); BSP_ML307_SendMessage(); } /** * @brief ML307超时任务处理函数 */ static uint16_t BSP_ML307_TimeoutTask(uint8_t task_id, uint16_t events) { if (events & ML307_TIMEOUT_EVT) { logDebug("ML307 timeout, stopping task\n"); BSP_Stop_ML307_Task(); return (events ^ ML307_TIMEOUT_EVT); } return 0; } /** * @brief 启动ML307活动超时定时器 */ void BSP_ML307_StartTimeoutTimer(void) { if (ml307_timeout_task_id == INVALID_TASK_ID) { ml307_timeout_task_id = TMOS_ProcessEventRegister(BSP_ML307_TimeoutTask); } tmos_stop_task(ml307_timeout_task_id, ML307_TIMEOUT_EVT); tmos_start_task(ml307_timeout_task_id, ML307_TIMEOUT_EVT, MS1_TO_SYSTEM_TIME(5000)); // 5秒超时 } /** * @brief 将ML307设置为活动状态,阻止系统睡眠 */ void BSP_ML307_SetActive(void) { BSP_BlockSleep(); BSP_ML307_StartTimeoutTimer(); } void BSP_ML307_SendMessage(void) { char json_buffer[300]; snprintf(json_buffer, sizeof(json_buffer), "{" "\"device\":{" "\"id\":\"SCV001\"," "\"time\":\"2025\"" "}," "\"status\":\"closed\"," "\"fault\":{" "\"lowBattery\":true," "\"code\":1001" "}," "\"monitor\":{" "\"pressure\":0.8," "\"lowVoltage\":true" "}," "\"network\":{" "\"sinr\":15.2," "\"signal\":4" "}," "\"standards\":{" "\"iotId\":\"IoT-SCV-12345\"" "}" "}"); BSP_Module_Send_Data((uint8_t*)json_buffer, strlen(json_buffer)); logDebug("BSP_ML307_SendMessage: %s\n", json_buffer); }