diff options
| author | Chick Markley | 2019-10-18 19:44:08 -0700 |
|---|---|---|
| committer | Adam Izraelevitz | 2019-10-18 19:44:08 -0700 |
| commit | 7b93b0f8c48e39cc9730cf9f91340cf733dadafe (patch) | |
| tree | 3e9666c29d6c9901f221fed4728d05b9fd75067e /chiselFrontend/src/main/scala/chisel3/UIntFactory.scala | |
| parent | fafd984a923591841917cd4c3a1f4c823dc485b4 (diff) | |
Interval Data Type Support for Chisel (#1210)
Plan to be released with 3.3.
Breaks experimental Range API.
Adds new Interval type and associated support.
This commit adds the following:
- Renamed Range to IntervalRange to avoid name collision with scala Range
- Changed RangeTransform macro to Return an IntervalRange
- Improved error messages on missing comma or decimal
- Added notational support for binary point
- Some formatting cleanup also
- SIntFactory
- Change to use IntervalRange API
- UIntFactory
- UInt from range has custom width computation
- It does not need to deal with lowerbound extending bit requirements
- Code to handle special case of range"[0,0]" to have a width of 1
- IR.scala
- Removed Bound and other constraint code that was duplicating firrtl stuff
- Added new RangeType
- Added IntervalRange class and object
- RangeSpec
- modified just a bit to handle notational differences
- previous range interpolator returned tuple now returns IntervalRange
- Add IntervalType to emitter
- Added IntervalSpec with many tests
- Added ScalaIntervalSimulatorSpec which tests golden model for Interval
- Added ScalaIntervalSimulator which is a golden model for Interval
- This gold may not have been polished to a high sheen
- Add IntervalLit cases to Converter
- Add Interval PrimOps to IR
- asInterval, wrap, squz, clip, setp, decp, incp
- Add IntervalLit class to IR
- Add Interval to MonoConnect
- Add Interval Type to Bits (in experimental package)
- add conversions to Interval from other types
- Add Interval clone stuff to Data
- Add Literal creation helpers to chisel3 package
- these may move to experimental if I can figure that out
Diffstat (limited to 'chiselFrontend/src/main/scala/chisel3/UIntFactory.scala')
| -rw-r--r-- | chiselFrontend/src/main/scala/chisel3/UIntFactory.scala | 37 |
1 files changed, 26 insertions, 11 deletions
diff --git a/chiselFrontend/src/main/scala/chisel3/UIntFactory.scala b/chiselFrontend/src/main/scala/chisel3/UIntFactory.scala index a62aa493..3868962b 100644 --- a/chiselFrontend/src/main/scala/chisel3/UIntFactory.scala +++ b/chiselFrontend/src/main/scala/chisel3/UIntFactory.scala @@ -2,9 +2,10 @@ package chisel3 -import chisel3.internal.firrtl.{KnownUIntRange, NumericBound, Range, ULit, Width} - -// scalastyle:off method.name +import chisel3.internal.firrtl.{IntervalRange, KnownWidth, ULit, UnknownWidth, Width} +import firrtl.Utils +import firrtl.constraint.IsKnown +import firrtl.ir.{Closed, IntWidth, Open} // This is currently a factory because both Bits and UInt inherit it. trait UIntFactory { @@ -13,20 +14,34 @@ trait UIntFactory { /** Create a UInt port with specified width. */ def apply(width: Width): UInt = new UInt(width) - /** Create a UInt literal with specified width. */ + /** Create a UInt literal with specified width. */ + // scalastyle:off method.name protected[chisel3] def Lit(value: BigInt, width: Width): UInt = { val lit = ULit(value, width) val result = new UInt(lit.width) // Bind result to being an Literal lit.bindLitArg(result) } + /** Create a UInt with the specified range, validate that range is effectively > 0 + */ + //scalastyle:off cyclomatic.complexity + def apply(range: IntervalRange): UInt = { + // Check is only done against lower bound because range will already insist that range high >= low + range.lowerBound match { + case Closed(bound) if bound < 0 => + throw new ChiselException(s"Attempt to create UInt with closed lower bound of $bound, must be > 0") + case Open(bound) if bound < -1 => + throw new ChiselException(s"Attempt to create UInt with open lower bound of $bound, must be > -1") + case _ => + } - /** Create a UInt with the specified range */ - def apply(range: Range): UInt = { - apply(range.getWidth) - } - /** Create a UInt with the specified range */ - def apply(range: (NumericBound[Int], NumericBound[Int])): UInt = { - apply(KnownUIntRange(range._1, range._2)) + // because this is a UInt we don't have to take into account the lower bound + val newWidth = if(range.upperBound.isInstanceOf[IsKnown]) { + KnownWidth(Utils.getUIntWidth(range.maxAdjusted.get).max(1)) // max(1) handles range"[0,0]" + } else { + UnknownWidth() + } + + apply(newWidth) } } |
