← Design Verification Interviews
Interview Question · Code Reading
The Order of UVM Phases
The Question
The interviewer asks
A test builds an env, which builds a scoreboard and an agent with a driver. Each prints in build, connect, report and final. What prints, in what order?
// Each class prints its full name in build, connect, report and final.
class my_env extends uvm_env;
my_scoreboard sb; my_agent agt; // the agent holds a driver, drv
function void build_phase(uvm_phase phase);
$display("build: %s", get_full_name());
sb = my_scoreboard::type_id::create("sb", this); // created first
agt = my_agent::type_id::create("agt", this);
endfunction
endclass
// The test builds env the same way. What prints, in what order?You have two and a half minutes. Speak or type, then press Get Feedback under your answer. No credits needed.
Speech-to-text runs in your browser. Chrome and Edge may send audio to their own speech service.
You can edit your answer before you send it. Feedback uses AI and checks your answer only against our written answer. No credits are used and your answer is not saved.
Reveal the Model Answer
Build runs top-down: test, env, then the children, then the driver. A parent must build first, because its build_phase creates its children. Connect and report run bottom-up, so the driver prints first and the test last. Final runs top-down again. In uvm-core the agent builds before the scoreboard, although the scoreboard was created first.
type_id::create calls made inside each parent's build_phase. The last arrow is the monitor-to-scoreboard link that env makes in connect_phase. All of this happens at time 0.- The test builds first0 ns (illustrative)
UVM calls
build_phaseonuvm_test_top, which creates env.Follow the calls, values and waits
- call create("env"): uvm_test_top → env
- Waiting: env — exists; build_phase not run yet
- env builds: agent and sb exist0 ns (illustrative)
env's
build_phasecreates the agent and the scoreboard. Neither has built anything yet, soagent.monis still null.Follow the calls, values and waits
- call create("agent"): env → agent
- call create("sb"): env → sb
- Waiting: agent — mon is null
- Waiting: sb — exists; build_phase not run yet
- Released: env
- The agent builds, then sb0 ns (illustrative)
The agent's
build_phasecreates the driver and the monitor. The scoreboard builds after the whole agent subtree.Follow the calls, values and waits
- call create("drv"): agent → drv
- call create("mon"): agent → mon
- Released: agent
- Released: sb
- Connect from the leaves up0 ns (illustrative)
Now every component exists. connect_phase runs drv, mon, agent, sb, then env, so env links the monitor's port to the scoreboard after both are complete.
Read the diagram as text
- uvm_test_top: phase_test
- env: Creates agent and sb
- agent: Creates drv and mon
- sb: Scoreboard
- drv: Driver
- mon: Monitor with port ap
- uvm_test_top → env: creates
- env → agent: creates
- env → sb: creates
- agent → drv: creates
- agent → mon: creates
- mon → sb: ap.connect(sb.imp)
The parent goes first in build because it creates its children. In connect, the parent goes last, after every child is complete.
The full program: four components print their names in four phases.
build: uvm_test_top build: uvm_test_top.env build: uvm_test_top.env.agt build: uvm_test_top.env.agt.drv build: uvm_test_top.env.sb connect: uvm_test_top.env.agt.drv connect: uvm_test_top.env.agt connect: uvm_test_top.env.sb connect: uvm_test_top.env connect: uvm_test_top report: uvm_test_top.env.agt.drv report: uvm_test_top.env.agt report: uvm_test_top.env.sb report: uvm_test_top.env report: uvm_test_top final: uvm_test_top final: uvm_test_top.env final: uvm_test_top.env.agt final: uvm_test_top.env.agt.drv final: uvm_test_top.env.sbSelf-Check
Tick each key point you covered in your answer.
What Interviewers Listen For (Fresher)
A good fresher answer gets build top-down and connect bottom-up. It explains build with one idea: a parent must exist before it can create its children.
What Interviewers Listen For (Junior)
A good junior answer also places final as top-down. It says that all run_phase tasks start together at time 0.
What Interviewers Listen For (Mid-Level)
A good mid-level answer refuses to depend on the build order of siblings. It keeps work that needs another component out of build_phase.
Cross-Questions
Where the interviewer goes next. Open a node to practise that follow-up.
WhyWhat IfBreak ItCompare
- The Order of UVM Phases
-
WhyWhy Build Runs Top-DownL1 Junior
Why must build run top-down? What would break if it ran bottom-up?
2:30You have two and a half minutes. Speak or type, then press Get Feedback under your answer. No credits needed.
Speech-to-text runs in your browser. Chrome and Edge may send audio to their own speech service.
You can edit your answer before you send it. Feedback uses AI and checks your answer only against our written answer. No credits are used and your answer is not saved.
Reveal the Model Answer
A child does not exist until its parent's
build_phasecreates it, so bottom-up has nothing to start from. Top-down also lets a parent set configuration for its children before they read it. That is how a test sets a value that an agent reads two levels below.Self-Check
Tick each key point you covered in your answer.
Misconception
"Top-down is only a convention for readability."
It is required: configuration set by a parent in its build must exist before the child's build reads it.
Source Verification Academy, UVM Cookbook, Configuring a Test Environment: precedence during build (PDF p140)
-
What IfA Config Set After the Child Has Read ItL1 JuniorL2 Mid-Level
What if the test sets a config value in
connect_phaseinstead ofbuild_phase?2:30You have two and a half minutes. Speak or type, then press Get Feedback under your answer. No credits needed.
Speech-to-text runs in your browser. Chrome and Edge may send audio to their own speech service.
You can edit your answer before you send it. Feedback uses AI and checks your answer only against our written answer. No credits are used and your answer is not saved.
Reveal the Model Answer
The children read their configuration during build, so the late set has no effect on them. Nothing warns you, because the earlier
getalready returned. Set configuration before or during build.check_config_usage()lists sets that no component read, which exposes this mistake.Self-Check
Tick each key point you covered in your answer.
Misconception
"The config database is live, so a later set updates the agent."
The agent copied the value at its
getduring build. A later set changes the database, not that copy.Source uvm-core 2020.3.1 (IEEE 1800.2 library) source, base/uvm_config_db.svh
-
CompareFunction Phases vs the Run PhaseL1 Junior
Compare
build_phasewithrun_phase. Why is one a function and the other a task?2:30You have two and a half minutes. Speak or type, then press Get Feedback under your answer. No credits needed.
Speech-to-text runs in your browser. Chrome and Edge may send audio to their own speech service.
You can edit your answer before you send it. Feedback uses AI and checks your answer only against our written answer. No credits are used and your answer is not saved.
Reveal the Model Answer
Build, connect, check and report must finish in zero simulation time, so they are functions and cannot wait.
run_phaseis where time passes, so it is a task that can wait on clocks and events. The twelve run-time phases, such asreset_phaseandmain_phase, run alongsiderun_phaseas tasks too.Two Branches Between Start of Simulation and ExtractArrows show which phase starts after which. In this measured run the test objects in run_phasefor 10 ns and inreset_phasefor 20 ns. It objects inmain_phasefor 30 ns and inshutdown_phasefor 10 ns.Illustrative sequenceCallValueReturnWaiting- Both branches start0 ns (illustrative)
run_phaseandpre_reset_phasestart in the same time step.pre_resethas no objection, so it ends at once andreset_phasestarts.Follow the calls, values and waits
- call start run_phase: start_of_simulation → run_phase
- call start pre_reset: start_of_simulation → pre_reset .. post_reset
- Waiting: run_phase — test objects until 10 ns
- Waiting: pre_reset .. post_reset — reset objection until 20 ns
- run_phase has dropped, but waits10 ns (illustrative)
The test drops its
run_phaseobjection at 10 ns. The run phase does not end yet: it shares its successor, extract, with the schedule, and waits for it.Follow the calls, values and waits
- Waiting: run_phase — objections 0; waits for the schedule
- Released: run_phase
- Reset ends; main begins20 ns (illustrative)
The reset objection drops at 20 ns.
post_resetand the three configure phases have no objection, so they pass in zero time andmain_phasestarts at 20 ns.Follow the calls, values and waits
- call start pre_configure: pre_reset .. post_reset → pre_configure .. post_main
- Waiting: pre_configure .. post_main — main objection until 50 ns
- Released: pre_reset .. post_reset
- Main ends; shutdown begins50 ns (illustrative)
The main objection drops at 50 ns.
post_mainandpre_shutdownpass in zero time, andshutdown_phaseholds until 60 ns.Follow the calls, values and waits
- call start pre_shutdown: pre_configure .. post_main → pre_shutdown .. post_shutdown
- Waiting: pre_shutdown .. post_shutdown — shutdown objection until 60 ns
- Released: pre_configure .. post_main
- Both branches end60 ns (illustrative)
The shutdown objection drops at 60 ns. The run phase and
post_shutdownboth end at 60 ns, and extract starts.Follow the calls, values and waits
- return post_shutdown ended: pre_shutdown .. post_shutdown → extract
- return run_phase ended: run_phase → extract
- Released: pre_shutdown .. post_shutdown
- Released: run_phase
Read the diagram as text
- start_of_simulation: Last zero-time step
- run_phase: Objection 0-10 ns
- pre_reset .. post_reset: reset objection 0-20 ns
- pre_configure .. post_main: configure takes 0 ns; main 20-50 ns
- pre_shutdown .. post_shutdown: shutdown objection 50-60 ns
- extract: Starts when both branches end
- start_of_simulation → run_phase: starts at 0
- start_of_simulation → pre_reset .. post_reset: starts at 0
- pre_reset .. post_reset → pre_configure .. post_main: ends at 20
- pre_configure .. post_main → pre_shutdown .. post_shutdown: ends at 50
- pre_shutdown .. post_shutdown → extract: ends at 60
- run_phase → extract: ends at 60
The run phase ends at 60 ns, although its own objection dropped at 10 ns.
Self-Check
Tick each key point you covered in your answer.
Misconception
"Put a
#10inbuild_phaseto wait for the DUT."A function cannot contain a delay, so it does not compile. Anything that needs time belongs in a task phase.
Source IEEE 1800-2017 §13.4
- Both branches start0 ns (illustrative)
-
Break ItWhy Components Are Fixed After BuildL1 JuniorL2 Mid-Level
Why can't the scoreboard be created in
connect_phaseorrun_phase?2:30You have two and a half minutes. Speak or type, then press Get Feedback under your answer. No credits needed.
Speech-to-text runs in your browser. Chrome and Edge may send audio to their own speech service.
You can edit your answer before you send it. Feedback uses AI and checks your answer only against our written answer. No credits are used and your answer is not saved.
Reveal the Model Answer
Every phase after build walks a tree that must already be complete. Connections, configuration lookups and end-of-elaboration checks all assume that no new parts appear. The library enforces this. Once build is done,
new()on a component reports a fatalILLCRTerror.Self-Check
Tick each key point you covered in your answer.
Misconception
"Creating it in
connect_phaseis fine because nothing runs yet."Build is over by then, so the library refuses. Its children would also miss their own build phase.
Source uvm-core 2020.3.1 (IEEE 1800.2 library) source, base/uvm_component.svh, new(): "illegal to create a component ... after the build phase has ended"
-
What IfA Component That Needs Its Sibling in BuildL2 Mid-Level
Asked if they notice the scoreboard builds last
What if the agent's
build_phasereads a handle from the scoreboard, its sibling?2:30You have two and a half minutes. Speak or type, then press Get Feedback under your answer. No credits needed.
Speech-to-text runs in your browser. Chrome and Edge may send audio to their own speech service.
You can edit your answer before you send it. Feedback uses AI and checks your answer only against our written answer. No credits are used and your answer is not saved.
Reveal the Model Answer
It works or crashes depending on which sibling builds first, and that order is not something to design around. Keep each build self-contained. Make links between siblings in the parent's
connect_phase, when every component exists.Self-Check
Tick each key point you covered in your answer.
Missed Corner
"Create the scoreboard first and the agent will see it."
Creation order is not build order: the run on the root shows the agent building before a scoreboard created earlier.
Source Measured: the run on dv.uvm.phase-order, uvm-core 2020.3.1 on Verilator 5.052
What People Get Wrong
Common wrong answers and why they fail.
Misconception
"All phases run top-down, like build."
Only build and final are top-down among the common phases. Connect, end of elaboration, start of simulation, extract, check and report are bottom-up.
Source uvm-core 2020.3.1 (IEEE 1800.2 library) source, base/uvm_common_phases.svh (each phase class extends uvm_topdown_phase or uvm_bottomup_phase)
Tool as Truth
"Siblings build in the order the parent created them."
In uvm-core the scoreboard, created first, builds after the agent: children are visited in name order. Code that relies on sibling order breaks when someone renames a component.
Source Measured: the run on this question (agt builds before sb), uvm-core 2020.3.1 on Verilator 5.052
Half-Truth
"run_phase starts only after every component has finished build and connect, one component at a time."
The first half is right. But all run_phase tasks then start in parallel at time 0, not one after another.
Source IEEE 1800.2-2020 §9.8.1.5 (uvm-core base/uvm_common_phases.svh, uvm_run_phase is a task phase)