4、复位与初始化问题:复位信号毛刺、异步复位同步释放、初始化顺序错误、看门狗误触发

复位和初始化,听起来像是基本功对吧?

但我跟你说,这恰恰是上板后最容易翻车的地方。我见过太多项目,仿真跑得飞起,一上板就各种诡异现象——要么系统起不来,要么跑着跑着突然复位。说白了,都是复位和初始化埋的雷。

4.1 复位信号毛刺——你以为复位了,其实没有

先说说复位毛刺。这个问题很隐蔽。

你想想看,如果复位信号上有一个窄脉冲毛刺,刚好在时钟沿附近出现,会发生什么?

有些寄存器被复位了,有些没被复位。整个系统的状态就乱了。

⚠️ 典型场景: 按键复位、上电瞬间、板级走线过长,都容易引入毛刺。

我在项目中遇到过一块板子,每次用手摸一下复位按键附近,系统就重启。查了半天,发现是按键抖动加上走线耦合,给FPGA送了一串毛刺。

怎么解决?

  • 硬件滤波: 复位引脚加RC低通滤波,时间常数选1~10ms
  • 软件去抖: 在FPGA内部做连续采样,连续N个周期为低才认为是复位
  • 施密特触发器: 如果板级允许,用施密特触发器芯片做整形
💡 我的习惯: 不管外部复位干不干净,进FPGA第一件事就是做两级同步+去抖。成本几乎为零,但能省掉你三天查bug的时间。

4.2 异步复位同步释放——这个真不是玄学

好,毛刺问题解决了。但还有一个更常见的坑:异步复位。

很多工程师喜欢直接用异步复位,因为简单嘛——复位信号一来,寄存器立刻清零。但问题出在复位释放的时候。

如果复位释放时刻刚好靠近时钟沿,有些寄存器会认为复位已经结束,有些还认为在复位中。这叫复位撤销的亚稳态。

我建议的做法是:异步复位,同步释放。

// 异步复位同步释放的典型写法
reg rst_sync1, rst_sync2;

always @(posedge clk or negedge rst_n) begin
    if (!rst_n) begin
        rst_sync1 <= 1'b0;
        rst_sync2 <= 1'b0;
    end else begin
        rst_sync1 <= 1'b1;
        rst_sync2 <= rst_sync1;
    end
end

// 用 rst_sync2 作为内部复位
always @(posedge clk or negedge rst_sync2) begin
    if (!rst_sync2) begin
        // 复位逻辑
    end else begin
        // 正常逻辑
    end
end

你看,复位信号进来时是异步的,直接清零。但释放时,经过两级同步,保证所有寄存器都在同一个时钟沿退出复位。嗯,这个写法我用了十年,从来没出过问题。

🔑 核心要点: 异步复位用于「进入复位」,同步释放用于「退出复位」。两者结合,既快又稳。

4.3 初始化顺序错误——谁先谁后,有讲究

接下来聊初始化顺序。这个在复杂系统里特别常见。

比如你有DDR、有以太网PHY、有ADC,上电后谁先初始化?

我曾经遇到一个项目,FPGA先初始化了,然后才去配PHY。结果PHY还没准备好,FPGA已经发了配置命令,全丢了。系统跑起来后网络死活不通。

正确的初始化顺序一般是这样:

  1. 电源稳定: 等所有电源轨都OK
  2. 时钟稳定: PLL锁定、晶振起振
  3. 外部器件初始化: PHY、ADC、DDR等先配好
  4. FPGA内部状态机启动: 等外部都就绪了,再开始干活
  5. 看门狗喂狗: 最后再开看门狗,避免初始化期间误触发
⚠️ 注意: 很多芯片有「就绪引脚」,比如PHY的INT_B、DDR的CKE。别省这个信号,老老实实等它拉高再往下走。

我个人习惯写一个初始化状态机,每个步骤完成后给一个done信号,串行推进。这样逻辑清晰,调试也方便。

4.4 看门狗误触发——你还没喂它,它就咬人了

最后说说看门狗。这东西本来是保护系统的,但用不好反而添乱。

最常见的场景:系统上电后,看门狗先启动了,但主控还在初始化,没来得及喂狗。结果看门狗超时,直接复位。系统陷入「上电→复位→上电→复位」的死循环。

怎么避免?

  • 延迟启动: 看门狗在初始化完成后再使能
  • 长超时时间: 初始化阶段用较长的超时时间,比如10秒
  • 硬件使能引脚: 如果看门狗芯片有EN引脚,用FPGA的GPIO控制它
💡 避坑指南: 我曾经在一个项目里,看门狗超时时间设了1秒,结果DDR初始化要1.5秒。每次上电都复位。后来改成「先初始化DDR,再开看门狗」,问题解决。嗯,有时候就是这么简单。

4.5 本章小结——一张图说清楚

好了,四个问题讲完了。我画了一张图,帮你把整个复位与初始化的流程串起来:

复位与初始化流程 1. 系统上电 2. 电源稳定检测 3. 时钟稳定(PLL锁定) 4. 异步复位同步释放 5. 外部器件初始化 6. 看门狗使能(最后一步) 常见问题 • 复位毛刺 → 硬件滤波+去抖 • 异步复位亚稳态 → 同步释放 • 初始化顺序错 → 状态机控制 • 看门狗误触发 → 最后使能

这张图把整个流程串起来了。你照着这个顺序做,复位和初始化的问题基本都能规避。

嗯,这一章就到这里。复位和初始化看似基础,但往往是系统稳定性的第一道关卡。把这里做好了,后面的调试会顺畅很多。

📌 一句话记住: 复位要干净、释放要同步、初始化要排队、看门狗要最后开。