Commit 2cd5e201 authored by Jens Korinth's avatar Jens Korinth
Browse files

Start port to Chisel3

parent 8d7821f5
......@@ -4,9 +4,7 @@ organization := "esa.cs.tu-darmstadt.de"
version := "0.4-SNAPSHOT"
crossScalaVersions := Seq("2.10.3", "2.10.4", "2.11.0")
scalaVersion := "2.11.7"
scalaVersion := "2.11.11"
resolvers ++= Seq(
Resolver.sonatypeRepo("snapshots"),
......@@ -26,12 +24,6 @@ libraryDependencies ++= Seq(
"com.typesafe.play" %% "play-json" % "2.4.8"
)
// no parallel testing
parallelExecution in Test := false
testForkedParallel in Test := false
scalacOptions ++= Seq("-language:implicitConversions", "-language:reflectiveCalls", "-deprecation", "-feature")
// project structure
......
......@@ -34,7 +34,7 @@ object AxiModuleBuilder extends ModuleBuilder {
implicit val axi = Axi4.Configuration(AddrWidth(32),
DataWidth(64),
IdWidth(1))
implicit val axilite = Axi4Lite.Configuration(Axi4Lite.AddrWidth(32),
implicit val axilite = Axi4Lite.Configuration(AddrWidth(32),
Axi4Lite.Width64)
val modules: List[(() => Module, CoreDefinition)] = List(
......@@ -113,15 +113,15 @@ object AxiModuleBuilder extends ModuleBuilder {
)))
))
},
CoreDefinition.withActions(
CoreDefinition/*.withActions*/(
name = "Axi4LiteRegisterFile",
vendor = "esa.cs.tu-darmstadt.de",
library = "chisel",
version = "0.1",
root = root("Axi4LiteRegisterFile"),
root = root("Axi4LiteRegisterFile")/*,
postBuildActions = Seq(_ match {
case m: Axi4LiteRegisterFile => m.dumpAddressMap(root("Axi4LiteRegisterFile"))
})
})*/
)
)/*,
( // AXI4 Dummy
......
......@@ -98,34 +98,6 @@ object Axi4 {
}
}
class Protection extends Bundle {
val prot = UInt(3.W)
}
object Protection {
sealed trait Flag extends Function[Int, Int] { def apply(i: Int): Int }
object Flag {
final case object NON_PRIVILEGED extends Flag { def apply(i: Int): Int = i & ~(1 << 0) }
final case object PRIVILEGED extends Flag { def apply(i: Int): Int = i | (1 << 0) }
final case object SECURE extends Flag { def apply(i: Int): Int = i & ~(1 << 1) }
final case object NON_SECURE extends Flag { def apply(i: Int): Int = i | (1 << 1) }
final case object DATA extends Flag { def apply(i: Int): Int = i & ~(1 << 2) }
final case object INSTRUCTION extends Flag { def apply(i: Int): Int = i | (1 << 2) }
}
def apply(fs: Flag*): Int = (fs fold (identity[Int] _)) (_ andThen _) (0)
}
class Strobe(implicit cfg: Configuration) extends Bundle {
val strb = UInt((cfg.dataWidth / 8).W)
override def cloneType = { new Strobe()(cfg).asInstanceOf[this.type] }
}
object Strobe {
def apply(byteEnables: Int*): UInt = ((byteEnables map (i => (1 << i)) fold 0) (_ | _)).U
}
class Address(implicit cfg: Configuration) extends Bundle {
val id = UInt(cfg.idWidth)
val addr = UInt(cfg.addrWidth)
......@@ -155,7 +127,7 @@ object Axi4 {
}
class Write(implicit cfg: Configuration) extends DataChannel {
val strb = new Strobe
val strb = new Strobe(cfg.dataWidth)
override def cloneType = { new Write()(cfg).asInstanceOf[this.type] }
}
......@@ -169,10 +141,6 @@ object Axi4 {
override def cloneType = { new WriteResponse()(cfg).asInstanceOf[this.type] }
}
object Response {
val okay :: exokay :: slverr :: decerr :: Nil = Enum(4)
}
class Master private (implicit cfg: Configuration) extends Bundle {
val writeAddr = Decoupled(new Address)
val writeData = Decoupled(new Data.Write)
......
......@@ -4,49 +4,16 @@ import chisel3.util._
import chisel3.internal.firrtl.Width
object Axi4Lite {
sealed trait WidthLike { def width: Int }
final case class AddrWidth(width: Int) extends WidthLike
sealed trait DataWidth extends WidthLike
final case object Width32 extends DataWidth { def width = 32 }
final case object Width64 extends DataWidth { def width = 64 }
final case class IdWidth(width: Int) extends WidthLike
final case class UserWidth(width: Int) extends WidthLike
final case class RegionWidth(width: Int) extends WidthLike
implicit def fromWidthLikeToWidth(wl: WidthLike): Width = wl.width.W
implicit def fromWidthLikeToInt(wl: WidthLike): Int = wl.width
case class Configuration(addrWidth: AddrWidth,
dataWidth: DataWidth,
userWidth: UserWidth = UserWidth(0),
regionWidth: RegionWidth = RegionWidth(0))
class Protection extends Bundle {
val prot = UInt(3.W)
}
object Protection {
sealed trait Flag extends Function[Int, Int] { def apply(i: Int): Int }
final case object NON_PRIVILEGED extends Flag { def apply(i: Int): Int = i & ~(1 << 0) }
final case object PRIVILEGED extends Flag { def apply(i: Int): Int = i | (1 << 0) }
final case object SECURE extends Flag { def apply(i: Int): Int = i & ~(1 << 1) }
final case object NON_SECURE extends Flag { def apply(i: Int): Int = i | (1 << 1) }
final case object DATA extends Flag { def apply(i: Int): Int = i & ~(1 << 2) }
final case object INSTRUCTION extends Flag { def apply(i: Int): Int = i | (1 << 2) }
def apply(fs: Flag*): Int = (fs fold (identity[Int] _)) (_ andThen _) (0)
}
class Strobe(implicit cfg: Configuration) extends Bundle {
val strb = UInt((cfg.dataWidth / 8).W)
override def cloneType = { new Strobe()(cfg).asInstanceOf[this.type] }
}
object Strobe {
def apply(byteEnables: Int*): UInt = ((byteEnables map (i => (1 << i)) fold 0) (_ | _)).U
}
class Address(implicit cfg: Configuration) extends Bundle {
val addr = UInt(cfg.addrWidth)
val prot = new Protection
......@@ -69,7 +36,7 @@ object Axi4Lite {
}
class Write(implicit cfg: Configuration) extends DataChannel {
val strb = new Strobe
val strb = new Strobe(cfg.dataWidth)
override def cloneType = { new Write()(cfg).asInstanceOf[this.type] }
}
......@@ -82,10 +49,6 @@ object Axi4Lite {
override def cloneType = { new WriteResponse()(cfg).asInstanceOf[this.type] }
}
object Response {
val okay :: exokay :: slverr :: decerr :: Nil = Enum(4)
}
class Master private (implicit cfg: Configuration) extends Bundle {
val writeAddr = Decoupled(new Address)
val writeData = Decoupled(new Data.Write)
......
package chisel
import chisel3._
import chisel3.util.Enum
import chisel3.internal.firrtl.Width
package object axi {
sealed trait WidthLike { def width: Int }
private[axi] trait WidthLike { def width: Int; def toInt: Int = this }
final case class AddrWidth(width: Int) extends WidthLike {
require (width > 0 && width <= 64, "addrWidth (%d) must be 0 < addrWidth <= 64".format(width))
}
......@@ -16,4 +17,35 @@ package object axi {
implicit def fromWidthLikeToWidth(wl: WidthLike): Width = wl.width.W
implicit def fromWidthLikeToInt(wl: WidthLike): Int = wl.width
class Protection extends Bundle {
val prot = UInt(3.W)
}
object Protection {
sealed trait Flag extends Function[Int, Int] { def apply(i: Int): Int }
object Flag {
final case object NON_PRIVILEGED extends Flag { def apply(i: Int): Int = i & ~(1 << 0) }
final case object PRIVILEGED extends Flag { def apply(i: Int): Int = i | (1 << 0) }
final case object SECURE extends Flag { def apply(i: Int): Int = i & ~(1 << 1) }
final case object NON_SECURE extends Flag { def apply(i: Int): Int = i | (1 << 1) }
final case object DATA extends Flag { def apply(i: Int): Int = i & ~(1 << 2) }
final case object INSTRUCTION extends Flag { def apply(i: Int): Int = i | (1 << 2) }
}
def apply(fs: Flag*): Int = (fs fold (identity[Int] _)) (_ andThen _) (0)
}
object Response {
val okay :: exokay :: slverr :: decerr :: Nil = Enum(4)
}
class Strobe(dataWidth: Int) extends Bundle {
val strb = UInt((dataWidth / 8).W)
override def cloneType = { new Strobe(dataWidth).asInstanceOf[this.type] }
}
object Strobe {
def apply(byteEnables: Int*): UInt = ((byteEnables map (i => (1 << i)) fold 0) (_ | _)).U
}
}
package chisel.axiutils.registers
import chisel.axi.Axi4Lite._
import chisel.axi._, Axi4Lite._
import chisel.axiutils.registers._
import chisel3._
import chisel3.util._
......@@ -10,11 +10,11 @@ import scala.util.Properties.{lineSeparator => NL}
* @param width Register data width (in bits).
* @param regs Map from offsets in addrGranularity to register implementations.
**/
case class Axi4LiteRegisterFileConfiguration(addrGranularity: Int = 8, regs: Map[Int, ControlRegister])
case class Axi4LiteRegisterFileConfiguration(addrGranularity: Int = 32, regs: Map[Int, ControlRegister])
(implicit axi: Configuration) {
/* internal helpers: */
private def overlap(p: (BitRange, BitRange)) = p._1.overlapsWith(p._2)
private def makeRange(a: Int): BitRange = BitRange(a * addrGranularity + axi.dataWidth - 1, a * addrGranularity)
private def makeRange(a: Int): BitRange = BitRange(a * addrGranularity + axi.dataWidth.toInt - 1, a * addrGranularity)
private lazy val m = regs.keys.toList.sorted map makeRange
private lazy val o: Seq[Boolean] = (m.take(m.length - 1) zip m.tail) map overlap
......@@ -24,7 +24,7 @@ case class Axi4LiteRegisterFileConfiguration(addrGranularity: Int = 8, regs: Map
/** Minimum bit width of address lines. */
lazy val minAddrWidth: AddrWidth =
AddrWidth(Seq(log2Ceil(regs.size * axi.dataWidth / addrGranularity), log2Ceil(regs.keys.max)).max)
AddrWidth(Seq(log2Ceil(regs.size * axi.dataWidth.toInt / addrGranularity), log2Ceil(regs.keys.max)).max)
}
/**
......
......@@ -132,7 +132,7 @@ class Axi4LiteRegisterFileSuite extends ChiselFlatSpec {
// basic Chisel arguments
val chiselArgs = Array("--fint-write-vcd")
// implicit AXI configuration
implicit val axi = Axi4Lite.Configuration(dataWidth = Axi4Lite.Width32, addrWidth = Axi4Lite.AddrWidth(32))
implicit val axi = Axi4Lite.Configuration(dataWidth = Axi4Lite.Width32, addrWidth = AddrWidth(32))
/** Attempts to read from all registers. **/
private def readTest(size: Int, off: Int) = {
......
......@@ -14,7 +14,7 @@ class AxiMuxReadTestModule(val n: Int)(implicit axi: Axi4.Configuration) extends
val io = IO(new Bundle {
val afa_deq_ready = Output(UInt(n.W))
val afa_deq_valid = Output(UInt(n.W))
val afa_deq_bits = Vector(Output(UInt(axi.dataWidth)))
val afa_deq_bits = Input(Vec(n, UInt(axi.dataWidth)))
})
val mux = Module(new AxiMux(n))
private val asmcfg = AxiSlaveModelConfiguration(size = Some(n * 128))
......
......@@ -26,10 +26,25 @@ class FifoAxiAdapterModule1(size: Int)(implicit val axi: Axi4.Configuration) ext
class FifoAxiAdapterSuite extends ChiselFlatSpec {
"test1" should "be ok" in {
implicit val axi = Axi4.Configuration(AddrWidth(8), DataWidth(8))
Driver.execute(Array("--fint-write-vcd", "--target-dir", "test/fad"),
() => new FifoAxiAdapterModule1(size = 256))
Driver.execute(Array("--fint-write-vcd", "--target-dir", "test/fad"), () => new FifoAxiAdapterModule1(size = 256))
{ m => new FifoAxiAdapterModule1Test(m) }
}
/*"Poked data" should "be retrievable via peekAt" in {
implicit val axi = Axi4.Configuration(AddrWidth(8), DataWidth(8))
Driver.execute(Array("--is-verbose", "--fint-write-vcd", "--target-dir", "test/pokedpeekat"),
() => new AxiSlaveModel(AxiSlaveModelConfiguration(size = Some(256))))
{ m => new PeekPokeTester(m) {
reset(10)
for (i <- 0 until 256) pokeAt(m.mem, i, i.toChar)
step(100)
for (i <- 0 until 256) {
val v = peekAt(m.mem, i)
println(s"peekAt($i, mem) = $v")
expect(BigInt(i) == v, "Mem[%03d] = %d, expected: %d".format(i, v, i))
}
}}
}*/
}
class FifoAxiAdapterModule1Test(fad: FifoAxiAdapterModule1) extends PeekPokeTester(fad) {
......@@ -49,11 +64,12 @@ class FifoAxiAdapterModule1Test(fad: FifoAxiAdapterModule1) extends PeekPokeTest
reset(10)
while (peek(fad.io.datasrc_out_valid) != 0 || peek(fad.io.fifo_count) > 0) step(1)
step(10) // settle
println("--- done ---")
// check
for (i <- 0 until 256) {
assert(0 until 256 map { i =>
val v = peekAt(fad.saxi.mem, i)
expect(peekAt(fad.saxi.mem, i) == i, "Mem[%03d] = %d (%s), expected: %d (%s)"
.format(i, v, toBinaryString(v), i, toBinaryString(i)))
}
println("Mem[%03d] = %d (%s), expected: %d (%s)".format(i, v, toBinaryString(v), i, toBinaryString(i)))
v equals BigInt(i)
} reduce (_ && _))
}
Markdown is supported
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment