aboutsummaryrefslogtreecommitdiff
path: root/src/main/scala/firrtl/Compiler.scala
diff options
context:
space:
mode:
Diffstat (limited to 'src/main/scala/firrtl/Compiler.scala')
-rw-r--r--src/main/scala/firrtl/Compiler.scala53
1 files changed, 39 insertions, 14 deletions
diff --git a/src/main/scala/firrtl/Compiler.scala b/src/main/scala/firrtl/Compiler.scala
index 1ef35891..a15ca6cb 100644
--- a/src/main/scala/firrtl/Compiler.scala
+++ b/src/main/scala/firrtl/Compiler.scala
@@ -14,6 +14,7 @@ import firrtl.Utils.{error, throwInternalError}
import firrtl.annotations.TargetToken
import firrtl.annotations.TargetToken.{Field, Index}
import firrtl.annotations.transforms.{EliminateTargetPaths, ResolvePaths}
+import firrtl.options.StageUtils
/** Container of all annotations for a Firrtl compiler */
class AnnotationSeq private (private[firrtl] val underlying: List[Annotation]) {
@@ -101,6 +102,9 @@ object CircuitState {
sealed abstract class CircuitForm(private val value: Int) extends Ordered[CircuitForm] {
// Note that value is used only to allow comparisons
def compare(that: CircuitForm): Int = this.value - that.value
+
+ /** Defines a suffix to use if this form is written to a file */
+ def outputSuffix: String
}
// scalastyle:off magic.number
@@ -113,7 +117,10 @@ sealed abstract class CircuitForm(private val value: Int) extends Ordered[Circui
*
* See [[CDefMemory]] and [[CDefMPort]]
*/
-final case object ChirrtlForm extends CircuitForm(value = 3)
+final case object ChirrtlForm extends CircuitForm(value = 3) {
+ val outputSuffix: String = ".fir"
+}
+
/** High Form
*
* As detailed in the Firrtl specification
@@ -121,7 +128,10 @@ final case object ChirrtlForm extends CircuitForm(value = 3)
*
* Also see [[firrtl.ir]]
*/
-final case object HighForm extends CircuitForm(2)
+final case object HighForm extends CircuitForm(2) {
+ val outputSuffix: String = ".hi.fir"
+}
+
/** Middle Form
*
* A "lower" form than [[HighForm]] with the following restrictions:
@@ -129,14 +139,20 @@ final case object HighForm extends CircuitForm(2)
* - All whens must be removed
* - There can only be a single connection to any element
*/
-final case object MidForm extends CircuitForm(1)
+final case object MidForm extends CircuitForm(1) {
+ val outputSuffix: String = ".mid.fir"
+}
+
/** Low Form
*
* The "lowest" form. In addition to the restrictions in [[MidForm]]:
* - All aggregate types (vector/bundle) must have been removed
* - All implicit truncations must be made explicit
*/
-final case object LowForm extends CircuitForm(0)
+final case object LowForm extends CircuitForm(0) {
+ val outputSuffix: String = ".lo.fir"
+}
+
/** Unknown Form
*
* Often passes may modify a circuit (e.g. InferTypes), but return
@@ -150,6 +166,8 @@ final case object LowForm extends CircuitForm(0)
*/
final case object UnknownForm extends CircuitForm(-1) {
override def compare(that: CircuitForm): Int = { sys.error("Illegal to compare UnknownForm"); 0 }
+
+ val outputSuffix: String = ".unknown.fir"
}
// scalastyle:on magic.number
@@ -178,7 +196,7 @@ abstract class Transform extends LazyLogging {
@deprecated("Just collect the actual Annotation types the transform wants", "1.1")
final def getMyAnnotations(state: CircuitState): Seq[Annotation] = {
val msg = "getMyAnnotations is deprecated, use collect and match on concrete types"
- Driver.dramaticWarning(msg)
+ StageUtils.dramaticWarning(msg)
state.annotations.collect { case a: LegacyAnnotation if a.transform == this.getClass => a }
}
@@ -293,6 +311,9 @@ trait ResolvedAnnotationPaths {
trait Emitter extends Transform {
@deprecated("Use emission annotations instead", "firrtl 1.0")
def emit(state: CircuitState, writer: Writer): Unit
+
+ /** An output suffix to use if the output of this [[Emitter]] was written to a file */
+ def outputSuffix: String
}
/** Wraps exceptions from CustomTransforms so they can be reported appropriately */
@@ -325,11 +346,10 @@ object CompilerUtils extends LazyLogging {
/** Merge a Seq of lowering transforms with custom transforms
*
- * Custom Transforms are inserted based on their [[Transform.inputForm]] and
- * [[Transform.outputForm]]. Custom transforms are inserted in order at the
- * last location in the Seq of transforms where previous.outputForm ==
- * customTransform.inputForm. If a customTransform outputs a higher form
- * than input, [[getLoweringTransforms]] is used to relower the circuit.
+ * Custom Transforms are inserted based on their [[Transform.inputForm]] and [[Transform.outputForm]] with any
+ * [[Emitter]]s being scheduled last. Custom transforms are inserted in order at the last location in the Seq of
+ * transforms where previous.outputForm == customTransform.inputForm. If a customTransform outputs a higher form than
+ * input, [[getLoweringTransforms]] is used to relower the circuit.
*
* @example
* {{{
@@ -356,7 +376,13 @@ object CompilerUtils extends LazyLogging {
* of the previous transform.
*/
def mergeTransforms(lowering: Seq[Transform], custom: Seq[Transform]): Seq[Transform] = {
- custom.foldLeft(lowering) { case (transforms, xform) =>
+ custom
+ .sortWith{
+ case (a, b) => (a, b) match {
+ case (_: Emitter, _: Emitter) => false
+ case (_, _: Emitter) => true
+ case _ => false }}
+ .foldLeft(lowering) { case (transforms, xform) =>
val index = transforms lastIndexWhere (_.outputForm == xform.inputForm)
assert(index >= 0 || xform.inputForm == ChirrtlForm, // If ChirrtlForm just put at front
s"No transform in $lowering has outputForm ${xform.inputForm} as required by $xform")
@@ -427,7 +453,7 @@ trait Compiler extends LazyLogging {
def compileAndEmit(state: CircuitState,
customTransforms: Seq[Transform] = Seq.empty): CircuitState = {
val emitAnno = EmitCircuitAnnotation(emitter.getClass)
- compile(state.copy(annotations = emitAnno +: state.annotations), customTransforms)
+ compile(state.copy(annotations = emitAnno +: state.annotations), emitter +: customTransforms)
}
private def isCustomTransform(xform: Transform): Boolean = {
@@ -449,7 +475,7 @@ trait Compiler extends LazyLogging {
* @return result of compilation
*/
def compile(state: CircuitState, customTransforms: Seq[Transform]): CircuitState = {
- val allTransforms = CompilerUtils.mergeTransforms(transforms, customTransforms) :+ emitter
+ val allTransforms = CompilerUtils.mergeTransforms(transforms, customTransforms)
val (timeMillis, finalState) = Utils.time {
allTransforms.foldLeft(state) { (in, xform) =>
@@ -468,4 +494,3 @@ trait Compiler extends LazyLogging {
}
}
-