From 922a4c11ada9f230cff0122cb49ddb748f8b5e4d Mon Sep 17 00:00:00 2001 From: Jerry Zhao Date: Thu, 25 May 2023 16:37:36 -0700 Subject: [PATCH] Add tethered chip bringup example --- .../chipyard/src/main/scala/IOBinders.scala | 9 +++ .../src/main/scala/config/ChipConfigs.scala | 56 ++++++++++++++++++- .../src/main/scala/config/NoCoreConfigs.scala | 9 +++ .../config/fragments/ClockingFragments.scala | 8 +++ .../fragments/PeripheralFragments.scala | 18 +++++- .../main/scala/harness/HarnessBinders.scala | 22 +++++++- 6 files changed, 119 insertions(+), 3 deletions(-) diff --git a/generators/chipyard/src/main/scala/IOBinders.scala b/generators/chipyard/src/main/scala/IOBinders.scala index d00067b4..3c8fbeb0 100644 --- a/generators/chipyard/src/main/scala/IOBinders.scala +++ b/generators/chipyard/src/main/scala/IOBinders.scala @@ -303,6 +303,15 @@ class WithSerialTLIOCells extends OverrideIOBinder({ }).getOrElse((Nil, Nil)) }) +class WithSerialTLPunchthrough extends OverrideIOBinder({ + (system: CanHavePeripheryTLSerial) => system.serial_tl.map({ s => + val sys = system.asInstanceOf[BaseSubsystem] + val port = IO(s.getWrappedValue.cloneType) + port <> s.getWrappedValue + (Seq(port), Nil) + }).getOrElse((Nil, Nil)) +}) + class WithAXI4MemPunchthrough extends OverrideLazyIOBinder({ (system: CanHaveMasterAXI4MemPort) => { implicit val p: Parameters = GetSystemParameters(system) diff --git a/generators/chipyard/src/main/scala/config/ChipConfigs.scala b/generators/chipyard/src/main/scala/config/ChipConfigs.scala index e7c8ce9b..10c9be23 100644 --- a/generators/chipyard/src/main/scala/config/ChipConfigs.scala +++ b/generators/chipyard/src/main/scala/config/ChipConfigs.scala @@ -2,7 +2,8 @@ package chipyard import org.chipsalliance.cde.config.{Config} import freechips.rocketchip.diplomacy._ -import freechips.rocketchip.subsystem.{MBUS} +import freechips.rocketchip.subsystem.{MBUS, SBUS} +import testchipip.{OBUS} // A simple config demonstrating how to set up a basic chip in Chipyard class ChipLikeRocketConfig extends Config( @@ -43,3 +44,56 @@ class ChipLikeRocketConfig extends Config( new chipyard.config.AbstractConfig) +// A simple config demonstrating a "bringup prototype" to bringup the ChipLikeRocketconfig +class ChipBringupHostConfig extends Config( + //============================= + // Set up TestHarness for standalone-sim + // These fragments only affect the design when simulated by itself (without the ChipLikeRocketConfig) + //============================= + new chipyard.harness.WithAbsoluteFreqHarnessClockInstantiator ++ + new chipyard.harness.WithSerialTLTiedOff ++ // when doing standalone sim, tie off the serial-tl port + new chipyard.harness.WithSimTSIToUARTTSI ++ + new chipyard.iobinders.WithSerialTLPunchthrough ++ + + //============================= + // Setup the SerialTL side on the bringup device + //============================= + new testchipip.WithSerialTLWidth(4) ++ // match width with the chip + new testchipip.WithSerialTLMem(base = 0x0, size = BigInt(1) << 48, // accessible memory of the chip + idBits = 4, isMainMemory = false) ++ + new testchipip.WithSerialTLClockDirection(provideClockFreqMHz = Some(75)) ++ // bringup board drives the clock for the serial-tl receiver on the chip, use 50MHz clock + + //============================ + // Setup bus topology on the bringup system + //============================ + new testchipip.WithOffchipBusManager(SBUS, + blockRange = AddressSet.misaligned(0x80000000L, (BigInt(1) << 30) * 4), + replicationBase = Some(BigInt(1) << 48)) ++ + new testchipip.WithOffchipBus ++ // offchip bus + + //============================= + // Set up memory on the bringup system + //============================= + new freechips.rocketchip.subsystem.WithExtMemSize((1 << 30) * 4L) ++ // match what the chip believes + + //============================= + // Generate the TSI-over-UART side of the bringup system + //============================= + new testchipip.WithUARTTSIClient(initBaudRate = BigInt(921600)) ++ // nonstandard baud rate to improve performance + + //============================= + // Set up clocks of the bringup system + //============================= + new chipyard.clocking.WithPassthroughClockGenerator ++ // pass all the clocks through, since this isn't a chip + new chipyard.config.WithFrontBusFrequency(75.0) ++ + new chipyard.config.WithMemoryBusFrequency(75.0) ++ + new chipyard.config.WithPeripheryBusFrequency(75.0) ++ + + // Base is the no-cores config + new chipyard.NoCoresConfig) + +class TetheredChipLikeRocketConfig extends Config( + new chipyard.harness.WithAbsoluteFreqHarnessClockInstantiator ++ // use absolute freqs for sims in the harness + new chipyard.harness.WithMultiChipSerialTL(0, 1) ++ + new chipyard.harness.WithMultiChip(0, new ChipLikeRocketConfig) ++ + new chipyard.harness.WithMultiChip(1, new ChipBringupHostConfig)) diff --git a/generators/chipyard/src/main/scala/config/NoCoreConfigs.scala b/generators/chipyard/src/main/scala/config/NoCoreConfigs.scala index 10be8aca..19e9a7e0 100644 --- a/generators/chipyard/src/main/scala/config/NoCoreConfigs.scala +++ b/generators/chipyard/src/main/scala/config/NoCoreConfigs.scala @@ -4,6 +4,15 @@ import org.chipsalliance.cde.config.{Config} // A empty config with no cores. Useful for testing class NoCoresConfig extends Config( + new testchipip.WithNoBootAddrReg ++ + new testchipip.WithNoCustomBootPin ++ + new chipyard.config.WithNoCLINT ++ + new chipyard.config.WithNoBootROM ++ + new chipyard.config.WithBroadcastManager ++ + new chipyard.config.WithNoUART ++ + new chipyard.config.WithNoTileClockGaters ++ + new chipyard.config.WithNoTileResetSetters ++ + new chipyard.config.WithNoBusErrorDevices ++ new chipyard.config.WithNoDebug ++ new chipyard.config.WithNoPLIC ++ new chipyard.config.AbstractConfig) diff --git a/generators/chipyard/src/main/scala/config/fragments/ClockingFragments.scala b/generators/chipyard/src/main/scala/config/fragments/ClockingFragments.scala index 1f7bb943..509b2a73 100644 --- a/generators/chipyard/src/main/scala/config/fragments/ClockingFragments.scala +++ b/generators/chipyard/src/main/scala/config/fragments/ClockingFragments.scala @@ -106,3 +106,11 @@ class WithControlBusFrequency(freqMHz: Double) extends Config((site, here, up) = class WithRationalMemoryBusCrossing extends WithSbusToMbusCrossingType(RationalCrossing(Symmetric)) class WithAsynchrousMemoryBusCrossing extends WithSbusToMbusCrossingType(AsynchronousCrossing()) + +class WithNoTileClockGaters extends Config((site, here, up) => { + case ChipyardPRCIControlKey => up(ChipyardPRCIControlKey).copy(enableTileClockGating = false) +}) + +class WithNoTileResetSetters extends Config((site, here, up) => { + case ChipyardPRCIControlKey => up(ChipyardPRCIControlKey).copy(enableTileResetSetting = false) +}) diff --git a/generators/chipyard/src/main/scala/config/fragments/PeripheralFragments.scala b/generators/chipyard/src/main/scala/config/fragments/PeripheralFragments.scala index 3b607ae0..85606494 100644 --- a/generators/chipyard/src/main/scala/config/fragments/PeripheralFragments.scala +++ b/generators/chipyard/src/main/scala/config/fragments/PeripheralFragments.scala @@ -5,7 +5,7 @@ import chisel3._ import chisel3.util.{log2Up} import org.chipsalliance.cde.config.{Config} -import freechips.rocketchip.devices.tilelink.{BootROMLocated, PLICKey} +import freechips.rocketchip.devices.tilelink.{BootROMLocated, PLICKey, CLINTKey} import freechips.rocketchip.devices.debug.{Debug, ExportDebug, DebugModuleKey, DMI} import freechips.rocketchip.stage.phases.TargetDirKey import freechips.rocketchip.subsystem._ @@ -75,3 +75,19 @@ class WithNoPLIC extends Config((site, here, up) => { class WithDebugModuleAbstractDataWords(words: Int = 16) extends Config((site, here, up) => { case DebugModuleKey => up(DebugModuleKey).map(_.copy(nAbstractDataWords=words)) }) + +class WithNoCLINT extends Config((site, here, up) => { + case CLINTKey => None +}) + +class WithNoBootROM extends Config((site, here, up) => { + case BootROMLocated(_) => None +}) + +class WithNoBusErrorDevices extends Config((site, here, up) => { + case SystemBusKey => up(SystemBusKey).copy(errorDevice = None) + case ControlBusKey => up(ControlBusKey).copy(errorDevice = None) + case PeripheryBusKey => up(PeripheryBusKey).copy(errorDevice = None) + case MemoryBusKey => up(MemoryBusKey).copy(errorDevice = None) + case FrontBusKey => up(FrontBusKey).copy(errorDevice = None) +}) diff --git a/generators/chipyard/src/main/scala/harness/HarnessBinders.scala b/generators/chipyard/src/main/scala/harness/HarnessBinders.scala index db6f0cda..4cb85aba 100644 --- a/generators/chipyard/src/main/scala/harness/HarnessBinders.scala +++ b/generators/chipyard/src/main/scala/harness/HarnessBinders.scala @@ -290,7 +290,9 @@ class WithSerialTLTiedOff extends OverrideHarnessBinder({ implicit val p = chipyard.iobinders.GetSystemParameters(system) ports.map({ port => val bits = port.bits - port.clock := false.B.asClock + if (DataMirror.directionOf(port.clock) == Direction.Input) { + port.clock := false.B.asClock + } port.bits.out.ready := false.B port.bits.in.valid := false.B port.bits.in.bits := DontCare @@ -325,6 +327,24 @@ class WithSimUARTToUARTTSI extends OverrideHarnessBinder({ } }) +class WithSimTSIToUARTTSI extends OverrideHarnessBinder({ + (system: CanHavePeripheryUARTTSI, th: HasHarnessInstantiators, ports: Seq[UARTTSIIO]) => { + implicit val p = chipyard.iobinders.GetSystemParameters(system) + require(ports.size <= 1) + ports.map({ port => + val freq = th.getHarnessBinderClockFreqHz.toInt + val uart_to_serial = Module(new UARTToSerial(freq, port.uartParams)) + val serial_width_adapter = Module(new SerialWidthAdapter(8, TSI.WIDTH)) + val success = SimTSI.connect(Some(TSIIO(serial_width_adapter.io.wide)), th.harnessBinderClock, th.harnessBinderReset) + when (success) { th.success := true.B } + assert(!uart_to_serial.io.dropped) + serial_width_adapter.io.narrow.flipConnect(uart_to_serial.io.serial) + uart_to_serial.io.uart.rxd := port.uart.txd + port.uart.rxd := uart_to_serial.io.uart.txd + }) + } +}) + class WithTraceGenSuccess extends OverrideHarnessBinder({ (system: TraceGenSystemModuleImp, th: HasHarnessInstantiators, ports: Seq[Bool]) => {