summaryrefslogtreecommitdiff
path: root/chiselFrontend/src
diff options
context:
space:
mode:
Diffstat (limited to 'chiselFrontend/src')
-rw-r--r--chiselFrontend/src/main/scala/chisel3/core/Aggregate.scala8
-rw-r--r--chiselFrontend/src/main/scala/chisel3/core/Data.scala68
-rw-r--r--chiselFrontend/src/main/scala/chisel3/core/Mem.scala6
-rw-r--r--chiselFrontend/src/main/scala/chisel3/core/Reg.scala12
4 files changed, 56 insertions, 38 deletions
diff --git a/chiselFrontend/src/main/scala/chisel3/core/Aggregate.scala b/chiselFrontend/src/main/scala/chisel3/core/Aggregate.scala
index 8700b444..47f4b3e7 100644
--- a/chiselFrontend/src/main/scala/chisel3/core/Aggregate.scala
+++ b/chiselFrontend/src/main/scala/chisel3/core/Aggregate.scala
@@ -93,7 +93,7 @@ trait VecFactory {
if (compileOptions.declaredTypeMustBeUnbound) {
requireIsChiselType(gen, "vec type")
}
- new Vec(gen.chiselCloneType, n)
+ new Vec(gen.cloneTypeFull, n)
}
/** Truncate an index to implement modulo-power-of-2 addressing. */
@@ -580,9 +580,3 @@ class Bundle(implicit compileOptions: CompileOptions) extends Record {
*/
override def toPrintable: Printable = toPrintableHelper(elements.toList.reverse)
}
-
-private[core] object Bundle {
- val keywords = List("flip", "asInput", "asOutput", "cloneType", "chiselCloneType", "toBits",
- "widthOption", "signalName", "signalPathName", "signalParent", "signalComponent")
-}
-
diff --git a/chiselFrontend/src/main/scala/chisel3/core/Data.scala b/chiselFrontend/src/main/scala/chisel3/core/Data.scala
index b5c9d319..aa286e0d 100644
--- a/chiselFrontend/src/main/scala/chisel3/core/Data.scala
+++ b/chiselFrontend/src/main/scala/chisel3/core/Data.scala
@@ -87,6 +87,10 @@ object DataMirror {
// Internal reflection-style APIs, subject to change and removal whenever.
object internal {
def isSynthesizable(target: Data) = target.hasBinding
+ // For those odd cases where you need to care about object reference and uniqueness
+ def chiselTypeClone[T<:Data](target: Data): T = {
+ target.cloneTypeFull.asInstanceOf[T]
+ }
}
}
@@ -126,7 +130,7 @@ private[core] object cloneSupertype {
throw new AssertionError(
s"can't create $createdType with heterogeneous Bits types ${elt1.getClass} and ${elt2.getClass}")
}).asInstanceOf[T] }
- model.chiselCloneType
+ model.cloneTypeFull
}
else {
for (elt <- elts.tail) {
@@ -135,11 +139,20 @@ private[core] object cloneSupertype {
require(elt typeEquivalent elts.head,
s"can't create $createdType with non-equivalent types ${elts.head} and ${elt}")
}
- elts.head.chiselCloneType
+ elts.head.cloneTypeFull
}
}
}
+/** Returns the chisel type of a hardware object, allowing other hardware to be constructed from it.
+ */
+object chiselTypeOf {
+ def apply[T <: Data](target: T): T = {
+ requireIsHardware(target)
+ target.cloneTypeFull.asInstanceOf[T]
+ }
+}
+
/**
* Input, Output, and Flipped are used to define the directions of Module IOs.
*
@@ -148,22 +161,31 @@ private[core] object cloneSupertype {
* Thus, an error will be thrown if these are used on bound Data
*/
object Input {
- def apply[T<:Data](source: T): T = {
- val out = source.cloneType
+ def apply[T<:Data](source: T)(implicit compileOptions: CompileOptions): T = {
+ if (compileOptions.checkSynthesizable) {
+ requireIsChiselType(source)
+ }
+ val out = source.cloneType.asInstanceOf[T]
out.specifiedDirection = SpecifiedDirection.Input
out
}
}
object Output {
- def apply[T<:Data](source: T): T = {
- val out = source.cloneType
+ def apply[T<:Data](source: T)(implicit compileOptions: CompileOptions): T = {
+ if (compileOptions.checkSynthesizable) {
+ requireIsChiselType(source)
+ }
+ val out = source.cloneType.asInstanceOf[T]
out.specifiedDirection = SpecifiedDirection.Output
out
}
}
object Flipped {
- def apply[T<:Data](source: T): T = {
- val out = source.cloneType
+ def apply[T<:Data](source: T)(implicit compileOptions: CompileOptions): T = {
+ if (compileOptions.checkSynthesizable) {
+ requireIsChiselType(source)
+ }
+ val out = source.cloneType.asInstanceOf[T]
out.specifiedDirection = SpecifiedDirection.flip(source.specifiedDirection)
out
}
@@ -314,25 +336,27 @@ abstract class Data extends HasId {
private[chisel3] def width: Width
private[core] def legacyConnect(that: Data)(implicit sourceInfo: SourceInfo): Unit
- /** cloneType must be defined for any Chisel object extending Data.
+ /** Internal API; Chisel users should look at chisel3.chiselTypeOf(...).
+ *
+ * cloneType must be defined for any Chisel object extending Data.
* It is responsible for constructing a basic copy of the object being cloned.
- * If cloneType needs to recursively clone elements of an object, it should call
- * the cloneType methods on those elements.
+ *
* @return a copy of the object.
*/
def cloneType: this.type
- /** chiselCloneType is called at the top-level of a clone chain.
- * It calls the client's cloneType() method to construct a basic copy of the object being cloned,
- * then performs any fixups required to reconstruct the appropriate core state of the cloned object.
- * @return a copy of the object with appropriate core state.
+ /** Internal API; Chisel users should look at chisel3.chiselTypeOf(...).
+ *
+ * Returns a copy of this data type, with hardware bindings (if any) removed.
+ * Directionality data is still preserved.
*/
- def chiselCloneType: this.type = {
- val clone = this.cloneType // get a fresh object, without bindings
+ private[chisel3] def cloneTypeFull: this.type = {
+ val clone = this.cloneType.asInstanceOf[this.type] // get a fresh object, without bindings
// Only the top-level direction needs to be fixed up, cloneType should do the rest
clone.specifiedDirection = specifiedDirection
clone
}
+
final def := (that: Data)(implicit sourceInfo: SourceInfo, connectionCompileOptions: CompileOptions): Unit = this.connect(that)(sourceInfo, connectionCompileOptions)
final def <> (that: Data)(implicit sourceInfo: SourceInfo, connectionCompileOptions: CompileOptions): Unit = this.bulkConnect(that)(sourceInfo, connectionCompileOptions)
def litArg(): Option[LitArg] = None
@@ -357,7 +381,7 @@ abstract class Data extends HasId {
/** Does a reinterpret cast of the bits in this node into the format that provides.
* Returns a new Wire of that type. Does not modify existing nodes.
*
- * x.asTypeOf(that) performs the inverse operation of x = that.toBits.
+ * x.asTypeOf(that) performs the inverse operation of x := that.toBits.
*
* @note bit widths are NOT checked, may pad or drop bits from input
* @note that should have known widths
@@ -365,7 +389,7 @@ abstract class Data extends HasId {
def asTypeOf[T <: Data](that: T): T = macro SourceInfoTransform.thatArg
def do_asTypeOf[T <: Data](that: T)(implicit sourceInfo: SourceInfo, compileOptions: CompileOptions): T = {
- val thatCloned = Wire(that.chiselCloneType)
+ val thatCloned = Wire(that.cloneTypeFull)
thatCloned.connectFromBits(this.asUInt())
thatCloned
}
@@ -395,7 +419,7 @@ trait WireFactory {
if (compileOptions.declaredTypeMustBeUnbound) {
requireIsChiselType(t, "wire type")
}
- val x = t.chiselCloneType
+ val x = t.cloneTypeFull
// Bind each element of x to being a Wire
x.bind(WireBinding(Builder.forcedUserModule))
@@ -413,10 +437,10 @@ object WireInit {
def apply[T <: Data](init: T)(implicit sourceInfo: SourceInfo, compileOptions: CompileOptions): T = {
val model = (init.litArg match {
// For e.g. Wire(init=0.U(k.W)), fix the Reg's width to k
- case Some(lit) if lit.forcedWidth => init.chiselCloneType
+ case Some(lit) if lit.forcedWidth => init.cloneTypeFull
case _ => init match {
case init: Bits => init.cloneTypeWidth(Width())
- case init => init.chiselCloneType
+ case init => init.cloneTypeFull
}
}).asInstanceOf[T]
apply(model, init)
diff --git a/chiselFrontend/src/main/scala/chisel3/core/Mem.scala b/chiselFrontend/src/main/scala/chisel3/core/Mem.scala
index 1e7a795a..72d91c3c 100644
--- a/chiselFrontend/src/main/scala/chisel3/core/Mem.scala
+++ b/chiselFrontend/src/main/scala/chisel3/core/Mem.scala
@@ -23,7 +23,7 @@ object Mem {
if (compileOptions.declaredTypeMustBeUnbound) {
requireIsChiselType(t, "memory type")
}
- val mt = t.chiselCloneType
+ val mt = t.cloneTypeFull
val mem = new Mem(mt, size)
pushCommand(DefMemory(sourceInfo, mem, mt, size))
mem
@@ -92,7 +92,7 @@ sealed abstract class MemBase[T <: Data](t: T, val length: Int) extends HasId {
val port = pushCommand(
DefMemPort(sourceInfo,
- t.chiselCloneType, Node(this), dir, i.ref, Node(Builder.forcedClock))
+ t.cloneTypeFull, Node(this), dir, i.ref, Node(Builder.forcedClock))
).id
// Bind each element of port to being a MemoryPort
port.bind(MemoryPortBinding(Builder.forcedUserModule))
@@ -126,7 +126,7 @@ object SyncReadMem {
if (compileOptions.declaredTypeMustBeUnbound) {
requireIsChiselType(t, "memory type")
}
- val mt = t.chiselCloneType
+ val mt = t.cloneTypeFull
val mem = new SyncReadMem(mt, size)
pushCommand(DefSeqMemory(sourceInfo, mem, mt, size))
mem
diff --git a/chiselFrontend/src/main/scala/chisel3/core/Reg.scala b/chiselFrontend/src/main/scala/chisel3/core/Reg.scala
index 19bbee1c..14674b37 100644
--- a/chiselFrontend/src/main/scala/chisel3/core/Reg.scala
+++ b/chiselFrontend/src/main/scala/chisel3/core/Reg.scala
@@ -19,7 +19,7 @@ object Reg {
if (compileOptions.declaredTypeMustBeUnbound) {
requireIsChiselType(t, "reg type")
}
- val reg = t.chiselCloneType
+ val reg = t.cloneTypeFull
val clock = Node(Builder.forcedClock)
reg.bind(RegBinding(Builder.forcedUserModule))
@@ -36,7 +36,7 @@ object RegNext {
def apply[T <: Data](next: T)(implicit sourceInfo: SourceInfo, compileOptions: CompileOptions): T = {
val model = (next match {
case next: Bits => next.cloneTypeWidth(Width())
- case next => next.chiselCloneType
+ case next => next.cloneTypeFull
}).asInstanceOf[T]
val reg = Reg(model)
@@ -53,7 +53,7 @@ object RegNext {
def apply[T <: Data](next: T, init: T)(implicit sourceInfo: SourceInfo, compileOptions: CompileOptions): T = {
val model = (next match {
case next: Bits => next.cloneTypeWidth(Width())
- case next => next.chiselCloneType
+ case next => next.cloneTypeFull
}).asInstanceOf[T]
val reg = RegInit(model, init) // TODO: this makes NO sense
@@ -71,10 +71,10 @@ object RegInit {
def apply[T <: Data](init: T)(implicit sourceInfo: SourceInfo, compileOptions: CompileOptions): T = {
val model = (init.litArg match {
// For e.g. Reg(init=UInt(0, k)), fix the Reg's width to k
- case Some(lit) if lit.forcedWidth => init.chiselCloneType
+ case Some(lit) if lit.forcedWidth => init.cloneTypeFull
case _ => init match {
case init: Bits => init.cloneTypeWidth(Width())
- case init => init.chiselCloneType
+ case init => init.cloneTypeFull
}
}).asInstanceOf[T]
RegInit(model, init)
@@ -86,7 +86,7 @@ object RegInit {
if (compileOptions.declaredTypeMustBeUnbound) {
requireIsChiselType(t, "reg type")
}
- val reg = t.chiselCloneType
+ val reg = t.cloneTypeFull
val clock = Node(Builder.forcedClock)
val reset = Node(Builder.forcedReset)