risc core and wishbone domain seperated + Stagging FF added at wishbone interconnect
diff --git a/verilog/dv/risc_boot/risc_boot.c b/verilog/dv/risc_boot/risc_boot.c
index d042822..f0d8010 100644
--- a/verilog/dv/risc_boot/risc_boot.c
+++ b/verilog/dv/risc_boot/risc_boot.c
@@ -170,7 +170,6 @@
// Add some delay for user core to boot
for(i = 0; i < 40; i ++);
- for(i = 0; i < 40; i ++);
if(reg_mprj_globl_reg6 != 0x11223344) bFail = 1;
if(reg_mprj_globl_reg7 != 0x22334455) bFail = 1;
diff --git a/verilog/dv/risc_boot/risc_boot_tb.v b/verilog/dv/risc_boot/risc_boot_tb.v
index 80c7d98..fe5a499 100644
--- a/verilog/dv/risc_boot/risc_boot_tb.v
+++ b/verilog/dv/risc_boot/risc_boot_tb.v
@@ -91,7 +91,7 @@
$dumpfile("simx.vcd");
$dumpvars(1,risc_boot_tb);
//$dumpvars(2,risc_boot_tb.uut);
- $dumpvars(1,risc_boot_tb.uut.mprj.u_core);
+ $dumpvars(4,risc_boot_tb.uut.mprj.u_core);
//$dumpvars(0,risc_boot_tb.u_user_spiflash);
$display("Waveform Dump started");
end
@@ -100,7 +100,7 @@
initial begin
// Repeat cycles of 1000 clock edges as needed to complete testbench
- repeat (600) begin
+ repeat (200) begin
repeat (1000) @(posedge clock);
// $display("+1000 cycles");
end
diff --git a/verilog/dv/user_risc_boot/uprj_netlists.v b/verilog/dv/user_risc_boot/uprj_netlists.v
index 45af4a9..fe938c1 100644
--- a/verilog/dv/user_risc_boot/uprj_netlists.v
+++ b/verilog/dv/user_risc_boot/uprj_netlists.v
@@ -38,6 +38,7 @@
`include "digital_core/src/glbl_cfg.sv"
`include "digital_core/src/digital_core.sv"
+ `include "lib/wb_stagging.sv"
`include "wb_interconnect/src/wb_arb.sv"
`include "wb_interconnect/src/wb_interconnect.sv"
diff --git a/verilog/dv/user_risc_boot/user_risc_boot.hex b/verilog/dv/user_risc_boot/user_risc_boot.hex
index 1fdd96c..5ab43fa 100755
--- a/verilog/dv/user_risc_boot/user_risc_boot.hex
+++ b/verilog/dv/user_risc_boot/user_risc_boot.hex
@@ -38,20 +38,20 @@
93 08 00 00 13 09 00 00 93 09 00 00 13 0A 00 00
93 0A 00 00 13 0B 00 00 93 0B 00 00 13 0C 00 00
93 0C 00 00 13 0D 00 00 93 0D 00 00 13 0E 00 00
-93 0E 00 00 13 0F 00 00 93 0F 00 00 97 01 48 00
-93 81 41 62 13 05 00 40 97 05 48 00 93 85 85 D7
-17 06 48 00 13 06 06 E3 63 0D B5 00 29 A0 14 41
-94 C1 11 05 91 05 E3 9C C5 FE 17 06 48 00 13 06
-66 E1 97 05 48 00 93 85 E5 E0 21 A0 23 20 06 00
-11 06 E3 9D C5 FE 17 01 49 00 13 01 A1 D3 17 05
-48 00 13 05 25 DF 17 06 48 00 13 06 A6 DE B3 05
-A6 40 17 07 49 00 13 07 E7 91 33 02 B7 40 92 85
-17 06 48 00 13 06 06 DD 29 A0 14 41 94 C1 11 05
+93 0E 00 00 13 0F 00 00 93 0F 00 00 97 01 00 20
+93 81 41 62 13 05 00 40 97 05 00 20 93 85 85 D7
+17 06 00 20 13 06 06 E3 63 0D B5 00 29 A0 14 41
+94 C1 11 05 91 05 E3 9C C5 FE 17 06 00 20 13 06
+66 E1 97 05 00 20 93 85 E5 E0 21 A0 23 20 06 00
+11 06 E3 9D C5 FE 17 01 01 20 13 01 A1 D3 17 05
+00 20 13 05 25 DF 17 06 00 20 13 06 A6 DE B3 05
+A6 40 17 07 01 20 13 07 E7 91 33 02 B7 40 92 85
+17 06 00 20 13 06 06 DD 29 A0 14 41 94 C1 11 05
91 05 E3 1C C5 FE 21 A0 23 A0 05 00 91 05 E3 9D
E5 FE B7 02 49 00 05 43 23 A0 62 00 B7 02 49 00
91 02 13 03 30 06 23 A0 62 00 B7 02 49 00 C1 02
7D 53 23 A0 62 00 23 A2 62 00 01 45 81 45 97 02
-48 00 E7 80 22 CC 97 02 48 00 93 82 A2 D1 6D 71
+00 20 E7 80 22 CC 97 02 00 20 93 82 A2 D1 6D 71
06 C2 0A C4 0E C6 12 C8 16 CA 1A CC 1E CE 22 D0
26 D2 2A D4 2E D6 32 D8 36 DA 3A DC 3E DE C2 C0
C6 C2 CA C4 CE C6 D2 C8 D6 CA DA CC DE CE E2 D0
@@ -70,7 +70,7 @@
66 55 D4 D3 93 08 88 78 37 9E 77 66 23 A4 17 03
93 0E 9E 89 23 A6 D7 03 01 A0 00 00 00 00 00 00
00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
-97 02 B8 FF 93 82 42 09 82 82 13 00 00 00 13 00
+97 02 00 E0 93 82 42 09 82 82 13 00 00 00 13 00
00 00 13 00 00 00 13 00 00 00 13 00 00 00 01 00
00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
diff --git a/verilog/rtl/digital_core/src/digital_core.sv b/verilog/rtl/digital_core/src/digital_core.sv
index 82df8cd..7ae0a6b 100644
--- a/verilog/rtl/digital_core/src/digital_core.sv
+++ b/verilog/rtl/digital_core/src/digital_core.sv
@@ -73,7 +73,7 @@
inout vssd2, // User area 2 digital ground
`endif
input logic wb_clk_i , // System clock
- input logic rtc_clk , // Real-time clock
+ input logic user_clock2 , // user Clock
input logic wb_rst_i , // Regular Reset signal
input logic wbd_ext_cyc_i , // strobe/request
@@ -301,7 +301,7 @@
`endif // SCR1_DBG_EN
// Clock
- .clk (wb_clk_i ),
+ .core_clk (cpu_clk ),
.rtc_clk (rtc_clk ),
// Fuses
@@ -332,6 +332,9 @@
.tdo_en (tdo_en ),
`endif // SCR1_DBG_EN
+
+ .wb_rst_n (wb_rst_n ),
+ .wb_clk (wb_clk_i ),
// Instruction memory interface
.wbd_imem_stb_o (wbd_riscv_imem_stb_i ),
.wbd_imem_adr_o (wbd_riscv_imem_adr_i ),
@@ -534,6 +537,7 @@
.mclk (wb_clk_i ),
.reset_n (wb_rst_n ),
+ .user_clock2 (user_clock2 ),
.device_idcode ( ),
// Reg Bus Interface Signal
@@ -550,6 +554,8 @@
// SDRAM Clock
.sdram_clk (sdram_clk ),
+ .cpu_clk (cpu_clk ),
+ .rtc_clk (rtc_clk ),
// reset
.cpu_rst_n (cpu_rst_n ),
diff --git a/verilog/rtl/digital_core/src/glbl_cfg.sv b/verilog/rtl/digital_core/src/glbl_cfg.sv
index 6844c9f..22e68c5 100644
--- a/verilog/rtl/digital_core/src/glbl_cfg.sv
+++ b/verilog/rtl/digital_core/src/glbl_cfg.sv
@@ -48,6 +48,7 @@
module glbl_cfg (
input logic mclk,
+ input logic user_clock2,
input logic reset_n,
output logic [31:0] device_idcode,
@@ -65,6 +66,8 @@
// SDRAM Clock
output logic sdram_clk,
+ output logic cpu_clk,
+ output logic rtc_clk,
// reset
output logic cpu_rst_n,
@@ -110,7 +113,6 @@
logic reg_cs_l ;
logic reg_cs_2l ;
-logic cfg_sdram_clk_div;
logic [31:0] reg_0; // Software_Reg_0
@@ -252,12 +254,24 @@
// reg-0
// -----------------------------------------------------------------
-assign cpu_rst_n = reg_0[0];
-assign spi_rst_n = reg_0[1];
-assign sdram_rst_n = reg_0[2];
-assign cfg_sdram_clk_div = reg_0[3];
+assign cpu_rst_n = reg_0[0];
+assign spi_rst_n = reg_0[1];
+assign sdram_rst_n = reg_0[2];
+// SDRAM Clock source & div selection
+wire cfg_sdram_clk_src_sel = reg_0[4];
+wire cfg_sdram_clk_div = reg_0[5];
+wire [1:0] cfg_sdram_clk_ratio = reg_0[7:6];
+// Core Clock source & div selection
+wire cfg_cpu_clk_src_sel = reg_0[8];
+wire cfg_cpu_clk_div = reg_0[9];
+wire [1:0] cfg_cpu_clk_ratio = reg_0[11:10];
+
+// RTC Clock source & div selection
+wire cfg_rtc_clk_src_sel = reg_0[12];
+wire cfg_rtc_clk_div = reg_0[13];
+wire [1:0] cfg_rtc_clk_ratio = reg_0[15:14];
generic_register #(8,0 ) u_reg0_be0 (
.we ({8{sw_wr_en_0 &
@@ -429,7 +443,7 @@
.data_out (reg_3[15:8] )
);
generic_register #(4,0 ) u_reg3_be2 (
- .we ({1{sw_wr_en_3 &
+ .we ({4{sw_wr_en_3 &
wr_be[2] }} ),
.data_in (sw_reg_wdata[19:16] ),
.reset_n (reset_n ),
@@ -1030,29 +1044,72 @@
.clk (mclk ),
//List of Outs
- .data_out (reg_15[31:24] )
+ .data_out (reg_15[31:24] )
);
//----------------------------------
-// Generate SDRAM Div-2 Clock
+// Generate SDRAM Clock Generation
//----------------------------------
-wire sdram_clk_div2;
+wire sdram_clk_div;
+wire sdram_ref_clk;
-assign sdram_clk = (cfg_sdram_clk_div) ? sdram_clk_div2 : mclk;
+assign sdram_ref_clk = (cfg_sdram_clk_src_sel) ? user_clock2 : mclk;
+
+
+
+assign sdram_clk = (cfg_sdram_clk_div) ? sdram_clk_div : sdram_ref_clk;
clk_ctl #(1) u_sdramclk (
// Outputs
- .clk_o (sdram_clk_div2),
+ .clk_o (sdram_clk_div ),
// Inputs
- .mclk (mclk),
- .reset_n (reset_n),
- .clk_div_ratio (2'b00)
+ .mclk (sdram_ref_clk ),
+ .reset_n (reset_n ),
+ .clk_div_ratio (cfg_sdram_clk_ratio)
);
+//----------------------------------
+// Generate CORE Clock Generation
+//----------------------------------
+wire cpu_clk_div;
+wire cpu_ref_clk;
+
+assign cpu_ref_clk = (cfg_cpu_clk_src_sel) ? user_clock2 : mclk;
+assign cpu_clk = (cfg_cpu_clk_div) ? cpu_clk_div : cpu_ref_clk;
+
+
+clk_ctl #(1) u_cpuclk (
+ // Outputs
+ .clk_o (cpu_clk_div ),
+ // Inputs
+ .mclk (cpu_ref_clk ),
+ .reset_n (reset_n ),
+ .clk_div_ratio (cfg_cpu_clk_ratio)
+ );
+
+//----------------------------------
+// Generate RTC Clock Generation
+//----------------------------------
+wire rtc_clk_div;
+wire rtc_ref_clk;
+
+assign rtc_ref_clk = (cfg_rtc_clk_src_sel) ? user_clock2 : mclk;
+assign rtc_clk = (cfg_rtc_clk_div) ? rtc_clk_div : rtc_ref_clk;
+
+
+clk_ctl #(1) u_rtcclk (
+ // Outputs
+ .clk_o (rtc_clk_div ),
+ // Inputs
+ .mclk (rtc_ref_clk ),
+ .reset_n (reset_n ),
+ .clk_div_ratio (cfg_rtc_clk_ratio)
+ );
+
endmodule
diff --git a/verilog/rtl/lib/wb_crossbar.v b/verilog/rtl/lib/wb_crossbar.v
deleted file mode 100644
index 76b9981..0000000
--- a/verilog/rtl/lib/wb_crossbar.v
+++ /dev/null
@@ -1,398 +0,0 @@
-//////////////////////////////////////////////////////////////////////
-//// ////
-//// yifive common library Module ////
-//// ////
-//// This file is part of the yifive cores project ////
-//// http://www.opencores.org/cores/yifive/ ////
-//// ////
-//// Description ////
-//// This module does the Wishone crossbar network ////
-//// ////
-//// To Do: ////
-//// nothing ////
-//// ////
-//// Author(s): ////
-//// - Dinesh Annayya, dinesha@opencores.org ////
-//// ////
-//////////////////////////////////////////////////////////////////////
-//// Revision : ////
-//// v0: Nov 26, 2016, Dinesh A ////
-//// This files copied from my open core ////
-//// turbo8051 project ////
-//////////////////////////////////////////////////////////////////////
-//// ////
-//// Copyright (C) 2000 Authors and OPENCORES.ORG ////
-//// ////
-//// This source file may be used and distributed without ////
-//// restriction provided that this copyright statement is not ////
-//// removed from the file and that any derivative work contains ////
-//// the original copyright notice and the associated disclaimer. ////
-//// ////
-//// This source file is free software; you can redistribute it ////
-//// and/or modify it under the terms of the GNU Lesser General ////
-//// Public License as published by the Free Software Foundation; ////
-//// either version 2.1 of the License, or (at your option) any ////
-//// later version. ////
-//// ////
-//// This source is distributed in the hope that it will be ////
-//// useful, but WITHOUT ANY WARRANTY; without even the implied ////
-//// warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR ////
-//// PURPOSE. See the GNU Lesser General Public License for more ////
-//// details. ////
-//// ////
-//// You should have received a copy of the GNU Lesser General ////
-//// Public License along with this source; if not, download it ////
-//// from http://www.opencores.org/lgpl.shtml ////
-//// ////
-//////////////////////////////////////////////////////////////////////
-
-/**********************************************
- Wish-bone cross bar M-Master By S-Slave
-**********************************************/
-
-module wb_crossbar (
-
- rst_n ,
- clk ,
-
-
- // Master Interface Signal
- wbd_taddr_master ,
- wbd_din_master ,
- wbd_dout_master ,
- wbd_adr_master ,
- wbd_be_master ,
- wbd_we_master ,
- wbd_ack_master ,
- wbd_stb_master ,
- wbd_cyc_master ,
- wbd_err_master ,
- wbd_rty_master ,
-
- // Slave Interface Signal
- wbd_din_slave ,
- wbd_dout_slave ,
- wbd_adr_slave ,
- wbd_be_slave ,
- wbd_we_slave ,
- wbd_ack_slave ,
- wbd_stb_slave ,
- wbd_cyc_slave ,
- wbd_err_slave ,
- wbd_rty_slave
- );
-
-parameter WB_SLAVE = 4 ;
-parameter WB_MASTER = 4 ;
-
-parameter D_WD = 16; // Data Width
-parameter BE_WD = 2; // Byte Enable
-parameter ADR_WD = 28; // Address Width
-parameter TAR_WD = 4; // Target Width
-
-input clk; // CLK_I The clock input [CLK_I] coordinates all activities
- // for the internal logic within the WISHBONE interconnect.
- // All WISHBONE output signals are registered at the
- // rising edge of [CLK_I].
- // All WISHBONE input signals must be stable before the
- // rising edge of [CLK_I].
-input rst_n; // RST_I The reset input [RST_I] forces the WISHBONE interface
- // to restart. Furthermore, all internal self-starting state
- // machines will be forced into an initial state.
-
-input [(WB_MASTER *TAR_WD)-1:0] wbd_taddr_master; // target address from master
-input [WB_MASTER-1:0] wbd_stb_master;
- // STB_O The strobe output [STB_O] indicates a valid data
- // transfer cycle. It is used to qualify various other signals
- // on the interface such as [SEL_O(7..0)]. The SLAVE must
- // assert either the [ACK_I], [ERR_I] or [RTY_I] signals in
- // response to every assertion of the [STB_O] signal.
-output [WB_SLAVE-1:0] wbd_stb_slave;
- // STB_O The strobe output [STB_O] indicates a valid data
- // transfer cycle. It is used to qualify various other signals
- // on the interface such as [SEL_O(7..0)]. The SLAVE must
- // assert either the [ACK_I], [ERR_I] or [RTY_I] signals in
- // response to every assertion of the [STB_O] signal.
-
-input [WB_MASTER-1:0] wbd_we_master;
- // WE_O The write enable output [WE_O] indicates whether the
- // current local bus cycle is a READ or WRITE cycle. The
- // signal is negated during READ cycles, and is asserted
- // during WRITE cycles.
-output [WB_SLAVE-1:0] wbd_we_slave;
- // WE_O The write enable output [WE_O] indicates whether the
- // current local bus cycle is a READ or WRITE cycle. The
- // signal is negated during READ cycles, and is asserted
- // during WRITE cycles.
-
-output [WB_MASTER-1:0] wbd_ack_master;
- // The acknowledge input [ACK_I], when asserted,
- // indicates the termination of a normal bus cycle.
- // Also see the [ERR_I] and [RTY_I] signal descriptions.
-input [WB_SLAVE-1:0] wbd_ack_slave;
- // The acknowledge input [ACK_I], when asserted,
- // indicates the termination of a normal bus cycle.
- // Also see the [ERR_I] and [RTY_I] signal descriptions.
-
-input [(WB_MASTER *ADR_WD)-1:0] wbd_adr_master;
- // The address output array [ADR_O(63..0)] is used
- // to pass a binary address, with the most significant
- // address bit at the higher numbered end of the signal array.
- // The lower array boundary is specific to the data port size.
- // The higher array boundary is core-specific.
- // In some cases (such as FIFO interfaces)
- // the array may not be present on the interface.
-
-output [(WB_SLAVE *ADR_WD)-1:0] wbd_adr_slave;
- // The address output array [ADR_O(63..0)] is used
- // to pass a binary address, with the most significant
- // address bit at the higher numbered end of the signal array.
- // The lower array boundary is specific to the data port size.
- // The higher array boundary is core-specific.
- // In some cases (such as FIFO interfaces)
- // the array may not be present on the interface.
-
-input [(WB_MASTER * BE_WD)-1:0] wbd_be_master; // Byte Enable
- // SEL_O(7..0) The select output array [SEL_O(7..0)] indicates
- // where valid data is expected on the [DAT_I(63..0)] signal
- // array during READ cycles, and where it is placed on the
- // [DAT_O(63..0)] signal array during WRITE cycles.
- // Also see the [DAT_I(63..0)], [DAT_O(63..0)] and [STB_O]
- // signal descriptions.
-output [(WB_SLAVE * BE_WD)-1:0] wbd_be_slave; // Byte Enable
- // SEL_O(7..0) The select output array [SEL_O(7..0)] indicates
- // where valid data is expected on the [DAT_I(63..0)] signal
- // array during READ cycles, and where it is placed on the
- // [DAT_O(63..0)] signal array during WRITE cycles.
- // Also see the [DAT_I(63..0)], [DAT_O(63..0)] and [STB_O]
- // signal descriptions.
-
-input [WB_MASTER -1:0] wbd_cyc_master;
- // CYC_O The cycle output [CYC_O], when asserted,
- // indicates that a valid bus cycle is in progress.
- // The signal is asserted for the duration of all bus cycles.
- // For example, during a BLOCK transfer cycle there can be
- // multiple data transfers. The [CYC_O] signal is asserted
- // during the first data transfer, and remains asserted
- // until the last data transfer. The [CYC_O] signal is useful
- // for interfaces with multi-port interfaces
- // (such as dual port memories). In these cases,
- // the [CYC_O] signal requests use of a common bus from an
- // arbiter. Once the arbiter grants the bus to the MASTER,
- // it is held until [CYC_O] is negated.
-output [WB_SLAVE -1:0] wbd_cyc_slave;
- // CYC_O The cycle output [CYC_O], when asserted,
- // indicates that a valid bus cycle is in progress.
- // The signal is asserted for the duration of all bus cycles.
- // For example, during a BLOCK transfer cycle there can be
- // multiple data transfers. The [CYC_O] signal is asserted
- // during the first data transfer, and remains asserted
- // until the last data transfer. The [CYC_O] signal is useful
- // for interfaces with multi-port interfaces
- // (such as dual port memories). In these cases,
- // the [CYC_O] signal requests use of a common bus from an
- // arbiter. Once the arbiter grants the bus to the MASTER,
- // it is held until [CYC_O] is negated.
-
-input [(WB_MASTER * D_WD)-1:0] wbd_din_master;
- // DAT_I(63..0) The data input array [DAT_I(63..0)] is
- // used to pass binary data. The array boundaries are
- // determined by the port size. Also see the [DAT_O(63..0)]
- // and [SEL_O(7..0)] signal descriptions.
-
-output [(WB_SLAVE * D_WD)-1:0] wbd_din_slave;
- // DAT_I(63..0) The data input array [DAT_I(63..0)] is
- // used to pass binary data. The array boundaries are
- // determined by the port size. Also see the [DAT_O(63..0)]
- // and [SEL_O(7..0)] signal descriptions.
-
-output [(WB_MASTER * D_WD)-1:0] wbd_dout_master;
- // DAT_O(63..0) The data output array [DAT_O(63..0)] is
- // used to pass binary data. The array boundaries are
- // determined by the port size. Also see the [DAT_I(63..0)]
- // and [SEL_O(7..0)] signal descriptions.
-input [(WB_SLAVE * D_WD)-1:0] wbd_dout_slave;
- // DAT_O(63..0) The data output array [DAT_O(63..0)] is
- // used to pass binary data. The array boundaries are
- // determined by the port size. Also see the [DAT_I(63..0)]
- // and [SEL_O(7..0)] signal descriptions.
-
-output [WB_MASTER -1:0] wbd_err_master;
- // ERR_I The error input [ERR_I] indicates an abnormal
- // cycle termination. The source of the error, and the
- // response generated by the MASTER is defined by the IP core
- // supplier in the WISHBONE DATASHEET. Also see the [ACK_I]
- // and [RTY_I] signal descriptions.
-input [WB_SLAVE -1:0] wbd_err_slave;
- // ERR_I The error input [ERR_I] indicates an abnormal
- // cycle termination. The source of the error, and the
- // response generated by the MASTER is defined by the IP core
- // supplier in the WISHBONE DATASHEET. Also see the [ACK_I]
- // and [RTY_I] signal descriptions.
-
-output [WB_MASTER -1:0] wbd_rty_master;
- // RTY_I The retry input [RTY_I] indicates that the indicates
- // that the interface is not ready to accept or send data, and
- // that the cycle should be retried. When and how the cycle is
- // retried is defined by the IP core supplier in the WISHBONE
- // DATASHEET. Also see the [ERR_I] and [RTY_I] signal
- // descriptions.
-input [WB_SLAVE -1:0] wbd_rty_slave;
- // RTY_I The retry input [RTY_I] indicates that the indicates
- // that the interface is not ready to accept or send data, and
- // that the cycle should be retried. When and how the cycle is
- // retried is defined by the IP core supplier in the WISHBONE
- // DATASHEET. Also see the [ERR_I] and [RTY_I] signal
- // descriptions.
-
-
-reg [WB_MASTER-1:0] wbd_ack_master;
-reg [WB_MASTER-1:0] wbd_err_master;
-reg [WB_MASTER-1:0] wbd_rty_master;
-
-
-reg [WB_MASTER-1:0] master_busy; // master busy flag
-reg [WB_SLAVE-1:0] slave_busy; // slave busy flag
-reg [TAR_WD -1:0] master_mx_id[WB_MASTER-1:0];
-reg [TAR_WD -1:0] slave_mx_id [WB_SLAVE-1:0];
-
-wire [TAR_WD-1:0] wbd_taddr_master_t[WB_MASTER-1:0]; // target address from master
-wire [D_WD-1:0] wbd_din_master_t[WB_MASTER-1:0]; // target address from master
-reg [D_WD-1:0] wbd_dout_master_t[WB_MASTER-1:0]; // target address from master
-wire [ADR_WD-1:0] wbd_adr_master_t[WB_MASTER-1:0]; // target address from master
-wire [BE_WD-1:0] wbd_be_master_t[WB_MASTER-1:0]; // target address from master
-
-
-reg [WB_SLAVE-1:0] wbd_stb_slave;
-reg [WB_SLAVE-1:0] wbd_we_slave;
-reg [WB_SLAVE-1:0] wbd_cyc_slave;
-wire [D_WD-1:0] wbd_dout_slave_t[WB_SLAVE-1:0]; // target data towards master
-
-
-reg [D_WD-1:0] wbd_din_slave_t[WB_SLAVE-1:0]; // target address from master
-reg [ADR_WD-1:0] wbd_adr_slave_t[WB_SLAVE-1:0]; // target address from master
-reg [BE_WD-1:0] wbd_be_slave_t[WB_SLAVE-1:0]; // target address from master
-
-integer i,k,l,n;
-
-
-/**********************************************************
- Re-Arraging the array in seperate two dimensional information
-***********************************************************/
-
-genvar j,m;
-generate
-
- // Connect the Master Mux
- for(j=0; j < WB_MASTER ; j = j + 1) begin : master_expand
- assign wbd_taddr_master_t[j] = wbd_taddr_master[((j+1)*TAR_WD)-1:j * TAR_WD];
- assign wbd_din_master_t[j] = wbd_din_master[((j+1)*D_WD)-1:j * D_WD];
- assign wbd_adr_master_t[j] = wbd_adr_master[((j+1)*ADR_WD)-1:j * ADR_WD];
- assign wbd_be_master_t[j] = wbd_be_master[((j+1)*BE_WD)-1:j * BE_WD];
-
- assign wbd_dout_master[((j+1)*D_WD)-1:j * D_WD] = wbd_dout_master_t[j];
- end
-
- // Connect the Slave Mux
- for(m=0; m < WB_SLAVE ; m = m + 1) begin : slave_expand
- assign wbd_din_slave[((m+1)*D_WD)-1:m * D_WD] = wbd_din_slave_t[m];
- assign wbd_adr_slave[((m+1)*ADR_WD)-1:m * ADR_WD] = wbd_adr_slave_t[m];
- assign wbd_be_slave[((m+1)*BE_WD)-1:m * BE_WD] = wbd_be_slave_t[m];
-
- assign wbd_dout_slave_t[m] = wbd_dout_slave[((m+1)*D_WD)-1:m * D_WD];
-
- end
-endgenerate
-
-always @* begin
- for(k = 0; k < WB_MASTER; k = k + 1) begin
- if(master_busy[k] == 1) begin
- wbd_dout_master_t[k] = wbd_dout_slave_t[master_mx_id[k]];
- wbd_ack_master[k] = wbd_ack_slave[master_mx_id[k]];
- wbd_err_master[k] = wbd_err_slave[master_mx_id[k]];
- wbd_rty_master[k] = wbd_rty_slave[master_mx_id[k]];
- end else begin
- wbd_dout_master_t[k] = 0;
- wbd_ack_master[k] = 0;
- wbd_err_master[k] = 0;
- wbd_rty_master[k] = 0;
- end
- end
- for(l = 0; l < WB_SLAVE; l = l + 1) begin
- if(slave_busy[l] == 1) begin
- wbd_din_slave_t[l] = wbd_din_master_t[slave_mx_id[l]];
- wbd_adr_slave_t[l] = wbd_adr_master_t[slave_mx_id[l]];
- wbd_be_slave_t[l] = wbd_be_master_t[slave_mx_id[l]];
- wbd_stb_slave[l] = wbd_stb_master[slave_mx_id[l]];
- wbd_we_slave[l] = wbd_we_master[slave_mx_id[l]];
- wbd_cyc_slave[l] = wbd_cyc_master[slave_mx_id[l]];
- end else begin
- wbd_din_slave_t[l] = 0;
- wbd_adr_slave_t[l] = 0;
- wbd_be_slave_t[l] = 0;
- wbd_stb_slave[l] = 0;
- wbd_we_slave[l] = 0;
- wbd_cyc_slave[l] = 0;
- end
- end
-end
-
-/*******************************************************
- Parsing through the master and deciding on mux connectio
- Step-1: analysis the master from 0 to total master
- Step-2: If the previously master is not busy,
- Then check for any new request from the master and
- check corresponding slave is free or not. If there is
- master request and requesting slave is free.
- Then set the master max id to slave id &
- requesting slave to master number & set the master
- and slave busy flag
- Step-3: If the previous state of master is busy and bus-cycle
- is de-asserted, then reset the master and corresponding
- slave busy flag
-
-*********************************************************/
-
-always @(negedge rst_n or posedge clk) begin
- if(rst_n == 0) begin
- master_busy <= 0;
- slave_busy <= 0;
- end else begin
- for(i = 0; i < WB_MASTER; i = i + 1) begin
- if(master_busy[i] == 0) begin
- if(wbd_stb_master[i] & slave_busy[wbd_taddr_master_t[i]] == 0) begin
- $display("Locking Master Id: %d for tar_master: %d, Total Master: %x ", i, wbd_taddr_master_t[i], wbd_taddr_master);
- slave_busy[wbd_taddr_master_t[i]] = 1;
- master_busy[i] = 1;
- end
- end else if(wbd_cyc_master[i] == 0) begin
- master_busy[i] <= 0;
- slave_busy[wbd_taddr_master_t[i]] <= 0;
- end
- end
- end
-end
-
-// Seperated non resetable two dimensional reg
-always @(posedge clk) begin
- for(n = 0; n < WB_MASTER; n = n + 1) begin
- if(master_busy[n] == 0) begin
- if(wbd_stb_master[n] & slave_busy[wbd_taddr_master_t[n]] == 0) begin
- master_mx_id[n] <= wbd_taddr_master_t[n];
- slave_mx_id [wbd_taddr_master_t[n]] <= n;
- // synopsys translate_off
- $display("%m:%t: Locking Master : %d with Slave : %d",$time,i,wbd_taddr_master_t[n]);
- // synopsys translate_on
- end
- end else if(wbd_cyc_master[n] == 0) begin
- if(master_busy[n] == 1) begin
- // synopsys translate_off
- $display("%m:%t: Releasing Master : %d with Slave : %d",$time,i,wbd_taddr_master_t[n]);
- // synopsys translate_on
- end
- end
- end
-end
-
-
-endmodule
diff --git a/verilog/rtl/lib/wb_stagging.sv b/verilog/rtl/lib/wb_stagging.sv
new file mode 100644
index 0000000..7c1330a
--- /dev/null
+++ b/verilog/rtl/lib/wb_stagging.sv
@@ -0,0 +1,148 @@
+//----------------------------------------------------------------------
+// This logic create a holding register for Wishbone interface.
+// This is usefull to break timing issue at interconnect
+//
+// Limitation: Due to stagging FF, Continous Burst of Wishbone will have one
+// cycle break between each transaction
+//----------------------------------------------------------------------
+//////////////////////////////////////////////////////////////////////
+//// ////
+//// Wishbone Stagging FF ////
+//// ////
+//// This file is part of the YIFive cores project ////
+//// http://www.opencores.org/cores/yifive/ ////
+//// ////
+//// Description ////
+//// This logic create a holding FF for Wishbone interface. ////
+//// This is usefull to break timing issue at interconnect ////
+//// ////
+//// Limitation: Due to stagging FF, Continous Burst of ////
+//// Wishbone will have one cycle break between each transaction ////
+//// ////
+//// To Do: ////
+//// nothing ////
+//// ////
+//// Author(s): ////
+//// - Dinesh Annayya, dinesha@opencores.org ////
+//// ////
+//// Revision : ////
+//// 0.1 - 12th June 2021, Dinesh A ////
+//// ////
+//////////////////////////////////////////////////////////////////////
+//// ////
+//// Copyright (C) 2000 Authors and OPENCORES.ORG ////
+//// ////
+//// This source file may be used and distributed without ////
+//// restriction provided that this copyright statement is not ////
+//// removed from the file and that any derivative work contains ////
+//// the original copyright notice and the associated disclaimer. ////
+//// ////
+//// This source file is free software; you can redistribute it ////
+//// and/or modify it under the terms of the GNU Lesser General ////
+//// Public License as published by the Free Software Foundation; ////
+//// either version 2.1 of the License, or (at your option) any ////
+//// later version. ////
+//// ////
+//// This source is distributed in the hope that it will be ////
+//// useful, but WITHOUT ANY WARRANTY; without even the implied ////
+//// warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR ////
+//// PURPOSE. See the GNU Lesser General Public License for more ////
+//// details. ////
+//// ////
+//// You should have received a copy of the GNU Lesser General ////
+//// Public License along with this source; if not, download it ////
+//// from http://www.opencores.org/lgpl.shtml ////
+//// ////
+//////////////////////////////////////////////////////////////////////
+
+
+module wb_stagging (
+ input logic clk_i,
+ input logic rst_n,
+ // WishBone Input master I/P
+ input logic [31:0] m_wbd_dat_i,
+ input logic [31:0] m_wbd_adr_i,
+ input logic [3:0] m_wbd_sel_i,
+ input logic m_wbd_we_i,
+ input logic m_wbd_cyc_i,
+ input logic m_wbd_stb_i,
+ output logic [31:0] m_wbd_dat_o,
+ output logic m_wbd_ack_o,
+ output logic m_wbd_err_o,
+
+ // Slave Interface
+ input logic [31:0] s_wbd_dat_i,
+ input logic s_wbd_ack_i,
+ input logic s_wbd_err_i,
+ output logic [31:0] s_wbd_dat_o,
+ output logic [31:0] s_wbd_adr_o,
+ output logic [3:0] s_wbd_sel_o,
+ output logic s_wbd_we_o,
+ output logic s_wbd_cyc_o,
+ output logic s_wbd_stb_o
+
+);
+
+logic holding_busy ; // Indicate Stagging for Free or not
+logic [31:0] m_wbd_dat_i_ff ; // Flopped vesion of m_wbd_dat_i
+logic [31:0] m_wbd_adr_i_ff ; // Flopped vesion of m_wbd_adr_i
+logic [3:0] m_wbd_sel_i_ff ; // Flopped vesion of m_wbd_sel_i
+logic m_wbd_we_i_ff ; // Flopped vesion of m_wbd_we_i
+logic m_wbd_cyc_i_ff ; // Flopped vesion of m_wbd_cyc_i
+logic m_wbd_stb_i_ff ; // Flopped vesion of m_wbd_stb_i
+logic [31:0] s_wbd_dat_i_ff ; // Flopped vesion of s_wbd_dat_i
+logic s_wbd_ack_i_ff ; // Flopped vesion of s_wbd_ack_i
+logic s_wbd_err_i_ff ; // Flopped vesion of s_wbd_err_i
+
+
+assign s_wbd_dat_o = m_wbd_dat_i_ff;
+assign s_wbd_adr_o = m_wbd_adr_i_ff;
+assign s_wbd_sel_o = m_wbd_sel_i_ff;
+assign s_wbd_we_o = m_wbd_we_i_ff;
+assign s_wbd_cyc_o = m_wbd_cyc_i_ff;
+assign s_wbd_stb_o = m_wbd_stb_i_ff;
+
+assign m_wbd_dat_o = s_wbd_dat_i_ff;
+assign m_wbd_ack_o = s_wbd_ack_i_ff;
+assign m_wbd_err_o = s_wbd_err_i_ff;
+
+always @(negedge rst_n or posedge clk_i)
+begin
+ if(rst_n == 1'b0) begin
+ holding_busy <= 1'b0;
+ m_wbd_dat_i_ff <= 'h0;
+ m_wbd_adr_i_ff <= 'h0;
+ m_wbd_sel_i_ff <= 'h0;
+ m_wbd_we_i_ff <= 'h0;
+ m_wbd_cyc_i_ff <= 'h0;
+ m_wbd_stb_i_ff <= 'h0;
+ s_wbd_dat_i_ff <= 'h0;
+ s_wbd_ack_i_ff <= 'h0;
+ s_wbd_err_i_ff <= 'h0;
+ end begin
+ s_wbd_dat_i_ff <= s_wbd_dat_i;
+ s_wbd_ack_i_ff <= s_wbd_ack_i;
+ s_wbd_err_i_ff <= s_wbd_err_i;
+ if(m_wbd_stb_i && holding_busy == 0 && m_wbd_ack_o == 0) begin
+ holding_busy <= 1'b1;
+ m_wbd_dat_i_ff <= m_wbd_dat_i;
+ m_wbd_adr_i_ff <= m_wbd_adr_i;
+ m_wbd_sel_i_ff <= m_wbd_sel_i;
+ m_wbd_we_i_ff <= m_wbd_we_i;
+ m_wbd_cyc_i_ff <= m_wbd_cyc_i;
+ m_wbd_stb_i_ff <= m_wbd_stb_i;
+ end else if (holding_busy && s_wbd_ack_i) begin
+ holding_busy <= 1'b0;
+ m_wbd_dat_i_ff <= 'h0;
+ m_wbd_adr_i_ff <= 'h0;
+ m_wbd_sel_i_ff <= 'h0;
+ m_wbd_we_i_ff <= 'h0;
+ m_wbd_cyc_i_ff <= 'h0;
+ m_wbd_stb_i_ff <= 'h0;
+ end
+ end
+end
+
+
+endmodule
+
diff --git a/verilog/rtl/spi_master/src/spim_clkgen.sv b/verilog/rtl/spi_master/src/spim_clkgen.sv
index 9c825a6..8c9fa83 100644
--- a/verilog/rtl/spi_master/src/spim_clkgen.sv
+++ b/verilog/rtl/spi_master/src/spim_clkgen.sv
@@ -58,16 +58,16 @@
input logic clk,
input logic rstn,
input logic en,
- input logic [7:0] cfg_sck_period,
+ input logic [5:0] cfg_sck_period,
output logic spi_clk,
output logic spi_fall,
output logic spi_rise
);
- logic [7:0] sck_half_period;
- logic [7:0] clk_cnt;
+ logic [5:0] sck_half_period;
+ logic [5:0] clk_cnt;
- assign sck_half_period = {1'b0, cfg_sck_period[7:1]};
+ assign sck_half_period = {1'b0, cfg_sck_period[5:1]};
// The first transition on the sck_toggle happens one SCK period
// after en is asserted
diff --git a/verilog/rtl/spi_master/src/spim_ctrl.sv b/verilog/rtl/spi_master/src/spim_ctrl.sv
index 8ce6524..5ae41ad 100644
--- a/verilog/rtl/spi_master/src/spim_ctrl.sv
+++ b/verilog/rtl/spi_master/src/spim_ctrl.sv
@@ -49,7 +49,7 @@
input logic rstn,
output logic eot,
- input logic [7:0] spi_clk_div,
+ input logic [5:0] spi_clk_div,
output logic [8:0] spi_status,
diff --git a/verilog/rtl/syntacore/scr1/src/top/scr1_dmem_wb.sv b/verilog/rtl/syntacore/scr1/src/top/scr1_dmem_wb.sv
index 85a0c5c..b9e893a 100644
--- a/verilog/rtl/syntacore/scr1/src/top/scr1_dmem_wb.sv
+++ b/verilog/rtl/syntacore/scr1/src/top/scr1_dmem_wb.sv
@@ -21,6 +21,9 @@
//// On power up, wishbone output are unkown as it ////
//// driven from fifo output. To avoid unknown ////
//// propgation, we are driving 'h0 when fifo empty ////
+//// v2: June 18, 2021, Dinesh A ////
+//// core and wishbone is made async and async fifo ////
+//// added to take care of domain cross-over ////
//// ////
//////////////////////////////////////////////////////////////////////
//// ////
@@ -60,8 +63,8 @@
module scr1_dmem_wb (
// Control Signals
- input logic rst_n,
- input logic clk,
+ input logic core_rst_n, // core reset
+ input logic core_clk, // Core clock
// Core Interface
output logic dmem_req_ack,
@@ -74,6 +77,8 @@
output logic [1:0] dmem_resp,
// WB Interface
+ input logic wb_rst_n, // wishbone reset
+ input logic wb_clk, // wishbone clock
output logic wbd_stb_o, // strobe/request
output logic [SCR1_WB_WIDTH-1:0] wbd_adr_o, // address
output logic wbd_we_o, // write
@@ -88,31 +93,19 @@
//-------------------------------------------------------------------------------
// Local Parameters
//-------------------------------------------------------------------------------
-`ifndef SCR1_DMEM_WB_OUT_BP
-localparam SCR1_FIFO_WIDTH = 2;
-localparam SCR1_FIFO_CNT_WIDTH = 2;
-`endif // SCR1_DMEM_WB_OUT_BP
//-------------------------------------------------------------------------------
// Local type declaration
//-------------------------------------------------------------------------------
-typedef enum logic {
- SCR1_FSM_ADDR = 1'b0,
- SCR1_FSM_DATA = 1'b1,
- SCR1_FSM_ERR = 1'bx
-} type_scr1_fsm_e;
typedef struct packed {
+ logic [3:0] hbel;
logic hwrite;
logic [2:0] hwidth;
logic [SCR1_WB_WIDTH-1:0] haddr;
logic [SCR1_WB_WIDTH-1:0] hwdata;
} type_scr1_req_fifo_s;
-typedef struct packed {
- logic [2:0] hwidth;
- logic [1:0] haddr;
-} type_scr1_data_fifo_s;
typedef struct packed {
logic hresp;
@@ -238,85 +231,18 @@
//-------------------------------------------------------------------------------
logic req_fifo_rd;
logic req_fifo_wr;
-logic req_fifo_up;
-`ifdef SCR1_DMEM_WB_OUT_BP
-type_scr1_req_fifo_s req_fifo_new;
-type_scr1_req_fifo_s req_fifo_r;
-type_scr1_req_fifo_s [0:0] req_fifo;
-`else // SCR1_DMEM_WB_OUT_BP
-type_scr1_req_fifo_s [0:SCR1_FIFO_WIDTH-1] req_fifo;
-type_scr1_req_fifo_s [0:SCR1_FIFO_WIDTH-1] req_fifo_new;
-logic [SCR1_FIFO_CNT_WIDTH-1:0] req_fifo_cnt;
-logic [SCR1_FIFO_CNT_WIDTH-1:0] req_fifo_cnt_new;
-`endif // SCR1_DMEM_WB_OUT_BP
logic req_fifo_empty;
logic req_fifo_full;
-type_scr1_data_fifo_s data_fifo;
-type_scr1_resp_fifo_s resp_fifo;
-logic resp_fifo_hready;
+
+logic resp_fifo_rd;
+logic resp_fifo_empty;
+logic resp_fifo_full;
+
//-------------------------------------------------------------------------------
-// Interface to Core
+// REQ_FIFO (CORE to WB)
//-------------------------------------------------------------------------------
-assign dmem_req_ack = ~req_fifo_full;
-assign req_fifo_wr = ~req_fifo_full & dmem_req;
-
-assign dmem_rdata = (resp_fifo_hready) ? scr1_conv_wb2mem_rdata(resp_fifo.hwidth, resp_fifo.haddr, resp_fifo.hrdata) : 'h0;
-
-assign dmem_resp = (resp_fifo_hready)
- ? (resp_fifo.hresp == 1'b1)
- ? SCR1_MEM_RESP_RDY_OK
- : SCR1_MEM_RESP_RDY_ER
- : SCR1_MEM_RESP_NOTRDY ;
-
-//-------------------------------------------------------------------------------
-// REQ_FIFO
-//-------------------------------------------------------------------------------
-`ifdef SCR1_DMEM_WB_OUT_BP
-always_ff @(negedge rst_n, posedge clk) begin
- if (~rst_n) begin
- req_fifo_full <= 1'b0;
- end else begin
- if (~req_fifo_full) begin
- req_fifo_full <= dmem_req & ~req_fifo_rd;
- end else begin
- req_fifo_full <= ~req_fifo_rd;
- end
- end
-end
-assign req_fifo_empty = ~(req_fifo_full | dmem_req);
-
-assign req_fifo_up = ~req_fifo_rd & req_fifo_wr;
-always_ff @(posedge clk) begin
- if (req_fifo_up) begin
- req_fifo_r <= req_fifo_new;
- end
-end
-
-assign req_fifo_new.hwrite = dmem_req ? (dmem_cmd == SCR1_MEM_CMD_WR) : 1'b0;
-assign req_fifo_new.hwidth = dmem_req ? scr1_conv_mem2wb_width(dmem_width) : '0;
-assign req_fifo_new.haddr = dmem_req ? dmem_addr : '0;
-assign req_fifo_new.hwdata = (dmem_req & (dmem_cmd == SCR1_MEM_CMD_WR))
- ? scr1_conv_mem2wb_wdata(dmem_addr[1:0], dmem_width, dmem_wdata)
- : '0;
-assign req_fifo[0] = (req_fifo_full) ? req_fifo_r: req_fifo_new;
-
-//-------------------------------------------------------------------------------
-// Register Data from response path - Used by Read path logic
-//-------------------------------------------------------------------------------
-always_ff @(posedge clk) begin
- if (wbd_ack_i) begin
- if (~req_fifo_empty) begin
- data_fifo.hwidth <= req_fifo[0].hwidth;
- data_fifo.haddr <= req_fifo[0].haddr[1:0];
- end
- end
-end
-
-`else // SCR1_DMEM_WB_OUT_BP
-
-
wire hwrite_in = (dmem_cmd == SCR1_MEM_CMD_WR);
wire [2:0] hwidth_in = scr1_conv_mem2wb_width(dmem_width);
wire [SCR1_WB_WIDTH-1:0] haddr_in = dmem_addr;
@@ -339,47 +265,46 @@
end
-wire [SCR1_WB_WIDTH+SCR1_WB_WIDTH+3+4:0] req_fifo_din = {hbel_in,hwrite_in,hwidth_in,haddr_in,hwdata_in};
-wire [SCR1_WB_WIDTH+SCR1_WB_WIDTH+3+4:0] req_fifo_dout;
+//-------------------------------------------------------------------------------
+// REQ_FIFO (WB to CORE)
+//-------------------------------------------------------------------------------
+type_scr1_req_fifo_s req_fifo_din;
+type_scr1_req_fifo_s req_fifo_dout;
- sync_fifo #(
+
+assign dmem_req_ack = ~req_fifo_full;
+assign req_fifo_wr = ~req_fifo_full & dmem_req;
+
+//pack data in
+assign req_fifo_din.hbel = hbel_in;
+assign req_fifo_din.hwrite = hwrite_in;
+assign req_fifo_din.hwidth = hwidth_in;
+assign req_fifo_din.haddr = haddr_in;
+assign req_fifo_din.hwdata = hwdata_in;
+
+
+ async_fifo #(
.W(SCR1_WB_WIDTH+SCR1_WB_WIDTH+3+1+4), // Data Width
- .D(2) // FIFO DEPTH
+ .DP(4), // FIFO DEPTH
+ .WR_FAST(1), // We need FF'ed Full
+ .RD_FAST(1) // We need FF'ed Empty
) u_req_fifo(
+ // Writc Clock
+ .wr_clk (core_clk ),
+ .wr_reset_n (core_rst_n ),
+ .wr_en (req_fifo_wr ),
+ .wr_data (req_fifo_din ),
+ .full (req_fifo_full ),
+ .afull ( ),
- .rd_data (req_fifo_dout ),
-
- .reset_n (rst_n ),
- .clk (clk ),
- .wr_en (req_fifo_wr ), // Write
- .rd_en (req_fifo_rd ), // Read
- .wr_data (req_fifo_din ),
- .full (req_fifo_full ),
- .empty (req_fifo_empty )
-);
-
-//-------------------------------------------------------------------------------
-// Register Data from response path - Used by Read path logic
-//-------------------------------------------------------------------------------
-wire hwrite_out;
-wire [2:0] hwidth_out;
-wire [SCR1_WB_WIDTH-1:0] haddr_out;
-wire [SCR1_WB_WIDTH-1:0] hwdata_out;
-wire [3:0] hbel_out;
-
-
-assign {hbel_out,hwrite_out,hwidth_out,haddr_out,hwdata_out} = req_fifo_dout;
-
-always_ff @(posedge clk) begin
- if (wbd_ack_i) begin
- if (~req_fifo_empty) begin
- data_fifo.hwidth <= hwidth_out;
- data_fifo.haddr <= haddr_out[1:0];
- end
- end
-end
-
-`endif // SCR1_DMEM_WB_OUT_BP
+ // RD Clock
+ .rd_clk (wb_clk ),
+ .rd_reset_n (wb_rst_n ),
+ .rd_en (req_fifo_rd ),
+ .empty (req_fifo_empty ),
+ .aempty ( ),
+ .rd_data (req_fifo_dout )
+ );
always_comb begin
@@ -390,64 +315,62 @@
end
-//-------------------------------------------------------------------------------
-// FIFO response
-//-------------------------------------------------------------------------------
-`ifdef SCR1_DMEM_WB_IN_BP
-
-assign resp_fifo_hready = wbd_ack_i;
-assign resp_fifo.hresp = (wbd_err_i) ? 1'b0 : 1'b1;
-assign resp_fifo.hwidth = data_fifo.hwidth;
-assign resp_fifo.haddr = data_fifo.haddr;
-assign resp_fifo.hrdata = wbd_dat_i;
-
-assign wbd_stb_o = ~req_fifo_empty;
-assign wbd_adr_o = req_fifo[0].haddr;
-assign wbd_we_o = req_fifo[0].hwrite;
-assign wbd_dat_o = req_fifo[0].hwdata;
-
-always_comb begin
- wbd_sel_o = 0;
- case (req_fifo[0].hwidth)
- SCR1_DSIZE_8B : begin
- wbd_sel_o = 4'b0001 << req_fifo[0].haddr[1:0];
- end
- SCR1_DSIZE_16B : begin
- wbd_sel_o = 4'b0011 << req_fifo[0].haddr[1:0];
- end
- SCR1_DSIZE_32B : begin
- wbd_sel_o = 4'b1111;
- end
- endcase
-end
-`else // SCR1_DMEM_WB_IN_BP
-always_ff @(negedge rst_n, posedge clk) begin
- if (~rst_n) begin
- resp_fifo_hready <= 1'b0;
- end else begin
- resp_fifo_hready <= wbd_ack_i ;
- end
-end
-
-always_ff @(posedge clk) begin
- if (wbd_ack_i) begin
- resp_fifo.hresp <= (wbd_err_i) ? 1'b0 : 1'b1;
- resp_fifo.hwidth <= hwidth_out;
- resp_fifo.haddr <= haddr_out[1:0];
- resp_fifo.hrdata <= (wbd_we_o) ? 'h0: wbd_dat_i;
- end
-end
-
-
assign wbd_stb_o = ~req_fifo_empty;
// To avoid unknown progating the design, driven zero when fifo is empty
-assign wbd_adr_o = (req_fifo_empty) ? 'h0 : haddr_out;
-assign wbd_we_o = (req_fifo_empty) ? 'h0 : hwrite_out;
-assign wbd_dat_o = (req_fifo_empty) ? 'h0 : hwdata_out;
-assign wbd_sel_o = (req_fifo_empty) ? 'h0 : hbel_out;
+assign wbd_adr_o = (req_fifo_empty) ? 'h0 : req_fifo_dout.haddr;
+assign wbd_we_o = (req_fifo_empty) ? 'h0 : req_fifo_dout.hwrite;
+assign wbd_dat_o = (req_fifo_empty) ? 'h0 : req_fifo_dout.hwdata;
+assign wbd_sel_o = (req_fifo_empty) ? 'h0 : req_fifo_dout.hbel;
-`endif // SCR1_DMEM_WB_IN_BP
+
+//-------------------------------------------------------------------------------
+// Response path - Used by Read path logic
+//-------------------------------------------------------------------------------
+type_scr1_resp_fifo_s resp_fifo_din;
+type_scr1_resp_fifo_s resp_fifo_dout;
+
+
+assign resp_fifo_din.hresp = (wbd_err_i) ? 1'b0 : 1'b1;
+assign resp_fifo_din.hwidth = req_fifo_dout.hwidth;
+assign resp_fifo_din.haddr = req_fifo_dout.haddr[1:0];
+assign resp_fifo_din.hrdata = (wbd_we_o) ? 'h0: wbd_dat_i;
+
+ async_fifo #(
+ .W(SCR1_WB_WIDTH+2+3+1), // Data Width
+ .DP(4), // FIFO DEPTH
+ .WR_FAST(1), // We need FF'ed Full
+ .RD_FAST(1) // We need FF'ed Empty
+ ) u_res_fifo(
+ // Writc Clock
+ .wr_clk (wb_clk ),
+ .wr_reset_n (wb_rst_n ),
+ .wr_en (wbd_ack_i ),
+ .wr_data (resp_fifo_din ),
+ .full ( ), // Assmed FIFO will never be full as it's Response a Single Request
+ .afull ( ),
+
+ // RD Clock
+ .rd_clk (core_clk ),
+ .rd_reset_n (core_rst_n ),
+ .rd_en (resp_fifo_rd ),
+ .empty (resp_fifo_empty ),
+ .aempty ( ),
+ .rd_data (resp_fifo_dout )
+ );
+
+
+
+assign resp_fifo_rd = !resp_fifo_empty;
+
+assign dmem_rdata = (resp_fifo_rd) ? scr1_conv_wb2mem_rdata(resp_fifo_dout.hwidth, resp_fifo_dout.haddr, resp_fifo_dout.hrdata) : 'h0;
+
+assign dmem_resp = (resp_fifo_rd)
+ ? (resp_fifo_dout.hresp == 1'b1)
+ ? SCR1_MEM_RESP_RDY_OK
+ : SCR1_MEM_RESP_RDY_ER
+ : SCR1_MEM_RESP_NOTRDY ;
+
diff --git a/verilog/rtl/syntacore/scr1/src/top/scr1_imem_wb.sv b/verilog/rtl/syntacore/scr1/src/top/scr1_imem_wb.sv
index d91c9e3..fb6c137 100644
--- a/verilog/rtl/syntacore/scr1/src/top/scr1_imem_wb.sv
+++ b/verilog/rtl/syntacore/scr1/src/top/scr1_imem_wb.sv
@@ -21,6 +21,9 @@
//// On power up, wishbone output are unkown as it ////
//// driven from fifo output. To avoid unknown ////
//// propgation, we are driving 'h0 when fifo empty ////
+//// v2: June 18, 2021, Dinesh A ////
+//// core and wishbone is made async and async fifo ////
+//// added to take care of domain cross-over ////
//// ////
//////////////////////////////////////////////////////////////////////
//// ////
@@ -60,8 +63,8 @@
module scr1_imem_wb (
// Control Signals
- input logic rst_n,
- input logic clk,
+ input logic core_rst_n, // core reset
+ input logic core_clk, // Core clock
// Core Interface
output logic imem_req_ack,
@@ -71,6 +74,8 @@
output logic [1:0] imem_resp,
// WB Interface
+ input logic wb_rst_n, // wishbone reset
+ input logic wb_clk, // wishbone clock
output logic wbd_stb_o, // strobe/request
output logic [SCR1_WB_WIDTH-1:0] wbd_adr_o, // address
output logic wbd_we_o, // write
@@ -85,19 +90,10 @@
//-------------------------------------------------------------------------------
// Local parameters declaration
//-------------------------------------------------------------------------------
-`ifndef SCR1_IMEM_WB_OUT_BP
-localparam SCR1_FIFO_WIDTH = 2;
-localparam SCR1_FIFO_CNT_WIDTH = $clog2(SCR1_FIFO_WIDTH+1);
-`endif // SCR1_IMEM_WB_OUT_BP
//-------------------------------------------------------------------------------
// Local types declaration
//-------------------------------------------------------------------------------
-typedef enum logic {
- SCR1_FSM_ADDR = 1'b0,
- SCR1_FSM_DATA = 1'b1,
- SCR1_FSM_ERR = 1'bx
-} type_scr1_fsm_e;
typedef struct packed {
logic [SCR1_WB_WIDTH-1:0] haddr;
@@ -111,86 +107,57 @@
//-------------------------------------------------------------------------------
// Local signal declaration
//-------------------------------------------------------------------------------
-type_scr1_fsm_e fsm;
+
+//-------------------------------------------------------------------------------
+// Request FIFO
+// ------------------------------------------------------------------------------
logic req_fifo_rd;
logic req_fifo_wr;
-logic req_fifo_up;
-`ifdef SCR1_IMEM_WB_OUT_BP
-type_scr1_req_fifo_s req_fifo_r;
-type_scr1_req_fifo_s [0:0] req_fifo;
-`else // SCR1_IMEM_WB_OUT_BP
-logic [SCR1_WB_WIDTH-1:0] req_fifo_dout;
-`endif // SCR1_IMEM_WB_OUT_BP
-
logic req_fifo_empty;
logic req_fifo_full;
-type_scr1_resp_fifo_s resp_fifo;
-logic resp_fifo_hready;
-//-------------------------------------------------------------------------------
-// Interface to Core
-//-------------------------------------------------------------------------------
-assign imem_req_ack = ~req_fifo_full;
-assign req_fifo_wr = ~req_fifo_full & imem_req;
+//-----------------------------------------------------
+// Response FIFO (READ PATH
+// ----------------------------------------------------
+logic resp_fifo_empty;
+logic resp_fifo_rd;
-assign imem_rdata = resp_fifo.hrdata;
-assign imem_resp = (resp_fifo_hready)
- ? (resp_fifo.hresp == 1'b1)
- ? SCR1_MEM_RESP_RDY_OK
- : SCR1_MEM_RESP_RDY_ER
- : SCR1_MEM_RESP_NOTRDY;
//-------------------------------------------------------------------------------
// REQ_FIFO
//-------------------------------------------------------------------------------
-`ifdef SCR1_IMEM_WB_OUT_BP
-always_ff @(negedge rst_n, posedge clk) begin
- if (~rst_n) begin
- req_fifo_full <= 1'b0;
- end else begin
- if (~req_fifo_full) begin
- req_fifo_full <= imem_req & ~req_fifo_rd;
- end else begin
- req_fifo_full <= ~req_fifo_rd;
- end
- end
-end
-assign req_fifo_empty = ~(req_fifo_full | imem_req);
+type_scr1_req_fifo_s req_fifo_din;
+type_scr1_req_fifo_s req_fifo_dout;
-assign req_fifo_up = ~req_fifo_rd & req_fifo_wr;
-always_ff @(posedge clk) begin
- if (req_fifo_up) begin
- req_fifo_r.haddr <= imem_addr;
- end
-end
+assign req_fifo_wr = ~req_fifo_full & imem_req;
+assign imem_req_ack = ~req_fifo_full;
-assign req_fifo[0] = (req_fifo_full) ? req_fifo_r : imem_addr;
+assign req_fifo_din.haddr = imem_addr;
-`else // SCR1_IMEM_WB_OUT_BP
-
-
- sync_fifo #(
+ async_fifo #(
.W(SCR1_WB_WIDTH), // Data Width
- .D(2) // FIFO DEPTH
+ .DP(4), // FIFO DEPTH
+ .WR_FAST(1), // We need FF'ed Full
+ .RD_FAST(1) // We need FF'ed Empty
) u_req_fifo(
+ // Writc Clock
+ .wr_clk (core_clk ),
+ .wr_reset_n (core_rst_n ),
+ .wr_en (req_fifo_wr ),
+ .wr_data (req_fifo_din ),
+ .full (req_fifo_full ),
+ .afull ( ),
- .rd_data (req_fifo_dout ),
-
- .reset_n (rst_n ),
- .clk (clk ),
- .wr_en (req_fifo_wr ), // Write
- .rd_en (req_fifo_rd ), // Read
- .wr_data (imem_addr ),
- .full (req_fifo_full ),
- .empty (req_fifo_empty )
-);
-
-
-
-
-`endif // SCR1_IMEM_WB_OUT_BP
+ // RD Clock
+ .rd_clk (wb_clk ),
+ .rd_reset_n (wb_rst_n ),
+ .rd_en (req_fifo_rd ),
+ .empty (req_fifo_empty ),
+ .aempty ( ),
+ .rd_data (req_fifo_dout )
+ );
always_comb begin
@@ -200,44 +167,53 @@
end
end
-//-------------------------------------------------------------------------------
-// FIFO response
-//-------------------------------------------------------------------------------
-`ifdef SCR1_IMEM_WB_IN_BP
-assign resp_fifo_hready = wbd_ack_i;
-assign resp_fifo.hresp = (wbd_err_i) ? 1'b0 : 1'b1;
-assign resp_fifo.hrdata = wbd_dat_i;
-assign wbd_stb_o = ~req_fifo_empty;
-assign wbd_adr_o = req_fifo[0];
-assign wbd_we_o = 0; // Only Read supported
-assign wbd_dat_o = 32'h0; // No Write
-assign wbd_sel_o = 4'b1111; // Only Read allowed in imem i/f
-
-
-`else // SCR1_IMEM_WB_IN_BP
-always_ff @(negedge rst_n, posedge clk) begin
- if (~rst_n) begin
- resp_fifo_hready <= 1'b0;
- end else begin
- resp_fifo_hready <= wbd_ack_i ;
- end
-end
-
-always_ff @(posedge clk) begin
- if (wbd_ack_i) begin
- resp_fifo.hresp <= (wbd_err_i) ? 1'b0 : 1'b1;
- resp_fifo.hrdata <= wbd_dat_i;
- end
-end
-
assign wbd_stb_o = ~req_fifo_empty;
// On Power, to avoid unknow propgating the value
-assign wbd_adr_o = (req_fifo_empty) ? 'h0 : req_fifo_dout;
+assign wbd_adr_o = (req_fifo_empty) ? 'h0 : req_fifo_dout.haddr;
assign wbd_we_o = 0; // Only Read supported
assign wbd_dat_o = 32'h0; // No Write
assign wbd_sel_o = 4'b1111; // Only Read allowed in imem i/f
-`endif // SCR1_IMEM_WB_IN_BP
+//-------------------------------------------------------------------------------
+// Response path - Used by Read path logic
+//-------------------------------------------------------------------------------
+type_scr1_resp_fifo_s resp_fifo_din;
+type_scr1_resp_fifo_s resp_fifo_dout;
+assign resp_fifo_din.hresp = (wbd_err_i) ? 1'b0 : 1'b1;
+assign resp_fifo_din.hrdata = wbd_dat_i;
+
+ async_fifo #(
+ .W(SCR1_WB_WIDTH+1), // Data Width
+ .DP(4), // FIFO DEPTH
+ .WR_FAST(1), // We need FF'ed Full
+ .RD_FAST(1) // We need FF'ed Empty
+ ) u_res_fifo(
+ // Writc Clock
+ .wr_clk (wb_clk ),
+ .wr_reset_n (wb_rst_n ),
+ .wr_en (wbd_ack_i ),
+ .wr_data (resp_fifo_din ),
+ .full ( ), // Assmed FIFO will never be full as it's Response a Single Request
+ .afull ( ),
+
+ // RD Clock
+ .rd_clk (core_clk ),
+ .rd_reset_n (core_rst_n ),
+ .rd_en (resp_fifo_rd ),
+ .empty (resp_fifo_empty ),
+ .aempty ( ),
+ .rd_data (resp_fifo_dout )
+ );
+
+
+assign resp_fifo_rd = !resp_fifo_empty;
+assign imem_rdata = resp_fifo_dout.hrdata;
+
+assign imem_resp = (resp_fifo_rd)
+ ? (resp_fifo_dout.hresp == 1'b1)
+ ? SCR1_MEM_RESP_RDY_OK
+ : SCR1_MEM_RESP_RDY_ER
+ : SCR1_MEM_RESP_NOTRDY ;
`ifdef SCR1_TRGT_SIMULATION
diff --git a/verilog/rtl/syntacore/scr1/src/top/scr1_top_wb.sv b/verilog/rtl/syntacore/scr1/src/top/scr1_top_wb.sv
index 97f565c..d72afd1 100644
--- a/verilog/rtl/syntacore/scr1/src/top/scr1_top_wb.sv
+++ b/verilog/rtl/syntacore/scr1/src/top/scr1_top_wb.sv
@@ -17,6 +17,9 @@
//// Revision : ////
//// v0: June 7, 2021, Dinesh A ////
//// wishbone integration ////
+//// v1: June 17, 2021, Dinesh A ////
+//// core and wishbone clock domain are seperated ////
+//// Async fifo added in imem and dmem path ////
//// ////
//////////////////////////////////////////////////////////////////////
//// ////
@@ -69,7 +72,7 @@
input logic cpu_rst_n, // CPU Reset (Core Reset)
input logic test_mode, // Test mode
input logic test_rst_n, // Test mode's reset
- input logic clk, // System clock
+ input logic core_clk, // Core clock
input logic rtc_clk, // Real-time clock
`ifdef SCR1_DBG_EN
output logic sys_rst_n_o, // External System Reset output
@@ -103,6 +106,8 @@
output logic tdo_en,
`endif // SCR1_DBG_EN
+ input logic wb_rst_n, // Wish bone reset
+ input logic wb_clk, // wish bone clock
// Instruction Memory Interface
output logic wbd_imem_stb_o, // strobe/request
output logic [SCR1_WB_WIDTH-1:0] wbd_imem_adr_o, // address
@@ -219,7 +224,7 @@
.STAGES_AMOUNT (SCR1_CLUSTER_TOP_RST_SYNC_STAGES_NUM)
) i_pwrup_rstn_reset_sync (
.rst_n (pwrup_rst_n ),
- .clk (clk ),
+ .clk (core_clk ),
.test_rst_n (test_rst_n ),
.test_mode (test_mode ),
.rst_n_in (1'b1 ),
@@ -231,7 +236,7 @@
.STAGES_AMOUNT (SCR1_CLUSTER_TOP_RST_SYNC_STAGES_NUM)
) i_rstn_reset_sync (
.rst_n (pwrup_rst_n ),
- .clk (clk ),
+ .clk (core_clk ),
.test_rst_n (test_rst_n ),
.test_mode (test_mode ),
.rst_n_in (rst_n ),
@@ -243,7 +248,7 @@
.STAGES_AMOUNT (SCR1_CLUSTER_TOP_RST_SYNC_STAGES_NUM)
) i_cpu_rstn_reset_sync (
.rst_n (pwrup_rst_n ),
- .clk (clk ),
+ .clk (core_clk ),
.test_rst_n (test_rst_n ),
.test_mode (test_mode ),
.rst_n_in (cpu_rst_n ),
@@ -270,7 +275,7 @@
.cpu_rst_n (cpu_rst_n_sync ),
.test_mode (test_mode ),
.test_rst_n (test_rst_n ),
- .clk (clk ),
+ .clk (core_clk ),
.core_rst_n_o (core_rst_n_local ),
.core_rdc_qlfy_o ( ),
`ifdef SCR1_DBG_EN
@@ -333,7 +338,7 @@
scr1_tcm #(
.SCR1_TCM_SIZE (`SCR1_DMEM_AWIDTH'(~SCR1_TCM_ADDR_MASK + 1'b1))
) i_tcm (
- .clk (clk ),
+ .clk (core_clk ),
.rst_n (core_rst_n_local),
// Instruction interface to TCM
@@ -362,7 +367,7 @@
scr1_timer i_timer (
// Common
.rst_n (core_rst_n_local ),
- .clk (clk ),
+ .clk (core_clk ),
.rtc_clk (rtc_clk ),
// Memory interface
@@ -392,7 +397,7 @@
`endif // SCR1_TCM_EN
) i_imem_router (
.rst_n (core_rst_n_local ),
- .clk (clk ),
+ .clk (core_clk ),
// Interface to core
.imem_req_ack (core_imem_req_ack),
.imem_req (core_imem_req ),
@@ -447,7 +452,7 @@
) i_dmem_router (
.rst_n (core_rst_n_local ),
- .clk (clk ),
+ .clk (core_clk ),
// Interface to core
.dmem_req_ack (core_dmem_req_ack ),
.dmem_req (core_dmem_req ),
@@ -502,8 +507,8 @@
// Instruction memory WB bridge
//-------------------------------------------------------------------------------
scr1_imem_wb i_imem_wb (
- .rst_n (core_rst_n_local ),
- .clk (clk ),
+ .core_rst_n (core_rst_n_local ),
+ .core_clk (core_clk ),
// Interface to imem router
.imem_req_ack (wb_imem_req_ack ),
.imem_req (wb_imem_req ),
@@ -511,6 +516,8 @@
.imem_rdata (wb_imem_rdata ),
.imem_resp (wb_imem_resp ),
// WB interface
+ .wb_rst_n (wb_rst_n ),
+ .wb_clk (wb_clk ),
.wbd_stb_o (wbd_imem_stb_o ),
.wbd_adr_o (wbd_imem_adr_o ),
.wbd_we_o (wbd_imem_we_o ),
@@ -526,8 +533,8 @@
// Data memory WB bridge
//-------------------------------------------------------------------------------
scr1_dmem_wb i_dmem_wb (
- .rst_n (core_rst_n_local ),
- .clk (clk ),
+ .core_rst_n (core_rst_n_local ),
+ .core_clk (core_clk ),
// Interface to dmem router
.dmem_req_ack (wb_dmem_req_ack ),
.dmem_req (wb_dmem_req ),
@@ -538,6 +545,8 @@
.dmem_rdata (wb_dmem_rdata ),
.dmem_resp (wb_dmem_resp ),
// WB interface
+ .wb_rst_n (wb_rst_n ),
+ .wb_clk (wb_clk ),
.wbd_stb_o (wbd_dmem_stb_o ),
.wbd_adr_o (wbd_dmem_adr_o ),
.wbd_we_o (wbd_dmem_we_o ),
diff --git a/verilog/rtl/uprj_netlists.v b/verilog/rtl/uprj_netlists.v
index b97154e..689eca3 100644
--- a/verilog/rtl/uprj_netlists.v
+++ b/verilog/rtl/uprj_netlists.v
@@ -46,6 +46,7 @@
`include "digital_core/src/glbl_cfg.sv"
`include "digital_core/src/digital_core.sv"
+ `include "lib/wb_stagging.sv"
`include "wb_interconnect/src/wb_arb.sv"
`include "wb_interconnect/src/wb_interconnect.sv"
diff --git a/verilog/rtl/user_project_wrapper.v b/verilog/rtl/user_project_wrapper.v
index 976047b..8e7547b 100644
--- a/verilog/rtl/user_project_wrapper.v
+++ b/verilog/rtl/user_project_wrapper.v
@@ -97,7 +97,7 @@
.wb_clk_i(wb_clk_i),
.wb_rst_i(wb_rst_i),
- .rtc_clk(user_clock2),
+ .user_clock2(user_clock2),
// MGMT SoC Wishbone Slave
diff --git a/verilog/rtl/wb_interconnect/src/wb_interconnect.sv b/verilog/rtl/wb_interconnect/src/wb_interconnect.sv
index b3552ec..b2e1df2 100644
--- a/verilog/rtl/wb_interconnect/src/wb_interconnect.sv
+++ b/verilog/rtl/wb_interconnect/src/wb_interconnect.sv
@@ -17,6 +17,9 @@
//// ////
//// Revision : ////
//// 0.1 - 12th June 2021, Dinesh A ////
+//// 0.2 - 17th June 2021, Dinesh A ////
+//// Stagging FF added at Slave Interface to break ////
+//// path ////
//// ////
//////////////////////////////////////////////////////////////////////
//// ////
@@ -238,43 +241,43 @@
assign m2_wbd_ack_o = m2_wb_rd.wbd_ack;
assign m2_wbd_err_o = m2_wb_rd.wbd_err;
-assign s0_wb_rd.wbd_dat = s0_wbd_dat_i ;
-assign s0_wb_rd.wbd_ack = s0_wbd_ack_i ;
-assign s0_wb_rd.wbd_err = s0_wbd_err_i ;
-
-assign s1_wb_rd.wbd_dat = s1_wbd_dat_i ;
-assign s1_wb_rd.wbd_ack = s1_wbd_ack_i ;
-assign s1_wb_rd.wbd_err = s1_wbd_err_i ;
-
-assign s2_wb_rd.wbd_dat = s2_wbd_dat_i ;
-assign s2_wb_rd.wbd_ack = s2_wbd_ack_i ;
-assign s2_wb_rd.wbd_err = s2_wbd_err_i ;
-
-
//----------------------------------------
// Slave Mapping
// -------------------------------------
+// Masked Now and added stagging FF now
+// assign s0_wbd_dat_o = s0_wb_wr.wbd_dat ;
+// assign s0_wbd_adr_o = s0_wb_wr.wbd_adr ;
+// assign s0_wbd_sel_o = s0_wb_wr.wbd_sel ;
+// assign s0_wbd_we_o = s0_wb_wr.wbd_we ;
+// assign s0_wbd_cyc_o = s0_wb_wr.wbd_cyc ;
+// assign s0_wbd_stb_o = s0_wb_wr.wbd_stb ;
+//
+// assign s1_wbd_dat_o = s1_wb_wr.wbd_dat ;
+// assign s1_wbd_adr_o = s1_wb_wr.wbd_adr ;
+// assign s1_wbd_sel_o = s1_wb_wr.wbd_sel ;
+// assign s1_wbd_we_o = s1_wb_wr.wbd_we ;
+// assign s1_wbd_cyc_o = s1_wb_wr.wbd_cyc ;
+// assign s1_wbd_stb_o = s1_wb_wr.wbd_stb ;
+//
+// assign s2_wbd_dat_o = s2_wb_wr.wbd_dat ;
+// assign s2_wbd_adr_o = s2_wb_wr.wbd_adr ;
+// assign s2_wbd_sel_o = s2_wb_wr.wbd_sel ;
+// assign s2_wbd_we_o = s2_wb_wr.wbd_we ;
+// assign s2_wbd_cyc_o = s2_wb_wr.wbd_cyc ;
+// assign s2_wbd_stb_o = s2_wb_wr.wbd_stb ;
+//
+// assign s0_wb_rd.wbd_dat = s0_wbd_dat_i ;
+// assign s0_wb_rd.wbd_ack = s0_wbd_ack_i ;
+// assign s0_wb_rd.wbd_err = s0_wbd_err_i ;
+//
+// assign s1_wb_rd.wbd_dat = s1_wbd_dat_i ;
+// assign s1_wb_rd.wbd_ack = s1_wbd_ack_i ;
+// assign s1_wb_rd.wbd_err = s1_wbd_err_i ;
+//
+// assign s2_wb_rd.wbd_dat = s2_wbd_dat_i ;
+// assign s2_wb_rd.wbd_ack = s2_wbd_ack_i ;
+// assign s2_wb_rd.wbd_err = s2_wbd_err_i ;
-assign s0_wbd_dat_o = s0_wb_wr.wbd_dat ;
-assign s0_wbd_adr_o = s0_wb_wr.wbd_adr ;
-assign s0_wbd_sel_o = s0_wb_wr.wbd_sel ;
-assign s0_wbd_we_o = s0_wb_wr.wbd_we ;
-assign s0_wbd_cyc_o = s0_wb_wr.wbd_cyc ;
-assign s0_wbd_stb_o = s0_wb_wr.wbd_stb ;
-
-assign s1_wbd_dat_o = s1_wb_wr.wbd_dat ;
-assign s1_wbd_adr_o = s1_wb_wr.wbd_adr ;
-assign s1_wbd_sel_o = s1_wb_wr.wbd_sel ;
-assign s1_wbd_we_o = s1_wb_wr.wbd_we ;
-assign s1_wbd_cyc_o = s1_wb_wr.wbd_cyc ;
-assign s1_wbd_stb_o = s1_wb_wr.wbd_stb ;
-
-assign s2_wbd_dat_o = s2_wb_wr.wbd_dat ;
-assign s2_wbd_adr_o = s2_wb_wr.wbd_adr ;
-assign s2_wbd_sel_o = s2_wb_wr.wbd_sel ;
-assign s2_wbd_we_o = s2_wb_wr.wbd_we ;
-assign s2_wbd_cyc_o = s2_wb_wr.wbd_cyc ;
-assign s2_wbd_stb_o = s2_wb_wr.wbd_stb ;
//
// arbitor
@@ -284,9 +287,9 @@
wb_arb u_wb_arb(
.clk(clk_i),
.rstn(rst_n),
- .req({ m2_wbd_cyc_i,
- m1_wbd_cyc_i,
- m0_wbd_cyc_i}),
+ .req({ m2_wbd_stb_i & !m2_wbd_ack_o,
+ m1_wbd_stb_i & !m1_wbd_ack_o,
+ m0_wbd_stb_i & !m0_wbd_ack_o}),
.gnt(gnt)
);
@@ -326,5 +329,89 @@
+// Wishbone Stagging FF towards S0 to break timing path
+wb_stagging u_s0_wb_stage(
+ .clk_i (clk_i ),
+ .rst_n (rst_n ),
+ // WishBone Input master I/P
+ .m_wbd_dat_i (s0_wb_wr.wbd_dat ),
+ .m_wbd_adr_i (s0_wb_wr.wbd_adr ),
+ .m_wbd_sel_i (s0_wb_wr.wbd_sel ),
+ .m_wbd_we_i (s0_wb_wr.wbd_we ),
+ .m_wbd_cyc_i (s0_wb_wr.wbd_cyc ),
+ .m_wbd_stb_i (s0_wb_wr.wbd_stb ),
+ .m_wbd_dat_o (s0_wb_rd.wbd_dat ),
+ .m_wbd_ack_o (s0_wb_rd.wbd_ack ),
+ .m_wbd_err_o (s0_wb_rd.wbd_err ),
+
+ // Slave Interface
+ .s_wbd_dat_i (s0_wbd_dat_i ),
+ .s_wbd_ack_i (s0_wbd_ack_i ),
+ .s_wbd_err_i (s0_wbd_err_i ),
+ .s_wbd_dat_o (s0_wbd_dat_o ),
+ .s_wbd_adr_o (s0_wbd_adr_o ),
+ .s_wbd_sel_o (s0_wbd_sel_o ),
+ .s_wbd_we_o (s0_wbd_we_o ),
+ .s_wbd_cyc_o (s0_wbd_cyc_o ),
+ .s_wbd_stb_o (s0_wbd_stb_o )
+
+);
+
+// Wishbone Stagging FF towards S1 to break timing path
+wb_stagging u_s1_wb_stage(
+ .clk_i (clk_i ),
+ .rst_n (rst_n ),
+ // WishBone Input master I/P
+ .m_wbd_dat_i (s1_wb_wr.wbd_dat ),
+ .m_wbd_adr_i (s1_wb_wr.wbd_adr ),
+ .m_wbd_sel_i (s1_wb_wr.wbd_sel ),
+ .m_wbd_we_i (s1_wb_wr.wbd_we ),
+ .m_wbd_cyc_i (s1_wb_wr.wbd_cyc ),
+ .m_wbd_stb_i (s1_wb_wr.wbd_stb ),
+ .m_wbd_dat_o (s1_wb_rd.wbd_dat ),
+ .m_wbd_ack_o (s1_wb_rd.wbd_ack ),
+ .m_wbd_err_o (s1_wb_rd.wbd_err ),
+
+ // Slave Interface
+ .s_wbd_dat_i (s1_wbd_dat_i ),
+ .s_wbd_ack_i (s1_wbd_ack_i ),
+ .s_wbd_err_i (s1_wbd_err_i ),
+ .s_wbd_dat_o (s1_wbd_dat_o ),
+ .s_wbd_adr_o (s1_wbd_adr_o ),
+ .s_wbd_sel_o (s1_wbd_sel_o ),
+ .s_wbd_we_o (s1_wbd_we_o ),
+ .s_wbd_cyc_o (s1_wbd_cyc_o ),
+ .s_wbd_stb_o (s1_wbd_stb_o )
+
+);
+
+// Wishbone Stagging FF towards S1 to break timing path
+wb_stagging u_s2_wb_stage(
+ .clk_i (clk_i ),
+ .rst_n (rst_n ),
+ // WishBone Input master I/P
+ .m_wbd_dat_i (s2_wb_wr.wbd_dat ),
+ .m_wbd_adr_i (s2_wb_wr.wbd_adr ),
+ .m_wbd_sel_i (s2_wb_wr.wbd_sel ),
+ .m_wbd_we_i (s2_wb_wr.wbd_we ),
+ .m_wbd_cyc_i (s2_wb_wr.wbd_cyc ),
+ .m_wbd_stb_i (s2_wb_wr.wbd_stb ),
+ .m_wbd_dat_o (s2_wb_rd.wbd_dat ),
+ .m_wbd_ack_o (s2_wb_rd.wbd_ack ),
+ .m_wbd_err_o (s2_wb_rd.wbd_err ),
+
+ // Slave Interface
+ .s_wbd_dat_i (s2_wbd_dat_i ),
+ .s_wbd_ack_i (s2_wbd_ack_i ),
+ .s_wbd_err_i (s2_wbd_err_i ),
+ .s_wbd_dat_o (s2_wbd_dat_o ),
+ .s_wbd_adr_o (s2_wbd_adr_o ),
+ .s_wbd_sel_o (s2_wbd_sel_o ),
+ .s_wbd_we_o (s2_wbd_we_o ),
+ .s_wbd_cyc_o (s2_wbd_cyc_o ),
+ .s_wbd_stb_o (s2_wbd_stb_o )
+
+);
+
endmodule