BCU CPLD 固件升级后整机下电生效控制报错问题分析
更新时间: 2026/05/28
在Gitcode上查看源码

问题背景

  • 单板类型:NA
  • 软件版本:NA
  • 涉及功能:升级CPLD。
  • 触发条件:BCU CPLD固件升级。
  • 业务表现:预期升级完成后选择整机下电可以生效;实际选择“整机下电”作为生效控制类型时出现操作失败的报错,而同时勾选“重启BMC”和“整机下电”则可以成功执行生效动作。

问题复现步骤

  1. 在进行BCU CPLD固件升级后,选择“整机下电”作为生效控制类型时出现操作失败的报错,而同时勾选“重启BMC”和“整机下电”则可以成功执行生效动作。

  2. 重启bmc 和整机下电后,执行了生效控制动作,查看代码,发现两者都勾选后是实际是 reset ac 。

关键日志信息

选择“整机下电”作为生效控制类型时出现操作失败的报错,web接口响应:

app.log日志如下:

text
2025-03-22 16:33:04.329388 firmware_mgmt NOTICE: active_info.lua(569): active policy ActivationControl is PowerOff
2025-03-22 16:33:04.329929 firmware_mgmt NOTICE: active_info.lua(575): No firmware suit for the active_policys
2025-03-22 16:33:04.330731 firmware_mgmt WARNING: init.lua(97): model.lua:1376 > active_proc.lua:84 > active_control.lua:45: An error occurred during the firmware upgrade process. Details: No firmware need to be actived in this situation

定位过程

从REST API /UI/Rest/BMCSettings/UpdateService/StartActive 的请求体定义可见,ActivationActions 参数支持两个可选项:ResetBMC 和 PowerOff。当仅传入 PowerOff 时,系统尝试仅通过整机下电使CPLD固件生效;但部分硬件平台(如BCU)对CPLD升级后的生效机制有严格要求——必须经历完整的AC掉电再上电周期(即物理断电)才能确保新固件被正确加载。

然而,在某些实现中,“整机下电”若未伴随后续明确的电源恢复指令,可能无法触发真正的“断电-通电”循环,导致CPLD未能重新初始化,从而造成升级未实际生效或校验失败。因此,系统在检测到同时选择 ResetBMC 和 PowerOff 时,会将其解释为一个复合动作 ResetAC(等效于整框AC重启),这实际上模拟了完整的断电重启流程。

根据所提供的 Lua 脚本逻辑:

lua
function m.get_active_policy(policy)
  if not policy or #policy == 0 then
    return {}
  end

  local res
  for _, value in pairs(policy) do
    if not res then
      res = value
    elseif res ~= policy then
      res = 'ResetAC'
      break
    end
  end

  return {ActivationControl = res}
end

此函数逻辑表明:

  • 若只传一个策略(如 PowerOff 或 ResetBMC),返回对应动作;
  • 若传入多个不同策略,则强制合并为 'ResetAC'。

这意味着系统将多选策略视为需要更彻底的复位方式,以确保所有组件(包括CPLD)都能进入预期状态。这种设计是为了保证升级可靠性,特别是在涉及低级硬件控制器(如CPLD)时,避免因部分复位不充分导致的状态不一致。

问题原因

单独选择“整机下电”可能导致系统无法确认是否完成了真正意义上的 AC 断电重启,因而拒绝仅以此方式生效关键固件(如CPLD)。

解决方案

同时选择“重启BMC”和“整机下电”触发 ResetAC,代表一次完整电源循环,符合CPLD固件加载的安全要求,确保升级可靠生效。

对于CPLD类固件升级,应始终采用“重启BMC + 整机下电”组合策略,以满足底层硬件的复位需求。