I am designing a Chisel module with the following code:
import chisel3._
import chisel3.util._
class DisplayDriver extends Module {
val io = IO(new Bundle {
val digits = Input(Vec(4, UInt(4.W)))
val leds = Output(UInt(7.W))
val selector = Output(UInt(4.W))
})
// Divisor de frecuencia
val freqDiv = RegInit(0.U(11.W))
val tick = freqDiv === (4000 - 1).U
freqDiv := freqDiv + 1.U;
when (tick) {
freqDiv := 0.U
}
// Multiplexor de dÃgitos
val digitSel = RegInit(0.U(2.W))
when (tick) {
digitSel := digitSel + 1.U
}
val digit = UInt(4.W)
digit := io.digits(digitSel)
// Decodificador para el selector
io.selector := 0.U
switch (digitSel) {
is (0.U) { io.selector := "b1110".U }
is (1.U) { io.selector := "b1101".U }
is (2.U) { io.selector := "b1011".U }
is (3.U) { io.selector := "b0111".U }
}
// Decodificador para los leds
io.leds := 0.U
switch (digit) {
is (0.U) { io.leds := "b0000001".U }
is (1.U) { io.leds := "b1001111".U }
is (2.U) { io.leds := "b0010010".U }
is (3.U) { io.leds := "b0000110".U }
is (4.U) { io.leds := "b1001100".U }
is (5.U) { io.leds := "b0100100".U }
is (6.U) { io.leds := "b0100000".U }
is (7.U) { io.leds := "b0001111".U }
is (8.U) { io.leds := "b0000000".U }
is (9.U) { io.leds := "b0000100".U }
is (10.U) { io.leds := "b0001000".U }
is (11.U) { io.leds := "b1100000".U }
is (12.U) { io.leds := "b0110001".U }
is (13.U) { io.leds := "b1000010".U }
is (14.U) { io.leds := "b0110000".U }
is (15.U) { io.leds := "b0111000".U }
}
}
class Top extends Module {
val io = IO(new Bundle {
val leds = Output(UInt(7.W))
val selector = Output(UInt(4.W))
})
val displayDriver = Module(new DisplayDriver())
displayDriver.io.digits(3) := 1.U
displayDriver.io.digits(2) := 2.U
displayDriver.io.digits(1) := 3.U
displayDriver.io.digits(0) := 4.U
io.leds := displayDriver.io.leds
io.selector := displayDriver.io.selector
}
But I get the following error when running it:
[error] (run-main-0) chisel3.package$ExpectedHardwareException: data to be connected 'UInt<4>' must be hardware, not a bare Chisel type. Perhaps you forgot to wrap it in Wire(_) or IO(_)?
[error] chisel3.package$ExpectedHardwareException: data to be connected 'UInt<4>' must be hardware, not a bare Chisel type. Perhaps you forgot to wrap it in Wire(_) or IO(_)?
which apparently points to the line
digit := io.digits(digitSel)
I have tried many combinations with Wire around io.digits but it still does not compile. Indeed, following other examples, I am not able to see why I'm getting this error, since the vector is inside an IO. What is happening?
The error comes from the left hand side of the connect operation: digit should be defined as Wire.
val digit = Wire(UInt(4.W))
digit := io.digits(digitSel)
Related
When I wrote this :
class MullerC(val WIDTH: Int = 2) extends Module {
val io = IO(new Bundle {
val in = Input(Vec(WIDTH, Bool()))
val out = Output(Bool())
})
io.out := false.B
when (io.in.reduce(_ & _)) {
io.out := true.B
}.elsewhen (io.in.map(!_).reduce(_ & _)) {
io.out := false.B
}
}
I got Verilog like this :
module MullerC(
input clock,
input reset,
input io_in_0,
input io_in_1,
output io_out
);
assign io_out = io_in_0 & io_in_1;
endmodule
That is a simple and gate instead of a C gate.
But when I tried to add otherwise like this :
class MullerC(val WIDTH: Int = 2) extends Module {
val io = IO(new Bundle {
val in = Input(Vec(WIDTH, Bool()))
val out = Output(Bool())
})
io.out := false.B
when (io.in.reduce(_ & _)) {
io.out := true.B
}.elsewhen (io.in.map(!_).reduce(_ & _)) {
io.out := false.B
}.otherwise {
io.out := io.out
}
}
It could not be compiled any more:
Exception in thread "main" firrtl.transforms.CheckCombLoops$CombLoopException: : [module MullerC] Combinational loop detected:
MullerC.io_out
MullerC._GEN_0 #[----.scala 14:38 ----.scala 15:12 ----.scala 17:12]
MullerC._GEN_1 #[----.scala 12:30 ----.scala 13:12]
MullerC.io_out
How should I implement the Muller C in Chisel? Many thanks.
I found the answer via this link: Disable FIRRTL pass that checks for combinational loops
I should use otherwise and then add --no-check-comb-loops as a parameter to emit verilog code. Thanks.
By the way, I also tried this and it works as well.
class MullerC(val WIDTH: Int = 2) extends Module {
val io = IO(new Bundle {
val in = Input(Vec(WIDTH, Bool()))
val out = Output(Bool())
})
io.out := false.B
val allTrue = Wire(Bool())
val allFalse = Wire(Bool())
allTrue := io.in.reduce(_ & _);
allFalse := io.in.map(!_).reduce(_ & _)
io.out := Mux(allTrue | allFalse, Mux(allTrue, true.B, false.B), io.out)
}
This will generate more beautiful verilog code althought it does not matter.
First of all, I implemented adder which is shown below.
class AdderSwitch(InputBandwidth: Int, OutputBandwidth: Int, NumberOfOutputBuffer: Int) extends Module {
val io = IO(new Bundle {
val InputLeft = Input(SInt(InputBandwidth.W))
val InputRight = Input(SInt(InputBandwidth.W))
val OutputLeft = Output(SInt(InputBandwidth.W))
val OutputSum = Output(SInt(OutputBandwidth.W))
val OutputRight = Output(SInt(InputBandwidth.W))
val PassingOrSum = Input(Bool())
val OutputLeftReady = Input(Bool())
val OutputSumReady = Input(Bool())
val OutputRightReady = Input(Bool())
})
val Demux0 = Module(new Demux(InputBandwidth = InputBandwidth))
Demux0.io.Sel := io.PassingOrSum
Demux0.io.DemuxInput := io.InputLeft
val Demux1 = Module(new Demux(InputBandwidth = InputBandwidth))
Demux1.io.Sel := io.PassingOrSum
Demux1.io.DemuxInput := io.InputRight
val OutputSumWire = Wire(SInt(OutputBandwidth.W))
OutputSumWire := Demux0.io.Output1 + Demux1.io.Output1// + Mux(io.ForwardingMux, io.ForwardRightInput, io.ForwardLeftInput)
val OutputLeftBuffer = Module (new Queue(SInt(), NumberOfOutputBuffer))
val OutputSumBuffer = Module (new Queue(SInt(), NumberOfOutputBuffer))
val OutputRightBuffer = Module (new Queue(SInt(), NumberOfOutputBuffer))
OutputLeftBuffer.io.enq.bits := Mux(io.PassingOrSum, OutputSumWire, Demux0.io.Output0)
OutputLeftBuffer.io.enq.valid := true.B
OutputSumBuffer.io.enq.bits := OutputSumWire
OutputSumBuffer.io.enq.valid := true.B
OutputRightBuffer.io.enq.bits := Mux(io.PassingOrSum, OutputSumWire, Demux1.io.Output0)
OutputRightBuffer.io.enq.valid := true.B
io.OutputLeft := OutputLeftBuffer.io.deq.bits
io.OutputSum := OutputSumBuffer.io.deq.bits
io.OutputRight := OutputRightBuffer.io.deq.bits
OutputLeftBuffer.io.deq.ready := io.OutputLeftReady
OutputSumBuffer.io.deq.ready := io.OutputSumReady
OutputRightBuffer.io.deq.ready := io.OutputRightReady
}
I checked my code works well when it is tested.
I want to make adder tree which looks like below with chisel 3.
I was trying to use my adder code as a node of this tree.
So, I decided to use scala library, scala.immutable.collection.
However, there are so many object and class. And, I am very new to this definition.
To implement scala tree data structure for my chisel code, what do I have to do first?
I'm trying to implement a Carry Select Adder using Chisel in Scala. However after various efforts i keep getting errors. The ripple carry adder and multiplexers are tested and working. This is my current Version. Any Input is greatly appreciated!
class CarrySelectAdder(val n:Int, val m:Int) extends Module {
val io = IO(new Bundle {
val a = Input(UInt(n.W))
val b = Input(UInt(n.W))
val cin = Input(UInt(1.W))
val sum = Output(UInt((n+1).W))
})
object carryselecthelper{ //not used atm
def n_sum_idx(stage:UInt) : UInt = {
return stage * (stage + 1.U) / 2.U;
}
}
//val test = math.ceil(n/m)
val rcas = Array.fill(2 * (n/m)){Module(new RcaAdder(m)).io} //2*math.ceil(n/m)
val muxs = Array.fill(n/m){Module(new Multiplexer(m+1)).io} //math.ceil(n/m)
val Sum = Wire(Vec(n, Bool()))
for (i <- 0 until n) {
rcas(i*2).a := io.a.apply(i*m+m,i*m)
rcas(i*2).b := io.b.apply(i*m+m,i*m)
rcas(i*2).cin := 0.asUInt
rcas(2*i+1).a := io.a.apply(i*m+m,i*m)
rcas(2*i+1).b := io.b.apply(i*m+m,i*m)
rcas(2*i+1).cin := 1.asUInt
muxs(i).a := rcas(i*2).sum
muxs(i).b := rcas(2*i+1).sum
if(i > 0){
muxs(i).sel := io.cin
}
if(i > 0){
if(muxs(i).sel == 0){
muxs(i).sel := rcas(2*i).cout
}else{
muxs(i).sel := rcas(2*i+1).cout
}
}
Sum(i) := muxs(i).out
}
io.sum := Sum.asUInt
}
Currently I'm getting an Exception in "ChiselGeneratorAnnotation":
l3.internal.ChiselException: Exception thrown when elaborating ChiselGeneratorAnnotation
at chisel3.stage.ChiselGeneratorAnnotation.elaborate(ChiselAnnotations.scala:55)
ChiselAnnotations.scala:55
at chisel3.stage.phases.Elaborate.$anonfun$transform$1(Elaborate.scala:19)
Elaborate.scala:19
at scala.collection.TraversableLike.$anonfun$flatMap$1(TraversableLike.scala:245)
TraversableLike.scala:245
at scala.collection.immutable.List.foreach(List.scala:392)
List.scala:392
at scala.collection.TraversableLike.flatMap(TraversableLike.scala:245)
TraversableLike.scala:245
at scala.collection.TraversableLike.flatMap$(TraversableLike.scala:242)
TraversableLike.scala:242
at scala.collection.immutable.List.flatMap(List.scala:355)
List.scala:355
at chisel3.stage.phases.Elaborate.transform(Elaborate.scala:18)
Elaborate.scala:18
at chisel3.iotesters.setupTreadleBackend$.apply(TreadleBackend.scala:143)
TreadleBackend.scala:143
at chisel3.iotesters.Driver$.$anonfun$execute$2(Driver.scala:53)
Driver.scala:53
at scala.runtime.java8.JFunction0$mcZ$sp.apply(JFunction0$mcZ$sp.java:23)
at logger.Logger$.$anonfun$makeScope$2(Logger.scala:168)
Logger.scala:168
at scala.util.DynamicVariable.withValue(DynamicVariable.scala:62)
DynamicVariable.scala:62
at logger.Logger$.makeScope(Logger.scala:166)
Logger.scala:166
at logger.Logger$.makeScope(Logger.scala:127)
Logger.scala:127
at chisel3.iotesters.Driver$.$anonfun$execute$1(Driver.scala:38)
Driver.scala:38
at scala.runtime.java8.JFunction0$mcZ$sp.apply(JFunction0$mcZ$sp.java:23)
at scala.util.DynamicVariable.withValue(DynamicVariable.scala:62)
DynamicVariable.scala:62
at chisel3.iotesters.Driver$.execute(Driver.scala:38)
Driver.scala:38
Upon request I added the Multiplexer and RCA class, they should work fine, since they ran all tests without issues. Thanks!
class Multiplexer(val n:Int) extends Module {
val io = IO(new Bundle {
val a = Input(UInt(n.W))
val b = Input(UInt(n.W))
val sel = Input(UInt(n.W))
val out = Output(UInt(n.W))
})
io.out := (io.sel & io.a) | (~io.sel & io.b)
}
class RcaAdder(val n:Int) extends Module {
val io = IO(new Bundle {
val a = Input(UInt(n.W))
val b = Input(UInt(n.W))
val cin = Input(UInt(1.W))
val sum = Output(UInt(n.W))
val cout = Output(UInt(1.W))
})
val FAs = Array.fill(n){Module(new FullAdder()).io}
val carry = Wire(Vec(n+1, UInt(1.W)))
val sum = Wire(Vec(n, Bool()))
carry(0) := io.cin
for (i <- 0 until n) {
FAs(i).a := io.a(i)
FAs(i).b := io.b(i)
FAs(i).cin := carry(i)
carry(i+1) := FAs(i).cout
sum(i) := FAs(i).sum.asBool
}
io.sum := sum.asUInt
io.cout := carry(n)
}
(This is what is used to test the code.)
class CarrySelectAdderTester(dut: CarrySelectAdder, n: Int) extends PeekPokeTester(dut) {
val max=scala.math.pow(2,n).toInt-1
for(i <- 0 to max){
for (j <- 0 to max){
for (k <- 0 to 1){
poke(dut.io.a,i)
poke(dut.io.b,j)
poke(dut.io.cin,k)
step(100)
expect(dut.io.sum,(i+j+k))
}
}
}
}
object CarrySelectAdderTester extends App{
val bitWidth=6
val bitsperblock=3
println("Testing the Carry Select Adder")
iotesters.Driver.execute(Array[String](), () => new CarrySelectAdder(bitWidth, bitsperblock)){
c => new CarrySelectAdderTester(c,bitWidth)
}
}
Hi I am using the following code to fetch various things from DynamoDB using Scala.
I am stuck at fetching the table description.
I get the following error when I build my project:
constructor DescribeTableRequest in class DescribeTableRequest cannot be accessed in class dynDBMetadata
val tableDescription = ddbClient.describeTable(new DescribeTableRequest("Music"))
package dynDBFetchAPIs
import software.amazon.awssdk.auth.credentials.{AwsBasicCredentials, StaticCredentialsProvider}
import software.amazon.awssdk.http.apache.ApacheHttpClient
import software.amazon.awssdk.regions.Region
import software.amazon.awssdk.services.dynamodb.DynamoDbClient
import software.amazon.awssdk.services.dynamodb.model.DescribeTableRequest
class dynDBMetadata {
def dynDBMetadataInit(): Unit = {
regionDetails()
}
def regionDetails(): Unit = {
val ddbClient = getDynDBClient()
val region = Region.US_EAST_1
var tableCount: Int = 0
var tableSize: Map[String, Int] = null
var regionSize: Int = 0
val tableList = ddbClient.listTables().tableNames()
val tableIterator = tableList.iterator()
while (tableIterator.hasNext) {
tableCount = tableCount + 1
tableIterator.next()
}
val descTabReq = new DescribeTableRequest("Music")
val tableDescription = ddbClient.describeTable(descTabReq)
println(tableDescription)
println("Region of AWS DynamoDB: " + region)
println("List of DynamoDB Tables: " + tableList)
println("Count of DynamoDB Tables: " + tableCount)
}
private def getDynDBClient(): DynamoDbClient = {
var awsBasicCredentials: AwsBasicCredentials = null
var dynamoDbClient: DynamoDbClient = null
try {
val accessKey = "****************************"
val secretKey = "****************************"
awsBasicCredentials = AwsBasicCredentials.create(accessKey, secretKey)
dynamoDbClient = DynamoDbClient.builder()
.region(Region.US_EAST_1)
.credentialsProvider(StaticCredentialsProvider.create(awsBasicCredentials))
.httpClient(ApacheHttpClient.builder().build())
.build();
} catch {
case e: Exception => {
e.printStackTrace()
}
}
dynamoDbClient
}
}
Why is the given constructor not accessible when I use Scala?
contents of build.sbt
name := "dynamodb"
version := "0.1"
scalaVersion := "2.11.12"
scalacOptions := Seq("-target:jvm-1.8")
libraryDependencies ++= Seq(
"software.amazon.awssdk" % "dynamodb" % "2.15.1"
)
I believe that happends because class software.amazon.awssdk.services.dynamodb.model.DescribeTableRequest doesn't have a primary constructor.
You should create with the builder, like this
val tableRequest = DescribeTableRequest.builder
.tableName(tableName)
.build
com.amazonaws.services.dynamodbv2.model.DescribeTableRequest instead, does have a primary constructor. So, maybe you've just included a wrong dependency.
I'm trying to implement a simple Address Decoder with a curried function inside. The code below won't compile, could anybody help me with this?
class AddrDecoder[T<:UInt] (dType:T, n:Int) extends Module {
val io = IO (new Bundle {
//val range = (Vec(Seq.fill(n){(dType,dType)})) // This won't compile, how to fix ?
val range = (List.fill(n){(dType,dType)})
val addr = Input (dType)
val en = Input (Bool())
val sel = Output(Bool())
})
def inside (range:(T,T))(addr:T):Bool = {
addr >= range._1 && addr < range._1 + range._2
}
when (io.en) {
io.sel := io.range map (inside(_)(io.addr))
}
}
[error] found : List[chisel3.Bool]
[error] (which expands to) List[chisel3.core.Bool]
[error] required: chisel3.core.Data
[error] io.sel := io.range map (inside(_)(io.addr))
#jkoenig provided an excellent solution. Posting it here for other's benefit
class AddrDecoder[T<:Data with Num[T]] (dType:T, n:Int) extends Module {
val io = IO (new Bundle {
val range0 = Input (Vec(n,dType))
val range1 = Input (Vec(n,dType))
val addr = Input (dType)
val en = Input (Bool())
val sel = Output(Vec(n,Bool()))
})
// Curried function which accepts a tuple and an input addr
// Use map to apply it to inputs
def inside (range:(T,T))(addr:T):Bool = {
addr >= range._1 && addr < range._1 + range._2
}
// MUX output
for (i <- 0 until n) {
io.sel(i) := false.B
}
when (io.en) {
io.sel := io.range0 zip io.range1 map (inside(_)(io.addr))
}
// $onehot0 output encoding check
assert (PopCount(io.sel) <= 1.U, "Invalid addr decoding")
}