Merge branch 'master' of https://github.gatech.edu/casl/Vortex
This commit is contained in:
@@ -69,8 +69,8 @@ SRC = \
|
||||
../rtl/cache/VX_generic_pe.v \
|
||||
../rtl/cache/cache_set.v \
|
||||
../rtl/cache/VX_cache_data_per_index.v \
|
||||
../rtl/pipe_regs/VX_d_e_reg.v \
|
||||
../rtl/pipe_regs/VX_f_d_reg.v \
|
||||
../rtl/VX_d_e_reg.v \
|
||||
../rtl/VX_f_d_reg.v \
|
||||
../models/memory/cln28hpm/rf2_128x128_wm1/rf2_128x128_wm1.v \
|
||||
../models/memory/cln28hpm/rf2_256x128_wm1/rf2_256x128_wm1.v \
|
||||
../models/memory/cln28hpm/rf2_256x19_wm0/rf2_256x19_wm0.v \
|
||||
|
||||
@@ -62,6 +62,7 @@ make ase
|
||||
# tests
|
||||
./run_ase.sh build_ase_1c ../../driver/tests/basic/basic
|
||||
./run_ase.sh build_ase_1c ../../driver/tests/demo/demo
|
||||
./run_ase.sh build_ase_1c ../../benchmarks/opencl/vecadd/vecadd
|
||||
|
||||
# modify "vsim_run.tcl" to dump VCD trace
|
||||
vcd file vortex.vcd
|
||||
|
||||
@@ -7,6 +7,9 @@ BUILD_DIR=$1
|
||||
PROGRAM=$(basename "$2")
|
||||
PROGRAM_DIR=`dirname $2`
|
||||
|
||||
POCL_RT_PATH=$SCRIPT_DIR/../../benchmarks/opencl/runtime/lib
|
||||
VORTEX_DRV_PATH=$SCRIPT_DIR/../../driver/opae/ase
|
||||
|
||||
# Export ASE_WORKDIR variable
|
||||
export ASE_WORKDIR=$SCRIPT_DIR/$BUILD_DIR/work
|
||||
|
||||
@@ -33,5 +36,5 @@ done
|
||||
# run application
|
||||
pushd $PROGRAM_DIR
|
||||
echo " [DBG] running ./$PROGRAM $*"
|
||||
ASE_LOG=0 LD_LIBRARY_PATH=../../opae/ase:$LD_LIBRARY_PATH ./$PROGRAM $*
|
||||
ASE_LOG=0 LD_LIBRARY_PATH=$POCL_RT_PATH:$VORTEX_DRV_PATH:$LD_LIBRARY_PATH ./$PROGRAM $*
|
||||
popd
|
||||
@@ -48,6 +48,8 @@ QI:vortex_afu.qsf
|
||||
../rtl/interfaces/VX_cache_snp_req_if.v
|
||||
../rtl/interfaces/VX_cache_snp_rsp_if.v
|
||||
../rtl/interfaces/VX_csr_req_if.v
|
||||
../rtl/interfaces/VX_csr_io_req_if.v
|
||||
../rtl/interfaces/VX_csr_io_rsp_if.v
|
||||
../rtl/interfaces/VX_exec_unit_req_if.v
|
||||
../rtl/interfaces/VX_backend_req_if.v
|
||||
../rtl/interfaces/VX_gpr_read_if.v
|
||||
@@ -67,6 +69,7 @@ QI:vortex_afu.qsf
|
||||
../rtl/libs/VX_priority_encoder.v
|
||||
../rtl/libs/VX_generic_queue.v
|
||||
../rtl/libs/VX_indexable_queue.v
|
||||
../rtl/libs/VX_fair_arbiter.v
|
||||
../rtl/libs/VX_fixed_arbiter.v
|
||||
../rtl/libs/VX_rr_arbiter.v
|
||||
../rtl/libs/VX_countones.v
|
||||
@@ -89,6 +92,8 @@ QI:vortex_afu.qsf
|
||||
../rtl/VX_writeback.v
|
||||
../rtl/VX_csr_pipe.v
|
||||
../rtl/VX_csr_data.v
|
||||
../rtl/VX_csr_arb.v
|
||||
../rtl/VX_csr_io_arb.v
|
||||
../rtl/VX_warp_sched.v
|
||||
../rtl/VX_gpr_ram.v
|
||||
../rtl/VX_gpr_stage.v
|
||||
@@ -98,10 +103,9 @@ QI:vortex_afu.qsf
|
||||
../rtl/VX_inst_multiplex.v
|
||||
../rtl/VX_dcache_arb.v
|
||||
../rtl/VX_mem_arb.v
|
||||
|
||||
../rtl/pipe_regs/VX_f_d_reg.v
|
||||
../rtl/pipe_regs/VX_i_d_reg.v
|
||||
../rtl/pipe_regs/VX_d_e_reg.v
|
||||
../rtl/VX_f_d_reg.v
|
||||
../rtl/VX_i_d_reg.v
|
||||
../rtl/VX_d_e_reg.v
|
||||
|
||||
ccip_interface_reg.sv
|
||||
ccip_std_afu.sv
|
||||
|
||||
@@ -5,18 +5,24 @@
|
||||
"clock-frequency-high": "auto",
|
||||
"clock-frequency-low": "auto",
|
||||
|
||||
"mmio-csr-cmd": 10,
|
||||
"mmio-csr-io-addr": 12,
|
||||
"mmio-csr-mem-addr": 14,
|
||||
"mmio-csr-data-size": 16,
|
||||
"mmio-csr-status": 18,
|
||||
"mmio-csr-scope-cmd": 20,
|
||||
"mmio-csr-scope-data": 22,
|
||||
"cmd-mem-read": 1,
|
||||
"cmd-mem-write": 2,
|
||||
"cmd-run": 3,
|
||||
"cmd-clflush": 4,
|
||||
"cmd-csr-read": 5,
|
||||
"cmd-csr-write": 6,
|
||||
|
||||
"cmd-type-read": 1,
|
||||
"cmd-type-write": 2,
|
||||
"cmd-type-run": 3,
|
||||
"cmd-type-clflush": 4,
|
||||
"mmio-cmd-type": 10,
|
||||
"mmio-io-addr": 12,
|
||||
"mmio-mem-addr": 14,
|
||||
"mmio-data-size": 16,
|
||||
"mmio-status": 18,
|
||||
"mmio-scope-read": 20,
|
||||
"mmio-scope-write": 22,
|
||||
"mmio-csr-core": 24,
|
||||
"mmio-csr-addr": 26,
|
||||
"mmio-csr-data": 28,
|
||||
"mmio-csr-read": 30,
|
||||
|
||||
"afu-top-interface":
|
||||
{
|
||||
|
||||
@@ -53,19 +53,26 @@ localparam CCI_RW_QUEUE_SIZE = 1024;
|
||||
localparam AFU_ID_L = 16'h0002; // AFU ID Lower
|
||||
localparam AFU_ID_H = 16'h0004; // AFU ID Higher
|
||||
|
||||
localparam CMD_TYPE_READ = `AFU_IMAGE_CMD_TYPE_READ;
|
||||
localparam CMD_TYPE_WRITE = `AFU_IMAGE_CMD_TYPE_WRITE;
|
||||
localparam CMD_TYPE_RUN = `AFU_IMAGE_CMD_TYPE_RUN;
|
||||
localparam CMD_TYPE_CLFLUSH = `AFU_IMAGE_CMD_TYPE_CLFLUSH;
|
||||
localparam CMD_MEM_READ = `AFU_IMAGE_CMD_MEM_READ;
|
||||
localparam CMD_MEM_WRITE = `AFU_IMAGE_CMD_MEM_WRITE;
|
||||
localparam CMD_RUN = `AFU_IMAGE_CMD_RUN;
|
||||
localparam CMD_CLFLUSH = `AFU_IMAGE_CMD_CLFLUSH;
|
||||
localparam CMD_CSR_READ = `AFU_IMAGE_CMD_CSR_READ;
|
||||
localparam CMD_CSR_WRITE = `AFU_IMAGE_CMD_CSR_WRITE;
|
||||
|
||||
localparam MMIO_CSR_CMD = `AFU_IMAGE_MMIO_CSR_CMD;
|
||||
localparam MMIO_CSR_IO_ADDR = `AFU_IMAGE_MMIO_CSR_IO_ADDR;
|
||||
localparam MMIO_CSR_MEM_ADDR = `AFU_IMAGE_MMIO_CSR_MEM_ADDR;
|
||||
localparam MMIO_CSR_DATA_SIZE = `AFU_IMAGE_MMIO_CSR_DATA_SIZE;
|
||||
localparam MMIO_CSR_STATUS = `AFU_IMAGE_MMIO_CSR_STATUS;
|
||||
localparam MMIO_CMD_TYPE = `AFU_IMAGE_MMIO_CMD_TYPE;
|
||||
localparam MMIO_IO_ADDR = `AFU_IMAGE_MMIO_IO_ADDR;
|
||||
localparam MMIO_MEM_ADDR = `AFU_IMAGE_MMIO_MEM_ADDR;
|
||||
localparam MMIO_DATA_SIZE = `AFU_IMAGE_MMIO_DATA_SIZE;
|
||||
localparam MMIO_STATUS = `AFU_IMAGE_MMIO_STATUS;
|
||||
|
||||
localparam MMIO_CSR_SCOPE_CMD = `AFU_IMAGE_MMIO_CSR_SCOPE_CMD;
|
||||
localparam MMIO_CSR_SCOPE_DATA= `AFU_IMAGE_MMIO_CSR_SCOPE_DATA;
|
||||
localparam MMIO_SCOPE_READ = `AFU_IMAGE_MMIO_SCOPE_READ;
|
||||
localparam MMIO_SCOPE_WRITE = `AFU_IMAGE_MMIO_SCOPE_WRITE;
|
||||
|
||||
localparam MMIO_CSR_CORE = `AFU_IMAGE_MMIO_CSR_CORE;
|
||||
localparam MMIO_CSR_ADDR = `AFU_IMAGE_MMIO_CSR_ADDR;
|
||||
localparam MMIO_CSR_DATA = `AFU_IMAGE_MMIO_CSR_DATA;
|
||||
localparam MMIO_CSR_READ = `AFU_IMAGE_MMIO_CSR_READ;
|
||||
|
||||
logic [127:0] afu_id = `AFU_ACCEL_UUID;
|
||||
|
||||
@@ -75,7 +82,9 @@ typedef enum logic[3:0] {
|
||||
STATE_WRITE,
|
||||
STATE_START,
|
||||
STATE_RUN,
|
||||
STATE_CLFLUSH
|
||||
STATE_CLFLUSH,
|
||||
STATE_CSR_READ,
|
||||
STATE_CSR_WRITE
|
||||
} state_t;
|
||||
|
||||
typedef logic [$clog2(CCI_RD_WINDOW_SIZE)-1:0] t_cci_rdq_tag;
|
||||
@@ -114,6 +123,17 @@ logic [`VX_SNP_TAG_WIDTH-1:0] vx_snp_rsp_tag;
|
||||
`DEBUG_END
|
||||
logic vx_snp_rsp_ready;
|
||||
|
||||
logic vx_csr_io_req_valid;
|
||||
logic [`VX_CSR_ID_WIDTH-1:0] vx_csr_io_req_coreid;
|
||||
logic [11:0] vx_csr_io_req_addr;
|
||||
logic vx_csr_io_req_rw;
|
||||
logic [31:0] vx_csr_io_req_data;
|
||||
logic vx_csr_io_req_ready;
|
||||
|
||||
logic vx_csr_io_rsp_valid;
|
||||
logic [31:0] vx_csr_io_rsp_data;
|
||||
logic vx_csr_io_rsp_ready;
|
||||
|
||||
logic vx_reset;
|
||||
logic vx_busy;
|
||||
|
||||
@@ -134,20 +154,25 @@ logic avs_rdq_empty;
|
||||
logic avs_rdq_full;
|
||||
`DEBUG_END
|
||||
|
||||
// CSR variables //////////////////////////////////////////////////////////////
|
||||
// CMD variables //////////////////////////////////////////////////////////////
|
||||
|
||||
logic [2:0] csr_cmd;
|
||||
t_ccip_clAddr csr_io_addr;
|
||||
logic[DRAM_ADDR_WIDTH-1:0] csr_mem_addr;
|
||||
logic[DRAM_ADDR_WIDTH-1:0] csr_data_size;
|
||||
logic [2:0] cmd_type;
|
||||
t_ccip_clAddr cmd_io_addr;
|
||||
logic[DRAM_ADDR_WIDTH-1:0] cmd_mem_addr;
|
||||
logic[DRAM_ADDR_WIDTH-1:0] cmd_data_size;
|
||||
|
||||
`ifdef SCOPE
|
||||
logic [63:0] csr_scope_cmd;
|
||||
logic [63:0] csr_scope_data;
|
||||
logic csr_scope_read;
|
||||
logic csr_scope_write;
|
||||
logic [63:0] cmd_scope_rdata;
|
||||
logic [63:0] cmd_scope_wdata;
|
||||
logic cmd_scope_read;
|
||||
logic cmd_scope_write;
|
||||
`endif
|
||||
|
||||
logic [`VX_CSR_ID_WIDTH-1:0] cmd_csr_core;
|
||||
logic [11:0] cmd_csr_addr;
|
||||
logic [31:0] cmd_csr_rdata;
|
||||
logic [31:0] cmd_csr_wdata;
|
||||
|
||||
// MMIO controller ////////////////////////////////////////////////////////////
|
||||
|
||||
`IGNORE_WARNINGS_BEGIN
|
||||
@@ -159,9 +184,9 @@ t_if_ccip_c2_Tx mmio_tx;
|
||||
assign af2cp_sTxPort.c2 = mmio_tx;
|
||||
|
||||
`ifdef SCOPE
|
||||
assign csr_scope_cmd = 64'(cp2af_sRxPort.c0.data);
|
||||
assign csr_scope_write = cp2af_sRxPort.c0.mmioWrValid && (MMIO_CSR_SCOPE_CMD == mmio_hdr.address);
|
||||
assign csr_scope_read = cp2af_sRxPort.c0.mmioRdValid && (MMIO_CSR_SCOPE_DATA == mmio_hdr.address);
|
||||
assign cmd_scope_wdata = 64'(cp2af_sRxPort.c0.data);
|
||||
assign cmd_scope_read = cp2af_sRxPort.c0.mmioRdValid && (MMIO_SCOPE_READ == mmio_hdr.address);
|
||||
assign cmd_scope_write = cp2af_sRxPort.c0.mmioWrValid && (MMIO_SCOPE_WRITE == mmio_hdr.address);
|
||||
`endif
|
||||
|
||||
always_ff @(posedge clk)
|
||||
@@ -170,57 +195,69 @@ begin
|
||||
mmio_tx.hdr <= 0;
|
||||
mmio_tx.data <= 0;
|
||||
mmio_tx.mmioRdValid <= 0;
|
||||
csr_cmd <= 0;
|
||||
csr_io_addr <= 0;
|
||||
csr_mem_addr <= 0;
|
||||
csr_data_size <= 0;
|
||||
cmd_type <= 0;
|
||||
cmd_io_addr <= 0;
|
||||
cmd_mem_addr <= 0;
|
||||
cmd_data_size <= 0;
|
||||
end
|
||||
else begin
|
||||
|
||||
csr_cmd <= 0;
|
||||
cmd_type <= 0;
|
||||
mmio_tx.mmioRdValid <= 0;
|
||||
|
||||
// serve MMIO write request
|
||||
if (cp2af_sRxPort.c0.mmioWrValid)
|
||||
begin
|
||||
case (mmio_hdr.address)
|
||||
MMIO_CSR_IO_ADDR: begin
|
||||
csr_io_addr <= t_ccip_clAddr'(cp2af_sRxPort.c0.data);
|
||||
MMIO_IO_ADDR: begin
|
||||
cmd_io_addr <= t_ccip_clAddr'(cp2af_sRxPort.c0.data);
|
||||
`ifdef DBG_PRINT_OPAE
|
||||
$display("%t: CSR_IO_ADDR: 0x%0h", $time, t_ccip_clAddr'(cp2af_sRxPort.c0.data));
|
||||
$display("%t: MMIO_IO_ADDR: 0x%0h", $time, t_ccip_clAddr'(cp2af_sRxPort.c0.data));
|
||||
`endif
|
||||
end
|
||||
MMIO_CSR_MEM_ADDR: begin
|
||||
csr_mem_addr <= t_local_mem_addr'(cp2af_sRxPort.c0.data);
|
||||
MMIO_MEM_ADDR: begin
|
||||
cmd_mem_addr <= t_local_mem_addr'(cp2af_sRxPort.c0.data);
|
||||
`ifdef DBG_PRINT_OPAE
|
||||
$display("%t: CSR_MEM_ADDR: 0x%0h", $time, t_local_mem_addr'(cp2af_sRxPort.c0.data));
|
||||
$display("%t: MMIO_MEM_ADDR: 0x%0h", $time, t_local_mem_addr'(cp2af_sRxPort.c0.data));
|
||||
`endif
|
||||
end
|
||||
MMIO_CSR_DATA_SIZE: begin
|
||||
csr_data_size <= $bits(csr_data_size)'(cp2af_sRxPort.c0.data);
|
||||
MMIO_DATA_SIZE: begin
|
||||
cmd_data_size <= $bits(cmd_data_size)'(cp2af_sRxPort.c0.data);
|
||||
`ifdef DBG_PRINT_OPAE
|
||||
$display("%t: CSR_DATA_SIZE: %0d", $time, $bits(csr_data_size)'(cp2af_sRxPort.c0.data));
|
||||
$display("%t: MMIO_DATA_SIZE: %0d", $time, $bits(cmd_data_size)'(cp2af_sRxPort.c0.data));
|
||||
`endif
|
||||
end
|
||||
MMIO_CSR_CMD: begin
|
||||
csr_cmd <= $bits(csr_cmd)'(cp2af_sRxPort.c0.data);
|
||||
MMIO_CMD_TYPE: begin
|
||||
cmd_type <= $bits(cmd_type)'(cp2af_sRxPort.c0.data);
|
||||
`ifdef DBG_PRINT_OPAE
|
||||
$display("%t: CSR_CMD: %0d", $time, $bits(csr_cmd)'(cp2af_sRxPort.c0.data));
|
||||
$display("%t: MMIO_CMD_TYPE: %0d", $time, $bits(cmd_type)'(cp2af_sRxPort.c0.data));
|
||||
`endif
|
||||
end
|
||||
`ifdef SCOPE
|
||||
MMIO_CSR_SCOPE_CMD: begin
|
||||
MMIO_SCOPE_WRITE: begin
|
||||
`ifdef DBG_PRINT_OPAE
|
||||
$display("%t: CSR_SCOPE_CMD: %0h", $time, 64'(cp2af_sRxPort.c0.data));
|
||||
$display("%t: MMIO_SCOPE_WRITE: %0h", $time, 64'(cp2af_sRxPort.c0.data));
|
||||
`endif
|
||||
end
|
||||
`endif
|
||||
default: begin
|
||||
// user-defined CSRs
|
||||
//if (mmio_hdr.addres >= MMIO_CSR_USER) begin
|
||||
// write Vortex CRS
|
||||
//end
|
||||
end
|
||||
MMIO_CSR_CORE: begin
|
||||
cmd_csr_core <= $bits(cmd_csr_core)'(cp2af_sRxPort.c0.data);
|
||||
`ifdef DBG_PRINT_OPAE
|
||||
$display("%t: MMIO_CSR_CORE: %0h", $time, $bits(cmd_csr_core)'(cp2af_sRxPort.c0.data));
|
||||
`endif
|
||||
end
|
||||
MMIO_CSR_ADDR: begin
|
||||
cmd_csr_addr <= $bits(cmd_csr_addr)'(cp2af_sRxPort.c0.data);
|
||||
`ifdef DBG_PRINT_OPAE
|
||||
$display("%t: MMIO_CSR_ADDR: %0h", $time, $bits(cmd_csr_addr)'(cp2af_sRxPort.c0.data));
|
||||
`endif
|
||||
end
|
||||
MMIO_CSR_DATA: begin
|
||||
cmd_csr_wdata <= $bits(cmd_csr_wdata)'(cp2af_sRxPort.c0.data);
|
||||
`ifdef DBG_PRINT_OPAE
|
||||
$display("%t: MMIO_CSR_DATA: %0h", $time, $bits(cmd_csr_wdata)'(cp2af_sRxPort.c0.data));
|
||||
`endif
|
||||
end
|
||||
endcase
|
||||
end
|
||||
|
||||
@@ -243,22 +280,28 @@ begin
|
||||
AFU_ID_H: mmio_tx.data <= afu_id[127:64]; // afu id hi
|
||||
16'h0006: mmio_tx.data <= 64'h0; // next AFU
|
||||
16'h0008: mmio_tx.data <= 64'h0; // reserved
|
||||
MMIO_CSR_STATUS: begin
|
||||
MMIO_STATUS: begin
|
||||
`ifdef DBG_PRINT_OPAE
|
||||
if (state != state_t'(mmio_tx.data)) begin
|
||||
$display("%t: STATUS: state=%0d", $time, state);
|
||||
$display("%t: MMIO_STATUS: state=%0d", $time, state);
|
||||
end
|
||||
`endif
|
||||
mmio_tx.data <= 64'(state);
|
||||
end
|
||||
`ifdef SCOPE
|
||||
MMIO_CSR_SCOPE_DATA: begin
|
||||
mmio_tx.data <= csr_scope_data;
|
||||
MMIO_SCOPE_READ: begin
|
||||
mmio_tx.data <= cmd_scope_rdata;
|
||||
`ifdef DBG_PRINT_OPAE
|
||||
$display("%t: SCOPE: data=%0h", $time, csr_scope_data);
|
||||
$display("%t: MMIO_SCOPE_READ: data=%0h", $time, cmd_scope_rdata);
|
||||
`endif
|
||||
end
|
||||
`endif
|
||||
MMIO_CSR_READ: begin
|
||||
mmio_tx.data <= 64'(cmd_csr_rdata);
|
||||
`ifdef DBG_PRINT_OPAE
|
||||
$display("%t: MMIO_CSR_READ: data=%0h", $time, cmd_csr_rdata);
|
||||
`endif
|
||||
end
|
||||
default: mmio_tx.data <= 64'h0;
|
||||
endcase
|
||||
mmio_tx.mmioRdValid <= 1; // post response
|
||||
@@ -271,6 +314,7 @@ end
|
||||
logic cmd_read_done;
|
||||
logic cmd_write_done;
|
||||
logic cmd_clflush_done;
|
||||
logic cmd_csr_done;
|
||||
logic cmd_run_done;
|
||||
|
||||
always_ff @(posedge clk)
|
||||
@@ -285,32 +329,44 @@ begin
|
||||
|
||||
case (state)
|
||||
STATE_IDLE: begin
|
||||
case (csr_cmd)
|
||||
CMD_TYPE_READ: begin
|
||||
case (cmd_type)
|
||||
CMD_MEM_READ: begin
|
||||
`ifdef DBG_PRINT_OPAE
|
||||
$display("%t: STATE READ: ia=%0h da=%0h sz=%0d", $time, csr_io_addr, csr_mem_addr, csr_data_size);
|
||||
$display("%t: STATE READ: ia=%0h addr=%0h size=%0d", $time, cmd_io_addr, cmd_mem_addr, cmd_data_size);
|
||||
`endif
|
||||
state <= STATE_READ;
|
||||
end
|
||||
CMD_TYPE_WRITE: begin
|
||||
CMD_MEM_WRITE: begin
|
||||
`ifdef DBG_PRINT_OPAE
|
||||
$display("%t: STATE WRITE: ia=%0h da=%0h sz=%0d", $time, csr_io_addr, csr_mem_addr, csr_data_size);
|
||||
$display("%t: STATE WRITE: ia=%0h addr=%0h size=%0d", $time, cmd_io_addr, cmd_mem_addr, cmd_data_size);
|
||||
`endif
|
||||
state <= STATE_WRITE;
|
||||
end
|
||||
CMD_TYPE_RUN: begin
|
||||
CMD_RUN: begin
|
||||
`ifdef DBG_PRINT_OPAE
|
||||
$display("%t: STATE START", $time);
|
||||
`endif
|
||||
vx_reset <= 1;
|
||||
state <= STATE_START;
|
||||
end
|
||||
CMD_TYPE_CLFLUSH: begin
|
||||
CMD_CLFLUSH: begin
|
||||
`ifdef DBG_PRINT_OPAE
|
||||
$display("%t: STATE CFLUSH: da=%0h sz=%0d", $time, csr_mem_addr, csr_data_size);
|
||||
$display("%t: STATE CFLUSH: addr=%0h size=%0d", $time, cmd_mem_addr, cmd_data_size);
|
||||
`endif
|
||||
state <= STATE_CLFLUSH;
|
||||
end
|
||||
CMD_CSR_READ: begin
|
||||
`ifdef DBG_PRINT_OPAE
|
||||
$display("%t: STATE CSR_READ: addr=%0h", $time, cmd_csr_addr);
|
||||
`endif
|
||||
state <= STATE_CSR_READ;
|
||||
end
|
||||
CMD_CSR_WRITE: begin
|
||||
`ifdef DBG_PRINT_OPAE
|
||||
$display("%t: STATE CSR_WRITE: addr=%0h data=%0d", $time, cmd_csr_addr, cmd_csr_wdata);
|
||||
`endif
|
||||
state <= STATE_CSR_WRITE;
|
||||
end
|
||||
default: begin
|
||||
state <= state;
|
||||
end
|
||||
@@ -345,6 +401,18 @@ begin
|
||||
end
|
||||
end
|
||||
|
||||
STATE_CSR_READ: begin
|
||||
if (cmd_csr_done) begin
|
||||
state <= STATE_IDLE;
|
||||
end
|
||||
end
|
||||
|
||||
STATE_CSR_WRITE: begin
|
||||
if (cmd_csr_done) begin
|
||||
state <= STATE_IDLE;
|
||||
end
|
||||
end
|
||||
|
||||
default: begin
|
||||
state <= state;
|
||||
end
|
||||
@@ -385,7 +453,7 @@ assign cci_dram_rd_req_enable = (state == STATE_READ)
|
||||
|
||||
assign cci_dram_wr_req_enable = (state == STATE_WRITE)
|
||||
&& !cci_rdq_empty
|
||||
&& (cci_dram_wr_req_ctr < csr_data_size);
|
||||
&& (cci_dram_wr_req_ctr < cmd_data_size);
|
||||
|
||||
assign vx_dram_req_enable = vortex_enabled && (avs_pending_reads < AVS_RD_QUEUE_SIZE);
|
||||
assign vx_dram_rd_req_enable = vx_dram_req_enable && vx_dram_req_valid && !vx_dram_req_rw;
|
||||
@@ -414,19 +482,19 @@ end
|
||||
always_comb
|
||||
begin
|
||||
case (state)
|
||||
CMD_TYPE_READ: avs_address = cci_dram_rd_req_addr;
|
||||
CMD_TYPE_WRITE: avs_address = cci_dram_wr_req_addr + ((DRAM_ADDR_WIDTH)'(t_cci_rdq_tag'(cci_rdq_dout)));
|
||||
CMD_MEM_READ: avs_address = cci_dram_rd_req_addr;
|
||||
CMD_MEM_WRITE: avs_address = cci_dram_wr_req_addr + ((DRAM_ADDR_WIDTH)'(t_cci_rdq_tag'(cci_rdq_dout)));
|
||||
default: avs_address = vx_dram_req_addr[`VX_DRAM_ADDR_WIDTH-1:`VX_DRAM_ADDR_WIDTH-DRAM_ADDR_WIDTH];
|
||||
endcase
|
||||
|
||||
case (state)
|
||||
CMD_TYPE_READ: avs_byteenable = 64'hffffffffffffffff;
|
||||
CMD_TYPE_WRITE: avs_byteenable = 64'hffffffffffffffff;
|
||||
CMD_MEM_READ: avs_byteenable = 64'hffffffffffffffff;
|
||||
CMD_MEM_WRITE: avs_byteenable = 64'hffffffffffffffff;
|
||||
default: avs_byteenable = vx_dram_req_byteen_;
|
||||
endcase
|
||||
|
||||
case (state)
|
||||
CMD_TYPE_WRITE: avs_writedata = cci_rdq_dout[$bits(t_ccip_clData) + $bits(t_cci_rdq_tag)-1:$bits(t_cci_rdq_tag)];
|
||||
CMD_MEM_WRITE: avs_writedata = cci_rdq_dout[$bits(t_ccip_clData) + $bits(t_cci_rdq_tag)-1:$bits(t_cci_rdq_tag)];
|
||||
default: avs_writedata = (DRAM_LINE_WIDTH)'(vx_dram_req_data) << vx_dram_req_offset;
|
||||
endcase
|
||||
end
|
||||
@@ -434,7 +502,7 @@ end
|
||||
assign avs_read = cci_dram_rd_req_enable || vx_dram_rd_req_enable;
|
||||
assign avs_write = cci_dram_wr_req_enable || vx_dram_wr_req_enable;
|
||||
|
||||
assign cmd_write_done = (cci_dram_wr_req_ctr >= csr_data_size);
|
||||
assign cmd_write_done = (cci_dram_wr_req_ctr >= cmd_data_size);
|
||||
|
||||
always_ff @(posedge clk)
|
||||
begin
|
||||
@@ -451,12 +519,12 @@ begin
|
||||
else begin
|
||||
|
||||
if (state == STATE_IDLE) begin
|
||||
if (CMD_TYPE_READ == csr_cmd) begin
|
||||
cci_dram_rd_req_addr <= csr_mem_addr;
|
||||
cci_dram_rd_req_ctr <= csr_data_size;
|
||||
if (CMD_MEM_READ == cmd_type) begin
|
||||
cci_dram_rd_req_addr <= cmd_mem_addr;
|
||||
cci_dram_rd_req_ctr <= cmd_data_size;
|
||||
end
|
||||
else if (CMD_TYPE_WRITE == csr_cmd) begin
|
||||
cci_dram_wr_req_addr <= csr_mem_addr;
|
||||
else if (CMD_MEM_WRITE == cmd_type) begin
|
||||
cci_dram_wr_req_addr <= cmd_mem_addr;
|
||||
cci_dram_wr_req_ctr <= 0;
|
||||
end
|
||||
end
|
||||
@@ -598,17 +666,17 @@ begin
|
||||
else begin
|
||||
|
||||
if ((STATE_IDLE == state)
|
||||
&& (CMD_TYPE_WRITE == csr_cmd)) begin
|
||||
cci_rd_req_addr <= csr_io_addr;
|
||||
&& (CMD_MEM_WRITE == cmd_type)) begin
|
||||
cci_rd_req_addr <= cmd_io_addr;
|
||||
cci_rd_req_ctr <= 0;
|
||||
cci_rd_rsp_ctr <= 0;
|
||||
cci_pending_reads <= 0;
|
||||
cci_rd_req_enable <= (csr_data_size != 0);
|
||||
cci_rd_req_enable <= (cmd_data_size != 0);
|
||||
cci_rd_req_wait <= 0;
|
||||
end
|
||||
|
||||
cci_rd_req_enable <= (STATE_WRITE == state)
|
||||
&& (cci_rd_req_ctr_next < csr_data_size)
|
||||
&& (cci_rd_req_ctr_next < cmd_data_size)
|
||||
&& (cci_pending_reads_next < CCI_RD_QUEUE_SIZE);
|
||||
|
||||
if (cci_rd_req_fire) begin
|
||||
@@ -618,7 +686,7 @@ begin
|
||||
cci_rd_req_wait <= 1; // end current request batch
|
||||
end
|
||||
`ifdef DBG_PRINT_OPAE
|
||||
$display("%t: CCI Rd Req: addr=%0h, rem=%0d, pending=%0d", $time, cci_rd_req_addr, (csr_data_size - cci_rd_req_ctr_next), cci_pending_reads_next);
|
||||
$display("%t: CCI Rd Req: addr=%0h, rem=%0d, pending=%0d", $time, cci_rd_req_addr, (cmd_data_size - cci_rd_req_ctr_next), cci_pending_reads_next);
|
||||
`endif
|
||||
end
|
||||
|
||||
@@ -695,9 +763,9 @@ begin
|
||||
else begin
|
||||
|
||||
if ((STATE_IDLE == state)
|
||||
&& (CMD_TYPE_READ == csr_cmd)) begin
|
||||
cci_wr_req_addr <= csr_io_addr;
|
||||
cci_wr_req_ctr <= csr_data_size;
|
||||
&& (CMD_MEM_READ == cmd_type)) begin
|
||||
cci_wr_req_addr <= cmd_io_addr;
|
||||
cci_wr_req_ctr <= cmd_data_size;
|
||||
cci_pending_writes <= 0;
|
||||
end
|
||||
|
||||
@@ -733,11 +801,11 @@ logic [`VX_DRAM_ADDR_WIDTH-1:0] snp_rsp_ctr, snp_rsp_ctr_next;
|
||||
logic vx_snp_req_fire, vx_snp_rsp_fire;
|
||||
|
||||
if (`VX_DRAM_LINE_WIDTH != DRAM_LINE_WIDTH) begin
|
||||
assign snp_req_baseaddr = {csr_mem_addr, (`VX_DRAM_ADDR_WIDTH - DRAM_ADDR_WIDTH)'(0)};
|
||||
assign snp_req_size = {csr_data_size, (`VX_DRAM_ADDR_WIDTH - DRAM_ADDR_WIDTH)'(0)};
|
||||
assign snp_req_baseaddr = {cmd_mem_addr, (`VX_DRAM_ADDR_WIDTH - DRAM_ADDR_WIDTH)'(0)};
|
||||
assign snp_req_size = {cmd_data_size, (`VX_DRAM_ADDR_WIDTH - DRAM_ADDR_WIDTH)'(0)};
|
||||
end else begin
|
||||
assign snp_req_baseaddr = csr_mem_addr;
|
||||
assign snp_req_size = csr_data_size;
|
||||
assign snp_req_baseaddr = cmd_mem_addr;
|
||||
assign snp_req_size = cmd_data_size;
|
||||
end
|
||||
|
||||
assign vx_snp_req_fire = vx_snp_req_valid && vx_snp_req_ready;
|
||||
@@ -761,7 +829,7 @@ begin
|
||||
else begin
|
||||
|
||||
if ((STATE_IDLE == state)
|
||||
&& (CMD_TYPE_CLFLUSH == csr_cmd)) begin
|
||||
&& (CMD_CLFLUSH == cmd_type)) begin
|
||||
vx_snp_req_addr <= snp_req_baseaddr;
|
||||
vx_snp_req_tag <= 0;
|
||||
snp_req_ctr <= 0;
|
||||
@@ -802,6 +870,42 @@ begin
|
||||
end
|
||||
end
|
||||
|
||||
// CSRs///////////////////////////////////////////////////////////////////////
|
||||
|
||||
logic csr_io_req_sent;
|
||||
|
||||
assign vx_csr_io_req_valid = !csr_io_req_sent
|
||||
&& ((STATE_CSR_READ == state || STATE_CSR_WRITE == state));
|
||||
assign vx_csr_io_req_coreid = cmd_csr_core;
|
||||
assign vx_csr_io_req_rw = (STATE_CSR_WRITE == state);
|
||||
assign vx_csr_io_req_addr = cmd_csr_addr;
|
||||
assign vx_csr_io_req_data = cmd_csr_wdata;
|
||||
|
||||
assign vx_csr_io_rsp_ready = 1;
|
||||
|
||||
assign cmd_csr_done = (STATE_CSR_WRITE == state) ? vx_csr_io_req_ready : vx_csr_io_rsp_valid;
|
||||
|
||||
always_ff @(posedge clk)
|
||||
begin
|
||||
if (SoftReset) begin
|
||||
csr_io_req_sent <= 0;
|
||||
cmd_csr_rdata <= 0;
|
||||
end
|
||||
else begin
|
||||
if (vx_csr_io_req_valid && vx_csr_io_req_ready) begin
|
||||
csr_io_req_sent <= 1;
|
||||
end
|
||||
if (cmd_csr_done) begin
|
||||
csr_io_req_sent <= 0;
|
||||
end
|
||||
if ((STATE_CSR_READ == state)
|
||||
&& vx_csr_io_rsp_ready
|
||||
&& vx_csr_io_rsp_valid) begin
|
||||
cmd_csr_rdata <= vx_csr_io_rsp_data;
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
// Vortex /////////////////////////////////////////////////////////////////////
|
||||
|
||||
assign cmd_run_done = !vx_busy;
|
||||
@@ -815,7 +919,7 @@ Vortex #() vortex (
|
||||
`SCOPE_SIGNALS_BE_BIND
|
||||
|
||||
.clk (clk),
|
||||
.reset (vx_reset),
|
||||
.reset (SoftReset | vx_reset),
|
||||
|
||||
// DRAM request
|
||||
.dram_req_valid (vx_dram_req_valid),
|
||||
@@ -858,6 +962,19 @@ Vortex #() vortex (
|
||||
.io_rsp_data (0),
|
||||
.io_rsp_tag (0),
|
||||
`UNUSED_PIN (io_rsp_ready),
|
||||
|
||||
// CSR I/O Request
|
||||
.csr_io_req_valid (vx_csr_io_req_valid),
|
||||
.csr_io_req_coreid(vx_csr_io_req_coreid),
|
||||
.csr_io_req_addr (vx_csr_io_req_addr),
|
||||
.csr_io_req_rw (vx_csr_io_req_rw),
|
||||
.csr_io_req_data (vx_csr_io_req_data),
|
||||
.csr_io_req_ready (vx_csr_io_req_ready),
|
||||
|
||||
// CSR I/O Response
|
||||
.csr_io_rsp_valid (vx_csr_io_rsp_valid),
|
||||
.csr_io_rsp_data (vx_csr_io_rsp_data),
|
||||
.csr_io_rsp_ready (vx_csr_io_rsp_ready),
|
||||
|
||||
// status
|
||||
.busy (vx_busy),
|
||||
@@ -944,10 +1061,10 @@ VX_scope #(
|
||||
.stop (0),
|
||||
.changed (scope_data_in_ste[1]),
|
||||
.data_in (scope_data_in_ste[SCOPE_DATAW+1:2]),
|
||||
.bus_in (csr_scope_cmd),
|
||||
.bus_out (csr_scope_data),
|
||||
.bus_read (csr_scope_read),
|
||||
.bus_write(csr_scope_write)
|
||||
.bus_in (cmd_scope_wdata),
|
||||
.bus_out (cmd_scope_rdata),
|
||||
.bus_read (cmd_scope_read),
|
||||
.bus_write(cmd_scope_write)
|
||||
);
|
||||
|
||||
`endif
|
||||
|
||||
@@ -12,17 +12,25 @@
|
||||
|
||||
`define AFU_ACCEL_NAME "vortex_afu"
|
||||
`define AFU_ACCEL_UUID 128'h35f9452b_25c2_434c_93d5_6f8c60db361c
|
||||
`define AFU_IMAGE_CMD_TYPE_CLFLUSH 4
|
||||
`define AFU_IMAGE_CMD_TYPE_READ 1
|
||||
`define AFU_IMAGE_CMD_TYPE_RUN 3
|
||||
`define AFU_IMAGE_CMD_TYPE_WRITE 2
|
||||
`define AFU_IMAGE_MMIO_CSR_CMD 10
|
||||
`define AFU_IMAGE_MMIO_CSR_DATA_SIZE 12
|
||||
`define AFU_IMAGE_MMIO_CSR_IO_ADDR 14
|
||||
`define AFU_IMAGE_MMIO_CSR_MEM_ADDR 16
|
||||
`define AFU_IMAGE_MMIO_CSR_STATUS 18
|
||||
`define AFU_IMAGE_MMIO_CSR_SCOPE_CMD 20
|
||||
`define AFU_IMAGE_MMIO_CSR_SCOPE_DATA 22
|
||||
|
||||
`define AFU_IMAGE_CMD_CLFLUSH 4
|
||||
`define AFU_IMAGE_CMD_CSR_READ 5
|
||||
`define AFU_IMAGE_CMD_CSR_WRITE 6
|
||||
`define AFU_IMAGE_CMD_MEM_READ 1
|
||||
`define AFU_IMAGE_CMD_MEM_WRITE 2
|
||||
`define AFU_IMAGE_CMD_RUN 3
|
||||
`define AFU_IMAGE_MMIO_CMD_TYPE 10
|
||||
`define AFU_IMAGE_MMIO_CSR_CORE 24
|
||||
`define AFU_IMAGE_MMIO_CSR_ADDR 26
|
||||
`define AFU_IMAGE_MMIO_CSR_DATA 28
|
||||
`define AFU_IMAGE_MMIO_CSR_READ 30
|
||||
`define AFU_IMAGE_MMIO_DATA_SIZE 16
|
||||
`define AFU_IMAGE_MMIO_IO_ADDR 12
|
||||
`define AFU_IMAGE_MMIO_MEM_ADDR 14
|
||||
`define AFU_IMAGE_MMIO_SCOPE_READ 20
|
||||
`define AFU_IMAGE_MMIO_SCOPE_WRITE 22
|
||||
`define AFU_IMAGE_MMIO_STATUS 18
|
||||
|
||||
`define AFU_IMAGE_POWER 0
|
||||
`define AFU_TOP_IFC "ccip_std_afu_avalon_mm"
|
||||
|
||||
|
||||
@@ -13,9 +13,6 @@ module VX_alu_unit (
|
||||
output reg [31:0] alu_result,
|
||||
output reg alu_stall
|
||||
);
|
||||
localparam DIV_PIPELINE_LEN = 18;
|
||||
localparam MUL_PIPELINE_LEN = 1;
|
||||
|
||||
wire[31:0] div_result_unsigned;
|
||||
wire[31:0] div_result_signed;
|
||||
|
||||
@@ -28,7 +25,7 @@ module VX_alu_unit (
|
||||
wire[31:0] alu_in2 = (src_rs2 == `RS2_IMMED) ? itype_immed : src_b;
|
||||
|
||||
wire[31:0] upper_immed_s = {upper_immed, {12{1'b0}}};
|
||||
|
||||
|
||||
reg [7:0] inst_delay;
|
||||
reg [7:0] curr_inst_delay;
|
||||
|
||||
@@ -37,11 +34,11 @@ module VX_alu_unit (
|
||||
`ALU_DIV,
|
||||
`ALU_DIVU,
|
||||
`ALU_REM,
|
||||
`ALU_REMU: inst_delay = DIV_PIPELINE_LEN;
|
||||
`ALU_REMU: inst_delay = `DIV_LATENCY;
|
||||
`ALU_MUL,
|
||||
`ALU_MULH,
|
||||
`ALU_MULHSU,
|
||||
`ALU_MULHU: inst_delay = MUL_PIPELINE_LEN;
|
||||
`ALU_MULHU: inst_delay = `MUL_LATENCY;
|
||||
default: inst_delay = 0;
|
||||
endcase
|
||||
end
|
||||
@@ -73,7 +70,6 @@ module VX_alu_unit (
|
||||
`ALU_SUBU: alu_result = (alu_in1 >= alu_in2) ? 32'h0 : 32'hffffffff;
|
||||
`ALU_LUI: alu_result = upper_immed_s;
|
||||
`ALU_AUIPC: alu_result = $signed(curr_PC) + $signed(upper_immed_s);
|
||||
// TODO: profitable to roll these exceptional cases into inst_delay_tmp to avoid pipeline when possible?
|
||||
`ALU_MUL: alu_result = mul_result[31:0];
|
||||
`ALU_MULH: alu_result = mul_result[63:32];
|
||||
`ALU_MULHSU: alu_result = mul_result[63:32];
|
||||
@@ -83,7 +79,7 @@ module VX_alu_unit (
|
||||
`ALU_REM: alu_result = (alu_in2 == 0) ? alu_in1 : rem_result_signed;
|
||||
`ALU_REMU: alu_result = (alu_in2 == 0) ? alu_in1 : rem_result_unsigned;
|
||||
default: alu_result = 32'h0;
|
||||
endcase // alu_op
|
||||
endcase
|
||||
end
|
||||
|
||||
VX_divide #(
|
||||
@@ -91,7 +87,7 @@ module VX_alu_unit (
|
||||
.WIDTHD(32),
|
||||
.NSIGNED(0),
|
||||
.DSIGNED(0),
|
||||
.PIPELINE(DIV_PIPELINE_LEN)
|
||||
.PIPELINE(`DIV_LATENCY)
|
||||
) udiv (
|
||||
.clk(clk),
|
||||
.reset(reset),
|
||||
@@ -106,7 +102,7 @@ module VX_alu_unit (
|
||||
.WIDTHD(32),
|
||||
.NSIGNED(1),
|
||||
.DSIGNED(1),
|
||||
.PIPELINE(DIV_PIPELINE_LEN)
|
||||
.PIPELINE(`DIV_LATENCY)
|
||||
) sdiv (
|
||||
.clk(clk),
|
||||
.reset(reset),
|
||||
@@ -124,7 +120,7 @@ module VX_alu_unit (
|
||||
.WIDTHB(33),
|
||||
.WIDTHP(64),
|
||||
.SIGNED(1),
|
||||
.PIPELINE(MUL_PIPELINE_LEN)
|
||||
.PIPELINE(`MUL_LATENCY)
|
||||
) multiplier (
|
||||
.clk(clk),
|
||||
.reset(reset),
|
||||
|
||||
@@ -9,6 +9,9 @@ module VX_back_end #(
|
||||
input wire clk,
|
||||
input wire reset,
|
||||
|
||||
VX_csr_io_req_if csr_io_req_if,
|
||||
VX_csr_io_rsp_if csr_io_rsp_if,
|
||||
|
||||
input wire schedule_delay,
|
||||
|
||||
VX_cache_core_req_if dcache_req_if,
|
||||
@@ -31,6 +34,7 @@ module VX_back_end #(
|
||||
wire no_slot_mem;
|
||||
wire no_slot_exec;
|
||||
|
||||
|
||||
// LSU input + output
|
||||
VX_lsu_req_if lsu_req_if();
|
||||
VX_wb_if mem_wb_if();
|
||||
@@ -63,7 +67,7 @@ module VX_back_end #(
|
||||
// End new
|
||||
.memory_delay (mem_delay),
|
||||
.exec_delay (exec_delay),
|
||||
.gpr_stage_delay (gpr_stage_delay)
|
||||
.delay (gpr_stage_delay)
|
||||
);
|
||||
|
||||
assign ebreak = exec_unit_req_if.is_etype && (| exec_unit_req_if.valid);
|
||||
@@ -76,7 +80,7 @@ module VX_back_end #(
|
||||
.clk (clk),
|
||||
.reset (reset),
|
||||
.lsu_req_if (lsu_req_if),
|
||||
.mem_wb_if_p1 (mem_wb_if),
|
||||
.mem_wb_if (mem_wb_if),
|
||||
.dcache_req_if (dcache_req_if),
|
||||
.dcache_rsp_if (dcache_rsp_if),
|
||||
.delay (mem_delay),
|
||||
@@ -99,15 +103,34 @@ module VX_back_end #(
|
||||
.warp_ctl_if (warp_ctl_if)
|
||||
);
|
||||
|
||||
VX_csr_req_if issued_csr_req_if();
|
||||
|
||||
VX_wb_if csr_pipe_rsp_if();
|
||||
|
||||
VX_csr_arb csr_arb (
|
||||
.clk (clk),
|
||||
.reset (reset),
|
||||
|
||||
.csr_pipe_stall (stall_gpr_csr),
|
||||
|
||||
.csr_core_req_if (csr_req_if),
|
||||
.csr_io_req_if (csr_io_req_if),
|
||||
.issued_csr_req_if(issued_csr_req_if),
|
||||
|
||||
.csr_pipe_rsp_if (csr_pipe_rsp_if),
|
||||
.csr_wb_if (csr_wb_if),
|
||||
.csr_io_rsp_if (csr_io_rsp_if)
|
||||
);
|
||||
|
||||
VX_csr_pipe #(
|
||||
.CORE_ID(CORE_ID)
|
||||
) csr_pipe (
|
||||
.clk (clk),
|
||||
.reset (reset),
|
||||
.no_slot_csr (no_slot_csr),
|
||||
.csr_req_if (csr_req_if),
|
||||
.csr_req_if (issued_csr_req_if),
|
||||
.writeback_if (writeback_if),
|
||||
.csr_wb_if (csr_wb_if),
|
||||
.csr_wb_if (csr_pipe_rsp_if),
|
||||
.stall_gpr_csr (stall_gpr_csr)
|
||||
);
|
||||
|
||||
|
||||
@@ -56,6 +56,19 @@ module VX_cluster #(
|
||||
input wire [`L2CORE_TAG_WIDTH-1:0] io_rsp_tag,
|
||||
output wire io_rsp_ready,
|
||||
|
||||
// CSR I/O Request
|
||||
input wire csr_io_req_valid,
|
||||
input wire [`NC_BITS-1:0] csr_io_req_coreid,
|
||||
input wire [11:0] csr_io_req_addr,
|
||||
input wire csr_io_req_rw,
|
||||
input wire [31:0] csr_io_req_data,
|
||||
output wire csr_io_req_ready,
|
||||
|
||||
// CSR I/O Response
|
||||
output wire csr_io_rsp_valid,
|
||||
output wire [31:0] csr_io_rsp_data,
|
||||
input wire csr_io_rsp_ready,
|
||||
|
||||
// Status
|
||||
output wire busy,
|
||||
output wire ebreak
|
||||
@@ -109,10 +122,21 @@ module VX_cluster #(
|
||||
wire [`NUM_CORES-1:0][31:0] per_core_io_rsp_data;
|
||||
wire [`NUM_CORES-1:0] per_core_io_rsp_ready;
|
||||
|
||||
wire [`NUM_CORES-1:0] per_core_csr_io_req_valid;
|
||||
wire [`NUM_CORES-1:0][11:0] per_core_csr_io_req_addr;
|
||||
wire [`NUM_CORES-1:0] per_core_csr_io_req_rw;
|
||||
wire [`NUM_CORES-1:0][31:0] per_core_csr_io_req_data;
|
||||
wire [`NUM_CORES-1:0] per_core_csr_io_req_ready;
|
||||
|
||||
wire [`NUM_CORES-1:0] per_core_csr_io_rsp_valid;
|
||||
wire [`NUM_CORES-1:0][31:0] per_core_csr_io_rsp_data;
|
||||
wire [`NUM_CORES-1:0] per_core_csr_io_rsp_ready;
|
||||
|
||||
wire [`NUM_CORES-1:0] per_core_busy;
|
||||
wire [`NUM_CORES-1:0] per_core_ebreak;
|
||||
|
||||
genvar i;
|
||||
|
||||
for (i = 0; i < `NUM_CORES; i++) begin
|
||||
VX_core #(
|
||||
.CORE_ID(i + (CLUSTER_ID * `NUM_CORES))
|
||||
@@ -174,6 +198,16 @@ module VX_cluster #(
|
||||
.io_rsp_tag (per_core_io_rsp_tag [i]),
|
||||
.io_rsp_ready (per_core_io_rsp_ready [i]),
|
||||
|
||||
.csr_io_req_valid (per_core_csr_io_req_valid [i]),
|
||||
.csr_io_req_rw (per_core_csr_io_req_rw [i]),
|
||||
.csr_io_req_addr (per_core_csr_io_req_addr [i]),
|
||||
.csr_io_req_data (per_core_csr_io_req_data [i]),
|
||||
.csr_io_req_ready (per_core_csr_io_req_ready [i]),
|
||||
|
||||
.csr_io_rsp_valid (per_core_csr_io_rsp_valid [i]),
|
||||
.csr_io_rsp_data (per_core_csr_io_rsp_data [i]),
|
||||
.csr_io_rsp_ready (per_core_csr_io_rsp_ready [i]),
|
||||
|
||||
.busy (per_core_busy [i]),
|
||||
.ebreak (per_core_ebreak [i])
|
||||
);
|
||||
@@ -217,7 +251,40 @@ module VX_cluster #(
|
||||
.out_mem_rsp_tag (io_rsp_tag),
|
||||
.out_mem_rsp_data (io_rsp_data),
|
||||
.out_mem_rsp_ready (io_rsp_ready)
|
||||
);
|
||||
);
|
||||
|
||||
VX_csr_io_arb #(
|
||||
.NUM_REQUESTS (`NUM_CORES)
|
||||
) csr_io_arb (
|
||||
.clk (clk),
|
||||
.reset (reset),
|
||||
|
||||
.request_id (csr_io_req_coreid),
|
||||
|
||||
// input requests
|
||||
.in_csr_io_req_valid (csr_io_req_valid),
|
||||
.in_csr_io_req_addr (csr_io_req_addr),
|
||||
.in_csr_io_req_rw (csr_io_req_rw),
|
||||
.in_csr_io_req_data (csr_io_req_data),
|
||||
.in_csr_io_req_ready (csr_io_req_ready),
|
||||
|
||||
// input responses
|
||||
.in_csr_io_rsp_valid (per_core_csr_io_rsp_valid),
|
||||
.in_csr_io_rsp_data (per_core_csr_io_rsp_data),
|
||||
.in_csr_io_rsp_ready (per_core_csr_io_rsp_ready),
|
||||
|
||||
// output request
|
||||
.out_csr_io_req_valid (per_core_csr_io_req_valid),
|
||||
.out_csr_io_req_addr (per_core_csr_io_req_addr),
|
||||
.out_csr_io_req_rw (per_core_csr_io_req_rw),
|
||||
.out_csr_io_req_data (per_core_csr_io_req_data),
|
||||
.out_csr_io_req_ready (per_core_csr_io_req_ready),
|
||||
|
||||
// output response
|
||||
.out_csr_io_rsp_valid (csr_io_rsp_valid),
|
||||
.out_csr_io_rsp_data (csr_io_rsp_data),
|
||||
.out_csr_io_rsp_ready (csr_io_rsp_ready)
|
||||
);
|
||||
|
||||
assign busy = (| per_core_busy);
|
||||
assign ebreak = (& per_core_ebreak);
|
||||
@@ -537,4 +604,4 @@ module VX_cluster #(
|
||||
|
||||
end
|
||||
|
||||
endmodule
|
||||
endmodule
|
||||
|
||||
@@ -59,21 +59,33 @@
|
||||
`define L3_ENABLE (`NUM_CLUSTERS > 1)
|
||||
`endif
|
||||
|
||||
`define CSR_LTID 12'h020
|
||||
`define CSR_LWID 12'h021
|
||||
`define CSR_GTID 12'hF14 // reserved Hardware Thread ID (mhartid)
|
||||
`define CSR_GWID 12'h023
|
||||
`define CSR_GCID 12'h024
|
||||
`define CSR_NT 12'h025
|
||||
`define CSR_NW 12'h026
|
||||
`define CSR_NC 12'h027
|
||||
// Configuration Values =======================================================
|
||||
|
||||
`define CSR_CYCLL 12'hC00
|
||||
`define CSR_CYCLH 12'hC80
|
||||
`define CSR_INSTL 12'hC02
|
||||
`define CSR_INSTH 12'hC82
|
||||
`define VENDOR_ID 0
|
||||
`define ARCHITECTURE_ID 0
|
||||
`define IMPLEMENTATION_ID 0
|
||||
|
||||
// ========================= Dcache Configurable Knobs ========================
|
||||
// CSR Addresses ==============================================================
|
||||
|
||||
`define CSR_VEND_ID 12'hF11
|
||||
`define CSR_ARCH_ID 12'hF12
|
||||
`define CSR_IMPL_ID 12'hF13
|
||||
`define CSR_GTID 12'hF14
|
||||
|
||||
`define CSR_LTID 12'h020
|
||||
`define CSR_LWID 12'h021
|
||||
`define CSR_GWID 12'h023
|
||||
`define CSR_GCID 12'h024
|
||||
`define CSR_NT 12'h025
|
||||
`define CSR_NW 12'h026
|
||||
`define CSR_NC 12'h027
|
||||
|
||||
`define CSR_CYCLE_L 12'hC00
|
||||
`define CSR_CYCLE_H 12'hC80
|
||||
`define CSR_INSTR_L 12'hC02
|
||||
`define CSR_INSTR_H 12'hC82
|
||||
|
||||
// Dcache Configurable Knobs ==================================================
|
||||
|
||||
// Size of cache in bytes
|
||||
`ifndef DCACHE_SIZE
|
||||
@@ -144,7 +156,7 @@
|
||||
`define DPRFQ_STRIDE 0
|
||||
`endif
|
||||
|
||||
// ========================== Icache Configurable Knobs =======================
|
||||
// Icache Configurable Knobs ==================================================
|
||||
|
||||
// Size of cache in bytes
|
||||
`ifndef ICACHE_SIZE
|
||||
@@ -210,7 +222,7 @@
|
||||
`define IPRFQ_STRIDE 0
|
||||
`endif
|
||||
|
||||
// =========================== SM Configurable Knobs ==========================
|
||||
// SM Configurable Knobs ======================================================
|
||||
|
||||
// Size of cache in bytes
|
||||
`ifndef SCACHE_SIZE
|
||||
@@ -247,7 +259,7 @@
|
||||
`define SCWBQ_SIZE `SCREQ_SIZE
|
||||
`endif
|
||||
|
||||
// ======================== L2cache Configurable Knobs ========================
|
||||
// L2cache Configurable Knobs =================================================
|
||||
|
||||
// Size of cache in bytes
|
||||
`ifndef L2CACHE_SIZE
|
||||
@@ -318,7 +330,7 @@
|
||||
`define L2PRFQ_STRIDE 0
|
||||
`endif
|
||||
|
||||
// ======================== L3cache Configurable Knobs ========================
|
||||
// L3cache Configurable Knobs =================================================
|
||||
|
||||
// Size of cache in bytes
|
||||
`ifndef L3CACHE_SIZE
|
||||
|
||||
156
hw/rtl/VX_core.v
156
hw/rtl/VX_core.v
@@ -70,12 +70,22 @@ module VX_core #(
|
||||
input wire [`DCORE_TAG_WIDTH-1:0] io_rsp_tag,
|
||||
output wire io_rsp_ready,
|
||||
|
||||
// CSR I/O request
|
||||
input wire csr_io_req_valid,
|
||||
input wire [11:0] csr_io_req_addr,
|
||||
input wire csr_io_req_rw,
|
||||
input wire [31:0] csr_io_req_data,
|
||||
output wire csr_io_req_ready,
|
||||
|
||||
// CSR I/O response
|
||||
output wire csr_io_rsp_valid,
|
||||
output wire [31:0] csr_io_rsp_data,
|
||||
input wire csr_io_rsp_ready,
|
||||
|
||||
// Status
|
||||
output wire busy,
|
||||
output wire ebreak
|
||||
);
|
||||
// Dcache Interfaces
|
||||
|
||||
VX_cache_dram_req_if #(
|
||||
.DRAM_LINE_WIDTH(`DDRAM_LINE_WIDTH),
|
||||
.DRAM_ADDR_WIDTH(`DDRAM_ADDR_WIDTH),
|
||||
@@ -87,18 +97,18 @@ module VX_core #(
|
||||
.DRAM_TAG_WIDTH(`DDRAM_TAG_WIDTH)
|
||||
) dcache_dram_rsp_if();
|
||||
|
||||
assign D_dram_req_valid = dcache_dram_req_if.dram_req_valid;
|
||||
assign D_dram_req_rw = dcache_dram_req_if.dram_req_rw;
|
||||
assign D_dram_req_byteen= dcache_dram_req_if.dram_req_byteen;
|
||||
assign D_dram_req_addr = dcache_dram_req_if.dram_req_addr;
|
||||
assign D_dram_req_data = dcache_dram_req_if.dram_req_data;
|
||||
assign D_dram_req_tag = dcache_dram_req_if.dram_req_tag;
|
||||
assign dcache_dram_req_if.dram_req_ready = D_dram_req_ready;
|
||||
assign D_dram_req_valid = dcache_dram_req_if.valid;
|
||||
assign D_dram_req_rw = dcache_dram_req_if.rw;
|
||||
assign D_dram_req_byteen= dcache_dram_req_if.byteen;
|
||||
assign D_dram_req_addr = dcache_dram_req_if.addr;
|
||||
assign D_dram_req_data = dcache_dram_req_if.data;
|
||||
assign D_dram_req_tag = dcache_dram_req_if.tag;
|
||||
assign dcache_dram_req_if.ready = D_dram_req_ready;
|
||||
|
||||
assign dcache_dram_rsp_if.dram_rsp_valid = D_dram_rsp_valid;
|
||||
assign dcache_dram_rsp_if.dram_rsp_data = D_dram_rsp_data;
|
||||
assign dcache_dram_rsp_if.dram_rsp_tag = D_dram_rsp_tag;
|
||||
assign D_dram_rsp_ready = dcache_dram_rsp_if.dram_rsp_ready;
|
||||
assign dcache_dram_rsp_if.valid = D_dram_rsp_valid;
|
||||
assign dcache_dram_rsp_if.data = D_dram_rsp_data;
|
||||
assign dcache_dram_rsp_if.tag = D_dram_rsp_tag;
|
||||
assign D_dram_rsp_ready = dcache_dram_rsp_if.ready;
|
||||
|
||||
VX_cache_core_req_if #(
|
||||
.NUM_REQUESTS(`DNUM_REQUESTS),
|
||||
@@ -114,18 +124,18 @@ module VX_core #(
|
||||
.CORE_TAG_ID_BITS(`DCORE_TAG_ID_BITS)
|
||||
) core_dcache_rsp_if(), arb_dcache_rsp_if(), arb_io_rsp_if();
|
||||
|
||||
assign io_req_valid = arb_io_req_if.core_req_valid[0];
|
||||
assign io_req_rw = arb_io_req_if.core_req_rw[0];
|
||||
assign io_req_byteen = arb_io_req_if.core_req_byteen[0];
|
||||
assign io_req_addr = arb_io_req_if.core_req_addr[0];
|
||||
assign io_req_data = arb_io_req_if.core_req_data[0];
|
||||
assign io_req_tag = arb_io_req_if.core_req_tag[0];
|
||||
assign arb_io_req_if.core_req_ready = io_req_ready;
|
||||
assign io_req_valid = arb_io_req_if.valid[0];
|
||||
assign io_req_rw = arb_io_req_if.rw[0];
|
||||
assign io_req_byteen = arb_io_req_if.byteen[0];
|
||||
assign io_req_addr = arb_io_req_if.addr[0];
|
||||
assign io_req_data = arb_io_req_if.data[0];
|
||||
assign io_req_tag = arb_io_req_if.tag[0];
|
||||
assign arb_io_req_if.ready = io_req_ready;
|
||||
|
||||
assign arb_io_rsp_if.core_rsp_valid = {{(`NUM_THREADS-1){1'b0}}, io_rsp_valid};
|
||||
assign arb_io_rsp_if.core_rsp_data[0] = io_rsp_data;
|
||||
assign arb_io_rsp_if.core_rsp_tag = io_rsp_tag;
|
||||
assign io_rsp_ready = arb_io_rsp_if.core_rsp_ready;
|
||||
assign arb_io_rsp_if.valid = {{(`NUM_THREADS-1){1'b0}}, io_rsp_valid};
|
||||
assign arb_io_rsp_if.data[0] = io_rsp_data;
|
||||
assign arb_io_rsp_if.tag = io_rsp_tag;
|
||||
assign io_rsp_ready = arb_io_rsp_if.ready;
|
||||
|
||||
// Icache interfaces
|
||||
|
||||
@@ -140,18 +150,18 @@ module VX_core #(
|
||||
.DRAM_TAG_WIDTH(`IDRAM_TAG_WIDTH)
|
||||
) icache_dram_rsp_if();
|
||||
|
||||
assign I_dram_req_valid = icache_dram_req_if.dram_req_valid;
|
||||
assign I_dram_req_rw = icache_dram_req_if.dram_req_rw;
|
||||
assign I_dram_req_byteen= icache_dram_req_if.dram_req_byteen;
|
||||
assign I_dram_req_addr = icache_dram_req_if.dram_req_addr;
|
||||
assign I_dram_req_data = icache_dram_req_if.dram_req_data;
|
||||
assign I_dram_req_tag = icache_dram_req_if.dram_req_tag;
|
||||
assign icache_dram_req_if.dram_req_ready = I_dram_req_ready;
|
||||
assign I_dram_req_valid = icache_dram_req_if.valid;
|
||||
assign I_dram_req_rw = icache_dram_req_if.rw;
|
||||
assign I_dram_req_byteen= icache_dram_req_if.byteen;
|
||||
assign I_dram_req_addr = icache_dram_req_if.addr;
|
||||
assign I_dram_req_data = icache_dram_req_if.data;
|
||||
assign I_dram_req_tag = icache_dram_req_if.tag;
|
||||
assign icache_dram_req_if.ready = I_dram_req_ready;
|
||||
|
||||
assign icache_dram_rsp_if.dram_rsp_valid = I_dram_rsp_valid;
|
||||
assign icache_dram_rsp_if.dram_rsp_data = I_dram_rsp_data;
|
||||
assign icache_dram_rsp_if.dram_rsp_tag = I_dram_rsp_tag;
|
||||
assign I_dram_rsp_ready = icache_dram_rsp_if.dram_rsp_ready;
|
||||
assign icache_dram_rsp_if.valid = I_dram_rsp_valid;
|
||||
assign icache_dram_rsp_if.data = I_dram_rsp_data;
|
||||
assign icache_dram_rsp_if.tag = I_dram_rsp_tag;
|
||||
assign I_dram_rsp_ready = icache_dram_rsp_if.ready;
|
||||
|
||||
VX_cache_core_req_if #(
|
||||
.NUM_REQUESTS(`INUM_REQUESTS),
|
||||
@@ -179,34 +189,46 @@ module VX_core #(
|
||||
.reset(reset),
|
||||
|
||||
// Dcache core request
|
||||
.dcache_req_valid (core_dcache_req_if.core_req_valid),
|
||||
.dcache_req_rw (core_dcache_req_if.core_req_rw),
|
||||
.dcache_req_byteen (core_dcache_req_if.core_req_byteen),
|
||||
.dcache_req_addr (core_dcache_req_if.core_req_addr),
|
||||
.dcache_req_data (core_dcache_req_if.core_req_data),
|
||||
.dcache_req_tag (core_dcache_req_if.core_req_tag),
|
||||
.dcache_req_ready (core_dcache_req_if.core_req_ready),
|
||||
.dcache_req_valid (core_dcache_req_if.valid),
|
||||
.dcache_req_rw (core_dcache_req_if.rw),
|
||||
.dcache_req_byteen (core_dcache_req_if.byteen),
|
||||
.dcache_req_addr (core_dcache_req_if.addr),
|
||||
.dcache_req_data (core_dcache_req_if.data),
|
||||
.dcache_req_tag (core_dcache_req_if.tag),
|
||||
.dcache_req_ready (core_dcache_req_if.ready),
|
||||
|
||||
// Dcache core reponse
|
||||
.dcache_rsp_valid (core_dcache_rsp_if.core_rsp_valid),
|
||||
.dcache_rsp_data (core_dcache_rsp_if.core_rsp_data),
|
||||
.dcache_rsp_tag (core_dcache_rsp_if.core_rsp_tag),
|
||||
.dcache_rsp_ready (core_dcache_rsp_if.core_rsp_ready),
|
||||
.dcache_rsp_valid (core_dcache_rsp_if.valid),
|
||||
.dcache_rsp_data (core_dcache_rsp_if.data),
|
||||
.dcache_rsp_tag (core_dcache_rsp_if.tag),
|
||||
.dcache_rsp_ready (core_dcache_rsp_if.ready),
|
||||
|
||||
// Dcache core request
|
||||
.icache_req_valid (core_icache_req_if.core_req_valid),
|
||||
.icache_req_rw (core_icache_req_if.core_req_rw),
|
||||
.icache_req_byteen (core_icache_req_if.core_req_byteen),
|
||||
.icache_req_addr (core_icache_req_if.core_req_addr),
|
||||
.icache_req_data (core_icache_req_if.core_req_data),
|
||||
.icache_req_tag (core_icache_req_if.core_req_tag),
|
||||
.icache_req_ready (core_icache_req_if.core_req_ready),
|
||||
.icache_req_valid (core_icache_req_if.valid),
|
||||
.icache_req_rw (core_icache_req_if.rw),
|
||||
.icache_req_byteen (core_icache_req_if.byteen),
|
||||
.icache_req_addr (core_icache_req_if.addr),
|
||||
.icache_req_data (core_icache_req_if.data),
|
||||
.icache_req_tag (core_icache_req_if.tag),
|
||||
.icache_req_ready (core_icache_req_if.ready),
|
||||
|
||||
// Dcache core reponse
|
||||
.icache_rsp_valid (core_icache_rsp_if.core_rsp_valid),
|
||||
.icache_rsp_data (core_icache_rsp_if.core_rsp_data),
|
||||
.icache_rsp_tag (core_icache_rsp_if.core_rsp_tag),
|
||||
.icache_rsp_ready (core_icache_rsp_if.core_rsp_ready),
|
||||
.icache_rsp_valid (core_icache_rsp_if.valid),
|
||||
.icache_rsp_data (core_icache_rsp_if.data),
|
||||
.icache_rsp_tag (core_icache_rsp_if.tag),
|
||||
.icache_rsp_ready (core_icache_rsp_if.ready),
|
||||
|
||||
// CSR I/O request
|
||||
.csr_io_req_valid (csr_io_req_valid),
|
||||
.csr_io_req_rw (csr_io_req_rw),
|
||||
.csr_io_req_addr (csr_io_req_addr),
|
||||
.csr_io_req_data (csr_io_req_data),
|
||||
.csr_io_req_ready (csr_io_req_ready),
|
||||
|
||||
// CSR I/O response
|
||||
.csr_io_rsp_valid (csr_io_rsp_valid),
|
||||
.csr_io_rsp_data (csr_io_rsp_data),
|
||||
.csr_io_rsp_ready (csr_io_rsp_ready),
|
||||
|
||||
// Status
|
||||
.busy(busy),
|
||||
@@ -224,15 +246,15 @@ module VX_core #(
|
||||
.SNP_TAG_WIDTH(`DSNP_TAG_WIDTH)
|
||||
) dcache_snp_rsp_if();
|
||||
|
||||
assign dcache_snp_req_if.snp_req_valid = snp_req_valid;
|
||||
assign dcache_snp_req_if.snp_req_addr = snp_req_addr;
|
||||
assign dcache_snp_req_if.snp_req_invalidate = snp_req_invalidate;
|
||||
assign dcache_snp_req_if.snp_req_tag = snp_req_tag;
|
||||
assign snp_req_ready = dcache_snp_req_if.snp_req_ready;
|
||||
assign dcache_snp_req_if.valid = snp_req_valid;
|
||||
assign dcache_snp_req_if.addr = snp_req_addr;
|
||||
assign dcache_snp_req_if.invalidate = snp_req_invalidate;
|
||||
assign dcache_snp_req_if.tag = snp_req_tag;
|
||||
assign snp_req_ready = dcache_snp_req_if.ready;
|
||||
|
||||
assign snp_rsp_valid = dcache_snp_rsp_if.snp_rsp_valid;
|
||||
assign snp_rsp_tag = dcache_snp_rsp_if.snp_rsp_tag;
|
||||
assign dcache_snp_rsp_if.snp_rsp_ready = snp_rsp_ready;
|
||||
assign snp_rsp_valid = dcache_snp_rsp_if.valid;
|
||||
assign snp_rsp_tag = dcache_snp_rsp_if.tag;
|
||||
assign dcache_snp_rsp_if.ready = snp_rsp_ready;
|
||||
|
||||
VX_mem_unit #(
|
||||
.CORE_ID(CORE_ID)
|
||||
@@ -262,8 +284,8 @@ module VX_core #(
|
||||
);
|
||||
|
||||
// select io address
|
||||
wire is_io_addr = ({core_dcache_req_if.core_req_addr[0], 2'b0} >= `IO_BUS_BASE_ADDR);
|
||||
wire io_select = (| core_dcache_req_if.core_req_valid) ? is_io_addr : 0;
|
||||
wire is_io_addr = ({core_dcache_req_if.addr[0], 2'b0} >= `IO_BUS_BASE_ADDR);
|
||||
wire io_select = (| core_dcache_req_if.valid) ? is_io_addr : 0;
|
||||
|
||||
VX_dcache_arb dcache_io_arb (
|
||||
.req_select (io_select),
|
||||
|
||||
51
hw/rtl/VX_csr_arb.v
Normal file
51
hw/rtl/VX_csr_arb.v
Normal file
@@ -0,0 +1,51 @@
|
||||
`include "VX_define.vh"
|
||||
|
||||
module VX_csr_arb (
|
||||
input wire clk,
|
||||
input wire reset,
|
||||
|
||||
input wire csr_pipe_stall,
|
||||
|
||||
VX_csr_req_if csr_core_req_if,
|
||||
VX_csr_io_req_if csr_io_req_if,
|
||||
VX_csr_req_if issued_csr_req_if,
|
||||
|
||||
VX_wb_if csr_pipe_rsp_if,
|
||||
VX_wb_if csr_wb_if,
|
||||
VX_csr_io_rsp_if csr_io_rsp_if
|
||||
);
|
||||
|
||||
`UNUSED_VAR (clk)
|
||||
`UNUSED_VAR (reset)
|
||||
|
||||
wire pick_core = (| csr_core_req_if.valid);
|
||||
|
||||
// Mux between core and io
|
||||
assign issued_csr_req_if.valid = pick_core ? csr_core_req_if.valid : {`NUM_THREADS{csr_io_req_if.valid}};
|
||||
assign issued_csr_req_if.is_csr = pick_core ? csr_core_req_if.is_csr : 1'b1;
|
||||
assign issued_csr_req_if.alu_op = pick_core ? csr_core_req_if.alu_op : (csr_io_req_if.rw ? `ALU_CSR_RW : `ALU_CSR_RS);
|
||||
assign issued_csr_req_if.csr_addr = pick_core ? csr_core_req_if.csr_addr : csr_io_req_if.addr;
|
||||
assign issued_csr_req_if.csr_immed = pick_core ? csr_core_req_if.csr_immed : 0;
|
||||
assign issued_csr_req_if.csr_mask = pick_core ? csr_core_req_if.csr_mask : (csr_io_req_if.rw ? csr_io_req_if.data : 32'b0);
|
||||
assign issued_csr_req_if.is_io = !pick_core;
|
||||
assign issued_csr_req_if.warp_num = csr_core_req_if.warp_num;
|
||||
assign issued_csr_req_if.rd = csr_core_req_if.rd;
|
||||
assign issued_csr_req_if.wb = csr_core_req_if.wb;
|
||||
|
||||
assign csr_io_req_if.ready = !(csr_pipe_stall || pick_core);
|
||||
|
||||
// Core Writeback
|
||||
assign csr_wb_if.valid = csr_pipe_rsp_if.valid & {`NUM_THREADS{~csr_pipe_rsp_if.is_io}};
|
||||
assign csr_wb_if.data = csr_pipe_rsp_if.data;
|
||||
assign csr_wb_if.warp_num = csr_pipe_rsp_if.warp_num;
|
||||
assign csr_wb_if.rd = csr_pipe_rsp_if.rd;
|
||||
assign csr_wb_if.wb = csr_pipe_rsp_if.wb;
|
||||
assign csr_wb_if.curr_PC = csr_pipe_rsp_if.curr_PC;
|
||||
|
||||
// CSR I/O response
|
||||
assign csr_io_rsp_if.valid = csr_pipe_rsp_if.valid[0] & csr_pipe_rsp_if.is_io;
|
||||
assign csr_io_rsp_if.data = csr_pipe_rsp_if.data[0];
|
||||
wire x = csr_io_rsp_if.ready;
|
||||
`UNUSED_VAR(x)
|
||||
|
||||
endmodule
|
||||
@@ -43,18 +43,21 @@ module VX_csr_data #(
|
||||
|
||||
always @(*) begin
|
||||
case (read_addr)
|
||||
`CSR_LWID : read_data = 32'(warp_num);
|
||||
`CSR_GTID ,
|
||||
`CSR_GWID : read_data = CORE_ID * `NUM_WARPS + 32'(warp_num);
|
||||
`CSR_GCID : read_data = CORE_ID;
|
||||
`CSR_NT : read_data = `NUM_THREADS;
|
||||
`CSR_NW : read_data = `NUM_WARPS;
|
||||
`CSR_NC : read_data = `NUM_CORES * `NUM_CLUSTERS;
|
||||
`CSR_CYCLL : read_data = num_cycles[31:0];
|
||||
`CSR_CYCLH : read_data = num_cycles[63:32];
|
||||
`CSR_INSTL : read_data = num_instrs[31:0];
|
||||
`CSR_INSTH : read_data = num_instrs[63:32];
|
||||
default: read_data = 32'(csr_table[rd_addr]);
|
||||
`CSR_LWID : read_data = 32'(warp_num);
|
||||
`CSR_GTID ,
|
||||
`CSR_GWID : read_data = CORE_ID * `NUM_WARPS + 32'(warp_num);
|
||||
`CSR_GCID : read_data = CORE_ID;
|
||||
`CSR_NT : read_data = `NUM_THREADS;
|
||||
`CSR_NW : read_data = `NUM_WARPS;
|
||||
`CSR_NC : read_data = `NUM_CORES * `NUM_CLUSTERS;
|
||||
`CSR_CYCLE_L : read_data = num_cycles[31:0];
|
||||
`CSR_CYCLE_H : read_data = num_cycles[63:32];
|
||||
`CSR_INSTR_L : read_data = num_instrs[31:0];
|
||||
`CSR_INSTR_H : read_data = num_instrs[63:32];
|
||||
`CSR_VEND_ID : read_data = `VENDOR_ID;
|
||||
`CSR_ARCH_ID : read_data = `ARCHITECTURE_ID;
|
||||
`CSR_IMPL_ID : read_data = `IMPLEMENTATION_ID;
|
||||
default : read_data = 32'(csr_table[rd_addr]);
|
||||
endcase
|
||||
end
|
||||
|
||||
|
||||
86
hw/rtl/VX_csr_io_arb.v
Normal file
86
hw/rtl/VX_csr_io_arb.v
Normal file
@@ -0,0 +1,86 @@
|
||||
`include "VX_define.vh"
|
||||
|
||||
module VX_csr_io_arb #(
|
||||
parameter NUM_REQUESTS = 1,
|
||||
parameter REQS_BITS = `CLOG2(NUM_REQUESTS)
|
||||
) (
|
||||
input wire clk,
|
||||
input wire reset,
|
||||
|
||||
input wire [REQS_BITS-1:0] request_id,
|
||||
|
||||
// input requests
|
||||
input wire in_csr_io_req_valid,
|
||||
input wire [11:0] in_csr_io_req_addr,
|
||||
input wire in_csr_io_req_rw,
|
||||
input wire [31:0] in_csr_io_req_data,
|
||||
output wire in_csr_io_req_ready,
|
||||
|
||||
// input response
|
||||
input wire [NUM_REQUESTS-1:0] in_csr_io_rsp_valid,
|
||||
input wire [NUM_REQUESTS-1:0][31:0] in_csr_io_rsp_data,
|
||||
output wire [NUM_REQUESTS-1:0] in_csr_io_rsp_ready,
|
||||
|
||||
// output request
|
||||
output wire [NUM_REQUESTS-1:0] out_csr_io_req_valid,
|
||||
output wire [NUM_REQUESTS-1:0][11:0] out_csr_io_req_addr,
|
||||
output wire [NUM_REQUESTS-1:0] out_csr_io_req_rw,
|
||||
output wire [NUM_REQUESTS-1:0][31:0] out_csr_io_req_data,
|
||||
input wire [NUM_REQUESTS-1:0] out_csr_io_req_ready,
|
||||
|
||||
// output response
|
||||
output wire out_csr_io_rsp_valid,
|
||||
output wire [31:0] out_csr_io_rsp_data,
|
||||
input wire out_csr_io_rsp_ready
|
||||
);
|
||||
if (NUM_REQUESTS == 1) begin
|
||||
|
||||
`UNUSED_VAR (clk)
|
||||
`UNUSED_VAR (reset)
|
||||
|
||||
assign out_csr_io_req_valid = in_csr_io_req_valid;
|
||||
assign out_csr_io_req_rw = in_csr_io_req_rw;
|
||||
assign out_csr_io_req_addr = in_csr_io_req_addr;
|
||||
assign out_csr_io_req_data = in_csr_io_req_data;
|
||||
assign in_csr_io_req_ready = out_csr_io_req_ready;
|
||||
|
||||
assign out_csr_io_rsp_valid = in_csr_io_rsp_valid;
|
||||
assign out_csr_io_rsp_data = in_csr_io_rsp_data;
|
||||
assign in_csr_io_rsp_ready = out_csr_io_rsp_ready;
|
||||
|
||||
end else begin
|
||||
|
||||
genvar i;
|
||||
|
||||
for (i = 0; i < NUM_REQUESTS; i++) begin
|
||||
assign out_csr_io_req_valid[i] = in_csr_io_req_valid && (request_id == `REQS_BITS'(i));
|
||||
assign out_csr_io_req_rw[i] = in_csr_io_req_rw;
|
||||
assign out_csr_io_req_addr[i] = in_csr_io_req_addr;
|
||||
assign out_csr_io_req_data[i] = in_csr_io_req_data;
|
||||
end
|
||||
|
||||
assign in_csr_io_req_ready = out_csr_io_req_ready[request_id];
|
||||
|
||||
reg [REQS_BITS-1:0] bus_rsp_sel;
|
||||
|
||||
VX_fixed_arbiter #(
|
||||
.N(NUM_REQUESTS)
|
||||
) arbiter (
|
||||
.clk (clk),
|
||||
.reset (reset),
|
||||
.requests (in_csr_io_rsp_valid),
|
||||
.grant_index (bus_rsp_sel),
|
||||
`UNUSED_PIN (grant_valid),
|
||||
`UNUSED_PIN (grant_onehot)
|
||||
);
|
||||
|
||||
assign out_csr_io_rsp_valid = in_csr_io_rsp_valid [bus_rsp_sel];
|
||||
assign out_csr_io_rsp_data = in_csr_io_rsp_data [bus_rsp_sel];
|
||||
|
||||
for (i = 0; i < NUM_REQUESTS; i++) begin
|
||||
assign in_csr_io_rsp_ready[i] = out_csr_io_rsp_ready && (bus_rsp_sel == `REQS_BITS'(i));
|
||||
end
|
||||
|
||||
end
|
||||
|
||||
endmodule
|
||||
@@ -17,7 +17,7 @@ module VX_csr_pipe #(
|
||||
wire[4:0] rd_s2;
|
||||
wire[1:0] wb_s2;
|
||||
wire is_csr_s2;
|
||||
wire[`CSR_ADDR_SIZE-1:0] csr_address_s2;
|
||||
wire[`CSR_ADDR_SIZE-1:0] csr_addr_s2;
|
||||
wire[31:0] csr_read_data_s2;
|
||||
wire[31:0] csr_updated_data_s2;
|
||||
|
||||
@@ -29,17 +29,16 @@ module VX_csr_pipe #(
|
||||
) csr_data (
|
||||
.clk (clk),
|
||||
.reset (reset),
|
||||
.read_addr (csr_req_if.csr_address),
|
||||
.read_addr (csr_req_if.csr_addr),
|
||||
.read_data (csr_read_data_unqual),
|
||||
.write_enable (is_csr_s2),
|
||||
.write_data (csr_updated_data_s2[`CSR_WIDTH-1:0]),
|
||||
.write_addr (csr_address_s2),
|
||||
.write_addr (csr_addr_s2),
|
||||
.warp_num (csr_req_if.warp_num),
|
||||
.wb_valid (| writeback_if.valid)
|
||||
);
|
||||
|
||||
// wire hazard = (csr_address_s2 == csr_req_if.csr_address) & (warp_num_s2 == csr_req_if.warp_num) & |(valid_s2) & is_csr_s2;
|
||||
wire car_hazard = (csr_address_s2 == csr_req_if.csr_address) & (warp_num_s2 == csr_req_if.warp_num) & |(valid_s2) & is_csr_s2;
|
||||
wire car_hazard = (csr_addr_s2 == csr_req_if.csr_addr) & (warp_num_s2 == csr_req_if.warp_num) & |(valid_s2) & is_csr_s2;
|
||||
|
||||
assign csr_read_data = car_hazard ? csr_updated_data_s2 : csr_read_data_unqual;
|
||||
|
||||
@@ -55,14 +54,14 @@ module VX_csr_pipe #(
|
||||
end
|
||||
|
||||
VX_generic_register #(
|
||||
.N(32 + 32 + 12 + 1 + 2 + 5 + (`NW_BITS-1+1) + `NUM_THREADS)
|
||||
.N(32 + 32 + 12 + 1 + 1 + 2 + 5 + (`NW_BITS-1+1) + `NUM_THREADS)
|
||||
) csr_reg_s2 (
|
||||
.clk (clk),
|
||||
.reset(reset),
|
||||
.stall(no_slot_csr),
|
||||
.flush(1'b0),
|
||||
.in ({csr_req_if.valid, csr_req_if.warp_num, csr_req_if.rd, csr_req_if.wb, csr_req_if.is_csr, csr_req_if.csr_address, csr_read_data , csr_updated_data }),
|
||||
.out ({valid_s2 , warp_num_s2 , rd_s2 , wb_s2 , is_csr_s2 , csr_address_s2 , csr_read_data_s2, csr_updated_data_s2})
|
||||
.in ({csr_req_if.valid, csr_req_if.warp_num, csr_req_if.rd, csr_req_if.wb, csr_req_if.is_csr, csr_req_if.csr_addr, csr_req_if.is_io, csr_read_data , csr_updated_data }),
|
||||
.out ({valid_s2 , warp_num_s2 , rd_s2 , wb_s2 , is_csr_s2 , csr_addr_s2 , csr_wb_if.is_io , csr_read_data_s2, csr_updated_data_s2})
|
||||
);
|
||||
|
||||
assign csr_wb_if.valid = valid_s2;
|
||||
@@ -72,9 +71,9 @@ module VX_csr_pipe #(
|
||||
|
||||
genvar i;
|
||||
for (i = 0; i < `NUM_THREADS; i++) begin
|
||||
assign csr_wb_if.data[i] = (csr_address_s2 == `CSR_LTID) ? i :
|
||||
(csr_address_s2 == `CSR_GTID) ? (csr_read_data_s2 * `NUM_THREADS + i) :
|
||||
csr_read_data_s2;
|
||||
assign csr_wb_if.data[i] = (csr_addr_s2 == `CSR_LTID) ? i :
|
||||
(csr_addr_s2 == `CSR_GTID) ? (csr_read_data_s2 * `NUM_THREADS + i) :
|
||||
csr_read_data_s2;
|
||||
end
|
||||
|
||||
assign stall_gpr_csr = no_slot_csr && csr_req_if.is_csr && (| csr_req_if.valid);
|
||||
|
||||
@@ -21,28 +21,28 @@ module VX_dcache_arb (
|
||||
// output response
|
||||
VX_cache_core_rsp_if out_core_rsp_if
|
||||
);
|
||||
assign out0_core_req_if.core_req_valid = in_core_req_if.core_req_valid & {`NUM_THREADS{~req_select}};
|
||||
assign out0_core_req_if.core_req_rw = in_core_req_if.core_req_rw;
|
||||
assign out0_core_req_if.core_req_byteen = in_core_req_if.core_req_byteen;
|
||||
assign out0_core_req_if.core_req_addr = in_core_req_if.core_req_addr;
|
||||
assign out0_core_req_if.core_req_data = in_core_req_if.core_req_data;
|
||||
assign out0_core_req_if.core_req_tag = in_core_req_if.core_req_tag;
|
||||
assign out0_core_req_if.valid = in_core_req_if.valid & {`NUM_THREADS{~req_select}};
|
||||
assign out0_core_req_if.rw = in_core_req_if.rw;
|
||||
assign out0_core_req_if.byteen = in_core_req_if.byteen;
|
||||
assign out0_core_req_if.addr = in_core_req_if.addr;
|
||||
assign out0_core_req_if.data = in_core_req_if.data;
|
||||
assign out0_core_req_if.tag = in_core_req_if.tag;
|
||||
|
||||
assign out1_core_req_if.core_req_valid = in_core_req_if.core_req_valid & {`NUM_THREADS{req_select}};
|
||||
assign out1_core_req_if.core_req_rw = in_core_req_if.core_req_rw;
|
||||
assign out1_core_req_if.core_req_byteen = in_core_req_if.core_req_byteen;
|
||||
assign out1_core_req_if.core_req_addr = in_core_req_if.core_req_addr;
|
||||
assign out1_core_req_if.core_req_data = in_core_req_if.core_req_data;
|
||||
assign out1_core_req_if.core_req_tag = in_core_req_if.core_req_tag;
|
||||
assign out1_core_req_if.valid = in_core_req_if.valid & {`NUM_THREADS{req_select}};
|
||||
assign out1_core_req_if.rw = in_core_req_if.rw;
|
||||
assign out1_core_req_if.byteen = in_core_req_if.byteen;
|
||||
assign out1_core_req_if.addr = in_core_req_if.addr;
|
||||
assign out1_core_req_if.data = in_core_req_if.data;
|
||||
assign out1_core_req_if.tag = in_core_req_if.tag;
|
||||
|
||||
assign in_core_req_if.core_req_ready = req_select ? out1_core_req_if.core_req_ready : out0_core_req_if.core_req_ready;
|
||||
assign in_core_req_if.ready = req_select ? out1_core_req_if.ready : out0_core_req_if.ready;
|
||||
|
||||
wire rsp_select0 = (| in0_core_rsp_if.core_rsp_valid);
|
||||
wire rsp_select0 = (| in0_core_rsp_if.valid);
|
||||
|
||||
assign out_core_rsp_if.core_rsp_valid = rsp_select0 ? in0_core_rsp_if.core_rsp_valid : in1_core_rsp_if.core_rsp_valid;
|
||||
assign out_core_rsp_if.core_rsp_data = rsp_select0 ? in0_core_rsp_if.core_rsp_data : in1_core_rsp_if.core_rsp_data;
|
||||
assign out_core_rsp_if.core_rsp_tag = rsp_select0 ? in0_core_rsp_if.core_rsp_tag : in1_core_rsp_if.core_rsp_tag;
|
||||
assign in0_core_rsp_if.core_rsp_ready = out_core_rsp_if.core_rsp_ready && rsp_select0;
|
||||
assign in1_core_rsp_if.core_rsp_ready = out_core_rsp_if.core_rsp_ready && !rsp_select0;
|
||||
assign out_core_rsp_if.valid = rsp_select0 ? in0_core_rsp_if.valid : in1_core_rsp_if.valid;
|
||||
assign out_core_rsp_if.data = rsp_select0 ? in0_core_rsp_if.data : in1_core_rsp_if.data;
|
||||
assign out_core_rsp_if.tag = rsp_select0 ? in0_core_rsp_if.tag : in1_core_rsp_if.tag;
|
||||
assign in0_core_rsp_if.ready = out_core_rsp_if.ready && rsp_select0;
|
||||
assign in1_core_rsp_if.ready = out_core_rsp_if.ready && !rsp_select0;
|
||||
|
||||
endmodule
|
||||
@@ -12,7 +12,7 @@ module VX_decode(
|
||||
);
|
||||
wire in_valid = (| fd_inst_meta_de.valid);
|
||||
wire[31:0] in_instruction = fd_inst_meta_de.instruction;
|
||||
wire[31:0] in_curr_PC = fd_inst_meta_de.inst_pc;
|
||||
wire[31:0] in_curr_PC = fd_inst_meta_de.curr_PC;
|
||||
wire[`NW_BITS-1:0] in_warp_num = fd_inst_meta_de.warp_num;
|
||||
|
||||
assign frE_to_bckE_req_if.curr_PC = in_curr_PC;
|
||||
@@ -104,7 +104,7 @@ module VX_decode(
|
||||
assign is_lui = (curr_opcode == `INST_LUI);
|
||||
assign is_auipc = (curr_opcode == `INST_AUIPC);
|
||||
assign is_csr = (curr_opcode == `INST_SYS) && (func3 != 0);
|
||||
assign is_csr_immed = (is_csr) && (func3[2] == 1);
|
||||
assign is_csr_immed = is_csr && (func3[2] == 1);
|
||||
|
||||
assign is_gpgpu = (curr_opcode == `INST_GPGPU);
|
||||
|
||||
@@ -114,8 +114,8 @@ module VX_decode(
|
||||
assign is_split = is_gpgpu && (func3 == 2); // Goes to BE
|
||||
assign is_join = is_gpgpu && (func3 == 3); // Doesn't go to BE
|
||||
|
||||
assign join_if.is_join = is_join && in_valid;
|
||||
assign join_if.join_warp_num = in_warp_num;
|
||||
assign join_if.is_join = is_join && in_valid;
|
||||
assign join_if.warp_num = in_warp_num;
|
||||
|
||||
assign frE_to_bckE_req_if.is_wspawn = is_wspawn;
|
||||
assign frE_to_bckE_req_if.is_tmc = is_tmc;
|
||||
@@ -204,7 +204,7 @@ module VX_decode(
|
||||
assign csr_cond1 = func3 != 3'h0;
|
||||
assign csr_cond2 = u_12 >= 12'h2;
|
||||
|
||||
assign frE_to_bckE_req_if.csr_address = (csr_cond1 && csr_cond2) ? u_12 : 12'h55;
|
||||
assign frE_to_bckE_req_if.csr_addr = (csr_cond1 && csr_cond2) ? u_12 : 12'h55;
|
||||
|
||||
// ITYPE IMEED
|
||||
assign alu_shift_i = (func3 == 3'h1) || (func3 == 3'h5);
|
||||
@@ -227,7 +227,7 @@ module VX_decode(
|
||||
case (curr_opcode)
|
||||
`INST_B: begin
|
||||
// $display("BRANCH IN DECODE");
|
||||
temp_branch_stall = 1'b1 && in_valid;
|
||||
temp_branch_stall = in_valid;
|
||||
case (func3)
|
||||
3'h0: temp_branch_type = `BR_EQ;
|
||||
3'h1: temp_branch_type = `BR_NE;
|
||||
@@ -240,15 +240,15 @@ module VX_decode(
|
||||
end
|
||||
`INST_JAL: begin
|
||||
temp_branch_type = `BR_NO;
|
||||
temp_branch_stall = 1'b1 && in_valid;
|
||||
temp_branch_stall = in_valid;
|
||||
end
|
||||
`INST_JALR: begin
|
||||
temp_branch_type = `BR_NO;
|
||||
temp_branch_stall = 1'b1 && in_valid;
|
||||
temp_branch_stall = in_valid;
|
||||
end
|
||||
default: begin
|
||||
temp_branch_type = `BR_NO;
|
||||
temp_branch_stall = 1'b0 && in_valid;
|
||||
temp_branch_stall = 1'b0;
|
||||
end
|
||||
endcase
|
||||
end
|
||||
|
||||
@@ -72,6 +72,10 @@
|
||||
|
||||
`define CSR_WIDTH 12
|
||||
|
||||
`define DIV_LATENCY 22
|
||||
|
||||
`define MUL_LATENCY 2
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
`define BYTE_EN_NO 3'h7
|
||||
@@ -284,6 +288,7 @@
|
||||
`define VX_DRAM_TAG_WIDTH `L3DRAM_TAG_WIDTH
|
||||
`define VX_SNP_TAG_WIDTH `L3SNP_TAG_WIDTH
|
||||
`define VX_CORE_TAG_WIDTH `L3CORE_TAG_WIDTH
|
||||
`define VX_CSR_ID_WIDTH `CLOG2(`NUM_CLUSTERS * `NUM_CORES)
|
||||
|
||||
`define DRAM_TO_BYTE_ADDR(x) {x, (32-$bits(x))'(0)}
|
||||
|
||||
|
||||
@@ -15,18 +15,18 @@ module VX_exec_unit (
|
||||
output wire delay
|
||||
);
|
||||
|
||||
wire[`NUM_THREADS-1:0][31:0] in_a_reg_data;
|
||||
wire[`NUM_THREADS-1:0][31:0] in_b_reg_data;
|
||||
wire[4:0] in_alu_op;
|
||||
wire in_rs2_src;
|
||||
wire[31:0] in_itype_immed;
|
||||
wire [`NUM_THREADS-1:0][31:0] in_a_reg_data;
|
||||
wire [`NUM_THREADS-1:0][31:0] in_b_reg_data;
|
||||
wire [4:0] in_alu_op;
|
||||
wire in_rs2_src;
|
||||
wire [31:0] in_itype_immed;
|
||||
`DEBUG_BEGIN
|
||||
wire[2:0] in_branch_type;
|
||||
wire [2:0] in_branch_type;
|
||||
`DEBUG_END
|
||||
wire[19:0] in_upper_immed;
|
||||
wire in_jal;
|
||||
wire[31:0] in_jal_offset;
|
||||
wire[31:0] in_curr_PC;
|
||||
wire [19:0] in_upper_immed;
|
||||
wire in_jal;
|
||||
wire [31:0] in_jal_offset;
|
||||
wire [31:0] in_curr_PC;
|
||||
|
||||
assign in_a_reg_data = exec_unit_req_if.a_reg_data;
|
||||
assign in_b_reg_data = exec_unit_req_if.b_reg_data;
|
||||
@@ -39,12 +39,12 @@ module VX_exec_unit (
|
||||
assign in_jal_offset = exec_unit_req_if.jal_offset;
|
||||
assign in_curr_PC = exec_unit_req_if.curr_PC;
|
||||
|
||||
wire[`NUM_THREADS-1:0][31:0] alu_result;
|
||||
wire[`NUM_THREADS-1:0] alu_stall;
|
||||
wire [`NUM_THREADS-1:0][31:0] alu_result;
|
||||
wire [`NUM_THREADS-1:0] alu_stall;
|
||||
|
||||
genvar i;
|
||||
generate
|
||||
for (i = 0; i < `NUM_THREADS; i++) begin : alu_defs
|
||||
for (i = 0; i < `NUM_THREADS; i++) begin
|
||||
VX_alu_unit alu_unit (
|
||||
.clk (clk),
|
||||
.reset (reset),
|
||||
@@ -61,25 +61,21 @@ module VX_exec_unit (
|
||||
end
|
||||
endgenerate
|
||||
|
||||
wire internal_stall;
|
||||
assign internal_stall = (| alu_stall);
|
||||
wire internal_stall = (| alu_stall);
|
||||
|
||||
assign delay = no_slot_exec || internal_stall;
|
||||
|
||||
`DEBUG_BEGIN
|
||||
wire [$clog2(`NUM_THREADS)-1:0] jal_branch_use_index;
|
||||
wire jal_branch_found_valid;
|
||||
`DEBUG_END
|
||||
|
||||
VX_priority_encoder #(
|
||||
.N(`NUM_THREADS)
|
||||
) choose_alu_result (
|
||||
.data_in (exec_unit_req_if.valid),
|
||||
.data_out (jal_branch_use_index),
|
||||
.valid_out (jal_branch_found_valid)
|
||||
.data_in (exec_unit_req_if.valid),
|
||||
.data_out (jal_branch_use_index),
|
||||
`UNUSED_PIN (valid_out)
|
||||
);
|
||||
|
||||
wire[31:0] branch_use_alu_result = alu_result[jal_branch_use_index];
|
||||
wire [31:0] branch_use_alu_result = alu_result[jal_branch_use_index];
|
||||
|
||||
reg temp_branch_dir;
|
||||
always @(*)
|
||||
@@ -96,7 +92,7 @@ module VX_exec_unit (
|
||||
endcase // in_branch_type
|
||||
end
|
||||
|
||||
wire[`NUM_THREADS-1:0][31:0] duplicate_PC_data;
|
||||
wire [`NUM_THREADS-1:0][31:0] duplicate_PC_data;
|
||||
|
||||
generate
|
||||
for (i = 0; i < `NUM_THREADS; i++) begin
|
||||
@@ -116,15 +112,15 @@ module VX_exec_unit (
|
||||
assign inst_exec_wb_if.curr_PC = in_curr_PC;
|
||||
|
||||
// Jal rsp
|
||||
assign jal_rsp_temp_if.jal = in_jal;
|
||||
assign jal_rsp_temp_if.jal_dest = $signed(in_a_reg_data[jal_branch_use_index]) + $signed(in_jal_offset);
|
||||
assign jal_rsp_temp_if.jal_warp_num = exec_unit_req_if.warp_num;
|
||||
assign jal_rsp_temp_if.valid = in_jal;
|
||||
assign jal_rsp_temp_if.dest = $signed(in_a_reg_data[jal_branch_use_index]) + $signed(in_jal_offset);
|
||||
assign jal_rsp_temp_if.warp_num = exec_unit_req_if.warp_num;
|
||||
|
||||
// Branch rsp
|
||||
assign branch_rsp_temp_if.valid_branch = (exec_unit_req_if.branch_type != `BR_NO) && (| exec_unit_req_if.valid);
|
||||
assign branch_rsp_temp_if.branch_dir = temp_branch_dir;
|
||||
assign branch_rsp_temp_if.branch_warp_num = exec_unit_req_if.warp_num;
|
||||
assign branch_rsp_temp_if.branch_dest = $signed(exec_unit_req_if.curr_PC) + ($signed(exec_unit_req_if.itype_immed) << 1); // itype_immed = branch_offset
|
||||
assign branch_rsp_temp_if.valid = (exec_unit_req_if.branch_type != `BR_NO) && (| exec_unit_req_if.valid);
|
||||
assign branch_rsp_temp_if.dir = temp_branch_dir;
|
||||
assign branch_rsp_temp_if.warp_num = exec_unit_req_if.warp_num;
|
||||
assign branch_rsp_temp_if.dest = $signed(exec_unit_req_if.curr_PC) + ($signed(exec_unit_req_if.itype_immed) << 1); // itype_immed = branch_offset
|
||||
|
||||
VX_generic_register #(
|
||||
.N(33 + `NW_BITS-1 + 1)
|
||||
@@ -133,8 +129,8 @@ module VX_exec_unit (
|
||||
.reset (reset),
|
||||
.stall (1'b0),
|
||||
.flush (1'b0),
|
||||
.in ({jal_rsp_temp_if.jal, jal_rsp_temp_if.jal_dest, jal_rsp_temp_if.jal_warp_num}),
|
||||
.out ({jal_rsp_if.jal , jal_rsp_if.jal_dest , jal_rsp_if.jal_warp_num})
|
||||
.in ({jal_rsp_temp_if.valid, jal_rsp_temp_if.dest, jal_rsp_temp_if.warp_num}),
|
||||
.out ({jal_rsp_if.valid , jal_rsp_if.dest , jal_rsp_if.warp_num})
|
||||
);
|
||||
|
||||
VX_generic_register #(
|
||||
@@ -144,8 +140,8 @@ module VX_exec_unit (
|
||||
.reset (reset),
|
||||
.stall (1'b0),
|
||||
.flush (1'b0),
|
||||
.in ({branch_rsp_temp_if.valid_branch, branch_rsp_temp_if.branch_dir, branch_rsp_temp_if.branch_warp_num, branch_rsp_temp_if.branch_dest}),
|
||||
.out ({branch_rsp_if.valid_branch , branch_rsp_if.branch_dir , branch_rsp_if.branch_warp_num , branch_rsp_if.branch_dest })
|
||||
.in ({branch_rsp_temp_if.valid, branch_rsp_temp_if.dir, branch_rsp_temp_if.warp_num, branch_rsp_temp_if.dest}),
|
||||
.out ({branch_rsp_if.valid , branch_rsp_if.dir , branch_rsp_if.warp_num , branch_rsp_if.dest })
|
||||
);
|
||||
|
||||
endmodule : VX_exec_unit
|
||||
@@ -57,7 +57,7 @@ module VX_fetch (
|
||||
|
||||
// Join
|
||||
.is_join (join_if.is_join),
|
||||
.join_warp_num (join_if.join_warp_num),
|
||||
.join_warp_num (join_if.warp_num),
|
||||
|
||||
// Split
|
||||
.is_split (warp_ctl_if.is_split),
|
||||
@@ -68,15 +68,15 @@ module VX_fetch (
|
||||
.split_warp_num (warp_ctl_if.warp_num),
|
||||
|
||||
// JAL
|
||||
.jal (jal_rsp_if.jal),
|
||||
.jal_dest (jal_rsp_if.jal_dest),
|
||||
.jal_warp_num (jal_rsp_if.jal_warp_num),
|
||||
.jal (jal_rsp_if.valid),
|
||||
.dest (jal_rsp_if.dest),
|
||||
.jal_warp_num (jal_rsp_if.warp_num),
|
||||
|
||||
// Branch
|
||||
.branch_valid (branch_rsp_if.valid_branch),
|
||||
.branch_dir (branch_rsp_if.branch_dir),
|
||||
.branch_dest (branch_rsp_if.branch_dest),
|
||||
.branch_warp_num (branch_rsp_if.branch_warp_num),
|
||||
.branch_valid (branch_rsp_if.valid),
|
||||
.branch_dir (branch_rsp_if.dir),
|
||||
.branch_dest (branch_rsp_if.dest),
|
||||
.branch_warp_num (branch_rsp_if.warp_num),
|
||||
|
||||
// Outputs
|
||||
.thread_mask (thread_mask),
|
||||
@@ -89,7 +89,7 @@ module VX_fetch (
|
||||
assign fe_inst_meta_fi.warp_num = warp_num;
|
||||
assign fe_inst_meta_fi.valid = thread_mask;
|
||||
assign fe_inst_meta_fi.instruction = 32'h0;
|
||||
assign fe_inst_meta_fi.inst_pc = warp_pc;
|
||||
assign fe_inst_meta_fi.curr_PC = warp_pc;
|
||||
|
||||
`DEBUG_BEGIN
|
||||
wire start_mat_add = scheduled_warp && (warp_pc == 32'h80000ed8) && (warp_num == 0);
|
||||
|
||||
@@ -54,12 +54,15 @@ module VX_front_end #(
|
||||
.fe_inst_meta_fi (fe_inst_meta_fi)
|
||||
);
|
||||
|
||||
VX_f_d_reg f_i_reg (
|
||||
.clk (clk),
|
||||
.reset (reset),
|
||||
.freeze (icache_stage_delay),
|
||||
.fe_inst_meta_fd (fe_inst_meta_fi),
|
||||
.fd_inst_meta_de (fe_inst_meta_fi2)
|
||||
VX_generic_register #(
|
||||
.N(64+`NW_BITS-1+1+`NUM_THREADS)
|
||||
) f_d_reg (
|
||||
.clk (clk),
|
||||
.reset (reset),
|
||||
.stall (icache_stage_delay),
|
||||
.flush (1'b0),
|
||||
.in ({fe_inst_meta_fi.instruction, fe_inst_meta_fi.curr_PC, fe_inst_meta_fi.warp_num, fe_inst_meta_fi.valid}),
|
||||
.out ({fe_inst_meta_fi2.instruction, fe_inst_meta_fi2.curr_PC, fe_inst_meta_fi2.warp_num, fe_inst_meta_fi2.valid})
|
||||
);
|
||||
|
||||
VX_icache_stage #(
|
||||
@@ -79,12 +82,15 @@ module VX_front_end #(
|
||||
.icache_req_if (icache_req_if)
|
||||
);
|
||||
|
||||
VX_i_d_reg i_d_reg (
|
||||
.clk (clk),
|
||||
.reset (reset),
|
||||
.freeze (total_freeze),
|
||||
.fe_inst_meta_fd (fe_inst_meta_id),
|
||||
.fd_inst_meta_de (fd_inst_meta_de)
|
||||
VX_generic_register #(
|
||||
.N(64 + `NW_BITS-1 + 1 + `NUM_THREADS)
|
||||
) i_d_reg (
|
||||
.clk (clk),
|
||||
.reset (reset),
|
||||
.stall (total_freeze),
|
||||
.flush (1'b0),
|
||||
.in ({fe_inst_meta_id.instruction, fe_inst_meta_id.curr_PC, fe_inst_meta_id.warp_num, fe_inst_meta_id.valid}),
|
||||
.out ({fd_inst_meta_de.instruction, fd_inst_meta_de.curr_PC, fd_inst_meta_de.warp_num, fd_inst_meta_de.valid})
|
||||
);
|
||||
|
||||
VX_decode decode (
|
||||
@@ -94,16 +100,16 @@ module VX_front_end #(
|
||||
.join_if (join_if)
|
||||
);
|
||||
|
||||
wire no_br_stall = 0;
|
||||
|
||||
VX_d_e_reg d_e_reg (
|
||||
.clk (clk),
|
||||
.reset (reset),
|
||||
.branch_stall (no_br_stall),
|
||||
.freeze (total_freeze),
|
||||
.frE_to_bckE_req_if (frE_to_bckE_req_if),
|
||||
.bckE_req_if (bckE_req_if)
|
||||
);
|
||||
VX_generic_register #(
|
||||
.N(233 + `NW_BITS-1 + 1 + `NUM_THREADS)
|
||||
) d_e_reg (
|
||||
.clk (clk),
|
||||
.reset (reset),
|
||||
.stall (total_freeze),
|
||||
.flush (1'b0),
|
||||
.in ({frE_to_bckE_req_if.csr_addr, frE_to_bckE_req_if.is_jal, frE_to_bckE_req_if.is_etype, frE_to_bckE_req_if.is_csr, frE_to_bckE_req_if.csr_immed, frE_to_bckE_req_if.csr_mask, frE_to_bckE_req_if.rd, frE_to_bckE_req_if.rs1, frE_to_bckE_req_if.rs2, frE_to_bckE_req_if.alu_op, frE_to_bckE_req_if.wb, frE_to_bckE_req_if.rs2_src, frE_to_bckE_req_if.itype_immed, frE_to_bckE_req_if.mem_read, frE_to_bckE_req_if.mem_write, frE_to_bckE_req_if.branch_type, frE_to_bckE_req_if.upper_immed, frE_to_bckE_req_if.curr_PC, frE_to_bckE_req_if.jal, frE_to_bckE_req_if.jal_offset, frE_to_bckE_req_if.next_PC, frE_to_bckE_req_if.valid, frE_to_bckE_req_if.warp_num, frE_to_bckE_req_if.is_wspawn, frE_to_bckE_req_if.is_tmc, frE_to_bckE_req_if.is_split, frE_to_bckE_req_if.is_barrier}),
|
||||
.out ({bckE_req_if.csr_addr , bckE_req_if.is_jal , bckE_req_if.is_etype ,bckE_req_if.is_csr , bckE_req_if.csr_immed , bckE_req_if.csr_mask , bckE_req_if.rd , bckE_req_if.rs1 , bckE_req_if.rs2 , bckE_req_if.alu_op , bckE_req_if.wb , bckE_req_if.rs2_src , bckE_req_if.itype_immed , bckE_req_if.mem_read , bckE_req_if.mem_write , bckE_req_if.branch_type , bckE_req_if.upper_immed , bckE_req_if.curr_PC , bckE_req_if.jal , bckE_req_if.jal_offset , bckE_req_if.next_PC , bckE_req_if.valid , bckE_req_if.warp_num , bckE_req_if.is_wspawn , bckE_req_if.is_tmc , bckE_req_if.is_split , bckE_req_if.is_barrier })
|
||||
);
|
||||
|
||||
endmodule
|
||||
|
||||
|
||||
@@ -8,7 +8,7 @@ module VX_gpr_stage (
|
||||
input wire memory_delay,
|
||||
input wire exec_delay,
|
||||
input wire stall_gpr_csr,
|
||||
output wire gpr_stage_delay,
|
||||
output wire delay,
|
||||
|
||||
// decodee inputs
|
||||
VX_backend_req_if bckE_req_if,
|
||||
@@ -30,6 +30,8 @@ module VX_gpr_stage (
|
||||
wire is_jal = bckE_req_if.is_jal;
|
||||
`DEBUG_END
|
||||
|
||||
assign csr_req_if.is_io = 1'b0; // GPR only issues csr requests coming from core
|
||||
|
||||
VX_gpr_read_if gpr_read_if();
|
||||
assign gpr_read_if.rs1 = bckE_req_if.rs1;
|
||||
assign gpr_read_if.rs2 = bckE_req_if.rs2;
|
||||
@@ -79,7 +81,7 @@ module VX_gpr_stage (
|
||||
|
||||
wire stall_csr = stall_gpr_csr && bckE_req_if.is_csr && (| bckE_req_if.valid);
|
||||
|
||||
assign gpr_stage_delay = stall_lsu || stall_exec || stall_csr;
|
||||
assign delay = stall_lsu || stall_exec || stall_csr;
|
||||
|
||||
`ifdef ASIC
|
||||
wire delayed_lsu_last_cycle;
|
||||
@@ -97,10 +99,10 @@ module VX_gpr_stage (
|
||||
);
|
||||
|
||||
wire [`NUM_THREADS-1:0][31:0] temp_store_data;
|
||||
wire [`NUM_THREADS-1:0][31:0] temp_base_address; // A reg data
|
||||
wire [`NUM_THREADS-1:0][31:0] temp_base_addr; // A reg data
|
||||
|
||||
wire [`NUM_THREADS-1:0][31:0] real_store_data;
|
||||
wire [`NUM_THREADS-1:0][31:0] real_base_address; // A reg data
|
||||
wire [`NUM_THREADS-1:0][31:0] real_base_addr; // A reg data
|
||||
|
||||
wire store_curr_real = !delayed_lsu_last_cycle && stall_lsu;
|
||||
|
||||
@@ -111,15 +113,15 @@ module VX_gpr_stage (
|
||||
.reset (reset),
|
||||
.stall (!store_curr_real),
|
||||
.flush (stall_rest),
|
||||
.in ({real_store_data, real_base_address}),
|
||||
.out ({temp_store_data, temp_base_address})
|
||||
.in ({real_store_data, real_base_addr}),
|
||||
.out ({temp_store_data, temp_base_addr})
|
||||
);
|
||||
|
||||
assign real_store_data = lsu_req_temp_if.store_data;
|
||||
assign real_base_address = lsu_req_temp_if.base_address;
|
||||
assign real_store_data = lsu_req_temp_if.store_data;
|
||||
assign real_base_addr = lsu_req_temp_if.base_addr;
|
||||
|
||||
assign lsu_req_if.store_data = (delayed_lsu_last_cycle) ? temp_store_data : real_store_data;
|
||||
assign lsu_req_if.base_address = (delayed_lsu_last_cycle) ? temp_base_address : real_base_address;
|
||||
assign lsu_req_if.store_data = (delayed_lsu_last_cycle) ? temp_store_data : real_store_data;
|
||||
assign lsu_req_if.base_addr = (delayed_lsu_last_cycle) ? temp_base_addr : real_base_addr;
|
||||
|
||||
VX_generic_register #(
|
||||
.N(77 + `NW_BITS-1 + 1 + (`NUM_THREADS))
|
||||
@@ -139,11 +141,11 @@ module VX_gpr_stage (
|
||||
.reset (reset),
|
||||
.stall (stall_exec),
|
||||
.flush (flush_exec),
|
||||
.in ({exec_unit_req_temp_if.valid, exec_unit_req_temp_if.warp_num, exec_unit_req_temp_if.curr_PC, exec_unit_req_temp_if.next_PC, exec_unit_req_temp_if.rd, exec_unit_req_temp_if.wb, exec_unit_req_temp_if.alu_op, exec_unit_req_temp_if.rs1, exec_unit_req_temp_if.rs2, exec_unit_req_temp_if.rs2_src, exec_unit_req_temp_if.itype_immed, exec_unit_req_temp_if.upper_immed, exec_unit_req_temp_if.branch_type, exec_unit_req_temp_if.is_jal, exec_unit_req_temp_if.jal, exec_unit_req_temp_if.jal_offset, exec_unit_req_temp_if.is_etype, exec_unit_req_temp_if.wspawn, exec_unit_req_temp_if.is_csr, exec_unit_req_temp_if.csr_address, exec_unit_req_temp_if.csr_immed, exec_unit_req_temp_if.csr_mask}),
|
||||
.out ({exec_unit_req_if.valid , exec_unit_req_if.warp_num , exec_unit_req_if.curr_PC , exec_unit_req_if.next_PC , exec_unit_req_if.rd , exec_unit_req_if.wb , exec_unit_req_if.alu_op , exec_unit_req_if.rs1 , exec_unit_req_if.rs2 , exec_unit_req_if.rs2_src , exec_unit_req_if.itype_immed , exec_unit_req_if.upper_immed , exec_unit_req_if.branch_type , exec_unit_req_if.is_jal , exec_unit_req_if.jal , exec_unit_req_if.jal_offset , exec_unit_req_if.is_etype , exec_unit_req_if.wspawn , exec_unit_req_if.is_csr , exec_unit_req_if.csr_address , exec_unit_req_if.csr_immed , exec_unit_req_if.csr_mask })
|
||||
.in ({exec_unit_req_temp_if.valid, exec_unit_req_temp_if.warp_num, exec_unit_req_temp_if.curr_PC, exec_unit_req_temp_if.next_PC, exec_unit_req_temp_if.rd, exec_unit_req_temp_if.wb, exec_unit_req_temp_if.alu_op, exec_unit_req_temp_if.rs1, exec_unit_req_temp_if.rs2, exec_unit_req_temp_if.rs2_src, exec_unit_req_temp_if.itype_immed, exec_unit_req_temp_if.upper_immed, exec_unit_req_temp_if.branch_type, exec_unit_req_temp_if.is_jal, exec_unit_req_temp_if.jal, exec_unit_req_temp_if.jal_offset, exec_unit_req_temp_if.is_etype, exec_unit_req_temp_if.wspawn, exec_unit_req_temp_if.is_csr, exec_unit_req_temp_if.csr_addr, exec_unit_req_temp_if.csr_immed, exec_unit_req_temp_if.csr_mask}),
|
||||
.out ({exec_unit_req_if.valid , exec_unit_req_if.warp_num , exec_unit_req_if.curr_PC , exec_unit_req_if.next_PC , exec_unit_req_if.rd , exec_unit_req_if.wb , exec_unit_req_if.alu_op , exec_unit_req_if.rs1 , exec_unit_req_if.rs2 , exec_unit_req_if.rs2_src , exec_unit_req_if.itype_immed , exec_unit_req_if.upper_immed , exec_unit_req_if.branch_type , exec_unit_req_if.is_jal , exec_unit_req_if.jal , exec_unit_req_if.jal_offset , exec_unit_req_if.is_etype , exec_unit_req_if.wspawn , exec_unit_req_if.is_csr , exec_unit_req_if.csr_addr , exec_unit_req_if.csr_immed , exec_unit_req_if.csr_mask })
|
||||
);
|
||||
|
||||
assign exec_unit_req_if.a_reg_data = real_base_address;
|
||||
assign exec_unit_req_if.a_reg_data = real_base_addr;
|
||||
assign exec_unit_req_if.b_reg_data = real_store_data;
|
||||
|
||||
VX_generic_register #(
|
||||
@@ -157,7 +159,7 @@ module VX_gpr_stage (
|
||||
.out ({gpu_inst_req_if.valid , gpu_inst_req_if.warp_num , gpu_inst_req_if.is_wspawn , gpu_inst_req_if.is_tmc , gpu_inst_req_if.is_split , gpu_inst_req_if.is_barrier , gpu_inst_req_if.next_PC })
|
||||
);
|
||||
|
||||
assign gpu_inst_req_if.a_reg_data = real_base_address;
|
||||
assign gpu_inst_req_if.a_reg_data = real_base_addr;
|
||||
assign gpu_inst_req_if.rd2 = real_store_data;
|
||||
|
||||
VX_generic_register #(
|
||||
@@ -167,10 +169,11 @@ module VX_gpr_stage (
|
||||
.reset (reset),
|
||||
.stall (stall_gpr_csr),
|
||||
.flush (flush_rest),
|
||||
.in ({csr_req_temp_if.valid, csr_req_temp_if.warp_num, csr_req_temp_if.rd, csr_req_temp_if.wb, csr_req_temp_if.alu_op, csr_req_temp_if.is_csr, csr_req_temp_if.csr_address, csr_req_temp_if.csr_immed, csr_req_temp_if.csr_mask}),
|
||||
.out ({csr_req_if.valid , csr_req_if.warp_num , csr_req_if.rd , csr_req_if.wb , csr_req_if.alu_op , csr_req_if.is_csr , csr_req_if.csr_address , csr_req_if.csr_immed , csr_req_if.csr_mask })
|
||||
.in ({csr_req_temp_if.valid, csr_req_temp_if.warp_num, csr_req_temp_if.rd, csr_req_temp_if.wb, csr_req_temp_if.alu_op, csr_req_temp_if.is_csr, csr_req_temp_if.csr_addr, csr_req_temp_if.csr_immed, csr_req_temp_if.csr_mask}),
|
||||
.out ({csr_req_if.valid , csr_req_if.warp_num , csr_req_if.rd , csr_req_if.wb , csr_req_if.alu_op , csr_req_if.is_csr , csr_req_if.csr_addr , csr_req_if.csr_immed , csr_req_if.csr_mask })
|
||||
);
|
||||
|
||||
|
||||
`else
|
||||
|
||||
// 341
|
||||
@@ -181,8 +184,8 @@ module VX_gpr_stage (
|
||||
.reset (reset),
|
||||
.stall (stall_lsu),
|
||||
.flush (flush_lsu),
|
||||
.in ({lsu_req_temp_if.valid, lsu_req_temp_if.curr_PC, lsu_req_temp_if.warp_num, lsu_req_temp_if.store_data, lsu_req_temp_if.base_address, lsu_req_temp_if.offset, lsu_req_temp_if.mem_read, lsu_req_temp_if.mem_write, lsu_req_temp_if.rd, lsu_req_temp_if.wb}),
|
||||
.out ({lsu_req_if.valid , lsu_req_if.curr_PC , lsu_req_if.warp_num , lsu_req_if.store_data , lsu_req_if.base_address , lsu_req_if.offset , lsu_req_if.mem_read , lsu_req_if.mem_write , lsu_req_if.rd , lsu_req_if.wb })
|
||||
.in ({lsu_req_temp_if.valid, lsu_req_temp_if.curr_PC, lsu_req_temp_if.warp_num, lsu_req_temp_if.store_data, lsu_req_temp_if.base_addr, lsu_req_temp_if.offset, lsu_req_temp_if.mem_read, lsu_req_temp_if.mem_write, lsu_req_temp_if.rd, lsu_req_temp_if.wb}),
|
||||
.out ({lsu_req_if.valid , lsu_req_if.curr_PC , lsu_req_if.warp_num , lsu_req_if.store_data , lsu_req_if.base_addr , lsu_req_if.offset , lsu_req_if.mem_read , lsu_req_if.mem_write , lsu_req_if.rd , lsu_req_if.wb })
|
||||
);
|
||||
|
||||
VX_generic_register #(
|
||||
@@ -192,8 +195,8 @@ module VX_gpr_stage (
|
||||
.reset (reset),
|
||||
.stall (stall_exec),
|
||||
.flush (flush_exec),
|
||||
.in ({exec_unit_req_temp_if.valid, exec_unit_req_temp_if.warp_num, exec_unit_req_temp_if.curr_PC, exec_unit_req_temp_if.next_PC, exec_unit_req_temp_if.rd, exec_unit_req_temp_if.wb, exec_unit_req_temp_if.a_reg_data, exec_unit_req_temp_if.b_reg_data, exec_unit_req_temp_if.alu_op, exec_unit_req_temp_if.rs1, exec_unit_req_temp_if.rs2, exec_unit_req_temp_if.rs2_src, exec_unit_req_temp_if.itype_immed, exec_unit_req_temp_if.upper_immed, exec_unit_req_temp_if.branch_type, exec_unit_req_temp_if.is_jal, exec_unit_req_temp_if.jal, exec_unit_req_temp_if.jal_offset, exec_unit_req_temp_if.is_etype, exec_unit_req_temp_if.wspawn, exec_unit_req_temp_if.is_csr, exec_unit_req_temp_if.csr_address, exec_unit_req_temp_if.csr_immed, exec_unit_req_temp_if.csr_mask}),
|
||||
.out ({exec_unit_req_if.valid , exec_unit_req_if.warp_num , exec_unit_req_if.curr_PC , exec_unit_req_if.next_PC , exec_unit_req_if.rd , exec_unit_req_if.wb , exec_unit_req_if.a_reg_data , exec_unit_req_if.b_reg_data , exec_unit_req_if.alu_op , exec_unit_req_if.rs1 , exec_unit_req_if.rs2 , exec_unit_req_if.rs2_src , exec_unit_req_if.itype_immed , exec_unit_req_if.upper_immed , exec_unit_req_if.branch_type , exec_unit_req_if.is_jal , exec_unit_req_if.jal , exec_unit_req_if.jal_offset , exec_unit_req_if.is_etype , exec_unit_req_if.wspawn , exec_unit_req_if.is_csr , exec_unit_req_if.csr_address , exec_unit_req_if.csr_immed , exec_unit_req_if.csr_mask })
|
||||
.in ({exec_unit_req_temp_if.valid, exec_unit_req_temp_if.warp_num, exec_unit_req_temp_if.curr_PC, exec_unit_req_temp_if.next_PC, exec_unit_req_temp_if.rd, exec_unit_req_temp_if.wb, exec_unit_req_temp_if.a_reg_data, exec_unit_req_temp_if.b_reg_data, exec_unit_req_temp_if.alu_op, exec_unit_req_temp_if.rs1, exec_unit_req_temp_if.rs2, exec_unit_req_temp_if.rs2_src, exec_unit_req_temp_if.itype_immed, exec_unit_req_temp_if.upper_immed, exec_unit_req_temp_if.branch_type, exec_unit_req_temp_if.is_jal, exec_unit_req_temp_if.jal, exec_unit_req_temp_if.jal_offset, exec_unit_req_temp_if.is_etype, exec_unit_req_temp_if.wspawn, exec_unit_req_temp_if.is_csr, exec_unit_req_temp_if.csr_addr, exec_unit_req_temp_if.csr_immed, exec_unit_req_temp_if.csr_mask}),
|
||||
.out ({exec_unit_req_if.valid , exec_unit_req_if.warp_num , exec_unit_req_if.curr_PC , exec_unit_req_if.next_PC , exec_unit_req_if.rd , exec_unit_req_if.wb , exec_unit_req_if.a_reg_data , exec_unit_req_if.b_reg_data , exec_unit_req_if.alu_op , exec_unit_req_if.rs1 , exec_unit_req_if.rs2 , exec_unit_req_if.rs2_src , exec_unit_req_if.itype_immed , exec_unit_req_if.upper_immed , exec_unit_req_if.branch_type , exec_unit_req_if.is_jal , exec_unit_req_if.jal , exec_unit_req_if.jal_offset , exec_unit_req_if.is_etype , exec_unit_req_if.wspawn , exec_unit_req_if.is_csr , exec_unit_req_if.csr_addr , exec_unit_req_if.csr_immed , exec_unit_req_if.csr_mask })
|
||||
);
|
||||
|
||||
VX_generic_register #(
|
||||
@@ -214,10 +217,10 @@ module VX_gpr_stage (
|
||||
.reset (reset),
|
||||
.stall (stall_gpr_csr),
|
||||
.flush (flush_rest),
|
||||
.in ({csr_req_temp_if.valid, csr_req_temp_if.warp_num, csr_req_temp_if.rd, csr_req_temp_if.wb, csr_req_temp_if.alu_op, csr_req_temp_if.is_csr, csr_req_temp_if.csr_address, csr_req_temp_if.csr_immed, csr_req_temp_if.csr_mask}),
|
||||
.out ({csr_req_if.valid , csr_req_if.warp_num , csr_req_if.rd , csr_req_if.wb , csr_req_if.alu_op , csr_req_if.is_csr , csr_req_if.csr_address , csr_req_if.csr_immed , csr_req_if.csr_mask })
|
||||
.in ({csr_req_temp_if.valid, csr_req_temp_if.warp_num, csr_req_temp_if.rd, csr_req_temp_if.wb, csr_req_temp_if.alu_op, csr_req_temp_if.is_csr, csr_req_temp_if.csr_addr, csr_req_temp_if.csr_immed, csr_req_temp_if.csr_mask}),
|
||||
.out ({csr_req_if.valid , csr_req_if.warp_num , csr_req_if.rd , csr_req_if.wb , csr_req_if.alu_op , csr_req_if.is_csr , csr_req_if.csr_addr , csr_req_if.csr_immed , csr_req_if.csr_mask })
|
||||
);
|
||||
|
||||
`endif
|
||||
|
||||
endmodule : VX_gpr_stage
|
||||
endmodule : VX_gpr_stage
|
||||
|
||||
@@ -25,10 +25,10 @@ module VX_icache_stage #(
|
||||
wire [`LOG2UP(`ICREQ_SIZE)-1:0] mrq_write_addr, mrq_read_addr, dbg_mrq_write_addr;
|
||||
wire mrq_full;
|
||||
|
||||
wire mrq_push = icache_req_if.core_req_valid && icache_req_if.core_req_ready;
|
||||
wire mrq_pop = icache_rsp_if.core_rsp_valid && icache_rsp_if.core_rsp_ready;
|
||||
wire mrq_push = icache_req_if.valid && icache_req_if.ready;
|
||||
wire mrq_pop = icache_rsp_if.valid && icache_rsp_if.ready;
|
||||
|
||||
assign mrq_read_addr = icache_rsp_if.core_rsp_tag[0][`LOG2UP(`ICREQ_SIZE)-1:0];
|
||||
assign mrq_read_addr = icache_rsp_if.tag[0][`LOG2UP(`ICREQ_SIZE)-1:0];
|
||||
|
||||
VX_indexable_queue #(
|
||||
.DATAW (`LOG2UP(`ICREQ_SIZE) + 32 + `NW_BITS),
|
||||
@@ -36,13 +36,13 @@ module VX_icache_stage #(
|
||||
) mem_req_queue (
|
||||
.clk (clk),
|
||||
.reset (reset),
|
||||
.write_data ({mrq_write_addr, fe_inst_meta_fi.inst_pc, fe_inst_meta_fi.warp_num}),
|
||||
.write_data ({mrq_write_addr, fe_inst_meta_fi.curr_PC, fe_inst_meta_fi.warp_num}),
|
||||
.write_addr (mrq_write_addr),
|
||||
.push (mrq_push),
|
||||
.full (mrq_full),
|
||||
.pop (mrq_pop),
|
||||
.read_addr (mrq_read_addr),
|
||||
.read_data ({dbg_mrq_write_addr, fe_inst_meta_id.inst_pc, fe_inst_meta_id.warp_num}),
|
||||
.read_data ({dbg_mrq_write_addr, fe_inst_meta_id.curr_PC, fe_inst_meta_id.warp_num}),
|
||||
`UNUSED_PIN (empty)
|
||||
);
|
||||
|
||||
@@ -56,48 +56,48 @@ module VX_icache_stage #(
|
||||
end
|
||||
|
||||
// Icache Request
|
||||
assign icache_req_if.core_req_valid = valid_inst && !mrq_full;
|
||||
assign icache_req_if.core_req_rw = 0;
|
||||
assign icache_req_if.core_req_byteen = 4'b1111;
|
||||
assign icache_req_if.core_req_addr = fe_inst_meta_fi.inst_pc[31:2];
|
||||
assign icache_req_if.core_req_data = 0;
|
||||
assign icache_req_if.valid = valid_inst && !mrq_full;
|
||||
assign icache_req_if.rw = 0;
|
||||
assign icache_req_if.byteen = 4'b1111;
|
||||
assign icache_req_if.addr = fe_inst_meta_fi.curr_PC[31:2];
|
||||
assign icache_req_if.data = 0;
|
||||
|
||||
// Can't accept new request
|
||||
assign icache_stage_delay = mrq_full || !icache_req_if.core_req_ready;
|
||||
assign icache_stage_delay = mrq_full || !icache_req_if.ready;
|
||||
|
||||
`ifdef DBG_CORE_REQ_INFO
|
||||
assign icache_req_if.core_req_tag = {fe_inst_meta_fi.inst_pc, 2'b1, 5'b0, fe_inst_meta_fi.warp_num, mrq_write_addr};
|
||||
assign icache_req_if.tag = {fe_inst_meta_fi.curr_PC, 2'b1, 5'b0, fe_inst_meta_fi.warp_num, mrq_write_addr};
|
||||
`else
|
||||
assign icache_req_if.core_req_tag = mrq_write_addr;
|
||||
assign icache_req_if.tag = mrq_write_addr;
|
||||
`endif
|
||||
|
||||
assign fe_inst_meta_id.instruction = icache_rsp_if.core_rsp_valid ? icache_rsp_if.core_rsp_data[0] : 0;
|
||||
assign fe_inst_meta_id.valid = icache_rsp_if.core_rsp_valid ? valid_threads[fe_inst_meta_id.warp_num] : 0;
|
||||
assign fe_inst_meta_id.instruction = icache_rsp_if.valid ? icache_rsp_if.data[0] : 0;
|
||||
assign fe_inst_meta_id.valid = icache_rsp_if.valid ? valid_threads[fe_inst_meta_id.warp_num] : 0;
|
||||
|
||||
assign icache_stage_response = mrq_pop;
|
||||
assign icache_stage_wid = fe_inst_meta_id.warp_num;
|
||||
|
||||
// Can't accept new response
|
||||
assign icache_rsp_if.core_rsp_ready = !total_freeze;
|
||||
assign icache_rsp_if.ready = !total_freeze;
|
||||
|
||||
`SCOPE_ASSIGN(scope_icache_req_valid, icache_req_if.core_req_valid);
|
||||
`SCOPE_ASSIGN(scope_icache_req_valid, icache_req_if.valid);
|
||||
`SCOPE_ASSIGN(scope_icache_req_warp_num, fe_inst_meta_fi.warp_num);
|
||||
`SCOPE_ASSIGN(scope_icache_req_addr, {icache_req_if.core_req_addr, 2'b0});
|
||||
`SCOPE_ASSIGN(scope_icache_req_tag, icache_req_if.core_req_tag);
|
||||
`SCOPE_ASSIGN(scope_icache_req_ready, icache_req_if.core_req_ready);
|
||||
`SCOPE_ASSIGN(scope_icache_req_addr, {icache_req_if.addr, 2'b0});
|
||||
`SCOPE_ASSIGN(scope_icache_req_tag, icache_req_if.tag);
|
||||
`SCOPE_ASSIGN(scope_icache_req_ready, icache_req_if.ready);
|
||||
|
||||
`SCOPE_ASSIGN(scope_icache_rsp_valid, icache_rsp_if.core_rsp_valid);
|
||||
`SCOPE_ASSIGN(scope_icache_rsp_data, icache_rsp_if.core_rsp_data);
|
||||
`SCOPE_ASSIGN(scope_icache_rsp_tag, icache_rsp_if.core_rsp_tag);
|
||||
`SCOPE_ASSIGN(scope_icache_rsp_ready, icache_rsp_if.core_rsp_ready);
|
||||
`SCOPE_ASSIGN(scope_icache_rsp_valid, icache_rsp_if.valid);
|
||||
`SCOPE_ASSIGN(scope_icache_rsp_data, icache_rsp_if.data);
|
||||
`SCOPE_ASSIGN(scope_icache_rsp_tag, icache_rsp_if.tag);
|
||||
`SCOPE_ASSIGN(scope_icache_rsp_ready, icache_rsp_if.ready);
|
||||
|
||||
`ifdef DBG_PRINT_CORE_ICACHE
|
||||
always @(posedge clk) begin
|
||||
if (icache_req_if.core_req_valid && icache_req_if.core_req_ready) begin
|
||||
$display("%t: I%0d$ req: tag=%0h, pc=%0h, warp=%0d", $time, CORE_ID, mrq_write_addr, fe_inst_meta_fi.inst_pc, fe_inst_meta_fi.warp_num);
|
||||
if (icache_req_if.valid && icache_req_if.ready) begin
|
||||
$display("%t: I%0d$ req: tag=%0h, pc=%0h, warp=%0d", $time, CORE_ID, mrq_write_addr, fe_inst_meta_fi.curr_PC, fe_inst_meta_fi.warp_num);
|
||||
end
|
||||
if (icache_rsp_if.core_rsp_valid && icache_rsp_if.core_rsp_ready) begin
|
||||
$display("%t: I%0d$ rsp: tag=%0h, pc=%0h, warp=%0d, instr=%0h", $time, CORE_ID, mrq_read_addr, fe_inst_meta_id.inst_pc, fe_inst_meta_id.warp_num, fe_inst_meta_id.instruction);
|
||||
if (icache_rsp_if.valid && icache_rsp_if.ready) begin
|
||||
$display("%t: I%0d$ rsp: tag=%0h, pc=%0h, warp=%0d, instr=%0h", $time, CORE_ID, mrq_read_addr, fe_inst_meta_id.curr_PC, fe_inst_meta_id.warp_num, fe_inst_meta_id.instruction);
|
||||
end
|
||||
end
|
||||
`endif
|
||||
|
||||
@@ -33,7 +33,7 @@ module VX_inst_multiplex (
|
||||
// LSU Unit
|
||||
assign lsu_req_if.valid = bckE_req_if.valid & is_mem_mask;
|
||||
assign lsu_req_if.warp_num = bckE_req_if.warp_num;
|
||||
assign lsu_req_if.base_address = gpr_read_if.a_reg_data;
|
||||
assign lsu_req_if.base_addr = gpr_read_if.a_reg_data;
|
||||
assign lsu_req_if.store_data = gpr_read_if.b_reg_data;
|
||||
|
||||
assign lsu_req_if.offset = bckE_req_if.itype_immed;
|
||||
@@ -83,7 +83,7 @@ module VX_inst_multiplex (
|
||||
assign csr_req_if.wb = bckE_req_if.wb;
|
||||
assign csr_req_if.alu_op = bckE_req_if.alu_op;
|
||||
assign csr_req_if.is_csr = bckE_req_if.is_csr;
|
||||
assign csr_req_if.csr_address = bckE_req_if.csr_address;
|
||||
assign csr_req_if.csr_addr = bckE_req_if.csr_addr;
|
||||
assign csr_req_if.csr_immed = bckE_req_if.csr_immed;
|
||||
assign csr_req_if.csr_mask = bckE_req_if.csr_mask;
|
||||
|
||||
|
||||
@@ -12,7 +12,7 @@ module VX_lsu_unit #(
|
||||
VX_lsu_req_if lsu_req_if,
|
||||
|
||||
// Write back to GPR
|
||||
VX_wb_if mem_wb_if_p1,
|
||||
VX_wb_if mem_wb_if,
|
||||
|
||||
// Dcache interface
|
||||
VX_cache_core_req_if dcache_req_if,
|
||||
@@ -21,92 +21,98 @@ module VX_lsu_unit #(
|
||||
output wire delay
|
||||
);
|
||||
|
||||
VX_wb_if mem_wb_if();
|
||||
VX_wb_if mem_wb_unqual_if();
|
||||
|
||||
wire[`NUM_THREADS-1:0][31:0] use_address;
|
||||
wire[`NUM_THREADS-1:0][31:0] use_store_data;
|
||||
wire[`NUM_THREADS-1:0] use_valid;
|
||||
wire[`BYTE_EN_BITS-1:0] use_mem_read;
|
||||
wire[`BYTE_EN_BITS-1:0] use_mem_write;
|
||||
wire[4:0] use_rd;
|
||||
wire[`NW_BITS-1:0] use_warp_num;
|
||||
wire[1:0] use_wb;
|
||||
wire[31:0] use_pc;
|
||||
wire [`NUM_THREADS-1:0] use_valid;
|
||||
wire use_req_rw;
|
||||
wire [`NUM_THREADS-1:0][29:0] use_req_addr;
|
||||
wire [`NUM_THREADS-1:0][1:0] use_req_offset;
|
||||
wire [`NUM_THREADS-1:0][3:0] use_req_byteen;
|
||||
wire [`NUM_THREADS-1:0][31:0] use_req_data;
|
||||
wire [`BYTE_EN_BITS-1:0] use_mem_read;
|
||||
wire [4:0] use_rd;
|
||||
wire [`NW_BITS-1:0] use_warp_num;
|
||||
wire [1:0] use_wb;
|
||||
wire [31:0] use_pc;
|
||||
|
||||
genvar i;
|
||||
|
||||
// Generate Full Addresses
|
||||
wire[`NUM_THREADS-1:0][31:0] full_address;
|
||||
wire[`NUM_THREADS-1:0][31:0] full_address;
|
||||
for (i = 0; i < `NUM_THREADS; i++) begin
|
||||
assign full_address[i] = lsu_req_if.base_address[i] + lsu_req_if.offset;
|
||||
assign full_address[i] = lsu_req_if.base_addr[i] + lsu_req_if.offset;
|
||||
end
|
||||
|
||||
VX_generic_register #(
|
||||
.N(45 + `NW_BITS-1 + 1 + `NUM_THREADS*65)
|
||||
) lsu_buffer (
|
||||
.clk (clk),
|
||||
.reset (reset),
|
||||
.stall (delay),
|
||||
.flush (1'b0),
|
||||
.in ({full_address,lsu_req_if.store_data, lsu_req_if.valid, lsu_req_if.mem_read, lsu_req_if.mem_write, lsu_req_if.rd, lsu_req_if.warp_num, lsu_req_if.wb, lsu_req_if.curr_PC}),
|
||||
.out ({use_address, use_store_data , use_valid , use_mem_read , use_mem_write , use_rd , use_warp_num , use_wb , use_pc })
|
||||
);
|
||||
|
||||
wire core_req_rw = (use_mem_write != `BYTE_EN_NO);
|
||||
|
||||
wire [`NUM_THREADS-1:0][4:0] mem_req_offset;
|
||||
wire [`NUM_THREADS-1:0][29:0] mem_req_addr;
|
||||
wire [`NUM_THREADS-1:0][3:0] mem_req_byteen;
|
||||
wire [`NUM_THREADS-1:0][31:0] mem_req_data;
|
||||
|
||||
wire [`NUM_THREADS-1:0][4:0] mem_rsp_offset;
|
||||
wire[2:0] core_rsp_mem_read;
|
||||
wire mem_req_rw = (lsu_req_if.mem_write != `BYTE_EN_NO);
|
||||
|
||||
reg [3:0] wmask;
|
||||
always @(*) begin
|
||||
case ((core_req_rw ? use_mem_write[1:0] : use_mem_read[1:0]))
|
||||
case ((mem_req_rw ? lsu_req_if.mem_write[1:0] : lsu_req_if.mem_read[1:0]))
|
||||
0: wmask = 4'b0001;
|
||||
1: wmask = 4'b0011;
|
||||
default : wmask = 4'b1111;
|
||||
endcase
|
||||
end
|
||||
|
||||
for (i = 0; i < `NUM_THREADS; ++i) begin
|
||||
assign mem_req_addr[i] = use_address[i][31:2];
|
||||
assign mem_req_offset[i] = (5'(use_address[i][1:0])) << 3;
|
||||
assign mem_req_byteen[i] = (wmask << use_address[i][1:0]);
|
||||
assign mem_req_data[i] = (use_store_data[i] << mem_req_offset[i]);
|
||||
end
|
||||
wire [`NUM_THREADS-1:0][29:0] mem_req_addr;
|
||||
wire [`NUM_THREADS-1:0][1:0] mem_req_offset;
|
||||
wire [`NUM_THREADS-1:0][3:0] mem_req_byteen;
|
||||
wire [`NUM_THREADS-1:0][31:0] mem_req_data;
|
||||
|
||||
for (i = 0; i < `NUM_THREADS; i++) begin
|
||||
assign mem_req_addr[i] = full_address[i][31:2];
|
||||
assign mem_req_offset[i] = full_address[i][1:0];
|
||||
assign mem_req_byteen[i] = wmask << full_address[i][1:0];
|
||||
assign mem_req_data[i] = lsu_req_if.store_data[i] << {mem_req_offset[i], 3'b0};
|
||||
end
|
||||
|
||||
`IGNORE_WARNINGS_BEGIN
|
||||
wire[`NUM_THREADS-1:0][31:0] use_address;
|
||||
`IGNORE_WARNINGS_END
|
||||
|
||||
VX_generic_register #(
|
||||
.N((`NUM_THREADS * 1) + (`NUM_THREADS * 32) + `BYTE_EN_BITS + 1 + (`NUM_THREADS * (30 + 2 + 4 + 32)) + 5 + `NW_BITS + 2 + 32)
|
||||
) lsu_buffer (
|
||||
.clk (clk),
|
||||
.reset (reset),
|
||||
.stall (delay),
|
||||
.flush (1'b0),
|
||||
.in ({lsu_req_if.valid, full_address, lsu_req_if.mem_read, mem_req_rw, mem_req_addr, mem_req_offset, mem_req_byteen, mem_req_data, lsu_req_if.rd, lsu_req_if.warp_num, lsu_req_if.wb, lsu_req_if.curr_PC}),
|
||||
.out ({use_valid , use_address, use_mem_read , use_req_rw, use_req_addr, use_req_offset, use_req_byteen, use_req_data, use_rd , use_warp_num , use_wb , use_pc})
|
||||
);
|
||||
|
||||
wire [`NUM_THREADS-1:0][1:0] mem_rsp_offset;
|
||||
wire [`BYTE_EN_BITS-1:0] core_rsp_mem_read;
|
||||
|
||||
reg [`NUM_THREADS-1:0] mem_rsp_mask[`DCREQ_SIZE-1:0];
|
||||
|
||||
wire [`LOG2UP(`DCREQ_SIZE)-1:0] mrq_write_addr, mrq_read_addr, dbg_mrq_write_addr;
|
||||
wire mrq_full;
|
||||
|
||||
wire mrq_push = (| dcache_req_if.core_req_valid) && dcache_req_if.core_req_ready
|
||||
&& (0 == core_req_rw); // only push read requests
|
||||
wire mrq_push = (| dcache_req_if.valid) && dcache_req_if.ready
|
||||
&& (0 == use_req_rw); // only push read requests
|
||||
|
||||
wire mrq_pop_part = (| dcache_rsp_if.core_rsp_valid) && dcache_rsp_if.core_rsp_ready;
|
||||
wire mrq_pop_part = (| dcache_rsp_if.valid) && dcache_rsp_if.ready;
|
||||
|
||||
assign mrq_read_addr = dcache_rsp_if.core_rsp_tag[0][`LOG2UP(`DCREQ_SIZE)-1:0];
|
||||
assign mrq_read_addr = dcache_rsp_if.tag[0][`LOG2UP(`DCREQ_SIZE)-1:0];
|
||||
|
||||
wire [`NUM_THREADS-1:0] mem_rsp_mask_upd = mem_rsp_mask[mrq_read_addr] & ~dcache_rsp_if.core_rsp_valid;
|
||||
wire [`NUM_THREADS-1:0] mem_rsp_mask_upd = mem_rsp_mask[mrq_read_addr] & ~dcache_rsp_if.valid;
|
||||
|
||||
wire mrq_pop = mrq_pop_part && (0 == mem_rsp_mask_upd);
|
||||
|
||||
VX_indexable_queue #(
|
||||
.DATAW (`LOG2UP(`DCREQ_SIZE) + 32 + 2 + (`NUM_THREADS * 5) + `BYTE_EN_BITS + 5 + `NW_BITS),
|
||||
.DATAW (`LOG2UP(`DCREQ_SIZE) + 32 + 2 + (`NUM_THREADS * 2) + `BYTE_EN_BITS + 5 + `NW_BITS),
|
||||
.SIZE (`DCREQ_SIZE)
|
||||
) mem_req_queue (
|
||||
.clk (clk),
|
||||
.reset (reset),
|
||||
.write_data ({mrq_write_addr, use_pc, use_wb, mem_req_offset, use_mem_read, use_rd, use_warp_num}),
|
||||
.write_data ({mrq_write_addr, use_pc, use_wb, use_req_offset, use_mem_read, use_rd, use_warp_num}),
|
||||
.write_addr (mrq_write_addr),
|
||||
.push (mrq_push),
|
||||
.full (mrq_full),
|
||||
.pop (mrq_pop),
|
||||
.read_addr (mrq_read_addr),
|
||||
.read_data ({dbg_mrq_write_addr, mem_wb_if.curr_PC, mem_wb_if.wb, mem_rsp_offset, core_rsp_mem_read, mem_wb_if.rd, mem_wb_if.warp_num}),
|
||||
.read_data ({dbg_mrq_write_addr, mem_wb_unqual_if.curr_PC, mem_wb_unqual_if.wb, mem_rsp_offset, core_rsp_mem_read, mem_wb_unqual_if.rd, mem_wb_unqual_if.warp_num}),
|
||||
`UNUSED_PIN (empty)
|
||||
);
|
||||
|
||||
@@ -122,80 +128,80 @@ module VX_lsu_unit #(
|
||||
|
||||
// Core Request
|
||||
|
||||
assign dcache_req_if.core_req_valid = use_valid & {`NUM_THREADS{~mrq_full}};
|
||||
assign dcache_req_if.core_req_rw = {`NUM_THREADS{core_req_rw}};
|
||||
assign dcache_req_if.core_req_byteen= mem_req_byteen;
|
||||
assign dcache_req_if.core_req_addr = mem_req_addr;
|
||||
assign dcache_req_if.core_req_data = mem_req_data;
|
||||
assign dcache_req_if.valid = use_valid & {`NUM_THREADS{~mrq_full}};
|
||||
assign dcache_req_if.rw = {`NUM_THREADS{use_req_rw}};
|
||||
assign dcache_req_if.byteen = use_req_byteen;
|
||||
assign dcache_req_if.addr = use_req_addr;
|
||||
assign dcache_req_if.data = use_req_data;
|
||||
|
||||
`ifdef DBG_CORE_REQ_INFO
|
||||
assign dcache_req_if.core_req_tag = {use_pc, use_wb, use_rd, use_warp_num, mrq_write_addr};
|
||||
assign dcache_req_if.tag = {use_pc, use_wb, use_rd, use_warp_num, mrq_write_addr};
|
||||
`else
|
||||
assign dcache_req_if.core_req_tag = mrq_write_addr;
|
||||
assign dcache_req_if.tag = mrq_write_addr;
|
||||
`endif
|
||||
|
||||
// Can't accept new request
|
||||
assign delay = mrq_full || !dcache_req_if.core_req_ready;
|
||||
assign delay = mrq_full || !dcache_req_if.ready;
|
||||
|
||||
// Core Response
|
||||
|
||||
reg [`NUM_THREADS-1:0][31:0] core_rsp_data;
|
||||
wire [`NUM_THREADS-1:0][31:0] rsp_data_shifted;
|
||||
|
||||
for (i = 0; i < `NUM_THREADS; ++i) begin
|
||||
assign rsp_data_shifted[i] = (dcache_rsp_if.core_rsp_data[i] >> mem_rsp_offset[i]);
|
||||
for (i = 0; i < `NUM_THREADS; i++) begin
|
||||
assign rsp_data_shifted[i] = dcache_rsp_if.data[i] >> {mem_rsp_offset[i], 3'b0};
|
||||
always @(*) begin
|
||||
case (core_rsp_mem_read)
|
||||
`BYTE_EN_SB: core_rsp_data[i] = rsp_data_shifted[i][7] ? (rsp_data_shifted[i] | 32'hFFFFFF00) : (rsp_data_shifted[i] & 32'h000000FF);
|
||||
`BYTE_EN_SH: core_rsp_data[i] = rsp_data_shifted[i][15] ? (rsp_data_shifted[i] | 32'hFFFF0000) : (rsp_data_shifted[i] & 32'h0000FFFF);
|
||||
`BYTE_EN_UB: core_rsp_data[i] = (rsp_data_shifted[i] & 32'h000000FF);
|
||||
`BYTE_EN_UH: core_rsp_data[i] = (rsp_data_shifted[i] & 32'h0000FFFF);
|
||||
`BYTE_EN_SB: core_rsp_data[i] = {{24{rsp_data_shifted[i][7]}}, rsp_data_shifted[i][7:0]};
|
||||
`BYTE_EN_SH: core_rsp_data[i] = {{16{rsp_data_shifted[i][15]}}, rsp_data_shifted[i][15:0]};
|
||||
`BYTE_EN_UB: core_rsp_data[i] = 32'(rsp_data_shifted[i][7:0]);
|
||||
`BYTE_EN_UH: core_rsp_data[i] = 32'(rsp_data_shifted[i][15:0]);
|
||||
default : core_rsp_data[i] = rsp_data_shifted[i];
|
||||
endcase
|
||||
end
|
||||
end
|
||||
|
||||
assign mem_wb_if.valid = dcache_rsp_if.core_rsp_valid;
|
||||
assign mem_wb_if.data = core_rsp_data;
|
||||
assign mem_wb_unqual_if.valid = dcache_rsp_if.valid;
|
||||
assign mem_wb_unqual_if.data = core_rsp_data;
|
||||
|
||||
// Can't accept new response
|
||||
assign dcache_rsp_if.core_rsp_ready = !(no_slot_mem & (|mem_wb_if_p1.valid));
|
||||
assign dcache_rsp_if.ready = !(no_slot_mem & (|mem_wb_if.valid));
|
||||
|
||||
// From LSU to WB
|
||||
localparam WB_REQ_SIZE = (`NUM_THREADS) + (`NUM_THREADS * 32) + (`NW_BITS) + (5) + (2) + 32;
|
||||
VX_generic_register #(.N(WB_REQ_SIZE)) lsu_to_wb(
|
||||
VX_generic_register #(.N(WB_REQ_SIZE)) lsu_to_wb (
|
||||
.clk (clk),
|
||||
.reset (reset),
|
||||
.stall (no_slot_mem),
|
||||
.flush (1'b0),
|
||||
.in ({mem_wb_if.valid , mem_wb_if.data , mem_wb_if.warp_num , mem_wb_if.rd , mem_wb_if.wb , mem_wb_if.curr_PC }),
|
||||
.out ({mem_wb_if_p1.valid, mem_wb_if_p1.data, mem_wb_if_p1.warp_num, mem_wb_if_p1.rd, mem_wb_if_p1.wb, mem_wb_if_p1.curr_PC})
|
||||
.in ({mem_wb_unqual_if.valid, mem_wb_unqual_if.data, mem_wb_unqual_if.warp_num, mem_wb_unqual_if.rd, mem_wb_unqual_if.wb, mem_wb_unqual_if.curr_PC}),
|
||||
.out ({mem_wb_if.valid, mem_wb_if.data, mem_wb_if.warp_num, mem_wb_if.rd, mem_wb_if.wb, mem_wb_if.curr_PC})
|
||||
);
|
||||
|
||||
`SCOPE_ASSIGN(scope_dcache_req_valid, dcache_req_if.core_req_valid);
|
||||
`SCOPE_ASSIGN(scope_dcache_req_valid, dcache_req_if.valid);
|
||||
`SCOPE_ASSIGN(scope_dcache_req_warp_num, use_warp_num);
|
||||
`SCOPE_ASSIGN(scope_dcache_req_curr_PC, use_pc);
|
||||
`SCOPE_ASSIGN(scope_dcache_req_addr, use_address);
|
||||
`SCOPE_ASSIGN(scope_dcache_req_rw, core_req_rw);
|
||||
`SCOPE_ASSIGN(scope_dcache_req_byteen,dcache_req_if.core_req_byteen);
|
||||
`SCOPE_ASSIGN(scope_dcache_req_data, dcache_req_if.core_req_data);
|
||||
`SCOPE_ASSIGN(scope_dcache_req_tag, dcache_req_if.core_req_tag);
|
||||
`SCOPE_ASSIGN(scope_dcache_req_ready, dcache_req_if.core_req_ready);
|
||||
`SCOPE_ASSIGN(scope_dcache_req_byteen,dcache_req_if.byteen);
|
||||
`SCOPE_ASSIGN(scope_dcache_req_data, dcache_req_if.data);
|
||||
`SCOPE_ASSIGN(scope_dcache_req_tag, dcache_req_if.tag);
|
||||
`SCOPE_ASSIGN(scope_dcache_req_ready, dcache_req_if.ready);
|
||||
|
||||
`SCOPE_ASSIGN(scope_dcache_rsp_valid, dcache_rsp_if.core_rsp_valid);
|
||||
`SCOPE_ASSIGN(scope_dcache_rsp_data, dcache_rsp_if.core_rsp_data);
|
||||
`SCOPE_ASSIGN(scope_dcache_rsp_tag, dcache_rsp_if.core_rsp_tag);
|
||||
`SCOPE_ASSIGN(scope_dcache_rsp_ready, dcache_rsp_if.core_rsp_ready);
|
||||
`SCOPE_ASSIGN(scope_dcache_rsp_valid, dcache_rsp_if.valid);
|
||||
`SCOPE_ASSIGN(scope_dcache_rsp_data, dcache_rsp_if.data);
|
||||
`SCOPE_ASSIGN(scope_dcache_rsp_tag, dcache_rsp_if.tag);
|
||||
`SCOPE_ASSIGN(scope_dcache_rsp_ready, dcache_rsp_if.ready);
|
||||
|
||||
`ifdef DBG_PRINT_CORE_DCACHE
|
||||
always @(posedge clk) begin
|
||||
if ((| dcache_req_if.core_req_valid) && dcache_req_if.core_req_ready) begin
|
||||
$display("%t: D%0d$ req: valid=%b, addr=%0h, tag=%0h, r=%0d, w=%0d, pc=%0h, rd=%0d, warp=%0d, byteen=%0h, data=%0h",
|
||||
$time, CORE_ID, use_valid, use_address, mrq_write_addr, use_mem_read, use_mem_write, use_pc, use_rd, use_warp_num, mem_req_byteen, mem_req_data);
|
||||
if ((| dcache_req_if.valid) && dcache_req_if.ready) begin
|
||||
$display("%t: D%0d$ req: valid=%b, addr=%0h, tag=%0h, rw=%0b, pc=%0h, rd=%0d, warp=%0d, byteen=%0h, data=%0h",
|
||||
$time, CORE_ID, use_valid, use_address, mrq_write_addr, use_req_rw, use_pc, use_rd, use_warp_num, use_req_byteen, use_req_data);
|
||||
end
|
||||
if ((| dcache_rsp_if.core_rsp_valid) && dcache_rsp_if.core_rsp_ready) begin
|
||||
if ((| dcache_rsp_if.valid) && dcache_rsp_if.ready) begin
|
||||
$display("%t: D%0d$ rsp: valid=%b, tag=%0h, pc=%0h, rd=%0d, warp=%0d, data=%0h",
|
||||
$time, CORE_ID, mem_wb_if.valid, mrq_read_addr, mem_wb_if.curr_PC, mem_wb_if.rd, mem_wb_if.warp_num, mem_wb_if.data);
|
||||
$time, CORE_ID, mem_wb_unqual_if.valid, mrq_read_addr, mem_wb_unqual_if.curr_PC, mem_wb_unqual_if.rd, mem_wb_unqual_if.warp_num, mem_wb_unqual_if.data);
|
||||
end
|
||||
end
|
||||
`endif
|
||||
|
||||
@@ -41,8 +41,8 @@ module VX_mem_unit # (
|
||||
) core_dcache_rsp_qual_if(), core_smem_rsp_if();
|
||||
|
||||
// select shared memory address
|
||||
wire is_smem_addr = (({core_dcache_req_if.core_req_addr[0], 2'b0} - `SHARED_MEM_BASE_ADDR) <= `SCACHE_SIZE);
|
||||
wire smem_select = (| core_dcache_req_if.core_req_valid) ? is_smem_addr : 0;
|
||||
wire is_smem_addr = (({core_dcache_req_if.addr[0], 2'b0} - `SHARED_MEM_BASE_ADDR) <= `SCACHE_SIZE);
|
||||
wire smem_select = (| core_dcache_req_if.valid) ? is_smem_addr : 0;
|
||||
|
||||
VX_dcache_arb dcache_smem_arb (
|
||||
.req_select (smem_select),
|
||||
@@ -84,19 +84,19 @@ module VX_mem_unit # (
|
||||
.reset (reset),
|
||||
|
||||
// Core request
|
||||
.core_req_valid (core_smem_req_if.core_req_valid),
|
||||
.core_req_rw (core_smem_req_if.core_req_rw),
|
||||
.core_req_byteen (core_smem_req_if.core_req_byteen),
|
||||
.core_req_addr (core_smem_req_if.core_req_addr),
|
||||
.core_req_data (core_smem_req_if.core_req_data),
|
||||
.core_req_tag (core_smem_req_if.core_req_tag),
|
||||
.core_req_ready (core_smem_req_if.core_req_ready),
|
||||
.core_req_valid (core_smem_req_if.valid),
|
||||
.core_req_rw (core_smem_req_if.rw),
|
||||
.core_req_byteen (core_smem_req_if.byteen),
|
||||
.core_req_addr (core_smem_req_if.addr),
|
||||
.core_req_data (core_smem_req_if.data),
|
||||
.core_req_tag (core_smem_req_if.tag),
|
||||
.core_req_ready (core_smem_req_if.ready),
|
||||
|
||||
// Core response
|
||||
.core_rsp_valid (core_smem_rsp_if.core_rsp_valid),
|
||||
.core_rsp_data (core_smem_rsp_if.core_rsp_data),
|
||||
.core_rsp_tag (core_smem_rsp_if.core_rsp_tag),
|
||||
.core_rsp_ready (core_smem_rsp_if.core_rsp_ready),
|
||||
.core_rsp_valid (core_smem_rsp_if.valid),
|
||||
.core_rsp_data (core_smem_rsp_if.data),
|
||||
.core_rsp_tag (core_smem_rsp_if.tag),
|
||||
.core_rsp_ready (core_smem_rsp_if.ready),
|
||||
|
||||
// DRAM request
|
||||
`UNUSED_PIN (dram_req_valid),
|
||||
@@ -169,46 +169,46 @@ module VX_mem_unit # (
|
||||
.reset (reset),
|
||||
|
||||
// Core req
|
||||
.core_req_valid (core_dcache_req_qual_if.core_req_valid),
|
||||
.core_req_rw (core_dcache_req_qual_if.core_req_rw),
|
||||
.core_req_byteen (core_dcache_req_qual_if.core_req_byteen),
|
||||
.core_req_addr (core_dcache_req_qual_if.core_req_addr),
|
||||
.core_req_data (core_dcache_req_qual_if.core_req_data),
|
||||
.core_req_tag (core_dcache_req_qual_if.core_req_tag),
|
||||
.core_req_ready (core_dcache_req_qual_if.core_req_ready),
|
||||
.core_req_valid (core_dcache_req_qual_if.valid),
|
||||
.core_req_rw (core_dcache_req_qual_if.rw),
|
||||
.core_req_byteen (core_dcache_req_qual_if.byteen),
|
||||
.core_req_addr (core_dcache_req_qual_if.addr),
|
||||
.core_req_data (core_dcache_req_qual_if.data),
|
||||
.core_req_tag (core_dcache_req_qual_if.tag),
|
||||
.core_req_ready (core_dcache_req_qual_if.ready),
|
||||
|
||||
// Core response
|
||||
.core_rsp_valid (core_dcache_rsp_qual_if.core_rsp_valid),
|
||||
.core_rsp_data (core_dcache_rsp_qual_if.core_rsp_data),
|
||||
.core_rsp_tag (core_dcache_rsp_qual_if.core_rsp_tag),
|
||||
.core_rsp_ready (core_dcache_rsp_qual_if.core_rsp_ready),
|
||||
.core_rsp_valid (core_dcache_rsp_qual_if.valid),
|
||||
.core_rsp_data (core_dcache_rsp_qual_if.data),
|
||||
.core_rsp_tag (core_dcache_rsp_qual_if.tag),
|
||||
.core_rsp_ready (core_dcache_rsp_qual_if.ready),
|
||||
|
||||
// DRAM request
|
||||
.dram_req_valid (dcache_dram_req_if.dram_req_valid),
|
||||
.dram_req_rw (dcache_dram_req_if.dram_req_rw),
|
||||
.dram_req_byteen (dcache_dram_req_if.dram_req_byteen),
|
||||
.dram_req_addr (dcache_dram_req_if.dram_req_addr),
|
||||
.dram_req_data (dcache_dram_req_if.dram_req_data),
|
||||
.dram_req_tag (dcache_dram_req_if.dram_req_tag),
|
||||
.dram_req_ready (dcache_dram_req_if.dram_req_ready),
|
||||
.dram_req_valid (dcache_dram_req_if.valid),
|
||||
.dram_req_rw (dcache_dram_req_if.rw),
|
||||
.dram_req_byteen (dcache_dram_req_if.byteen),
|
||||
.dram_req_addr (dcache_dram_req_if.addr),
|
||||
.dram_req_data (dcache_dram_req_if.data),
|
||||
.dram_req_tag (dcache_dram_req_if.tag),
|
||||
.dram_req_ready (dcache_dram_req_if.ready),
|
||||
|
||||
// DRAM response
|
||||
.dram_rsp_valid (dcache_dram_rsp_if.dram_rsp_valid),
|
||||
.dram_rsp_data (dcache_dram_rsp_if.dram_rsp_data),
|
||||
.dram_rsp_tag (dcache_dram_rsp_if.dram_rsp_tag),
|
||||
.dram_rsp_ready (dcache_dram_rsp_if.dram_rsp_ready),
|
||||
.dram_rsp_valid (dcache_dram_rsp_if.valid),
|
||||
.dram_rsp_data (dcache_dram_rsp_if.data),
|
||||
.dram_rsp_tag (dcache_dram_rsp_if.tag),
|
||||
.dram_rsp_ready (dcache_dram_rsp_if.ready),
|
||||
|
||||
// Snoop request
|
||||
.snp_req_valid (dcache_snp_req_if.snp_req_valid),
|
||||
.snp_req_addr (dcache_snp_req_if.snp_req_addr),
|
||||
.snp_req_invalidate (dcache_snp_req_if.snp_req_invalidate),
|
||||
.snp_req_tag (dcache_snp_req_if.snp_req_tag),
|
||||
.snp_req_ready (dcache_snp_req_if.snp_req_ready),
|
||||
.snp_req_valid (dcache_snp_req_if.valid),
|
||||
.snp_req_addr (dcache_snp_req_if.addr),
|
||||
.snp_req_invalidate (dcache_snp_req_if.invalidate),
|
||||
.snp_req_tag (dcache_snp_req_if.tag),
|
||||
.snp_req_ready (dcache_snp_req_if.ready),
|
||||
|
||||
// Snoop response
|
||||
.snp_rsp_valid (dcache_snp_rsp_if.snp_rsp_valid),
|
||||
.snp_rsp_tag (dcache_snp_rsp_if.snp_rsp_tag),
|
||||
.snp_rsp_ready (dcache_snp_rsp_if.snp_rsp_ready),
|
||||
.snp_rsp_valid (dcache_snp_rsp_if.valid),
|
||||
.snp_rsp_tag (dcache_snp_rsp_if.tag),
|
||||
.snp_rsp_ready (dcache_snp_rsp_if.ready),
|
||||
|
||||
// Snoop forward out
|
||||
`UNUSED_PIN (snp_fwdout_valid),
|
||||
@@ -253,34 +253,34 @@ module VX_mem_unit # (
|
||||
.reset (reset),
|
||||
|
||||
// Core request
|
||||
.core_req_valid (core_icache_req_if.core_req_valid),
|
||||
.core_req_rw (core_icache_req_if.core_req_rw),
|
||||
.core_req_byteen (core_icache_req_if.core_req_byteen),
|
||||
.core_req_addr (core_icache_req_if.core_req_addr),
|
||||
.core_req_data (core_icache_req_if.core_req_data),
|
||||
.core_req_tag (core_icache_req_if.core_req_tag),
|
||||
.core_req_ready (core_icache_req_if.core_req_ready),
|
||||
.core_req_valid (core_icache_req_if.valid),
|
||||
.core_req_rw (core_icache_req_if.rw),
|
||||
.core_req_byteen (core_icache_req_if.byteen),
|
||||
.core_req_addr (core_icache_req_if.addr),
|
||||
.core_req_data (core_icache_req_if.data),
|
||||
.core_req_tag (core_icache_req_if.tag),
|
||||
.core_req_ready (core_icache_req_if.ready),
|
||||
|
||||
// Core response
|
||||
.core_rsp_valid (core_icache_rsp_if.core_rsp_valid),
|
||||
.core_rsp_data (core_icache_rsp_if.core_rsp_data),
|
||||
.core_rsp_tag (core_icache_rsp_if.core_rsp_tag),
|
||||
.core_rsp_ready (core_icache_rsp_if.core_rsp_ready),
|
||||
.core_rsp_valid (core_icache_rsp_if.valid),
|
||||
.core_rsp_data (core_icache_rsp_if.data),
|
||||
.core_rsp_tag (core_icache_rsp_if.tag),
|
||||
.core_rsp_ready (core_icache_rsp_if.ready),
|
||||
|
||||
// DRAM Req
|
||||
.dram_req_valid (icache_dram_req_if.dram_req_valid),
|
||||
.dram_req_rw (icache_dram_req_if.dram_req_rw),
|
||||
.dram_req_byteen (icache_dram_req_if.dram_req_byteen),
|
||||
.dram_req_addr (icache_dram_req_if.dram_req_addr),
|
||||
.dram_req_data (icache_dram_req_if.dram_req_data),
|
||||
.dram_req_tag (icache_dram_req_if.dram_req_tag),
|
||||
.dram_req_ready (icache_dram_req_if.dram_req_ready),
|
||||
.dram_req_valid (icache_dram_req_if.valid),
|
||||
.dram_req_rw (icache_dram_req_if.rw),
|
||||
.dram_req_byteen (icache_dram_req_if.byteen),
|
||||
.dram_req_addr (icache_dram_req_if.addr),
|
||||
.dram_req_data (icache_dram_req_if.data),
|
||||
.dram_req_tag (icache_dram_req_if.tag),
|
||||
.dram_req_ready (icache_dram_req_if.ready),
|
||||
|
||||
// DRAM response
|
||||
.dram_rsp_valid (icache_dram_rsp_if.dram_rsp_valid),
|
||||
.dram_rsp_data (icache_dram_rsp_if.dram_rsp_data),
|
||||
.dram_rsp_tag (icache_dram_rsp_if.dram_rsp_tag),
|
||||
.dram_rsp_ready (icache_dram_rsp_if.dram_rsp_ready),
|
||||
.dram_rsp_valid (icache_dram_rsp_if.valid),
|
||||
.dram_rsp_data (icache_dram_rsp_if.data),
|
||||
.dram_rsp_tag (icache_dram_rsp_if.tag),
|
||||
.dram_rsp_ready (icache_dram_rsp_if.ready),
|
||||
|
||||
// Snoop request
|
||||
.snp_req_valid (0),
|
||||
|
||||
@@ -40,7 +40,19 @@ module VX_pipeline #(
|
||||
input wire icache_rsp_valid,
|
||||
input wire [31:0] icache_rsp_data,
|
||||
input wire [`ICORE_TAG_WIDTH-1:0] icache_rsp_tag,
|
||||
output wire icache_rsp_ready,
|
||||
output wire icache_rsp_ready,
|
||||
|
||||
// CSR I/O Request
|
||||
input wire csr_io_req_valid,
|
||||
input wire[11:0] csr_io_req_addr,
|
||||
input wire csr_io_req_rw,
|
||||
input wire[31:0] csr_io_req_data,
|
||||
output wire csr_io_req_ready,
|
||||
|
||||
// CSR I/O Response
|
||||
output wire csr_io_rsp_valid,
|
||||
output wire[31:0] csr_io_rsp_data,
|
||||
input wire csr_io_rsp_ready,
|
||||
|
||||
// Status
|
||||
output wire busy,
|
||||
@@ -86,6 +98,20 @@ module VX_pipeline #(
|
||||
.CORE_TAG_ID_BITS(`ICORE_TAG_ID_BITS)
|
||||
) core_icache_rsp_if();
|
||||
|
||||
|
||||
// CSR I/O
|
||||
VX_csr_io_req_if csr_io_req_if();
|
||||
assign csr_io_req_if.valid = csr_io_req_valid;
|
||||
assign csr_io_req_if.rw = csr_io_req_rw;
|
||||
assign csr_io_req_if.addr = csr_io_req_addr;
|
||||
assign csr_io_req_if.data = csr_io_req_data;
|
||||
assign csr_io_req_ready = csr_io_req_if.ready;
|
||||
|
||||
VX_csr_io_rsp_if csr_io_rsp_if();
|
||||
assign csr_io_rsp_valid = csr_io_rsp_if.valid;
|
||||
assign csr_io_rsp_data = csr_io_rsp_if.data;
|
||||
assign csr_io_rsp_if.ready = csr_io_rsp_ready;
|
||||
|
||||
// Front-end to Back-end
|
||||
VX_backend_req_if bckE_req_if();
|
||||
|
||||
@@ -134,6 +160,8 @@ module VX_pipeline #(
|
||||
|
||||
.clk (clk),
|
||||
.reset (reset),
|
||||
.csr_io_req_if (csr_io_req_if),
|
||||
.csr_io_rsp_if (csr_io_rsp_if),
|
||||
.schedule_delay (schedule_delay),
|
||||
.warp_ctl_if (warp_ctl_if),
|
||||
.bckE_req_if (bckE_req_if),
|
||||
@@ -148,31 +176,31 @@ module VX_pipeline #(
|
||||
.ebreak (ebreak)
|
||||
);
|
||||
|
||||
assign dcache_req_valid = core_dcache_req_if.core_req_valid;
|
||||
assign dcache_req_rw = core_dcache_req_if.core_req_rw;
|
||||
assign dcache_req_byteen = core_dcache_req_if.core_req_byteen;
|
||||
assign dcache_req_addr = core_dcache_req_if.core_req_addr;
|
||||
assign dcache_req_data = core_dcache_req_if.core_req_data;
|
||||
assign dcache_req_tag = core_dcache_req_if.core_req_tag;
|
||||
assign core_dcache_req_if.core_req_ready = dcache_req_ready;
|
||||
assign dcache_req_valid = core_dcache_req_if.valid;
|
||||
assign dcache_req_rw = core_dcache_req_if.rw;
|
||||
assign dcache_req_byteen = core_dcache_req_if.byteen;
|
||||
assign dcache_req_addr = core_dcache_req_if.addr;
|
||||
assign dcache_req_data = core_dcache_req_if.data;
|
||||
assign dcache_req_tag = core_dcache_req_if.tag;
|
||||
assign core_dcache_req_if.ready = dcache_req_ready;
|
||||
|
||||
assign core_dcache_rsp_if.core_rsp_valid = dcache_rsp_valid;
|
||||
assign core_dcache_rsp_if.core_rsp_data = dcache_rsp_data;
|
||||
assign core_dcache_rsp_if.core_rsp_tag = dcache_rsp_tag;
|
||||
assign dcache_rsp_ready = core_dcache_rsp_if.core_rsp_ready;
|
||||
assign core_dcache_rsp_if.valid = dcache_rsp_valid;
|
||||
assign core_dcache_rsp_if.data = dcache_rsp_data;
|
||||
assign core_dcache_rsp_if.tag = dcache_rsp_tag;
|
||||
assign dcache_rsp_ready = core_dcache_rsp_if.ready;
|
||||
|
||||
assign icache_req_valid = core_icache_req_if.core_req_valid;
|
||||
assign icache_req_rw = core_icache_req_if.core_req_rw;
|
||||
assign icache_req_byteen = core_icache_req_if.core_req_byteen;
|
||||
assign icache_req_addr = core_icache_req_if.core_req_addr;
|
||||
assign icache_req_data = core_icache_req_if.core_req_data;
|
||||
assign icache_req_tag = core_icache_req_if.core_req_tag;
|
||||
assign core_icache_req_if.core_req_ready = icache_req_ready;
|
||||
assign icache_req_valid = core_icache_req_if.valid;
|
||||
assign icache_req_rw = core_icache_req_if.rw;
|
||||
assign icache_req_byteen = core_icache_req_if.byteen;
|
||||
assign icache_req_addr = core_icache_req_if.addr;
|
||||
assign icache_req_data = core_icache_req_if.data;
|
||||
assign icache_req_tag = core_icache_req_if.tag;
|
||||
assign core_icache_req_if.ready = icache_req_ready;
|
||||
|
||||
assign core_icache_rsp_if.core_rsp_valid = icache_rsp_valid;
|
||||
assign core_icache_rsp_if.core_rsp_data = icache_rsp_data;
|
||||
assign core_icache_rsp_if.core_rsp_tag = icache_rsp_tag;
|
||||
assign icache_rsp_ready = core_icache_rsp_if.core_rsp_ready;
|
||||
assign core_icache_rsp_if.valid = icache_rsp_valid;
|
||||
assign core_icache_rsp_if.data = icache_rsp_data;
|
||||
assign core_icache_rsp_if.tag = icache_rsp_tag;
|
||||
assign icache_rsp_ready = core_icache_rsp_if.ready;
|
||||
|
||||
`SCOPE_ASSIGN(scope_busy, busy);
|
||||
`SCOPE_ASSIGN(scope_schedule_delay, schedule_delay);
|
||||
@@ -191,4 +219,4 @@ module VX_pipeline #(
|
||||
end
|
||||
`endif
|
||||
|
||||
endmodule
|
||||
endmodule
|
||||
|
||||
@@ -51,6 +51,7 @@ module VX_scheduler (
|
||||
integer i, w;
|
||||
|
||||
wire acquire_rd = (| bckE_req_if.valid) && (bckE_req_if.wb != 0) && (bckE_req_if.rd != 0) && !schedule_delay;
|
||||
|
||||
wire release_rd = (| writeback_if.valid) && (writeback_if.wb != 0) && (writeback_if.rd != 0);
|
||||
|
||||
wire [`NUM_THREADS-1:0] valid_wb_new_mask = rename_table[writeback_if.warp_num][writeback_if.rd] & ~writeback_if.valid;
|
||||
|
||||
@@ -9,7 +9,7 @@ module VX_warp (
|
||||
input wire[`NUM_THREADS-1:0] thread_mask,
|
||||
input wire change_mask,
|
||||
input wire jal,
|
||||
input wire[31:0] jal_dest,
|
||||
input wire[31:0] dest,
|
||||
input wire branch_dir,
|
||||
input wire[31:0] branch_dest,
|
||||
input wire wspawn,
|
||||
@@ -43,7 +43,7 @@ module VX_warp (
|
||||
|
||||
always @(*) begin
|
||||
if (jal == 1'b1) begin
|
||||
temp_PC = jal_dest;
|
||||
temp_PC = dest;
|
||||
end else if (branch_dir) begin
|
||||
temp_PC = branch_dest;
|
||||
end else begin
|
||||
|
||||
@@ -1,14 +1,14 @@
|
||||
`include "VX_define.vh"
|
||||
|
||||
module VX_warp_sched (
|
||||
input wire clk, // Clock
|
||||
input wire reset,
|
||||
input wire stall,
|
||||
input wire clk,
|
||||
input wire reset,
|
||||
input wire stall,
|
||||
|
||||
// Wspawn
|
||||
input wire wspawn,
|
||||
input wire[31:0] wsapwn_pc,
|
||||
input wire[`NUM_WARPS-1:0] wspawn_new_active,
|
||||
input wire wspawn,
|
||||
input wire[31:0] wsapwn_pc,
|
||||
input wire[`NUM_WARPS-1:0] wspawn_new_active,
|
||||
|
||||
// CTM
|
||||
input wire ctm,
|
||||
@@ -28,38 +28,38 @@ module VX_warp_sched (
|
||||
|
||||
// WSTALL
|
||||
input wire wstall,
|
||||
input wire[`NW_BITS-1:0] wstall_warp_num,
|
||||
input wire [`NW_BITS-1:0] wstall_warp_num,
|
||||
|
||||
// Split
|
||||
input wire is_split,
|
||||
input wire dont_split,
|
||||
input wire[`NUM_THREADS-1:0] split_new_mask,
|
||||
input wire[`NUM_THREADS-1:0] split_later_mask,
|
||||
input wire[31:0] split_save_pc,
|
||||
input wire[`NW_BITS-1:0] split_warp_num,
|
||||
input wire [`NUM_THREADS-1:0] split_new_mask,
|
||||
input wire [`NUM_THREADS-1:0] split_later_mask,
|
||||
input wire [31:0] split_save_pc,
|
||||
input wire [`NW_BITS-1:0] split_warp_num,
|
||||
|
||||
// Join
|
||||
input wire is_join,
|
||||
input wire[`NW_BITS-1:0] join_warp_num,
|
||||
input wire [`NW_BITS-1:0] join_warp_num,
|
||||
|
||||
// JAL
|
||||
input wire jal,
|
||||
input wire[31:0] jal_dest,
|
||||
input wire[`NW_BITS-1:0] jal_warp_num,
|
||||
input wire [31:0] dest,
|
||||
input wire [`NW_BITS-1:0] jal_warp_num,
|
||||
|
||||
// Branch
|
||||
input wire branch_valid,
|
||||
input wire branch_dir,
|
||||
input wire[31:0] branch_dest,
|
||||
input wire[`NW_BITS-1:0] branch_warp_num,
|
||||
input wire [31:0] branch_dest,
|
||||
input wire [`NW_BITS-1:0] branch_warp_num,
|
||||
|
||||
output wire[`NUM_THREADS-1:0] thread_mask,
|
||||
output wire[`NW_BITS-1:0] warp_num,
|
||||
output wire[31:0] warp_pc,
|
||||
output wire [`NUM_THREADS-1:0] thread_mask,
|
||||
output wire [`NW_BITS-1:0] warp_num,
|
||||
output wire [31:0] warp_pc,
|
||||
output wire busy,
|
||||
output wire scheduled_warp,
|
||||
|
||||
input wire[`NW_BITS-1:0] icache_stage_wid,
|
||||
input wire [`NW_BITS-1:0] icache_stage_wid,
|
||||
input wire icache_stage_response
|
||||
);
|
||||
wire update_use_wspawn;
|
||||
@@ -203,24 +203,24 @@ module VX_warp_sched (
|
||||
|
||||
// Jal
|
||||
if (jal) begin
|
||||
warp_pcs[jal_warp_num] <= jal_dest;
|
||||
warp_pcs[jal_warp_num] <= dest;
|
||||
warp_stalled[jal_warp_num] <= 0;
|
||||
end
|
||||
|
||||
// Branch
|
||||
if (branch_valid) begin
|
||||
if (branch_dir) warp_pcs[branch_warp_num] <= branch_dest;
|
||||
if (branch_dir) begin
|
||||
warp_pcs[branch_warp_num] <= branch_dest;
|
||||
end
|
||||
warp_stalled[branch_warp_num] <= 0;
|
||||
end
|
||||
|
||||
// Lock/Release
|
||||
if (scheduled_warp && !stall) begin
|
||||
warp_lock[warp_num] <= 1'b1;
|
||||
// warp_lock <= {`NUM_WARPS{1'b1}};
|
||||
end
|
||||
if (icache_stage_response) begin
|
||||
warp_lock[icache_stage_wid] <= 1'b0;
|
||||
// warp_lock <= {`NUM_WARPS{1'b0}};
|
||||
end
|
||||
|
||||
end
|
||||
@@ -282,8 +282,6 @@ module VX_warp_sched (
|
||||
end
|
||||
endgenerate
|
||||
|
||||
// wire should_stall = stall || (jal && (warp_to_schedule == jal_warp_num)) || (branch_dir && (warp_to_schedule == branch_warp_num));
|
||||
|
||||
wire should_jal = (jal && (warp_to_schedule == jal_warp_num));
|
||||
wire should_bra = (branch_valid && branch_dir && (warp_to_schedule == branch_warp_num));
|
||||
|
||||
@@ -308,7 +306,7 @@ module VX_warp_sched (
|
||||
assign use_active = (count_visible_active != 0) ? visible_active : (warp_active & (~warp_stalled) & (~total_barrier_stall) & (~warp_lock));
|
||||
|
||||
// Choosing a warp to schedule
|
||||
VX_rr_arbiter #(
|
||||
VX_fixed_arbiter #(
|
||||
.N(`NUM_WARPS)
|
||||
) choose_schedule (
|
||||
.clk (clk),
|
||||
|
||||
231
hw/rtl/Vortex.v
231
hw/rtl/Vortex.v
@@ -54,6 +54,19 @@ module Vortex (
|
||||
input wire [`VX_CORE_TAG_WIDTH-1:0] io_rsp_tag,
|
||||
output wire io_rsp_ready,
|
||||
|
||||
// CSR I/O Request
|
||||
input wire csr_io_req_valid,
|
||||
input wire [`VX_CSR_ID_WIDTH-1:0] csr_io_req_coreid,
|
||||
input wire [11:0] csr_io_req_addr,
|
||||
input wire csr_io_req_rw,
|
||||
input wire [31:0] csr_io_req_data,
|
||||
output wire csr_io_req_ready,
|
||||
|
||||
// CSR I/O Response
|
||||
output wire csr_io_rsp_valid,
|
||||
output wire [31:0] csr_io_rsp_data,
|
||||
input wire csr_io_rsp_ready,
|
||||
|
||||
// Status
|
||||
output wire busy,
|
||||
output wire ebreak
|
||||
@@ -61,7 +74,7 @@ module Vortex (
|
||||
if (`NUM_CLUSTERS == 1) begin
|
||||
|
||||
VX_cluster #(
|
||||
.CLUSTER_ID(`L3CACHE_ID)
|
||||
.CLUSTER_ID(0)
|
||||
) cluster (
|
||||
`SCOPE_SIGNALS_ISTAGE_BIND
|
||||
`SCOPE_SIGNALS_LSU_BIND
|
||||
@@ -109,50 +122,74 @@ module Vortex (
|
||||
.io_rsp_tag (io_rsp_tag),
|
||||
.io_rsp_ready (io_rsp_ready),
|
||||
|
||||
.csr_io_req_valid (csr_io_req_valid),
|
||||
.csr_io_req_coreid (csr_io_req_coreid),
|
||||
.csr_io_req_rw (csr_io_req_rw),
|
||||
.csr_io_req_addr (csr_io_req_addr),
|
||||
.csr_io_req_data (csr_io_req_data),
|
||||
.csr_io_req_ready (csr_io_req_ready),
|
||||
|
||||
.csr_io_rsp_valid (csr_io_rsp_valid),
|
||||
.csr_io_rsp_data (csr_io_rsp_data),
|
||||
.csr_io_rsp_ready (csr_io_rsp_ready),
|
||||
|
||||
.busy (busy),
|
||||
.ebreak (ebreak)
|
||||
);
|
||||
|
||||
end else begin
|
||||
|
||||
wire [`NUM_CLUSTERS-1:0] per_cluster_dram_req_valid;
|
||||
wire [`NUM_CLUSTERS-1:0] per_cluster_dram_req_rw;
|
||||
wire [`NUM_CLUSTERS-1:0][`L2DRAM_BYTEEN_WIDTH-1:0] per_cluster_dram_req_byteen;
|
||||
wire [`NUM_CLUSTERS-1:0][`L2DRAM_ADDR_WIDTH-1:0] per_cluster_dram_req_addr;
|
||||
wire [`NUM_CLUSTERS-1:0][`L2DRAM_LINE_WIDTH-1:0] per_cluster_dram_req_data;
|
||||
wire [`NUM_CLUSTERS-1:0][`L2DRAM_TAG_WIDTH-1:0] per_cluster_dram_req_tag;
|
||||
wire l3_core_req_ready;
|
||||
wire per_cluster_dram_req_valid [`NUM_CLUSTERS-1:0];
|
||||
wire per_cluster_dram_req_rw [`NUM_CLUSTERS-1:0];
|
||||
wire [`L2DRAM_BYTEEN_WIDTH-1:0] per_cluster_dram_req_byteen [`NUM_CLUSTERS-1:0];
|
||||
wire [`L2DRAM_ADDR_WIDTH-1:0] per_cluster_dram_req_addr [`NUM_CLUSTERS-1:0];
|
||||
wire [`L2DRAM_LINE_WIDTH-1:0] per_cluster_dram_req_data [`NUM_CLUSTERS-1:0];
|
||||
wire [`L2DRAM_TAG_WIDTH-1:0] per_cluster_dram_req_tag [`NUM_CLUSTERS-1:0];
|
||||
wire l3_core_req_ready;
|
||||
|
||||
wire [`NUM_CLUSTERS-1:0] per_cluster_dram_rsp_valid;
|
||||
wire [`NUM_CLUSTERS-1:0][`L3DRAM_LINE_WIDTH-1:0] per_cluster_dram_rsp_data;
|
||||
wire [`NUM_CLUSTERS-1:0][`L3DRAM_TAG_WIDTH-1:0] per_cluster_dram_rsp_tag;
|
||||
wire [`NUM_CLUSTERS-1:0] per_cluster_dram_rsp_ready;
|
||||
wire per_cluster_dram_rsp_valid [`NUM_CLUSTERS-1:0];
|
||||
wire [`L2DRAM_LINE_WIDTH-1:0] per_cluster_dram_rsp_data [`NUM_CLUSTERS-1:0];
|
||||
wire [`L2DRAM_TAG_WIDTH-1:0] per_cluster_dram_rsp_tag [`NUM_CLUSTERS-1:0];
|
||||
wire per_cluster_dram_rsp_ready [`NUM_CLUSTERS-1:0];
|
||||
|
||||
wire [`NUM_CLUSTERS-1:0] per_cluster_snp_req_valid;
|
||||
wire [`NUM_CLUSTERS-1:0][`L2DRAM_ADDR_WIDTH-1:0] per_cluster_snp_req_addr;
|
||||
wire [`NUM_CLUSTERS-1:0] per_cluster_snp_req_invalidate;
|
||||
wire [`NUM_CLUSTERS-1:0][`L2SNP_TAG_WIDTH-1:0] per_cluster_snp_req_tag;
|
||||
wire [`NUM_CLUSTERS-1:0] per_cluster_snp_req_ready;
|
||||
wire per_cluster_snp_req_valid [`NUM_CLUSTERS-1:0];
|
||||
wire [`L2DRAM_ADDR_WIDTH-1:0] per_cluster_snp_req_addr [`NUM_CLUSTERS-1:0];
|
||||
wire per_cluster_snp_req_invalidate [`NUM_CLUSTERS-1:0];
|
||||
wire [`L2SNP_TAG_WIDTH-1:0] per_cluster_snp_req_tag [`NUM_CLUSTERS-1:0];
|
||||
wire per_cluster_snp_req_ready [`NUM_CLUSTERS-1:0];
|
||||
|
||||
wire [`NUM_CLUSTERS-1:0] per_cluster_snp_rsp_valid;
|
||||
wire [`NUM_CLUSTERS-1:0][`L2SNP_TAG_WIDTH-1:0] per_cluster_snp_rsp_tag;
|
||||
wire [`NUM_CLUSTERS-1:0] per_cluster_snp_rsp_ready;
|
||||
wire per_cluster_snp_rsp_valid [`NUM_CLUSTERS-1:0];
|
||||
wire [`L2SNP_TAG_WIDTH-1:0] per_cluster_snp_rsp_tag [`NUM_CLUSTERS-1:0];
|
||||
wire per_cluster_snp_rsp_ready [`NUM_CLUSTERS-1:0];
|
||||
|
||||
wire [`NUM_CLUSTERS-1:0] per_cluster_io_req_valid;
|
||||
wire [`NUM_CLUSTERS-1:0] per_cluster_io_req_rw;
|
||||
wire [`NUM_CLUSTERS-1:0][3:0] per_cluster_io_req_byteen;
|
||||
wire [`NUM_CLUSTERS-1:0][29:0] per_cluster_io_req_addr;
|
||||
wire [`NUM_CLUSTERS-1:0][31:0] per_cluster_io_req_data;
|
||||
wire [`NUM_CLUSTERS-1:0][`L2CORE_TAG_WIDTH-1:0] per_cluster_io_req_tag;
|
||||
wire [`NUM_CLUSTERS-1:0] per_cluster_io_req_ready;
|
||||
wire per_cluster_io_req_valid [`NUM_CLUSTERS-1:0];
|
||||
wire per_cluster_io_req_rw [`NUM_CLUSTERS-1:0];
|
||||
wire [3:0] per_cluster_io_req_byteen [`NUM_CLUSTERS-1:0];
|
||||
wire [29:0] per_cluster_io_req_addr [`NUM_CLUSTERS-1:0];
|
||||
wire [31:0] per_cluster_io_req_data [`NUM_CLUSTERS-1:0];
|
||||
wire [`L2CORE_TAG_WIDTH-1:0] per_cluster_io_req_tag [`NUM_CLUSTERS-1:0];
|
||||
wire per_cluster_io_req_ready [`NUM_CLUSTERS-1:0];
|
||||
|
||||
wire [`NUM_CLUSTERS-1:0] per_cluster_io_rsp_valid;
|
||||
wire [`NUM_CLUSTERS-1:0][`L2CORE_TAG_WIDTH-1:0] per_cluster_io_rsp_tag;
|
||||
wire [`NUM_CLUSTERS-1:0][31:0] per_cluster_io_rsp_data;
|
||||
wire [`NUM_CLUSTERS-1:0] per_cluster_io_rsp_ready;
|
||||
wire per_cluster_io_rsp_valid [`NUM_CLUSTERS-1:0];
|
||||
wire [`L2CORE_TAG_WIDTH-1:0] per_cluster_io_rsp_tag [`NUM_CLUSTERS-1:0];
|
||||
wire [31:0] per_cluster_io_rsp_data [`NUM_CLUSTERS-1:0];
|
||||
wire per_cluster_io_rsp_ready [`NUM_CLUSTERS-1:0];
|
||||
|
||||
wire [`NUM_CLUSTERS-1:0] per_cluster_busy;
|
||||
wire [`NUM_CLUSTERS-1:0] per_cluster_ebreak;
|
||||
wire per_cluster_csr_io_req_valid [`NUM_CLUSTERS-1:0];
|
||||
wire [11:0] per_cluster_csr_io_req_addr [`NUM_CLUSTERS-1:0];
|
||||
wire per_cluster_csr_io_req_rw [`NUM_CLUSTERS-1:0];
|
||||
wire [31:0] per_cluster_csr_io_req_data [`NUM_CLUSTERS-1:0];
|
||||
wire per_cluster_csr_io_req_ready [`NUM_CLUSTERS-1:0];
|
||||
|
||||
wire per_cluster_csr_io_rsp_valid [`NUM_CLUSTERS-1:0];
|
||||
wire [31:0] per_cluster_csr_io_rsp_data [`NUM_CLUSTERS-1:0];
|
||||
wire per_cluster_csr_io_rsp_ready [`NUM_CLUSTERS-1:0];
|
||||
|
||||
wire per_cluster_busy [`NUM_CLUSTERS-1:0];
|
||||
wire per_cluster_ebreak [`NUM_CLUSTERS-1:0];
|
||||
|
||||
wire [`CLOG2(`NUM_CLUSTERS)-1:0] csr_io_request_id = `CLOG2(`NUM_CLUSTERS)'(csr_io_req_coreid >> `CLOG2(`NUM_CLUSTERS));
|
||||
wire [`NC_BITS-1:0] per_cluster_csr_io_req_coreid = `NC_BITS'(csr_io_req_coreid);
|
||||
|
||||
genvar i;
|
||||
for (i = 0; i < `NUM_CLUSTERS; i++) begin
|
||||
@@ -205,6 +242,17 @@ module Vortex (
|
||||
.io_rsp_tag (per_cluster_io_rsp_tag [i]),
|
||||
.io_rsp_ready (per_cluster_io_rsp_ready [i]),
|
||||
|
||||
.csr_io_req_valid (per_cluster_csr_io_req_valid[i]),
|
||||
.csr_io_req_coreid (per_cluster_csr_io_req_coreid),
|
||||
.csr_io_req_rw (per_cluster_csr_io_req_rw [i]),
|
||||
.csr_io_req_addr (per_cluster_csr_io_req_addr[i]),
|
||||
.csr_io_req_data (per_cluster_csr_io_req_data[i]),
|
||||
.csr_io_req_ready (per_cluster_csr_io_req_ready[i]),
|
||||
|
||||
.csr_io_rsp_valid (per_cluster_csr_io_rsp_valid[i]),
|
||||
.csr_io_rsp_data (per_cluster_csr_io_rsp_data[i]),
|
||||
.csr_io_rsp_ready (per_cluster_csr_io_rsp_ready[i]),
|
||||
|
||||
.busy (per_cluster_busy [i]),
|
||||
.ebreak (per_cluster_ebreak [i])
|
||||
);
|
||||
@@ -216,38 +264,71 @@ module Vortex (
|
||||
.TAG_IN_WIDTH (`L2CORE_TAG_WIDTH),
|
||||
.TAG_OUT_WIDTH (`L3CORE_TAG_WIDTH)
|
||||
) io_arb (
|
||||
.clk (clk),
|
||||
.reset (reset),
|
||||
.clk (clk),
|
||||
.reset (reset),
|
||||
|
||||
// input requests
|
||||
.in_mem_req_valid (per_cluster_io_req_valid),
|
||||
.in_mem_req_rw (per_cluster_io_req_rw),
|
||||
.in_mem_req_byteen (per_cluster_io_req_byteen),
|
||||
.in_mem_req_addr (per_cluster_io_req_addr),
|
||||
.in_mem_req_data (per_cluster_io_req_data),
|
||||
.in_mem_req_tag (per_cluster_io_req_tag),
|
||||
.in_mem_req_ready (per_cluster_io_req_ready),
|
||||
.in_mem_req_valid (per_cluster_io_req_valid),
|
||||
.in_mem_req_rw (per_cluster_io_req_rw),
|
||||
.in_mem_req_byteen (per_cluster_io_req_byteen),
|
||||
.in_mem_req_addr (per_cluster_io_req_addr),
|
||||
.in_mem_req_data (per_cluster_io_req_data),
|
||||
.in_mem_req_tag (per_cluster_io_req_tag),
|
||||
.in_mem_req_ready (per_cluster_io_req_ready),
|
||||
|
||||
// input responses
|
||||
.in_mem_rsp_valid (per_cluster_io_rsp_valid),
|
||||
.in_mem_rsp_data (per_cluster_io_rsp_data),
|
||||
.in_mem_rsp_tag (per_cluster_io_rsp_tag),
|
||||
.in_mem_rsp_ready (per_cluster_io_rsp_ready),
|
||||
.in_mem_rsp_valid (per_cluster_io_rsp_valid),
|
||||
.in_mem_rsp_data (per_cluster_io_rsp_data),
|
||||
.in_mem_rsp_tag (per_cluster_io_rsp_tag),
|
||||
.in_mem_rsp_ready (per_cluster_io_rsp_ready),
|
||||
|
||||
// output request
|
||||
.out_mem_req_valid (io_req_valid),
|
||||
.out_mem_req_rw (io_req_rw),
|
||||
.out_mem_req_byteen (io_req_byteen),
|
||||
.out_mem_req_addr (io_req_addr),
|
||||
.out_mem_req_data (io_req_data),
|
||||
.out_mem_req_tag (io_req_tag),
|
||||
.out_mem_req_ready (io_req_ready),
|
||||
.out_mem_req_valid (io_req_valid),
|
||||
.out_mem_req_rw (io_req_rw),
|
||||
.out_mem_req_byteen (io_req_byteen),
|
||||
.out_mem_req_addr (io_req_addr),
|
||||
.out_mem_req_data (io_req_data),
|
||||
.out_mem_req_tag (io_req_tag),
|
||||
.out_mem_req_ready (io_req_ready),
|
||||
|
||||
// output response
|
||||
.out_mem_rsp_valid (io_rsp_valid),
|
||||
.out_mem_rsp_tag (io_rsp_tag),
|
||||
.out_mem_rsp_data (io_rsp_data),
|
||||
.out_mem_rsp_ready (io_rsp_ready)
|
||||
.out_mem_rsp_valid (io_rsp_valid),
|
||||
.out_mem_rsp_tag (io_rsp_tag),
|
||||
.out_mem_rsp_data (io_rsp_data),
|
||||
.out_mem_rsp_ready (io_rsp_ready)
|
||||
);
|
||||
|
||||
VX_csr_io_arb #(
|
||||
.NUM_REQUESTS (`NUM_CLUSTERS)
|
||||
) csr_io_arb (
|
||||
.clk (clk),
|
||||
.reset (reset),
|
||||
|
||||
.request_id (csr_io_request_id),
|
||||
|
||||
// input requests
|
||||
.in_csr_io_req_valid (csr_io_req_valid),
|
||||
.in_csr_io_req_addr (csr_io_req_addr),
|
||||
.in_csr_io_req_rw (csr_io_req_rw),
|
||||
.in_csr_io_req_data (csr_io_req_data),
|
||||
.in_csr_io_req_ready (csr_io_req_ready),
|
||||
|
||||
// input responses
|
||||
.in_csr_io_rsp_valid (per_cluster_csr_io_rsp_valid),
|
||||
.in_csr_io_rsp_data (per_cluster_csr_io_rsp_data),
|
||||
.in_csr_io_rsp_ready (per_cluster_csr_io_rsp_ready),
|
||||
|
||||
// output request
|
||||
.out_csr_io_req_valid (per_cluster_csr_io_req_valid),
|
||||
.out_csr_io_req_addr (per_cluster_csr_io_req_addr),
|
||||
.out_csr_io_req_rw (per_cluster_csr_io_req_rw),
|
||||
.out_csr_io_req_data (per_cluster_csr_io_req_data),
|
||||
.out_csr_io_req_ready (per_cluster_csr_io_req_ready),
|
||||
|
||||
// output response
|
||||
.out_csr_io_rsp_valid (csr_io_rsp_valid),
|
||||
.out_csr_io_rsp_data (csr_io_rsp_data),
|
||||
.out_csr_io_rsp_ready (csr_io_rsp_ready)
|
||||
);
|
||||
|
||||
assign busy = (| per_cluster_busy);
|
||||
@@ -255,27 +336,27 @@ module Vortex (
|
||||
|
||||
// L3 Cache ///////////////////////////////////////////////////////////
|
||||
|
||||
wire [`L3NUM_REQUESTS-1:0] l3_core_req_valid;
|
||||
wire [`L3NUM_REQUESTS-1:0] l3_core_req_rw;
|
||||
wire [`L3NUM_REQUESTS-1:0][`L2DRAM_BYTEEN_WIDTH-1:0] l3_core_req_byteen;
|
||||
wire [`L3NUM_REQUESTS-1:0][`L2DRAM_ADDR_WIDTH-1:0] l3_core_req_addr;
|
||||
wire [`L3NUM_REQUESTS-1:0][`L2DRAM_LINE_WIDTH-1:0] l3_core_req_data;
|
||||
wire [`L3NUM_REQUESTS-1:0][`L2DRAM_TAG_WIDTH-1:0] l3_core_req_tag;
|
||||
wire l3_core_req_valid [`L3NUM_REQUESTS-1:0];
|
||||
wire l3_core_req_rw [`L3NUM_REQUESTS-1:0];
|
||||
wire [`L2DRAM_BYTEEN_WIDTH-1:0] l3_core_req_byteen [`L3NUM_REQUESTS-1:0];
|
||||
wire [`L2DRAM_ADDR_WIDTH-1:0] l3_core_req_addr [`L3NUM_REQUESTS-1:0];
|
||||
wire [`L2DRAM_LINE_WIDTH-1:0] l3_core_req_data [`L3NUM_REQUESTS-1:0];
|
||||
wire [`L2DRAM_TAG_WIDTH-1:0] l3_core_req_tag [`L3NUM_REQUESTS-1:0];
|
||||
|
||||
wire [`L3NUM_REQUESTS-1:0] l3_core_rsp_valid;
|
||||
wire [`L3NUM_REQUESTS-1:0][`L2DRAM_LINE_WIDTH-1:0] l3_core_rsp_data;
|
||||
wire [`L3NUM_REQUESTS-1:0][`L2DRAM_TAG_WIDTH-1:0] l3_core_rsp_tag;
|
||||
wire l3_core_rsp_ready;
|
||||
wire l3_core_rsp_valid [`L3NUM_REQUESTS-1:0];
|
||||
wire [`L2DRAM_LINE_WIDTH-1:0] l3_core_rsp_data [`L3NUM_REQUESTS-1:0];
|
||||
wire [`L2DRAM_TAG_WIDTH-1:0] l3_core_rsp_tag [`L3NUM_REQUESTS-1:0];
|
||||
wire l3_core_rsp_ready;
|
||||
|
||||
wire [`NUM_CLUSTERS-1:0] l3_snp_fwdout_valid;
|
||||
wire [`NUM_CLUSTERS-1:0][`L2DRAM_ADDR_WIDTH-1:0] l3_snp_fwdout_addr;
|
||||
wire [`NUM_CLUSTERS-1:0] l3_snp_fwdout_invalidate;
|
||||
wire [`NUM_CLUSTERS-1:0][`L2SNP_TAG_WIDTH-1:0] l3_snp_fwdout_tag;
|
||||
wire [`NUM_CLUSTERS-1:0] l3_snp_fwdout_ready;
|
||||
wire l3_snp_fwdout_valid [`NUM_CLUSTERS-1:0];
|
||||
wire [`L2DRAM_ADDR_WIDTH-1:0] l3_snp_fwdout_addr [`NUM_CLUSTERS-1:0];
|
||||
wire l3_snp_fwdout_invalidate [`NUM_CLUSTERS-1:0];
|
||||
wire [`L2SNP_TAG_WIDTH-1:0] l3_snp_fwdout_tag [`NUM_CLUSTERS-1:0];
|
||||
wire l3_snp_fwdout_ready [`NUM_CLUSTERS-1:0];
|
||||
|
||||
wire [`NUM_CLUSTERS-1:0] l3_snp_fwdin_valid;
|
||||
wire [`NUM_CLUSTERS-1:0][`L2SNP_TAG_WIDTH-1:0] l3_snp_fwdin_tag;
|
||||
wire [`NUM_CLUSTERS-1:0] l3_snp_fwdin_ready;
|
||||
wire l3_snp_fwdin_valid [`NUM_CLUSTERS-1:0];
|
||||
wire [`L2SNP_TAG_WIDTH-1:0] l3_snp_fwdin_tag [`NUM_CLUSTERS-1:0];
|
||||
wire l3_snp_fwdin_ready [`NUM_CLUSTERS-1:0];
|
||||
|
||||
for (i = 0; i < `L3NUM_REQUESTS; i++) begin
|
||||
// Core Request
|
||||
|
||||
15
hw/rtl/cache/VX_cache_core_rsp_merge.v
vendored
15
hw/rtl/cache/VX_cache_core_rsp_merge.v
vendored
@@ -29,12 +29,7 @@ module VX_cache_core_rsp_merge #(
|
||||
input wire core_rsp_ready
|
||||
);
|
||||
|
||||
reg [NUM_BANKS-1:0] per_bank_core_rsp_pop_unqual;
|
||||
|
||||
assign per_bank_core_rsp_ready = per_bank_core_rsp_pop_unqual & {NUM_BANKS{core_rsp_ready}};
|
||||
|
||||
wire [`BANK_BITS-1:0] main_bank_index;
|
||||
wire grant_valid;
|
||||
VX_fair_arbiter #(
|
||||
.N(NUM_BANKS)
|
||||
) sel_bank (
|
||||
@@ -42,10 +37,14 @@ module VX_cache_core_rsp_merge #(
|
||||
.reset (reset),
|
||||
.requests (per_bank_core_rsp_valid),
|
||||
.grant_index (main_bank_index),
|
||||
.grant_valid (grant_valid),
|
||||
`UNUSED_PIN (grant_valid),
|
||||
`UNUSED_PIN (grant_onehot)
|
||||
);
|
||||
|
||||
reg [NUM_BANKS-1:0] per_bank_core_rsp_pop_unqual;
|
||||
|
||||
assign per_bank_core_rsp_ready = per_bank_core_rsp_pop_unqual & {NUM_BANKS{core_rsp_ready}};
|
||||
|
||||
integer i;
|
||||
|
||||
if (CORE_TAG_ID_BITS != 0) begin
|
||||
@@ -54,7 +53,7 @@ module VX_cache_core_rsp_merge #(
|
||||
core_rsp_valid = 0;
|
||||
core_rsp_data = 0;
|
||||
for (i = 0; i < NUM_BANKS; i++) begin
|
||||
if (grant_valid && per_bank_core_rsp_valid[i]
|
||||
if (per_bank_core_rsp_valid[i]
|
||||
&& (per_bank_core_rsp_tag[i][CORE_TAG_ID_BITS-1:0] == per_bank_core_rsp_tag[main_bank_index][CORE_TAG_ID_BITS-1:0])) begin
|
||||
core_rsp_valid[per_bank_core_rsp_tid[i]] = 1;
|
||||
core_rsp_data[per_bank_core_rsp_tid[i]] = per_bank_core_rsp_data[i];
|
||||
@@ -70,7 +69,7 @@ module VX_cache_core_rsp_merge #(
|
||||
core_rsp_data = 0;
|
||||
core_rsp_tag = 0;
|
||||
for (i = 0; i < NUM_BANKS; i++) begin
|
||||
if (grant_valid && per_bank_core_rsp_valid[i]
|
||||
if (per_bank_core_rsp_valid[i]
|
||||
&& !core_rsp_valid[per_bank_core_rsp_tid[i]]
|
||||
&& ((main_bank_index == `BANK_BITS'(i))
|
||||
|| (per_bank_core_rsp_tid[i] != per_bank_core_rsp_tid[main_bank_index]))) begin
|
||||
|
||||
2
hw/rtl/cache/VX_cache_miss_resrv.v
vendored
2
hw/rtl/cache/VX_cache_miss_resrv.v
vendored
@@ -66,7 +66,7 @@ module VX_cache_miss_resrv #(
|
||||
|
||||
reg [`LOG2UP(MRVQ_SIZE+1)-1:0] size;
|
||||
|
||||
`STATIC_ASSERT(MRVQ_SIZE > 5, "invalid size");
|
||||
`STATIC_ASSERT(MRVQ_SIZE > 5, "invalid size")
|
||||
|
||||
assign miss_resrv_full = (size == $bits(size)'(MRVQ_SIZE));
|
||||
assign miss_resrv_stop = (size > $bits(size)'(MRVQ_SIZE-5)); // need to add 5 cycles to prevent pipeline lock
|
||||
|
||||
4
hw/rtl/cache/VX_snp_forwarder.v
vendored
4
hw/rtl/cache/VX_snp_forwarder.v
vendored
@@ -37,7 +37,7 @@ module VX_snp_forwarder #(
|
||||
input wire [NUM_REQUESTS-1:0][`LOG2UP(SNRQ_SIZE)-1:0] snp_fwdin_tag,
|
||||
output wire [NUM_REQUESTS-1:0] snp_fwdin_ready
|
||||
);
|
||||
`STATIC_ASSERT(NUM_REQUESTS > 1, "invalid value");
|
||||
`STATIC_ASSERT(NUM_REQUESTS > 1, "invalid value")
|
||||
|
||||
reg [`REQS_BITS:0] pending_cntrs [SNRQ_SIZE-1:0];
|
||||
|
||||
@@ -88,7 +88,7 @@ module VX_snp_forwarder #(
|
||||
genvar i;
|
||||
|
||||
for (i = 0; i < NUM_REQUESTS; i++) begin
|
||||
assign snp_fwdout_valid[i] = snp_req_valid && !sfq_full;
|
||||
assign snp_fwdout_valid[i] = snp_req_valid && snp_req_ready;
|
||||
assign snp_fwdout_addr[i] = snp_req_addr;
|
||||
assign snp_fwdout_invalidate[i] = snp_req_invalidate;
|
||||
assign snp_fwdout_tag[i] = sfq_write_addr;
|
||||
|
||||
@@ -5,7 +5,10 @@
|
||||
|
||||
interface VX_backend_req_if ();
|
||||
|
||||
wire [11:0] csr_address;
|
||||
wire [`NUM_THREADS-1:0] valid;
|
||||
wire [`NW_BITS-1:0] warp_num;
|
||||
wire [31:0] curr_PC;
|
||||
wire [11:0] csr_addr;
|
||||
wire is_csr;
|
||||
wire csr_immed;
|
||||
wire [31:0] csr_mask;
|
||||
@@ -20,14 +23,11 @@ interface VX_backend_req_if ();
|
||||
wire [`BYTE_EN_BITS-1:0] mem_write;
|
||||
wire [2:0] branch_type;
|
||||
wire [19:0] upper_immed;
|
||||
wire [31:0] curr_PC;
|
||||
wire is_etype;
|
||||
wire is_jal;
|
||||
wire jal;
|
||||
wire [31:0] jal_offset;
|
||||
wire [31:0] next_PC;
|
||||
wire [`NUM_THREADS-1:0] valid;
|
||||
wire [`NW_BITS-1:0] warp_num;
|
||||
wire [31:0] next_PC;
|
||||
|
||||
// GPGPU stuff
|
||||
wire is_wspawn;
|
||||
|
||||
@@ -5,10 +5,10 @@
|
||||
|
||||
interface VX_branch_rsp_if ();
|
||||
|
||||
wire valid_branch;
|
||||
wire branch_dir;
|
||||
wire [31:0] branch_dest;
|
||||
wire [`NW_BITS-1:0] branch_warp_num;
|
||||
wire valid;
|
||||
wire dir;
|
||||
wire [31:0] dest;
|
||||
wire [`NW_BITS-1:0] warp_num;
|
||||
|
||||
endinterface
|
||||
|
||||
|
||||
@@ -10,13 +10,13 @@ interface VX_cache_core_req_if #(
|
||||
parameter CORE_TAG_ID_BITS = 0
|
||||
) ();
|
||||
|
||||
wire [NUM_REQUESTS-1:0] core_req_valid;
|
||||
wire [NUM_REQUESTS-1:0] core_req_rw;
|
||||
wire [NUM_REQUESTS-1:0][WORD_SIZE-1:0] core_req_byteen;
|
||||
wire [NUM_REQUESTS-1:0][`WORD_ADDR_WIDTH-1:0] core_req_addr;
|
||||
wire [NUM_REQUESTS-1:0][`WORD_WIDTH-1:0] core_req_data;
|
||||
wire [`CORE_REQ_TAG_COUNT-1:0][CORE_TAG_WIDTH-1:0] core_req_tag;
|
||||
wire core_req_ready;
|
||||
wire [NUM_REQUESTS-1:0] valid;
|
||||
wire [NUM_REQUESTS-1:0] rw;
|
||||
wire [NUM_REQUESTS-1:0][WORD_SIZE-1:0] byteen;
|
||||
wire [NUM_REQUESTS-1:0][`WORD_ADDR_WIDTH-1:0] addr;
|
||||
wire [NUM_REQUESTS-1:0][`WORD_WIDTH-1:0] data;
|
||||
wire [`CORE_REQ_TAG_COUNT-1:0][CORE_TAG_WIDTH-1:0] tag;
|
||||
wire ready;
|
||||
|
||||
endinterface
|
||||
|
||||
|
||||
@@ -10,10 +10,10 @@ interface VX_cache_core_rsp_if #(
|
||||
parameter CORE_TAG_ID_BITS = 0
|
||||
) ();
|
||||
|
||||
wire [NUM_REQUESTS-1:0] core_rsp_valid;
|
||||
wire [NUM_REQUESTS-1:0][`WORD_WIDTH-1:0] core_rsp_data;
|
||||
wire [`CORE_REQ_TAG_COUNT-1:0][CORE_TAG_WIDTH-1:0] core_rsp_tag;
|
||||
wire core_rsp_ready;
|
||||
wire [NUM_REQUESTS-1:0] valid;
|
||||
wire [NUM_REQUESTS-1:0][`WORD_WIDTH-1:0] data;
|
||||
wire [`CORE_REQ_TAG_COUNT-1:0][CORE_TAG_WIDTH-1:0] tag;
|
||||
wire ready;
|
||||
|
||||
endinterface
|
||||
|
||||
|
||||
@@ -9,13 +9,13 @@ interface VX_cache_dram_req_if #(
|
||||
parameter DRAM_TAG_WIDTH = 1
|
||||
) ();
|
||||
|
||||
wire dram_req_valid;
|
||||
wire dram_req_rw;
|
||||
wire [(DRAM_LINE_WIDTH/8)-1:0] dram_req_byteen;
|
||||
wire [DRAM_ADDR_WIDTH-1:0] dram_req_addr;
|
||||
wire [DRAM_LINE_WIDTH-1:0] dram_req_data;
|
||||
wire [DRAM_TAG_WIDTH-1:0] dram_req_tag;
|
||||
wire dram_req_ready;
|
||||
wire valid;
|
||||
wire rw;
|
||||
wire [(DRAM_LINE_WIDTH/8)-1:0] byteen;
|
||||
wire [DRAM_ADDR_WIDTH-1:0] addr;
|
||||
wire [DRAM_LINE_WIDTH-1:0] data;
|
||||
wire [DRAM_TAG_WIDTH-1:0] tag;
|
||||
wire ready;
|
||||
|
||||
endinterface
|
||||
|
||||
|
||||
@@ -8,10 +8,10 @@ interface VX_cache_dram_rsp_if #(
|
||||
parameter DRAM_TAG_WIDTH = 1
|
||||
) ();
|
||||
|
||||
wire dram_rsp_valid;
|
||||
wire [DRAM_LINE_WIDTH-1:0] dram_rsp_data;
|
||||
wire [DRAM_TAG_WIDTH-1:0] dram_rsp_tag;
|
||||
wire dram_rsp_ready;
|
||||
wire valid;
|
||||
wire [DRAM_LINE_WIDTH-1:0] data;
|
||||
wire [DRAM_TAG_WIDTH-1:0] tag;
|
||||
wire ready;
|
||||
|
||||
endinterface
|
||||
|
||||
|
||||
@@ -8,11 +8,11 @@ interface VX_cache_snp_req_if #(
|
||||
parameter SNP_TAG_WIDTH = 0
|
||||
) ();
|
||||
|
||||
wire snp_req_valid;
|
||||
wire [DRAM_ADDR_WIDTH-1:0] snp_req_addr;
|
||||
wire snp_req_invalidate;
|
||||
wire [SNP_TAG_WIDTH-1:0] snp_req_tag;
|
||||
wire snp_req_ready;
|
||||
wire valid;
|
||||
wire [DRAM_ADDR_WIDTH-1:0] addr;
|
||||
wire invalidate;
|
||||
wire [SNP_TAG_WIDTH-1:0] tag;
|
||||
wire ready;
|
||||
|
||||
endinterface
|
||||
|
||||
|
||||
@@ -7,9 +7,9 @@ interface VX_cache_snp_rsp_if #(
|
||||
parameter SNP_TAG_WIDTH = 0
|
||||
) ();
|
||||
|
||||
wire snp_rsp_valid;
|
||||
wire [SNP_TAG_WIDTH-1:0] snp_rsp_tag;
|
||||
wire snp_rsp_ready;
|
||||
wire valid;
|
||||
wire [SNP_TAG_WIDTH-1:0] tag;
|
||||
wire ready;
|
||||
|
||||
endinterface
|
||||
|
||||
|
||||
16
hw/rtl/interfaces/VX_csr_io_req_if.v
Normal file
16
hw/rtl/interfaces/VX_csr_io_req_if.v
Normal file
@@ -0,0 +1,16 @@
|
||||
`ifndef VX_CSR_IO_REQ_IF
|
||||
`define VX_CSR_IO_REQ_IF
|
||||
|
||||
`include "VX_define.vh"
|
||||
|
||||
interface VX_csr_io_req_if ();
|
||||
|
||||
wire valid;
|
||||
wire rw;
|
||||
wire [11:0] addr;
|
||||
wire [31:0] data;
|
||||
wire ready;
|
||||
|
||||
endinterface
|
||||
|
||||
`endif
|
||||
14
hw/rtl/interfaces/VX_csr_io_rsp_if.v
Normal file
14
hw/rtl/interfaces/VX_csr_io_rsp_if.v
Normal file
@@ -0,0 +1,14 @@
|
||||
`ifndef VX_CSR_IO_RSP_IF
|
||||
`define VX_CSR_IO_RSP_IF
|
||||
|
||||
`include "VX_define.vh"
|
||||
|
||||
interface VX_csr_io_rsp_if ();
|
||||
|
||||
wire valid;
|
||||
wire [31:0] data;
|
||||
wire ready;
|
||||
|
||||
endinterface
|
||||
|
||||
`endif
|
||||
@@ -11,10 +11,12 @@ interface VX_csr_req_if ();
|
||||
wire [1:0] wb;
|
||||
wire [4:0] alu_op;
|
||||
wire is_csr;
|
||||
wire [11:0] csr_address;
|
||||
wire [11:0] csr_addr;
|
||||
wire csr_immed;
|
||||
wire [31:0] csr_mask;
|
||||
|
||||
wire is_io;
|
||||
|
||||
endinterface
|
||||
|
||||
`endif
|
||||
`endif
|
||||
|
||||
@@ -38,7 +38,7 @@ interface VX_exec_unit_req_if ();
|
||||
|
||||
// CSR info
|
||||
wire is_csr;
|
||||
wire [11:0] csr_address;
|
||||
wire [11:0] csr_addr;
|
||||
wire csr_immed;
|
||||
wire [31:0] csr_mask;
|
||||
|
||||
|
||||
@@ -5,10 +5,10 @@
|
||||
|
||||
interface VX_inst_meta_if ();
|
||||
|
||||
wire [31:0] instruction;
|
||||
wire [31:0] inst_pc;
|
||||
wire [`NW_BITS-1:0] warp_num;
|
||||
wire [`NUM_THREADS-1:0] valid;
|
||||
wire [31:0] curr_PC;
|
||||
wire [`NW_BITS-1:0] warp_num;
|
||||
wire [31:0] instruction;
|
||||
|
||||
endinterface
|
||||
|
||||
|
||||
@@ -6,9 +6,9 @@
|
||||
|
||||
interface VX_jal_rsp_if ();
|
||||
|
||||
wire jal;
|
||||
wire [31:0] jal_dest;
|
||||
wire [`NW_BITS-1:0] jal_warp_num;
|
||||
wire valid;
|
||||
wire [31:0] dest;
|
||||
wire [`NW_BITS-1:0] warp_num;
|
||||
|
||||
endinterface
|
||||
|
||||
|
||||
@@ -7,7 +7,7 @@
|
||||
interface VX_join_if ();
|
||||
|
||||
wire is_join;
|
||||
wire [`NW_BITS-1:0] join_warp_num;
|
||||
wire [`NW_BITS-1:0] warp_num;
|
||||
|
||||
endinterface
|
||||
|
||||
|
||||
@@ -10,8 +10,8 @@ interface VX_lsu_req_if ();
|
||||
wire [31:0] curr_PC;
|
||||
wire [`NW_BITS-1:0] warp_num;
|
||||
wire [`NUM_THREADS-1:0][31:0] store_data;
|
||||
wire [`NUM_THREADS-1:0][31:0] base_address; // A reg data
|
||||
wire [31:0] offset; // itype_immed
|
||||
wire [`NUM_THREADS-1:0][31:0] base_addr; // A reg data
|
||||
wire [31:0] offset; // itype_immed
|
||||
wire [`BYTE_EN_BITS-1:0] mem_read;
|
||||
wire [`BYTE_EN_BITS-1:0] mem_write;
|
||||
wire [4:0] rd; // dest register
|
||||
|
||||
@@ -10,8 +10,9 @@ interface VX_wb_if ();
|
||||
wire [`NW_BITS-1:0] warp_num;
|
||||
wire [4:0] rd;
|
||||
wire [1:0] wb;
|
||||
wire [31:0] curr_PC;
|
||||
wire [31:0] curr_PC;
|
||||
wire is_io;
|
||||
|
||||
endinterface
|
||||
|
||||
`endif
|
||||
`endif
|
||||
|
||||
@@ -10,11 +10,11 @@ module VX_divide #(
|
||||
input wire clk,
|
||||
input wire reset,
|
||||
|
||||
input [WIDTHN-1:0] numer,
|
||||
input [WIDTHD-1:0] denom,
|
||||
input wire [WIDTHN-1:0] numer,
|
||||
input wire [WIDTHD-1:0] denom,
|
||||
|
||||
output reg [WIDTHN-1:0] quotient,
|
||||
output reg [WIDTHD-1:0] remainder
|
||||
output wire [WIDTHN-1:0] quotient,
|
||||
output wire [WIDTHD-1:0] remainder
|
||||
);
|
||||
|
||||
`ifdef QUARTUS
|
||||
@@ -35,8 +35,8 @@ module VX_divide #(
|
||||
quartus_div.lpm_widthd = WIDTHD,
|
||||
quartus_div.lpm_nrepresentation = NSIGNED ? "SIGNED" : "UNSIGNED",
|
||||
quartus_div.lpm_drepresentation = DSIGNED ? "SIGNED" : "UNSIGNED",
|
||||
quartus_div.lpm_hint = "LPM_REMAINDERPOSITIVE=FALSE,MAXIMIZE_SPEED=9",
|
||||
quartus_div.lpm_pipeline = PIPELINE;
|
||||
quartus_div.lpm_hint = "MAXIMIZE_SPEED=6,LPM_REMAINDERPOSITIVE=FALSE",
|
||||
quartus_div.lpm_pipeline = PIPELINE;
|
||||
|
||||
`else
|
||||
|
||||
|
||||
@@ -3,20 +3,19 @@
|
||||
module VX_encoder_onehot #(
|
||||
parameter N = 6
|
||||
) (
|
||||
input wire [N-1:0] onehot,
|
||||
output reg valid,
|
||||
output reg [`LOG2UP(N)-1:0] value
|
||||
input wire [N-1:0] onehot,
|
||||
output reg [`LOG2UP(N)-1:0] binary,
|
||||
output reg valid
|
||||
);
|
||||
integer i;
|
||||
|
||||
always @(*) begin
|
||||
valid = 1'b0;
|
||||
value = {`LOG2UP(N){1'bx}};
|
||||
binary = `LOG2UP(N)'(0);
|
||||
for (i = 0; i < N; i++) begin
|
||||
if (onehot[i]) begin
|
||||
valid = 1'b1;
|
||||
value = `LOG2UP(N)'(i);
|
||||
break;
|
||||
binary = `LOG2UP(N)'(i);
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
`include "VX_define.vh"
|
||||
|
||||
module VX_fair_arbiter #(
|
||||
parameter N = 0
|
||||
parameter N = 1
|
||||
) (
|
||||
input wire clk,
|
||||
input wire reset,
|
||||
@@ -11,7 +11,6 @@ module VX_fair_arbiter #(
|
||||
output wire grant_valid
|
||||
);
|
||||
|
||||
|
||||
if (N == 1) begin
|
||||
|
||||
`UNUSED_VAR (clk)
|
||||
@@ -20,8 +19,7 @@ module VX_fair_arbiter #(
|
||||
assign grant_onehot = requests;
|
||||
assign grant_valid = requests[0];
|
||||
|
||||
end else begin
|
||||
|
||||
end else begin
|
||||
|
||||
reg [N-1:0] requests_use;
|
||||
wire [N-1:0] update_value;
|
||||
@@ -48,7 +46,7 @@ module VX_fair_arbiter #(
|
||||
|
||||
reg [N-1:0] grant_onehot_r;
|
||||
|
||||
VX_priority_encoder # (
|
||||
VX_priority_encoder #(
|
||||
.N(N)
|
||||
) priority_encoder (
|
||||
.data_in (requests_use),
|
||||
@@ -61,7 +59,7 @@ module VX_fair_arbiter #(
|
||||
grant_onehot_r[grant_index] = 1;
|
||||
end
|
||||
assign grant_onehot = grant_onehot_r;
|
||||
assign late_value = ((refill_original ^ requests) & ~refill_original);
|
||||
assign late_value = ((refill_original ^ requests) & ~refill_original);
|
||||
assign update_value = (requests_use & ~grant_onehot_r) | late_value;
|
||||
|
||||
end
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
`include "VX_define.vh"
|
||||
|
||||
module VX_fixed_arbiter #(
|
||||
parameter N = 0
|
||||
parameter N = 1
|
||||
) (
|
||||
input wire clk,
|
||||
input wire reset,
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
`include "VX_define.vh"
|
||||
|
||||
module VX_generic_queue #(
|
||||
parameter DATAW,
|
||||
parameter DATAW = 1,
|
||||
parameter SIZE = 16,
|
||||
parameter BUFFERED_OUTPUT = 1
|
||||
) (
|
||||
@@ -15,7 +15,7 @@ module VX_generic_queue #(
|
||||
output wire full,
|
||||
output wire [`LOG2UP(SIZE+1)-1:0] size
|
||||
);
|
||||
`STATIC_ASSERT(`ISPOW2(SIZE), "must be 0 or power of 2!");
|
||||
`STATIC_ASSERT(`ISPOW2(SIZE), "must be 0 or power of 2!")
|
||||
|
||||
reg [`LOG2UP(SIZE+1)-1:0] size_r;
|
||||
wire reading;
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
`include "VX_define.vh"
|
||||
|
||||
module VX_generic_register #(
|
||||
parameter N,
|
||||
parameter N = 1,
|
||||
parameter PASSTHRU = 0
|
||||
) (
|
||||
input wire clk,
|
||||
|
||||
@@ -1,8 +1,8 @@
|
||||
`include "VX_define.vh"
|
||||
|
||||
module VX_indexable_queue #(
|
||||
parameter DATAW,
|
||||
parameter SIZE
|
||||
parameter DATAW = 1,
|
||||
parameter SIZE = 1
|
||||
) (
|
||||
input wire clk,
|
||||
input wire reset,
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
`include "VX_define.vh"
|
||||
|
||||
module VX_matrix_arbiter #(
|
||||
parameter N = 0
|
||||
parameter N = 1
|
||||
) (
|
||||
input wire clk,
|
||||
input wire reset,
|
||||
@@ -27,8 +27,8 @@ module VX_matrix_arbiter #(
|
||||
|
||||
genvar i, j;
|
||||
|
||||
for (i = 0; i < N; ++i) begin
|
||||
for (j = 0; j < N; ++j) begin
|
||||
for (i = 0; i < N; i++) begin
|
||||
for (j = 0; j < N; j++) begin
|
||||
if (j > i) begin
|
||||
assign pri[j][i] = requests[i] && state[i][j];
|
||||
end
|
||||
@@ -43,8 +43,8 @@ module VX_matrix_arbiter #(
|
||||
assign grant_onehot[i] = requests[i] && !(| pri[i]);
|
||||
end
|
||||
|
||||
for (i = 0; i < N; ++i) begin
|
||||
for (j = i + 1; j < N; ++j) begin
|
||||
for (i = 0; i < N; i++) begin
|
||||
for (j = i + 1; j < N; j++) begin
|
||||
always @(posedge clk) begin
|
||||
if (reset) begin
|
||||
state[i][j] <= 0;
|
||||
|
||||
@@ -7,13 +7,12 @@ module VX_mult #(
|
||||
parameter SIGNED = 0,
|
||||
parameter PIPELINE = 0
|
||||
) (
|
||||
input clk,
|
||||
input reset,
|
||||
input wire clk,
|
||||
input wire reset,
|
||||
|
||||
input [WIDTHA-1:0] dataa,
|
||||
input [WIDTHB-1:0] datab,
|
||||
|
||||
output reg [WIDTHP-1:0] result
|
||||
input wire [WIDTHA-1:0] dataa,
|
||||
input wire [WIDTHB-1:0] datab,
|
||||
output wire [WIDTHP-1:0] result
|
||||
);
|
||||
|
||||
`ifdef QUARTUS
|
||||
@@ -23,9 +22,9 @@ module VX_mult #(
|
||||
.dataa (dataa),
|
||||
.datab (datab),
|
||||
.result (result),
|
||||
.sclr (reset),
|
||||
.aclr (1'b0),
|
||||
.clken (1'b1),
|
||||
.sclr (1'b0),
|
||||
.sum (1'b0)
|
||||
);
|
||||
|
||||
@@ -35,7 +34,7 @@ module VX_mult #(
|
||||
quartus_mult.lpm_widthp = WIDTHP,
|
||||
quartus_mult.lpm_representation = SIGNED ? "SIGNED" : "UNSIGNED",
|
||||
quartus_mult.lpm_pipeline = PIPELINE,
|
||||
quartus_mult.lpm_hint = "MAXIMIZE_SPEED=9";
|
||||
quartus_mult.lpm_hint = "DEDICATED_MULTIPLIER_CIRCUITRY=YES,MAXIMIZE_SPEED=9";
|
||||
`else
|
||||
|
||||
wire [WIDTHP-1:0] result_unqual;
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
`include "VX_define.vh"
|
||||
|
||||
module VX_priority_encoder #(
|
||||
parameter N
|
||||
parameter N = 1
|
||||
) (
|
||||
input wire [N-1:0] data_in,
|
||||
output reg [`LOG2UP(N)-1:0] data_out,
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
`include "VX_define.vh"
|
||||
|
||||
module VX_rr_arbiter #(
|
||||
parameter N = 0
|
||||
parameter N = 1
|
||||
) (
|
||||
input wire clk,
|
||||
input wire reset,
|
||||
@@ -29,9 +29,9 @@ module VX_rr_arbiter #(
|
||||
integer i, j;
|
||||
|
||||
always @(*) begin
|
||||
for (i = 0; i < N; ++i) begin
|
||||
for (i = 0; i < N; i++) begin
|
||||
grant_table[i] = `CLOG2(N)'(i);
|
||||
for (j = 0; j < N; ++j) begin
|
||||
for (j = 0; j < N; j++) begin
|
||||
if (requests[(i+j) % N]) begin
|
||||
grant_table[i] = `CLOG2(N)'((i+j) % N);
|
||||
end
|
||||
|
||||
@@ -1,30 +0,0 @@
|
||||
`include "VX_define.vh"
|
||||
|
||||
module VX_d_e_reg (
|
||||
input wire clk,
|
||||
input wire reset,
|
||||
input wire branch_stall,
|
||||
input wire freeze,
|
||||
VX_backend_req_if frE_to_bckE_req_if,
|
||||
VX_backend_req_if bckE_req_if
|
||||
);
|
||||
|
||||
wire stall = freeze;
|
||||
wire flush = (branch_stall != 0);
|
||||
|
||||
VX_generic_register #(
|
||||
.N(233 + `NW_BITS-1 + 1 + `NUM_THREADS)
|
||||
) d_e_reg (
|
||||
.clk (clk),
|
||||
.reset (reset),
|
||||
.stall (stall),
|
||||
.flush (flush),
|
||||
.in ({frE_to_bckE_req_if.csr_address, frE_to_bckE_req_if.is_jal, frE_to_bckE_req_if.is_etype, frE_to_bckE_req_if.is_csr, frE_to_bckE_req_if.csr_immed, frE_to_bckE_req_if.csr_mask, frE_to_bckE_req_if.rd, frE_to_bckE_req_if.rs1, frE_to_bckE_req_if.rs2, frE_to_bckE_req_if.alu_op, frE_to_bckE_req_if.wb, frE_to_bckE_req_if.rs2_src, frE_to_bckE_req_if.itype_immed, frE_to_bckE_req_if.mem_read, frE_to_bckE_req_if.mem_write, frE_to_bckE_req_if.branch_type, frE_to_bckE_req_if.upper_immed, frE_to_bckE_req_if.curr_PC, frE_to_bckE_req_if.jal, frE_to_bckE_req_if.jal_offset, frE_to_bckE_req_if.next_PC, frE_to_bckE_req_if.valid, frE_to_bckE_req_if.warp_num, frE_to_bckE_req_if.is_wspawn, frE_to_bckE_req_if.is_tmc, frE_to_bckE_req_if.is_split, frE_to_bckE_req_if.is_barrier}),
|
||||
.out ({bckE_req_if.csr_address , bckE_req_if.is_jal , bckE_req_if.is_etype ,bckE_req_if.is_csr , bckE_req_if.csr_immed , bckE_req_if.csr_mask , bckE_req_if.rd , bckE_req_if.rs1 , bckE_req_if.rs2 , bckE_req_if.alu_op , bckE_req_if.wb , bckE_req_if.rs2_src , bckE_req_if.itype_immed , bckE_req_if.mem_read , bckE_req_if.mem_write , bckE_req_if.branch_type , bckE_req_if.upper_immed , bckE_req_if.curr_PC , bckE_req_if.jal , bckE_req_if.jal_offset , bckE_req_if.next_PC , bckE_req_if.valid , bckE_req_if.warp_num , bckE_req_if.is_wspawn , bckE_req_if.is_tmc , bckE_req_if.is_split , bckE_req_if.is_barrier })
|
||||
);
|
||||
|
||||
endmodule
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -1,27 +0,0 @@
|
||||
`include "VX_define.vh"
|
||||
|
||||
module VX_f_d_reg (
|
||||
input wire clk,
|
||||
input wire reset,
|
||||
input wire freeze,
|
||||
|
||||
VX_inst_meta_if fe_inst_meta_fd,
|
||||
VX_inst_meta_if fd_inst_meta_de
|
||||
|
||||
);
|
||||
|
||||
wire flush = 1'b0;
|
||||
wire stall = freeze == 1'b1;
|
||||
|
||||
VX_generic_register #(
|
||||
.N(64+`NW_BITS-1+1+`NUM_THREADS)
|
||||
) f_d_reg (
|
||||
.clk (clk),
|
||||
.reset (reset),
|
||||
.stall (stall),
|
||||
.flush (flush),
|
||||
.in ({fe_inst_meta_fd.instruction, fe_inst_meta_fd.inst_pc, fe_inst_meta_fd.warp_num, fe_inst_meta_fd.valid}),
|
||||
.out ({fd_inst_meta_de.instruction, fd_inst_meta_de.inst_pc, fd_inst_meta_de.warp_num, fd_inst_meta_de.valid})
|
||||
);
|
||||
|
||||
endmodule
|
||||
@@ -1,27 +0,0 @@
|
||||
`include "VX_define.vh"
|
||||
|
||||
module VX_i_d_reg (
|
||||
input wire clk,
|
||||
input wire reset,
|
||||
input wire freeze,
|
||||
|
||||
VX_inst_meta_if fe_inst_meta_fd,
|
||||
VX_inst_meta_if fd_inst_meta_de
|
||||
|
||||
);
|
||||
|
||||
wire flush = 1'b0;
|
||||
wire stall = freeze == 1'b1;
|
||||
|
||||
VX_generic_register #(
|
||||
.N(64 + `NW_BITS-1 + 1 + `NUM_THREADS)
|
||||
) i_d_reg (
|
||||
.clk (clk),
|
||||
.reset (reset),
|
||||
.stall (stall),
|
||||
.flush (flush),
|
||||
.in ({fe_inst_meta_fd.instruction, fe_inst_meta_fd.inst_pc, fe_inst_meta_fd.warp_num, fe_inst_meta_fd.valid}),
|
||||
.out ({fd_inst_meta_de.instruction, fd_inst_meta_de.inst_pc, fd_inst_meta_de.warp_num, fd_inst_meta_de.valid})
|
||||
);
|
||||
|
||||
endmodule
|
||||
@@ -15,7 +15,7 @@ DBG_PRINT_FLAGS += -DDBG_PRINT_OPAE
|
||||
#DBG_FLAGS += $(DBG_PRINT_FLAGS)
|
||||
DBG_FLAGS += -DDBG_CORE_REQ_INFO
|
||||
|
||||
INCLUDE = -I../rtl/ -I../rtl/libs -I../rtl/interfaces -I../rtl/pipe_regs -I../rtl/cache -I../rtl/simulate
|
||||
INCLUDE = -I../rtl/ -I../rtl/libs -I../rtl/interfaces -I../rtl/cache -I../rtl/simulate
|
||||
|
||||
SRCS = simulator.cpp testbench.cpp
|
||||
|
||||
|
||||
5
hw/syn/quartus/.gitignore
vendored
5
hw/syn/quartus/.gitignore
vendored
@@ -8,4 +8,7 @@
|
||||
!/vortex/Makefile
|
||||
|
||||
/pipeline/*
|
||||
!/pipeline/Makefile
|
||||
!/pipeline/Makefile
|
||||
|
||||
/core/*
|
||||
!/core/Makefile
|
||||
|
||||
@@ -49,7 +49,7 @@ smart.log: $(PROJECT_FILES)
|
||||
|
||||
# Project initialization
|
||||
$(PROJECT_FILES):
|
||||
quartus_sh -t ../project.tcl -project $(PROJECT) -family $(FAMILY) -device $(DEVICE) -top $(TOP_LEVEL_ENTITY) -src $(SRC_FILE) -sdc ../project.sdc -inc "../../../rtl;../../../rtl/libs;../../../rtl/interfaces;../../../rtl/pipe_regs;../../../rtl/cache"
|
||||
quartus_sh -t ../project.tcl -project $(PROJECT) -family $(FAMILY) -device $(DEVICE) -top $(TOP_LEVEL_ENTITY) -src $(SRC_FILE) -sdc ../project.sdc -inc "../../../rtl;../../../rtl/libs;../../../rtl/interfaces;../../../rtl/cache"
|
||||
|
||||
syn.chg:
|
||||
$(STAMP) syn.chg
|
||||
|
||||
@@ -49,7 +49,7 @@ smart.log: $(PROJECT_FILES)
|
||||
|
||||
# Project initialization
|
||||
$(PROJECT_FILES):
|
||||
quartus_sh -t ../project.tcl -project $(PROJECT) -family $(FAMILY) -device $(DEVICE) -top $(TOP_LEVEL_ENTITY) -src $(SRC_FILE) -sdc ../project.sdc -inc "../../../rtl;../../../rtl/libs;../../../rtl/interfaces;../../../rtl/pipe_regs"
|
||||
quartus_sh -t ../project.tcl -project $(PROJECT) -family $(FAMILY) -device $(DEVICE) -top $(TOP_LEVEL_ENTITY) -src $(SRC_FILE) -sdc ../project.sdc -inc "../../../rtl;../../../rtl/libs;../../../rtl/interfaces"
|
||||
|
||||
syn.chg:
|
||||
$(STAMP) syn.chg
|
||||
|
||||
@@ -49,7 +49,7 @@ smart.log: $(PROJECT_FILES)
|
||||
|
||||
# Project initialization
|
||||
$(PROJECT_FILES):
|
||||
quartus_sh -t ../project.tcl -project $(PROJECT) -family $(FAMILY) -device $(DEVICE) -top $(TOP_LEVEL_ENTITY) -src $(SRC_FILE) -set "NOPAE" -sdc ../project.sdc -inc "../../../rtl;../../../rtl/libs;../../../rtl/interfaces;../../../rtl/pipe_regs;../../../rtl/cache;../../../opae;../../../opae/ccip"
|
||||
quartus_sh -t ../project.tcl -project $(PROJECT) -family $(FAMILY) -device $(DEVICE) -top $(TOP_LEVEL_ENTITY) -src $(SRC_FILE) -set "NOPAE" -sdc ../project.sdc -inc "../../../rtl;../../../rtl/libs;../../../rtl/interfaces;../../../rtl/cache;../../../opae;../../../opae/ccip"
|
||||
|
||||
syn.chg:
|
||||
$(STAMP) syn.chg
|
||||
|
||||
@@ -49,7 +49,7 @@ smart.log: $(PROJECT_FILES)
|
||||
|
||||
# Project initialization
|
||||
$(PROJECT_FILES):
|
||||
quartus_sh -t ../project.tcl -project $(PROJECT) -family $(FAMILY) -device $(DEVICE) -top $(TOP_LEVEL_ENTITY) -src $(SRC_FILE) -sdc ../project.sdc -inc "../../../rtl;../../../rtl/libs;../../../rtl/interfaces;../../../rtl/pipe_regs;../../../rtl/cache"
|
||||
quartus_sh -t ../project.tcl -project $(PROJECT) -family $(FAMILY) -device $(DEVICE) -top $(TOP_LEVEL_ENTITY) -src $(SRC_FILE) -sdc ../project.sdc -inc "../../../rtl;../../../rtl/libs;../../../rtl/interfaces;../../../rtl/cache"
|
||||
|
||||
syn.chg:
|
||||
$(STAMP) syn.chg
|
||||
|
||||
32
hw/syn/yosys/synth.sh
Executable file
32
hw/syn/yosys/synth.sh
Executable file
@@ -0,0 +1,32 @@
|
||||
#!/bin/bash
|
||||
|
||||
dir_list='../../rtl/libs ../../rtl/cache ../../rtl/interfaces ../../rtl'
|
||||
|
||||
inc_list=""
|
||||
for dir in $dir_list; do
|
||||
inc_list="$inc_list -I$dir"
|
||||
done
|
||||
|
||||
echo "inc_list=$inc_list"
|
||||
|
||||
{
|
||||
# read design sources
|
||||
for dir in $dir_list; do
|
||||
for file in $(find $dir -name '*.v' -o -name '*.sv' -type f)
|
||||
do
|
||||
echo "read_verilog -sv $inc_list $file"
|
||||
done
|
||||
done
|
||||
|
||||
echo "hierarchy -check -top Vortex"
|
||||
|
||||
# insertation of global reset
|
||||
echo "add -global_input reset 1"
|
||||
echo "proc -global_arst reset"
|
||||
|
||||
echo "synth -run coarse; opt -fine"
|
||||
echo "tee -o brams.log memory_bram -rules scripts/brams.txt;;"
|
||||
echo "write_verilog -noexpr -noattr synth.v"
|
||||
} > synth.ys
|
||||
|
||||
yosys -l synth.log synth.ys
|
||||
@@ -1,27 +0,0 @@
|
||||
# load design
|
||||
read_verilog -sv -I../../rtl -I../../rtl/libs -I../../rtl/interfaces -I../../rtl/pipe_regs -I../../rtl/cache ../../rtl/Vortex.v
|
||||
|
||||
# high-level synthesis
|
||||
proc; opt; fsm;; memory -nomap; opt
|
||||
|
||||
# substitute block rams
|
||||
techmap -map map_rams.v
|
||||
|
||||
# map remaining memories
|
||||
memory_map
|
||||
|
||||
# low-level synthesis
|
||||
techmap; opt; flatten;; abc -lut6
|
||||
techmap -map map_xl_cells.v
|
||||
|
||||
# add clock buffers
|
||||
select -set xl_clocks t:FDRE %x:+FDRE[C] t:FDRE %d
|
||||
iopadmap -inpad BUFGP O:I @xl_clocks
|
||||
|
||||
# add io buffers
|
||||
select -set xl_nonclocks w:* t:BUFGP %x:+BUFGP[I] %d
|
||||
iopadmap -outpad OBUF I:O -inpad IBUF O:I @xl_nonclocks
|
||||
|
||||
# write synthesis results
|
||||
write_edif synth.edif
|
||||
|
||||
Reference in New Issue
Block a user