尧图网络科技YAOTU DIGITAL 获取报价
获取报价
首页 / 资讯中心 / 文章详情

Cadence中PLL相位域建模:Verilog-A实现RAK分频与切换仿真

发布时间:2026/9/8 14:28:00

资讯中心
01
ARTICLE

Cadence中PLL相位域建模:Verilog-A实现RAK分频与切换仿真

Cadence中PLL相位域建模:Verilog-A实现RAK分频与切换仿真
先说一个直觉在Cadence环境里做PLL验证大多数人第一反应是打开Virtuoso把PFD、CP、VCO、分频器一个个晶体管电路搭出来然后跑tran。这个习惯在模块级验证时没问题但一旦涉及环路级尤其是要评估RAK分频结构、小数分频切换、锁定时间、相位裕度这一类问题晶体管级仿真基本是灾难——跑一个毫秒的瞬态可能要挂机好几天而且收敛性随随便便就崩给你看。所以我这几年在Cadence里做PLL环路验证主力方案已经从晶体管级转向了相位域模型用Verilog-A在Spectre里搭一套行为级的PLL闭环速度快了不止两个数量级而且能直接看到N/N1分频切换时的相位误差波形。这篇文章就把这套模型的核心拆解、关键代码、仿真方法和踩坑记录都写清楚。很多工程师一听到“相位域模型”就觉得是学术派的东西觉得做工程用不上。但实际上它恰恰是芯片公司里PLL设计组最常用的验证手段。Cadence Virtuoso环境里有现成的PLL行为模型库不过商业PDK里通常不会给你封装好更多时候还是要自己用Verilog-A写。这篇内容适合三类人正在做PLL项目但苦于仿真时间太长的模拟工程师做射频或数字SoC集成的系统验证工程师还有研究生阶段需要快速验证PLL架构的学生。读完你至少能在自己的Virtuoso环境里跑出一个可用的相位域PLL闭环并复现分频比切换时的相位误差波形。1. 先回答一个问题为什么要做PLL相位域模型1.1 晶体管级仿真扛不住环路级验证PLL是一个负反馈系统它的核心变量不是电压是相位。这个特点决定了它的仿真时间尺度极其尴尬PFD工作在参考频率量级VCO工作在GHz量级而环路锁定时间往往是几十到几百微秒。晶体管级仿真里仿真器为了分辨VCO的每个振荡周期步长必须压到皮秒甚至飞秒量级但为了看到环路锁定总仿真时间又要拉长到百微秒级别。这两个要求叠在一起就是天文数字的计算量。我做过一次实测一个3.3GHz、环路带宽200kHz的电荷泵PLL用Spectre跑晶体管级闭环仅仅50微秒的仿真时间单核跑了两天半还没跑完而且中间的DC收敛点已经报了一堆warning。这种情况下你根本没法做参数扫描连改一个环路滤波器的电容值都要重新挂机两天。相位域模型的优势就在这里它把VCO的GHz震荡抽象成一个瞬时相位的积分项把PFD/CP抽象成一个增益环节仿真步长不再受限于VCO周期跑同样的50微秒只需要几分钟。1.2 相位域模型到底在建模什么要理解相位域模型先记住一句话PLL锁定的是相位不是频率。因此建模时我们关心的是“相位随时间怎么变”而不是“电压波形长什么样”。整个闭环可以被拆成几个相位运算关系PFDCP比较参考相位与反馈相位输出一个与相位误差成正比的平均电流增益用Kpd表示单位是A/rad。环路滤波器把电荷泵的电流脉冲变成VCO的调谐电压这是典型的线性滤波电路。VCO控制电压通过压控增益Kvco转换成瞬时角频率相位是角频率的积分。分频器输出相位是输入相位除以分频比反馈回路的相位关系是Фdiv Фvco / N。把一个非线性很强的混合信号系统简化成这样的线性/准线性模型好处是可以用控制理论那套工具直接分析稳定性坏处是丢掉了很多非理想效应。实际项目中我通常是两条腿走路相位域模型负责环路级快速验证和参数初选晶体管级仿真只用来验证关键模块比如PFD/CP的匹配、VCO的调谐范围是否符合模型假设。两者各干各的活效率最高。1.3 什么场景下相位域模型是刚需并不是所有PLL仿真都需要相位域模型。如果你的目标仅仅是验证某个模块的功能、看PFD输出的脉宽、测CP的充放电电流匹配那用晶体管电路直接跑就完了。但凡是涉及下面这几种场景相位域模型几乎就是刚需环路带宽、相位裕度、锁定时间需要扫描验证分频比切换如N/N1切换、跳频时观察环路动态响应小数分频中Sigma-Delta调制器带来的量化噪声与杂散估算锁相环启动过程的频率牵引和失锁恢复评估环路滤波器元件变化对稳定性的影响。就拿N/N1切换来说这个场景如果在晶体管级仿真里做不仅慢而且很难直观看到相位误差。因为phase误差不是一个直接可测的电压节点你得自己写脚本去提取VCO过零点再和参考时钟过零点做对比麻烦得很。但在相位域模型里相位本身就是模型内部的一个状态变量你直接把它引出来plot切换瞬间的相位误差一目了然。2. RAK分频结构在相位域里的等价关系2.1 RAK到底是什么RAK这个词在PLL设计里的含义不同团队多少有些差别但基本指向同一种东西参考路径上的多级分频组合。我在项目里遇到的RAK结构通常由R分频器、A计数器和K计数器级联构成用于把外部参考时钟和VCO反馈信号整形成合适的比较频率并支持不同的分频比配置。有些设计里R是参考预分频A和K再配合组成可编程分频因子有些设计里RAK出现在反馈路径的预分频器内部与Sigma-Delta调制器配合产生小数分频比。无论具体结构怎么排它在相位域里对应的数学关系是一样的假设输入信号相位是Фin经过一个分频比为D的分频器输出相位就是Фout Фin / D。这里有个值得注意的细节分频器本质上是一个“相位取模”器件它会周期性清除相位累加量。所以严格说分频器输出相位是输入相位在模2π意义下除以D建模时要把这个取模操作体现出来否则仿真结果会出现莫名其妙的相位漂移。2.2 反馈分频比的瞬态变化是建模关键RAK结构最核心的建模难点不是它的稳态分频比而是它的瞬态分频比变化。比如你要看N和N1分频切换时的相位误差实际发生在电路里的过程是这样的在某个参考时钟沿或反馈时钟沿到来时RAK内部计数器改变计数模式从每N个输入周期输出一个反馈脉冲变成每N1个输入周期输出一个反馈脉冲。这个变化不是瞬时的它发生在具体的某一个沿上。相位域建模时我用了一个非常实用的近似把分频器当成一个受控的相位累加器。当分频比为N时每检测到一个输入沿输出相位就增加(2π/N)的整数值当分频比切换成N1后输出相位的增量变成(2π/(N1))。这样建模的好处是分频比的切换被自然地映射成了输出相位的“相位台阶”。你只要在模型里维护一个整数计数值然后用计数结果直接驱动输出相位变量就能精确复现切换瞬间的相位跳变情况。2.3 与小数分频的关系RAK结构在小数分频PLL里还有一个重要作用配合Sigma-Delta调制器实现平均分频比的小数部分。Sigma-Delta调制器每次输出一个要么N要么N1的控制字交替切换分频比平均下来等效于N0.3或者N0.7这样的分数。如果你用传统的时域电路模型去仿真这种情况仿真器必须在每个参考周期内精确处理大量分频比切换事件步长会被压得很小。而在相位域模型里Sigma-Delta调制器的输出控制字可以直接作为一个离散输入信号驱动分频器模型模型内部根据控制字实时调整相位增量不需要仿真器去解析每一个切换沿。这也是相位域模型做小数分频杂散仿真时比晶体管级仿真快几个数量级的原因。3. 在Cadence Virtuoso中搭可仿真的相位域模型3.1 模型的分层设计思路我在Cadence里搭相位域模型的时候没有把所有功能写进一个巨型Verilog-A单元而是按模块拆成了四个独立cell分频器、PFDCP、环路滤波器、VCO。这样拆的好处是调试方便哪个模块行为不对就单独跑那个cell不用每次整个环路一起debug。四个cell之间用电压节点连接和真实电路连接关系一一对应。连接关系上注意一点分频器的输入来自VCO输出节点但VCO在相位域模型里输出的不是正弦波而是一个相位电压信号。为了让分频器模型能在这个相位电压驱动下工作我在VCO里额外输出一个“等效时钟”它是根据瞬时频率动态生成的脉冲串。这样分频器依然可以用传统的事件触发方式工作不用改成纯相位运算逻辑写起来省事很多。3.2 分频器Verilog-A代码示例下面给出一个我在Virtuoso里用的RAK反馈分频器简化版模型。这个模型支持分频比N并提供一个额外的切换控制端口frac_ctrl当frac_ctrl大于阈值时分频比切换为N1。实际RAK结构里如果还有R分频和K计数逻辑上都是相同的模式只是分频比D不同而已。include constants.vams include disciplines.vams module divider_frac(in, out, frac_ctrl); input in; output out; input frac_ctrl; electrical in, frac_ctrl; electrical out; parameter integer N_min 2; parameter real vth 0.5; parameter real vout_high 1.8; parameter real vout_low 0.0; integer count, base_div; real out_phase; analog begin (initial_step) begin count 0; base_div N_min; out_phase 0.0; end (cross(V(in) - vth, 1)) begin if (V(frac_ctrl) 0.5 * vout_high) base_div N_min 1; else base_div N_min; count count 1; if (count base_div) begin count 0; out_phase out_phase 2.0 * M_PI; end end V(out) (out_phase 0.0 ? vout_high : vout_low); // 用相位累加值的符号产生输出脉冲脉冲宽度由后续离散事件更新决定 end endmodule这段代码的思路是每个输入上升沿计数当计数值达到当前分频比时把内部相位累计变量增加2π同时清空计数器。输出电平在相位累计变量为正时输出高电平复位后输出低电平。这个写法很朴素但足够用于环路级仿真。实际项目中如果你想更精确地控制输出脉冲宽度可以在此基础上增加一个脉宽参数或者在计数器到值时只输出一个固定宽度的脉冲事件。3.3 PFDCP与环路滤波器的行为建模PFDCP的行为模型我一般用增益放大的方式来实现不再模拟上下电流源的开关细节。定义相位误差为ref_phase和div_phase之差然后输出一个平均电流include constants.vams include disciplines.vams module pfd_cp(pfd_in, pfd_fb, cp_out); input pfd_in, pfd_fb; output cp_out; electrical pfd_in, pfd_fb, cp_out; parameter real Kpd 100e-6; // A/rad parameter real min_err 1e-12; real phase_err, out_current; analog begin (cross(V(pfd_in) - 0.5, 1)) begin // 用时间戳计算参考沿到来此处简化处理 end phase_err V(pfd_in) - V(pfd_fb); out_current Kpd * phase_err; I(cp_out) out_current; end endmodule这里把PFD输入直接当作相位电压节点来用好处是模型非常简洁坏处是没有体现PFD作为离散边沿触发器的采样特性。实际PLL里PFD只有在相位误差存在的那些时刻泵出电流其他时间是高阻态。如果应用场景需要分析杂散和纹波这种连续增益模型就过于理想化了。所以我通常会准备两套PFD模型一套是增益模型做快速扫描一套是事件触发模型做精细杂散分析。环路滤波器不需要单独写代码直接用Virtuoso里的R、C、理想运放元件搭出来就行。这样滤波器的传递函数由真实电路特性决定你改电容值、电阻值时不需要改模型还可以顺带做PVT角度的tran仿真。元件值要和电荷泵增益、VCO增益匹配不然环路参数对不上。3.4 VCO行为模型VCO模型也是Verilog-A考虑相位与频率的积分关系。我写的VCO模型输出两样东西一个是瞬时相位电压ph_vco一个是等效输出时钟clk_vco。瞬时相位用idt算输出时钟则用相位穿越0/2π生成上升沿驱动后面的分频器。include constants.vams include disciplines.vams module vco_behavior(ctrl, clk_out, phase_out); input ctrl; output clk_out, phase_out; electrical ctrl, clk_out, phase_out; parameter real vco_gain 1e9; // Hz/V parameter real fc 3.3e9; // center frequency parameter real vctrl_nom 0.9; real phase_val, freq_inst; analog begin freq_inst fc vco_gain * (V(ctrl) - vctrl_nom); phase_val 2.0 * M_PI * idt(freq_inst, 0.0); V(phase_out) phase_val; V(clk_out) (sin(phase_val) 0.0 ? 1.8 : 0.0); end endmodule注意实际中VCO相位噪声、KVCO非线性、电源扰动对模型精度都有影响但在相位域模型阶段我通常先忽略这些只保留理想积分关系。等环路参数确定后再在相位噪声仿真阶段往VCO模型里注入noise源。4. N/N1切换的瞬时相位误差到底怎么仿真4.1 为什么要专门看N/N1切换跳频和分频比切换是PLL实际使用中最容易出问题的场景。典型的多模收发机在信道切换时分频比从一个信道对应的N跳变到另一个信道对应的N1甚至更大的步进PLL必然会出现一个瞬态的相位误差过冲然后通过环路反馈逐渐收敛回来。这个过冲的大小、持续时间直接决定了锁相环能否满足系统的settling time要求。更关键的是N/N1切换发生在小数分频的Sigma-Delta调制器中是每个参考周期都可能发生的。如果是平均分频比固定的小数工作模式每次N/N1切换引入的相位误差没有规律会被Sigma-Delta调制器整形到高频听起来问题不大。但要是在跳频快速切换过程中分频比在一个很短的窗口内剧烈变化环路滤波器来不及滤除误差就可能出现明显的输出频率过冲甚至失锁。相位域模型可以让你在几秒内看到这个过程而晶体管级仿真基本不可能。4.2 模型上如何注入分频比切换激励要仿真N到N1切换在RAK结构的分频器模型里加一个控制信号就够了。控制信号可以是分段电压源在想要切换的时刻从0V跳到1.8V让分频器模块内部的frac_ctrl从低电平变高电平。具体配置我会这么做把分频器模型的frac_ctrl端口接到一个pulse电压源设置pulse源初始电压0V延迟时间等于你要切换的时间点比如100us脉冲宽度足够长例如10us仿真开始时PLL处于锁定状态分频比为N在100us时刻frac_ctrl变高分频比切换为N1PLL进入重新锁定过程。仿真总时间取200us左右步长上限设成100ns或者更宽松相位域模型在这种步长下依然能给出平滑的瞬态曲线。如果你设的步长太紧反而会失去相位域模型的性能优势。4.3 相位误差波形的提取方法提取相位误差波形有两种办法。第一种是利用模型内部变量在VCO模型里已经把相位val引到了phase_out端口分频器的反馈相位也被PFD模块内部隐式处理了你可以在PFD模块里把“参考相位减去反馈相位”的结果直接引到额外的一个输出端口然后在ADE里plot这个端口电压。这是最简单的方法只要在PFD模型里加一个额外的analog输出就行。第二种是间接提取如果没有引内部相位可以分别plot参考时钟和VCO输出然后用Cadence Calculator里的phase()函数或cross()函数计算两者过零点时间差再换算成相位。这个方法更接近真实测试场景但步骤繁琐适合用来交叉验证模型的正确性。实际跑出来的波形通常是这样的分频比切换前相位误差在0附近小幅抖动切换发生瞬间相位误差会出现一个明显的正向或负向阶跃跳变幅度和分频比步进成正比随后在环路带宽决定的时间常数内呈指数衰减最终收敛到新的稳态。通过这个波形你可以直接读出切换引入的峰值相位误差、恢复时间等关键指标。5. 仿真不收敛、结果跳变的几类常见原因5.1 Verilog-A事件触发导致的收敛失败相位域模型里大量用到(cross(...))和(initial_step)这样的离散事件触发。这在Cadence Spectre里是常规操作但不收敛的坑也通常出在这里。我在项目中遇到过好几次“timestep too small”崩溃最后定位到的原因是分频器模型里(cross(V(in) - vth, 1))的vth设得太靠近输入信号的DC工作点输入信号在这个DC点附近反复穿越导致仿真器在每个穿越点都要缩步长。解决办法有几种把cross的阈值设成确定性较高的中间电平比如VCO输出高电平1.8V、低电平0V时阈值设0.5V或0.9V都行但不要设成0.2V这种接近低电平噪声带的数值给cross事件加滞回(cross(V(in) - 0.9, 1))再配合一个状态判断避免反复触发如果是数字脉冲信号驱动尽量用(above(V(in) - vth))替代cross在边界处的敏感性。5.2 VCO模型中的高频振荡问题VCO行为模型使用idt对瞬时频率积分时会在闭环里形成一个极高频的相位斜率。这个高频分量并不是真实的输出信号而是相位变量本身的剧烈变化。如果环路滤波器的带宽设得很高控制电压上的微小纹波被Kvco放大后又会反馈到相位域形成数值上的自激振荡。遇到这种问题我一般会在VCO的输出相位上加一个低通或者把Kvco在一阶上设定一个合理的range。更稳妥的方法是把VCO增益的绝对值控制在模型可处理的范围内例如VCO输出3.3GHz、KVCO为50MHz/V时控制电压波动1mV只带来50kHz的频率变化在相位域里就是每秒约3e5弧度的相位变化率这个数值量级在Spectre里可以正常处理。但如果KVCO设成10GHz/V同样的1mV纹波就会产生10MHz频率摆动相位斜率瞬间飙升仿真器肯定会报收敛问题。5.3 模型内部变量未初始化Verilog-A模型里用到的integer和real变量在(initial_step)里没有赋值或赋值顺序不对是导致瞬态结果一开始就紊乱的常见原因。尤其在分频器模型里count和out_phase如果初始化顺序颠倒输出脉冲的第一个沿会失真导致PFD一开始就捕获到错误的相位差整个环路从起始点就锁定了错误的频率。我的建议是在initial_step块里把所有内部变量统一清零或设置明确的初值不要依赖Verilog-A的默认值。即使Cadence文档里写了变量默认初始化为0实际跑多核并行仿真时不同processor之间的初始化顺序可能有差异这个坑一旦踩上非常难排查。显式初始化能最大程度保证一致性。5.4 混用瞬态仿真与噪声仿真的细节如果你在相位域模型上做噪声仿真或者跑pss/pnoise需要额外注意一个事情行为级模型里的(cross)事件在pss中不会被自动当作非线性器件对待多个不同域的模型并联后可能让仿真器无法识别周期稳态。我在Cadence里做相位域模型的pss仿真时通常会把分频器模型替换成更简单的基于电压控制的分频模型或者直接用SpectreRF的PLL噪声分析流程而不是让Verilog-A离散事件模型去负责所有功能。这算是Cadence仿真器目前在行为级模型上的一个限制写代码时就该提前规划好。6. 我这套模型的使用边界与后续扩展先别把这套相位域模型当成万能工具。它的适用范围是环路级动态响应、稳定性评估、分频比切换现象这类宏观指标。如果你要分析PFD死区对杂散的影响、CP上下电流源不匹配产生的参考杂散、VCO的相位噪声在环路里的传递特性那必须在模型里加入相应的非理想因素或者回到晶体管级仿真去做精细建模。我给自己的项目定了一条分工原则相位域模型只用于快速探索“如果改这个参数环路行为会怎么变”用最少的时间把设计空间压缩到几个候选点。之后再用晶体管级仿真在这几个候选点做精确验证。这样既没有完全抛弃行为模型的效率优势也没有盲目相信行为模型而丢掉精度。后续如果要扩展我建议按三个方向走。第一个方向是给VCO模型加相位噪声注入这样可以做出闭环输出相位噪声谱和实测频谱对比验证。第二个方向是给PFD/CP模型加死区、失配参数观察杂散的变化趋势。第三个方向是把Sigma-Delta调制器的高阶噪声整形模型集成进去在相位域里做完整的小数分频杂散评估。最后一个个人经验在Cadence里写Verilog-A行为模型不要追求立刻做一个“完全版”而是从最简单的增益模型开始跑通闭环之后逐步往里面加非理想因素。每加一个因素就同时看它给仿真收敛和结果精度带来的影响。我自己最初搭的版本只有一个PFD增益模块、一个理想VCO和一个理想分频器整个环路没有任何离散事件仿真快得惊人也正因为从简单开始后来排查每个非理想因素引入的问题时才没有陷入无从下手的境地。
02
RELATED NEWS

相关资讯

更多网站建设与数字化升级内容

03
WHY YAOTU

想打造同款高转化官网?

懂行业、懂生意,从建站到增长一站式陪跑

场景化定制

不做模板站,围绕你的业务场景量身设计,小众不撞款。

营销型架构

以转化目标组织内容与路径,让官网真正带来询盘。

全周期服务

设计、开发、运营、运维一体,上线只是开始。

免费获取你的建站方案

留下需求,专属顾问 24 小时内为你输出方案建议。