Skip to content

Commit 377450a

Browse files
committed
Add option for externally clocked GCD peripheral example
1 parent 5e038eb commit 377450a

File tree

3 files changed

+62
-19
lines changed

3 files changed

+62
-19
lines changed

generators/chipyard/src/main/scala/config/MMIOAcceleratorConfigs.scala

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -32,6 +32,11 @@ class GCDHLSRocketConfig extends Config(
3232
new freechips.rocketchip.rocket.WithNHugeCores(1) ++
3333
new chipyard.config.AbstractConfig)
3434

35+
class GCDExternallyClockedRocketConfig extends Config(
36+
new chipyard.example.WithGCD(externallyClocked=true)++
37+
new freechips.rocketchip.rocket.WithNHugeCores(1) ++
38+
new chipyard.config.AbstractConfig)
39+
3540
// DOC include start: InitZeroRocketConfig
3641
class InitZeroRocketConfig extends Config(
3742
new chipyard.example.WithInitZero(0x88000000L, 0x1000L) ++ // add InitZero

generators/chipyard/src/main/scala/example/GCD.scala

Lines changed: 44 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -12,15 +12,19 @@ import org.chipsalliance.cde.config.{Parameters, Field, Config}
1212
import freechips.rocketchip.diplomacy._
1313
import freechips.rocketchip.regmapper.{HasRegMap, RegField}
1414
import freechips.rocketchip.tilelink._
15-
import freechips.rocketchip.util.UIntIsOneOf
15+
import freechips.rocketchip.util._
1616

1717
// DOC include start: GCD params
1818
case class GCDParams(
1919
address: BigInt = 0x4000,
2020
width: Int = 32,
2121
useAXI4: Boolean = false,
2222
useBlackBox: Boolean = true,
23-
useHLS: Boolean = false)
23+
useHLS: Boolean = false,
24+
externallyClocked: Boolean = false
25+
) {
26+
require(!(useAXI4 && useHLS))
27+
}
2428
// DOC include end: GCD params
2529

2630
// DOC include start: GCD key
@@ -287,13 +291,33 @@ trait CanHavePeripheryGCD { this: BaseSubsystem =>
287291
private val pbus = locateTLBusWrapper(PBUS)
288292

289293
// Only build if we are using the TL (nonAXI4) version
290-
val gcd_busy = p(GCDKey) match {
294+
val (gcd_busy, gcd_clock) = p(GCDKey) match {
291295
case Some(params) => {
296+
297+
val gcd_clock = Option.when(params.externallyClocked) {
298+
InModuleBody { IO(Input(Clock())).suggestName("gcd_clock_in") }
299+
}
300+
val gcdClockNode = if (params.externallyClocked) {
301+
val gcdSourceClockNode = ClockSourceNode(Seq(ClockSourceParameters()))
302+
InModuleBody {
303+
gcdSourceClockNode.out(0)._1.clock := gcd_clock.get
304+
gcdSourceClockNode.out(0)._1.reset := ResetCatchAndSync(gcd_clock.get, pbus.module.reset.asBool)
305+
}
306+
gcdSourceClockNode
307+
} else {
308+
pbus.fixedClockNode
309+
}
310+
val gcdCrossing = if (params.externallyClocked) {
311+
AsynchronousCrossing()
312+
} else {
313+
SynchronousCrossing()
314+
}
315+
292316
val gcd = if (params.useAXI4) {
293317
val gcd = LazyModule(new GCDAXI4(params, pbus.beatBytes)(p))
294-
gcd.clockNode := pbus.fixedClockNode
318+
gcd.clockNode := gcdClockNode
295319
pbus.coupleTo(portName) {
296-
gcd.node :=
320+
AXI4InwardClockCrossingHelper("gcd_crossing", gcd, gcd.node)(gcdCrossing) :=
297321
AXI4Buffer () :=
298322
TLToAXI4 () :=
299323
// toVariableWidthSlave doesn't use holdFirstDeny, which TLToAXI4() needsx
@@ -302,33 +326,39 @@ trait CanHavePeripheryGCD { this: BaseSubsystem =>
302326
gcd
303327
} else if (params.useHLS) {
304328
val gcd = LazyModule(new HLSGCDAccel(params, pbus.beatBytes)(p))
305-
gcd.clockNode := pbus.fixedClockNode
306-
pbus.coupleTo(portName) { gcd.node := TLFragmenter(pbus.beatBytes, pbus.blockBytes) := _ }
329+
gcd.clockNode := gcdClockNode
330+
pbus.coupleTo(portName) {
331+
TLInwardClockCrossingHelper("gcd_crossing", gcd, gcd.node)(gcdCrossing) :=
332+
TLFragmenter(pbus.beatBytes, pbus.blockBytes) := _
333+
}
307334
gcd
308335
} else {
309336
val gcd = LazyModule(new GCDTL(params, pbus.beatBytes)(p))
310-
gcd.clockNode := pbus.fixedClockNode
311-
pbus.coupleTo(portName) { gcd.node := TLFragmenter(pbus.beatBytes, pbus.blockBytes) := _ }
337+
gcd.clockNode := gcdClockNode
338+
pbus.coupleTo(portName) {
339+
TLInwardClockCrossingHelper("gcd_crossing", gcd, gcd.node)(gcdCrossing) :=
340+
TLFragmenter(pbus.beatBytes, pbus.blockBytes) := _
341+
}
312342
gcd
313343
}
314344
val gcd_busy = InModuleBody {
315345
val busy = IO(Output(Bool())).suggestName("gcd_busy")
316346
busy := gcd.module.io.gcd_busy
317347
busy
318348
}
319-
Some(gcd_busy)
349+
(Some(gcd_busy), gcd_clock)
320350
}
321-
case None => None
351+
case None => (None, None)
322352
}
323353
}
324354
// DOC include end: GCD lazy trait
325355

326356
// DOC include start: GCD config fragment
327-
class WithGCD(useAXI4: Boolean = false, useBlackBox: Boolean = false, useHLS: Boolean = false) extends Config((site, here, up) => {
357+
class WithGCD(useAXI4: Boolean = false, useBlackBox: Boolean = false, useHLS: Boolean = false, externallyClocked: Boolean = false) extends Config((site, here, up) => {
328358
case GCDKey => {
329359
// useHLS cannot be used with useAXI4 and useBlackBox
330-
assert(!useHLS || (useHLS && !useAXI4 && !useBlackBox))
331-
Some(GCDParams(useAXI4 = useAXI4, useBlackBox = useBlackBox, useHLS = useHLS))
360+
assert(!useHLS || (useHLS && !useAXI4 && !useBlackBox))
361+
Some(GCDParams(useAXI4 = useAXI4, useBlackBox = useBlackBox, useHLS = useHLS, externallyClocked = externallyClocked))
332362
}
333363
})
334364
// DOC include end: GCD config fragment

generators/chipyard/src/main/scala/iobinders/IOBinders.scala

Lines changed: 13 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -561,11 +561,19 @@ class WithNMITiedOff extends ComposeIOBinder({
561561
})
562562

563563
class WithGCDBusyPunchthrough extends OverrideIOBinder({
564-
(system: CanHavePeripheryGCD) => system.gcd_busy.map { busy =>
565-
val io_gcd_busy = IO(Output(Bool()))
566-
io_gcd_busy := busy
567-
(Seq(GCDBusyPort(() => io_gcd_busy)), Nil)
568-
}.getOrElse((Nil, Nil))
564+
(system: CanHavePeripheryGCD) => {
565+
val gcdBusyPort = system.gcd_busy.map { busy =>
566+
val io_gcd_busy = IO(Output(Bool()))
567+
io_gcd_busy := busy
568+
GCDBusyPort(() => io_gcd_busy)
569+
}.toSeq
570+
val gcdClockPort = system.gcd_clock.map { clock =>
571+
val io_gcd_clock = IO(Input(Clock()))
572+
clock := io_gcd_clock
573+
ClockPort(() => io_gcd_clock, freqMHz = 60.0) // freqMHz used in sims
574+
}.toSeq
575+
(gcdBusyPort ++ gcdClockPort, Nil)
576+
}
569577
})
570578

571579
class WithOffchipBusSel extends OverrideIOBinder({

0 commit comments

Comments
 (0)