summaryrefslogtreecommitdiff
path: root/chiselFrontend/src/main/scala/chisel3/core/Binder.scala
diff options
context:
space:
mode:
authorJim Lawson2016-07-06 10:01:23 -0700
committerJim Lawson2016-07-18 15:17:56 -0700
commitc5f9ea3133ef363ff8944e17d94fea79767b6bed (patch)
treecc80a6df1eb58f0feaf9f138eb7fe261ccda4ea2 /chiselFrontend/src/main/scala/chisel3/core/Binder.scala
parent53813f61b7dfe246d214ab966739d01c65c8ecb0 (diff)
Rename "Chisel" to "chisel3" (only git mv).
Diffstat (limited to 'chiselFrontend/src/main/scala/chisel3/core/Binder.scala')
-rw-r--r--chiselFrontend/src/main/scala/chisel3/core/Binder.scala64
1 files changed, 64 insertions, 0 deletions
diff --git a/chiselFrontend/src/main/scala/chisel3/core/Binder.scala b/chiselFrontend/src/main/scala/chisel3/core/Binder.scala
new file mode 100644
index 00000000..ca074527
--- /dev/null
+++ b/chiselFrontend/src/main/scala/chisel3/core/Binder.scala
@@ -0,0 +1,64 @@
+package Chisel
+
+/**
+* A Binder is a function from UnboundBinding to some Binding.
+*
+* These are used exclusively by Binding.bind and sealed in order to keep
+* all of them in one place. There are two flavors of Binders:
+* Non-terminal (returns another UnboundBinding): These are used to reformat an
+* UnboundBinding (like setting direction) before it is terminally bound.
+* Terminal (returns any other Binding): Due to the nature of Bindings, once a
+* Data is bound to anything but an UnboundBinding, it is forever locked to
+* being that type (as it now represents something in the hardware graph).
+*
+* Note that some Binders require extra arguments to be constructed, like the
+* enclosing Module.
+*/
+
+sealed trait Binder[Out <: Binding] extends Function1[UnboundBinding, Out]{
+ def apply(in: UnboundBinding): Out
+}
+
+// THE NON-TERMINAL BINDERS
+// These 'rebind' to another unbound node of different direction!
+case object InputBinder extends Binder[UnboundBinding] {
+ def apply(in: UnboundBinding) = UnboundBinding(Some(Direction.Input))
+}
+case object OutputBinder extends Binder[UnboundBinding] {
+ def apply(in: UnboundBinding) = UnboundBinding(Some(Direction.Output))
+}
+case object FlippedBinder extends Binder[UnboundBinding] {
+ def apply(in: UnboundBinding) = UnboundBinding(in.direction.map(_.flip))
+ // TODO(twigg): flipping a None should probably be a warning/error
+}
+// The need for this should be transient.
+case object NoDirectionBinder extends Binder[UnboundBinding] {
+ def apply(in: UnboundBinding) = UnboundBinding(None)
+}
+
+// THE TERMINAL BINDERS
+case object LitBinder extends Binder[LitBinding] {
+ def apply(in: UnboundBinding) = LitBinding()
+}
+
+case class MemoryPortBinder(enclosure: Module) extends Binder[MemoryPortBinding] {
+ def apply(in: UnboundBinding) = MemoryPortBinding(enclosure)
+}
+
+case class OpBinder(enclosure: Module) extends Binder[OpBinding] {
+ def apply(in: UnboundBinding) = OpBinding(enclosure)
+}
+
+// Notice how PortBinder uses the direction of the UnboundNode
+case class PortBinder(enclosure: Module) extends Binder[PortBinding] {
+ def apply(in: UnboundBinding) = PortBinding(enclosure, in.direction)
+}
+
+case class RegBinder(enclosure: Module) extends Binder[RegBinding] {
+ def apply(in: UnboundBinding) = RegBinding(enclosure)
+}
+
+case class WireBinder(enclosure: Module) extends Binder[WireBinding] {
+ def apply(in: UnboundBinding) = WireBinding(enclosure)
+}
+