112 lines
4.1 KiB
C
112 lines
4.1 KiB
C
#include "network.h"
|
||
#include "air780e.h"
|
||
#include "led.h"
|
||
#include "log.h"
|
||
#include "main.h"
|
||
#include "stdio.h"
|
||
#include "string.h"
|
||
|
||
volatile uint8_t g_net_mqtt_ready = 0;
|
||
volatile uint8_t g_net_first_publish_ok = 0;
|
||
|
||
/* 网络发送互斥标志:OTA 下载等 AT 交互期间置位 */
|
||
volatile uint8_t g_net_tx_busy = 0;
|
||
|
||
/* 4G 无 SIM 卡标志:由 air780e.c 在初始化失败时设置 */
|
||
volatile uint8_t g_no_sim_detected = 0;
|
||
|
||
void NET_init(void)
|
||
{
|
||
g_net_mqtt_ready = 0;
|
||
g_net_first_publish_ok = 0;
|
||
g_no_sim_detected = 0;
|
||
|
||
air780e_init();
|
||
|
||
if (g_no_sim_detected) {
|
||
log_warn("> 4G no SIM, please insert SIM card");
|
||
/* 不再回退到 WiFi,4G 无 SIM 时持续等待用户插卡 */
|
||
}
|
||
|
||
g_net_mqtt_ready = g_air780e_mqtt_ready;
|
||
}
|
||
|
||
void NET_process(void)
|
||
{
|
||
static uint32_t no_sim_retry_tick = 0;
|
||
static uint16_t no_sim_retry_count = 0;
|
||
|
||
/* 网络未就绪时自动重试 */
|
||
if (!g_air780e_mqtt_ready) {
|
||
if (g_no_sim_detected) {
|
||
/* 检测到无 SIM 卡:每隔 10s 重新初始化一次,
|
||
用户插卡后可自动恢复;超过 20 次(约 3min)仍无卡则复位 */
|
||
if (no_sim_retry_tick == 0 ||
|
||
(HAL_GetTick() - no_sim_retry_tick) >= 10000) {
|
||
no_sim_retry_tick = HAL_GetTick();
|
||
no_sim_retry_count++;
|
||
log_warn("> NET: no SIM detected, retry init %d/20", no_sim_retry_count);
|
||
g_no_sim_detected = 0;
|
||
air780e_init();
|
||
if (!g_no_sim_detected) {
|
||
log_info("> NET: SIM card OK or network recovered");
|
||
no_sim_retry_count = 0;
|
||
} else if (no_sim_retry_count >= 20) {
|
||
log_error("> NET: no SIM for 3min, system reset");
|
||
HAL_Delay(100);
|
||
NVIC_SystemReset();
|
||
}
|
||
}
|
||
} else {
|
||
/* 其他原因未就绪,由 air780e_init 内部已经会复位;
|
||
这里清零计数,避免后续误触发 */
|
||
no_sim_retry_tick = 0;
|
||
no_sim_retry_count = 0;
|
||
}
|
||
} else {
|
||
no_sim_retry_tick = 0;
|
||
no_sim_retry_count = 0;
|
||
}
|
||
|
||
air780e_process();
|
||
g_net_mqtt_ready = g_air780e_mqtt_ready;
|
||
g_net_first_publish_ok = g_air780e_first_publish_ok;
|
||
}
|
||
|
||
void NET_publish_status(int feeding, int sw2, int sw3, int sw4,
|
||
float weight_kg, float once_wt_kg, float zero_kg)
|
||
{
|
||
if (g_net_tx_busy) { log_info("> NET: status dropped (tx busy)"); return; }
|
||
/* 云平台字段映射与参考代码字面相反:weight 显示为“空载重量”,zero 显示为“剩余料重” */
|
||
/* ver 字段:固件版本号,平台据此可识别设备是否发生了 OTA 回退 */
|
||
CAT1_printf("AT+MPUB=\"/iot/data/up/%s\",0,0,\"{\\22header\\22:\\22iot.prop.post\\22,\\22body\\22:{\\22ver\\22:%u,\\22weight\\22:%.1f,\\22onceWt\\22:%.1f,\\22zero\\22:%.1f,\\22feeding\\22:%d,\\22sw2\\22:%d,\\22sw3\\22:%d,\\22sw4\\22:%d}}\"",
|
||
MqttInfoStr.ClientID, (unsigned)MqttInfoStr.Ver, zero_kg, once_wt_kg, weight_kg, feeding, sw2, sw3, sw4);
|
||
}
|
||
|
||
void NET_publish_response(const char *cmd_id, int ok, const char *msg)
|
||
{
|
||
if (g_net_tx_busy) { log_info("> NET: response dropped (tx busy)"); return; }
|
||
const char *text = msg ? msg : (ok ? "OK" : "command failed");
|
||
CAT1_printf("AT+MPUB=\"/iot/data/up/%s\",0,0,\"{\\22id\\22:\\22%s\\22,\\22code\\22:0,\\22message\\22:\\22%s\\22}\"",
|
||
MqttInfoStr.ClientID, cmd_id, text);
|
||
}
|
||
|
||
/* 上报电量状态: on=1 正常, on=0 低电量 */
|
||
void NET_publish_power(int on)
|
||
{
|
||
if (g_net_tx_busy) { log_info("> NET: power dropped (tx busy)"); return; }
|
||
CAT1_printf("AT+MPUB=\"/iot/data/up/%s\",0,0,\"{\\22header\\22:\\22iot.prop.post\\22,\\22body\\22:{\\22pow\\22:%d}}\"",
|
||
MqttInfoStr.ClientID, on ? 1 : 0);
|
||
}
|
||
|
||
void NET_mqtt_report(const char *header, const char *ota_id, int val)
|
||
{
|
||
if (g_net_tx_busy) { log_info("> NET: report dropped (tx busy)"); return; }
|
||
air780e_mqtt_report(header, ota_id, val);
|
||
}
|
||
|
||
void NET_ota_confirm(void)
|
||
{
|
||
air780e_ota_confirm();
|
||
}
|