Currying in hardware

℡╲_俬逩灬. 提交于 2020-01-24 15:45:09

问题


I'm trying to implement a simple Address Decoder with a curried function inside. The code below won't compile, could anybody help me with this?

class AddrDecoder[T<:UInt] (dType:T, n:Int) extends Module {
  val io = IO (new Bundle {
    //val range = (Vec(Seq.fill(n){(dType,dType)})) // This won't compile, how to fix ?
    val range = (List.fill(n){(dType,dType)})        
    val addr  = Input (dType)
    val en    = Input (Bool())        
    val sel   = Output(Bool())
  })

  def inside (range:(T,T))(addr:T):Bool = {
    addr >= range._1 && addr < range._1 + range._2
  }

  when (io.en) {
    io.sel := io.range map (inside(_)(io.addr))
  }
}

[error] found : List[chisel3.Bool]
[error] (which expands to) List[chisel3.core.Bool]
[error] required: chisel3.core.Data
[error] io.sel := io.range map (inside(_)(io.addr))

回答1:


@jkoenig provided an excellent solution. Posting it here for other's benefit

class AddrDecoder[T<:Data with Num[T]] (dType:T, n:Int) extends Module {
  val io = IO (new Bundle {
    val range0  = Input (Vec(n,dType))
    val range1  = Input (Vec(n,dType))        
    val addr    = Input (dType)
    val en      = Input (Bool())        
    val sel     = Output(Vec(n,Bool()))
  })

  // Curried function which accepts a tuple and an input addr
  // Use map to apply it to inputs
  def inside (range:(T,T))(addr:T):Bool = {
    addr >= range._1 && addr < range._1 + range._2
  }

  // MUX output
  for (i <- 0 until n) {
    io.sel(i) := false.B
  }

  when (io.en) {
    io.sel := io.range0 zip io.range1 map (inside(_)(io.addr))
  }    
  // $onehot0 output encoding check
  assert (PopCount(io.sel) <= 1.U, "Invalid addr decoding")
}


来源:https://stackoverflow.com/questions/53008404/currying-in-hardware

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!