1 Sequencer和Driver

sequencer和item只在合适的时间点产生需要的数据,至于怎么处理数据,则由driver来实现。为了便于item传输,UVM专门定义了匹配的TLM端口供sequencer和driver使用:

uvm_seq_item_pull_port #(type REQ=int, type RSP=REQ) 
uvm_seq_item_pull_export #(type REQ=int, type RSP=REQ) 
uvm_seq_item_pull_imp #(type REQ=int, type RSP=REQ, type imp=int)

由于driver是请求发起端,所以在driver 一侧例化了下面两种端口: 

uvm_seq_item_pull_port #(REP, RSP) seq_item_port

uvm_analysis_port #(RSP) rsp_port

而sequencer 一侧则为请求的响应端,在sequencer 一侧例化了对应的两种端口:

uvm_seq_item_pull_imp #(REQ, RSP, this_type) seq_item_export

uvm_analysis_export #(RSP) rsp_export

通常情况下,用户可以通过匹配的第 一对 TLM 端口 完成item 的完整传送,即driver::seq_ item_port和sequencer::seq_ item_ export。这一对端口在连接时同其他端口连接方式一样,即通过 driver::seq_item_port.connect(sequencer::seq_item_export)完成。这一种类型的TLM端口支持如下方法:

•    task get_next_item(output REQ req_arg): 采取blocking的方式等待从sequence获取下一个item。

•    task try_next_item(output REQ req_arg): 采取nonblocking 的方式从 sequencer获取item, 如果立即返回的结果req_arg为null, 则表示sequence还没有准备好。
•    function void item_done(input RSP rsp_arg=null): 用来通知sequence当前的sequence item已经消化完毕,可以选择性地传递RSP参数,返回状态值。

•    task wait_for_sequences(): 等待当前的sequence直到产生下一个有效的item。

•    function bit has_do_available(): 如果当前的 sequence 准备好而且可以获取下一个有效的 item, 则返回 I, 否则返回 0。
•    function void put_response(input RSP rsp_arg): 采取 nonblocking 方式发送 response, 如果成功返回1, 否则返回0。
•    task get(output REQ req_ arg): 采用 get 方式获取 item。
•    task peek(output REQ req_arg): 采用 peek 方式获取 item。
•    task put(input RSP rsp_arg): 采取 blocking 方式将 response 发送回 sequence。

上面这一类端口功能主要用来实现 driver 与 sequencer 的 request 获取和 response 返回。读者在这里需要了解关于 REQ 和 RSP 类型的一致性, 由于 uvm_sequencer 与 uvm_driver 实际上都是参数化的类:

uvm_sequencer #(type REQ=uvm_sequence_item, RSP=REQ)

uvm_driver #(type REQ=uvm_sequence_item, RSP=REQ)

自定义 sequencer或driver 时, 可以使用默认类型 type REQ = uvm_sequence_item, 以及 RSP 与 REQ 类型保持一致。 这会带来一个潜在的类型转换要求,即 driver 得到 REQ 对象 (uvm_sequence_item) 在进行下一步处理时, 需要进行动态的类型转换, 将 REQ 转换为 uvm_sequence_item 的子类型才可以从中获取有效的成员数据;而另一种可行的方式是在自定义 sequencer 和 driver 时就标明其传递的具体 item 类型, 这样就不用再进行额外的类型转换了。 通常情况下 RSP 类型与 REQ 类型保持一致, 这么做的好处是便于统一处理, 方便 item 对象的复制、 修改等操作。
driver 消化完当前的 request 后, 可以通过 item_done(input RSP rsp_arg=null)方法来告知 sequence此次传输已经结束, 参数中的 RSP 可以选择填入, 返回相应的状态值。 driver 也可以通过 put_response()或 put()方法来单独发送 response。此外发送 response 还可以通过成对的 uvm_ driver::rsp _port和uvm_driver: :rsp_export端口来完成,方法为 uvm_driver::rsp_port::write (RSP)。

事务传输实例:

class bus_trans extends uvm_sequence_item;
rand int data;
`uvm_object_utils_begin(bus_trans)
`uvm_field_int(data, UVM_ALL_ON)
`uvm_object_utils_end
...
endclass class flat_seq extends uvm_sequence;
`uvm_object_utils(flat_seq)
...
task body();    //相当于run()
uvm_sequence_item tmp;   //父类句柄
bus_trans req, rsp;      //子类句柄
tmp = create_item (bus_trans::get_type(), m_sequencer, "req"); //创建item
void'($cast (req, tmp));   //父类句柄指向子类句柄,cast转换
start_item(req);       //开始发送item  立即返回等待driver.get_next_item
reg.randomize with {data == 10;};  //item 随机化
`uvm_info ("SEQ", $sformatf ("sent a item \n %s", req. sprint()), UVM_LOW)
finish_item(req);      //结束发送   等待仲裁
get_response(tmp);      //得到response数据tmp 等待drive.item_done 父类句柄
void'($cast (rsp, tmp));   //父类句柄指向子类句柄,cast转换
`uvm_info("SEQ", $sformatf("got a item \n %s", rsp.sprint()), UVM_LOW)
endtask
endclass class sequencer extends uvm_sequencer;
`uvm_component_utils(sequencer)
...
endclass class driver extends uvm_driver;
`uvm_component_utils(driver)
...
task run_phase(uvm_phase phase);
REQ tmp;  //默认父类句柄
bus_trans req, rsp;
seq_item_port.get_next_item(tmp); // 从 sequencer 获取有效的 request item
void'($cast (req, tmp));
`uvm_info("DRV", Ssformatf ("got a item \n %s", req. sprint()), UVM_LOW)
void'(Scast(rsp, req.clone()));    //子类对象克隆完返回父类句柄
rsp.set_sequence_id(req.get_sequence_id()); //便于数据返回
rsp.data += 100;
seq_item_port.item_done(rsp);   //response item 对象返回给 sequence
`uvm_info("DRV", Ssformatf ("sent a item \n %s", req. sprint()), UVM_LOW)
endtask
endclass class env extends uvm_env;
sequencer sqr;
driver drv;
`uvm_component_utils(env)
...
function void build_phase(uvm_phase phase);
sqr = sequencer::type_id::create("sqr", this);
drv = driver::type_id::create("drv", this);
endfunction
function void connect_phase(uvm_phase phase);
drv.seq_item_port.connect(sqr.seq_item_export);//连接
endfunction
endclass class testl extends uvm_test;
env e;
`uvm_cornponent_utils(test1)
function void build_phase(uvm_phase phase);
e = env::type_id::create("e", this);
endfunction
task run_phase(uvm_phase phase);
flat_seq seq;
phase.raise_objection(phase);
seq = new ();
seq.start(e.sqr); //sequence 挂载到env的sequencer上 就得到m.sequencer,且开始body开始自动执行
phase.drop_objection(phase);
endtask
endclass //输出结果:
UVM INFO@ 0: uvm_test_top.e.sqr@@flat_seq [SEQ] sent a item
UVM INFO@ 0: uvm_test_top.e.drv [ORV] got a item
UVM INFO@ 0: uvm_test_top.e.drv [ORV] sent a item
UVM INFO@ 0: uvm_test_top.e.sqr@@flat_seq [SEQ] got a item 

上面这段例码展示了从 item 定义,到 sequence 定义, 最后到 sequencer 与 driver 的连接。这段精简的代码对于大家理解 driver 从 sequencer 获取 item, 经过时序处理再返回给 sequence 的握手过程很有帮助。 为此做出详细的分析, 帮助大家理清例码中的关键处理:

•    在定义 sequencer 时,默认了 REQ 类型为 uvm_ sequence _item类型,这与稍后定义 driver时采取默认 REQ 类型保持一致。

•    flat_seq 作为动态创建的数据生成载体,它的主任务 flat_seq::body()做了如下的几件事情:

UVM-- Sequencer和driver相关推荐

  1. (17)UVM sequencer和driver

    UVM sequencer和driver 文章目录 UVM sequencer和driver 一.概述 二.端口和方法 三.事务传输实例 四.事务传输过程分析 五.通信时序 六.握手建议 关注作者 一 ...

  2. (8)UVM Sequencer和Driver

    UVM Sequencer和Driver 概述 端口和方法 实例 通信时序 握手建议 概述 driver同sequencer之间的TLM通信采取了get模式,即由driver发起请求,从sequenc ...

  3. UVM——Sequencer Driver

    driver和sequencer之间的通信方式采取get模式,即由driver发起请求,从sequencer一端获得item,再由sequencer将其传递至drive.driver只要可以从sequ ...

  4. UVM——sequence、sequencer、driver概述

    sequence.sequencer.driver关系 三者的关系如上图所示: - sequence产生目标数量的sequence item,并通过随机化使每一个sequence item对象的数据内 ...

  5. (18)UVM sequencer和sequence

    UVM sequencer和sequence 文章目录 UVM sequencer和sequence 一.概述 二.sequence和item发送实例 三.发送sequence/item方法建议 四. ...

  6. sequencer和driver

    1. 双方的TLM端口和方法 driver是initiator,TLM通信采用get模式,即driver从sequencer一端获得item,再由sequencer传递给driver. driver是 ...

  7. UVM学习笔记--sequence和sequencer

    1. UVM sequence机制的意义 UVM的sequence机制最大的作用就是将test case和testbench分离开来. 对一个项目而言,testbench是相对稳定的框架,而针对各个m ...

  8. sequence和sequencer — UVM

    文章目录 简介 1.sequence 和 item 2.sequencer 和 driver 1. 通信方式--TLM端口 2.事务传输 3. 通信时序 3.sequence和sequencer 1. ...

  9. UVM基础-Sequence、Sequencer(二)

    目录 sequence和sequencer 将sequence挂载到sequencer 将item挂载到sequencer 宏定义使用实例 sequencer仲裁特性 实例 sequencer的锁定机 ...

  10. UVM基础-Sequence、Sequencer(一)

    目录 Sequence.Sequencer.Driver大局观 Sequence和item item与sequence的关系 flat sequence hierarchical sequence s ...

最新文章

  1. GridView中实现单选RadioButton
  2. h.264 html播放,浏览器 – 我如何播放H264视频?
  3. jQuery之滚动事件$(window).scroll(function()
  4. 1292 - Incorrect datetime valuemysql插入非法的时间数据解决方案
  5. python类与对象-如何为创建大量实例节省内存
  6. Linux设备树相关
  7. Skype for Business Server 2015-12-WAP-发布-1-前端服务器-OWAS01
  8. 工作七年,从实习生到测试主管,我认识到倾听对一个人有多重要!
  9. ASP.NET服务器对于请求的处理过程
  10. Trie字典树数组实现
  11. 图解通信原理与案例分析-27: 卫星通信系统及关键技术
  12. 服务器虚拟化技术有kvm,只用VMware开虚拟机?来了解一下更强大KVM虚拟化技术
  13. 计算机小知识140,140个电脑小知识,电脑知识-
  14. Volatile能不能保证线程安全?
  15. arcpy投影(二)——基准面变换概念及参数、空间参考对象获取、变换关系获取方法梳理与解析(Spatial Reference、ListTransformations)
  16. OPENCV入门教程十一:dilate图像膨胀
  17. 计算机专业进国企有什么难度,大学毕业后才发现,国企与私企的差距不是一星半点,希望你没选错...
  18. 电子合同管理有这些细节更需要注意!
  19. Shiro基础应用——角色和权限校验
  20. AR试妆跑出了“第一股”,华为、旷视、欧莱雅也在抢蛋糕

热门文章

  1. 2021-11-30 网工基础(三)物理层、数据链路层、VRP系统等基础
  2. Neutron的Web Server启动过程中的关键参数
  3. 常见五轴机床的机械结构形式讲解!
  4. 青春魅族为何一幅“龙钟老态”?
  5. s17王者服务器维护几点,王者荣耀S17赛季更新维护几点开始?王者荣耀四周年更新多久...
  6. python怎么取共轭_python实现共轭梯度法
  7. 如何在ex表格导入php_怎么使用php把表格中的数据导入到excel中,php如何快速导入excel表格数据...
  8. “一年前,我来到国企搞IT”
  9. python爬虫安装教程_环境安装-Python 原生爬虫教程 | IT大叔
  10. 自己怎么开发一个软件app、如何开发一个app系统软件?