aboutsummaryrefslogtreecommitdiff
path: root/spec/spec.md
diff options
context:
space:
mode:
Diffstat (limited to 'spec/spec.md')
-rw-r--r--spec/spec.md2722
1 files changed, 2722 insertions, 0 deletions
diff --git a/spec/spec.md b/spec/spec.md
new file mode 100644
index 00000000..1ab779cb
--- /dev/null
+++ b/spec/spec.md
@@ -0,0 +1,2722 @@
+---
+author:
+- |
+ Patrick S. Li\
+ <psli@eecs.berkeley.edu>
+- |
+ Adam M. Izraelevitz\
+ <adamiz@eecs.berkeley.edu>
+- |
+ Jonathan Bachrach\
+ <jrb@eecs.berkeley.edu>
+title: Specification for the FIRRTL Language
+date: \today
+# Custom options added to the customized template
+version: 0.2.0
+# Options passed to the document class
+classoption:
+- 12pt
+# Link options
+colorlinks: true
+linkcolor: blue
+filecolor: magenta
+urlcolor: cyan
+toccolor: blue
+# General pandoc configuration
+toc: true
+numbersections: true
+# Header Setup
+pagestyle:
+ fancy: true
+# Margins
+geometry: margin=1in
+# pandoc-crossref
+autoSectionLabels: true
+figPrefix:
+ - Figure
+ - Figures
+eqnPrefix:
+ - Equation
+ - Equations
+tblPrefix:
+ - Table
+ - Tables
+lstPrefix:
+ - Listing
+ - Listings
+secPrefix:
+ - Section
+ - Sections
+# This 'lastDelim' option does not work...
+lastDelim: ", and"
+---
+
+# Introduction
+
+## Background
+
+The ideas for FIRRTL (Flexible Intermediate Representation for RTL) originated
+from work on Chisel, a hardware description language (HDL) embedded in Scala
+used for writing highly-parameterized circuit design generators. Chisel
+designers manipulate circuit components using Scala functions, encode their
+interfaces in Scala types, and use Scala's object-orientation features to write
+their own circuit libraries. This form of meta-programming enables expressive,
+reliable and type-safe generators that improve RTL design productivity and
+robustness.
+
+The computer architecture research group at U.C. Berkeley relies critically on
+Chisel to allow small teams of graduate students to design sophisticated RTL
+circuits. Over a three year period with under twelve graduate students, the
+architecture group has taped-out over ten different designs.
+
+Internally, the investment in developing and learning Chisel was rewarded with
+huge gains in productivity. However, Chisel's external rate of adoption was slow
+for the following reasons.
+
+1. Writing custom circuit transformers requires intimate knowledge about the
+ internals of the Chisel compiler.
+
+2. Chisel semantics are under-specified and thus impossible to target from
+ other languages.
+
+3. Error checking is unprincipled due to under-specified semantics resulting in
+ incomprehensible error messages.
+
+4. Learning a functional programming language (Scala) is difficult for RTL
+ designers with limited programming language experience.
+
+5. Confounding the previous point, conceptually separating the embedded Chisel
+ HDL from the host language is difficult for new users.
+
+6. The output of Chisel (Verilog) is unreadable and slow to simulate.
+
+As a consequence, Chisel needed to be redesigned from the ground up to
+standardize its semantics, modularize its compilation process, and cleanly
+separate its front-end, intermediate representation, and backends. A well
+defined intermediate representation (IR) allows the system to be targeted by
+other HDLs embedded in other host programming languages, making it possible for
+RTL designers to work within a language they are already comfortable with. A
+clearly defined IR with a concrete syntax also allows for inspection of the
+output of circuit generators and transformers thus making clear the distinction
+between the host language and the constructed circuit. Clearly defined semantics
+allows users without knowledge of the compiler implementation to write circuit
+transformers; examples include optimization of circuits for simulation speed,
+and automatic insertion of signal activity counters. An additional benefit of a
+well defined IR is the structural invariants that can be enforced before and
+after each compilation stage, resulting in a more robust compiler and structured
+mechanism for error checking.
+
+## Design Philosophy
+
+FIRRTL represents the standardized elaborated circuit that the Chisel HDL
+produces. FIRRTL represents the circuit immediately after Chisel's elaboration
+but before any circuit simplification. It is designed to resemble the Chisel HDL
+after all meta-programming has executed. Thus, a user program that makes little
+use of meta-programming facilities should look almost identical to the generated
+FIRRTL.
+
+For this reason, FIRRTL has first-class support for high-level constructs such
+as vector types, bundle types, conditional statements, partial connects, and
+modules. These high-level constructs are then gradually removed by a sequence of
+*lowering* transformations. During each lowering transformation, the circuit is
+rewritten into an equivalent circuit using simpler, lower-level
+constructs. Eventually the circuit is simplified to its most restricted form,
+resembling a structured netlist, which allows for easy translation to an output
+language (e.g. Verilog). This form is given the name *lowered FIRRTL* (LoFIRRTL)
+and is a strict subset of the full FIRRTL language.
+
+Because the host language is now used solely for its meta-programming
+facilities, the frontend can be very light-weight, and additional HDLs written
+in other languages can target FIRRTL and reuse the majority of the compiler
+toolchain.
+
+# Acknowledgments
+
+The FIRRTL language could not have been developed without the help of many of
+the faculty and students in the ASPIRE lab, and the University of California,
+Berkeley.
+
+This project originated from discussions with the authors' advisor, Jonathan
+Bachrach, who indicated the need for a structural redesign of the Chisel system
+around a well-defined intermediate representation. Patrick Li designed and
+implemented the first prototype of the FIRRTL language, wrote the initial
+specification for the language, and presented it to the Chisel group consisting
+of Adam Izraelevitz, Scott Beamer, David Biancolin, Christopher Celio, Henry
+Cook, Palmer Dabbelt, Donggyu Kim, Jack Koenig, Martin Maas, Albert Magyar,
+Colin Schmidt, Andrew Waterman, Yunsup Lee, Richard Lin, Eric Love, Albert Ou,
+Stephen Twigg, John Bachan, David Donofrio, Farzad Fatollahi-Fard, Jim Lawson,
+Brian Richards, Krste Asanović, and John Wawrzynek.
+
+Adam Izraelevitz then reworked the design and re-implemented FIRRTL, and after
+many discussions with Patrick Li and the Chisel group, refined the design to its
+present version.
+
+The authors would like to thank the following individuals in particular for
+their contributions to the FIRRTL project:
+
+- Andrew Waterman: for his many contributions to the design of FIRRTL's
+ constructs, for his work on Chisel 3.0, and for porting architecture
+ research infrastructure
+
+- Richard Lin: for improving the Chisel 3.0 code base for release quality
+
+- Jack Koenig: for implementing the FIRRTL parser in Scala
+
+- Henry Cook: for porting and cleaning up many aspects of Chisel 3.0,
+ including the testing infrastructure and the parameterization library
+
+- Chick Markley: for creating the new testing harness and porting the Chisel
+ tutorial
+
+- Stephen Twigg: for his expertise in hardware intermediate representations
+ and for providing many corner cases to consider
+
+- Palmer Dabbelt, Eric Love, Martin Maas, Christopher Celio, and Scott Beamer:
+ for their feedback on previous drafts of the FIRRTL specification
+
+And finally this project would not have been possible without the continuous
+feedback and encouragement of Jonathan Bachrach, and his leadership on and
+implementation of Chisel.
+
+This research was partially funded by DARPA Award Number HR0011-12-2-0016, the
+Center for Future Architecture Research, a member of STARnet, a Semiconductor
+Research Corporation program sponsored by MARCO and DARPA, and ASPIRE Lab
+industrial sponsors and affiliates Intel, Google, Huawei, Nokia, NVIDIA, Oracle,
+and Samsung. Any opinions, findings, conclusions, or recommendations in this
+paper are solely those of the authors and does not necessarily reflect the
+position or the policy of the sponsors.
+
+# Circuits and Modules
+
+## Circuits
+
+All FIRRTL circuits consist of a list of modules, each representing a hardware
+block that can be instantiated. The circuit must specify the name of the
+top-level module.
+
+``` firrtl
+circuit MyTop :
+ module MyTop :
+ ; ...
+ module MyModule :
+ ; ...
+```
+
+## Modules
+
+Each module has a given name, a list of ports, and a statement representing the
+circuit connections within the module. A module port is specified by its , which
+may be input or output, a name, and the data type of the port.
+
+The following example declares a module with one input port, one output port,
+and one statement connecting the input port to the output port. See
+[@sec:connects] for details on the connect statement.
+
+``` firrtl
+module MyModule :
+ input foo: UInt
+ output bar: UInt
+ bar <= foo
+```
+
+Note that a module definition does *not* indicate that the module will be
+physically present in the final circuit. Refer to the description of the
+instance statement for details on how to instantiate a module
+([@sec:instances]).
+
+## Externally Defined Modules
+
+Externally defined modules are modules whose implementation is not provided in
+the current circuit. Only the ports and name of the externally defined module
+are specified in the circuit. An externally defined module may include, in
+order, an optional _defname_ which sets the name of the external module in the
+resulting Verilog and zero or more name--value _parameter_ statements. Each
+name--value parameter statement will result in a value being passed to the named
+parameter in the resulting Verilog.
+
+An example of an externally defined module is:
+
+``` firrtl
+extmodule MyExternalModule :
+ input foo: UInt<2>
+ output bar: UInt<4>
+ output baz: SInt<8>
+ defname = VerilogName
+ parameter x = "hello"
+ parameter y = 42
+```
+
+The widths of all externally defined module ports must be specified. Width
+inference, described in [@sec:width-inference], is not supported for module
+ports.
+
+A common use of an externally defined module is to represent a Verilog module
+that will be written separately and provided together with FIRRTL-generated
+Verilog to downstream tools.
+
+# Types
+
+Types are used to specify the structure of the data held by each circuit
+component. All types in FIRRTL are either one of the fundamental ground types or
+are built up from aggregating other types.
+
+## Ground Types
+
+There are five ground types in FIRRTL: an unsigned integer type, a signed
+integer type, a fixed-point number type, a clock type, and an analog type.
+
+### Integer Types
+
+Both unsigned and signed integer types may optionally be given a known
+non-negative integer bit width.
+
+``` firrtl
+UInt<10>
+SInt<32>
+```
+
+Alternatively, if the bit width is omitted, it will be automatically inferred by
+FIRRTL's width inferencer, as detailed in [@sec:width-inference].
+
+``` firrtl
+UInt
+SInt
+```
+
+### Fixed-Point Number Type
+
+In general, a fixed-point binary number type represents a range of values
+corresponding with the range of some integral type scaled by a fixed power of
+two. In the FIRRTL language, the number represented by a signal of fixed-point
+type may expressed in terms of a base integer *value* term and a *binary point*,
+which represents an inverse power of two.
+
+The range of the value term is governed by a *width* an a manner analogous to
+integral types, with the additional restriction that all fixed-point number
+types are inherently signed in FIRRTL. Whenever an operation such as a
+`cat`{.firrtl} operates on the "bits" of a fixed-point number, it operates on
+the string of bits that is the signed representation of the integer value
+term. The *width* of a fixed-point typed signal is the width of this string of
+bits.
+
+$$\begin{aligned}
+ \text{fixed-point quantity} &= \left( \text{integer value} \right) \times 2^{-\left(\text{binary point}\right)}\\
+ \text{integer value} &\in \left[ -2^{(\text{width})-1}, 2^{(\text{width})-1} \right)\\
+ \text{binary point} &\in \mathbb{Z}\end{aligned}$$
+
+In the above equation, the range of possible fixed-point quantities is governed
+by two parameters beyond a the particular "value" assigned to a signal: the
+width and the binary point. Note that when the binary point is positive, it is
+equivalent to the number of bits that would fall after the binary point. Just as
+width is a parameter of integer types in FIRRTL, width and binary point are both
+parameters of the fixed-point type.
+
+When declaring a component with fixed-point number type, it is possible to leave
+the width and/or the binary point unspecified. The unspecified parameters will
+be inferred to be sufficient to hold the results of all expressions that may
+drive the component. Similar to how width inference for integer types depends on
+width-propagation rules for each FIRRTL expression and each kind of primitive
+operator, fixed-point parameter inference depends on a set of rules outlined
+throughout this spec.
+
+Included below are examples of the syntax for all possible combinations of
+specified and inferred fixed-point type parameters.
+
+``` firrtl
+Fixed<3><<2>> ; 3-bit width, 2 bits after binary point
+Fixed<10> ; 10-bit width, inferred binary point
+Fixed<<-4>> ; Inferred width, binary point of -4
+Fixed ; Inferred width and binary point
+```
+
+### Clock Type
+
+The clock type is used to describe wires and ports meant for carrying clock
+signals. The usage of components with clock types are restricted. Clock signals
+cannot be used in most primitive operations, and clock signals can only be
+connected to components that have been declared with the clock type.
+
+The clock type is specified as follows:
+
+``` firrtl
+Clock
+```
+
+### Analog Type
+
+The analog type specifies that a wire or port can be attached to multiple
+drivers. `Analog`{.firrtl} cannot be used as the type of a node or register, nor
+can it be used as the datatype of a memory. In this respect, it is similar to
+how `inout`{.firrtl} ports are used in Verilog, and FIRRTL analog signals are
+often used to interface with external Verilog or VHDL IP.
+
+In contrast with all other ground types, analog signals cannot appear on either
+side of a connection statement. Instead, analog signals are attached to each
+other with the commutative `attach`{.firrtl} statement. An analog signal may
+appear in any number of attach statements, and a legal circuit may also contain
+analog signals that are never attached. The only primitive operations that may
+be applied to analog signals are casts to other signal types.
+
+When an analog signal appears as a field of an aggregate type, the aggregate
+cannot appear in a standard connection statement; however, the partial
+connection statement will `attach`{.firrtl} corresponding analog fields of its
+operands according to the partial connection algorithm described in
+[@sec:the-partial-connection-algorithm].
+
+As with integer types, an analog type can represent a multi-bit signal. When
+analog signals are not given a concrete width, their widths are inferred
+according to a highly restrictive width inference rule, which requires that the
+widths of all arguments to a given attach operation be identical.
+
+``` firrtl
+Analog<1> ; 1-bit analog type
+Analog<32> ; 32-bit analog type
+Analog ; analog type with inferred width
+```
+
+## Vector Types
+
+A vector type is used to express an ordered sequence of elements of a given
+type. The length of the sequence must be non-negative and known.
+
+The following example specifies a ten element vector of 16-bit unsigned
+integers.
+
+``` firrtl
+UInt<16>[10]
+```
+
+The next example specifies a ten element vector of unsigned integers of omitted
+but identical bit widths.
+
+``` firrtl
+UInt[10]
+```
+
+Note that any type, including other aggregate types, may be used as the element
+type of the vector. The following example specifies a twenty element vector,
+each of which is a ten element vector of 16-bit unsigned integers.
+
+``` firrtl
+UInt<16>[10][20]
+```
+
+## Bundle Types
+
+A bundle type is used to express a collection of nested and named types. All
+fields in a bundle type must have a given name, and type.
+
+The following is an example of a possible type for representing a complex
+number. It has two fields, `real`{.firrtl}, and `imag`{.firrtl}, both 10-bit
+signed integers.
+
+``` firrtl
+{real: SInt<10>, imag: SInt<10>}
+```
+
+Additionally, a field may optionally be declared with a *flipped* orientation.
+
+``` firrtl
+{word: UInt<32>, valid: UInt<1>, flip ready: UInt<1>}
+```
+
+In a connection between circuit components with bundle types, the data carried
+by the flipped fields flow in the opposite direction as the data carried by the
+non-flipped fields.
+
+As an example, consider a module output port declared with the following type:
+
+``` firrtl
+output a: {word: UInt<32>, valid: UInt<1>, flip ready: UInt<1>}
+```
+
+In a connection to the `a`{.firrtl} port, the data carried by the
+`word`{.firrtl} and `valid`{.firrtl} sub-fields will flow out of the module,
+while data carried by the `ready`{.firrtl} sub-field will flow into the
+module. More details about how the bundle field orientation affects connections
+are explained in [@sec:connects].
+
+As in the case of vector types, a bundle field may be declared with any type,
+including other aggregate types.
+
+``` firrtl
+{real: {word: UInt<32>, valid: UInt<1>, flip ready: UInt<1>}
+ imag: {word: UInt<32>, valid: UInt<1>, flip ready: UInt<1>}}
+
+```
+
+When calculating the final direction of data flow, the orientation of a field is
+applied recursively to all nested types in the field. As an example, consider
+the following module port declared with a bundle type containing a nested bundle
+type.
+
+``` firrtl
+output myport: {a: UInt, flip b: {c: UInt, flip d: UInt}}
+```
+
+In a connection to `myport`{.firrtl}, the `a`{.firrtl} sub-field flows out of
+the module. The `c`{.firrtl} sub-field contained in the `b`{.firrtl} sub-field
+flows into the module, and the `d`{.firrtl} sub-field contained in the
+`b`{.firrtl} sub-field flows out of the module.
+
+## Passive Types
+
+It is inappropriate for some circuit components to be declared with a type that
+allows for data to flow in both directions. For example, all sub-elements in a
+memory should flow in the same direction. These components are restricted to
+only have a passive type.
+
+Intuitively, a passive type is a type where all data flows in the same
+direction, and is defined to be a type that recursively contains no fields with
+flipped orientations. Thus all ground types are passive types. Vector types are
+passive if their element type is passive. And bundle types are passive if no
+fields are flipped and if all field types are passive.
+
+## Type Equivalence
+
+The type equivalence relation is used to determine whether a connection between
+two components is legal. See [@sec:connects] for further details about connect
+statements.
+
+An unsigned integer type is always equivalent to another unsigned integer type
+regardless of bit width, and is not equivalent to any other type. Similarly, a
+signed integer type is always equivalent to another signed integer type
+regardless of bit width, and is not equivalent to any other type.
+
+A fixed-point number type is always equivalent to another fixed-point number
+type, regardless of width or binary point. It is not equivalent to any other
+type.
+
+Clock types are equivalent to clock types, and are not equivalent to any other
+type.
+
+Two vector types are equivalent if they have the same length, and if their
+element types are equivalent.
+
+Two bundle types are equivalent if they have the same number of fields, and both
+the bundles' i'th fields have matching names and orientations, as well as
+equivalent types. Consequently, `{a:UInt, b:UInt}`{.firrtl} is not equivalent to
+`{b:UInt, a:UInt}`{.firrtl}, and `{a: {flip b:UInt}}`{.firrtl} is not equivalent
+to `{flip a: {b: UInt}}`{.firrtl}.
+
+## Weak Type Equivalence
+
+The weak type equivalence relation is used to determine whether a partial
+connection between two components is legal. See [@sec:partial-connects] for
+further details about partial connect statements.
+
+Two types are weakly equivalent if their corresponding oriented types are
+equivalent.
+
+### Oriented Types
+
+The weak type equivalence relation requires first a definition of *oriented
+types*. Intuitively, an oriented type is a type where all orientation
+information is collated and coupled with the leaf ground types instead of in
+bundle fields.
+
+An oriented ground type is an orientation coupled with a ground type. An
+oriented vector type is an ordered sequence of positive length of elements of a
+given oriented type. An oriented bundle type is a collection of oriented fields,
+each containing a name and an oriented type, but no orientation.
+
+Applying a flip orientation to an oriented type recursively reverses the
+orientation of every oriented ground type contained within. Applying a non-flip
+orientation to an oriented type does nothing.
+
+### Conversion to Oriented Types
+
+To convert a ground type to an oriented ground type, attach a non-flip
+orientation to the ground type.
+
+To convert a vector type to an oriented vector type, convert its element type to
+an oriented type, and retain its length.
+
+To convert a bundle field to an oriented field, convert its type to an oriented
+type, apply the field orientation, and combine this with the original field's
+name to create the oriented field. To convert a bundle type to an oriented
+bundle type, convert each field to an oriented field.
+
+### Oriented Type Equivalence
+
+Two oriented ground types are equivalent if their orientations match and their
+types are equivalent.
+
+Two oriented vector types are equivalent if their element types are equivalent.
+
+Two oriented bundle types are not equivalent if there exists two fields, one
+from each oriented bundle type, that have identical names but whose oriented
+types are not equivalent. Otherwise, the oriented bundle types are equivalent.
+
+As stated earlier, two types are weakly equivalent if their corresponding
+oriented types are equivalent.
+
+# Statements
+
+Statements are used to describe the components within a module and how they
+interact.
+
+## Connects
+
+The connect statement is used to specify a physically wired connection between
+two circuit components.
+
+The following example demonstrates connecting a module's input port to its
+output port, where port `myinput`{.firrtl} is connected to port
+`myoutput`{.firrtl}.
+
+``` firrtl
+module MyModule :
+ input myinput: UInt
+ output myoutput: UInt
+ myoutput <= myinput
+```
+
+In order for a connection to be legal the following conditions must hold:
+
+1. The types of the left-hand and right-hand side expressions must be
+ equivalent (see [@sec:type-equivalence] for details).
+
+2. The bit widths of the two expressions must allow for data to always flow
+ from a smaller bit width to an equal size or larger bit width.
+
+3. The flow of the left-hand side expression must be sink or duplex (see
+ [@sec:flows] for an explanation of flow).
+
+4. Either the flow of the right-hand side expression is source or duplex, or
+ the right-hand side expression has a passive type.
+
+Connect statements from a narrower ground type component to a wider ground type
+component will have its value automatically sign-extended or zero-extended to
+the larger bit width. The behaviour of connect statements between two circuit
+components with aggregate types is defined by the connection algorithm in
+[@sec:the-connection-algorithm].
+
+### The Connection Algorithm
+
+Connect statements between ground types cannot be expanded further.
+
+Connect statements between two vector typed components recursively connects each
+sub-element in the right-hand side expression to the corresponding sub-element
+in the left-hand side expression.
+
+Connect statements between two bundle typed components connects the i'th field
+of the right-hand side expression and the i'th field of the left-hand side
+expression. If the i'th field is not flipped, then the right-hand side field is
+connected to the left-hand side field. Conversely, if the i'th field is
+flipped, then the left-hand side field is connected to the right-hand side
+field.
+
+## Partial Connects
+
+Like the connect statement, the partial connect statement is also used to
+specify a physically wired connection between two circuit components. However,
+it enforces fewer restrictions on the types and widths of the circuit components
+it connects.
+
+In order for a partial connect to be legal the following conditions must hold:
+
+1. The types of the left-hand and right-hand side expressions must be weakly
+ equivalent (see [@sec:weak-type-equivalence] for details).
+
+2. The flow of the left-hand side expression must be sink or duplex (see
+ [@sec:flows] for an explanation of flow).
+
+3. Either the flow of the right-hand side expression is source or duplex, or
+ the right-hand side expression has a passive type.
+
+Partial connect statements from a narrower ground type component to a wider
+ground type component will have its value automatically sign-extended to the
+larger bit width. Partial connect statements from a wider ground type component
+to a narrower ground type component will have its value automatically truncated
+to fit the smaller bit width.
+
+Intuitively, bundle fields with matching names will be connected appropriately,
+while bundle fields not present in both types will be ignored. Similarly,
+vectors with mismatched lengths will be connected up to the shorter length, and
+the remaining sub-elements are ignored. The full algorithm is detailed in
+[@sec:the-partial-connection-algorithm].
+
+The following example demonstrates partially connecting a module's input port to
+its output port, where port `myinput`{.firrtl} is connected to port
+`myoutput`{.firrtl}.
+
+``` firrtl
+module MyModule :
+ input myinput: {flip a: UInt, b: UInt[2]}
+ output myoutput: {flip a: UInt, b: UInt[3], c: UInt}
+ myoutput <- myinput
+```
+
+The above example is equivalent to the following:
+
+``` firrtl
+module MyModule :
+ input myinput: {flip a: UInt, b: UInt[2]}
+ output myoutput: {flip a: UInt, b: UInt[3], c: UInt}
+ myinput.a <- myoutput.a
+ myoutput.b[0] <- myinput.b[0]
+ myoutput.b[1] <- myinput.b[1]
+```
+
+For details on the syntax and semantics of the sub-field expression, sub-index
+expression, and statement groups, see [@sec:sub-fields; @sec:sub-indices;
+@sec:statement-groups].
+
+### The Partial Connection Algorithm
+
+A partial connect statement between two non-analog ground type components
+connects the right-hand side expression to the left-hand side
+expression. Conversely, a *reverse* partial connect statement between two
+non-analog ground type components connects the left-hand side expression to the
+right-hand side expression. A partial connect statement between two analog-typed
+components performs an attach between the two signals.
+
+A partial (or reverse partial) connect statement between two vector typed
+components applies a partial (or reverse partial) connect from the first n
+sub-elements in the right-hand side expression to the first n corresponding
+sub-elements in the left-hand side expression, where n is the length of the
+shorter vector.
+
+A partial (or reverse partial) connect statement between two bundle typed
+components considers any pair of fields, one from the first bundle type and one
+from the second, with matching names. If the first field in the pair is not
+flipped, then we apply a partial (or reverse partial) connect from the
+right-hand side field to the left-hand side field. However, if the first field
+is flipped, then we apply a reverse partial (or partial) connect from the
+right-hand side field to the left-hand side field.
+
+## Statement Groups
+
+An ordered sequence of one or more statements can be grouped into a single
+statement, called a statement group. The following example demonstrates a
+statement group composed of three connect statements.
+
+``` firrtl
+module MyModule :
+ input a: UInt
+ input b: UInt
+ output myport1: UInt
+ output myport2: UInt
+ myport1 <= a
+ myport1 <= b
+ myport2 <= a
+```
+
+### Last Connect Semantics
+
+Ordering of statements is significant in a statement group. Intuitively, during
+elaboration, statements execute in order, and the effects of later statements
+take precedence over earlier ones. In the previous example, in the resultant
+circuit, port `b`{.firrtl} will be connected to `myport1`{.firrtl}, and port
+`a`{.firrtl} will be connected to `myport2`{.firrtl}.
+
+Note that connect and partial connect statements have equal priority, and later
+connect or partial connect statements always take priority over earlier connect
+or partial connect statements. Conditional statements are also affected by last
+connect semantics, and for details see [@sec:conditional-last-connect-semantics].
+
+In the case where a connection to a circuit component with an aggregate type is
+followed by a connection to a sub-element of that component, only the connection
+to the sub-element is overwritten. Connections to the other sub-elements remain
+unaffected. In the following example, in the resultant circuit, the `c`{.firrtl}
+sub-element of port `portx`{.firrtl} will be connected to the `c`{.firrtl}
+sub-element of `myport`{.firrtl}, and port `porty`{.firrtl} will be connected to
+the `b`{.firrtl} sub-element of `myport`{.firrtl}.
+
+``` firrtl
+module MyModule :
+ input portx: {b: UInt, c: UInt}
+ input porty: UInt
+ output myport: {b: UInt, c: UInt}
+ myport <= portx
+ myport.b <= porty
+```
+
+The above circuit can be rewritten equivalently as follows.
+
+``` firrtl
+module MyModule :
+ input portx: {b: UInt, c: UInt}
+ input porty: UInt
+ output myport: {b: UInt, c: UInt}
+ myport.b <= porty
+ myport.c <= portx.c
+```
+
+In the case where a connection to a sub-element of an aggregate circuit
+component is followed by a connection to the entire circuit component, the later
+connection overwrites the earlier connections completely.
+
+``` firrtl
+module MyModule :
+ input portx: {b: UInt, c: UInt}
+ input porty: UInt
+ output myport: {b: UInt, c: UInt}
+ myport.b <= porty
+ myport <= portx
+```
+
+The above circuit can be rewritten equivalently as follows.
+
+``` firrtl
+module MyModule :
+ input portx: {b: UInt, c: UInt}
+ input porty: UInt
+ output myport: {b: UInt, c: UInt}
+ myport <= portx
+```
+
+See [@sec:sub-fields] for more details about sub-field expressions.
+
+## Empty
+
+The empty statement does nothing and is used simply as a placeholder where a
+statement is expected. It is specified using the `skip`{.firrtl} keyword.
+
+The following example:
+
+``` firrtl
+a <= b
+skip
+c <= d
+```
+
+can be equivalently expressed as:
+
+``` firrtl
+a <= b
+c <= d
+```
+
+The empty statement is most often used as the `else`{.firrtl} branch in a
+conditional statement, or as a convenient placeholder for removed components
+during transformational passes. See [@sec:conditionals] for details on the
+conditional statement.
+
+## Wires
+
+A wire is a named combinational circuit component that can be connected to and
+from using connect and partial connect statements.
+
+The following example demonstrates instantiating a wire with the given name
+`mywire`{.firrtl} and type `UInt`{.firrtl}.
+
+``` firrtl
+wire mywire: UInt
+```
+
+## Registers
+
+A register is a named stateful circuit component.
+
+The following example demonstrates instantiating a register with the given name
+`myreg`{.firrtl}, type `SInt`{.firrtl}, and is driven by the clock signal
+`myclock`{.firrtl}.
+
+``` firrtl
+wire myclock: Clock
+reg myreg: SInt, myclock
+; ...
+```
+
+Optionally, for the purposes of circuit initialization, a register can be
+declared with a reset signal and value. In the following example,
+`myreg`{.firrtl} is assigned the value `myinit`{.firrtl} when the signal
+`myreset`{.firrtl} is high.
+
+``` firrtl
+wire myclock: Clock
+wire myreset: UInt<1>
+wire myinit: SInt
+reg myreg: SInt, myclock with: (reset => (myreset, myinit))
+; ...
+```
+
+Note that the clock signal for a register must be of type `clock`{.firrtl}, the
+reset signal must be a single bit `UInt`{.firrtl}, and the type of
+initialization value must match the declared type of the register.
+
+## Invalidates
+
+An invalidate statement is used to indicate that a circuit component contains
+indeterminate values. It is specified as follows:
+
+``` firrtl
+wire w: UInt
+w is invalid
+```
+
+Invalidate statements can be applied to any circuit component of any
+type. However, if the circuit component cannot be connected to, then the
+statement has no effect on the component. This allows the invalidate statement
+to be applied to any component, to explicitly ignore initialization coverage
+errors.
+
+The following example demonstrates the effect of invalidating a variety of
+circuit components with aggregate types. See [@sec:the-invalidate-algorithm] for
+details on the algorithm for determining what is invalidated.
+
+``` firrtl
+module MyModule :
+ input in: {flip a: UInt, b: UInt}
+ output out: {flip a: UInt, b: UInt}
+ wire w: {flip a: UInt, b: UInt}
+ in is invalid
+ out is invalid
+ w is invalid
+```
+
+is equivalent to the following:
+
+``` firrtl
+module MyModule :
+ input in: {flip a: UInt, b: UInt}
+ output out: {flip a: UInt, b: UInt}
+ wire w: {flip a: UInt, b: UInt}
+ in.a is invalid
+ out.b is invalid
+ w.a is invalid
+ w.b is invalid
+```
+
+For the purposes of simulation, invalidated components are initialized to random
+values, and operations involving indeterminate values produce undefined
+behaviour. This is useful for early detection of errors in simulation.
+
+### The Invalidate Algorithm
+
+Invalidating a component with a ground type indicates that the component's value
+is undetermined if the component has sink or duplex flow (see [@sec:flows]).
+Otherwise, the component is unaffected.
+
+Invalidating a component with a vector type recursively invalidates each
+sub-element in the vector.
+
+Invalidating a component with a bundle type recursively invalidates each
+sub-element in the bundle.
+
+## Attaches
+
+The `attach`{.firrtl} statement is used to attach two or more analog signals,
+defining that their values be the same in a commutative fashion that lacks the
+directionality of a regular connection. It can only be applied to signals with
+analog type, and each analog signal may be attached zero or more times.
+
+``` firrtl
+wire x: Analog<2>
+wire y: Analog<2>
+wire z: Analog<2>
+attach(x, y) ; binary attach
+attach(z, y, x) ; attach all three signals
+```
+
+When signals of aggregate types that contain analog-typed fields are used as
+operators of a partial connection, corresponding fields of analog type are
+attached, rather than connected.
+
+## Nodes
+
+A node is simply a named intermediate value in a circuit. The node must be
+initialized to a value with a passive type and cannot be connected to. Nodes are
+often used to split a complicated compound expression into named
+sub-expressions.
+
+The following example demonstrates instantiating a node with the given name
+`mynode`{.firrtl} initialized with the output of a multiplexer (see
+[@sec:multiplexers]).
+
+``` firrtl
+wire pred: UInt<1>
+wire a: SInt
+wire b: SInt
+node mynode = mux(pred, a, b)
+```
+
+## Conditionals
+
+Connections within a conditional statement that connect to previously declared
+components hold only when the given condition is high. The condition must have a
+1-bit unsigned integer type.
+
+In the following example, the wire `x`{.firrtl} is connected to the input
+`a`{.firrtl} only when the `en`{.firrtl} signal is high. Otherwise, the wire
+`x`{.firrtl} is connected to the input `b`{.firrtl}.
+
+``` firrtl
+module MyModule :
+ input a: UInt
+ input b: UInt
+ input en: UInt<1>
+ wire x: UInt
+ when en :
+ x <= a
+ else :
+ x <= b
+```
+
+### Syntactic Shorthands
+
+The `else`{.firrtl} branch of a conditional statement may be omitted, in which
+case a default `else`{.firrtl} branch is supplied consisting of the empty
+statement.
+
+Thus the following example:
+
+``` firrtl
+module MyModule :
+ input a: UInt
+ input b: UInt
+ input en: UInt<1>
+ wire x: UInt
+ when en :
+ x <= a
+```
+
+can be equivalently expressed as:
+
+``` firrtl
+module MyModule :
+ input a: UInt
+ input b: UInt
+ input en: UInt<1>
+ wire x: UInt
+ when en :
+ x <= a
+ else :
+ skip
+```
+
+To aid readability of long chains of conditional statements, the colon following
+the `else`{.firrtl} keyword may be omitted if the `else`{.firrtl} branch
+consists of a single conditional statement.
+
+Thus the following example:
+
+``` firrtl
+module MyModule :
+ input a: UInt
+ input b: UInt
+ input c: UInt
+ input d: UInt
+ input c1: UInt<1>
+ input c2: UInt<1>
+ input c3: UInt<1>
+ wire x: UInt
+ when c1 :
+ x <= a
+ else :
+ when c2 :
+ x <= b
+ else :
+ when c3 :
+ x <= c
+ else :
+ x <= d
+```
+
+can be equivalently written as:
+
+``` firrtl
+module MyModule :
+ input a: UInt
+ input b: UInt
+ input c: UInt
+ input d: UInt
+ input c1: UInt<1>
+ input c2: UInt<1>
+ input c3: UInt<1>
+ wire x: UInt
+ when c1 :
+ x <= a
+ else when c2 :
+ x <= b
+ else when c3 :
+ x <= c
+ else :
+ x <= d
+```
+
+To additionally aid readability, a conditional statement where the contents of
+the `when`{.firrtl} branch consist of a single line may be combined into a
+single line. If an `else`{.firrtl} branch exists, then the `else`{.firrtl}
+keyword must be included on the same line.
+
+The following statement:
+
+``` firrtl
+when c :
+ a <= b
+else :
+ e <= f
+```
+
+can have the `when`{.firrtl} keyword, the `when`{.firrtl} branch, and the
+`else`{.firrtl} keyword expressed as a single line:
+
+``` firrtl
+when c : a <= b else :
+ e <= f
+```
+
+The `else`{.firrtl} branch may also be added to the single line:
+
+``` firrtl
+when c : a <= b else : e <= f
+```
+
+### Nested Declarations
+
+If a component is declared within a conditional statement, connections to the
+component are unaffected by the condition. In the following example, register
+`myreg1`{.firrtl} is always connected to `a`{.firrtl}, and register
+`myreg2`{.firrtl} is always connected to `b`{.firrtl}.
+
+``` firrtl
+module MyModule :
+ input a: UInt
+ input b: UInt
+ input en: UInt<1>
+ input clk : Clock
+ when en :
+ reg myreg1 : UInt, clk
+ myreg1 <= a
+ else :
+ reg myreg2 : UInt, clk
+ myreg2 <= b
+```
+
+Intuitively, a line can be drawn between a connection (or partial connection) to
+a component and that component's declaration. All conditional statements that
+are crossed by the line apply to that connection (or partial connection).
+
+### Initialization Coverage
+
+Because of the conditional statement, it is possible to syntactically express
+circuits containing wires that have not been connected to under all conditions.
+
+In the following example, the wire `a`{.firrtl} is connected to the wire
+`w`{.firrtl} when `en`{.firrtl} is high, but it is not specified what is
+connected to `w`{.firrtl} when `en`{.firrtl} is low.
+
+``` firrtl
+module MyModule :
+ input en: UInt<1>
+ input a: UInt
+ wire w: UInt
+ when en :
+ w <= a
+```
+
+This is an illegal FIRRTL circuit and an error will be thrown during
+compilation. All wires, memory ports, instance ports, and module ports that can
+be connected to must be connected to under all conditions. Registers do not
+need to be connected to under all conditions, as it will keep its previous value
+if unconnected.
+
+### Scoping
+
+The conditional statement creates a new *scope* within each of its
+`when`{.firrtl} and `else`{.firrtl} branches. It is an error to refer to any
+component declared within a branch after the branch has ended. As mention in
+[@sec:namespaces], circuit component declarations in a module must be unique
+within the module's flat namespace; this means that shadowing a component in an
+enclosing scope with a component of the same name inside a conditional statement
+is not allowed.
+
+### Conditional Last Connect Semantics
+
+In the case where a connection to a circuit component is followed by a
+conditional statement containing a connection to the same component, the
+connection is overwritten only when the condition holds. Intuitively, a
+multiplexer is generated such that when the condition is low, the multiplexer
+returns the old value, and otherwise returns the new value. For details about
+the multiplexer, see [@sec:multiplexers].
+
+The following example:
+
+``` firrtl
+wire a: UInt
+wire b: UInt
+wire c: UInt<1>
+wire w: UInt
+w <= a
+when c :
+ w <= b
+```
+
+can be rewritten equivalently using a multiplexer as follows:
+
+``` firrtl
+wire a: UInt
+wire b: UInt
+wire c: UInt<1>
+wire w: UInt
+w <= mux(c, b, a)
+```
+
+In the case where an invalid statement is followed by a conditional statement
+containing a connect to the invalidated component, the resulting connection to
+the component can be expressed using a conditionally valid expression. See
+[@sec:conditionally-valids] for more details about the conditionally valid
+expression.
+
+``` firrtl
+wire a: UInt
+wire c: UInt<1>
+wire w: UInt
+w is invalid
+when c :
+ w <= a
+```
+
+can be rewritten equivalently as follows:
+
+``` firrtl
+wire a: UInt
+wire c: UInt<1>
+wire w: UInt
+w <= validif(c, a)
+```
+
+The behaviour of conditional connections to circuit components with aggregate
+types can be modeled by first expanding each connect into individual connect
+statements on its ground elements (see [@sec:the-connection-algorithm;
+@sec:the-partial-connection-algorithm] for the connection and partial connection
+algorithms) and then applying the conditional last connect semantics.
+
+For example, the following snippet:
+
+``` firrtl
+wire x: {a: UInt, b: UInt}
+wire y: {a: UInt, b: UInt}
+wire c: UInt<1>
+wire w: {a: UInt, b: UInt}
+w <= x
+when c :
+ w <= y
+```
+
+can be rewritten equivalently as follows:
+
+``` firrtl
+wire x: {a:UInt, b:UInt}
+wire y: {a:UInt, b:UInt}
+wire c: UInt<1>
+wire w: {a:UInt, b:UInt}
+w.a <= mux(c, y.a, x.a)
+w.b <= mux(c, y.b, x.b)
+```
+
+Similar to the behavior of aggregate types under last connect semantics (see
+[@sec:last-connect-semantics]), the conditional connects to a sub-element of an
+aggregate component only generates a multiplexer for the sub-element that is
+overwritten.
+
+For example, the following snippet:
+
+``` firrtl
+wire x: {a: UInt, b: UInt}
+wire y: UInt
+wire c: UInt<1>
+wire w: {a: UInt, b: UInt}
+w <= x
+when c :
+ w.a <= y
+```
+
+can be rewritten equivalently as follows:
+
+``` firrtl
+wire x: {a: UInt, b: UInt}
+wire y: UInt
+wire c: UInt<1>
+wire w: {a: UInt, b: UInt}
+w.a <= mux(c, y, x.a)
+w.b <= x.b
+```
+
+## Memories
+
+A memory is an abstract representation of a hardware memory. It is characterized
+by the following parameters.
+
+1. A passive type representing the type of each element in the memory.
+
+2. A positive integer representing the number of elements in the memory.
+
+3. A variable number of named ports, each being a read port, a write port, or
+ readwrite port.
+
+4. A non-negative integer indicating the read latency, which is the number of
+ cycles after setting the port's read address before the corresponding
+ element's value can be read from the port's data field.
+
+5. A positive integer indicating the write latency, which is the number of
+ cycles after setting the port's write address and data before the
+ corresponding element within the memory holds the new value.
+
+6. A read-under-write flag indicating the behaviour when a memory location is
+ written to while a read to that location is in progress.
+
+The following example demonstrates instantiating a memory containing 256 complex
+numbers, each with 16-bit signed integer fields for its real and imaginary
+components. It has two read ports, `r1`{.firrtl} and `r2`{.firrtl}, and one
+write port, `w`{.firrtl}. It is combinationally read (read latency is zero
+cycles) and has a write latency of one cycle. Finally, its read-under-write
+behavior is undefined.
+
+``` firrtl
+mem mymem :
+ data-type => {real:SInt<16>, imag:SInt<16>}
+ depth => 256
+ reader => r1
+ reader => r2
+ writer => w
+ read-latency => 0
+ write-latency => 1
+ read-under-write => undefined
+```
+
+In the example above, the type of `mymem`{.firrtl} is:
+
+``` firrtl
+{flip r1: {addr: UInt<8>,
+ en: UInt<1>,
+ clk: Clock,
+ flip data: {real: SInt<16>, imag: SInt<16>}}
+ flip r2: {addr: UInt<8>,
+ en: UInt<1>,
+ clk: Clock,
+ flip data: {real: SInt<16>, imag: SInt<16>}}
+ flip w: {addr: UInt<8>,
+ en: UInt<1>,
+ clk: Clock,
+ data: {real: SInt<16>, imag: SInt<16>},
+ mask: {real: UInt<1>, imag: UInt<1>}}}
+```
+
+The following sections describe how a memory's field types are calculated and
+the behavior of each type of memory port.
+
+### Read Ports
+
+If a memory is declared with element type `T`{.firrtl}, has a size less than or
+equal to $2^N$, then its read ports have type:
+
+``` firrtl
+{addr: UInt<N>, en: UInt<1>, clk: Clock, flip data: T}
+```
+
+If the `en`{.firrtl} field is high, then the element value associated with the
+address in the `addr`{.firrtl} field can be retrieved by reading from the
+`data`{.firrtl} field after the appropriate read latency. If the `en`{.firrtl}
+field is low, then the value in the `data`{.firrtl} field, after the appropriate
+read latency, is undefined. The port is driven by the clock signal in the
+`clk`{.firrtl} field.
+
+### Write Ports
+
+If a memory is declared with element type `T`{.firrtl}, has a size less than or
+equal to $2^N$, then its write ports have type:
+
+``` firrtl
+{addr: UInt<N>, en: UInt<1>, clk: Clock, data: T, mask: M}
+```
+
+where `M`{.firrtl} is the mask type calculated from the element type
+`T`{.firrtl}. Intuitively, the mask type mirrors the aggregate structure of the
+element type except with all ground types replaced with a single bit unsigned
+integer type. The *non-masked portion* of the data value is defined as the set
+of data value leaf sub-elements where the corresponding mask leaf sub-element is
+high.
+
+If the `en`{.firrtl} field is high, then the non-masked portion of the
+`data`{.firrtl} field value is written, after the appropriate write latency, to
+the location indicated by the `addr`{.firrtl} field. If the `en`{.firrtl} field
+is low, then no value is written after the appropriate write latency. The port
+is driven by the clock signal in the `clk`{.firrtl} field.
+
+### Readwrite Ports
+
+Finally, the readwrite ports have type:
+
+``` firrtl
+{addr: UInt<N>, en: UInt<1>, clk: Clock, flip rdata: T, wmode: UInt<1>,
+ wdata: T, wmask: M}
+```
+
+A readwrite port is a single port that, on a given cycle, can be used either as
+a read or a write port. If the readwrite port is not in write mode (the
+`wmode`{.firrtl} field is low), then the `rdata`{.firrtl}, `addr`{.firrtl},
+`en`{.firrtl}, and `clk`{.firrtl} fields constitute its read port fields, and
+should be used accordingly. If the readwrite port is in write mode (the
+`wmode`{.firrtl} field is high), then the `wdata`{.firrtl}, `wmask`{.firrtl},
+`addr`{.firrtl}, `en`{.firrtl}, and `clk`{.firrtl} fields constitute its write
+port fields, and should be used accordingly.
+
+### Read Under Write Behaviour
+
+The read-under-write flag indicates the value held on a read port's
+`data`{.firrtl} field if its memory location is written to while it is reading.
+The flag may take on three settings: `old`{.firrtl}, `new`{.firrtl}, and
+`undefined`{.firrtl}.
+
+If the read-under-write flag is set to `old`{.firrtl}, then a read port always
+returns the value existing in the memory on the same cycle that the read was
+requested.
+
+Assuming that a combinational read always returns the value stored in the memory
+(no write forwarding), then intuitively, this is modeled as a combinational read
+from the memory that is then delayed by the appropriate read latency.
+
+If the read-under-write flag is set to `new`{.firrtl}, then a read port always
+returns the value existing in the memory on the same cycle that the read was
+made available. Intuitively, this is modeled as a combinational read from the
+memory after delaying the read address by the appropriate read latency.
+
+If the read-under-write flag is set to `undefined`{.firrtl}, then the value held
+by the read port after the appropriate read latency is undefined.
+
+For the purpose of defining such collisions, an "active write port" is a write
+port or a readwrite port that is used to initiate a write operation on a given
+clock edge, where `en`{.firrtl} is set and, for a readwriter, `wmode`{.firrtl}
+is set. An "active read port" is a read port or a readwrite port that is used to
+initiate a read operation on a given clock edge, where `en`{.firrtl} is set and,
+for a readwriter, `wmode`{.firrtl} is not set. Each operation is defined to be
+"active" for the number of cycles set by its corresponding latency, starting
+from the cycle where its inputs were provided to its associated port. Note that
+this excludes combinational reads, which are simply modeled as combinationally
+selecting from stored values
+
+For memories with independently clocked ports, a collision between a read
+operation and a write operation with independent clocks is defined to occur when
+the address of an active write port and the address of an active read port are
+the same for overlapping clock periods, or when any portion of a read operation
+overlaps part of a write operation with a matching addresses. In such cases, the
+data that is read out of the read port is undefined.
+
+### Write Under Write Behaviour
+
+In all cases, if a memory location is written to by more than one port on the
+same cycle, the stored value is undefined.
+
+## Instances
+
+FIRRTL modules are instantiated with the instance statement. The following
+example demonstrates creating an instance named `myinstance`{.firrtl} of the
+`MyModule`{.firrtl} module within the top level module `Top`{.firrtl}.
+
+``` firrtl
+circuit Top :
+ module MyModule :
+ input a: UInt
+ output b: UInt
+ b <= a
+ module Top :
+ inst myinstance of MyModule
+```
+
+The resulting instance has a bundle type. Each port of the instantiated module
+is represented by a field in the bundle with the same name and type as the
+port. The fields corresponding to input ports are flipped to indicate their data
+flows in the opposite direction as the output ports. The `myinstance`{.firrtl}
+instance in the example above has type `{flip a:UInt, b:UInt}`.
+
+Modules have the property that instances can always be *inlined* into the parent
+module without affecting the semantics of the circuit.
+
+To disallow infinitely recursive hardware, modules cannot contain instances of
+itself, either directly, or indirectly through instances of other modules it
+instantiates.
+
+## Stops
+
+The stop statement is used to halt simulations of the circuit. Backends are free
+to generate hardware to stop a running circuit for the purpose of debugging, but
+this is not required by the FIRRTL specification.
+
+A stop statement requires a clock signal, a halt condition signal that has a
+single bit unsigned integer type, and an integer exit code.
+
+For clocked statements that have side effects in the environment (stop, print,
+and verification statements), the order of execution of any such statements that
+are triggered on the same clock edge is determined by their syntactic order in
+the enclosing module. The order of execution of clocked, side-effect-having
+statements in different modules or with different clocks that trigger
+concurrently is undefined.
+
+The stop statement has an optional name attribute which can be used to attach
+metadata to the statement. The name is part of the module level
+namespace. However it can never be used in a reference since it is not of any
+valid type.
+
+``` firrtl
+wire clk: Clock
+wire halt: UInt<1>
+stop(clk, halt, 42) : optional_name
+```
+
+## Formatted Prints
+
+The formatted print statement is used to print a formatted string during
+simulations of the circuit. Backends are free to generate hardware that relays
+this information to a hardware test harness, but this is not required by the
+FIRRTL specification.
+
+A printf statement requires a clock signal, a print condition signal, a format
+string, and a variable list of argument signals. The condition signal must be a
+single bit unsigned integer type, and the argument signals must each have a
+ground type.
+
+For information about execution ordering of clocked statements with observable
+environmental side effects, see [@sec:stops].
+
+The printf statement has an optional name attribute which can be used to attach
+metadata to the statement. The name is part of the module level
+namespace. However it can never be used in a reference since it is not of any
+valid type.
+
+``` firrtl
+wire clk: Clock
+wire cond: UInt<1>
+wire a: UInt
+wire b: UInt
+printf(clk, cond, "a in hex: %x, b in decimal:%d.\n", a, b) : optional_name
+```
+
+On each positive clock edge, when the condition signal is high, the printf
+statement prints out the format string where its argument placeholders are
+substituted with the value of the corresponding argument.
+
+### Format Strings
+
+Format strings support the following argument placeholders:
+
+- `%b` : Prints the argument in binary
+
+- `%d` : Prints the argument in decimal
+
+- `%x` : Prints the argument in hexadecimal
+
+- `%%` : Prints a single `%` character
+
+Format strings support the following escape characters:
+
+- `\n` : New line
+
+- `\t` : Tab
+
+- `\\` : Back slash
+
+- `\"` : Double quote
+
+- `\'` : Single quote
+
+## Verification
+
+To facilitate simulation, model checking and formal methods, there are three
+non-synthesizable verification statements available: assert, assume and
+cover. Each type of verification statement requires a clock signal, a predicate
+signal, an enable signal and an explanatory message string literal. The
+predicate and enable signals must have single bit unsigned integer type. When an
+assert is violated the explanatory message may be issued as guidance. The
+explanatory message may be phrased as if prefixed by the words "Verifies
+that\...".
+
+Backends are free to generate the corresponding model checking constructs in the
+target language, but this is not required by the FIRRTL specification. Backends
+that do not generate such constructs should issue a warning. For example, the
+SystemVerilog emitter produces SystemVerilog assert, assume and cover
+statements, but the Verilog emitter does not and instead warns the user if any
+verification statements are encountered.
+
+For information about execution ordering of clocked statements with observable
+environmental side effects, see [@sec:stops].
+
+Any verification statement has an optional name attribute which can be used to
+attach metadata to the statement. The name is part of the module level
+namespace. However it can never be used in a reference since it is not of any
+valid type.
+
+### Assert
+
+The assert statement verifies that the predicate is true on the rising edge of
+any clock cycle when the enable is true. In other words, it verifies that enable
+implies predicate.
+
+``` firrtl
+wire clk: Clock
+wire pred: UInt<1>
+wire en: UInt<1>
+pred <= eq(X, Y)
+en <= Z_valid
+assert(clk, pred, en, "X equals Y when Z is valid") : optional_name
+```
+
+### Assume
+
+The assume statement directs the model checker to disregard any states where the
+enable is true and the predicate is not true at the rising edge of the clock
+cycle. In other words, it reduces the states to be checked to only those where
+enable implies predicate is true by definition. In simulation, assume is treated
+as an assert.
+
+``` firrtl
+wire clk: Clock
+wire pred: UInt<1>
+wire en: UInt<1>
+pred <= eq(X, Y)
+en <= Z_valid
+assume(clk, pred, en, "X equals Y when Z is valid") : optional_name
+```
+
+### Cover
+
+The cover statement verifies that the predicate is true on the rising edge of
+some clock cycle when the enable is true. In other words, it directs the model
+checker to find some way to make enable implies predicate true at some time
+step.
+
+``` firrtl
+wire clk: Clock
+wire pred: UInt<1>
+wire en: UInt<1>
+pred <= eq(X, Y)
+en <= Z_valid
+cover(clk, pred, en, "X equals Y when Z is valid") : optional_name
+```
+
+# Expressions
+
+FIRRTL expressions are used for creating literal unsigned and signed integers,
+for referring to a declared circuit component, for statically and dynamically
+accessing a nested element within a component, for creating multiplexers and
+conditionally valid signals, and for performing primitive operations.
+
+## Unsigned Integers
+
+A literal unsigned integer can be created given a non-negative integer value and
+an optional positive bit width. The following example creates a 10-bit unsigned
+integer representing the number 42.
+
+``` firrtl
+UInt<10>(42)
+```
+
+Note that it is an error to supply a bit width that is not large enough to fit
+the given value. If the bit width is omitted, then the minimum number of bits
+necessary to fit the given value will be inferred.
+
+``` firrtl
+UInt(42)
+```
+
+## Unsigned Integers from Literal Bits
+
+A literal unsigned integer can alternatively be created given a string
+representing its bit representation and an optional bit width.
+
+The following radices are supported:
+
+1.`b`{.firrtl} : For representing binary numbers.
+
+2.`o`{.firrtl} : For representing octal numbers.
+
+3.`h`{.firrtl} : For representing hexadecimal numbers.
+
+If a bit width is not given, the number of bits in the bit representation is
+directly represented by the string. The following examples create a 8-bit
+integer representing the number 13.
+
+``` firrtl
+UInt("b00001101")
+UInt("h0D")
+```
+
+If the provided bit width is larger than the number of bits required to
+represent the string's value, then the resulting value is equivalent to the
+string zero-extended up to the provided bit width. If the provided bit width is
+smaller than the number of bits represented by the string, then the resulting
+value is equivalent to the string truncated down to the provided bit width. All
+truncated bits must be zero.
+
+The following examples create a 7-bit integer representing the number 13.
+
+``` firrtl
+UInt<7>("b00001101")
+UInt<7>("o015")
+UInt<7>("hD")
+```
+
+## Signed Integers
+
+Similar to unsigned integers, a literal signed integer can be created given an
+integer value and an optional positive bit width. The following example creates
+a 10-bit unsigned integer representing the number -42.
+
+``` firrtl
+SInt<10>(-42)
+```
+
+Note that it is an error to supply a bit width that is not large enough to fit
+the given value using two's complement representation. If the bit width is
+omitted, then the minimum number of bits necessary to fit the given value will
+be inferred.
+
+``` firrtl
+SInt(-42)
+```
+
+## Signed Integers from Literal Bits
+
+Similar to unsigned integers, a literal signed integer can alternatively be
+created given a string representing its bit representation and an optional bit
+width.
+
+The bit representation contains a binary, octal or hex indicator, followed by an
+optional sign, followed by the value.
+
+If a bit width is not given, the number of bits in the bit representation is the
+minimal bitwidth to represent the value represented by the string. The following
+examples create a 8-bit integer representing the number -13. For all bases, a
+negative sign acts as if it were a unary negation; in other words, a negative
+literal produces the additive inverse of the unsigned interpretation of the
+digit pattern.
+
+``` firrtl
+SInt("b-1101")
+SInt("h-d")
+```
+
+If the provided bit width is larger than the number of bits represented by the
+string, then the resulting value is unchanged. It is an error to provide a bit
+width smaller than the number of bits required to represent the string's value.
+
+## References
+
+A reference is simply a name that refers to a previously declared circuit
+component. It may refer to a module port, node, wire, register, instance, or
+memory.
+
+The following example connects a reference expression `in`{.firrtl}, referring
+to the previously declared port `in`{.firrtl}, to the reference expression
+`out`{.firrtl}, referring to the previously declared port `out`{.firrtl}.
+
+``` firrtl
+module MyModule :
+ input in: UInt
+ output out: UInt
+ out <= in
+```
+
+In the rest of the document, for brevity, the names of components will be used
+to refer to a reference expression to that component. Thus, the above example
+will be rewritten as "the port `in`{.firrtl} is connected to the port
+`out`{.firrtl}".
+
+## Sub-fields
+
+The sub-field expression refers to a sub-element of an expression with a bundle
+type.
+
+The following example connects the `in`{.firrtl} port to the `a`{.firrtl}
+sub-element of the `out`{.firrtl} port.
+
+``` firrtl
+module MyModule :
+ input in: UInt
+ output out: {a: UInt, b: UInt}
+ out.a <= in
+```
+
+## Sub-indices
+
+The sub-index expression statically refers, by index, to a sub-element of an
+expression with a vector type. The index must be a non-negative integer and
+cannot be equal to or exceed the length of the vector it indexes.
+
+The following example connects the `in`{.firrtl} port to the fifth sub-element
+of the `out`{.firrtl} port.
+
+``` firrtl
+module MyModule :
+ input in: UInt
+ output out: UInt[10]
+ out[4] <= in
+```
+
+## Sub-accesses
+
+The sub-access expression dynamically refers to a sub-element of a vector-typed
+expression using a calculated index. The index must be an expression with an
+unsigned integer type.
+
+The following example connects the n'th sub-element of the `in`{.firrtl} port to
+the `out`{.firrtl} port.
+
+``` firrtl
+module MyModule :
+ input in: UInt[3]
+ input n: UInt<2>
+ output out: UInt
+ out <= in[n]
+```
+
+A connection from a sub-access expression can be modeled by conditionally
+connecting from every sub-element in the vector, where the condition holds when
+the dynamic index is equal to the sub-element's static index.
+
+``` firrtl
+module MyModule :
+ input in: UInt[3]
+ input n: UInt<2>
+ output out: UInt
+ when eq(n, UInt(0)) :
+ out <= in[0]
+ else when eq(n, UInt(1)) :
+ out <= in[1]
+ else when eq(n, UInt(2)) :
+ out <= in[2]
+ else :
+ out is invalid
+```
+
+The following example connects the `in`{.firrtl} port to the n'th sub-element of
+the `out`{.firrtl} port. All other sub-elements of the `out`{.firrtl} port are
+connected from the corresponding sub-elements of the `default`{.firrtl} port.
+
+``` firrtl
+module MyModule :
+ input in: UInt
+ input default: UInt[3]
+ input n: UInt<2>
+ output out: UInt[3]
+ out <= default
+ out[n] <= in
+```
+
+A connection to a sub-access expression can be modeled by conditionally
+connecting to every sub-element in the vector, where the condition holds when
+the dynamic index is equal to the sub-element's static index.
+
+``` firrtl
+module MyModule :
+ input in: UInt
+ input default: UInt[3]
+ input n: UInt<2>
+ output out: UInt[3]
+ out <= default
+ when eq(n, UInt(0)) :
+ out[0] <= in
+ else when eq(n, UInt(1)) :
+ out[1] <= in
+ else when eq(n, UInt(2)) :
+ out[2] <= in
+```
+
+The following example connects the `in`{.firrtl} port to the m'th
+`UInt`{.firrtl} sub-element of the n'th vector-typed sub-element of the
+`out`{.firrtl} port. All other sub-elements of the `out`{.firrtl} port are
+connected from the corresponding sub-elements of the `default`{.firrtl} port.
+
+``` firrtl
+module MyModule :
+ input in: UInt
+ input default: UInt[2][2]
+ input n: UInt<1>
+ input m: UInt<1>
+ output out: UInt[2][2]
+ out <= default
+ out[n][m] <= in
+```
+
+A connection to an expression containing multiple nested sub-access expressions
+can also be modeled by conditionally connecting to every sub-element in the
+expression. However the condition holds only when all dynamic indices are equal
+to all of the sub-element's static indices.
+
+``` firrtl
+module MyModule :
+ input in: UInt
+ input default: UInt[2][2]
+ input n: UInt<1>
+ input m: UInt<1>
+ output out: UInt[2][2]
+ out <= default
+ when and(eq(n, UInt(0)), eq(m, UInt(0))) :
+ out[0][0] <= in
+ else when and(eq(n, UInt(0)), eq(m, UInt(1))) :
+ out[0][1] <= in
+ else when and(eq(n, UInt(1)), eq(m, UInt(0))) :
+ out[1][0] <= in
+ else when and(eq(n, UInt(1)), eq(m, UInt(1))) :
+ out[1][1] <= in
+```
+
+## Multiplexers
+
+A multiplexer outputs one of two input expressions depending on the value of an
+unsigned selection signal.
+
+The following example connects to the `c`{.firrtl} port the result of selecting
+between the `a`{.firrtl} and `b`{.firrtl} ports. The `a`{.firrtl} port is
+selected when the `sel`{.firrtl} signal is high, otherwise the `b`{.firrtl} port
+is selected.
+
+``` firrtl
+module MyModule :
+ input a: UInt
+ input b: UInt
+ input sel: UInt<1>
+ output c: UInt
+ c <= mux(sel, a, b)
+```
+
+A multiplexer expression is legal only if the following holds.
+
+1. The type of the selection signal is an unsigned integer.
+
+1. The width of the selection signal is any of:
+
+ 1. One-bit
+
+ 1. Unspecified, but will infer to one-bit
+
+1. The types of the two input expressions are equivalent.
+
+1. The types of the two input expressions are passive (see
+ [@sec:passive-types]).
+
+## Conditionally Valids
+
+A conditionally valid expression is expressed as an input expression guarded
+with an unsigned single bit valid signal. It outputs the input expression when
+the valid signal is high, otherwise the result is undefined.
+
+The following example connects the `a`{.firrtl} port to the `c`{.firrtl} port
+when the `valid`{.firrtl} signal is high. Otherwise, the value of the
+`c`{.firrtl} port is undefined.
+
+``` firrtl
+module MyModule :
+ input a: UInt
+ input valid: UInt<1>
+ output c: UInt
+ c <= validif(valid, a)
+```
+
+A conditionally valid expression is legal only if the following holds.
+
+1. The type of the valid signal is a single bit unsigned integer.
+
+2. The type of the input expression is passive (see [@sec:passive-types]).
+
+Conditional statements can be equivalently expressed as multiplexers and
+conditionally valid expressions. See [@sec:conditionals] for details.
+
+## Primitive Operations
+
+All fundamental operations on ground types are expressed as a FIRRTL primitive
+operation. In general, each operation takes some number of argument expressions,
+along with some number of static integer literal parameters.
+
+The general form of a primitive operation is expressed as follows:
+
+``` firrtl
+op(arg0, arg1, ..., argn, int0, int1, ..., intm)
+```
+
+The following examples of primitive operations demonstrate adding two
+expressions, `a`{.firrtl} and `b`{.firrtl}, shifting expression `a`{.firrtl}
+left by 3 bits, selecting the fourth bit through and including the seventh bit
+in the `a`{.firrtl} expression, and interpreting the expression `x`{.firrtl} as
+a Clock typed signal.
+
+``` firrtl
+add(a, b)
+shl(a, 3)
+bits(a, 7, 4)
+asClock(x)
+```
+
+[@sec:primitive-operations] will describe the format and semantics of each
+primitive operation.
+
+# Primitive Operations
+
+The arguments of all primitive operations must be expressions with ground types,
+while their parameters are static integer literals. Each specific operation can
+place additional restrictions on the number and types of their arguments and
+parameters.
+
+Notationally, the width of an argument e is represented as w~e~.
+
+## Add Operation
+
+| Name | Arguments | Parmaeters | Arg Types | Result Type | Result Width |
+|------|-----------|------------|---------------|-------------|-----------------------------|
+| add | (e1,e2) | () | (UInt,UInt) | UInt | max(w~e1~,w~e2~)+1 |
+| | | | (SInt,SInt) | SInt | max(w~e1~,w~e2~)+1 |
+| | | | (Fixed,Fixed) | Fixed | see [@sec:fixed-point-math] |
+
+The add operation result is the sum of e1 and e2 without loss of precision.
+
+## Subtract Operation
+
+
+| Name | Arguments | Parmaeters | Arg Types | Result Type | Result Width |
+|------|-----------|------------|---------------|-------------|-----------------------------|
+| sub | (e1,e2) | () | (UInt,UInt) | UInt | max(w~e1~,w~e2~)+1 |
+| | | | (SInt,SInt) | SInt | max(w~e1~,w~e2~)+1 |
+| | | | (Fixed,Fixed) | Fixed | see [@sec:fixed-point-math] |
+
+The subtract operation result is e2 subtracted from e1, without loss of
+precision.
+
+## Multiply Operation
+
+| Name | Arguments | Parmaeters | Arg Types | Result Type | Result Width |
+|------|-----------|------------|---------------|-------------|-----------------------------|
+| mul | (e1,e2) | () | (UInt,UInt) | UInt | w~e1~+w~e2~ |
+| | | | (SInt,SInt) | SInt | w~e1~+w~e2~ |
+| | | | (Fixed,Fixed) | Fixed | see [@sec:fixed-point-math] |
+
+The multiply operation result is the product of e1 and e2, without loss of
+precision.
+
+## Divide Operation
+
+
+| Name | Arguments | Parmaeters | Arg Types | Result Type | Result Width |
+|------|-----------|------------|-------------|-------------|--------------|
+| div | (num,den) | () | (UInt,UInt) | UInt | w~num~ |
+| | | | (SInt,SInt) | SInt | w~num~+1 |
+
+The divide operation divides num by den, truncating the fractional portion of
+the result. This is equivalent to rounding the result towards zero. The result
+of a division where den is zero is undefined.
+
+## Modulus Operation
+
+| Name | Arguments | Parmaeters | Arg Types | Result Type | Result Width |
+|------|-----------|------------|-------------|-------------|--------------------|
+| rem | (num,den) | () | (UInt,UInt) | UInt | min(w~num~,w~den~) |
+| | | | (SInt,SInt) | SInt | min(w~num~,w~den~) |
+
+The modulus operation yields the remainder from dividing num by den, keeping the
+sign of the numerator. Together with the divide operator, the modulus operator
+satisfies the relationship below:
+
+ num = add(mul(den,div(num,den)),rem(num,den))}
+
+## Comparison Operations
+
+| Name | Arguments | Parmaeters | Arg Types | Result Type | Result Width |
+|--------|-----------|------------|---------------|-------------|--------------|
+| lt,leq | | | (UInt,UInt) | UInt | 1 |
+| gt,geq | (e1,e2) | () | (SInt,SInt) | UInt | 1 |
+| eq,neq | | | (Fixed,Fixed) | UInt | 1 |
+
+The comparison operations return an unsigned 1 bit signal with value one if e1
+is less than (lt), less than or equal to (leq), greater than (gt), greater than
+or equal to (geq), equal to (eq), or not equal to (neq) e2. The operation
+returns a value of zero otherwise.
+
+## Padding Operations
+
+| Name | Arguments | Parmaeters | Arg Types | Result Type | Result Width |
+|------|-----------|------------|-----------|-------------|-----------------------------|
+| pad | \(e\) | \(n\) | (UInt) | UInt | max(w~e~,n) |
+| | | | (SInt) | SInt | max(w~e~,n) |
+| | | | (Fixed) | Fixed | see [@sec:fixed-point-math] |
+
+
+If e's bit width is smaller than n, then the pad operation zero-extends or
+sign-extends e up to the given width n. Otherwise, the result is simply e. n
+must be non-negative. The binary point of fixed-point values is not affected by
+padding.
+
+## Interpret As UInt
+
+| Name | Arguments | Parmaeters | Arg Types | Result Type | Result Width |
+|--------|-----------|------------|-----------|-------------|--------------|
+| asUInt | \(e\) | () | (UInt) | UInt | w~e~ |
+| | | | (SInt) | UInt | w~e~ |
+| | | | (Fixed) | UInt | w~e~ |
+| | | | (Clock) | UInt | 1 |
+
+The interpret as UInt operation reinterprets e's bits as an unsigned integer.
+
+## Interpret As SInt
+
+| Name | Arguments | Parmaeters | Arg Types | Result Type | Result Width |
+|--------|-----------|------------|-----------|-------------|--------------|
+| asSInt | \(e\) | () | (UInt) | SInt | w~e~ |
+| | | | (SInt) | SInt | w~e~ |
+| | | | (Fixed) | SInt | w~e~ |
+| | | | (Clock) | SInt | 1 |
+
+The interpret as SInt operation reinterprets e's bits as a signed integer
+according to two's complement representation.
+
+## Interpret As Fixed-Point Number
+
+| Name | Arguments | Parmaeters | Arg Types | Result Type | Result Width | Result Binary Point |
+|---------|-----------|------------|-----------|-------------|--------------|---------------------|
+| asFixed | \(e\) | \(p\) | (UInt) | Fixed | w~e~ | p |
+| | | | (SInt) | Fixed | w~e~ | p |
+| | | | (Fixed) | Fixed | w~e~ | p |
+| | | | (Clock) | Fixed | 1 | p |
+
+The interpret as fixed-point operation reinterprets e's bits as a fixed-point
+number of identical width. Since all fixed-point number in FIRRTL are signed,
+the bits are taken to mean a signed value according to two's complement
+representation. They are scaled by the provided binary point p, and the result
+type has binary point p.
+
+## Interpret as Clock
+
+| Name | Arguments | Parmaeters | Arg Types | Result Type | Result Width |
+|---------|-----------|------------|-----------|-------------|--------------|
+| asClock | \(e\) | () | (UInt) | Clock | n/a |
+| | | | (SInt) | Clock | n/a |
+| | | | (Fixed) | Clock | n/a |
+| | | | (Clock) | Clock | n/a |
+
+The result of the interpret as clock operation is the Clock typed signal
+obtained from interpreting a single bit integer as a clock signal.
+
+## Shift Left Operation
+
+| Name | Arguments | Parmaeters | Arg Types | Result Type | Result Width |
+|------|-----------|------------|-----------|-------------|-----------------------------|
+| shl | \(e\) | \(n\) | (UInt) | UInt | w~e~+n |
+| | | | (SInt) | SInt | w~e~+n |
+| | | | (Fixed) | Fixed | see [@sec:fixed-point-math] |
+
+The shift left operation concatenates n zero bits to the least significant end
+of e. n must be non-negative.
+
+## Shift Right Operation
+
+| Name | Arguments | Parmaeters | Arg Types | Result Type | Result Width |
+|------|-----------|------------|-----------|-------------|-----------------------------|
+| shr | \(e\) | \(n\) | (UInt) | UInt | max(w~e~-n, 1) |
+| | | | (SInt) | SInt | max(w~e~-n, 1) |
+| | | | (Fixed) | Fixed | see [@sec:fixed-point-math] |
+
+The shift right operation truncates the least significant n bits from e. If n
+is greater than or equal to the bit-width of e, the resulting value will be zero
+for unsigned types and the sign bit for signed types. n must be non-negative.
+
+## Dynamic Shift Left Operation
+
+| Name | Arguments | Parmaeters | Arg Types | Result Type | Result Width |
+|------|-----------|------------|---------------|-------------|-----------------------------|
+| dshl | (e1, e2) | () | (UInt, UInt) | UInt | w~e1~ + 2`^`w~e2~ - 1 |
+| | | | (SInt, UInt) | SInt | w~e1~ + 2`^`w~e2~ - 1 |
+| | | | (Fixed, UInt) | Fixed | see [@sec:fixed-point-math] |
+
+The dynamic shift left operation shifts the bits in e1 e2 places towards the
+most significant bit. e2 zeroes are shifted in to the least significant bits.
+
+## Dynamic Shift Right Operation
+
+| Name | Arguments | Parmaeters | Arg Types | Result Type | Result Width |
+|------|-----------|------------|---------------|-------------|-----------------------------|
+| dshr | (e1, e2) | () | (UInt, UInt) | UInt | w~e1~ |
+| | | | (SInt, UInt) | SInt | w~e1~ |
+| | | | (Fixed, UInt) | Fixed | see [@sec:fixed-point-math] |
+
+The dynamic shift right operation shifts the bits in e1 e2 places towards the
+least significant bit. e2 signed or zeroed bits are shifted in to the most
+significant bits, and the e2 least significant bits are truncated.
+
+## Arithmetic Convert to Signed Operation
+
+| Name | Arguments | Parmaeters | Arg Types | Result Type | Result Width |
+|------|-----------|------------|-----------|-------------|--------------|
+| cvt | \(e\) | () | (UInt) | SInt | w~e~+1 |
+| | | | (SInt) | SInt | w~e~ |
+
+The result of the arithmetic convert to signed operation is a signed integer
+representing the same numerical value as e.
+
+## Negate Operation
+
+| Name | Arguments | Parmaeters | Arg Types | Result Type | Result Width |
+|------|-----------|------------|-----------|-------------|--------------|
+| neg | \(e\) | () | (UInt) | SInt | w~e~+1 |
+| | | | (SInt) | SInt | w~e~+1 |
+
+The result of the negate operation is a signed integer representing the negated
+numerical value of e.
+
+## Bitwise Complement Operation
+
+| Name | Arguments | Parmaeters | Arg Types | Result Type | Result Width |
+|------|-----------|------------|-----------|-------------|--------------|
+| not | \(e\) | () | (UInt) | UInt | w~e~ |
+| | | | (SInt) | UInt | w~e~ |
+
+The bitwise complement operation performs a logical not on each bit in e.
+
+## Binary Bitwise Operations
+
+| Name | Arguments | Parmaeters | Arg Types | Result Type | Result Width |
+|------------|-----------|------------|-------------|-------------|------------------|
+| and,or,xor | (e1, e2) | () | (UInt,UInt) | UInt | max(w~e1~,w~e2~) |
+| | | | (SInt,SInt) | UInt | max(w~e1~,w~e2~) |
+
+The above bitwise operations perform a bitwise and, or, or exclusive or on e1
+and e2. The result has the same width as its widest argument, and any narrower
+arguments are automatically zero-extended or sign-extended to match the width of
+the result before performing the operation.
+
+## Bitwise Reduction Operations
+
+
+| Name | Arguments | Parmaeters | Arg Types | Result Type | Result Width |
+|---------------|-----------|------------|-----------|-------------|--------------|
+| andr,orr,xorr | \(e\) | () | (UInt) | UInt | 1 |
+| | | | (SInt) | UInt | 1 |
+
+The bitwise reduction operations correspond to a bitwise and, or, and exclusive
+or operation, reduced over every bit in e.
+
+In all cases, the reduction incorporates as an inductive base case the "identity
+value" associated with each operator. This is defined as the value that
+preserves the value of the other argument: one for and (as $x \wedge 1 = x$),
+zero for or (as $x \vee 0 = x$), and zero for xor (as $x \oplus 0 = x$). Note
+that the logical consequence is that the and-reduction of a zero-width
+expression returns a one, while the or- and xor-reductions of a zero-width
+expression both return zero.
+
+## Concatenate Operation
+
+| Name | Arguments | Parmaeters | Arg Types | Result Type | Result Width |
+|------|-----------|------------|----------------|-------------|--------------|
+| cat | (e1,e2) | () | (UInt, UInt) | UInt | w~e1~+w~e2~ |
+| | | | (SInt, SInt) | UInt | w~e1~+w~e2~ |
+| | | | (Fixed, Fixed) | UInt | w~e1~+w~e2~ |
+
+The result of the concatenate operation is the bits of e1 concatenated to the
+most significant end of the bits of e2.
+
+## Bit Extraction Operation
+
+| Name | Arguments | Parmaeters | Arg Types | Result Type | Result Width |
+|------|-----------|------------|-----------|-------------|--------------|
+| bits | \(e\) | (hi,lo) | (UInt) | UInt | hi-lo+1 |
+| | | | (SInt) | UInt | hi-lo+1 |
+| | | | (Fixed) | UInt | hi-lo+1 |
+
+The result of the bit extraction operation are the bits of e between lo
+(inclusive) and hi (inclusive). hi must be greater than or equal to lo. Both hi
+and lo must be non-negative and strictly less than the bit width of e.
+
+## Head
+
+| Name | Arguments | Parmaeters | Arg Types | Result Type | Result Width |
+|------|-----------|------------|-----------|-------------|--------------|
+| head | \(e\) | \(n\) | (UInt) | UInt | n |
+| | | | (SInt) | UInt | n |
+| | | | (Fixed) | UInt | n |
+
+The result of the head operation are the n most significant bits of e. n must be
+non-negative and less than or equal to the bit width of e.
+
+## Tail
+
+| Name | Arguments | Parmaeters | Arg Types | Result Type | Result Width |
+|------|-----------|------------|-----------|-------------|--------------|
+| tail | \(e\) | \(n\) | (UInt) | UInt | w~e~-n |
+| | | | (SInt) | UInt | w~e~-n |
+| | | | (Fixed) | UInt | w~e~-n |
+
+The tail operation truncates the n most significant bits from e. n must be
+non-negative and less than or equal to the bit width of e.
+
+## Fixed-Point Precision Modification Operations
+
+| Name | Arguments | Parmaeters | Arg Types | Result Type | Result Width |
+|------------------|-----------|------------|-----------|-------------|--------------|
+| incp, decp, setp | \(e\) | \(n\) | (Fixed) | Fixed | |
+
+The increase precision, decrease precision, and set precision operations are
+used to alter the number of bits that appear after the binary point in a
+fixed-point number. This will cause the binary point and consequently the total
+width of the fixed-point result type to differ from those of the fixed-point
+argument type. See [@sec:fixed-point-math] for more detail.
+
+# Flows
+
+An expression's flow partially determines the legality of connecting to and from
+the expression. Every expression is classified as either *source*, *sink*, or
+*duplex*. For details on connection rules refer back to [@sec:connects;
+@sec:partial-connects].
+
+The flow of a reference to a declared circuit component depends on the kind of
+circuit component. A reference to an input port, an instance, a memory, and a
+node, is a source. A reference to an output port is a sink. A reference to a
+wire or register is duplex.
+
+The flow of a sub-index or sub-access expression is the flow of the vector-typed
+expression it indexes or accesses.
+
+The flow of a sub-field expression depends upon the orientation of the field. If
+the field is not flipped, its flow is the same flow as the bundle-typed
+expression it selects its field from. If the field is flipped, then its flow is
+the reverse of the flow of the bundle-typed expression it selects its field
+from. The reverse of source is sink, and vice-versa. The reverse of duplex
+remains duplex.
+
+The flow of all other expressions are source.
+
+# Width Inference
+
+For all circuit components declared with unspecified widths, the FIRRTL compiler
+will infer the minimum possible width that maintains the legality of all its
+incoming connections. If a component has no incoming connections, and the width
+is unspecified, then an error is thrown to indicate that the width could not be
+inferred.
+
+For module input ports with unspecified widths, the inferred width is the
+minimum possible width that maintains the legality of all incoming connections
+to all instantiations of the module.
+
+The width of a ground-typed multiplexer expression is the maximum of its two
+corresponding input widths. For multiplexing aggregate-typed expressions, the
+resulting widths of each leaf sub-element is the maximum of its corresponding
+two input leaf sub-element widths.
+
+The width of a conditionally valid expression is the width of its input
+expression.
+
+The width of each primitive operation is detailed in [@sec:primitive-operations].
+
+The width of the integer literal expressions is detailed in their respective
+sections.
+
+# Fixed-Point Math
+
+| Operator | Result Width | Result Binary Point |
+|-------------|-------------------------------------------------------|---------------------|
+| add(e1, e2) | max(w~e1~-p~e1~, w~e2~-p~e2~) + max(p~e1~, p~e2~) + 1 | max(p~e1~, p~e2~) |
+| mul(e1, e2) | w~1~ + w~2~ | p~1~ + p~2~ |
+
+: Propagation rules for binary primitive operators that operate on two
+ fixed-point numbers. Here, w~e1~ and p~e1~ are used to indicate the width and
+ binary point of the first operand, while w~e2~ and p~e2~ are used to indicate
+ the width and binary point of the second operand.
+
+
+| Operator | Result Width | Result Binary Point |
+|------------|-----------------------------|---------------------|
+| pad(e, n) | max(w~e~, n) | p~e~ |
+| shl(e, n) | w~e~ + n | p~e~ |
+| shr(e, n) | max(w~e~ - n, max(1, p~e~)) | p~e~ |
+| incp(e, n) | w~e~ + n | p~e~ + n |
+| decp(e, n) | w~e~ - n | p~e~ - n |
+| setp(e, n) | w~e~ - p~e~ + n | n |
+
+: Propagation rules for binary primitive operators that modify the width and/or
+ precision of a single fixed-point number using a constant integer literal
+ parameter. Here, w~e~ and p~e~ are used to indicate the width and binary point
+ of the fixed-point operand, while `n` is used to represent the value of the
+ constant parameter.
+
+| Operator | Result Width | Result Binary Point |
+|--------------|-----------------------|---------------------|
+| dshl(e1, e1) | w~e1~ + 2`^`w~e2~ - 1 | p~e~ |
+| dshr(e1, e2) | w~e1~ | p~e~ |
+
+: Propagation rules for dynamic shifts on fixed-point numbers. These take a
+ fixed-point argument and an UInt argument. Here, w~e1~ and p~e1~ are used to
+ indicate the width and binary point of the fixed-point operand, while w~e1~ is
+ used to represent the width of the unsigned integer operand. Note that the
+ actual shift amount will be the dynamic value of the `e2` argument.
+
+# Namespaces
+
+All modules in a circuit exist in the same module namespace, and thus must all
+have a unique name.
+
+Each module has an identifier namespace containing the names of all port and
+circuit component declarations. Thus, all declarations within a module must have
+unique names. Furthermore, the set of component declarations within a module
+must be *prefix unique*. Please see [@sec:prefix-uniqueness] for the definition
+of prefix uniqueness.
+
+Within a bundle type declaration, all field names must be unique.
+
+Within a memory declaration, all port names must be unique.
+
+During the lowering transformation, all circuit component declarations with
+aggregate types are rewritten as a group of component declarations, each with a
+ground type. The name expansion algorithm in [@sec:name-expansion-algorithm]
+calculates the names of all replacement components derived from the original
+aggregate-typed component.
+
+After the lowering transformation, the names of the lowered circuit components
+are guaranteed by the name expansion algorithm and thus can be reliably
+referenced by users to pair meta-data or other annotations with named circuit
+components.
+
+## Name Expansion Algorithm
+
+Given a component with a ground type, the name of the component is returned.
+
+Given a component with a vector type, the suffix `$`*i* is appended to the
+expanded names of each sub-element, where *i* is the index of each sub-element.
+
+Given a component with a bundle type, the suffix `$`*f* is appended to the
+expanded names of each sub-element, where *f* is the field name of each
+sub-element.
+
+## Prefix Uniqueness
+
+The *symbol sequence* of a name is the ordered list of strings that results from
+splitting the name at each occurrence of the '\$' character.
+
+A symbol sequence $a$ is a *prefix* of another symbol sequence $b$ if the
+strings in $a$ occur in the beginning of $b$.
+
+A set of names are defined to be *prefix unique* if there exists no two names
+such that the symbol sequence of one is a prefix of the symbol sequence of the
+other.
+
+As an example `firetruck$y$z`{.firrtl} shares a prefix with
+`firetruck$y`{.firrtl} and `firetruck`{.firrtl}, but does not share a prefix
+with `fire`{.firrtl}.
+
+# The Lowered FIRRTL Forms
+
+The lowered FIRRTL forms, MidFIRRTL and LoFIRRTL, are increasingly restrictive
+subsets of the FIRRTL language that omit many of the higher level
+constructs. All conforming FIRRTL compilers must provide a *lowering
+transformation* that transforms arbitrary FIRRTL circuits into equivalent
+LoFIRRTL circuits. However, there are no additional requirements related to
+accepting or producing MidFIRRTL, as the LoFIRRTL output of the lowering
+transformation will already be a legal subset of MidFIRRTL.
+
+## MidFIRRTL
+
+A FIRRTL circuit is defined to be a valid MidFIRRTL circuit if it obeys the
+following restrictions:
+
+- All widths must be explicitly defined.
+
+- The conditional statement is not used.
+
+- The dynamic sub-access expression is not used.
+
+- All components are connected to exactly once.
+
+## LoFIRRTL
+
+A FIRRTL circuit is defined to be a valid LoFIRRTL circuit if it obeys the
+following restrictions:
+
+- All widths must be explicitly defined.
+
+- The conditional statement is not used.
+
+- All components are connected to exactly once.
+
+- All components must be declared with a ground type.
+
+- The partial connect statement is not used.
+
+The first three restrictions follow from the fact that any LoFIRRTL circuit is
+also a legal MidFIRRTL circuit. The additional restrictions give LoFIRRTL a
+direct correspondence to a circuit netlist.
+
+Low level circuit transformations can be conveniently written by first lowering
+a circuit to its LoFIRRTL form, then operating on the restricted (and thus
+simpler) subset of constructs. Note that circuit transformations are still free
+to generate high level constructs as they can simply be lowered again.
+
+The following module:
+
+``` firrtl
+module MyModule :
+ input in: {a: UInt<1>, b: UInt<2>[3]}
+ input clk: Clock
+ output out: UInt
+ wire c: UInt
+ c <= in.a
+ reg r: UInt[3], clk
+ r <= in.b
+ when c :
+ r[1] <= in.a
+ out <= r[0]
+```
+
+is rewritten as the following equivalent LoFIRRTL circuit by the lowering
+transform.
+
+``` firrtl
+module MyModule :
+ input in$a: UInt<1>
+ input in$b$0: UInt<2>
+ input in$b$1: UInt<2>
+ input in$b$2: UInt<2>
+ input clk: Clock
+ output out: UInt<2>
+ wire c: UInt<1>
+ c <= in$a
+ reg r$0: UInt<2>, clk
+ reg r$1: UInt<2>, clk
+ reg r$2: UInt<2>, clk
+ r$0 <= in$b$0
+ r$1 <= mux(c, in$a, in$b$1)
+ r$2 <= in$b$2
+ out <= r$0
+```
+
+# Details about Syntax
+
+FIRRTL's syntax is designed to be human-readable but easily algorithmically
+parsed.
+
+The following characters are allowed in identifiers: upper and lower case
+letters, digits, and `_`{.firrtl}. Identifiers cannot begin with a digit.
+
+An integer literal in FIRRTL begins with one of the following, where '\#'
+represents a digit between 0 and 9.
+
+- 'h' : For indicating a hexadecimal number, followed by an optional sign. The
+ rest of the literal must consist of either digits or a letter between 'A' and
+ 'F'.
+
+- 'o' : For indicating an octal number, followed by an optional sign. The rest
+ of the literal must consist of digits between 0 and 7.
+
+- 'b' : For indicating a binary number, followed by an optional sign. The rest
+ of the literal must consist of digits that are either 0 or 1.
+
+- '-\#' : For indicating a negative decimal number. The rest of the literal must
+ consist of digits between 0 and 9.
+
+- '\#' : For indicating a positive decimal number. The rest of the literal must
+ consist of digits between 0 and 9.
+
+Comments begin with a semicolon and extend until the end of the line. Commas
+are treated as whitespace, and may be used by the user for clarity if desired.
+
+In FIRRTL, indentation is significant. Indentation must consist of spaces
+only---tabs are illegal characters. The number of spaces appearing before a
+FIRRTL IR statement is used to establish its *indent level*. Statements with the
+same indent level have the same context. The indent level of the
+`circuit`{.firrtl} declaration must be zero.
+
+Certain constructs (`circuit`{.firrtl}, `module`{.firrtl}, `when`{.firrtl}, and
+`else`{.firrtl}) create a new sub-context. The indent used on the first line of
+the sub-context establishes the indent level. The indent level of a sub-context
+is one higher than the parent. All statements in the sub-context must be
+indented by the same number of spaces. To end the sub-context, a line must
+return to the indent level of the parent.
+
+Since conditional statements (`when`{.firrtl} and `else`{.firrtl}) may be
+nested, it is possible to create a hierarchy of indent levels, each with its own
+number of preceding spaces that must be larger than its parent's and consistent
+among all direct child statements (those that are not children of an even deeper
+conditional statement).
+
+As a concrete guide, a few consequences of these rules are summarized below:
+
+- The `circuit`{.firrtl} keyword must not be indented.
+
+- All `module`{.firrtl} keywords must be indented by the same number of spaces.
+
+- In a module, all port declarations and all statements (that are not children
+ of other statements) must be indented by the same number of spaces.
+
+- The number of spaces comprising the indent level of a module is specific to
+ each module.
+
+- The statements comprising a conditional statement's branch must be indented by
+ the same number of spaces.
+
+- The statements of nested conditional statements establish their own, deeper
+ indent level.
+
+- Each `when`{.firrtl} and each `else`{.firrtl} context may have a different
+ number of non-zero spaces in its indent level.
+
+As an example illustrating some of these points, the following is a legal FIRRTL
+circuit:
+
+``` firrtl
+circuit Foo :
+ module Foo :
+ skip
+ module Bar :
+ input a: UInt<1>
+ output b: UInt<1>
+ when a:
+ b <= a
+ else:
+ b <= not(a)
+```
+
+All circuits, modules, ports and statements can optionally be followed with the
+info token `@[fileinfo]` where fileinfo is a string containing the source file
+information from where it was generated. The following characters need to be
+escaped with a leading '`\`': '`\n`' (new line), '`\t`' (tab), '`]`' and '`\`'
+itself.
+
+The following example shows the info tokens included:
+
+``` firrtl
+circuit Top : @[myfile.txt 14:8]
+ module Top : @[myfile.txt 15:2]
+ output out: UInt @[myfile.txt 16:3]
+ input b: UInt<32> @[myfile.txt 17:3]
+ input c: UInt<1> @[myfile.txt 18:3]
+ input d: UInt<16> @[myfile.txt 19:3]
+ wire a: UInt @[myfile.txt 21:8]
+ when c : @[myfile.txt 24:8]
+ a <= b @[myfile.txt 27:16]
+ else :
+ a <= d @[myfile.txt 29:17]
+ out <= add(a,a) @[myfile.txt 34:4]
+```
+
+\pagebreak
+
+# FIRRTL Language Definition
+
+``` ebnf
+(* Whitespace definitions *)
+indent = " " , { " " } ;
+dedent = ? remove one level of indentation ? ;
+newline = ? a newline character ? ;
+
+(* Integer literal definitions *)
+digit_bin = "0" | "1" ;
+digit_oct = digit_bin | "2" | "3" | "4" | "5" | "6" | "7" ;
+digit_dec = digit_oct | "8" | "9" ;
+digit_hex = digit_dec
+ | "A" | "B" | "C" | "D" | "E" | "F"
+ | "a" | "b" | "c" | "d" | "e" | "f" ;
+(* An integer *)
+int = '"' , "b" , [ "-" ] , { digit_bin } , '"'
+ | '"' , "o" , [ "-" ] , { digit_oct } , '"'
+ | '"' , "h" , [ "-" ] , { digit_hex } , '"'
+ | [ "-" ] , { digit_bin } ;
+
+(* Identifiers define legal FIRRTL or Verilog names *)
+letter = "A" | "B" | "C" | "D" | "E" | "F" | "G"
+ | "H" | "I" | "J" | "K" | "L" | "M" | "N"
+ | "O" | "P" | "Q" | "R" | "S" | "T" | "U"
+ | "V" | "W" | "X" | "Y" | "Z"
+ | "a" | "b" | "c" | "d" | "e" | "f" | "g"
+ | "h" | "i" | "j" | "k" | "l" | "m" | "n"
+ | "o" | "p" | "q" | "r" | "s" | "t" | "u"
+ | "v" | "w" | "x" | "y" | "z" ;
+id = ( "_" | letter ) , { "_" | letter | digit_dec } ;
+
+(* Fileinfo communicates Chisel source file and line/column info *)
+linecol = digit_dec , { digit_dec } , ":" , digit_dec , { digit_dec } ;
+info = "@" , "[" , { string , " " , linecol } , "]" ;
+
+(* Type definitions *)
+width = "<" , int , ">" ;
+binarypoint = "<<" , int , ">>" ;
+type_ground = "Clock"
+ | ( "UInt" | "SInt" | "Analog" ) , [ width ]
+ | "Fixed" , [ width ] , [ binarypoint ] ;
+type_aggregate = "{" , field , { field } , "}"
+ | type , "[" , int , "]" ;
+field = [ "flip" ] , id , ":" , type ;
+type = type_ground | type_aggregate ;
+
+(* Primitive operations *)
+primop_2expr_keyword =
+ "add" | "sub" | "mul" | "div" | "mod"
+ | "lt" | "leq" | "gt" | "geq" | "eq" | "neq"
+ | "dshl" | "dshr"
+ | "and" | "or" | "xor" | "cat" ;
+primop_2expr =
+ primop_2expr_keyword , "(" , expr , "," , expr ")" ;
+primop_1expr_keyword =
+ "asUInt" | "asSInt" | "asClock" | "cvt"
+ | "neg" | "not"
+ | "andr" | "orr" | "xorr"
+ | "head" | "tail" ;
+primop_1expr =
+ primop_1expr_keyword , "(" , expr , ")" ;
+primop_1expr1int_keyword =
+ "pad" | "shl" | "shr" ;
+primop_1expr1int =
+ primop_1exrp1int_keywork , "(", expr , "," , int , ")" ;
+primop_1expr2int_keyword =
+ "bits" ;
+primop_1expr2int =
+ primop_1expr2int_keywork , "(" , expr , "," , int , "," , int , ")" ;
+primop = primop_2expr | primop_1expr | primop_1expr1int | primop_1expr2int ;
+
+(* Expression definitions *)
+expr =
+ ( "UInt" | "SInt" ) , [ width ] , "(" , ( int ) , ")"
+ | reference
+ | "mux" , "(" , expr , "," , expr , "," , expr , ")"
+ | "validif" , "(" , expr , "," , expr , ")"
+ | primop ;
+reference = id
+ | reference , "." , id
+ | reference , "[" , int , "]"
+ | reference , "[" , expr , "]" ;
+
+(* Memory *)
+ruw = ( "old" | "new" | "undefined" ) ;
+memory = "mem" , id , ":" , [ info ] , newline , indent ,
+ "data-type" , "=>" , type , newline ,
+ "depth" , "=>" , int , newline ,
+ "read-latency" , "=>" , int , newline ,
+ "write-latency" , "=>" , int , newline ,
+ "read-under-write" , "=>" , ruw , newline ,
+ { "reader" , "=>" , id , newline } ,
+ { "writer" , "=>" , id , newline } ,
+ { "readwriter" , "=>" , id , newline } ,
+ dedent ;
+
+(* Statements *)
+statement = "wire" , id , ":" , type , [ info ]
+ | "reg" , id , ":" , type , expr ,
+ [ "(with: {reset => (" , expr , "," , expr ")})" ] , [ info ]
+ | memory
+ | "inst" , id , "of" , id , [ info ]
+ | "node" , id , "=" , expr , [ info ]
+ | reference , "<=" , expr , [ info ]
+ | reference , "<-" , expr , [ info ]
+ | reference , "is invalid" , [ info ]
+ | "attach(" , { reference } , ")" , [ info ]
+ | "when" , expr , ":" [ info ] , newline , indent ,
+ { statement } ,
+ dedent , [ "else" , ":" , indent , { statement } , dedent ]
+ | "stop(" , expr , "," , expr , "," , int , ")" , [ info ]
+ | "printf(" , expr , "," , expr , "," , string ,
+ { expr } , ")" , [ ":" , id ] , [ info ]
+ | "skip" , [ info ] ;
+
+(* Module definitions *)
+port = ( "input" | "output" ) , id , ":": , type , [ info ] ;
+module = "module" , id , ":" , [ info ] , newline , indent ,
+ { port , newline } ,
+ { statement , newline } ,
+ dedent ;
+extmodule = "extmodule" , id , ":" , [ info ] , newline , indent ,
+ { port , newline } ,
+ [ "defname" , "=" , id , newline ] ,
+ { "parameter" , "=" , ( string | int ) , newline } ,
+ dedent ;
+
+(* Circuit definition *)
+circuit = "circuit" , id , ":" , [ info ] , newline , indent ,
+ { module | extmodule } ,
+ dedent ;
+```