blob: 641279912bb3f3978591982c39ae1f16fad2eaa4 (
plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
|
// SPDX-License-Identifier: Apache-2.0
package chisel3
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 {
/** Create a UInt type with inferred width. */
def apply(): UInt = apply(Width())
/** Create a UInt port with specified width. */
def apply(width: Width): UInt = new UInt(width)
/** Create a UInt literal with specified width. */
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
*/
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 _ =>
}
// 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)
}
}
|