跳转至

输入查询内容

    本页内容

    uvm_tlm_fifo::flush() 不再向 get_ap 广播,VCS 两项队列实测存在残留(S9)

    已复现的目标库问题

    目标库 FIFO 清场残留已复现;无并发边界的显式排空已验证。

    影响范围

    依赖 uvm_tlm_fifo::flush 清除残留事务时,至少填入两项对照;并发 producer/consumer 必须先停止。

    具体差异

    旧行为(1.2):先 while(r) r = try_get(t) 循环排空(走 uvm_tlm_fifo::try_get每条都会触发 get_ap.write(t) 分析广播),之后才检查"仍有残留且存在阻塞 get"并报 flush failed 错误。新行为(2.0):先 m_clear_zombie_gets() 清理已被 kill 的 get 进程;若 m.num() > 0 && m_pending_blocked_gets.size() != 0直接报错并 return,不做任何清空;否则用 m.try_get(t)(直接操作内部 mailbox,不触发 get_ap 分析广播)排空。净效果:① flush 时序对分析端口的副作用被移除;② 存在阻塞 get 时 FIFO 内容保持不动(1.2 会尽量排空)。

    修改方案

    在已确保没有并发 producer / 阻塞 consumer 的复位或清场边界,使用 while (fifo.try_get(item)) 排空并断言 fifo.used()==0;该公开方法将 mailbox 返回值归一成 bit,且保留 get_ap 广播。若刻意不需要广播,应在用户派生类中实现明确的排空策略并单独验证。并发场景须先停止参与方,不可仅将 flush 换成循环后宣称等价。

    uvm_tlm_fifo#(packet) 清场,旧调用为:

    fifo.flush();
    

    目标库中先停止生产者,再显式取空。packet 换成 FIFO 的实际数据类型:

    1
    2
    3
    4
    5
    packet discarded;
    while (fifo.try_get(discarded)) begin
    end
    if (fifo.used() != 0)
      `uvm_error("FIFO_DRAIN", "FIFO still contains pending items")
    

    try_get 会向 get_ap 广播取出的项;先确认下游把这类清场当作丢弃还是正常消费。并发生产或仍有阻塞消费者时,应先完成停机握手,再执行此片段。

    FIFO 中原有两项 1.2 2.0
    flush 后广播次数 2 0
    flush 后剩余项数(归档 VCS 构建) 0 1
    继续显式取空后的剩余项数 0 0

    兼容措施与范围:兼容措施不修复 flush 残留;try_get 排空仅用于收发已停止的边界,并保留 get_ap 广播。

    已知限制KI-007

    迁移后验证

    停止 producer/consumer 后放入至少两项,清场后断言 used=0;另检查广播次数符合下游契约。

    记录本条结果M08-001 · 状态与证据

    已有实测与复现

    VCS W-2024.09-SP2-8、同一无并发用例放入两个 int 后,1.2 flush 广播 2 次且 used=0;2.0 广播 0 次但 used=1。本机 mailbox::try_get 在原有两项时返回整数 2,而 2.0 源码 bit r; ... r = m.try_get(t) 将其截为 0,与循环提前退出的现象一致。该观察限定于本机 VCS 与测试条件,不据此声称所有仿真器都有同样结果。

    补充查阅

    扫描定位与记录结果

    有扫描规则,覆盖部分可识别写法。脚本检查名称、参数和部分 FLAG 表达式,并对少数直接声明关联使用点;未做完整类型解析或预处理,行为结果仍需验证。

    • S9 · 启发式:uvm_tlm_fifo::flush() 广播变化,VCS 两项 FIFO 实测残留一项。 按调用行识别 TLM FIFO 的 flush,包括同文件派生类的继承调用;排除已知 packer/printer 等无关接收者。未知接收者降为提示,须核对跨文件继承、typedef 和实际对象。
    uv run tools/uvm_migration_scan.py <SoC代码目录> --rules S9
    

    核对命中对象及生效分支后,在条目清单记录修改与验证证据;扫描规则记录用于整理命中位置。

    扫描器下载、输入范围与报告说明

    源码与标准依据

    核查方式:源码与实测核对。实测仅覆盖本条所列场景。

    VCS 内置 UVM-1.2uvm_tlm_fifos.svh:172

    VCS 内置 uvm-ieee-2020-2.0uvm_tlm_fifos.svh:200

    标准依据:IEEE 1800.2-2020 §12.2.8.2.6(2.0 源码标注)

    标为“源码标注”或未注明原文核对的条款仅作定位;具体库行为以源码和实测为准。

    引用代码(高亮为引用行);上方行号链接可直接定位。

    src/vcs-uvm-1.2/tlm1/uvm_tlm_fifos.svh
      // Removes all entries from the FIFO, after which <used> returns 0
      // and <is_empty> returns 1.
    
      virtual function void flush();
        T t;
        bit r;
    
        r = 1; 
        while( r ) r = try_get( t ) ;
    
        if( m.num() > 0 && m_pending_blocked_gets != 0 ) begin
          uvm_report_error("flush failed" ,
                   "there are blocked gets preventing the flush", UVM_NONE);
        end
    
      endfunction
    
    endclass 
    

    完整源码 · SHA256:f4de9fa81bff8301401a46a2b108a88d767dab7f5a78a4d0e0f2ed0ecd63020e

    src/vcs-uvm-ieee-2020-2.0/tlm1/uvm_tlm_fifos.svh
      // Removes all entries from the FIFO, after which <used> returns 0
      // and <is_empty> returns 1.
    
      virtual function void flush();
        T t;
        bit r;
    
        m_clear_zombie_gets();
    
        if( m.num() > 0 && m_pending_blocked_gets.size() != 0 ) begin
          uvm_report_error("flush failed" ,
                   "there are blocked gets preventing the flush", UVM_NONE);
          return;
        end
    
        r = 1; 
        while( r ) r = m.try_get( t ) ;
    

    完整源码 · SHA256:fe915359c5e25996ddb3cf93580e80d18a4d39ff0f290ab5c69c386a1ff5bef6

    术语解释 · 兼容配置

    返回TLM · 迁移清单

    版本适用范围