/******************************************************************************/
/* */
/* Copyright (c) 1999 Sun Microsystems, Inc. All rights reserved. */
/* */
/* The contents of this file are subject to the current version of the Sun */
/* Community Source License, microSPARCII ("the License"). You may not use */
/* this file except in compliance with the License. You may obtain a copy */
/* of the License by searching for "Sun Community Source License" on the */
/* World Wide Web at http://www.sun.com. See the License for the rights, */
/* obligations, and limitations governing use of the contents of this file. */
/* */
/* Sun Microsystems, Inc. has intellectual property rights relating to the */
/* technology embodied in these files. In particular, and without limitation, */
/* these intellectual property rights may include one or more U.S. patents, */
/* foreign patents, or pending applications. */
/* */
/* Sun, Sun Microsystems, the Sun logo, all Sun-based trademarks and logos, */
/* Solaris, Java and all Java-based trademarks and logos are trademarks or */
/* registered trademarks of Sun Microsystems, Inc. in the United States and */
/* other countries. microSPARC is a trademark or registered trademark of */
/* SPARC International, Inc. All SPARC trademarks are used under license and */
/* are trademarks or registered trademarks of SPARC International, Inc. in */
/* the United States and other countries. Products bearing SPARC trademarks */
/* are based upon an architecture developed by Sun Microsystems, Inc. */
/* */
/******************************************************************************/
// **************************************************************************
// @(#)rl_col_row_addr.v 1.17 10/18/93
// rl_col_row_addr.v
//
// Description:
// The Row/Column mux for memory subsystem in SingleSPARC.
// Refer to SingleSPARC Hardware Spec, section 2.7.3 for block diagram
// for more information.
//
//
// Dependencies:
// mem_cells.v
//
//
//
// **************************************************************************
//**************************************************************************
// The address flow path from MMU and GCB to final 11-bit Row/Column address
// generated for the DRAM/VRAM
module rl_col_row_addr
(rcaddr, ab,
mm_pa, mm_caddr, hld_mm_pa, col_en,
s_blk, ld_ct, mode_ct, inc_ct, ss_clock,
gaddr_hld, sel_hi_row, sel_row,
sel_gr_page, sel_default,
mm_pa_a_28,
mm_pa_a_27, mm_pa_a_26,
mm_pa_a_25, mm_pa_b_00,
mm_pa_b_01, mm_pa_b_02,
mm_fb_size, gr_s_blk, gr_mode_ct,
gr_inc_ct, odat_hld, mm_mem_dbg,
mm_issue_req, dly_bsy );
output [11:0] rcaddr
; // Column address to DRAM/VRAM
output [14:12] ab
; // graphics address to VRAM
input [24:12] mm_pa
; // 13 bits for 11bit row and high 2bit column.
input [11:03] mm_caddr
; // 9 bits for low 9bits of column addr.
input col_en
; // Gate column address when asserted (high).
input s_blk
; // Use incrementor o/p for block accesses.
input ld_ct
; // Load or count control of 2-bit incrementor.
input mode_ct
; // Set incrementor for modulo-2 or 4 count.
input inc_ct
; // If 0, hold contents of incrementor.
input hld_mm_pa
; // When low, addr from MMU is stored in regs.
input ss_clock
;
input gaddr_hld
;
input sel_hi_row
;
input sel_row
;
input sel_gr_page
;
input sel_default
;
input mm_pa_a_28
;
input mm_pa_a_27
;
input mm_pa_a_26
;
input mm_pa_a_25
;
input mm_pa_b_00
;
input mm_pa_b_01
;
input mm_pa_b_02
;
input [1:0] mm_fb_size
;
input gr_s_blk
;
input gr_mode_ct
;
input gr_inc_ct
;
input odat_hld
;
input [1:0] mm_mem_dbg
;
input mm_issue_req
;
input dly_bsy
;
wire [11:0] row_mm
, row
;
wire [10:0] col_mm
, col
;
wire [1:0] col_inc
;
wire [10:9] col_mm_in
;
wire [1:0] Gnd
= 2'b00; // assign 2 bit ground-bus
wire [3:0] Vcc
= 4'hF ; // assign 32 bit supply-bus
wire [28:0] gpa
;
wire [10:0] gaddr_out
;
// add graphics control for address
wire [1:0] gaddr_inc
;
wire [1:0] gpa_inc
;
GReg3 ffh_gaddr_27_25 (gpa[27:25],{mm_pa_a_27, mm_pa_a_26, mm_pa_a_25},
ss_clock, gaddr_hld);
GReg1 ffh_gaddr_28 (gpa[28], mm_pa_a_28, ss_clock, gaddr_hld);
GReg1 ffh_gaddr_21 (gpa[21], mm_pa[21], ss_clock, gaddr_hld);
GReg1 ffh_gaddr_12 (gpa[12], mm_pa[12], ss_clock, gaddr_hld);
GReg9 ffh_gaddr_11_3 (gpa[11:3], mm_caddr[11:3], ss_clock, gaddr_hld);
// GReg3 ffh_gaddr_2_0 (gpa[2:0],{mm_pa_b_02, mm_pa_b_01, mm_pa_b_00},
// ss_clock, gaddr_hld);
assign gpa[24] = row_mm[10];
assign gpa[23] = row_mm[11];
assign gpa[22] = row_mm[9];
assign gpa[20:13] = row_mm[8:1];
// decode mm_fb_size & pa before register.
wire [3:0] bm_in
;
wire [3:0] bm
;
function [3:0] bm_decode;
input [1:0] mm_fb_size;
input mm_pa_b_02;
input mm_pa_b_01;
input mm_pa_b_00;
begin
case (mm_fb_size) //PARALLEL_CASE
2'b00: begin
bm_decode[3] = 1'b0;
bm_decode[2:0] = {mm_pa_b_02, mm_pa_b_01, mm_pa_b_00};
end
2'b01: begin
bm_decode[3] = 1'b1;
bm_decode[2:1] = {mm_pa_b_02, mm_pa_b_01};
bm_decode[0] = 1'b0;
end
2'b10: begin
bm_decode[3] = 1'b1;
bm_decode[2] = {mm_pa_b_02};
bm_decode[1] = 1'b0;
bm_decode[0] = 1'b1;
end
2'b11: begin
bm_decode[3] = 1'b1;
bm_decode[2] = 1'b0;
bm_decode[1] = 1'b1;
bm_decode[0] = 1'b1;
end
endcase
end
endfunction
/*--------------------------------------------------------------------*/
assign bm_in[3:0] = bm_decode(mm_fb_size[1:0], mm_pa_b_02,
mm_pa_b_01, mm_pa_b_00);
GReg4 ffh_bm (bm, bm_in, ss_clock, odat_hld);
/*
case (mm_fb_size)
2'b00: begin
bm_in[3] = 1'b0;
bm_in[2:0] = {mm_pa_b_02, mm_pa_b_01, mm_pa_b_00};
end
2'b01: begin
bm_in[3] = 1'b1;
bm_in[2:1] = {mm_pa_b_02, mm_pa_b_01};
bm_in[0] = 1'b0;
end
2'b10: begin
bm_in[3] = 1'b1;
bm_in[2] = {mm_pa_b_02};
bm_in[1] = 1'b0;
bm_in[0] = 1'b1;
end
2'b11: begin
bm_in[3] = 1'b1;
bm_in[2] = 1'b0;
bm_in[1] = 1'b1;
bm_in[0] = 1'b1;
end
endcase
assign hld_size = sel_gr_page | sel_hi_row;
GReg4 ffh_bm (bm, bm_in, ss_clock, odat_hld);
*/
// Mux3D_11 mx_row_graddr (gaddr_out[10:0],{2'b00, gpa[27:19]}, sel_hi_row,
// {1'b1, size[1:0], gpa[1:0], gpa[18:13]}, sel_row,
// {gpa[12:5], gpa_inc[1:0], gpa[2]}, sel_gr_page,
// row[10:0], sel_default );
Mux3D_11 mx_row_graddr (gaddr_out[10:0],{gpa[23:14], gpa[28]}, sel_hi_row,
{gpa[13:5], gpa_inc[1:0]}, sel_gr_page,
row[10:0], sel_default );
// add debug feature to send out.
// Mux2_3 mx_ab_14_12 (ab[14:12],gpa[27:25], bm[3:1], sel_gr_page);
wire [1:0] mm_mem_dbg_n
;
GReg2 ffh_mm_mem_dbg_n (mm_mem_dbg_n[1:0], mm_mem_dbg[1:0],
ss_clock, ~mm_issue_req );
Mux2_1 mx_ab_12 (ab[12],gpa[25], bm[1], sel_gr_page);
Mux3D_2 mx_ab_14_13 (ab[14:13], bm[3:2], sel_gr_page,
gpa[27:26], sel_hi_row,
mm_mem_dbg_n[1:0], sel_default);
// All registers that latch the mm_pa addresses at the
// start of a cycle.
// The mm_caddr is now registered in MMU, so no need to register it here.
// just wire it up, using "assign".
assign col_mm[ 8:0] = mm_caddr[11:03] ;
// This is bizzare, why 2 stage of reg just to check bit 9 and 10 was not
// changed?
// GReg2 ffh_col_mm_hi_in (col_mm_in[10:9], {mm_pa[23], mm_pa[21]},
// ss_clock, hld_mm_pa);
// GReg2 ffh_col_mm_hi (col_mm[10:9], col_mm_in[10:9],
// ss_clock, col_en );
// Rewrite using mux and reg.
// Since rcaddr[11] is only for row address, dont care in this case.
GReg2 ffh_col_mm_hi_in (col_mm_in[10:9], {mm_pa[23], mm_pa[21]},
ss_clock, hld_mm_pa);
// this mux is changed to add 1 more mux to select col_mm_in[10:9] @ dly_bsy.
// Mux2_2 mx_col_mm_hi (col_mm[10:9],{mm_pa[23], mm_pa[21]}, col_mm_in[10:9],
// hld_mm_pa);
Mux2_2 mm_pa_a_new_mux ({mm_pa_a_23_new
, mm_pa_a_21_new
},{mm_pa[23], mm_pa[21]},
col_mm_in[10:9], dly_bsy);
Mux2_2 mx_col_mm_hi (col_mm[10:9],{mm_pa_a_23_new, mm_pa_a_21_new},
col_mm_in[10:9], hld_mm_pa);
GReg12 ffh_row_mm_reg (row_mm[11:0],
{mm_pa[23],mm_pa[24],mm_pa[22],mm_pa[20:12]},
ss_clock, gaddr_hld);
// do not hold row add at wrt2 or rdt5; also ok for dram for
// col add need to be released @ ~mbsy but not row.
// GReg12 ffh_row_mm_reg (row_mm[11:0],
// {mm_pa[23],mm_pa[24],mm_pa[22],mm_pa[20:12]},
// ss_clock, hld_mm_pa);
// 2 bit incrementor, to provide the 2 LSBs of column addr for block type
// cycles
rl_col_inc col_incr (col_inc[1:0], col_mm[1:0],
ld_ct, mode_ct, inc_ct, ss_clock);
// The muxes to produce the column address sourced by mmu request:
Mux2_2 mx_col10 (col[1:0], col_mm[1:0], col_inc[1:0], s_blk);
// Do wire renames, to keep the old (when gcb was present) notation.
assign col[10:2] = col_mm[10:2];
assign row[11:0] = row_mm[11:00];
// The column/row select mux.
Mux2_11 mx_rca (rcaddr[10:0], gaddr_out[10:0],col[10:0], col_en );
// The 12th bit of ROW addr for 12x10 matrix 4Mx4 DRAMs.
// mux out 12th bit from row or graphics.
// assign rcaddr[11] = row[11] ;
// This is added after pg1.0 to fix a bug in DRAM. To inhibit toggling of
// memaddr[11] in column access.
wire row_11_not_col_en
;
assign row_11_not_col_en = row[11] & ~col_en;
Mux3D_1 mx_row_graddr_11 (rcaddr[11], gpa[24], sel_hi_row,
bm[0], sel_gr_page,
row_11_not_col_en, sel_default );
/*
Mux3D_1 mx_row_graddr_11 (rcaddr[11], gpa[24], sel_hi_row,
bm[0], sel_gr_page,
row[11], sel_default );
*/
rl_col_inc gaddr_incr (gaddr_inc[1:0], mm_caddr[4:3],
ld_ct, gr_mode_ct, gr_inc_ct, ss_clock);
Mux2_2 mx_gr21 (gpa_inc[1:0], gpa[4:3], gaddr_inc[1:0], gr_s_blk);
endmodule
// **************************************************************************
// 2-bit loadable incrementor, used to increment column address for multi
// cycle memory operations.
// - For 4 cycle ops (I-cache fill and SBus 32byte block access)
// the counter is modulo-4.
// - For 2 cycle ops (D-cache fill and SBus 16byte block access)
// the counter is modulo-2.
![[Up: rl_col_row_addr col_incr]](v2html-up.gif)
module rl_col_inc
(col_inc, col_mm, ld_ct, mode_ct, inc_ct, ss_clock);
output [1:0] col_inc
; // Registered o/p from GReg2.
input [1:0] col_mm
; // MMU Col addr bits.
input ld_ct
; // If 1, col_inc = col_mm. If 0 count up.
input mode_ct
; // If 0, count modulo-2. If 1, count modulo-4.
input inc_ct
; // If 0, hold contents as is.
input ss_clock
;
wire [1:0] incr_w
;
wire Gnd
= 1'b0 ;
//------------- incr function --------------------------------
// Is a 2 bit loadable-incrementor used for incrementing the
// column address in block type accesses (I$, D$, SBus).
//-------------------------------------------------------------
function [1:0] f_incr;
input [1:0] col_mm, col_inc;
input ld_ct, mode_ct, inc_ct;
begin
f_incr = col_inc;
if ( ld_ct == 1'b1 ) begin /* load the input. */
f_incr = col_mm;
end
else if ( inc_ct == 1'b1 ) begin /* count up.*/
case (mode_ct) //synopsys parallel_case
1'b0 : begin
/*
8/30/93 JDW: Changed because of problem with
Verilog 1.7_beta. It did not execute previous
syntax correctly.
*/
f_incr = {f_incr[1], ~col_inc[0]}; // Toggle LSB only.
end
1'b1 :
f_incr = col_inc + 2'b01; // Modulo-2 counter.
endcase
end
end
endfunction
// edit to remove hold pin.
// first try with unconnect scanen and sin
// GReg2 ffh_col_inc (col_inc[1:0], incr_w[1:0], ss_clock, Gnd );
Mflipflop_noop_2 ffh_col_inc (col_inc[1:0], incr_w[1:0], ss_clock );
//-------------------------------------------------------------
assign incr_w = f_incr(col_mm,col_inc,ld_ct,mode_ct,inc_ct);
endmodule
This page: |
Created: | Thu Aug 19 12:02:10 1999 |
| From: |
../../../sparc_v8/ssparc/memif/rtl/rl_col_row_addr.v
|