SlidingWindowSuite.scala 4.27 KB
Newer Older
Jens Korinth's avatar
Jens Korinth committed
1
package chisel.axiutils.axi4
2
import  chisel.axi.Axi4._
Jens Korinth's avatar
Jens Korinth committed
3
4
5
import  chisel.axi._
import  chisel.axiutils._
import  chisel.miscutils.Logging
Jens Korinth's avatar
Jens Korinth committed
6
7
8
9
import  chisel3._
import  chisel3.util._
import  chisel3.iotesters.{ChiselFlatSpec, Driver, PeekPokeTester}

Jens Korinth's avatar
Jens Korinth committed
10
11
/** Test module for SlidingWindow:
 *  Connects SlidingWindow instance to AXI slave model.
12
 **/
Jens Korinth's avatar
Jens Korinth committed
13
14
15
class SlidingWindowTestModule[T <: Data](cfg: SlidingWindow.Configuration[T])
                                        (implicit val axi: Axi4.Configuration,
                                         logLevel: Logging.Level) extends Module {
Jens Korinth's avatar
Jens Korinth committed
16
17
18
19
20
  val io = IO(new Bundle {
    val ready          = Input(Bool())
    val asw_data_valid = Output(Bool())
    val asw_data_bits  = Output(UInt(axi.dataWidth))
  })
21
22

  /** AXI memory model **/
Jens Korinth's avatar
Jens Korinth committed
23
  val saxi = Module(new SlaveModel(SlaveModel.Configuration(size = Some(1024))))
24
  /** AxiSlidingWindow instance (DUT) **/
Jens Korinth's avatar
Jens Korinth committed
25
  val asw = Module(new SlidingWindow(cfg))
26
  asw.io.maxi <> saxi.io.saxi
Jens Korinth's avatar
Jens Korinth committed
27
28
  val ready = RegInit(false.B)
  ready := io.ready
29
  asw.io.data.ready := ready
Jens Korinth's avatar
Jens Korinth committed
30
  val base = RegInit(0.U(axi.addrWidth: chisel3.internal.firrtl.Width))
31
  asw.io.base := base
Jens Korinth's avatar
Jens Korinth committed
32
33
  io.asw_data_valid := asw.io.data.valid
  io.asw_data_bits  := asw.io.data.bits
34
35
}

Jens Korinth's avatar
Jens Korinth committed
36
37
38
39
/** Tester class for SlidingWindow:
 *  Fills memory model with increasing integers of configured element width,
 *  then checks sliding window against expected values at each step.
 *  Does not operate at full speed, each step has at least one cycle delay.
40
 **/
Jens Korinth's avatar
Jens Korinth committed
41
class SlidingWindowTester[T <: Data](m: SlidingWindowTestModule[T]) extends PeekPokeTester(m) {
42
  // fill memory model
Jens Korinth's avatar
Jens Korinth committed
43
  //SlaveModel.fillWithLinearSeq(m.saxi, m.axi.dataWidth)(m.axi, this)
44
45
46
47
48
  reset(10) // reset
  
  var noErrors = true
  var start = 0
  val maxData = scala.math.pow(2, m.asw.cfg.width).toInt
Jens Korinth's avatar
Jens Korinth committed
49
  val totalSteps = (m.saxi.cfg.size * m.axi.dataWidth) / m.asw.cfg.width - m.asw.cfg.depth
50
51
  printf("mem size = %d bytes, total steps = %d".format(m.saxi.cfg.size, totalSteps))
  // wait for data to be valid
Jens Korinth's avatar
Jens Korinth committed
52
  while (peek(m.io.asw_data_valid) == 0) step(1)
53
54
55
  // check all sliding windows within size of memory slave (no border handling)
  for (i <- 0 until totalSteps if noErrors) {
    val expected = (0 until m.asw.cfg.depth) map (i => (i + start) % maxData)
Jens Korinth's avatar
Jens Korinth committed
56
    val found = (0 until m.asw.cfg.depth) map (i => peek(m.io.asw_data_bits) & (1 << (m.asw.cfg.depth - i - 1)))
57
58
59
    noErrors = expected.equals(found)
    if (!noErrors)
      println("Mismatch at step #%d: expected %s, found %s".format(start, expected.toString, found.toString))
Jens Korinth's avatar
Jens Korinth committed
60
    assert(noErrors, "sliding window #%d should match".format(i))
61
62
    start += 1
    // advance simulation with handshake
Jens Korinth's avatar
Jens Korinth committed
63
    poke(m.io.ready, true)
64
    step(1)
Jens Korinth's avatar
Jens Korinth committed
65
    poke(m.io.ready, false)
66
    // wait for next valid
Jens Korinth's avatar
Jens Korinth committed
67
    while (peek(m.io.asw_data_valid) == 0) step(1)
68
69
70
71
  }
}

/** Unit test suite for AxiSlidingWindow. **/
Jens Korinth's avatar
Jens Korinth committed
72
73
class SlidingWindowSuite extends ChiselFlatSpec {
  implicit val logLevel = Logging.Level.Info
Jens Korinth's avatar
Jens Korinth committed
74
75
  val chiselArgs = Array("--fint-write-vcd")
  implicit val axi: Axi4.Configuration = Axi4.Configuration(addrWidth = AddrWidth(32), dataWidth = DataWidth(64))
76
  implicit val afa: AxiFifoAdapter.Configuration = AxiFifoAdapter.Configuration(fifoDepth = 16)
77

78
  private def slidingWindow(width: Int, depth: Int)(implicit afa: AxiFifoAdapter.Configuration) = {
Jens Korinth's avatar
Jens Korinth committed
79
    val args = chiselArgs ++ Array("--target-dir", "test/slidingWindow/%dx%d".format(width, depth))
Jens Korinth's avatar
Jens Korinth committed
80
81
82
83
84
85
    val cfg = SlidingWindow.Configuration(gen = UInt(width.W),
                                          depth = depth,
                                          width = width,
                                          afa = afa)
    Driver.execute(args, () => new SlidingWindowTestModule(cfg))
      { m => new SlidingWindowTester(m) }
86
87
  }

Jens Korinth's avatar
Jens Korinth committed
88
89
90
91
92
93
94
95
96
  "slidingWindow_8_3" should "be ok" in    { slidingWindow(8, 3) }
  "slidingWindow_16_8" should "be ok" in   { slidingWindow(16, 3) }
  "slidingWindow_32_8" should "be ok" in   { slidingWindow(32, 3) }
  "slidingWindow_8_10" should "be ok" in   { slidingWindow(8, 10) }
  "slidingWindow_16_10" should "be ok" in  { slidingWindow(16, 10) }
  "slidingWindow_32_10" should "be ok" in  { slidingWindow(32, 10) }
  "slidingWindow_8_16" should "be ok" in   { slidingWindow(8, 16) }
  "slidingWindow_16_16" should "be ok" in  { slidingWindow(16, 16) }
  "slidingWindow_32_16" should "be ok" in  { slidingWindow(32, 16) }
97
}