inovance_upgrade.h
源文件路径:
midware/inverter/inovance/inovance_upgrade.h所属模块:midware/inverter/inovance(汇川逆变器通信与固件升级) 代码行数:93
1. 文件职责
本头文件是汇川(Inovance)逆变器 MCU1/MCU2/FPGA 固件升级模块的对外契约:定义升级用到的全部协议命令字、寄存器地址、包长、超时等宏常量,定义返回码/升级对象/状态机三组枚举,定义升级上下文结构体 INOVANCE_UPGRDADE_T,并声明 7 个对外函数。
它本身不含任何可执行逻辑,是 inovance_upgrade.c(实现)与调用方(inovance_comm_usart.c、inverter.c)之间的接口层。数据流位置处于「云端固件已落到 SDRAM → 通过 USART2 写入逆变器 bootloader」这一段,头文件负责把这段流程的帧字段常量与状态枚举固定下来。
INOVANCE_UPGRDADE_T 结构体的实例并不在本头文件声明(inovance_upgrade.c:24 内以 static 单例 s_t_inovance_upgrade 存在),因此本头文件只导出类型定义,不导出任何变量。
2. 关键数据结构与宏
| 名称 | 类型 | 说明 |
|---|---|---|
INOVANCE_UPGRDADE_T | 结构体 | 升级上下文。u8* u8_upgrade_addr:SDRAM 中的固件镜像基址;u8 u8_upgrade_obj:升级对象(取值见 INOVANCE_UPGRADE_OBJ_E);u8 u8_upgrade_state:定义但全工程未使用(状态实际存在 inovance_upgrade.c 的 static 变量里);u8 u8_upgrade_buf[264]:单包固件数据缓冲;u32 u32_file_offset:已下发偏移;u32 u32_file_length:镜像总长 |
INOVANCE_UPGRADE_RETURN_E | 枚举 | 返回码/设备状态混合枚举,三组语义不同的取值重叠在同一枚举内(详见第 7 节风险点) |
INOVANCE_UPGRADE_OBJ_E | 枚举 | 升级对象:INOVANCE_NONE=0、INOVANCE_MCU1=1、INOVANCE_MCU2=2、INOVANCE_FPGA=3、INOVANCE_INIT=4、INOVANCE_MAX=5 |
INOVANCE_UPGRADE_STATE_E | 枚举 | 升级状态机状态:INOVANCE_UPGRADE_INIT=0、QUERY_STATUS、JUMP_BOOT、SET_DOWNLOAD_MODE、SEND_FILE、START_PROGRAM、END |
INOVANCE_UPGRADE_DEBUG | 宏 | (0),本模块调试打印总开关。置 1 后 inovance_upgrade.c 各状态进入/退出均 printf 详细过程 |
INOVANCE_UPGRADE_ADDR_READ_DEV_STATUS | 宏 | (0x04),APP_OPERATE(0x45) 命令读设备状态的寄存器地址 |
INOVANCE_UPGRADE_ADDR_JUMP_BOOT | 宏 | (0x05),APP_OPERATE(0x45) 命令跳转 bootloader 的寄存器地址 |
INOVANCE_UPGRADE_CMD_APP_OPERATE | 宏 | (0x45),APP 操作命令字(查状态 / 跳 boot 共用) |
INOVANCE_UPGRADE_CMD_SET_DOWNLOAD_MODE | 宏 | (0x64),令 boot 进入下载模式 |
INOVANCE_UPGRADE_CMD_SEND_FILE | 宏 | (0x69),下发固件数据包 |
INOVANCE_UPGRADE_CMD_START_PROGRAM | 宏 | (0x70),启动新程序(校验 + 跳转) |
INOVANCE_UPGRADE_FILE_LENGTH | 宏 | (264),单包固件数据长度;同时是 u8_upgrade_buf 的容量、以及「总长必须被其整除」的校验模数 |
INOVANCE_UPGRADE_DELAY | 宏 | (200),QUERY_STATUS 状态收不到应答时的时间片延时(ms) |
INOVANCE_SLAVE_ADDRESS | 宏(外部引入) | (0x01),来自 inovance_comm_usart.h:40,全部下发帧的从机地址 |
INOVANCE_DAT_PCK_INTERVAL_INV | 宏(外部引入) | (100),来自 inovance_comm_usart.h:25,用作命令帧的发送节流窗口与串口发送超时(ms) |
3. 函数清单
本文件是纯声明头,不含函数定义。下表为头文件中的全部 7 条函数声明:
| 函数名 | 作用域 | 说明 |
|---|---|---|
inovance_read_upgrade_flag_master | 全局(声明,定义于 inovance_upgrade.c:38) | 返回主机 MCU1 是否正处于升级中 |
inovance_read_upgrade_percent_master | 全局(声明,定义于 inovance_upgrade.c:49) | 返回主机 MCU1 升级进度百分比 |
inovance_read_upgrade_flag_slave | 全局(声明,定义于 inovance_upgrade.c:63) | 返回从机 MCU2 是否正处于升级中 |
inovance_read_upgrade_percent_slave | 全局(声明,定义于 inovance_upgrade.c:74) | 返回从机 MCU2 升级进度百分比 |
inovance_read_upgrade_flag_fpga | 全局(声明,定义于 inovance_upgrade.c:88) | 返回 FPGA(ARM) 是否正处于升级中 |
inovance_read_upgrade_percent_fpga | 全局(声明,定义于 inovance_upgrade.c:101) | 返回 FPGA(ARM) 升级进度百分比 |
inovance_upgrade_handle | 全局(声明,定义于 inovance_upgrade.c:362) | 升级主状态机入口,每次调用推进一个状态 |
4. 核心逻辑解析
本文件无运行逻辑,本节说明头文件所「描述」的协议约定与状态模型,细节实现见 inovance_upgrade.c 的对应分析。
4.1 头文件规定的协议帧布局
宏常量决定了 inovance_upgrade.c 中所有下发帧的内容。协议基于 USART2(115200bps)的 Modbus-RTU 风格帧,但用命令字(功能码位)承载自定义语义,帧尾为 Modbus CRC16、低字节先发:
| 帧用途 | 由哪些宏决定 | 实际字节序列 | 长度 |
|---|---|---|---|
| 查设备状态 | INOVANCE_SLAVE_ADDRESS + CMD_APP_OPERATE + ADDR_READ_DEV_STATUS | 01 45 00 04 00 01 CRC_L CRC_H | 8 |
| 跳转 boot | INOVANCE_SLAVE_ADDRESS + CMD_APP_OPERATE + ADDR_JUMP_BOOT | 01 45 00 05 00 01 CRC_L CRC_H | 8 |
| 进下载模式 | INOVANCE_SLAVE_ADDRESS + CMD_SET_DOWNLOAD_MODE | 01 64 F6 0F 00 08 CRC_L CRC_H | 8 |
| 下发固件包 | INOVANCE_SLAVE_ADDRESS + CMD_SEND_FILE + FILE_LENGTH | 01 69 <264B> CRC_L CRC_H | 268 |
| 启动新程序 | INOVANCE_SLAVE_ADDRESS + CMD_START_PROGRAM | 01 70 00 00 00 00 CRC_L CRC_H | 8 |
注意 SET_DOWNLOAD_MODE 帧中的 F6 0F 00 08 在头文件里没有对应宏,是硬编码在 inovance_upgrade.c:287-290 的字面量。
4.2 头文件规定的状态机模型
INOVANCE_UPGRADE_STATE_E 定义了 7 个状态,其序号即状态机的执行顺序,构成一条单向主链:
INIT(0) → QUERY_STATUS(1) → JUMP_BOOT(2) → SET_DOWNLOAD_MODE(3)
→ SEND_FILE(4) → START_PROGRAM(5) → END(6) → 回到 INIT
其中 JUMP_BOOT 只在「APP 仍在运行且处于安全状态」时才经过;若 QUERY_STATUS 发现 APP 已被擦除(异常回复且帧长 8),则直接跳到 SET_DOWNLOAD_MODE。SEND_FILE 单包连续失败 3 次时回退到 QUERY_STATUS 重走一遍;END 之后固定回 INIT,由 INOVANCE_UPGRADE_OBJ_E 的待办标志决定下一个升级对象(MCU1 → MCU2 → FPGA → 结束)。
4.3 头文件规定的时间参数
INOVANCE_UPGRADE_DELAY = 200:QUERY_STATUS无应答时的时间片延时,避免空转刷爆 CPU。INOVANCE_DAT_PCK_INTERVAL_INV = 100(来自inovance_comm_usart.h):命令帧(8 字节)的发送节流窗口,同时也是usart2_send_data的超时参数;固件数据帧则改用字面量200。INOVANCE_UPGRADE_FILE_LENGTH = 264:隐含两条硬性约束——(a) 镜像总长必须是 264 的整数倍,否则整轮放弃;(b)u8_upgrade_buf与栈上发送缓冲l_u8_tx_buf[300]都按此值定容。
4.4 与 uCOS-II 的配合
头文件不引入任何 RTOS 原语。它声明的 7 个函数全部由调用方任务同步调用:inovance_upgrade_handle() 由汇川逆变器通信任务(inovance_comm_usart.c:2592)驱动,6 个查询函数由 inverter.c 的只读适配层(:3828/:3863/:3898/:3933/:3984/:4011)调用,均无信号量或消息邮箱参与。
4.5 与结构体相关的全局状态
INOVANCE_UPGRDADE_T 是升级过程的唯一状态载体,但实例由 .c 文件私藏(static INOVANCE_UPGRDADE_T s_t_inovance_upgrade,inovance_upgrade.c:24),头文件只提供类型。因此 6 个 read_* 查询函数是外部读取这些状态的唯一合法途径,u8_upgrade_state 字段则完全闲置。
5. 对外接口
本文件导出
函数声明(7 条):inovance_read_upgrade_flag_master、inovance_read_upgrade_percent_master、inovance_read_upgrade_flag_slave、inovance_read_upgrade_percent_slave、inovance_read_upgrade_flag_fpga、inovance_read_upgrade_percent_fpga、inovance_upgrade_handle。
类型导出:INOVANCE_UPGRDADE_T、INOVANCE_UPGRADE_RETURN_E、INOVANCE_UPGRADE_OBJ_E、INOVANCE_UPGRADE_STATE_E。
宏导出:INOVANCE_UPGRADE_DEBUG、INOVANCE_UPGRADE_ADDR_READ_DEV_STATUS、INOVANCE_UPGRADE_ADDR_JUMP_BOOT、INOVANCE_UPGRADE_CMD_APP_OPERATE、INOVANCE_UPGRADE_CMD_SET_DOWNLOAD_MODE、INOVANCE_UPGRADE_CMD_SEND_FILE、INOVANCE_UPGRADE_CMD_START_PROGRAM、INOVANCE_UPGRADE_FILE_LENGTH、INOVANCE_UPGRADE_DELAY。
不导出任何变量(无 extern 声明)。
实际的调用方:
inovance_upgrade.c——唯一实现者,使用全部宏与类型midware/inverter/inovance/inovance_comm_usart.c——使用三个 flag 查询函数(:2585/2587/2589)与inovance_upgrade_handle(:2592)midware/inverter/inverter.c——使用全部 6 个查询函数(:3828/3863/3898/3933/3984/4011)
本文件依赖的外部符号
| 符号 | 来源 |
|---|---|
includes.h | 工程总头文件(:13 include),提供 u8/u16/u32、TRUE/FALSE、RTOS 与 HAL 声明 |
INOVANCE_SLAVE_ADDRESS | midware/inverter/inovance/inovance_comm_usart.h:40 |
INOVANCE_DAT_PCK_INTERVAL_INV | midware/inverter/inovance/inovance_comm_usart.h:25 |
6. 依赖关系
依赖:仅 includes.h(:13)。头文件自身不 include inovance_comm_usart.h,而是寄希望于包含者已经先引入它——INOVANCE_SLAVE_ADDRESS 与 INOVANCE_DAT_PCK_INTERVAL_INV 两个宏在 inovance_upgrade.c 中使用,但本头文件并未声明其来源(见第 7 节风险点)。
被依赖:
midware/inverter/inovance/inovance_upgrade.c:13——实现本头文件声明的全部函数midware/inverter/inovance/inovance_comm_usart.c——间接依赖(经inovance_upgrade.c的接口调用升级流程)midware/inverter/inverter.c——经上层适配函数间接依赖本头文件声明的查询接口
7. 备注与风险点
- 枚举三域混用,取值重叠:
INOVANCE_UPGRADE_RETURN_E(:26-52)把三种互不相干的码表塞进同一个枚举:- 设备运行状态:
RUNNING=0x01、REVERSE=2、SAFE=3(高字节语义) - APP 侧响应错误:
CMD_ERROR=0x01、ADDR_ERROR=2、LENGTH_ERROR=3、CRC_CHECK_ERROR=4、JUMPER_DISCONNECT=5 - boot 侧响应错误:
NO_ERROR=0x00、DATA_CRC16_ERROR=1、DECRYPT_ERROR=2、ERASE_ERROR=3、PROGRAM_ERROR=4、CHECK_ERROR=5、DATA_CRC32_ERROR=0x07、ID_ERROR=0x08、CRC32_INCOMPATIBLE_ERROR=0x11、DATA_FRAME_SEND_OVER_LENGTH=0x13、DATA_LENGTH_OUTOF_RANGE=0x14、ADDR_OUTOF_RANGE=0x15、FRAME_NUMBER_ERROR=0x16
- 设备运行状态:
例如 INOVANCE_UPGRADE_RUNNING 与 INOVANCE_UPGRADE_CMD_ERROR 都是 1,INOVANCE_UPGRADE_SAFE 与 INOVANCE_UPGRADE_LENGTH_ERROR 都是 3。使用时必须靠「ret >> 8 还是 ret 本身」来区分语义,极易写错。
- 枚举内的显式赋值依赖隐式续号:
INOVANCE_UPGRADE_CHECK_ERROR之后写INOVANCE_UPGRADE_DATA_CRC32_ERROR = 0x07(:44),是为了让后续的ID_ERROR顺延为0x08——而0x08正是协议里「ID 错误」的实际码值。这种「靠隐式续号凑上协议值」的写法,一旦在DATA_CRC32_ERROR之前插入新项就会静默改变协议语义。 u8_upgrade_state字段闲置:结构体(:75-83)里的u8_upgrade_state在全工程从未被读写,真正的状态保存在inovance_upgrade.c:364的static u8 s_u8_upgrade_state。属于重构残留,容易让阅读者误以为状态存放在结构体里。- 结构体命名拼写错误:类型名是
INOVANCE_UPGRDADE_T("UPGRDADE",多了一个 D、少了 A 的位置),应为UPGRADE。命名已扩散到 .c 文件,改名需同步多处。 - 宏来源未在本头文件引入:
INOVANCE_SLAVE_ADDRESS(inovance_comm_usart.h:40)与INOVANCE_DAT_PCK_INTERVAL_INV(inovance_comm_usart.h:25)在本头文件里既未#include也未注释来源,全靠使用处的 include 顺序。若某文件只 includeinovance_upgrade.h并在表达式中用到这两个宏,会直接编译报错。 - 无 include guard 保护冲突:守卫宏
__INOVANCE_UPGRADE_H__(:9-10)以双下划线开头,属 C 标准保留给实现的标识符,虽不影响功能但属不规范用法。 F6 0F 00 08未宏化:CMD_SET_DOWNLOAD_MODE帧的握手数据域硬编码在 .c 文件里,头文件未给出对应宏(对照ADDR_READ_DEV_STATUS/ADDR_JUMP_BOOT都建了宏),协议改动时容易漏改。- 版本/日期字段为空:文件头
@version、@date、@brief均为空(:4-6),无修订记录可追溯。