Compare commits
	
		
			14 Commits
		
	
	
		
			master
			...
			589e9960c0
		
	
	| Author | SHA1 | Date | |
|---|---|---|---|
| 589e9960c0 | |||
| 2707fa59a4 | |||
| 3797385a8c | |||
| 79b53cf2ae | |||
| 5bcc4e82fd | |||
| 9c06418352 | |||
| b2b19cc822 | |||
| 5db71d11c2 | |||
| f4ae1d469f | |||
| 0b421d5645 | |||
| 8329b232e2 | |||
| 2ff28e6af6 | |||
| 41362a1cb5 | |||
| e9625bf8ee | 
| @@ -0,0 +1,147 @@ | |||||||
|  | // See LICENSE.SiFive for license details. | ||||||
|  |  | ||||||
|  | package sifive.fpgashells.devices.xilinx.xilinxml507mig | ||||||
|  |  | ||||||
|  | import Chisel._ | ||||||
|  | import chisel3.core.{Input, Output} | ||||||
|  | import freechips.rocketchip.config.Parameters | ||||||
|  | import freechips.rocketchip.diplomacy._ | ||||||
|  | import freechips.rocketchip.subsystem.{AsynchronousCrossing, HasCrossing} | ||||||
|  | import freechips.rocketchip.tilelink._ | ||||||
|  | import freechips.rocketchip.util._ | ||||||
|  |  | ||||||
|  | case class XilinxML507MIGParams( | ||||||
|  |     address: Seq[AddressSet] | ||||||
|  | ) | ||||||
|  |  | ||||||
|  | class MemoryController extends BlackBox { | ||||||
|  |     val io = IO(new Bundle { | ||||||
|  |         val sys = new MemorySysIO | ||||||
|  |         val ddr2 = new MemoryDDR2IO | ||||||
|  |  | ||||||
|  |         val request_addr = Input(UInt(28.W)) | ||||||
|  |         val request_read = Input(Bool()) | ||||||
|  |         val request_data = Input(UInt(256.W)) | ||||||
|  |         val request_mask = Input(UInt(32.W)) | ||||||
|  |         val request_valid = Input(Bool()) | ||||||
|  |         val request_ready = Output(Bool()) | ||||||
|  |  | ||||||
|  |         val response_data = Output(UInt(256.W)) | ||||||
|  |         val response_valid = Output(Bool()) | ||||||
|  |         // no ready, as the mig does not wait | ||||||
|  |     }) | ||||||
|  |  | ||||||
|  |     override def desiredName: String = "memory_controller" | ||||||
|  | } | ||||||
|  |  | ||||||
|  | class XilinxML507MIGToTL(c: XilinxML507MIGParams)(implicit p: Parameters) extends LazyModule with HasCrossing { | ||||||
|  |     // Corresponds to MIG interface with 64 bit width and a burst length of 4 | ||||||
|  |     val width = 256 | ||||||
|  |     val beatBytes = width/8 // 32 byte (half a cache-line, fragmented) | ||||||
|  |     val crossing = AsynchronousCrossing(8) | ||||||
|  |  | ||||||
|  |     val device = new MemoryDevice | ||||||
|  |     val node = TLManagerNode( | ||||||
|  |         Seq(TLManagerPortParameters( | ||||||
|  |             Seq(TLManagerParameters( | ||||||
|  |                 address         = c.address, | ||||||
|  |                 resources       = device.reg, | ||||||
|  |                 regionType      = RegionType.UNCACHED, | ||||||
|  |                 executable      = true, | ||||||
|  |                 supportsGet     = TransferSizes(1, beatBytes), | ||||||
|  |                 supportsPutFull = TransferSizes(1, beatBytes), | ||||||
|  |                 fifoId          = Some(0) // in-order | ||||||
|  |             )), | ||||||
|  |             beatBytes = beatBytes | ||||||
|  |         )) | ||||||
|  |     ) | ||||||
|  |     // We could possibly also support supportsPutPartial, as we need support | ||||||
|  |     // for masks anyway because of the possibility of transfers smaller that | ||||||
|  |     // the data width (size signal, see below). | ||||||
|  |  | ||||||
|  |     lazy val module = new LazyModuleImp(this) { | ||||||
|  |         val io = IO(new Bundle { | ||||||
|  |             val port_sys = new MemorySysIO | ||||||
|  |             val port_ddr2 = new MemoryDDR2IO | ||||||
|  |         }) | ||||||
|  |  | ||||||
|  |         val controller = Module(new MemoryController) | ||||||
|  |         io.port_sys <> controller.io.sys | ||||||
|  |         io.port_ddr2 <> controller.io.ddr2 | ||||||
|  |  | ||||||
|  |         // in: TLBundle, edge: TLEdgeIn | ||||||
|  |         val (in, edge) = node.in(0) | ||||||
|  |  | ||||||
|  |         // Due to the Fragmenter defined above, all messages are 32 bytes or | ||||||
|  |         // smaller. The data signal of the TL channels is also 32 bytes, so | ||||||
|  |         // all messages will be transfered in a single beat. | ||||||
|  |         // Also, TL guarantees (see TL$4.6) that the payload of a data message | ||||||
|  |         // is always aligned to the width of the beat, e.g. in case of a 32 | ||||||
|  |         // byte data signal, data[7:0] will always have address 0x***00000 and | ||||||
|  |         // data[255:247] address 0x***11111. It is also guaranteed that the | ||||||
|  |         // mask bits always correctly reflect the active bytes inside the beat | ||||||
|  |         // with respect to the size and address. | ||||||
|  |         // So we can directly forward the mask, (relative) address and possibly | ||||||
|  |         // data to the MIG interface. | ||||||
|  |         // Put requests can be acknowledged as soon as they are latched into | ||||||
|  |         // the write fifo of the MIG (possibly combinatorily). | ||||||
|  |         // For read requests, we have to store the source id and size in a | ||||||
|  |         // queue for later acknowledgment. | ||||||
|  |         // We are ready if both the MIG and the response data queue are not | ||||||
|  |         // full. | ||||||
|  |  | ||||||
|  |         // Widths of the A channel: | ||||||
|  |         // addressBits: 32 | ||||||
|  |         // dataBits:    256 | ||||||
|  |         // sourceBits:  6 | ||||||
|  |         // sinkBits:    1 | ||||||
|  |         // sizeBits:    3 | ||||||
|  |  | ||||||
|  |         // source (from): in.a.bits.source | ||||||
|  |         // adresse (to): edgeIn.address(in.a.bits) | ||||||
|  |         // size: edgeIn.size(in.a.bits) | ||||||
|  |         // isPut: edgeIn.hasData(in.a.bits) | ||||||
|  |  | ||||||
|  |         // bits kommt von Decoupled: ready, valid + bits | ||||||
|  |  | ||||||
|  |         println("a parameters: " + in.a.bits.params) | ||||||
|  |  | ||||||
|  |         in.a.ready := Bool(false) | ||||||
|  |         in.d.valid := Bool(false) | ||||||
|  |  | ||||||
|  |         // Tie off unused channels | ||||||
|  |         in.b.valid := Bool(false) | ||||||
|  |         in.c.ready := Bool(true) | ||||||
|  |         in.e.ready := Bool(true) | ||||||
|  |     } | ||||||
|  | } | ||||||
|  |  | ||||||
|  | class XilinxML507MIG(c : XilinxML507MIGParams)(implicit p: Parameters) extends LazyModule { | ||||||
|  |     // The Fragmenter will not fragment messages <= 32 bytes, so all | ||||||
|  |     // slaves have to support this size. 64 byte specifies the maximum | ||||||
|  |     // supported transfer size that the slave side of the fragmenter supports | ||||||
|  |     // against the master (here the main memory bus). Specifying alwaysMin as | ||||||
|  |     // true results in all messages being fragmented to the minimal size | ||||||
|  |     // (32 byte). In TL1 terms, slaves correspond roughly to managers and | ||||||
|  |     // masters to clients (confusingly…). | ||||||
|  |     val fragmenter = LazyModule(new TLFragmenter(32, 64, alwaysMin=true)) | ||||||
|  |     val island = LazyModule(new XilinxML507MIGToTL(c)) | ||||||
|  |  | ||||||
|  |     val node: TLInwardNode = | ||||||
|  |         island.node := island.crossTLIn := fragmenter.node | ||||||
|  |  | ||||||
|  |     lazy val module = new LazyModuleImp(this) { | ||||||
|  |         val io = IO(new Bundle { | ||||||
|  |             val port_sys = new MemorySysIO | ||||||
|  |             val port_ddr2 = new MemoryDDR2IO | ||||||
|  |         }) | ||||||
|  |  | ||||||
|  |         io.port_sys <> island.module.io.port_sys | ||||||
|  |         io.port_ddr2 <> island.module.io.port_ddr2 | ||||||
|  |  | ||||||
|  |         // The MIGToTL module lives in a separate clock domain together with | ||||||
|  |         // the MIG, which is why it is called "island". | ||||||
|  |         island.module.clock := io.port_sys.clk0 | ||||||
|  |         island.module.reset := io.port_sys.reset | ||||||
|  |     } | ||||||
|  | } | ||||||
| @@ -0,0 +1,58 @@ | |||||||
|  | // See LICENSE.SiFive for license details. | ||||||
|  |  | ||||||
|  | package sifive.fpgashells.devices.xilinx.xilinxml507mig | ||||||
|  |  | ||||||
|  | import Chisel._ | ||||||
|  | import chisel3.core.{Input, Output} | ||||||
|  | import chisel3.experimental.Analog | ||||||
|  | import freechips.rocketchip.config.Field | ||||||
|  | import freechips.rocketchip.diplomacy._ | ||||||
|  | import freechips.rocketchip.subsystem.BaseSubsystem | ||||||
|  |  | ||||||
|  | case object MemoryML507Key extends Field[XilinxML507MIGParams] | ||||||
|  |  | ||||||
|  | trait HasMemoryML507 { this: BaseSubsystem => | ||||||
|  |     val memory = LazyModule(new XilinxML507MIG(p(MemoryML507Key))) | ||||||
|  |  | ||||||
|  |     memory.node := memBuses.head.toDRAMController(Some("xilinxml507mig"))() | ||||||
|  | } | ||||||
|  |  | ||||||
|  | class MemorySysIO extends Bundle { | ||||||
|  |     val clk0 = Input(Clock()) | ||||||
|  |     val clk90 = Input(Clock()) | ||||||
|  |     val clkdiv0 = Input(Clock()) | ||||||
|  |     val clk_locked = Input(Bool()) | ||||||
|  |     val clk_idelay = Input(Clock()) | ||||||
|  |     val reset = Input(Bool()) | ||||||
|  | } | ||||||
|  |  | ||||||
|  | class MemoryDDR2IO extends Bundle { | ||||||
|  |     val dq = Analog(64.W) | ||||||
|  |     val a = Output(Bits(13.W)) | ||||||
|  |     val ba = Output(Bits(2.W)) | ||||||
|  |     val ras_n = Output(Bits(1.W)) | ||||||
|  |     val cas_n = Output(Bits(1.W)) | ||||||
|  |     val we_n = Output(Bits(1.W)) | ||||||
|  |     val cs_n = Output(Bits(1.W)) | ||||||
|  |     val odt = Output(Bits(1.W)) | ||||||
|  |     val cke = Output(Bits(1.W)) | ||||||
|  |     val dm = Output(Bits(8.W)) | ||||||
|  |     val dqs = Analog(8.W) | ||||||
|  |     val dqs_n = Analog(8.W) | ||||||
|  |     val ck = Output(Bits(2.W)) | ||||||
|  |     val ck_n = Output(Bits(2.W)) | ||||||
|  | } | ||||||
|  |  | ||||||
|  | trait HasMemoryML507Bundle { | ||||||
|  |     val ddr_sys: MemorySysIO | ||||||
|  |     val ddr2: MemoryDDR2IO | ||||||
|  | } | ||||||
|  |  | ||||||
|  | trait HasMemoryML507ModuleImp extends LazyModuleImp with HasMemoryML507Bundle { | ||||||
|  |     val outer: HasMemoryML507 | ||||||
|  |     val ddr_sys = IO(new MemorySysIO) | ||||||
|  |     val ddr2 = IO(new MemoryDDR2IO) | ||||||
|  |  | ||||||
|  |     ddr_sys <> outer.memory.module.io.port_sys | ||||||
|  |     ddr2 <> outer.memory.module.io.port_ddr2 | ||||||
|  | } | ||||||
| @@ -94,6 +94,26 @@ object PowerOnResetFPGAOnly { | |||||||
|   } |   } | ||||||
| } | } | ||||||
|  |  | ||||||
|  | //------------------------------------------------------------------------- | ||||||
|  | // ml507 clocks (DCM_ADV) | ||||||
|  | //------------------------------------------------------------------------- | ||||||
|  |  | ||||||
|  | class ml507_sys_clock extends BlackBox { | ||||||
|  |   val io = new Bundle { | ||||||
|  |     val CLKIN_IN  = Clock(INPUT) | ||||||
|  |     val CLKFX_OUT = Clock(OUTPUT) | ||||||
|  |     val LOCKED_OUT = Bool(OUTPUT) | ||||||
|  |   } | ||||||
|  | } | ||||||
|  |  | ||||||
|  | class ml507_dvi_clock extends BlackBox { | ||||||
|  |   val io = new Bundle { | ||||||
|  |     val CLKIN_IN  = Clock(INPUT) | ||||||
|  |     val CLKFX_OUT = Clock(OUTPUT) | ||||||
|  |     val LOCKED_OUT = Bool(OUTPUT) | ||||||
|  |   } | ||||||
|  | } | ||||||
|  |  | ||||||
| //------------------------------------------------------------------------- | //------------------------------------------------------------------------- | ||||||
| // vc707_sys_clock_mmcm | // vc707_sys_clock_mmcm | ||||||
| //------------------------------------------------------------------------- | //------------------------------------------------------------------------- | ||||||
|   | |||||||
							
								
								
									
										221
									
								
								src/main/scala/shell/xilinx/ML507Shell.scala
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										221
									
								
								src/main/scala/shell/xilinx/ML507Shell.scala
									
									
									
									
									
										Normal file
									
								
							| @@ -0,0 +1,221 @@ | |||||||
|  | // See LICENSE for license details. | ||||||
|  | package sifive.fpgashells.shell.xilinx.ml507shell | ||||||
|  |  | ||||||
|  | import Chisel._ | ||||||
|  | import chisel3.core.{Input, Output, attach} | ||||||
|  | import chisel3.experimental.{RawModule, Analog, withClockAndReset} | ||||||
|  |  | ||||||
|  | import freechips.rocketchip.config._ | ||||||
|  | import freechips.rocketchip.devices.debug._ | ||||||
|  | import freechips.rocketchip.util.{SyncResetSynchronizerShiftReg, ElaborationArtefacts, HeterogeneousBag} | ||||||
|  |  | ||||||
|  | import sifive.blocks.devices.gpio._ | ||||||
|  | import sifive.blocks.devices.spi._ | ||||||
|  | import sifive.blocks.devices.uart._ | ||||||
|  | import sifive.blocks.devices.chiplink._ | ||||||
|  | import sifive.blocks.devices.terminal._ | ||||||
|  |  | ||||||
|  | import sifive.fpgashells.devices.xilinx.xilinxml507mig._ | ||||||
|  | import sifive.fpgashells.ip.xilinx.{PowerOnResetFPGAOnly, sdio_spi_bridge, ml507_dvi_clock, ml507_sys_clock, vc707reset} | ||||||
|  |  | ||||||
|  | //------------------------------------------------------------------------- | ||||||
|  | // ML507Shell | ||||||
|  | //------------------------------------------------------------------------- | ||||||
|  |  | ||||||
|  | // TODO: trait HasDDR2 { … } | ||||||
|  |  | ||||||
|  | trait HasDebugJTAG { this: ML507Shell => | ||||||
|  |   // JTAG | ||||||
|  |   val jtag_TCK             = IO(Input(Clock())) | ||||||
|  |   val jtag_TMS             = IO(Input(Bool())) | ||||||
|  |   val jtag_TDI             = IO(Input(Bool())) | ||||||
|  |   val jtag_TDO             = IO(Output(Bool())) | ||||||
|  |  | ||||||
|  |   def connectDebugJTAG(dut: HasPeripheryDebugModuleImp, fmcxm105: Boolean = true): SystemJTAGIO = { | ||||||
|  |     val djtag     = dut.debug.systemjtag.get | ||||||
|  |  | ||||||
|  |     djtag.jtag.TCK := jtag_TCK | ||||||
|  |     djtag.jtag.TMS := jtag_TMS | ||||||
|  |     djtag.jtag.TDI := jtag_TDI | ||||||
|  |     jtag_TDO       := djtag.jtag.TDO.data | ||||||
|  |  | ||||||
|  |     djtag.mfr_id   := p(JtagDTMKey).idcodeManufId.U(11.W) | ||||||
|  |  | ||||||
|  |     djtag.reset    := PowerOnResetFPGAOnly(dut_clock) | ||||||
|  |     dut_ndreset    := dut.debug.ndreset | ||||||
|  |     djtag | ||||||
|  |   } | ||||||
|  | } | ||||||
|  |  | ||||||
|  |  | ||||||
|  | abstract class ML507Shell(implicit val p: Parameters) extends RawModule { | ||||||
|  |  | ||||||
|  |   //----------------------------------------------------------------------- | ||||||
|  |   // Interface | ||||||
|  |   //----------------------------------------------------------------------- | ||||||
|  |  | ||||||
|  |   // 100Mhz sysclk | ||||||
|  |   val sys_clock            = IO(Input(Clock())) | ||||||
|  |  | ||||||
|  |   // active high async reset | ||||||
|  |   val reset                = IO(Input(Bool())) | ||||||
|  |  | ||||||
|  |   // LED | ||||||
|  |   val led                  = IO(Output(Vec(8, Bool()))) | ||||||
|  |  | ||||||
|  |   // DIP switches | ||||||
|  |   val dip                  = IO(Input(Vec(8, Bool()))) | ||||||
|  |  | ||||||
|  |   // UART | ||||||
|  |   val uart_tx              = IO(Output(Bool())) | ||||||
|  |   val uart_rx              = IO(Input(Bool())) | ||||||
|  |  | ||||||
|  |   // SDIO | ||||||
|  |   val sdio_clk             = IO(Output(Bool())) | ||||||
|  |   val sdio_cmd             = IO(Analog(1.W)) | ||||||
|  |   val sdio_dat             = IO(Analog(4.W)) | ||||||
|  |  | ||||||
|  |   // Feedback | ||||||
|  |   val clock_led            = IO(Output(Clock())) | ||||||
|  |   val reset_led            = IO(Output(Bool())) | ||||||
|  |  | ||||||
|  |   val dvi                  = IO(new TerminalDVIIO) | ||||||
|  |   val ddr2                 = IO(new MemoryDDR2IO) | ||||||
|  |  | ||||||
|  |   //----------------------------------------------------------------------- | ||||||
|  |   // Wire declrations | ||||||
|  |   //----------------------------------------------------------------------- | ||||||
|  |  | ||||||
|  |   // async resets | ||||||
|  |   val sys_reset       = Wire(Bool()) | ||||||
|  |   val do_reset        = Wire(Bool()) | ||||||
|  |   val dut_ndreset     = Wire(Bool()) | ||||||
|  |  | ||||||
|  |   val dut_clock       = Wire(Clock()) | ||||||
|  |   val dut_reset       = Wire(Bool()) | ||||||
|  |  | ||||||
|  |   val dvi_clock       = Wire(Clock()) | ||||||
|  |   val dvi_reset       = Wire(Bool()) | ||||||
|  |  | ||||||
|  |   val sd_spi_sck      = Wire(Bool()) | ||||||
|  |   val sd_spi_cs       = Wire(Bool()) | ||||||
|  |   val sd_spi_dq_i     = Wire(Vec(4, Bool())) | ||||||
|  |   val sd_spi_dq_o     = Wire(Vec(4, Bool())) | ||||||
|  |  | ||||||
|  |   val clk_locked      = Wire(Bool()) | ||||||
|  |  | ||||||
|  |  | ||||||
|  |   //----------------------------------------------------------------------- | ||||||
|  |   // System reset | ||||||
|  |   //----------------------------------------------------------------------- | ||||||
|  |  | ||||||
|  |   // Allow the debug module to reset everything. Resets the MIG | ||||||
|  |   sys_reset := reset | dut_ndreset | ||||||
|  |  | ||||||
|  |   //----------------------------------------------------------------------- | ||||||
|  |   // Clock generators | ||||||
|  |   //----------------------------------------------------------------------- | ||||||
|  |  | ||||||
|  |   // 80 MHz (processor clock) | ||||||
|  |   val ml507_sys_clock = Module(new ml507_sys_clock) | ||||||
|  |   ml507_sys_clock.io.CLKIN_IN := sys_clock | ||||||
|  |   dut_clock := ml507_sys_clock.io.CLKFX_OUT | ||||||
|  |  | ||||||
|  |   // 48 MHz (DVI pixel clock for SDR 640x480x60) | ||||||
|  |   val ml507_dvi_clock = Module(new ml507_dvi_clock) | ||||||
|  |   ml507_dvi_clock.io.CLKIN_IN := sys_clock | ||||||
|  |   dvi_clock := ml507_dvi_clock.io.CLKFX_OUT | ||||||
|  |  | ||||||
|  |   // Clocks locked? | ||||||
|  |   clk_locked := ml507_sys_clock.io.LOCKED_OUT & | ||||||
|  |                 ml507_dvi_clock.io.LOCKED_OUT | ||||||
|  |  | ||||||
|  |   //----------------------------------------------------------------------- | ||||||
|  |   // System reset | ||||||
|  |   //----------------------------------------------------------------------- | ||||||
|  |  | ||||||
|  |   do_reset             := !clk_locked || sys_reset | ||||||
|  |  | ||||||
|  |   // synchronize async resets | ||||||
|  |   val safe_reset = Module(new vc707reset) | ||||||
|  |  | ||||||
|  |   safe_reset.io.areset := do_reset | ||||||
|  |   safe_reset.io.clock1 := dut_clock | ||||||
|  |   safe_reset.io.clock2 := dut_clock | ||||||
|  |   safe_reset.io.clock3 := dvi_clock | ||||||
|  |   dvi_reset            := safe_reset.io.reset3 | ||||||
|  |   safe_reset.io.clock4 := dut_clock | ||||||
|  |   dut_reset            := safe_reset.io.reset4 | ||||||
|  |  | ||||||
|  |   // Setup feedback | ||||||
|  |   clock_led := dut_clock | ||||||
|  |   reset_led := dut_reset | ||||||
|  |  | ||||||
|  |   //----------------------------------------------------------------------- | ||||||
|  |   // Terminal | ||||||
|  |   //----------------------------------------------------------------------- | ||||||
|  |  | ||||||
|  |   def connectTerminal(dut: HasPeripheryTerminalModuleImp): Unit = { | ||||||
|  |     dvi <> dut.dvi | ||||||
|  |     dut.terminal.clk := dvi_clock | ||||||
|  |     dut.terminal.reset := dvi_reset | ||||||
|  |   } | ||||||
|  |  | ||||||
|  |   //----------------------------------------------------------------------- | ||||||
|  |   // Memory controller | ||||||
|  |   //----------------------------------------------------------------------- | ||||||
|  |  | ||||||
|  |   def connectDDRMemory(dut: HasMemoryML507ModuleImp): Unit = { | ||||||
|  |     ddr2 <> dut.ddr2 | ||||||
|  |   } | ||||||
|  |  | ||||||
|  |   //----------------------------------------------------------------------- | ||||||
|  |   // UART | ||||||
|  |   //----------------------------------------------------------------------- | ||||||
|  |  | ||||||
|  |   def connectUART(dut: HasPeripheryUARTModuleImp): Unit = { | ||||||
|  |     val uartParams = p(PeripheryUARTKey) | ||||||
|  |     if (!uartParams.isEmpty) { | ||||||
|  |       // uart connections | ||||||
|  |       dut.uart(0).rxd := SyncResetSynchronizerShiftReg(uart_rx, 2, init = Bool(true), name=Some("uart_rxd_sync")) | ||||||
|  |       uart_tx         := dut.uart(0).txd | ||||||
|  |     } | ||||||
|  |   } | ||||||
|  |  | ||||||
|  |   //----------------------------------------------------------------------- | ||||||
|  |   // SPI | ||||||
|  |   //----------------------------------------------------------------------- | ||||||
|  |  | ||||||
|  |   def connectSPI(dut: HasPeripherySPIModuleImp): Unit = { | ||||||
|  |     // SPI | ||||||
|  |     sd_spi_sck := dut.spi(0).sck | ||||||
|  |     sd_spi_cs  := dut.spi(0).cs(0) | ||||||
|  |  | ||||||
|  |     dut.spi(0).dq.zipWithIndex.foreach { | ||||||
|  |       case(pin, idx) => | ||||||
|  |         sd_spi_dq_o(idx) := pin.o | ||||||
|  |         pin.i            := sd_spi_dq_i(idx) | ||||||
|  |     } | ||||||
|  |  | ||||||
|  |     //------------------------------------------------------------------- | ||||||
|  |     // SDIO <> SPI Bridge | ||||||
|  |     //------------------------------------------------------------------- | ||||||
|  |  | ||||||
|  |     val ip_sdio_spi = Module(new sdio_spi_bridge()) | ||||||
|  |  | ||||||
|  |     ip_sdio_spi.io.clk   := dut_clock | ||||||
|  |     ip_sdio_spi.io.reset := dut_reset | ||||||
|  |  | ||||||
|  |     // SDIO | ||||||
|  |     attach(sdio_dat, ip_sdio_spi.io.sd_dat) | ||||||
|  |     attach(sdio_cmd, ip_sdio_spi.io.sd_cmd) | ||||||
|  |     sdio_clk := ip_sdio_spi.io.spi_sck | ||||||
|  |  | ||||||
|  |     // SPI | ||||||
|  |     ip_sdio_spi.io.spi_sck  := sd_spi_sck | ||||||
|  |     ip_sdio_spi.io.spi_cs   := sd_spi_cs | ||||||
|  |     sd_spi_dq_i             := ip_sdio_spi.io.spi_dq_i.toBools | ||||||
|  |     ip_sdio_spi.io.spi_dq_o := sd_spi_dq_o.asUInt | ||||||
|  |   } | ||||||
|  |  | ||||||
|  | } | ||||||
		Reference in New Issue
	
	Block a user