UVM之TLM通信基础概念

TLM是啥,为什么要用TLM?

TLM 就是 UVM 各个组件之间,传递 transaction(数据包)的 "专用通道"。

Driver、Monitor、Sequencer、Scoreboard、RM、Coverage 这些组件互相之间不能直接调用函数、不能直接访问变量,必须通过 TLM 端口 发数据、收数据。


为什么不用赋值?

  • 耦合太强
    一个组件改了,另一个直接报错
  • 线程不安全
    多线程同时读写会乱掉
  • 无法阻塞、同步
    数据来了你不知道,只能轮询
  • 无法层次化、复用
    换个环境就废了
  • 无法一对多广播
    一个 monitor 数据要同时给 sb + coverage,直接赋值做不到

基于以上问题,UVM 强制:组件之间必须用 TLM 通信,禁止直接访问。
简单说,TLM 让 UVM 各个组件变成模块化、可插拔、可复用。

一. TLM使用规则

  1. TLM 是事务级建模,只传 transaction,不传信号
  2. 端口永远是主动的(port)
  3. 实现永远是被动的(imp / export)
  4. 必须成对使用:发送 ↔ 接收
  5. 阻塞(blocking):会等待,要等对方接受完才返回;
  6. 非阻塞(nonblocking):不等待,发完立刻返回

二.TLM接口类型

  1. Put 类:主动发送数据,单向收发,分阻塞/非阻塞
  • 发送端调用:put(tr)
  • 接口列表
    uvm_blocking_put_port #(T)
    uvm_nonblocking_put_port #(T)
    uvm_put_port #(T)(阻塞 + 非阻塞)
  • 必须成对连接
    port → export / imp
  • 接收端实现
    task put(T tr)(阻塞)
    function bit try_put(T tr)(非阻塞)
  1. Get / Peek 类:主动获取数据,单向收发,分阻塞/非阻塞
  • get(tr):取出并删除
  • peek(tr):只看不取
  • 接口列表
    uvm_blocking_get_port
    uvm_blocking_peek_port
    uvm_blocking_get_peek_port(最常用)
    uvm_get_port、uvm_peek_port、uvm_get_peek_port
  • 必须成对连接
    port → export / imp
  • 接收端实现
    task get(output T tr)
    task peek(output T tr)
  1. Analysis 类:广播发送,一对多广播,非阻塞,环境数据分发
  • 只能调用 write(tr)
  • 接口列表
    uvm_analysis_port #(T)
    uvm_analysis_export #(T)
    uvm_analysis_imp #(T, IMP)
  • 接收端实现
    function void write(T tr)

三.TLM FIFO

  1. uvm_tlm_fifo #(T)
  • 支持:put_port/get_port
  • 不支持 analysis_port
  1. uvm_tlm_analysis_fifo #(T) (常用,analysis_fifo = 万能 FIFO)
    支持:analysis_port/put_port/get_peek_port

四.TLM 成对使用

发送端:主动发起请求,数据产生者;比如主动get数据,uvm_put_port;

接收端:被动响应,数据消费者;比如uvm_put_imp;

Export:中间传递端口,用于层次化连接;

  1. Put 成对
发送端 port 连接 接收端(imp/export) 调用方法
uvm_blocking_put_port uvm_blocking_put_imp / tlm_fifo.put_export put()
uvm_nonblocking_put_port uvm_nonblocking_put_imp try_put()
put_port put_imp put() / try_put()

连接规则:initiator.put_port.connect(target.put_imp);

比如drv发给rm

  1. Get / Peek 成对
获取端 port 连接 接收端(imp/export) 调用方法
uvm_blocking_get_port uvm_blocking_get_imp / fifo.get_export get()
uvm_blocking_peek_port uvm_blocking_peek_imp peek()
uvm_blocking_get_peek_port uvm_blocking_get_peek_imp / analysis_fifo get() / peek()

比如scoreboard从rm区数据做比对

  1. Analysis 成对
发送端 连接 接收端 调用
analysis_port analysis_imp / analysis_fifo write()

monitor发数据给rm和scoreboard

五.端口连接规则

port.connect(export);

export.connetc(imp);

  • 必须在connect_phase连接;
  • analysis port 不能直接连 get/peek port,必须加 uvm_tlm_analysis_fifo 中转。
  • 所有端口泛型参数必须一致(都用 my_transaction)。
  • put_port和put_imp:发送推数据
  • get_port和get_imp:接收拉数据
  • analysis_port和analysis_imp+write:广播专用,比如monitor

六.TLM优缺点

优点:

  1. 高抽象层级,脱离底层信号;不用时序,不用操作wire信号,直接传送事物,代码简洁,开发速度快,验证效率高;
  2. 组件解耦,标准化接口;比如drv,mon,rm等只靠TLM端口通信,互相不依赖内部实现,更换、复用、移植组件非常方便,符合面向对象+接口隔离思想;
  3. 天然支持层次化连接;port->export->imp层级转发,顶层env的connect_phase只做连接即可,内部组件不用改动;
  4. 阻塞/非阻塞通信灵活;阻塞适合同步交互、控制流水、天然同步时序;非阻塞适合异步收发、高吞吐;
  5. 便于后续收集覆盖率和调试打印;事物可以自带打印函数、时间戳、自动化比对等;
  6. 跨平台、可复用、易于升级;TLM是UVM标准,不同项目、不同IP之间通信协议统一,组件复用极强;

缺点:

  1. 抽象层级高,和真实硬件有差距;不是真实信号时序,无法反映精细时序、毛刺、跨时钟域和信号竞争等硬件细节;
  2. 仿真精度不足,低层缺陷难发现;只做事物级交互,时序违规、握手错误、协议细微违规容易遗漏,必须搭配monitor抓信号;
  3. 占用仿真内存高;比如频繁创建、拷贝、传送事物,大批量传输数据内存开销信号通信大;
  4. 初学者上手门槛高;端口种类多;连接关系和实现规则容易混淆,调试链路不通比较费时间;
  5. 阻塞TLM容易造成死锁:比如组件A等待B,B等待A,任务挂起死锁,需要仔细设计同步逻辑;
  6. analysis_port是广播型,可控性弱;比如一对多广播,无法单独控制某一个接口,流量大时容易冗余、影响性能仿真;
  7. 不适合物理层等底层验证;引脚级、时序、电平、串并转换等场景,TLM力不从心,还需要依赖信号级驱动和采样;

七.使用场景

组件内部环境之间用TLM,可高效传输数据,解耦复用;

验证环境与DUT交互用信号级,可保证硬件时序精度;

  1. monitor发包给scoreboard和rm,进行数据比对;

mon.put_port.connect(sb.put_imp);

使用uvm_tlm_fifo

// Monitor put_port → FIFO put_export

mon.put_port.connect(tlm_fifo.put_export);

// FIFO get_export → Scoreboard get_port

sb.get_port.connect(tlm_fifo.get_export);

或者uvm_tlm_analysis_fifo

// ========================

// blocking_put_port → ana_fifo.put_export

// ========================

mon.put_port.connect(ana_fifo.put_export);

// ========================

// get_peek_port ← ana_fifo.blocking_get_peek_imp

// ========================

sb.bgp_port.connect(ana_fifo.blocking_get_peek_imp);

  1. A环境drv和B环境的rm通信;

// RM 的 analysis port → FIFO 的 analysis_export

eA.rm.ap.connect(ana_fifo.analysis_export);

// Driver 的 get_peek_port → FIFO 的 blocking_get_peek_imp

eB.drv.bgp_port.connect(ana_fifo.blocking_get_peek_imp);

相关推荐
xwz_new4 天前
Verilog之CDC 跨时钟域
ic验证
xwz_new5 天前
UVM之sequencer
ic验证
xwz_new5 天前
Verilog之常见时钟分频
ic验证
xwz_new6 天前
system verilog之$cast
ic验证
xwz_new11 天前
数字芯片验证技能树概述(一)
ic验证
不会武功的火柴4 个月前
UVM验证入门(18)-Callback机制
systemverilog·ic验证·uvm方法学
愤怒学习的白菜4 个月前
0 trivial:UVM的空壳平台
学习·uvm·ic验证
不会武功的火柴4 个月前
UVM验证入门(15)-uvm_agent代理
systemverilog·ic验证·uvm方法学
SuperGQB8 个月前
UVM验证(三)—UVM机制(1)
systemverilog·ic验证·uvm方法