SpiSubSystem.v 10 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476
  1. //////////////////////////////////////////////////////////////////////////////////
  2. // Company: TAIR
  3. // Engineer:
  4. //
  5. // Create Date: 10/30/2023 11:24:31 AM
  6. // Design Name:
  7. // Module Name: SpiSubSystem
  8. // Project Name: S5443_V3_FPGA3
  9. // Target Devices: BOARD: BY5443v3. FPGA: xc7s25csga225-2
  10. // Tool Versions:
  11. // Description: This is wrapper that encapsulates FIFO's, Spi modules and
  12. // modules that multiplex Spi output lines
  13. //
  14. // Dependencies:
  15. //
  16. // Revision:
  17. // Revision 1.0 - File Created
  18. // Additional Comments:
  19. //
  20. //////////////////////////////////////////////////////////////////////////////////
  21. module SpiSubSystem #(
  22. parameter STAGES = 3,
  23. parameter AXI_DATA_WIDTH = 64,
  24. parameter CMD_REG_WIDTH = 32,
  25. parameter ADDR_REG_WIDTH = 12,
  26. parameter WIDTH = 1,
  27. parameter ISTEMPRD = 1,
  28. parameter ISPOWERRST = 1,
  29. parameter [AXI_DATA_WIDTH-1:0] SPI_BASE_ADDR = 64'h1000,
  30. parameter [AXI_DATA_WIDTH-1:0] RST_MEM_BASE_ADDR = 64'h9000,
  31. parameter [AXI_DATA_WIDTH-1:0] TMPRD_ADDR = 64'h9001
  32. )
  33. (
  34. input Clk_i,
  35. input SpiClk_i,
  36. input Rst_i,
  37. input [CMD_REG_WIDTH-1:0] WrData_i,
  38. input [CMD_REG_WIDTH-1:0] WrAddr_i,
  39. input [CMD_REG_WIDTH-1:0] RdAddr_i,
  40. input Val_i,
  41. input PowRstEn_i,
  42. input TxEn_i,
  43. output [CMD_REG_WIDTH-1:0] RdData_o,
  44. output Sck_o,
  45. output Ss_o,
  46. output SsFlash_o,
  47. output Mosi0_o,
  48. inout Mosi1_io,
  49. output Mosi2_o,
  50. output Mosi3_o
  51. );
  52. //================================================================================
  53. // REG/WIRE
  54. //================================================================================
  55. wire [CMD_REG_WIDTH-1:0] toSpiData;
  56. wire [CMD_REG_WIDTH-1:0] toSpiDataR;
  57. wire emptyFlagTx;
  58. wire sckR;
  59. wire ssR;
  60. wire mosi0R;
  61. wire valToTxR;
  62. wire valToRxR;
  63. wire sckQ;
  64. wire ssQ;
  65. wire mosi0Q;
  66. wire valToTxQ;
  67. wire valToTxFifoRead;
  68. wire valToRxFifoWrite;
  69. wire [CMD_REG_WIDTH-1:0] dataToRxFifo;
  70. wire [31:0] tempData;
  71. reg [31:0] tempDataReg;
  72. wire [31:0] powRstData;
  73. wire mosi1_o;
  74. /* Spi settings arrays */
  75. wire [AXI_DATA_WIDTH - 1 : 0] spiCtrlArray;
  76. wire [AXI_DATA_WIDTH - 1 : 0] spiClkArray;
  77. wire [AXI_DATA_WIDTH - 1 : 0] spiCsDelayArray;
  78. wire [AXI_DATA_WIDTH - 1 : 0] spiCsCtrlArray;
  79. wire [AXI_DATA_WIDTH - 1 : 0] spiTxRxFifoCtrlArray;
  80. /* Common Regs */
  81. wire [AXI_DATA_WIDTH-1:0] spiTxRxEnReg;
  82. wire [AXI_DATA_WIDTH-1:0] dataFromRegMap;
  83. /* Synced Regs */
  84. wire [AXI_DATA_WIDTH-1:0] spiCtrlRR;
  85. wire [AXI_DATA_WIDTH-1:0] spiCsDelayRR;
  86. wire [AXI_DATA_WIDTH-1:0] spiCsCtrlRR;
  87. wire [AXI_DATA_WIDTH-1:0] spiTxRxFifoCtrlRR;
  88. /* SpiSettings */
  89. wire [1:0] widthSel;
  90. wire spiEn;
  91. wire spiMode;
  92. wire clockPol;
  93. wire clockPhase;
  94. wire endianSel;
  95. wire selSt;
  96. wire assel;
  97. wire [5:0] stopDelay;
  98. wire lead;
  99. wire lag;
  100. wire fifoTxRst;
  101. wire fifoRxRst;
  102. wire txEn;
  103. wire chipSelFpga;
  104. wire chipSelFlash;
  105. wire fifoRxRstRdPtr;
  106. wire fifoTxRstWrPtr;
  107. wire [CMD_REG_WIDTH-1:0] dataFromRxFifo;
  108. //================================================================================
  109. // ASSIGNMENTS
  110. //================================================================================
  111. assign valToTxFifoRead = (spiMode) ? valToTxQ : valToTxR;
  112. assign Mosi1_io = (spiMode) ? mosi1_o : 1'bz;
  113. assign TempData_o = tempData;
  114. assign fifoRxRstRdPtr = spiTxRxFifoCtrlArray[32];
  115. assign fifoTxRstWrPtr = spiTxRxFifoCtrlArray[0];
  116. //================================================================================
  117. // CODING
  118. //================================================================================
  119. RegMap #(
  120. .AXI_DATA_WIDTH (AXI_DATA_WIDTH),
  121. .SPI_BASE_ADDR (SPI_BASE_ADDR)
  122. ) RegMap (
  123. .Clk_i(s_axi_aclk),
  124. .RstN_i(s_axi_aresetn),
  125. .WrData_i(WrData_i),
  126. .WrAddr_i(WrAddr_i),
  127. .RdAddr_i(RdAddr_i),
  128. .Val_i(Val_i),
  129. .SpiCtrlReg_o(spiCtrlArray),
  130. .SpiClkReg_o(spiClkArray),
  131. .SpiCsDelayReg_o(spiCsDelayArray),
  132. .SpiCsCtrlReg_o(spiCsCtrlArray),
  133. .SpiTxRxFifoCtrlReg_o(spiTxRxFifoCtrlArray),
  134. .AnsDataReg_o(dataFromRegMap)
  135. );
  136. /* CDC Block */
  137. CDC #(
  138. .WIDTH (AXI_DATA_WIDTH),
  139. .STAGES (STAGES)
  140. ) synchronizer
  141. (
  142. .ClkFast_i (s_axi_aclk),
  143. .ClkSlow_i (spiClkBus),
  144. .SpiCtrlReg_i (spiCtrlArray),
  145. .SpiCsCtrlReg_i (spiCsCtrlArray),
  146. .SpiCsDelayReg_i (spiCsDelayArray),
  147. .SpiTxRxFifoCtrlReg_i (spiTxRxFifoCtrlArray),
  148. .SpiCtrlReg_o (spiCtrlRR),
  149. .SpiCsCtrlReg_o (spiCsCtrlRR),
  150. .SpiCsDelayReg_o (spiCsDelayRR),
  151. .SpiTxRxFifoCtrlReg_o (spiTxRxFifoCtrlRR)
  152. );
  153. /* Spi Settings Block */
  154. SpiSettings #(
  155. .AXI_DATA_WIDTH(AXI_DATA_WIDTH)
  156. ) spiSettings (
  157. .SpiCtrlReg_i(spiCtrlRR),
  158. .SpiCsDelayReg_i(spiCsDelayRR),
  159. .SpiClkReg_i(spiClkArray),
  160. .SpiCsCtrlReg_i(spiCsCtrlRR),
  161. .SpiTxRxFifoCtrlReg_i(spiTxRxFifoCtrlRR),
  162. .SpiTxRxEnReg_i(spiTxRxEnReg),
  163. .WidthSel_o(widthSel),
  164. .SpiEn_o(spiEn),
  165. .SpiMode_o(spiMode),
  166. .ClockPol_o(clockPol),
  167. .ClockPhase_o(clockPhase),
  168. .EndianSel_o(endianSel),
  169. .SelSt_o(selSt),
  170. .Assel(assel),
  171. .StopDelay_o(stopDelay),
  172. .Lead_o(lead),
  173. .Lag_o(lag),
  174. .BaudRate_o(baudRate),
  175. .SpiRst_o(SpiRst_o),
  176. .FifoRxRst_o(fifoRxRst),
  177. .FifoTxRst_o(fifoTxRst),
  178. .ChipSelFpga_o(chipSelFpga),
  179. .ChipSelFlash_o(chipSelFlash),
  180. .SpiDir_o(SpiDir_o),
  181. .TxEn_o(txEn)
  182. );
  183. Sync1bit #(
  184. .WIDTH (1),
  185. .STAGES (STAGES)
  186. ) Sync1bit_inst
  187. (
  188. .ClkFast_i (Clk_i),
  189. .ClkSlow_i (SpiClk_i),
  190. .TxEn_i (TxEn_i),
  191. .TxEn_o (spiTxEnSync)
  192. );
  193. DataFifoWrapper #(
  194. .CMD_REG_WIDTH (CMD_REG_WIDTH),
  195. .ADDR_REG_WIDTH (ADDR_REG_WIDTH),
  196. .STAGES (STAGES),
  197. .TX_FIFO_ADDR (SPI_BASE_ADDR+64'h28),
  198. .RX_FIFO_ADDR (SPI_BASE_ADDR+64'h30)
  199. ) DataFifoWrapper (
  200. .WrClk_i (Clk_i),
  201. .RdClk_i (SpiClk_i),
  202. .FifoRxRst_i (fifoRxRst),
  203. .FifoTxRst_i (fifoTxRst),
  204. .FifoRxRstRdPtr_i (),
  205. .FifoTxRstWrPtr_i (),
  206. .WrData_i (WrData_i),
  207. .WrAddr_i (WrAddr_i),
  208. .RdAddr_i (RdAddr_i),
  209. .Val_i (Val_i),
  210. .ToFifoRxData_i (dataToRxFifo),
  211. .ToFifoRxWriteVal_i (valToRxR),
  212. .ToFifoTxReadVal_i (valToTxFifoRead),
  213. .TxFifoCtrlReg_o (TxFifoCtrlReg_o),
  214. .RxFifoCtrlReg_o (RxFifoCtrlReg_o),
  215. .EmptyFlagTx_o (emptyFlagTx),
  216. .DataFromRxFifo_o (dataFromRxFifo),
  217. .ToSpiData_o (toSpiData)
  218. );
  219. generate
  220. if (ISTEMPRD) begin : TempRdSpi
  221. SPIs TempRdSpi
  222. (
  223. .Clk_i (SpiClk_i),
  224. .Rst_i (Rst_i | spiMode),
  225. .Sck_i (sckR),
  226. .Ss_i (ssR),
  227. .Mosi0_i (Mosi1_io),
  228. .WidthSel_i (widthSel),
  229. .EndianSel_i (endianSel),
  230. .SelSt_i (selSt),
  231. .DataToRxFifo_o (tempData),
  232. .Val_o (tempVal)
  233. );
  234. always @(posedge Clk_i) begin
  235. if (Rst_i) begin
  236. tempDataReg <= 32'd0;
  237. end else begin
  238. if (tempVal) begin
  239. tempDataReg <= tempData;
  240. end
  241. end
  242. end
  243. assign RdData_o = (RdAddr_i == TMPRD_ADDR) ? tempDataReg : dataFromRxFifo;
  244. end else begin
  245. assign RdData_o = dataToRxFifo;
  246. end
  247. endgenerate
  248. generate
  249. if (ISPOWERRST) begin : PowRstMem
  250. PowRstMemWrapper #(
  251. .RST_MEM_BASE_ADDR(RST_MEM_BASE_ADDR)
  252. )
  253. PowRstMemWrapper
  254. (
  255. .Clk_i(Clk_i),
  256. .Rst_i(Rst_i),
  257. .WrData_i(WrData_i),
  258. .WrAddr_i(WrAddr_i),
  259. .Val_i(Val_i),
  260. .RdReq_i(),
  261. .Data_o(powRstData),
  262. .DataVal_o()
  263. );
  264. SpiDataMuxer SpiDataMuxer(
  265. .Clk_i (Clk_i),
  266. .Rst_i (Rst_i),
  267. .PowRstEn_i (PowRstEn_i),
  268. .PowRstData_i (powRstData),
  269. .RegularData_i (toSpiData),
  270. .Data_o (toSpiDataR)
  271. );
  272. SPIm SPIm (
  273. .Clk_i (SpiClk_i),
  274. .Start_i (spiTxEnSync),
  275. .Rst_i (Rst_i | spiMode | !spiEn),
  276. .EmptyFlag_i (emptyFlagTx),
  277. .SpiData_i (toSpiDataR),
  278. .WidthSel_i (widthSel),
  279. .PulsePol_i (clockPol),
  280. .ClockPhase_i (clockPhase),
  281. .EndianSel_i (endianSel),
  282. .Lag_i (lag),
  283. .Lead_i (lead),
  284. .Stop_i (stopDelay),
  285. .SelSt_i (selSt),
  286. .Sck_o (sckR),
  287. .Ss_o (ssR),
  288. .Mosi0_o (mosi0R),
  289. .Val_o (valToTxR)
  290. );
  291. SPIs SPIs (
  292. .Clk_i (SpiClk_i),
  293. .Rst_i (Rst_i | spiMode),
  294. .Sck_i (sckR),
  295. .Ss_i (ssR),
  296. .Mosi0_i (Mosi1_io),
  297. .WidthSel_i (widthSel),
  298. .EndianSel_i (endianSel),
  299. .SelSt_i (selSt),
  300. .DataToRxFifo_o (dataToRxFifo),
  301. .Val_o (valToRxR)
  302. );
  303. QuadSPIm QuadSPIm (
  304. .Clk_i (SpiClk_i),
  305. .Start_i (spiTxEnSync),
  306. .Rst_i (Rst_i | !spiMode | !spiEn),
  307. .EmptyFlag_i (emptyFlagTx),
  308. .SpiData_i (toSpiDataR),
  309. .WidthSel_i (widthSel),
  310. .PulsePol_i (clockPol),
  311. .ClockPhase_i (clockPhase),
  312. .EndianSel_i (endianSel),
  313. .Lag_i (lag),
  314. .Lead_i (lead),
  315. .Stop_i (stopDelay),
  316. .SelSt_i (selSt),
  317. .Sck_o (sckQ),
  318. .Ss_o (ssQ),
  319. .Mosi0_o (mosi0Q),
  320. .Mosi1_o (mosi1_o),
  321. .Mosi2_o (Mosi2_o),
  322. .Mosi3_o (Mosi3_o),
  323. .Val_o (valToTxQ)
  324. );
  325. SpiLinesMuxer SpiLinesMuxer (
  326. .SsR_i (ssR),
  327. .SsQ_i (ssQ),
  328. .SckR_i (sckR),
  329. .SckQ_i (sckQ),
  330. .Mosi0R_i (mosi0R),
  331. .Mosi0Q_i (mosi0Q),
  332. .ChipSelFpga_i (chipSelFpga),
  333. .ChipSelFlash_i (chipSelFlash),
  334. .Assel_i (assel),
  335. .SpiMode_i (spiMode),
  336. .Ss_o (Ss_o),
  337. .SsFlash_o (SsFlash_o),
  338. .Sck_o (Sck_o),
  339. .Mosi0_o (Mosi0_o)
  340. );
  341. end else begin
  342. SPIm SPIm (
  343. .Clk_i (SpiClk_i),
  344. .Start_i (spiTxEnSync),
  345. .Rst_i (Rst_i | spiMode | !spiEn),
  346. .EmptyFlag_i (emptyFlagTx),
  347. .SpiData_i (toSpiData),
  348. .WidthSel_i (widthSel),
  349. .PulsePol_i (clockPol),
  350. .ClockPhase_i (clockPhase),
  351. .EndianSel_i (endianSel),
  352. .Lag_i (lag),
  353. .Lead_i (lead),
  354. .Stop_i (stopDelay),
  355. .SelSt_i (selSt),
  356. .Sck_o (sckR),
  357. .Ss_o (ssR),
  358. .Mosi0_o (mosi0R),
  359. .Val_o (valToTxR)
  360. );
  361. SPIs SPIs (
  362. .Clk_i (SpiClk_i),
  363. .Rst_i (Rst_i | spiMode),
  364. .Sck_i (sckR),
  365. .Ss_i (ssR),
  366. .Mosi0_i (Mosi1_io),
  367. .WidthSel_i (widthSel),
  368. .EndianSel_i (endianSel),
  369. .SelSt_i (selSt),
  370. .DataToRxFifo_o (dataToRxFifo),
  371. .Val_o (valToRxR)
  372. );
  373. QuadSPIm QuadSPIm (
  374. .Clk_i (SpiClk_i),
  375. .Start_i (spiTxEnSync),
  376. .Rst_i (Rst_i | !spiMode | !spiEn),
  377. .EmptyFlag_i (emptyFlagTx),
  378. .SpiData_i (toSpiData),
  379. .WidthSel_i (widthSel),
  380. .PulsePol_i (clockPol),
  381. .ClockPhase_i (clockPhase),
  382. .EndianSel_i (endianSel),
  383. .Lag_i (lag),
  384. .Lead_i (lead),
  385. .Stop_i (stopDelay),
  386. .SelSt_i (selSt),
  387. .Sck_o (sckQ),
  388. .Ss_o (ssQ),
  389. .Mosi0_o (mosi0Q),
  390. .Mosi1_o (mosi1_o),
  391. .Mosi2_o (Mosi2_o),
  392. .Mosi3_o (Mosi3_o),
  393. .Val_o (valToTxQ)
  394. );
  395. SpiLinesMuxer SpiLinesMuxer (
  396. .SsR_i (ssR),
  397. .SsQ_i (ssQ),
  398. .SckR_i (sckR),
  399. .SckQ_i (sckQ),
  400. .Mosi0R_i (mosi0R),
  401. .Mosi0Q_i (mosi0Q),
  402. .ChipSelFpga_i (chipSelFpga),
  403. .ChipSelFlash_i (chipSelFlash),
  404. .Assel_i (assel),
  405. .SpiMode_i (spiMode),
  406. .Ss_o (Ss_o),
  407. .SsFlash_o (SsFlash_o),
  408. .Sck_o (Sck_o),
  409. .Mosi0_o (Mosi0_o)
  410. );
  411. end
  412. endgenerate
  413. endmodule