編 者 按
HaltIt
看名字,就基本能猜到這個函數的大體功能是流水線暫停。
在Stage中,流水線暫停提供了這么幾個API:
def haltIt()(implicit loc: Location) : Unit = haltIt(ConditionalContext.isTrue)def haltIt(cond : Bool)(implicit loc: Location) : Unit = internals.request.halts += nameFromLocation(CombInit(cond), "haltRequest")def haltWhen(cond : Bool)(implicit loc: Location) : Unit = haltIt(cond)
三個API最終所實現的都是往internals.request.halts中添加cond條件。那么就看下request.halts在Pipeline構建時所起的作用。
首先,在進行 connectionsWithoutSinks(沒有驅動其他級Stage)往前遍歷的函數propagateRequirements中:
if(stage.request.halts.nonEmpty){ stage.arbitration.propagateReady = true stage.isReady //Force creation}
可以看到,如果stage中的internals.request.halts非空,這里做了兩件事:
- stage.arbitration.propagateReady設置為true,即需向前級Stage傳遞Ready信號
- 為本級創建input.ready信號
隨后在propagateRequirements中的代碼片段:
stageDriver.get(stage) match { case Some(c : ConnectionModel) = > { if(c.s.arbitration.propagateReady && c.m.output.ready == null){ c.m.output.ready = Bool() if(c.m.input.ready == null){ c.m.input.ready = Bool() } }
這里在處理當前Stage中的ConnectionLogic時,因為當前stage.arbitration.propagateReady為true,如果驅動當前Stage的Master Stage的output.ready為空,那么這里就會確保Master Stage中具備input.ready以及output.ready,確保上級Stage具備這種握手機制。
而后在該函數中的遞歸調用:
for(m < - stageMasters(stage)){ if(stage.internals.arbitration.propagateReady) m.internals.arbitration.propagateReady = true propagateRequirements(m)}
這里如果當前stage如果存在stage.arbitration.propagateReady為true,那么也會設置其Master Stage的.arbitration.propagateReady為true,通過遞歸調用,確保整個鏈路上ready信號一直向前傳播,即確保反壓一路到底。
最后,在處理Stage Internal Connection階段時:
if(s.request.halts.nonEmpty){ val doHalt = s.request.halts.orR when(doHalt){ s.input.ready := False s.output.valid := False }}
如果當前Stage中request.halts中條件滿足,那么當前stage中的output.valid,input.ready信號將會統一拉低,從而暫停向下級傳輸。
Example
case class Test8() extends Component{ val io=new Bundle{ val data_in=slave(Stream(UInt(8 bits))) val data_out=master(Stream(UInt(8 bits))) val cond=in Bool() } noIoPrefix() val A=Stageable(UInt(8 bits)) val pip=new Pipeline{ val stage0=new Stage{ this.driveFrom(io.data_in) A:=io.data_in.payload } val stage1=new Stage(Connection.M2S()){ } val stage2=new Stage(Connection.M2S()){ io.data_out.valid:=this.internals.output.valid io.data_out.payload:=A internals.output.ready=Bool() this.haltIt(io.cond) internals.output.ready:=io.data_out.ready this.internals.arbitration.propagateReady=true } } pip.build()}
這里給出了一個haltIt的example。在staeg2階段,如果cond為true,那么則流水線暫停。
這里需注意的是這里將stage2的output.ready由io.data_out.ready信號進行驅動,但output.ready信號是默認不會創建的,故這里顯示創建internals.output.ready為Bool類型電路對象。
-
驅動器
+關注
關注
53文章
8255瀏覽量
146562 -
Pipeline
+關注
關注
0文章
28瀏覽量
9370
發布評論請先 登錄
相關推薦
評論