
1. 项目概述从功耗焦虑到精准节能在嵌入式处理器和SoC设计领域功耗已经和性能、面积一起成为了决定芯片成败的“铁三角”之一。尤其是在移动设备、物联网终端这些对续航和散热有严苛要求的场景里每一毫瓦的功耗都弥足珍贵。我们团队在多年的芯片设计实践中发现了一个普遍但常被忽视的功耗“黑洞”缓存Cache。随着处理器性能的提升缓存的容量越来越大访问频率也越来越高其动态功耗在系统总功耗中的占比常常能轻松突破20%甚至更高。这就像家里一台24小时待机但大部分时间闲置的电器虽然单次耗电不大但积年累月下来浪费的电能相当可观。传统的低功耗设计方法比如动态电压频率调节DVFS或者电源门控Power Gating要么控制粒度较粗要么引入的唤醒延迟和状态保存开销较大对于缓存这种需要快速响应的关键模块并不总是适用。而最经典的时钟门控Clock Gating技术其效果又严重依赖于软件工程师对硬件状态的精确感知和手动控制这在复杂多变的程序执行流中几乎是不可能完成的任务。缓存何时空闲、空闲多久对于写软件的程序员来说是完全透明的他们无从知晓自然也就无法精准地为其关闭时钟。正是基于这个痛点我们提出并实现了一种基于比较的自适应时钟门控方案。它的核心思想非常直接让硬件自己“看”着缓存的工作状态一旦发现它“闲着没事干”就自动把它的时钟关掉等有活干了再立刻打开。整个过程对软件完全透明无需任何额外的编程负担。我们在一颗基于TSMC 65nm工艺的SoC芯片上实现了该技术实测在典型的Dhrystone基准测试中为整个SoC带来了平均30.3%的功耗降低而付出的面积代价几乎可以忽略不计性能也毫无损失。这相当于在不改变处理器任何计算能力的前提下凭空“省”出了近三分之一的电量对于提升终端设备的续航能力意义重大。2. 时钟门控技术演进与CACG方案解析在深入我们的方案之前有必要先梳理一下时钟门控技术的来龙去脉理解为什么我们需要一种“自适应”的方法。2.1 传统时钟门控的局限最基础的时钟门控可以看作一个带使能端的与门当时钟使能信号clk_en为高时时钟正常输出为低时输出恒为低电平即门控。动态功耗主要来自于CMOS电路中晶体管在时钟跳变0-1, 1-0时的充放电过程。关掉时钟就消除了这些不必要的跳变从而节省功耗。1. 可编程时钟门控PCG这是最直观的方法如图1所示。系统为某个模块比如一个外设控制器提供一个可编程的时钟门控控制寄存器。当软件判断该模块暂时不用时就向这个寄存器写0硬件电路会据此产生低电平的clk_en信号关闭该模块的时钟。想再用时再写1打开。优点电路简单面积开销极小就是一个寄存器、一个锁存器加一个与门。缺点非透明需要软件深度参与。开发者必须非常清楚模块的工作状态并在代码中精确地插入控制指令。这增加了软件复杂度和出错风险。粒度粗通常以整个模块为单位进行开关无法应对模块内部更细粒度的空闲状态。易出错如果软件错误地提前关闭了时钟或者忘记打开时钟会导致功能失败且这类错误难以调试。2. 基于单比较器的时钟门控SCCG这种方法更精细常用于流水线寄存器。其原理是监测流水线级间数据的变化如果当前时钟周期输入到寄存器的数据与上一个周期锁存的数据完全相同那么即使时钟有效寄存器输出的值也不会改变。此时就可以关闭这个寄存器的时钟避免其无谓的翻转功耗。优点透明硬件自动判断、细粒度可以控制到单个寄存器。缺点面积和功耗开销大。每个需要门控的寄存器都需要一个比较器来比较其输入和当前值。对于32位或64位宽的数据通路比较器的规模会非常可观其自身引入的功耗和面积可能抵消掉一部分省电收益。注意SCCG是一种非常有效的微架构级优化但它优化的对象是寄存器级的动态功耗。而我们的目标是缓存SRAM阵列这类更大的、功耗更集中的模块需要一种与之匹配的、开销更小的控制策略。2.2 基于比较的自适应时钟门控CACG原理我们的CACG方案可以看作是在PCG的“自动控制”和SCCG的“细粒度感知”之间取了一个平衡点。它不再关注单个数据位是否变化而是关注模块整体的工作状态和外部访问请求的模式。核心状态机我们为受控模块此处即缓存定义了三个状态BUSY忙碌模块正在被访问或处理数据。IDLE空闲模块未被访问且内部无活动。END结束一个从BUSY到IDLE的中间过渡状态用于确保控制信号的稳定和消除毛刺。关键信号监测CACG电路持续监测两个关键信号外部请求Request来自CPU或其他主设备的读写请求信号。模块内部状态State由模块自身逻辑产生的状态指示。工作原理与判断逻辑电路的核心是一个历史寄存器和一个比较器。历史寄存器记录下上一次有效的访问请求包括地址、操作类型等。在每个时钟周期比较器将当前的访问请求与历史记录进行比较并结合当前模块状态产生最终的时钟使能信号clk_gate_en。具体在什么情况下可以关闭缓存时钟呢我们结合缓存的实际工作场景总结出两条核心规则无请求且空闲时关门当外部没有读写请求request_valid为低并且缓存自身处于IDLE状态时说明缓存确实无事可做可以安全地关闭其时钟。这是最直接的空闲检测。连续读相同地址时关门这是一个更精细的优化。当外部请求是连续的读操作且读取的地址与上一次读操作的地址完全相同时如果缓存处于IDLE状态那么其输出数据必然保持不变。在这种情况下即使有请求缓存SRAM阵列也无需进行新的访问操作因为数据已经准备好或可被保持因此可以关闭时钟。这在执行循环读取某个变量或栈顶数据时非常有效。电路实现与毛刺消除图3所示的CACG单元包含了必要的同步逻辑锁存器来确保产生的clk_gate_en信号是“无毛刺”的。这一点至关重要因为带有毛刺的时钟使能信号如果直接用于门控时钟可能会产生极窄的时钟脉冲导致触发器误动作引发功能错误。我们的设计确保了使能信号的开启和关闭都严格与时钟边沿对齐保证了电路的可靠性。CACG的优势总结对比前两种技术CACG的优势非常明显对用户透明完全由硬件自动完成状态检测和时钟控制软件无需任何干预降低了开发和调试难度。控制更高效由于判断逻辑在模块内部响应速度极快可以跟上模块状态频繁切换的节奏非常适合缓存这类访问模式变化快的部件。面积开销可忽略一个缓存模块如16KB的D-Cache只需要一个CACG单元相比SCCG为每个寄存器配比较器的方式面积开销微乎其微。在我们的实现中整个芯片仅增加了16个这样的单元。3. 缓存功耗优化将CACG应用于数据缓存理解了CACG的原理后我们来看如何将它精准地应用到嵌入式处理器的数据缓存上实现功耗优化。3.1 为何缓存是功耗优化的理想目标在RISC架构的处理器中如ARM MIPS RISC-V普遍采用加载-存储Load-Store架构。这意味着只有专门的LOAD和STORE指令才能访问内存包括缓存而所有算术逻辑运算ALU指令的操作数都必须在寄存器中。因此一个典型程序的指令流可以大致分为三类ALU指令进行运算不访问数据缓存。加载/存储指令访问数据缓存。跳转与分支指令改变控制流通常也不直接访问数据缓存。不同程序的指令混合比例差异很大。例如计算密集型程序如科学计算、密码学ALU指令占比极高可能超过70%。这意味着大部分时间CPU都在和寄存器打交道数据缓存处于“旁观”状态。数据密集型程序如媒体处理、数据库查询LOAD/STORE指令占比显著升高缓存访问频繁。关键在于当CPU在执行非LOAD/STORE指令时如果数据缓存没有待处理的写回或维护操作它就处于事实上的空闲状态。然而在传统设计中即使空闲缓存的时钟网络和部分电路仍在每个周期翻转消耗着可观的动态功耗。我们的目标就是抓住这些空闲周期。3.2 CACG缓存功耗优化电路设计图5展示了我们将CACG集成到数据缓存的具体方法。我们主要监控数据缓存的读端口因为读操作是最频繁的。监控信号选取读地址缓存SRAM的读地址输入。读使能指示当前周期是否是一个有效的读请求。写使能指示当前周期是否是一个写请求。在缓存空闲判断中写操作通常需要保持时钟有效以确保数据正确写入。工作流程历史记录CACG单元内部有一个历史寄存器用于记录上一个时钟周期中有效的读操作的地址如果上一个周期没有读操作则记录一个无效标记。比较判断如果当前周期没有有效的读使能且写使能无效同时缓存控制逻辑反馈状态为IDLE则触发上述规则1关闭时钟。如果当前周期有一个有效的读操作比较器会将其地址与历史寄存器中记录的地址进行比较。如果地址相同且写使能无效缓存状态为IDLE则触发上述规则2关闭时钟因为连续读同一地址数据不变。如果地址不同或者有写操作则保持时钟开启并将当前读地址更新到历史寄存器中。时钟门控执行CACG单元产生的clk_gate_en信号最终控制一个时钟门控单元一个集成的、无毛刺的时钟门控Cell这个单元负责将全局时钟GCLK转换为缓存实际使用的门控时钟CACHE_CLK。一个具体的例子假设一小段循环代码for (int i0; i10; i) { sum array[i]; }在计算sum array[i]时CPU需要先执行一条LOAD指令从缓存读取array[i]然后执行ADD指令。在ADD指令执行的周期里如果没有新的LOAD指令数据缓存就处于空闲状态。我们的CACG电路能立即检测到这种“请求间隙”并关闭缓存时钟。当下一条LOAD指令到来时电路又能迅速打开时钟确保访问延迟不受影响。如果循环体内访问的是同一个变量例如sum本身CACG还能识别出连续读同一地址的情况进一步节省功耗。实操心得状态判断的精确性缓存“空闲”状态的判断是核心也是容易出问题的地方。不能简单地认为没有外部请求就是空闲。缓存内部可能在进行写回、一致性维护对于多核缓存或预取等后台操作。因此我们必须从缓存控制器内部获取一个真正的IDLE状态信号这个信号需要综合考量所有内部状态机。在我们的实现中这个信号是在缓存控制器中专门生成并输出给CACG单元的确保了判断的准确性避免了在缓存忙时误关时钟导致的数据错误。4. SoC集成实现与实测结果分析理论再好也需要硅片验证。我们将这套CACG缓存功耗优化方案集成到了一款真实的SoC芯片中并进行了流片和实测。4.1 芯片与测试平台工艺节点TSMC 65nm LP低功耗CMOS工艺。芯片面积5.26 mm x 5.96 mm。核心处理器Unicore-2一款32位RISC处理器支持定点、浮点和多媒体指令集采用哈佛架构。缓存配置指令缓存I-Cache和数据缓存D-Cache各16KB均采用2级TLB架构。最高频率800MHz。峰值功耗约400mW。CACG集成在四个关键缓存模块I-Cache, D-Cache, I-TLB, D-TLB中各插入4个CACG单元共计16个。每个缓存模块的SRAM阵列和部分控制逻辑由独立的CACG单元控制。为了准确测量功耗我们搭建了专门的测试平台如图7所示包括可编程电源、测试主板和上位机软件。芯片的功能首先在其他验证平台上确保正确。在功耗测试时我们在系统中增加了一个CACG使能寄存器。通过配置该寄存器我们可以动态地开启或关闭整个CACG功能从而在完全相同的条件下对比“优化前”和“优化后”的功耗得到最纯净的优化效果数据。4.2 基准测试与功耗数据我们选取了三个业界经典的CPU性能基准测试程序来评估功耗优化效果Dhrystone侧重整数和逻辑运算性能的测试是典型的计算密集型程序。ALU指令占比高内存访问相对较少。Whetstone侧重浮点运算性能的测试同样属于计算密集型。Stream一个简单的合成测试程序用于测量可持续的内存带宽。它需要持续地、大规模地读写内存数据是典型的数据密集型程序。测试方法在SoC上分别运行这三个测试程序的核心循环每次运行300万次迭代。分别记录在CACG功能关闭和开启时整个芯片的平均功耗。结果对比如图8所示。基准测试类型无CACG功耗 (mW)有CACG功耗 (mW)功耗降低降低百分比Dhrystone计算密集型31021694 mW30.3%Whetstone计算密集型29820890 mW30.2%Stream数据密集型33527560 mW17.9%结果分析显著的计算密集型优势在Dhrystone和Whetstone测试中功耗降低都达到了约30%。这完美印证了我们的设计初衷对于ALU指令占比高的程序缓存有大量的空闲周期CACG技术可以非常高效地利用这些周期关闭时钟从而节省大量动态功耗。数据密集型程序效果减弱在Stream测试中功耗降低约为18%。这是因为Stream程序持续进行高强度的内存流读写缓存一直处于忙碌状态空闲周期很少。CACG电路能够发挥作用的机会自然就少了。这个结果也从反面证明了我们的方案是“智能”的只在真正空闲时才动作不会影响高负载下的性能。面积与性能开销面积增加的16个CACG单元相对于整个数百万门级的SoC来说面积开销小于0.1%完全可以忽略不计。性能在所有测试中开启CACG前后程序完成相同工作量所需的时钟周期数完全一致。这意味着CACG电路的判断和开关动作是在一个时钟周期内完成的没有引入任何额外的访问延迟或流水线停顿实现了零性能损失。4.3 与同类技术的对比为了更客观地评估我们将结果与学术界报道的类似工作进行了对比与基于前向预测器的L1数据缓存功耗优化方案对比该方案通过预测数据是否可从流水线直接转发来避免缓存访问平均节省了36%的缓存功耗。其节省比例略高于我们但该方案需要复杂的预测器逻辑设计复杂度和面积开销远大于我们的CACG方案。我们的方案在实现简易性和开销上优势明显。与基于单比较器的流水线时钟门控方案对比该方案通过仿真显示能为整个处理器节省20.8%的功耗。我们的方案在真实芯片上实现了30%的功耗降低且针对的是功耗占比更大的缓存模块实际效益更高。注意事项工艺角与电压温度变化的影响在实际芯片设计中CACG电路本身也需要考虑工艺偏差、电压波动和温度变化的影响。时钟门控单元的使能信号路径需要和时钟路径一样进行严格的时序分析确保在最差工艺角SS低电压高温下使能信号也能在时钟有效边沿之前稳定建立否则会导致门控失败或产生毛刺。我们在设计时对该路径进行了约束加固并留出了足够的时序余量。实测芯片在不同电压0.9V-1.1V和温度-40°C到125°C下CACG功能均工作正常功耗节省效果稳定。5. 常见问题、扩展应用与设计心得在实际的工程落地和后续推广中我们遇到并解决了一些典型问题也看到了这项技术更广阔的应用前景。5.1 实施中的常见问题与排查Q1插入CACG后芯片在某些极端用例下出现功能错误如何排查A1这通常是因为“空闲状态”判断不准确导致的。排查步骤如下首先关闭CACG功能确认功能错误消失定位问题与CACG相关。检查缓存控制器的IDLE状态生成逻辑。使用逻辑分析仪或仿真工具抓取在出错场景下缓存控制器输出的IDLE信号波形。确认在缓存实际进行内部操作如写回、替换算法更新LRU位时IDLE信号是否错误地变为了高电平。检查CACG的请求监控逻辑。确认其监控的“请求无效”条件是否完备。例如在某些总线协议中请求可能被拆分或延迟需要确保CACG能正确识别这些情况。进行门级仿真并关注时钟门控单元的输出时钟CACHE_CLK。检查在开关瞬间是否有毛刺或者时钟使能信号clk_gate_en的时序是否满足建立/保持时间要求。Q2功耗节省效果没有达到预期可能是什么原因A2程序特性如Stream测试所示数据密集型程序本身节省空间有限。这是正常现象。监控粒度太粗如果为一个很大的缓存块如整个32KB缓存只使用一个CACG单元那么只要该块内任何一部分被访问整个块的时钟都无法关闭。可以考虑分区门控将大缓存分成多个独立的、可分别门控的Bank例如4个8KB Bank这样空闲的Bank可以单独关电进一步提升效率。状态判断过于保守如果IDLE状态判断条件过于严格导致很多本可门控的周期被错过。需要结合微架构行为在确保功能正确的前提下适度放宽判断条件。Q3CACG会增加静态功耗吗A3CACG逻辑本身由标准单元构成会增加极少量静态功耗主要是漏电。但这部分开销与它节省的动态功耗相比几十毫瓦几乎可以忽略不计。总体来看动态功耗的节省远远大于静态功耗的增加净收益是显著的。5.2 技术的扩展应用CACG的思想并不局限于数据缓存。任何具有“忙-闲”状态且空闲可预测的模块都可以应用此技术进行功耗优化。我们在后续的项目中已经成功将其扩展到流水线停顿当处理器流水线因数据冲突、控制冲突而停顿时大部分流水段是空闲的。可以应用CACG来关闭这些空闲段的时钟。浮点运算单元对于非每周期发射浮点指令的处理器FPU经常空闲。可以监控浮点指令发射队列在队列为空且当前无执行指令时关闭FPU时钟。专用硬件加速器如图像处理、加解密等加速器在工作间隙存在明显的空闲期是CACG的理想应用目标。5.3 设计心得与总结回顾整个项目从提出想法到流片验证有几点深刻的体会功耗优化需要“对症下药”缓存功耗高但高在哪里主要是动态功耗。动态功耗怎么省关时钟最直接。问题就转化为如何精准、自动、无感地关时钟CACG给出了一个简洁而有效的答案。它没有追求最复杂的预测算法而是用最小的硬件代价解决了最实际的工程问题。“透明性”是工程友好的关键一个需要软件深度配合的硬件优化特性其推广难度会大大增加。CACG的硬件自动控制特性使得软件工程师无需学习新的编程模型无需修改现有代码就能享受到功耗优化带来的红利这是它能够被产品团队快速接纳的重要原因。面积与功耗的权衡永远是主题芯片设计是权衡的艺术。SCCG太“重”PCG太“笨”。CACG找到了一个很好的平衡点用几乎可忽略的面积开销十几个门控单元换来了30%的系统级功耗降低投资回报率极高。硅片验证是试金石仿真数据再漂亮也比不上实测波形有说服力。当在实验室里亲眼看到开启CACG后电源表上显示的电流值实实在在地下降时那种成就感是无与伦比的。这也提醒我们任何低功耗设计都必须考虑实际工艺、电压、温度的影响并进行充分的角落Corner验证。这项基于比较的自适应时钟门控技术以其低开销、高效益、易集成的特点已经成为我们团队后续低功耗SoC设计的标配技术之一。它证明了在追求极致能效的道路上有时一个巧妙而简单的硬件设计比复杂的算法更能直击要害。