Chisel3 - util - Pipe

https://mp.weixin.qq.com/s/WeFesE8k0ORxlaNfLvDzgg

 
流水线,用于添加延迟。
 
参考链接:
 
 
1. Pipe object提供了三个工厂方法
 
最基本的方法签名如下:
def apply[T <: Data](enqValid: Bool, enqBits: T, latency: Int)(implicit compileOptions: CompileOptions): Valid[T]
接收三个参数,返回一个Valid接口。
其中:latency为延迟的clock数,enqValid为valid位,enqBits为要输出的数据类型。
 
实现如下:
这里使用了递归调用,退出条件为latency为0。当latency为0时,不需要延时。直接把输入enqValid/enqBits输出到一个Valid类型的线。
当latency不为0时,则把enqValid和enqBits输出到一个新创建的寄存器中,以实现delay一个clock的目的,然后使用递归调用:apply(v, b, latency-1) 生成后续延时所需的寄存器。
 
另外两个方法基于这个方法实现:
a. 默认延时一个时钟
def apply[T <: Data](enqValid: Bool, enqBits: T)(implicit compileOptions: CompileOptions): Valid[T] = {
apply(enqValid, enqBits, 1)(compileOptions)
}
b. 延时一个Valid类型的变量
def apply[T <: Data](enq: Valid[T], latency: Int = 1)(implicit compileOptions: CompileOptions): Valid[T] = {
apply(enq.valid, enq.bits, latency)(compileOptions)
}
 
2. Pipe模块
 
Pipe模块内部定义了一个PipeIO,使用Pipe伴生对象提供的工厂方法,创建一个Valid类型的接口,用于构建Pipe模块。
 
 
输入接口enq是Valid类型,输出接口deq也是Valid类型,io.deq <> Pipe(io.enq, latency) 把io.enq延迟latency个时钟之后,输出到io.deq中。
 
PS. enq是入队的意思(enqueue), deq是出队的意思(dequeue)。
 
3. 附录
 
Valid.scala:
/** A hardware module that delays data coming down the pipeline
* by the number of cycles set by the latency parameter. Functionality
* is similar to ShiftRegister but this exposes a Pipe interface.
*
* Example usage:
* {{{
* val pipe = new Pipe(UInt())
* pipe.io.enq <> produce.io.out
* consumer.io.in <> pipe.io.deq
* }}}
*/
object Pipe
{
@chiselName
def apply[T <: Data](enqValid: Bool, enqBits: T, latency: Int)(implicit compileOptions: CompileOptions): Valid[T] = {
if (latency == 0) {
val out = Wire(Valid(chiselTypeOf(enqBits)))
out.valid := enqValid
out.bits := enqBits
out
} else {
val v = RegNext(enqValid, false.B)
val b = RegEnable(enqBits, enqValid)
apply(v, b, latency-1)(compileOptions)
}
}
def apply[T <: Data](enqValid: Bool, enqBits: T)(implicit compileOptions: CompileOptions): Valid[T] = {
apply(enqValid, enqBits, 1)(compileOptions)
}
def apply[T <: Data](enq: Valid[T], latency: Int = 1)(implicit compileOptions: CompileOptions): Valid[T] = {
apply(enq.valid, enq.bits, latency)(compileOptions)
}
}
 
class Pipe[T <: Data](gen: T, latency: Int = 1)(implicit compileOptions: CompileOptions) extends Module
{
class PipeIO extends Bundle {
val enq = Input(Valid(gen))
val deq = Output(Valid(gen))
}
 
val io = IO(new PipeIO)
 
io.deq <> Pipe(io.enq, latency)
}
 

 

 
 
 
posted @ 2018-12-13 22:41  wjcdx  阅读(668)  评论(0编辑  收藏  举报