OpenCores
URL https://opencores.org/ocsvn/s1_core/s1_core/trunk

Subversion Repositories s1_core

Compare Revisions

  • This comparison shows the changes necessary to convert path
    /
    from Rev 38 to Rev 39
    Reverse comparison

Rev 38 → Rev 39

/trunk/tools/src/bw_r_idct.v
0,0 → 1,32
// Empty module for cacheless Simply RISC S1 Core
 
module bw_r_idct(rdtag_w0_y, rdtag_w1_y, rdtag_w2_y, rdtag_w3_y, so, rclk, se,
si, reset_l, sehold, rst_tri_en, index0_x, index1_x, index_sel_x,
dec_wrway_x, rdreq_x, wrreq_x, wrtag_w0_y, wrtag_w1_y, wrtag_w2_y,
wrtag_w3_y, adj);
 
input rclk;
input se;
input si;
input reset_l;
input sehold;
input rst_tri_en;
input [6:0] index0_x;
input [6:0] index1_x;
input index_sel_x;
input [3:0] dec_wrway_x;
input rdreq_x;
input wrreq_x;
input [32:0] wrtag_w0_y;
input [32:0] wrtag_w1_y;
input [32:0] wrtag_w2_y;
input [32:0] wrtag_w3_y;
input [3:0] adj;
output [32:0] rdtag_w0_y;
output [32:0] rdtag_w1_y;
output [32:0] rdtag_w2_y;
output [32:0] rdtag_w3_y;
output so;
endmodule
 
/trunk/tools/src/bw_r_dcd.v
0,0 → 1,68
// Empty module for cacheless Simply RISC S1 Core
 
module bw_r_dcd (
// Outputs
so, dcache_rdata_wb, dcache_rparity_wb, dcache_rparity_err_wb,
dcache_rdata_msb_w0_m, dcache_rdata_msb_w1_m,
dcache_rdata_msb_w2_m, dcache_rdata_msb_w3_m,
dcd_fuse_repair_value, dcd_fuse_repair_en,
// Inputs
dcache_rd_addr_e, dcache_alt_addr_e, dcache_rvld_e, dcache_wvld_e,
dcache_wdata_e, dcache_wr_rway_e, dcache_byte_wr_en_e,
dcache_alt_rsel_way_e, dcache_rsel_way_wb, dcache_alt_mx_sel_e,
si, se, sehold, rst_tri_en, arst_l, rclk, dcache_alt_data_w0_m,
dcache_arry_data_sel_m, efc_spc_fuse_clk1, fuse_dcd_wren,
fuse_dcd_rid, fuse_dcd_repair_value, fuse_dcd_repair_en
) ;
 
input [10:3] dcache_rd_addr_e; // read cache index [10:4] + bit [3] offset
input [10:3] dcache_alt_addr_e; // write/bist/diagnostic read cache index + offset
 
input dcache_rvld_e; // read accesses d$.
input dcache_wvld_e; // valid write setup to m-stage.
input [143:0] dcache_wdata_e; // write data - 16Bx8 + 8b parity.
input [3:0] dcache_wr_rway_e; // replacement way for load miss/store.
input [15:0] dcache_byte_wr_en_e; // 16b byte wr enable for stores.
 
input [3:0] dcache_alt_rsel_way_e ; // bist/diagnostic read way select
input [3:0] dcache_rsel_way_wb; // load way select, connect to cache_way_hit
input dcache_alt_mx_sel_e;
input si;
input se;
input sehold;
output so;
 
input rst_tri_en ;
 
input arst_l; // used for redundancy flops - do not reset on wrm reset.
 
input rclk;
 
output [63:0] dcache_rdata_wb;
output [7:0] dcache_rparity_wb;
output dcache_rparity_err_wb;
 
input [63:0] dcache_alt_data_w0_m; //from qdp1
input dcache_arry_data_sel_m; //from dctl
output [7:0] dcache_rdata_msb_w0_m; //to dcdp
output [7:0] dcache_rdata_msb_w1_m; //to dcdp
output [7:0] dcache_rdata_msb_w2_m; //to dcdp
output [7:0] dcache_rdata_msb_w3_m; //to dcdp
 
input efc_spc_fuse_clk1;
input fuse_dcd_wren; //redundancy register write enable, qualified
input [2:0] fuse_dcd_rid; //redundancy register id
input [7:0] fuse_dcd_repair_value; //data in for redundancy register
input [1:0] fuse_dcd_repair_en; //enable bits to turn on redundancy
output [7:0] dcd_fuse_repair_value; //data out for redundancy register
output [1:0] dcd_fuse_repair_en; //enable bits out
endmodule
 
 
/trunk/tools/src/bw_r_icd.v
0,0 → 1,41
// Empty module for cacheless Simply RISC S1 Core
 
module bw_r_icd(icd_wsel_fetdata_s1, icd_wsel_topdata_s1, icd_fuse_repair_value,
icd_fuse_repair_en, so, rclk, se, si, reset_l, sehold, fdp_icd_index_bf,
ifq_icd_index_bf, fcl_icd_index_sel_ifq_bf, ifq_icd_wrway_bf,
ifq_icd_worden_bf, ifq_icd_wrdata_i2, fcl_icd_rdreq_bf,
fcl_icd_wrreq_bf, bist_ic_data, rst_tri_en, ifq_icd_data_sel_old_i2,
ifq_icd_data_sel_fill_i2, ifq_icd_data_sel_bist_i2, fuse_icd_wren,
fuse_icd_rid, fuse_icd_repair_value, fuse_icd_repair_en,
efc_spc_fuse_clk1);
 
input rclk;
input se;
input si;
input reset_l;
input sehold;
input [11:2] fdp_icd_index_bf;
input [11:2] ifq_icd_index_bf;
input fcl_icd_index_sel_ifq_bf;
input [1:0] ifq_icd_wrway_bf;
input [3:0] ifq_icd_worden_bf;
input [135:0] ifq_icd_wrdata_i2;
input fcl_icd_rdreq_bf;
input fcl_icd_wrreq_bf;
input [7:0] bist_ic_data;
input rst_tri_en;
input ifq_icd_data_sel_old_i2;
input ifq_icd_data_sel_fill_i2;
input ifq_icd_data_sel_bist_i2;
input fuse_icd_wren;
input [3:0] fuse_icd_rid;
input [7:0] fuse_icd_repair_value;
input [1:0] fuse_icd_repair_en;
input efc_spc_fuse_clk1;
output [135:0] icd_wsel_fetdata_s1;
output [135:0] icd_wsel_topdata_s1;
output [7:0] icd_fuse_repair_value;
output [1:0] icd_fuse_repair_en;
output so;
 
endmodule
/trunk/hdl/rtl/sparc_core/bw_r_idct.v
1,54 → 1,5
// ========== Copyright Header Begin ==========================================
//
// OpenSPARC T1 Processor File: bw_r_idct.v
// Copyright (c) 2006 Sun Microsystems, Inc. All Rights Reserved.
// DO NOT ALTER OR REMOVE COPYRIGHT NOTICES.
//
// The above named program is free software; you can redistribute it and/or
// modify it under the terms of the GNU General Public
// License version 2 as published by the Free Software Foundation.
//
// The above named program is distributed in the hope that it will be
// useful, but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
// General Public License for more details.
//
// You should have received a copy of the GNU General Public
// License along with this work; if not, write to the Free Software
// Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA.
//
// ========== Copyright Header End ============================================
////////////////////////////////////////////////////////////////////////
/*
// Module Name: bw_r_idct.v
// Description:
// Contains the RTL for the icache and dcache tag blocks.
// This is a 1RW 512 entry X 33b macro, with 132b rd and 132b wr,
// broken into 4 33b segments with its own write enable.
// Address and Control inputs are available the stage before
// array access, which is referred to as "_x". Write data is
// available in the same stage as the write to the ram, referred
// to as "_y". Read data is also read out and available in "_y".
//
// X | Y
// index | ram access
// index sel | write_tag
// rd/wr req | -> read_tag
// way enable |
*/
// Empty module for cacheless Simply RISC S1 Core
 
 
////////////////////////////////////////////////////////////////////////
// Local header file includes / local defines
////////////////////////////////////////////////////////////////////////
 
//FPGA_SYN enables all FPGA related modifications
`ifdef FPGA_SYN
`define FPGA_SYN_IDCT
`endif
 
`ifdef FPGA_SYN_IDCT
 
module bw_r_idct(rdtag_w0_y, rdtag_w1_y, rdtag_w2_y, rdtag_w3_y, so, rclk, se,
si, reset_l, sehold, rst_tri_en, index0_x, index1_x, index_sel_x,
dec_wrway_x, rdreq_x, wrreq_x, wrtag_w0_y, wrtag_w1_y, wrtag_w2_y,
76,322 → 27,6
output [32:0] rdtag_w2_y;
output [32:0] rdtag_w3_y;
output so;
 
wire clk;
reg [6:0] index_y;
reg rdreq_y;
reg wrreq_y;
reg [3:0] dec_wrway_y;
wire [6:0] index_x;
wire [3:0] we;
 
reg [131:0] rdtag_sa_y; //for error_inject XMR
 
assign clk = rclk;
assign index_x = (index_sel_x ? index1_x : index0_x);
assign we = ({4 {((wrreq_y & reset_l) & (~rst_tri_en))}} & dec_wrway_y);
 
always @(posedge clk) begin
if (~sehold) begin
rdreq_y <= rdreq_x;
wrreq_y <= wrreq_x;
index_y <= index_x;
dec_wrway_y <= dec_wrway_x;
end
end
 
bw_r_idct_array ictag_ary_00(
.we (we[0]),
.clk (clk),
.rd_data(rdtag_w0_y),
.wr_data(wrtag_w0_y),
.addr (index_y));
 
bw_r_idct_array ictag_ary_01(
.we (we[1]),
.clk (clk),
.rd_data(rdtag_w1_y),
.wr_data(wrtag_w1_y),
.addr (index_y));
 
bw_r_idct_array ictag_ary_10(
.we (we[2]),
.clk (clk),
.rd_data(rdtag_w2_y),
.wr_data(wrtag_w2_y),
.addr (index_y));
 
bw_r_idct_array ictag_ary_11(
.we (we[3]),
.clk (clk),
.rd_data(rdtag_w3_y),
.wr_data(wrtag_w3_y),
.addr (index_y));
 
endmodule
 
module bw_r_idct_array(we, clk, rd_data, wr_data, addr);
 
input we;
input clk;
input [32:0] wr_data;
input [6:0] addr;
output [32:0] rd_data;
reg [32:0] rd_data;
 
reg [32:0] array[127:0] /* synthesis syn_ramstyle = block_ram syn_ramstyle = no_rw_check */ ;
 
 
always @(negedge clk) begin
if (we) array[addr] <= wr_data;
else rd_data <= array[addr];
end
endmodule
 
`else
 
module bw_r_idct(/*AUTOARG*/
// Outputs
rdtag_w0_y, rdtag_w1_y, rdtag_w2_y, rdtag_w3_y, so,
// Inputs
rclk, se, si, reset_l, sehold, rst_tri_en, index0_x, index1_x,
index_sel_x, dec_wrway_x, rdreq_x, wrreq_x, wrtag_w0_y,
wrtag_w1_y, wrtag_w2_y, wrtag_w3_y, adj
);
 
input rclk,
se,
si,
reset_l; // active LOW reset
 
input sehold;
input rst_tri_en;
input [6:0] index0_x; // read/write address0
input [6:0] index1_x; // read/write address1
 
input index_sel_x; // selects between index1 and index0
 
input [3:0] dec_wrway_x; // way -- functions as a write enable
// per 33b
input rdreq_x, // read enable
wrreq_x; // write enable
 
// Don't use rdreq and wrreq to gate off the clock, since these are
// critical. A separate power down signal can be supplied if
// needed.
input [32:0] wrtag_w0_y; // write data, not flopped
input [32:0] wrtag_w1_y; //
input [32:0] wrtag_w2_y; //
input [32:0] wrtag_w3_y; //
 
input [3:0] adj;
 
output [32:0] rdtag_w0_y; // read data split into 4 ports
output [32:0] rdtag_w1_y; // not flopped
output [32:0] rdtag_w2_y; //
output [32:0] rdtag_w3_y; //
 
output so;
 
 
// Declarations
// local signals
`ifdef DEFINE_0IN
`else
reg [32:0] ictag_ary [511:0];
reg [131:0] rdtag_bl_y,
rdtag_sa_y;
`endif
 
wire clk;
 
reg [6:0] index_y;
reg rdreq_y,
wrreq_y;
reg [3:0] dec_wrway_y;
 
wire [6:0] index_x;
 
//----------------
// Code start here
//----------------
 
assign clk = rclk;
//-------------------------
// 2:1 mux on address input
//-------------------------
// address inputs are critical and this mux needs to be merged with
// the receiving flop.
assign index_x = index_sel_x ? index1_x :
index0_x;
 
//------------------------
// input flops from x to y
//------------------------
// these need to be scannable
always @ (posedge clk)
begin
if (~sehold)
begin
rdreq_y <= rdreq_x;
wrreq_y <= wrreq_x;
index_y <= index_x;
dec_wrway_y <= dec_wrway_x;
end
end
`ifdef DEFINE_0IN
wire [131:0] wm = { {33{(dec_wrway_y[3])}},{33{(dec_wrway_y[2])}},{33{(dec_wrway_y[1])}},{33{(dec_wrway_y[0])}} };
wire we = wrreq_y & ~se;
 
l1_tag l1_tag ( .nclk(~clk), .adr(index_y[6:0]), .we(we), .wm(wm),
.din ({wrtag_w3_y,wrtag_w2_y,wrtag_w1_y,wrtag_w0_y}),
.dout({rdtag_w3_y,rdtag_w2_y,rdtag_w1_y,rdtag_w0_y}) );
`else
 
//----------------------------------------------------------------------
// Read Operation
//----------------------------------------------------------------------
 
always @(/*AUTOSENSE*/ /*memory or*/ index_y or rdreq_y or reset_l
or wrreq_y)
begin
if (rdreq_y & reset_l)
begin
if (wrreq_y) // rd_wr conflict
begin
rdtag_bl_y = {132{1'bx}};
end
else // no write, read only
begin
rdtag_bl_y[32:0] = ictag_ary[{index_y,2'b00}]; // way0
rdtag_bl_y[65:33] = ictag_ary[{index_y,2'b01}]; // way1
rdtag_bl_y[98:66] = ictag_ary[{index_y,2'b10}]; // way2
rdtag_bl_y[131:99] = ictag_ary[{index_y,2'b11}];// way3
end
end
else // no read
begin
rdtag_bl_y = {132{1'bx}};
end
end // always @ (...
 
// SA latch -- to make 0in happy
always @ (/*AUTOSENSE*/clk or rdreq_y or rdtag_bl_y or reset_l)
begin
if (rdreq_y & ~clk & reset_l)
begin
rdtag_sa_y <= rdtag_bl_y;
end
end
 
// Output is held the same if there is no read. This is not a
// hard requirement, please let me know if the output has to
// be something else for ease of implementation.
 
// Output behavior during reset is currently not coded.
// Functionally there is no preference, though it should be
// unchanging to keep the power low.
 
// Final Output
assign rdtag_w0_y = rdtag_sa_y[32:0];
assign rdtag_w1_y = rdtag_sa_y[65:33];
assign rdtag_w2_y = rdtag_sa_y[98:66];
assign rdtag_w3_y = rdtag_sa_y[131:99];
 
//----------------------------------------------------------------------
// Write Operation
//----------------------------------------------------------------------
// Writes should be blocked off during scan shift.
always @ (negedge clk)
begin
if (wrreq_y & reset_l & ~rst_tri_en)
begin
if (dec_wrway_y[0])
ictag_ary[{index_y, 2'b00}] = wrtag_w0_y;
if (dec_wrway_y[1])
ictag_ary[{index_y, 2'b01}] = wrtag_w1_y;
if (dec_wrway_y[2])
ictag_ary[{index_y, 2'b10}] = wrtag_w2_y;
if (dec_wrway_y[3])
ictag_ary[{index_y, 2'b11}] = wrtag_w3_y;
end
end
 
// TBD: Need to model rd-wr contention
`endif
 
//******************************************************
// The stuff below is not part of the main functionality
// and has no representation in the actual circuit.
//******************************************************
 
// synopsys translate_off
//-----------------------
// Contention Monitor
//-----------------------
`ifdef INNO_MUXEX
`else
always @ (negedge clk)
begin
if (rdreq_y & wrreq_y & reset_l)
begin
// 0in <fire -message "FATAL ERROR: rd and wr contention in idct"
//$display("IDtag Contention", "ERROR rd and wr contention in idct");
end
end // always @ (negedge clk)
 
`endif
 
//--------------------------------
// // For dump_cache.v
// //--------------------------------
// //fake to make dump_cache.v happy
// reg [29:0] w0 [127:0];
// reg [29:0] w1 [127:0];
// reg [29:0] w2 [127:0];
// reg [29:0] w3 [127:0];
//
// always @ (negedge clk)
// begin
// if (wrreq_y & ~se)
// begin
// if (rdreq_y) begin // rd/wr contention
// case (dec_wrway_y)
// 4'b0001 : w0[index_y[6:0]] ={30{1'bx}};
// 4'b0010 : w1[index_y[6:0]] ={30{1'bx}};
// 4'b0100 : w2[index_y[6:0]] ={30{1'bx}};
// 4'b1000 : w3[index_y[6:0]] ={30{1'bx}};
// endcase // case(wrway_y)
// end
// else begin
// case (dec_wrway_y)
// 4'b0001 : w0[index_y[6:0]] = wrtag_w0_y[29:0];
// 4'b0010 : w1[index_y[6:0]] = wrtag_w1_y[29:0];
// 4'b0100 : w2[index_y[6:0]] = wrtag_w2_y[29:0];
// 4'b1000 : w3[index_y[6:0]] = wrtag_w3_y[29:0];
// endcase // case(wrway_y)
// end
// end
// end
 
// synopsys translate_on
endmodule // bw_r_idct
 
`endif
 
 
/trunk/hdl/rtl/sparc_core/bw_r_icd.v
1,63 → 1,5
// ========== Copyright Header Begin ==========================================
//
// OpenSPARC T1 Processor File: bw_r_icd.v
// Copyright (c) 2006 Sun Microsystems, Inc. All Rights Reserved.
// DO NOT ALTER OR REMOVE COPYRIGHT NOTICES.
//
// The above named program is free software; you can redistribute it and/or
// modify it under the terms of the GNU General Public
// License version 2 as published by the Free Software Foundation.
//
// The above named program is distributed in the hope that it will be
// useful, but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
// General Public License for more details.
//
// You should have received a copy of the GNU General Public
// License along with this work; if not, write to the Free Software
// Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA.
//
// ========== Copyright Header End ============================================
////////////////////////////////////////////////////////////////////////
/*
// Module Name: bw_r_icd
// Description:
// The ICD contains the icache data.
// 32B line size.
// Write BW: 16B
// Read BW: 16Bx2 (fetdata and topdata), collapsed to 4Bx2
// Associativity: 4
// Write boundary: 34b (32b inst + parity + predec bit)
// NOTES:
// 1. No clock enable. Rd/Wr enable is used to trigger the
// operation.
// 2. 2:1 mux on address input. Selects provided externally.
// 3. 3:1 mux on data input. Selects provided and guaranteed
// exclusive, externally.
//
*/
// Empty module for cacheless Simply RISC S1 Core
 
 
////////////////////////////////////////////////////////////////////////
// Global header file includes
////////////////////////////////////////////////////////////////////////
//`include "sys.h" // system level definition file which contains the
// time scale definition
 
 
////////////////////////////////////////////////////////////////////////
// Local header file includes / local defines
////////////////////////////////////////////////////////////////////////
 
`include "ifu.h"
 
//FPGA_SYN enables all FPGA related modifications
`ifdef FPGA_SYN
`define FPGA_SYN_ICD
`endif
 
`ifdef FPGA_SYN_ICD
 
module bw_r_icd(icd_wsel_fetdata_s1, icd_wsel_topdata_s1, icd_fuse_repair_value,
icd_fuse_repair_en, so, rclk, se, si, reset_l, sehold, fdp_icd_index_bf,
ifq_icd_index_bf, fcl_icd_index_sel_ifq_bf, ifq_icd_wrway_bf,
96,785 → 38,4
output [1:0] icd_fuse_repair_en;
output so;
 
reg [7:0] icd_fuse_repair_value;
reg [1:0] icd_fuse_repair_en;
reg [135:0] fetdata_f;
reg [135:0] topdata_f;
reg [135:0] fetdata_sa;
reg [135:0] topdata_sa;
reg [135:0] fetdata_s1;
reg [135:0] topdata_s1;
wire clk;
wire [135:0] next_wrdata_bf;
wire [135:0] wrdata_f;
wire [135:0] bist_data_expand;
wire [11:2] index_bf;
reg [11:2] index_f;
reg [11:0] wr_index0;
reg [11:0] wr_index1;
reg [11:0] wr_index2;
reg [11:0] wr_index3;
reg rdreq_f;
reg wrreq_f;
reg [3:0] worden_f;
reg [1:0] wrway_f;
 
reg [33:0] icdata_ary_00_00 [255:0] /* synthesis syn_ramstyle = block_ram syn_ramstyle = no_rw_check */ ;
reg [33:0] icdata_ary_00_01 [255:0] /* synthesis syn_ramstyle = block_ram syn_ramstyle = no_rw_check */ ;
reg [33:0] icdata_ary_00_10 [255:0] /* synthesis syn_ramstyle = block_ram syn_ramstyle = no_rw_check */ ;
reg [33:0] icdata_ary_00_11 [255:0] /* synthesis syn_ramstyle = block_ram syn_ramstyle = no_rw_check */ ;
reg [33:0] icdata_ary_01_00 [255:0] /* synthesis syn_ramstyle = block_ram syn_ramstyle = no_rw_check */ ;
reg [33:0] icdata_ary_01_01 [255:0] /* synthesis syn_ramstyle = block_ram syn_ramstyle = no_rw_check */ ;
reg [33:0] icdata_ary_01_10 [255:0] /* synthesis syn_ramstyle = block_ram syn_ramstyle = no_rw_check */ ;
reg [33:0] icdata_ary_01_11 [255:0] /* synthesis syn_ramstyle = block_ram syn_ramstyle = no_rw_check */ ;
reg [33:0] icdata_ary_10_00 [255:0] /* synthesis syn_ramstyle = block_ram syn_ramstyle = no_rw_check */ ;
reg [33:0] icdata_ary_10_01 [255:0] /* synthesis syn_ramstyle = block_ram syn_ramstyle = no_rw_check */ ;
reg [33:0] icdata_ary_10_10 [255:0] /* synthesis syn_ramstyle = block_ram syn_ramstyle = no_rw_check */ ;
reg [33:0] icdata_ary_10_11 [255:0] /* synthesis syn_ramstyle = block_ram syn_ramstyle = no_rw_check */ ;
reg [33:0] icdata_ary_11_00 [255:0] /* synthesis syn_ramstyle = block_ram syn_ramstyle = no_rw_check */ ;
reg [33:0] icdata_ary_11_01 [255:0] /* synthesis syn_ramstyle = block_ram syn_ramstyle = no_rw_check */ ;
reg [33:0] icdata_ary_11_10 [255:0] /* synthesis syn_ramstyle = block_ram syn_ramstyle = no_rw_check */ ;
reg [33:0] icdata_ary_11_11 [255:0] /* synthesis syn_ramstyle = block_ram syn_ramstyle = no_rw_check */ ;
 
 
 
assign clk = rclk;
assign index_bf = (fcl_icd_index_sel_ifq_bf ? ifq_icd_index_bf :
fdp_icd_index_bf);
wire [11:2] top_index = {index_f[11:3] , 1'b1};
 
assign bist_data_expand = {bist_ic_data[1:0], {4 {bist_ic_data[7:0]}},
bist_ic_data[1:0], {4 {bist_ic_data[7:0]}}, bist_ic_data[1:0],
{4 {bist_ic_data[7:0]}}, bist_ic_data[1:0], {4
{bist_ic_data[7:0]}}};
assign icd_wsel_fetdata_s1 = fetdata_s1;
assign icd_wsel_topdata_s1 = topdata_s1;
 
mux3ds #(136) icden_mux(
.dout (next_wrdata_bf),
.in0 (wrdata_f),
.in1 (ifq_icd_wrdata_i2),
.in2 (bist_data_expand),
.sel0 (ifq_icd_data_sel_old_i2),
.sel1 (ifq_icd_data_sel_fill_i2),
.sel2 (ifq_icd_data_sel_bist_i2));
dffe #(136) wrdata_reg(
.din (next_wrdata_bf),
.clk (clk),
.q (wrdata_f),
.en ((~sehold)),
.se (se));
 
always @(posedge clk) begin
if (~sehold) begin
rdreq_f <= fcl_icd_rdreq_bf;
wrreq_f <= fcl_icd_wrreq_bf;
index_f <= index_bf;
wrway_f <= ifq_icd_wrway_bf;
worden_f <= ifq_icd_worden_bf;
wr_index0 <= {index_bf[11:4], 2'b0, ifq_icd_wrway_bf};
wr_index1 <= {index_bf[11:4], 2'b1, ifq_icd_wrway_bf};
wr_index2 <= {index_bf[11:4], 2'b10, ifq_icd_wrway_bf};
wr_index3 <= {index_bf[11:4], 2'b11, ifq_icd_wrway_bf};
end
fetdata_s1 <= fetdata_f;
topdata_s1 <= topdata_f;
end
 
reg [33:0] fetch_00_00;
reg [33:0] fetch_00_01;
reg [33:0] fetch_00_10;
reg [33:0] fetch_00_11;
 
reg [33:0] fetch_01_00;
reg [33:0] fetch_01_01;
reg [33:0] fetch_01_10;
reg [33:0] fetch_01_11;
 
reg [33:0] fetch_10_00;
reg [33:0] fetch_10_01;
reg [33:0] fetch_10_10;
reg [33:0] fetch_10_11;
 
reg [33:0] fetch_11_00;
reg [33:0] fetch_11_01;
reg [33:0] fetch_11_10;
reg [33:0] fetch_11_11;
 
always @(posedge clk) begin
fetch_00_00 <= icdata_ary_00_00[index_bf[11:4]];
fetch_00_01 <= icdata_ary_00_01[index_bf[11:4]];
fetch_00_10 <= icdata_ary_00_10[index_bf[11:4]];
fetch_00_11 <= icdata_ary_00_11[index_bf[11:4]];
fetch_01_00 <= icdata_ary_01_00[index_bf[11:4]];
fetch_01_01 <= icdata_ary_01_01[index_bf[11:4]];
fetch_01_10 <= icdata_ary_01_10[index_bf[11:4]];
fetch_01_11 <= icdata_ary_01_11[index_bf[11:4]];
fetch_10_00 <= icdata_ary_10_00[index_bf[11:4]];
fetch_10_01 <= icdata_ary_10_01[index_bf[11:4]];
fetch_10_10 <= icdata_ary_10_10[index_bf[11:4]];
fetch_10_11 <= icdata_ary_10_11[index_bf[11:4]];
fetch_11_00 <= icdata_ary_11_00[index_bf[11:4]];
fetch_11_01 <= icdata_ary_11_01[index_bf[11:4]];
fetch_11_10 <= icdata_ary_11_10[index_bf[11:4]];
fetch_11_11 <= icdata_ary_11_11[index_bf[11:4]];
end
 
 
always @(index_f or rdreq_f or fetch_00_00 or fetch_01_00 or fetch_10_00 or fetch_11_00
or fetch_00_01 or fetch_01_01 or fetch_10_01 or fetch_11_01
or fetch_00_10 or fetch_01_10 or fetch_10_10 or fetch_11_10
or fetch_00_11 or fetch_01_11 or fetch_10_11 or fetch_11_11) begin
if (rdreq_f) begin
case(index_f[3:2])
2'b00: fetdata_f[33:0] = fetch_00_00;
2'b01: fetdata_f[33:0] = fetch_01_00;
2'b10: fetdata_f[33:0] = fetch_10_00;
2'b11: fetdata_f[33:0] = fetch_11_00;
endcase
case(index_f[3:2])
2'b00: fetdata_f[67:34] = fetch_00_01;
2'b01: fetdata_f[67:34] = fetch_01_01;
2'b10: fetdata_f[67:34] = fetch_10_01;
2'b11: fetdata_f[67:34] = fetch_11_01;
endcase
case(index_f[3:2])
2'b00: fetdata_f[101:68] = fetch_00_10;
2'b01: fetdata_f[101:68] = fetch_01_10;
2'b10: fetdata_f[101:68] = fetch_10_10;
2'b11: fetdata_f[101:68] = fetch_11_10;
endcase
case(index_f[3:2])
2'b00: fetdata_f[135:102] = fetch_00_11;
2'b01: fetdata_f[135:102] = fetch_01_11;
2'b10: fetdata_f[135:102] = fetch_10_11;
2'b11: fetdata_f[135:102] = fetch_11_11;
endcase
case(index_f[3])
1'b0: topdata_f[33:0] = fetch_01_00;
1'b1: topdata_f[33:0] = fetch_11_00;
endcase
case(index_f[3])
1'b0: topdata_f[67:34] = fetch_01_01;
1'b1: topdata_f[67:34] = fetch_11_01;
endcase
case(index_f[3])
1'b0: topdata_f[101:68] = fetch_01_10;
1'b1: topdata_f[101:68] = fetch_11_10;
endcase
case(index_f[3])
1'b0: topdata_f[135:102] = fetch_01_11;
1'b1: topdata_f[135:102] = fetch_11_11;
endcase
end
else
begin
fetdata_f = 136'b0;
topdata_f = 136'b0;
end
end
 
always @(negedge clk) begin
if (wrreq_f & (~rst_tri_en)) begin
if (worden_f[0]) begin
if (wr_index0[1:0] == 2'b0) begin
icdata_ary_00_00[wr_index0[11:4]] <= wrdata_f[135:102];
end
if (wr_index0[1:0] == 2'b1) begin
icdata_ary_00_01[wr_index0[11:4]] <= wrdata_f[135:102];
end
if (wr_index0[1:0] == 2'b10) begin
icdata_ary_00_10[wr_index0[11:4]] <= wrdata_f[135:102];
end
if (wr_index0[1:0] == 2'b11) begin
icdata_ary_00_11[wr_index0[11:4]] <= wrdata_f[135:102];
end
end
if (worden_f[1]) begin
if (wr_index1[1:0] == 2'b0) begin
icdata_ary_01_00[wr_index1[11:4]] <= wrdata_f[101:68];
end
if (wr_index1[1:0] == 2'b1) begin
icdata_ary_01_01[wr_index1[11:4]] <= wrdata_f[101:68];
end
if (wr_index1[1:0] == 2'b10) begin
icdata_ary_01_10[wr_index1[11:4]] <= wrdata_f[101:68];
end
if (wr_index1[1:0] == 2'b11) begin
icdata_ary_01_11[wr_index1[11:4]] <= wrdata_f[101:68];
end
end
if (worden_f[2]) begin
if (wr_index2[1:0] == 2'b0) begin
icdata_ary_10_00[wr_index2[11:4]] <= wrdata_f[67:34];
end
if (wr_index2[1:0] == 2'b1) begin
icdata_ary_10_01[wr_index2[11:4]] <= wrdata_f[67:34];
end
if (wr_index2[1:0] == 2'b10) begin
icdata_ary_10_10[wr_index2[11:4]] <= wrdata_f[67:34];
end
if (wr_index2[1:0] == 2'b11) begin
icdata_ary_10_11[wr_index2[11:4]] <= wrdata_f[67:34];
end
end
if (worden_f[3]) begin
if (wr_index3[1:0] == 2'b0) begin
icdata_ary_11_00[wr_index3[11:4]] <= wrdata_f[33:0];
end
if (wr_index3[1:0] == 2'b1) begin
icdata_ary_11_01[wr_index3[11:4]] <= wrdata_f[33:0];
end
if (wr_index3[1:0] == 2'b10) begin
icdata_ary_11_10[wr_index3[11:4]] <= wrdata_f[33:0];
end
if (wr_index3[1:0] == 2'b11) begin
icdata_ary_11_11[wr_index3[11:4]] <= wrdata_f[33:0];
end
end
end
end
endmodule
 
`else
 
module bw_r_icd(/*AUTOARG*/
// Outputs
icd_wsel_fetdata_s1, icd_wsel_topdata_s1, icd_fuse_repair_value,
icd_fuse_repair_en, so,
// Inputs
rclk, se, si, reset_l, sehold, fdp_icd_index_bf, ifq_icd_index_bf,
fcl_icd_index_sel_ifq_bf, ifq_icd_wrway_bf, ifq_icd_worden_bf,
ifq_icd_wrdata_i2, fcl_icd_rdreq_bf, fcl_icd_wrreq_bf,
bist_ic_data, rst_tri_en, ifq_icd_data_sel_old_i2,
ifq_icd_data_sel_fill_i2, ifq_icd_data_sel_bist_i2, fuse_icd_wren,
fuse_icd_rid, fuse_icd_repair_value, fuse_icd_repair_en,
efc_spc_fuse_clk1
);
 
input rclk,
se,
si,
reset_l;
input sehold;
input [11:2] fdp_icd_index_bf, // index to write to/read from
ifq_icd_index_bf;
input fcl_icd_index_sel_ifq_bf;
 
input [1:0] ifq_icd_wrway_bf; // way to write to
input [3:0] ifq_icd_worden_bf; // word to write to (ignore index 1:0)
input [135:0] ifq_icd_wrdata_i2; // 128b data, 4b sw, 4b parity
 
input fcl_icd_rdreq_bf,
fcl_icd_wrreq_bf;
 
input [7:0] bist_ic_data; // needs to be expanded
input rst_tri_en;
// datain mux selects
input ifq_icd_data_sel_old_i2,
ifq_icd_data_sel_fill_i2,
ifq_icd_data_sel_bist_i2;
 
// efuse values for redundancy
input fuse_icd_wren;
input [3:0] fuse_icd_rid;
input [7:0] fuse_icd_repair_value;
input [1:0] fuse_icd_repair_en;
 
// efuse non ovl clks
input efc_spc_fuse_clk1; // use this clk to talk to fuse hdr
// outputs
output [135:0] icd_wsel_fetdata_s1,
icd_wsel_topdata_s1;
 
// redundancy reg read
output [7:0] icd_fuse_repair_value;
output [1:0] icd_fuse_repair_en;
output so;
 
//----------------------------------------------------------------------
// Declarations
//----------------------------------------------------------------------
 
// local signals
`ifdef DEFINE_0IN
reg [135:0] fetdata_s1,
topdata_s1;
wire [135:0] fetdata_sa,
topdata_sa;
`else
reg [33:0] icdata_ary [4095:0];
 
reg [135:0] fetdata_f, // way0 is lsb, way3 is msb
topdata_f,
fetdata_sa,
topdata_sa,
fetdata_s1,
topdata_s1;
`endif
 
wire clk;
wire [135:0] next_wrdata_bf,
wrdata_f,
bist_data_expand;
 
wire [11:2] top_index,
index_bf;
reg [11:2] index_f;
 
wire [11:0] wr_index0,
wr_index1,
wr_index2,
wr_index3;
reg rdreq_f,
wrreq_f;
reg [3:0] worden_f;
reg [1:0] wrway_f;
 
 
// redundancy crap
reg [7:0] red0_ev_row,
red0_od_row;
reg [9:0] red0_ev_col,
red0_od_col;
reg [7:0] red1_ev_row,
red1_od_row;
reg [9:0] red1_ev_col,
red1_od_col;
reg [7:0] red2_ev_row,
red2_od_row;
reg [9:0] red2_ev_col,
red2_od_col;
reg [7:0] red3_ev_row,
red3_od_row;
reg [9:0] red3_ev_col,
red3_od_col;
 
reg [7:0] icd_fuse_repair_value;
reg [1:0] icd_fuse_repair_en;
//
// Code start here
//
 
// clk header derives clk from rclk
assign clk = rclk;
 
 
// mux merged with flop
assign index_bf = fcl_icd_index_sel_ifq_bf ? ifq_icd_index_bf :
fdp_icd_index_bf;
 
always @ (posedge clk)
begin
// input flops
if (~sehold)
begin
rdreq_f <= fcl_icd_rdreq_bf;
wrreq_f <= fcl_icd_wrreq_bf;
index_f <= index_bf;
wrway_f <= ifq_icd_wrway_bf;
worden_f <= ifq_icd_worden_bf;
end
// S stage flops (for rd data)
fetdata_s1 <= fetdata_sa;
topdata_s1 <= topdata_sa;
end // always @ (posedge clk)
 
// BIST data
assign bist_data_expand = {bist_ic_data[1:0], {4{bist_ic_data[7:0]}},
bist_ic_data[1:0], {4{bist_ic_data[7:0]}},
bist_ic_data[1:0], {4{bist_ic_data[7:0]}},
bist_ic_data[1:0], {4{bist_ic_data[7:0]}}};
 
// Mux + flop for write data input
// ic data enable mux
mux3ds #(136) icden_mux(.dout (next_wrdata_bf),
.in0 (wrdata_f),
.in1 (ifq_icd_wrdata_i2),
.in2 (bist_data_expand),
.sel0 (ifq_icd_data_sel_old_i2),
.sel1 (ifq_icd_data_sel_fill_i2),
.sel2 (ifq_icd_data_sel_bist_i2));
// write data regsiter
// se hold is taken care of by external logic (in ifqctl)
dffe #(136) wrdata_reg(.din (next_wrdata_bf),
.clk (clk),
.q (wrdata_f),
.en (~sehold),
.se (se), .si(), .so());
 
//----------------------------------------------------------------------
// Read Operation
//----------------------------------------------------------------------
 
// The index has 2 parts.
// 1. The 16B half-line index -- bits 11:4
// 2. The word offset -- bits 3:2 for reads, xx for writes
// 3. The way -- wrway_f for writes, xx for reads
// i.e. we read 1 word from each of 4 ways, but
// we write 4 words to 1 way
assign top_index = {index_f[11:3] , 1'b1};
 
`ifdef DEFINE_0IN
// physical implmentation: ignore this and use else portion
wire [15:0] we_wrd = ({ 3'b0,worden_f[3], 3'b0,worden_f[2],
3'b0,worden_f[1], 3'b0,worden_f[0] }) << wrway_f;
 
wire [543:0] we = (~wrreq_f ) ? 544'h0 :
{ {34{we_wrd[15]}}, {34{we_wrd[14]}}, {34{we_wrd[13]}}, {34{we_wrd[12]}},
{34{we_wrd[11]}}, {34{we_wrd[10]}}, {34{we_wrd[ 9]}}, {34{we_wrd[ 8]}},
{34{we_wrd[ 7]}}, {34{we_wrd[ 6]}}, {34{we_wrd[ 5]}}, {34{we_wrd[ 4]}},
{34{we_wrd[ 3]}}, {34{we_wrd[ 2]}}, {34{we_wrd[ 1]}}, {34{we_wrd[ 0]}} };
 
wire [543:0] din = ({ {4{wrdata_f[ 33: 0]}}, {4{wrdata_f[ 67: 34]}},
{4{wrdata_f[101:68]}}, {4{wrdata_f[135:102]}} });
wire [543:0] dout;
 
ic_data ic_data ( .nclk(~clk), .adr(index_f[11:4]), .we(we), .din(din), .dout(dout) );
 
wire [271:0] dout_l1 = index_f[3] ? dout[543:272] : dout[271:0];
 
assign fetdata_sa[135:0] = index_f[2] ? dout_l1[271:136] : dout_l1[135:0];
assign topdata_sa[135:0] = dout_l1[271:136];
 
 
`else
 
// for physical implementation use this
// read (inst[31:0] + sw bit + par bit) * 4 ways
always @(/*AUTOSENSE*/ /*memory or*/ index_f or rdreq_f
or top_index or wrreq_f)
begin
if (rdreq_f)
begin
if (wrreq_f) // rd-wr contention
begin
fetdata_f = 136'bx;
topdata_f = 136'bx;
end
else
begin // regular read
fetdata_f[33:0] = icdata_ary[{index_f,2'b00}]; // way 0
fetdata_f[67:34] = icdata_ary[{index_f,2'b01}]; // way 1
fetdata_f[101:68] = icdata_ary[{index_f,2'b10}]; // way 2
fetdata_f[135:102] = icdata_ary[{index_f,2'b11}]; // way 3
 
topdata_f[33:0] = icdata_ary[{top_index, 2'b00}];
topdata_f[67:34] = icdata_ary[{top_index, 2'b01}];
topdata_f[101:68] = icdata_ary[{top_index, 2'b10}];
topdata_f[135:102] = icdata_ary[{top_index, 2'b11}];
end // else: !if(wrreq_f)
end // if (rdreq_f)
 
else // icache disabled or rd disabled
begin
// JC modified begin
// fetdata_f = 136'bx;
// topdata_f = 136'bx;
fetdata_f = 136'b0;
topdata_f = 136'b0;
// JC modified end
end // else: !if(rdreq_f)
end // always @ (...
 
 
// SA latch -- to make 0in happy
always @ (clk or fetdata_f or topdata_f)
begin
if (~clk)
begin
fetdata_sa <= fetdata_f;
topdata_sa <= topdata_f;
end
end
`endif // !`ifdef DEFINE_0IN
 
// final outputs (272bits)
assign icd_wsel_fetdata_s1 = fetdata_s1;
assign icd_wsel_topdata_s1 = topdata_s1;
//----------------------------------------------------------------------
// Write Operation
//----------------------------------------------------------------------
// The index has 3 parts.
// 1. The 16B half-line index -- bits 11:4 of index_f
// 2. The word offset -- bits 3:2 for reads, xx for writes
// 3. The way -- wrway_f for writes, xx for reads
 
// index word way
// ----- ---- ---
assign wr_index0 = {index_f[11:4], 2'b00, wrway_f};
assign wr_index1 = {index_f[11:4], 2'b01, wrway_f};
assign wr_index2 = {index_f[11:4], 2'b10, wrway_f};
assign wr_index3 = {index_f[11:4], 2'b11, wrway_f};
 
`ifdef DEFINE_0IN
`else
// assume write happens @ negedge clk (i.e. phase 1)
always @ (negedge clk)
begin
if (wrreq_f & ~rst_tri_en)
begin
// instructions always Big Endian
if (worden_f[0])
icdata_ary[wr_index0] <= wrdata_f[135:102];
if (worden_f[1])
icdata_ary[wr_index1] <= wrdata_f[101:68];
if (worden_f[2])
icdata_ary[wr_index2] <= wrdata_f[67:34];
if (worden_f[3])
icdata_ary[wr_index3] <= wrdata_f[33:0];
end // if (wrreq_f)
end // always @ (...
`endif // !`ifdef DEFINE_0IN
 
 
//--------------------------------------------------------------
// Redundancy Registers
//--------------------------------------------------------------
//
// read red regs
// 16:1 mux
always @ (/*AUTOSENSE*/fuse_icd_rid or red0_ev_col or red0_ev_row
or red0_od_col or red0_od_row or red1_ev_col
or red1_ev_row or red1_od_col or red1_od_row
or red2_ev_col or red2_ev_row or red2_od_col
or red2_od_row or red3_ev_col or red3_ev_row
or red3_od_col or red3_od_row)
begin
// sub array 0
if (fuse_icd_rid[3:0] == 4'b0)
begin
icd_fuse_repair_value = {2'b0, red0_ev_row[5:0]};
icd_fuse_repair_en = red0_ev_row[7:6];
end
else if (fuse_icd_rid[3:0] == 4'b1)
begin
icd_fuse_repair_value = {2'b0, red0_od_row[5:0]};
icd_fuse_repair_en = red0_od_row[7:6];
end
else if (fuse_icd_rid[3:0] == 4'b10)
begin
icd_fuse_repair_value = red0_ev_col[7:0];
icd_fuse_repair_en = red0_ev_col[9:8];
end
else if (fuse_icd_rid[3:0] == 4'b11)
begin
icd_fuse_repair_value = red0_od_col[7:0];
icd_fuse_repair_en = red0_od_col[9:8];
end
 
// sub array 1
else if (fuse_icd_rid[3:0] == 4'b100)
begin
icd_fuse_repair_value = {2'b0, red1_ev_row[5:0]};
icd_fuse_repair_en = red1_ev_row[7:6];
end
else if (fuse_icd_rid[3:0] == 4'b101)
begin
icd_fuse_repair_value = {2'b0, red1_od_row[5:0]};
icd_fuse_repair_en = red1_od_row[7:6];
end
else if (fuse_icd_rid[3:0] == 4'b110)
begin
icd_fuse_repair_value = red1_ev_col[7:0];
icd_fuse_repair_en = red1_ev_col[9:8];
end
else if (fuse_icd_rid[3:0] == 4'b111)
begin
icd_fuse_repair_value = red1_od_col[7:0];
icd_fuse_repair_en = red1_od_col[9:8];
end
 
// sub array 2
else if (fuse_icd_rid[3:0] == 4'b1000)
begin
icd_fuse_repair_value = {2'b0, red2_ev_row[5:0]};
icd_fuse_repair_en = red2_ev_row[7:6];
end
else if (fuse_icd_rid[3:0] == 4'b1001)
begin
icd_fuse_repair_value = {2'b0, red2_od_row[5:0]};
icd_fuse_repair_en = red2_od_row[7:6];
end
else if (fuse_icd_rid[3:0] == 4'b1010)
begin
icd_fuse_repair_value = red2_ev_col[7:0];
icd_fuse_repair_en = red2_ev_col[9:8];
end
else if (fuse_icd_rid[3:0] == 4'b1011)
begin
icd_fuse_repair_value = red2_od_col[7:0];
icd_fuse_repair_en = red2_od_col[9:8];
end
 
// sub array 3
else if (fuse_icd_rid[3:0] == 4'b1100)
begin
icd_fuse_repair_value = {2'b0, red3_ev_row[5:0]};
icd_fuse_repair_en = red3_ev_row[7:6];
end
else if (fuse_icd_rid[3:0] == 4'b1101)
begin
icd_fuse_repair_value = {2'b0, red3_od_row[5:0]};
icd_fuse_repair_en = red3_od_row[7:6];
end
else if (fuse_icd_rid[3:0] == 4'b1110)
begin
icd_fuse_repair_value = red3_ev_col[7:0];
icd_fuse_repair_en = red3_ev_col[9:8];
end
else // if (fuse_icd_rid[3:0] == 4'b1111)
begin
icd_fuse_repair_value = red3_od_col[7:0];
icd_fuse_repair_en = red3_od_col[9:8];
end
end // always @ (...
 
 
//
// write red regs
//
// use clk1 to latch anything to/from the hdr
//
// reset_l is an asynchronous reset. Only the the repair enables [9:8]
// need to be reset. However, the actual circuit resets all the bits.
always @ (posedge efc_spc_fuse_clk1 or negedge reset_l)
begin
if (~reset_l)
begin // async reset
red0_ev_row[7:0] <= 8'b0;
red1_ev_row[7:0] <= 8'b0;
red2_ev_row[7:0] <= 8'b0;
red3_ev_row[7:0] <= 8'b0;
 
red0_od_row[7:0] <= 8'b0;
red1_od_row[7:0] <= 8'b0;
red2_od_row[7:0] <= 8'b0;
red3_od_row[7:0] <= 8'b0;
 
red0_ev_col[9:0] <= 10'b0;
red1_ev_col[9:0] <= 10'b0;
red2_ev_col[9:0] <= 10'b0;
red3_ev_col[9:0] <= 10'b0;
 
red0_od_col[9:0] <= 10'b0;
red1_od_col[9:0] <= 10'b0;
red2_od_col[9:0] <= 10'b0;
red3_od_col[9:0] <= 10'b0;
end // if (~reset_l)
else if (fuse_icd_wren & reset_l)
begin // 4:16 decode
if (fuse_icd_rid[3:0] == 4'b0)
begin
red0_ev_row <= {fuse_icd_repair_en[1:0],
fuse_icd_repair_value[5:0]};
end
else if (fuse_icd_rid[3:0] == 4'b1)
begin
red0_od_row <= {fuse_icd_repair_en[1:0],
fuse_icd_repair_value[5:0]};
end
else if (fuse_icd_rid[3:0] == 4'b10)
begin
red0_ev_col <= {fuse_icd_repair_en[1:0],
fuse_icd_repair_value[7:0]};
end
else if (fuse_icd_rid[3:0] == 4'b11)
begin
red0_od_col <= {fuse_icd_repair_en[1:0],
fuse_icd_repair_value[7:0]};
end
 
// sub array 1
else if (fuse_icd_rid[3:0] == 4'b100)
begin
red1_ev_row <= {fuse_icd_repair_en[1:0],
fuse_icd_repair_value[5:0]};
end
else if (fuse_icd_rid[3:0] == 4'b101)
begin
red1_od_row <= {fuse_icd_repair_en[1:0],
fuse_icd_repair_value[5:0]};
end
else if (fuse_icd_rid[3:0] == 4'b110)
begin
red1_ev_col <= {fuse_icd_repair_en[1:0],
fuse_icd_repair_value[7:0]};
end
else if (fuse_icd_rid[3:0] == 4'b111)
begin
red1_od_col <= {fuse_icd_repair_en[1:0],
fuse_icd_repair_value[7:0]};
end
 
// sub array 2
else if (fuse_icd_rid[3:0] == 4'b1000)
begin
red2_ev_row <= {fuse_icd_repair_en[1:0],
fuse_icd_repair_value[5:0]};
end
else if (fuse_icd_rid[3:0] == 4'b1001)
begin
red2_od_row <= {fuse_icd_repair_en[1:0],
fuse_icd_repair_value[5:0]};
end
else if (fuse_icd_rid[3:0] == 4'b1010)
begin
red2_ev_col <= {fuse_icd_repair_en[1:0],
fuse_icd_repair_value[7:0]};
end
else if (fuse_icd_rid[3:0] == 4'b1011)
begin
red2_od_col <= {fuse_icd_repair_en[1:0],
fuse_icd_repair_value[7:0]};
end
 
// sub array 2
else if (fuse_icd_rid[3:0] == 4'b1100)
begin
red3_ev_row <= {fuse_icd_repair_en[1:0],
fuse_icd_repair_value[5:0]};
end
else if (fuse_icd_rid[3:0] == 4'b1101)
begin
red3_od_row <= {fuse_icd_repair_en[1:0],
fuse_icd_repair_value[5:0]};
end
else if (fuse_icd_rid[3:0] == 4'b1110)
begin
red3_ev_col <= {fuse_icd_repair_en[1:0],
fuse_icd_repair_value[7:0]};
end
else // if (fuse_icd_rid[3:0] == 4'b1111)
begin
red3_od_col <= {fuse_icd_repair_en[1:0],
fuse_icd_repair_value[7:0]};
end
end // if (fuse_icd_wren)
end // always @ (...
 
endmodule // bw_r_icd
 
`endif
/trunk/hdl/rtl/sparc_core/bw_r_dcd.v
1,56 → 1,6
// ========== Copyright Header Begin ==========================================
//
// OpenSPARC T1 Processor File: bw_r_dcd.v
// Copyright (c) 2006 Sun Microsystems, Inc. All Rights Reserved.
// DO NOT ALTER OR REMOVE COPYRIGHT NOTICES.
//
// The above named program is free software; you can redistribute it and/or
// modify it under the terms of the GNU General Public
// License version 2 as published by the Free Software Foundation.
//
// The above named program is distributed in the hope that it will be
// useful, but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
// General Public License for more details.
//
// You should have received a copy of the GNU General Public
// License along with this work; if not, write to the Free Software
// Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA.
//
// ========== Copyright Header End ============================================
////////////////////////////////////////////////////////////////////////
/*
// Module Name:
// Description: LSU Data Cache.
// - Physically-Indexed Physically Tagged (PIPT)
// - 8KB
// - 4 way set-associative.
// - 16B lines
// - 2:1 column select by choosing either lower
// or upper half of 16B line.
// - Parity protected on a byte basis.
// - Byte enables for byte-wide stores.
//
*/
////////////////////////////////////////////////////////////////////////
// Global header file includes
////////////////////////////////////////////////////////////////////////
//`include "sys.h" // system level definition file which contains the
// time scale definition
// Empty module for cacheless Simply RISC S1 Core
 
//`include "iop.h"
//`include "fabric.h"
 
//FPGA_SYN enables all FPGA related modifications
`ifdef FPGA_SYN
`define FPGA_SYN_DCD
`endif
 
////////////////////////////////////////////////////////////////////////
// Local header file includes / local defines
////////////////////////////////////////////////////////////////////////
 
module bw_r_dcd ( /*AUTOARG*/
module bw_r_dcd (
// Outputs
so, dcache_rdata_wb, dcache_rparity_wb, dcache_rparity_err_wb,
dcache_rdata_msb_w0_m, dcache_rdata_msb_w1_m,
95,9 → 45,6
output [7:0] dcache_rparity_wb;
output dcache_rparity_err_wb;
 
//=================================
// dc_fill critical path
//=================================
input [63:0] dcache_alt_data_w0_m; //from qdp1
input dcache_arry_data_sel_m; //from dctl
106,10 → 53,6
output [7:0] dcache_rdata_msb_w2_m; //to dcdp
output [7:0] dcache_rdata_msb_w3_m; //to dcdp
 
//-----------------------------------------------------------------------------
// 32KB block fuse inputs
//-----------------------------------------------------------------------------
// efuse non ovl clks
input efc_spc_fuse_clk1;
input fuse_dcd_wren; //redundancy register write enable, qualified
119,518 → 62,7
output [7:0] dcd_fuse_repair_value; //data out for redundancy register
output [1:0] dcd_fuse_repair_en; //enable bits out
// Memory declaration.
 
`ifdef DEFINE_0IN
wire [143:0] temp_w0a;
wire [143:0] temp_w1a;
wire [143:0] temp_w2a;
wire [143:0] temp_w3a;
`else
reg [143:0] w0 [127:0]/* synthesis syn_ramstyle = block_ram syn_ramstyle = no_rw_check */ ; // way0, byte0. Data+Parity.
reg [143:0] w1 [127:0]/* synthesis syn_ramstyle = block_ram syn_ramstyle = no_rw_check */ ; // way0, byte0. Data+Parity.
reg [143:0] w2 [127:0]/* synthesis syn_ramstyle = block_ram syn_ramstyle = no_rw_check */ ; // way0, byte0. Data+Parity.
reg [143:0] w3 [127:0]/* synthesis syn_ramstyle = block_ram syn_ramstyle = no_rw_check */ ; // way0, byte0. Data+Parity.
 
reg [143:0] temp_w0a_reg;
reg [143:0] temp_w1a_reg;
reg [143:0] temp_w2a_reg;
reg [143:0] temp_w3a_reg;
wire [143:0] temp_w0a;
wire [143:0] temp_w1a;
wire [143:0] temp_w2a;
wire [143:0] temp_w3a;
 
reg [143:0] temp_w0;
reg [143:0] temp_w1;
reg [143:0] temp_w2;
reg [143:0] temp_w3;
`endif
reg [10:3] dcache_rwaddr_m ;
reg [10:3] dcache_raddr_m ;
reg dcache_rvld_m ;
reg wvld_m ;
reg [143:0] dcache_wdata_m ;
reg [127:0] rw_wdline ;
reg [3:0] dcache_wr_rway_m ;
 
reg [63:0] dcache_rdata_w0_wb; // way0 64b data.
reg [63:0] dcache_rdata_w1_wb; // way1 64b data.
reg [63:0] dcache_rdata_w2_wb; // way2 64b data.
reg [63:0] dcache_rdata_w3_wb; // way3 64b data.
reg [15:0] byte_wr_enable ;
reg [7:0] ctr;
 
reg dcache_alt_mx_sel_m, dcache_alt_mx_sel_wb;
reg [3:0] dcache_alt_rsel_way_m, dcache_alt_rsel_way_wb;
integer i,j;
 
wire dcache_wvld_m ;
wire [63:0] dcache_rdata_w0_m; // way0 64b data.
wire [63:0] dcache_rdata_w1_m; // way1 64b data.
wire [63:0] dcache_rdata_w2_m; // way2 64b data.
wire [63:0] dcache_rdata_w3_m; // way3 64b data.
wire [7:0] dcache_rparity_w0_m; // way0 8b parity.
wire [7:0] dcache_rparity_w1_m; // way1 8b parity.
wire [7:0] dcache_rparity_w2_m; // way2 8b parity.
wire [7:0] dcache_rparity_w3_m; // way3 8b parity.
 
wire [7:0] rd_parity_err_w0_m;
wire [7:0] rd_parity_err_w1_m;
wire [7:0] rd_parity_err_w2_m;
wire [7:0] rd_parity_err_w3_m;
wire [143:0] way_mask ;
wire [143:0] way_mask_inv ;
 
wire [10:3] dcache_rwaddr_e ;
wire [10:3] dcache_raddr_e ;
 
//calculated parity based on read-out data
wire [7:0] gen_dcache_parity_w0_m;
wire [7:0] gen_dcache_parity_w1_m;
wire [7:0] gen_dcache_parity_w2_m;
wire [7:0] gen_dcache_parity_w3_m;
 
wire clk;
assign clk = rclk;
//=========================================================================================
// Staging
//=========================================================================================
 
// BIST Rd used fill address port.
assign dcache_rwaddr_e[10:3] =
(dcache_alt_mx_sel_e) ? dcache_alt_addr_e[10:3] : dcache_rd_addr_e[10:3] ;
 
assign dcache_raddr_e[10:3] =
(dcache_alt_mx_sel_e) ? dcache_alt_addr_e[10:3] : dcache_rd_addr_e[10:3] ;
always @(posedge clk)
begin
dcache_alt_mx_sel_m <= sehold ? dcache_alt_mx_sel_m : dcache_alt_mx_sel_e;
dcache_alt_rsel_way_m <= sehold ? dcache_alt_rsel_way_m : dcache_alt_rsel_way_e;
dcache_rwaddr_m[10:3] <= sehold ? dcache_rwaddr_m[10:3] : dcache_rwaddr_e[10:3] ;
 
dcache_raddr_m[10:3] <= sehold ? dcache_raddr_m[10:3] : dcache_raddr_e[10:3] ;
 
dcache_rvld_m <= sehold ? dcache_rvld_m : dcache_rvld_e ;
 
wvld_m <= sehold ? wvld_m : dcache_wvld_e ;
 
dcache_wdata_m[143:0] <= sehold ? dcache_wdata_m[143:0] : dcache_wdata_e[143:0] ;
 
dcache_wr_rway_m[3:0] <= sehold ? dcache_wr_rway_m[3:0] : dcache_wr_rway_e[3:0] ;
 
byte_wr_enable[15:0] <= sehold ? byte_wr_enable[15:0] : dcache_byte_wr_en_e[15:0] ;
 
end
 
always @ (posedge clk)
begin
// JC modified begin
// dcache_alt_mx_sel_wb <= dcache_alt_mx_sel_m;
// dcache_alt_rsel_way_wb <= dcache_alt_rsel_way_m;
dcache_alt_mx_sel_wb <= sehold ? dcache_alt_mx_sel_wb :dcache_alt_mx_sel_m;
dcache_alt_rsel_way_wb <= sehold ? dcache_alt_rsel_way_wb :dcache_alt_rsel_way_m;
// JC modified end
end
assign dcache_wvld_m = wvld_m & ~rst_tri_en ;
 
 
`ifdef DEFINE_0IN
wire [3:0] dc_we = dcache_wvld_m ? dcache_wr_rway_m : 4'b0;
 
dc_data dc_data0 ( .nclk(~clk), .adr(dcache_rwaddr_m[10:4]),
.we(dc_we [0] ), .wm(way_mask [143:0]),
.din(dcache_wdata_m[143:0]), .dout(temp_w0a[143:0]) );
dc_data dc_data1 ( .nclk(~clk), .adr(dcache_rwaddr_m[10:4]),
.we(dc_we [1] ), .wm(way_mask [143:0]),
.din(dcache_wdata_m[143:0]), .dout(temp_w1a[143:0]) );
dc_data dc_data2 ( .nclk(~clk), .adr(dcache_rwaddr_m[10:4]),
.we(dc_we [2] ), .wm(way_mask [143:0]),
.din(dcache_wdata_m[143:0]), .dout(temp_w2a[143:0]) );
dc_data dc_data3 ( .nclk(~clk), .adr(dcache_rwaddr_m[10:4]),
.we(dc_we [3] ), .wm(way_mask [143:0]),
.din(dcache_wdata_m[143:0]), .dout(temp_w3a[143:0]) );
`else
//=========================================================================================
// generate wordlines
//=========================================================================================
 
// Generate at posedge of clk.
// JC modified begin
/*
always @ (posedge clk)
begin
for (ctr=8'h00;ctr<128;ctr=ctr+1)
begin
if (clk & ({1'b0,dcache_rwaddr_e[10:4]} == ctr) &
(dcache_rvld_e | dcache_wvld_e))
rw_wdline[ctr] = 1'b1;
else
rw_wdline[ctr] = 1'b0;
end
end
*/
 
`ifdef FPGA_SYN_DCD
`else
always @ (clk or dcache_rwaddr_m or dcache_wvld_m or dcache_rvld_m)
begin
if (clk) begin
for (ctr=8'h00;ctr<128;ctr=ctr+1)
begin
if (({1'b0,dcache_rwaddr_m[10:4]} == ctr) &
(dcache_rvld_m | dcache_wvld_m))
rw_wdline[ctr] = 1'b1;
else
rw_wdline[ctr] = 1'b0;
end
end
end
// JC modified end
`endif
 
 
//=========================================================================================
// Read from Memory.
//=========================================================================================
 
`ifdef FPGA_SYN_DCD
always @(posedge clk) begin
temp_w0a_reg[143:0] = w0[dcache_raddr_e[10:4]];
temp_w1a_reg[143:0] = w1[dcache_raddr_e[10:4]];
temp_w2a_reg[143:0] = w2[dcache_raddr_e[10:4]];
temp_w3a_reg[143:0] = w3[dcache_raddr_e[10:4]];
end
`else
// Read
always @ (negedge clk)
begin
for (i=0;i<128;i=i+1)
begin
if (rw_wdline[i] & dcache_rvld_m)
begin
temp_w0a_reg[143:0] <= w0[i];
temp_w1a_reg[143:0] <= w1[i];
temp_w2a_reg[143:0] <= w2[i];
temp_w3a_reg[143:0] <= w3[i];
end
end
end
`endif
 
//removed stablizer, zero out without read
assign temp_w0a[143:0] = dcache_rvld_m? temp_w0a_reg[143:0]: 144'b0;
assign temp_w1a[143:0] = dcache_rvld_m? temp_w1a_reg[143:0]: 144'b0;
assign temp_w2a[143:0] = dcache_rvld_m? temp_w2a_reg[143:0]: 144'b0;
assign temp_w3a[143:0] = dcache_rvld_m? temp_w3a_reg[143:0]: 144'b0;
 
`endif
 
// Prior to SA, column mux (64(D)+8(P))x4 bits. Assume parity is
// at the end of the 144b line. Entry is wX||Parity
 
// Select either upper or lower 64b from each of the 4 ways.
assign dcache_rdata_w0_m[63:0] = ~dcache_rwaddr_m[3] ? temp_w0a[143:80] : temp_w0a[79:16] ;
assign dcache_rdata_w1_m[63:0] = ~dcache_rwaddr_m[3] ? temp_w1a[143:80] : temp_w1a[79:16] ;
assign dcache_rdata_w2_m[63:0] = ~dcache_rwaddr_m[3] ? temp_w2a[143:80] : temp_w2a[79:16] ;
assign dcache_rdata_w3_m[63:0] = ~dcache_rwaddr_m[3] ? temp_w3a[143:80] : temp_w3a[79:16] ;
 
wire [7:0] dcache_msb_w0_m;
wire [7:0] dcache_alt_data_w0_msb_m;
//MSB sent out to dcdp in M stage
assign dcache_msb_w0_m[7:0]=
{dcache_rdata_w0_m[63],
dcache_rdata_w0_m[55],
dcache_rdata_w0_m[47],
dcache_rdata_w0_m[39],
dcache_rdata_w0_m[31],
dcache_rdata_w0_m[23],
dcache_rdata_w0_m[15],
dcache_rdata_w0_m[07]} ;
assign dcache_alt_data_w0_msb_m [7:0]=
{dcache_alt_data_w0_m[63],
dcache_alt_data_w0_m[55],
dcache_alt_data_w0_m[47],
dcache_alt_data_w0_m[39],
dcache_alt_data_w0_m[31],
dcache_alt_data_w0_m[23],
dcache_alt_data_w0_m[15],
dcache_alt_data_w0_m[07]} ;
 
//2-to-1 mux
assign dcache_rdata_msb_w0_m[7:0] = dcache_arry_data_sel_m ?
dcache_msb_w0_m[7:0] :
dcache_alt_data_w0_msb_m[7:0];
assign dcache_rdata_msb_w1_m[7:0]=
{dcache_rdata_w1_m[63],
dcache_rdata_w1_m[55],
dcache_rdata_w1_m[47],
dcache_rdata_w1_m[39],
dcache_rdata_w1_m[31],
dcache_rdata_w1_m[23],
dcache_rdata_w1_m[15],
dcache_rdata_w1_m[07]} ;
 
assign dcache_rdata_msb_w2_m[7:0]=
{dcache_rdata_w2_m[63],
dcache_rdata_w2_m[55],
dcache_rdata_w2_m[47],
dcache_rdata_w2_m[39],
dcache_rdata_w2_m[31],
dcache_rdata_w2_m[23],
dcache_rdata_w2_m[15],
dcache_rdata_w2_m[07]} ;
assign dcache_rdata_msb_w3_m[7:0]=
{dcache_rdata_w3_m[63],
dcache_rdata_w3_m[55],
dcache_rdata_w3_m[47],
dcache_rdata_w3_m[39],
dcache_rdata_w3_m[31],
dcache_rdata_w3_m[23],
dcache_rdata_w3_m[15],
dcache_rdata_w3_m[07]} ;
wire [63:0] rdata_w0_m;
wire [63:0] rdata_w1_m;
wire [63:0] rdata_w2_m;
wire [63:0] rdata_w3_m;
 
//2-to-1 mux
//dcache_alt_mx_sel default 0001 (way 0) when not in MBIST mode (logic in qdp2)
assign rdata_w0_m[63:0] = dcache_arry_data_sel_m ?
dcache_rdata_w0_m[63:0] : dcache_alt_data_w0_m[63:0];
 
//assign rdata_w0_m[63:0] = dcache_rdata_w0_m[63:0];
assign rdata_w1_m[63:0] = dcache_rdata_w1_m[63:0];
assign rdata_w2_m[63:0] = dcache_rdata_w2_m[63:0];
assign rdata_w3_m[63:0] = dcache_rdata_w3_m[63:0];
 
// Select upper half or lower half of parity.
assign dcache_rparity_w0_m[7:0] = ~dcache_rwaddr_m[3] ? temp_w0a[15:8] : temp_w0a[7:0] ;
assign dcache_rparity_w1_m[7:0] = ~dcache_rwaddr_m[3] ? temp_w1a[15:8] : temp_w1a[7:0] ;
assign dcache_rparity_w2_m[7:0] = ~dcache_rwaddr_m[3] ? temp_w2a[15:8] : temp_w2a[7:0] ;
assign dcache_rparity_w3_m[7:0] = ~dcache_rwaddr_m[3] ? temp_w3a[15:8] : temp_w3a[7:0] ;
 
reg [7:0] dcache_rparity_w0_wb;
reg [7:0] dcache_rparity_w1_wb;
reg [7:0] dcache_rparity_w2_wb;
reg [7:0] dcache_rparity_w3_wb;
 
reg [7:0] rd_parity_err_w0_wb;
reg [7:0] rd_parity_err_w1_wb;
reg [7:0] rd_parity_err_w2_wb;
reg [7:0] rd_parity_err_w3_wb;
// Stage to WB
always @(posedge clk)
begin
dcache_rdata_w0_wb[63:0] <= rdata_w0_m[63:0] ;
dcache_rdata_w1_wb[63:0] <= rdata_w1_m[63:0] ;
dcache_rdata_w2_wb[63:0] <= rdata_w2_m[63:0] ;
dcache_rdata_w3_wb[63:0] <= rdata_w3_m[63:0] ;
 
dcache_rparity_w0_wb[7:0] <= dcache_rparity_w0_m[7:0];
dcache_rparity_w1_wb[7:0] <= dcache_rparity_w1_m[7:0];
dcache_rparity_w2_wb[7:0] <= dcache_rparity_w2_m[7:0];
dcache_rparity_w3_wb[7:0] <= dcache_rparity_w3_m[7:0];
 
rd_parity_err_w0_wb [7:0] <= rd_parity_err_w0_m[7:0];
rd_parity_err_w1_wb [7:0] <= rd_parity_err_w1_m[7:0];
rd_parity_err_w2_wb [7:0] <= rd_parity_err_w2_m[7:0];
rd_parity_err_w3_wb [7:0] <= rd_parity_err_w3_m[7:0];
end
//parity calculation and check are done in M stage for 4 way data
wire rd_parity_err_w0;
wire rd_parity_err_w1;
wire rd_parity_err_w2;
wire rd_parity_err_w3;
lsu_dc_parity_gen #(8,8) parity_gen_w0 (
.data_in (dcache_rdata_w0_m[63:0]),
.parity_out (gen_dcache_parity_w0_m[7:0])
);
assign rd_parity_err_w0_m[7:0] = dcache_rvld_m ? (dcache_rparity_w0_m[7:0] ^ gen_dcache_parity_w0_m[7:0]) :
8'hff;
 
lsu_dc_parity_gen #(8,8) parity_gen_w1 (
.data_in (dcache_rdata_w1_m[63:0]),
.parity_out (gen_dcache_parity_w1_m[7:0])
);
 
assign rd_parity_err_w1_m[7:0] = dcache_rvld_m ? (dcache_rparity_w1_m[7:0] ^ gen_dcache_parity_w1_m[7:0]) :
8'hff;
 
lsu_dc_parity_gen #(8,8) parity_gen_w2 (
.data_in (dcache_rdata_w2_m[63:0]),
.parity_out (gen_dcache_parity_w2_m[7:0])
);
assign rd_parity_err_w2_m[7:0] = dcache_rvld_m ? (dcache_rparity_w2_m[7:0] ^ gen_dcache_parity_w2_m[7:0]) :
8'hff;
lsu_dc_parity_gen #(8,8) parity_gen_w3 (
.data_in (dcache_rdata_w3_m[63:0]),
.parity_out (gen_dcache_parity_w3_m[7:0])
);
assign rd_parity_err_w3_m[7:0] = dcache_rvld_m ? (dcache_rparity_w3_m[7:0] ^ gen_dcache_parity_w3_m[7:0]) :
8'hff;
 
 
// way select mux on READ
// Select one of four ways from indexed cache set.
 
wire [3:0] dcache_rd_sel_way_wb;
assign dcache_rd_sel_way_wb[3:0] = dcache_alt_mx_sel_wb ? dcache_alt_rsel_way_wb[3:0] :
dcache_rsel_way_wb[3:0];
assign dcache_rdata_wb[63:0] =
(dcache_rd_sel_way_wb[0] ? dcache_rdata_w0_wb[63:0] : 64'b0) |
(dcache_rd_sel_way_wb[1] ? dcache_rdata_w1_wb[63:0] : 64'b0) |
(dcache_rd_sel_way_wb[2] ? dcache_rdata_w2_wb[63:0] : 64'b0) |
(dcache_rd_sel_way_wb[3] ? dcache_rdata_w3_wb[63:0] : 64'b0);
 
//parity err in W-stage, cache_way_hit may not be one-hot
assign rd_parity_err_w0 = |(rd_parity_err_w0_wb[7:0]);
assign rd_parity_err_w1 = |(rd_parity_err_w1_wb[7:0]);
assign rd_parity_err_w2 = |(rd_parity_err_w2_wb[7:0]);
assign rd_parity_err_w3 = |(rd_parity_err_w3_wb[7:0]);
 
assign dcache_rparity_err_wb = rd_parity_err_w3 & dcache_rd_sel_way_wb[3] |
rd_parity_err_w2 & dcache_rd_sel_way_wb[2] |
rd_parity_err_w1 & dcache_rd_sel_way_wb[1] |
rd_parity_err_w0 & dcache_rd_sel_way_wb[0] ;
//mux4ds #(64) dcache_rdata_wb_mx (
// .in0 (dcache_rdata_w0_wb[63:0]),
// .in1 (dcache_rdata_w1_wb[63:0]),
// .in2 (dcache_rdata_w2_wb[63:0]),
// .in3 (dcache_rdata_w3_wb[63:0]),
// .sel0 (dcache_rd_sel_way_wb[0]),
// .sel1 (dcache_rd_sel_way_wb[1]),
// .sel2 (dcache_rd_sel_way_wb[2]),
// .sel3 (dcache_rd_sel_way_wb[3]),
// .dout (dcache_rdata_wb[63:0])
//);
// dcache_rparity_wb only used by MBIST
//mux4ds #(8) dcache_rparity_wb_mx (
// .in0 (dcache_rparity_w0_wb[7:0]),
// .in1 (dcache_rparity_w1_wb[7:0]),
// .in2 (dcache_rparity_w2_wb[7:0]),
// .in3 (dcache_rparity_w3_wb[7:0]),
// .sel0(dcache_alt_rsel_way_wb[0]),
// .sel1(dcache_alt_rsel_way_wb[1]),
// .sel2(dcache_alt_rsel_way_wb[2]),
// .sel3(dcache_alt_rsel_way_wb[3]),
// .dout(dcache_rparity_wb[7:0])
//);
 
assign dcache_rparity_wb[7:0] =
( dcache_rd_sel_way_wb[0] ? dcache_rparity_w0_wb[7:0] : 8'b0 ) |
( dcache_rd_sel_way_wb[1] ? dcache_rparity_w1_wb[7:0] : 8'b0 ) |
( dcache_rd_sel_way_wb[2] ? dcache_rparity_w2_wb[7:0] : 8'b0 ) |
( dcache_rd_sel_way_wb[3] ? dcache_rparity_w3_wb[7:0] : 8'b0 ) ;
//=========================================================================================
// Write to Memory
//=========================================================================================
 
// Reads and writes are mutex as array is single-ported.
 
 
// Includes data(128b)+parity(16b).
assign way_mask[143:0] =
{{8{byte_wr_enable[15]}},{8{byte_wr_enable[14]}},{8{byte_wr_enable[13]}},
{8{byte_wr_enable[12]}},{8{byte_wr_enable[11]}},{8{byte_wr_enable[10]}},
{8{byte_wr_enable[9]}}, {8{byte_wr_enable[8]}}, {8{byte_wr_enable[7]}},
{8{byte_wr_enable[6]}}, {8{byte_wr_enable[5]}}, {8{byte_wr_enable[4]}},
{8{byte_wr_enable[3]}}, {8{byte_wr_enable[2]}}, {8{byte_wr_enable[1]}},
{8{byte_wr_enable[0]}}, byte_wr_enable[15:0]} ;
 
assign way_mask_inv[143:0] = ~way_mask[143:0];
 
always @ (negedge clk)
begin
 
`ifdef FPGA_SYN_DCD
 
if(dcache_wvld_m & dcache_wr_rway_m[0]) begin
w0[dcache_rwaddr_m[10:4]] = (temp_w0a_reg[143:0] & way_mask_inv[143:0]) |
(dcache_wdata_m[143:0] & way_mask[143:0]) ;
end
if(dcache_wvld_m & dcache_wr_rway_m[1]) begin
w1[dcache_rwaddr_m[10:4]] = (temp_w1a_reg[143:0] & way_mask_inv[143:0]) |
(dcache_wdata_m[143:0] & way_mask[143:0]) ;
end
if(dcache_wvld_m & dcache_wr_rway_m[2]) begin
w2[dcache_rwaddr_m[10:4]] = (temp_w2a_reg[143:0] & way_mask_inv[143:0]) |
(dcache_wdata_m[143:0] & way_mask[143:0]) ;
end
if(dcache_wvld_m & dcache_wr_rway_m[3]) begin
w3[dcache_rwaddr_m[10:4]] = (temp_w3a_reg[143:0] & way_mask_inv[143:0]) |
(dcache_wdata_m[143:0] & way_mask[143:0]) ;
end
 
`else // !`ifdef FPGA_SYN_DCD
 
for (j=0;j<128;j=j+1)
begin
if (rw_wdline[j] & dcache_wvld_m & dcache_wr_rway_m[0])
begin
// read
temp_w0[143:0] = w0[j];
// modify & write
w0[j] = (temp_w0[143:0] & way_mask_inv[143:0]) |
(dcache_wdata_m[143:0] & way_mask[143:0]) ;
end
if (rw_wdline[j] & dcache_wvld_m & dcache_wr_rway_m[1])
begin
// read
temp_w1[143:0] = w1[j];
// modify & write
w1[j] = (temp_w1[143:0] & way_mask_inv[143:0]) |
(dcache_wdata_m[143:0] & way_mask[143:0]) ;
end
if (rw_wdline[j] & dcache_wvld_m & dcache_wr_rway_m[2])
begin
// read
temp_w2[143:0] = w2[j];
// modify & write
w2[j] = (temp_w2[143:0] & way_mask_inv[143:0]) |
(dcache_wdata_m[143:0] & way_mask[143:0]) ;
end
if (rw_wdline[j] & dcache_wvld_m & dcache_wr_rway_m[3])
begin
// read
temp_w3[143:0] = w3[j];
// modify & write.
w3[j] = (temp_w3[143:0] & way_mask_inv[143:0]) |
(dcache_wdata_m[143:0] & way_mask[143:0]) ;
end
end
`endif // !`ifdef FPGA_SYN_DCD
 
end // always @ (negedge clk)
endmodule
 
 

powered by: WebSVN 2.1.0

© copyright 1999-2024 OpenCores.org, equivalent to Oliscience, all rights reserved. OpenCores®, registered trademark.