2

I am trying to implement the way-prediction technique in the RocketChip core (in-order). For this, I need to access each way separately. So this is how SRAM for tags looks like after modification (separate SRAM for each way)

val tag_arrays = Seq.fill(nWays) { SeqMem(nSets, UInt(width = tECC.width(1 + tagBits)))}
val tag_rdata = Reg(Vec(nWays, UInt(width = tECC.width(1 + tagBits))))
for ((tag_array, i) <- tag_arrays zipWithIndex) {
  tag_rdata(i) := tag_array.read(s0_vaddr(untagBits-1,blockOffBits), !refill_done && s0_valid)
}

And I want to access it like

when (refill_done) {
  val enc_tag = tECC.encode(Cat(tl_out.d.bits.error, refill_tag))
  tag_arrays(repl_way).write(refill_idx, enc_tag)
  ccover(tl_out.d.bits.error, "D_ERROR", "I$ D-channel error")
}

Where repl_way is Chisel random UInt generated by LFSR. But Seq element can be accessed only by Scala Int index which causes a compilation error. Then I tried access it like this

when (refill_done) {
  val enc_tag = tECC.encode(Cat(tl_out.d.bits.error, refill_tag))
  for (i <- 0 until nWays) {
    when (repl_way === i.U) {tag_arrays(i).write(refill_idx, enc_tag)}
  }
  ccover(tl_out.d.bits.error, "D_ERROR", "I$ D-channel error")
}

But assertion arises -

assert(PopCount(s1_tag_hit zip s1_tag_disparity map { case (h, d) => h && !d }) <= 1)

I am trying to modify ICache.scala file. Any ideas on how to do this properly? Thanks!

  • The reason for arising of assertion above was that I tried to gather tags of all ways in one register of vectors and then compare them against incoming tag in the next cycle while the original solution is reading all ways at once into one vector and compare them at the same cycle in order to define cache hit or miss. Now, I am just reading each tag into a separate variable, then initialize a vector (i.e. 4 ways - 4 variables - Vec of 4 elements). The same for data_arrays. It works, I mean, I can access each way separately and choose which way to access but it is not universal anymore. – Khakim Akhunov Feb 02 '20 at 19:21

1 Answers1

1

I think you can just use a Vec here instead of a Seq

val tag_arrays = Vec(nWays, SeqMem(nSets, UInt(width = tECC.width(1 + tagBits))))

The Vec allows indexing with a UInt

Chick Markley
  • 4,023
  • 16
  • 17
  • Thank you for your answer but Vec does not support SeqMem as a parameter. ICache.scala:181:20: overloaded method value apply with alternatives: [error] [T <: Chisel.Data](elt0: T, elts: T*)Chisel.Vec[T] [error] [T <: Chisel.Data](gen: T, n: Int)(implicit compileOptions: chisel3.core.CompileOptions)Chisel.Vec[T] [error] [T <: chisel3.core.Data](n: Int, gen: T)(implicit sourceInfo: chisel3.internal.sourceinfo.SourceInfo, implicit compileOptions: chisel3.core.CompileOptions)chisel3.core.Vec[T] [error] cannot be applied to (Int, chisel3.core.SyncReadMem[Chisel.UInt]) – Khakim Akhunov Jan 29 '20 at 18:42