Search code examples
chisel

How to freely assign values to vec type variables in chisel?


I defined some vec variables.

val r_parameters = Wire(Vec(RANK, UInt(log2Ceil(RANK).W)))
val test0  = Wire(Vec(RANK, UInt(width.W)))
val test1  = Wire(Vec(RANK, UInt(width.W)))

I try to use for loop for assignment.

for (i <- 0 to RANK-1)
{
    test0(r_parameters(i)) := test1(i)
}

variable 'r_parameters' is from rom or ram. If parameter 'RANK' is 4, r_parameters has the form as '0 3 2 1' or '0 1 2 3'. Thus all test0 are assigned. But firrtl compiler reports that test0 is not fully initialized.


Solution

  • I think the problem is that the firrtl compiler cannot be sure that every element of test0 has been initialized to something. I have filled out your examples, with values supplied and a couple of stylistic changes to this.

    class Wires extends MultiIOModule {
      val RANK = 4
      val bits = 8
    
      // set to 0, 3, 2, 1
      val r_parameters = VecInit(Seq(0, 3, 2, 1).map(_.U) )
    
      val test0  = Wire(Vec(RANK, UInt(bits.W)))
    
      // Give values to test1
      val test1  = VecInit(Seq.tabulate(RANK) { i => i.U } )
    
      // Wire test1 into test using the map provided by r_parameters
      for (i <- test0.indices) {
        test0(r_parameters(i)) := test1(i)
      }
    }
    

    If you dump the emitted firrtl with

    println((new ChiselStage).emitFirrtl(new Wires))
    

    You will see

    test0[r_parameters[0]] <= test1[0] @[MemBank.scala 56:28]
    test0[r_parameters[1]] <= test1[1] @[MemBank.scala 56:28]
    test0[r_parameters[2]] <= test1[2] @[MemBank.scala 56:28]
    test0[r_parameters[3]] <= test1[3] @[MemBank.scala 56:28]
    

    Firrtl cannot confirm that r_parameters has exhaustively connected test0.

    One important question is do you need to need to have r_parameters be a Vec instead of just a Seq. If you change the r_parameters above to

    val r_parameters = Seq(0, 3, 2, 1)
    

    The Module will compile correctly. I suspect this is what you want. If you really need to r_parameters to be a dynamic index and you need to refactor your code. It is possible to add

    test0 := DontCare
    

    In front of your loop but I wouldn't recommend it in this case. Hope this helps, happy chiseling!