14.3 Lock and Grab Methods in UVM sequencer

文章详细介绍了UVMsequencer中的锁定(lock和grab)与解锁(unlock和ungrab)方法,以及它们如何控制driver对序列的访问。此外,还讨论了is_blocked和has_lock方法的作用,以及kill和do_kill在终止sequence时的用法。通过实例展示了不同方法在并行sequence中的应用。
摘要由CSDN通过智能技术生成

UVM sequencer通过使用锁定机制向driver提供对序列的独占访问权限(exclusive access)。此锁定机制是使用lock和grab方法实现的。
例如:在控制器或微处理器中,internal core中断服务处理以及其他操作。有时,如果设备引发特定中断,需要立即关注并停止正在进行的进程执行。一旦core为这个高优先级中断提供服务,就可以恢复之前的进程。

1 Lock method

sequence调用lock方法时,sequencer将在sequence通过sequencer仲裁机制获得下一个可用slot时,授予driver对sequence的独占访问权限。在sequence调用unlock方法之前,没有其他sequence可以访问driver。调用unlock方法时,之前的锁定被释放。lock是一种阻塞方法,一旦锁定被granted就会return。

task lock (uvm_sequencer_base sequencer = null)

2 grab method

The grab method is similar to the lock method except it takes immediate control to grab the next sequencer arbitration slot itself by overriding any other sequence priorities.

The pre-existing lock or grab condition on the sequence will stop from grabbing the sequence for the current sequence.

task grab (uvm_sequencer_base sequencer = null)

3 unlock method

sequencer的lock方法从sequence中调用,以释放lock或grab。必须调用unlock方法以避免sequencer锁定情况。

function void unlock (uvm_sequencer_base sequencer = null)

4 ungrab method

ungrab方法是unlock方法的别称。

function void ungrab( uvm_sequencer_base sequencer = null )

5 is_blocked method

is_block方法可用于查找由于sequencer lock条件而被block的当前sequence,并返回1。它返回0值,则sequence未被阻止,可在sequencer arbitration(仲裁器)中获取下一个slot。如果sequencer在sequence发出请求之前被lock,则sequence可能无法获得slot。

function bit is_blocked()

6 has_lock method

如果当前sequence被lock返回1,否则返回0。

function bit has_lock()

7 kill method

kill函数用于终止sequence,并删除序列默认sequencer中的所有当前locks和requests。这将不允许执行post_body和post_start回调方法,sequence状态将更改为UVM_STOPPED。

function void kill()

8 do_kill method

do_kill是一个用户钩子,当使用sequence kill()或sequencer.stop_sequences()终止序列时,将调用它。
:sequencer.stop_sequences()最终调用sequence.kill方法。

virtual function void do_kill()

注:

  1. lock、grab、unlock和ungrab方法将请求放在指定的sequencer上。如果没有传递参数,将使用默认的sequencer。
  2. lock方法将lock请求放在仲裁队列的后面,而grab方法将grab请求放在了仲裁队列的前面。因此,如果仲裁队列有中间挂起的请求,那么与lock请求相比,grab请求将立即得到服务。

9 Lock and unlock methods example

有三个sequence:seq_A、seq_B和seq_C并行。只有seq_B调用lock和unlock方法。

class seq_A extends uvm_sequence #(seq_item);
  seq_item req;
  `uvm_object_utils(seq_A)
  
  function new (string name = "seq_A");
    super.new(name);
  endfunction

  task body();
    req = seq_item::type_id::create("req");
    wait_for_grant();
    assert(req.randomize());
    send_request(req);
    `uvm_info(get_type_name(), $sformatf("%0t: seq_item is sent", $time), UVM_LOW);
    wait_for_item_done();
  endtask
endclass

class seq_B extends uvm_sequence #(seq_item);
  seq_item req;
  `uvm_object_utils(seq_B)
  
  function new (string name = "seq_B");
    super.new(name);
  endfunction

  task body();
      lock(m_sequencer);
      req = seq_item::type_id::create("req");
      wait_for_grant();
      assert(req.randomize());
      send_request(req);
      `uvm_info(get_type_name(), $sformatf("%0t: seq_item is sent", $time), UVM_LOW);
      wait_for_item_done();
      unlock(m_sequencer);
  endtask
endclass

class seq_C extends uvm_sequence #(seq_item);
  seq_item req;
  `uvm_object_utils(seq_C)
  
  function new (string name = "seq_C");
    super.new(name);
  endfunction

  task body();
    req = seq_item::type_id::create("req");
    wait_for_grant();
    assert(req.randomize());
    send_request(req);
    `uvm_info(get_type_name(), $sformatf("%0t: seq_item is sent", $time), UVM_LOW);
    wait_for_item_done();
  endtask
endclass

Output: 

UVM_INFO sequences.sv(14) @ 0: uvm_test_top.env_o.agt.seqr@@seq_a [seq_A] 0: seq_item is sent
UVM_INFO sequences.sv(33) @ 50: uvm_test_top.env_o.agt.seqr@@seq_b [seq_B] 50: seq_item is sent
UVM_INFO sequences.sv(52) @ 100: uvm_test_top.env_o.agt.seqr@@seq_c [seq_C] 100: seq_item is sent
UVM_INFO sequences.sv(14) @ 150: uvm_test_top.env_o.agt.seqr@@seq_a [seq_A] 150: seq_item is sent
UVM_INFO sequences.sv(33) @ 200: uvm_test_top.env_o.agt.seqr@@seq_b [seq_B] 200: seq_item is sent
UVM_INFO sequences.sv(52) @ 250: uvm_test_top.env_o.agt.seqr@@seq_c [seq_C] 250: seq_item is sent
UVM_INFO sequences.sv(14) @ 300: uvm_test_top.env_o.agt.seqr@@seq_a [seq_A] 300: seq_item is sent
UVM_INFO sequences.sv(33) @ 350: uvm_test_top.env_o.agt.seqr@@seq_b [seq_B] 350: seq_item is sent
UVM_INFO sequences.sv(52) @ 400: uvm_test_top.env_o.agt.seqr@@seq_c [seq_C] 400: seq_item is sent

log显示,seq_B的lock请求按默认仲裁模式放到了仲裁队列的后面。因此,所有请求按分配的slot提供服务,seq_B具有独占访问权限。 

10 Grab and ungrab methods example

 有三个sequence:seq_A、seq_B和seq_C并行。只有seq_B调用grab和ungrab方法。

class seq_A extends uvm_sequence #(seq_item);
  seq_item req;
  `uvm_object_utils(seq_A)
  
  function new (string name = "seq_A");
    super.new(name);
  endfunction

  task body();
    req = seq_item::type_id::create("req");
    wait_for_grant();
    assert(req.randomize());
    send_request(req);
    `uvm_info(get_type_name(), $sformatf("%0t: seq_item is sent", $time), UVM_LOW);
    wait_for_item_done();
  endtask
endclass

class seq_B extends uvm_sequence #(seq_item);
  seq_item req;
  `uvm_object_utils(seq_B)
  
  function new (string name = "seq_B");
    super.new(name);
  endfunction

  task body();
      grab(m_sequencer);
      req = seq_item::type_id::create("req");
      wait_for_grant();
      assert(req.randomize());
      send_request(req);
      `uvm_info(get_type_name(), $sformatf("%0t: seq_item is sent", $time), UVM_LOW);
      wait_for_item_done();
      ungrab(m_sequencer);
  endtask
endclass

class seq_C extends uvm_sequence #(seq_item);
  seq_item req;
  `uvm_object_utils(seq_C)
  
  function new (string name = "seq_C");
    super.new(name);
  endfunction

  task body();
    req = seq_item::type_id::create("req");
    wait_for_grant();
    assert(req.randomize());
    send_request(req);
    `uvm_info(get_type_name(), $sformatf("%0t: seq_item is sent", $time), UVM_LOW);
    wait_for_item_done();
  endtask
endclass

Output:

UVM_INFO sequences.sv(33) @ 0: uvm_test_top.env_o.agt.seqr@@seq_b [seq_B] 0: seq_item is sent
UVM_INFO sequences.sv(33) @ 50: uvm_test_top.env_o.agt.seqr@@seq_b [seq_B] 50: seq_item is sent
UVM_INFO sequences.sv(33) @ 100: uvm_test_top.env_o.agt.seqr@@seq_b [seq_B] 100: seq_item is sent
UVM_INFO sequences.sv(14) @ 150: uvm_test_top.env_o.agt.seqr@@seq_a [seq_A] 150: seq_item is sent
UVM_INFO sequences.sv(52) @ 200: uvm_test_top.env_o.agt.seqr@@seq_c [seq_C] 200: seq_item is sent
UVM_INFO sequences.sv(14) @ 250: uvm_test_top.env_o.agt.seqr@@seq_a [seq_A] 250: seq_item is sent
UVM_INFO sequences.sv(52) @ 300: uvm_test_top.env_o.agt.seqr@@seq_c [seq_C] 300: seq_item is sent
UVM_INFO sequences.sv(14) @ 350: uvm_test_top.env_o.agt.seqr@@seq_a [seq_A] 350: seq_item is sent
UVM_INFO sequences.sv(52) @ 400: uvm_test_top.env_o.agt.seqr@@seq_c [seq_C] 400: seq_item is sent

log显示,seq_B grab请求被放到l仲裁队列的前面。因此,seq_B请求被提前服务,随后是其他请求。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值