IHE-RM-04 软件设计
固件概述
| 属性 | 值 |
|---|---|
| 框架 | ESP-IDF v5.2 |
| 语言 | C (C99) |
| 构建 | CMake |
| 版本 | v2.0.0 |
| 代码位置 | ESP32_4_RelayModule/software/esp32_2.0.0/ |
软件架构
核心模块
1. 主程序入口 (main.c)
c
void app_main(void)
{
// 1. NVS 初始化 (存储继电器状态)
nvs_flash_init();
// 2. WiFi Station 模式连接
wifi_init_sta();
// 3. 生成设备 ID (基于 MAC 地址)
// 格式: MAC 地址大写十六进制字符串
// 4. I2C 总线 + CH423 驱动初始化
i2c_master_init(&bus_handle);
ch423_init(&ch423_dev, bus_handle);
// 5. 继电器初始化 (从 NVS 恢复状态)
relay_init(&ch423_dev, initial_states);
// 6. 按键扫描任务启动
key_init(&ch423_dev);
key_register_callback(on_key_long_press);
// 7. 等待 WiFi 连接后启动 MQTT
xEventGroupWaitBits(s_wifi_event_group, WIFI_CONNECTED_BIT, ...);
mqtt_app_start();
}2. 继电器组件 (components/relay/)
c
// relay.h — 核心 API
void relay_init(ch423_dev_t *dev, bool state[4]); // 初始化,从 NVS 恢复
void relay_set(uint8_t relay_num, bool state); // 设置指定继电器
void relay_on(uint8_t relay_num); // 打开
void relay_off(uint8_t relay_num); // 关闭
void relay_toggle(uint8_t relay_num); // 翻转
bool relay_get_state(uint8_t relay_num); // 读取状态状态持久化: 每次状态变更自动写入 NVS,断电后恢复。使用 relay_state 命名空间存储 4 字节状态数组。
3. 按键扫描 (components/key/)
- 周期性扫描频率: 50Hz (20ms)
- 长按判定时间: 1000ms
- CH423 IO 输入读取,逻辑:
0 = 按下(接地) - 按键 0-3 对应继电器 3-0 (反向映射)
- 长按触发回调函数,翻转对应继电器状态
4. CH423 驱动 (components/ch423/)
- 通信协议: I2C (400kHz)
- GPIO: SCL=IO4, SDA=IO5
- 功能: 8 路双向 IO 扩展 (4 路输出控制继电器 + 4 路输入扫描按键)
MQTT 通信
连接参数
c
#define MQTT_BROKER_URL "mqtt://www.duruofu.top:1883"设备 ID 由 WiFi MAC 地址生成 (12 位十六进制大写)。
Topic 定义
当前为 v2.0 简化格式。v3.0 将迁移至平台标准 Topic,参见 MQTT 通信协议 - 固件兼容性说明。
| 用途 | Topic 格式 (v2.0) | 标准 Topic (v3.0 目标) |
|---|---|---|
| 状态上报 | device/{MAC}/relay/status | sys/{pid}/{did}/thing/event/property/post |
| 控制指令 | device/{MAC}/relay/control | sys/{pid}/{did}/thing/service/property/set |
状态上报
设备在以下时机上报状态:
- MQTT 连接成功后
- 收到控制指令并执行后
- 按键触发继电器切换后
json
// Payload: device/{MAC}/relay/status
{
"relay0": 1,
"relay1": 0,
"relay2": 1,
"relay3": 0
}控制指令
json
// Topic: device/{MAC}/relay/control
// Payload:
{
"index": 0,
"state": 1
}| 字段 | 类型 | 说明 |
|---|---|---|
index | int | 继电器编号 (0-3) |
state | int | 目标状态 (0=关, 1=开) |
WiFi 配置
c
#define ESP_WIFI_STA_SSID "603"
#define ESP_WIFI_STA_PASSWD "3.1415926"注意: WiFi 凭据在固件中硬编码,后续版本将改为通过 Bluetooth 配网或 Web 配置页面设置。
构建与烧录
bash
# 进入固件目录
cd software/esp32_2.0.0
# 设置目标芯片
idf.py set-target esp32c3
# 编译
idf.py build
# 烧录 (USB-C)
idf.py -p /dev/ttyUSB0 flash
# 查看日志
idf.py -p /dev/ttyUSB0 monitor关键技术细节
断电记忆
- 使用 NVS 非易失存储
- 存储空间:
relay_state命名空间,4 bytes - 每次状态变更写入,上电时读取恢复
光耦控制逻辑
c
// CH423 输出逻辑与继电器状态相反
ch423_set_pin_state(dev, relay_num, !state);CH423 输出低电平时光耦导通,继电器吸合。因此代码中逻辑取反。
按键防抖
通过 20ms 周期性扫描 + 长按时间窗口判断,无需额外硬件消抖。
待实现功能
- [ ] 【高优先】迁移至标准 MQTT Topic — 改用
sys/{pid}/{did}/thing/...格式和标准 Payload - [ ] 【高优先】实现 Logical ID — 平台分配 UUID,替换 MAC 作为业务标识
- [ ] Bluetooth 配网 (WiFi 凭据配置)
- [ ] OTA 固件升级
- [ ] Modbus RTU 协议 (RS485)
- [ ] ESPNOW 网关子设备模式
- [ ] Home Assistant MQTT Discovery 自动注册
版本历史
| 版本 | 日期 | 变更 |
|---|---|---|
| v1.0.0 | 2024-03 | 基本功能:WiFi + MQTT + 按键控制 |
| v2.0.0 | 2025-03 | 重构为组件化架构,增加 CH423 驱动封装 |
