diff options
| author | Adam Izraelevitz | 2016-09-25 20:35:09 -0700 |
|---|---|---|
| committer | GitHub | 2016-09-25 20:35:09 -0700 |
| commit | e54fb610c6bf0a7fe5c9c0f0e0b3acbb3728cfd0 (patch) | |
| tree | 7c186c96c782f488a9ceea21abb3f60594bf98c7 /src/main/scala/firrtl/Emitter.scala | |
| parent | 7c4fa71a062f0c18a3af13c9e8853fdec2818da9 (diff) | |
Spec features added: AnalogType and Attach (#295)
* Spec features added: AnalogType and Attach
AnalogType(width: Width):
- Concrete syntax:
wire x: AnalogType<10>
- New groundtype, very restricted in use cases.
- Can only declare ports and wires with Analog type
- Analog types are never equivalent, thus if x and y have Analog
types: x <= y is never legal.
Attach(info: Info, source: Expression, exprs: Seq[Expression]):
- Concrete syntax:
attach x to (y, z)
- New statement
- Source can be any groundtyped expression (UInt, SInt, Analog, Clock)
- Exprs must have an Analog type reference an instance port
- Source and exprs must have identical widths
Included WDefInstanceConnector to enable emission of Verilog inout
Should be mostly feature complete.
Need to update spec if PR gets accepted.
* Fixed bug where invalidated ports aren't handled
* Bugfix for VerilogPrep
Intermediate wires for invalidated instance ports were not invalidated
* Bugfix: calling create_exp with name/tpe
Returns unknown gender, which was passing through
Caused temporary wire to not be declared
Because Verilog is dumb, undeclared wires are assumed to be 1bit signals
* Addressed donggyukim's style comments
* Reworked pass to only allow analog types in attach
Restrict source to be only wire or port kind
Much simpler implementation, almost identical functionality
Clearer semantics (i think?)
* Fixup bugs from pulling in new changes from master
* comments for type eqs and small style fixes
Diffstat (limited to 'src/main/scala/firrtl/Emitter.scala')
| -rw-r--r-- | src/main/scala/firrtl/Emitter.scala | 47 |
1 files changed, 24 insertions, 23 deletions
diff --git a/src/main/scala/firrtl/Emitter.scala b/src/main/scala/firrtl/Emitter.scala index 0269a4fc..0a3068bc 100644 --- a/src/main/scala/firrtl/Emitter.scala +++ b/src/main/scala/firrtl/Emitter.scala @@ -64,6 +64,7 @@ case class VRandom(width: BigInt) extends Expression { def mapType(f: Type => Type): Expression = this def mapWidth(f: Width => Width): Expression = this } + class VerilogEmitter extends Emitter { val tab = " " def AND(e1: WrappedExpression, e2: WrappedExpression): Expression = { @@ -87,6 +88,7 @@ class VerilogEmitter extends Emitter { case (t: UIntType) => e case (t: SIntType) => Seq("$signed(",e,")") case ClockType => e + case AnalogType(w) => e } (x) match { case (e: DoPrim) => emit(op_stream(e), top + 1) @@ -106,6 +108,9 @@ class VerilogEmitter extends Emitter { val wx = bitWidth(t) - 1 if (wx > 0) w write s"[$wx:0]" case ClockType => + case t: AnalogType => + val wx = bitWidth(t) - 1 + if (wx > 0) w write s"[$wx:0]" case (t: VectorType) => emit(t.tpe, top + 1) w write s"[${t.size - 1}:0]" @@ -371,21 +376,6 @@ class VerilogEmitter extends Emitter { initials += Seq("`endif") } - def instantiate(n: String,m: String, es: Seq[Expression]) { - instdeclares += Seq(m, " ", n, " (") - es.zipWithIndex foreach {case (e, i) => - val s = Seq(tab, ".", remove_root(e), "(", LowerTypes.loweredName(e), ")") - if (i != es.size - 1) instdeclares += Seq(s, ",") - else instdeclares += s - } - instdeclares += Seq(");") - es foreach { e => - declare("wire",LowerTypes.loweredName(e), e.tpe) - val ex = WRef(LowerTypes.loweredName(e), e.tpe, kind(e), gender(e)) - if (gender(e) == FEMALE) assign(ex,netlist(e)) - } - } - def simulate(clk: Expression, en: Expression, s: Seq[Any], cond: Option[String]) { if (!at_clock.contains(clk)) at_clock(clk) = ArrayBuffer[Seq[Any]]() at_clock(clk) += Seq("`ifndef SYNTHESIS") @@ -415,10 +405,12 @@ class VerilogEmitter extends Emitter { } def build_ports(): Unit = portdefs ++= m.ports.zipWithIndex map { - case (p, i) => p.direction match { - case Input => + case (p, i) => (p.tpe, p.direction) match { + case (AnalogType(_), _) => + Seq("inout", " ", p.tpe, " ", p.name) + case (_, Input) => Seq(p.direction, " ", p.tpe, " ", p.name) - case Output => + case (_, Output) => val ex = WRef(p.name, p.tpe, PortKind, FEMALE) assign(ex, netlist(ex)) Seq(p.direction, " ", p.tpe, " ", p.name) @@ -427,9 +419,12 @@ class VerilogEmitter extends Emitter { def build_streams(s: Statement): Statement = s map build_streams match { case (s: DefWire) => - declare("wire", s.name, s.tpe) - val e = wref(s.name, s.tpe) - assign(e,netlist(e)) + declare("wire",s.name,s.tpe) + val e = wref(s.name,s.tpe) + netlist get e match { + case Some(n) => assign(e,n) + case None => + } s case (s: DefRegister) => declare("reg", s.name, s.tpe) @@ -453,9 +448,15 @@ class VerilogEmitter extends Emitter { case (s: Print) => simulate(s.clk, s.en, printf(s.string, s.args), Some("PRINTF_COND")) s - case (s: WDefInstance) => + case (s: WDefInstanceConnector) => val es = create_exps(WRef(s.name, s.tpe, InstanceKind, MALE)) - instantiate(s.name, s.module, es) + instdeclares += Seq(s.module, " ", s.name, " (") + (es zip s.exprs).zipWithIndex foreach {case ((l, r), i) => + val s = Seq(tab, ".", remove_root(l), "(", r, ")") + if (i != es.size - 1) instdeclares += Seq(s, ",") + else instdeclares += s + } + instdeclares += Seq(");") s case (s: DefMemory) => declare("reg", s.name, VectorType(s.dataType, s.depth)) |
