sequence啟動的三種方式


1、seq相關的phase機制

首先你需明確的是UVM的框架下,消耗時間的task的執行都在在uvm_component底下的objection的機制來實現的。也就是說phase的機制跟uvm_component是緊密相關的。
uvm_sequence是一個uvm_object的類,uvm_sequencer是一個uvm_component的類。
seq需要掛載在seqr上執行。

run_time_phase.svh

在前面我們講過UVM_PHASE的機制,在execute函數的地方有對uvm_sequencer_base類型的做處理。

  • start_phase_sequence(phase):處理default_sequencer

  • 這里先做個遺留,到底這里是什么從外面獲得default_sequencer的。

方法一:利用default_sequence啟動seq

也只有在用default_sequence的方式啟動seq的時候,start_phase != null,原因是如果是sqr的時候在uvm_task_phase.svh里面有介紹,會自己調用start_phase_sequence,里面會對seq.set_starting_phase(phase);進行set。
前提
對應uvm1.2版本,

或者是my_seq.set_automatic_phase_objection(1);
在start_phase_sequence里面已經指定了phase,seq.set_starting_phase(phase);

命令行設置default_sequencer:
+UVM_SET_DEFAULT_SEQUENCE=uvm_test_top.env.i_agt.sqr,main_phase,case0_sequence

  • 第一個參數是指定seqr的路徑
  • 第二個參數是指定要執行的phase階段
  • 第三個參數是指定你的seq
    uvm_config_db設置default_sequencer

uvm_config_db#(uvm_object_wrapper)::set(this, "env.i_agt.sqr.main_phase", "default_sequence", case0_sequence::type_id::get());

function void my_case0::build_phase(uvm_phase phase);
   case0_sequence my_seq;
   super.build_phase(phase);
   my_seq = new("my_seq");
   uvm_config_db#(uvm_sequence_base)::set(this, 
                                           "env.i_agt.sqr.main_phase", 
                                           "default_sequence", 
                                           my_seq);
endfunction

方法二:利用seq.start(seqr)顯示啟動

前提:如果想用starting_phase的話,需要為其指定,不像default_sequencer那樣,start_phase_sequence(phase)里面已經調用了set_starting_phase

  • 利用starting_phase來啟動objection:直接調用seq.start(seqr)

  • 或者將my_seq.starting_phase=phase替換成my_seq.set_starting_phase這種寫法。
  • 利用common的objection機制:直接調用seq.start(seqr)

參考UVM_UG:


方法三:利用uvm_do_on系列的宏

`uvm_do系列的宏,我們知道這些宏最終都是調用的uvm_do_on_pri_with的宏。uvm_do系列的宏是可以在uvm_sequence_base以及其擴展類中才能調用的!

  • 當第一個參數是sequence類型的時候,會調用seq.start,也就是能啟動seq。

  • my_seq.start() -> my_seq.body() -> uvm_do(my_seq_0) -> my_seq_0.start() -> my_seq_0.body()

那么這里自然而言,我就會想可以在頂層這樣做嗎?

剛剛入行的時候,總會有這些問題,為什么不能這么做的?
首先宏是啥意思?在代碼編譯的時候,宏會依次展開,所以create_item/start_item/finish_item都會暴露出來,由於你是在uvm_sequencer中調用的,根據擴展關系,是找不到create_item/start_item/finish_item這些東西的啊,同學!!!!
create_item/start_item/finish_item是在uvm_sequence_base里面定義的。
也就是說uvm_do系列的宏是可以在uvm_sequence_base以及其擴展類中才能調用的!

小結:從本質上講,seq的啟動都是調用了uvm_squence_base的start函數。
下面簡單來看一下;uvm_sequence_base::start(sqr)的源碼:

start

  • 設置m_sequencer和p_sequencer
  • 注冊m_sequencer和sequence,將seq_id sqr_id等關聯起來

set_item_context
m_register_sequence

start

start

  • pre_start/pre_body/body/post_body/post_start,是一些callback函數。
  • parent_sequence也有pre_do/mid_do/post_do的callback函數,但這些很不常用。
  • 重點關注body()的override就行。
  • m_sequence_exiting()將sequence從arb_sequence_q[]中刪除。

m_sequence_exiting

真正sequence的跟driver交互的東西就是在body()里面實現的。


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM