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

Subversion Repositories sparc64soc

[/] [sparc64soc/] [trunk/] [T1-common/] [srams/] [bw_rf_16x81.v] - Blame information for rev 2

Details | Compare with Previous | View Log

Line No. Rev Author Line
1 2 dmitryr
// ========== Copyright Header Begin ==========================================
2
// 
3
// OpenSPARC T1 Processor File: bw_rf_16x81.v
4
// Copyright (c) 2006 Sun Microsystems, Inc.  All Rights Reserved.
5
// DO NOT ALTER OR REMOVE COPYRIGHT NOTICES.
6
// 
7
// The above named program is free software; you can redistribute it and/or
8
// modify it under the terms of the GNU General Public
9
// License version 2 as published by the Free Software Foundation.
10
// 
11
// The above named program is distributed in the hope that it will be 
12
// useful, but WITHOUT ANY WARRANTY; without even the implied warranty of
13
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
14
// General Public License for more details.
15
// 
16
// You should have received a copy of the GNU General Public
17
// License along with this work; if not, write to the Free Software
18
// Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA.
19
// 
20
// ========== Copyright Header End ============================================
21
module bw_rf_16x81(
22
   rd_clk,    // read clock
23
   wr_clk,    // read clock
24
   csn_rd,    // read enable -- active low 
25
   csn_wr,    // write enable -- active low
26
   hold,      // hold signal -- unflopped -- hold =1 holds input data 
27
   testmux_sel, // bypass  signal -- unflopped -- testmux_sel = 1 bypasses di to do 
28
   scan_en,   // Scan enable unflopped  
29
   margin,    // Delay for the circuits--- set to 01010101 
30
   rd_a,      // read address  
31
   wr_a,      // Write address
32
   di,        // Data input
33
   si,        // scan in  
34
   so,        // scan out  
35
   listen_out, // Listening flop-- 
36
   do          // Data out
37
 
38
);
39
 
40
   input rd_clk;
41
   input wr_clk;
42
   input csn_rd;
43
   input csn_wr;
44
   input hold;
45
   input testmux_sel;
46
   input scan_en;
47
   input [4:0] margin;
48
   input [3:0] rd_a;
49
   input [3:0] wr_a;
50
   input [80:0] di;
51
   input si;
52
   output so;
53
   output [80:0] do;
54
   output [80:0] listen_out;
55
 
56
parameter  SYNC_CLOCK_CHK1 = 1;
57
parameter  SYNC_CLOCK_CHK2 = 1;
58
parameter  SYNC_CLOCK_CHK3 = 1;
59
parameter  MARGIN_WARNING = 1; // margin warning is on by default
60
 
61
 
62
 
63
 
64
// Start code
65
reg [80:0] memarray[15:0] ;
66
reg [80:0] array_out  ;
67
 
68
reg [80:0] array_out_latch    ;
69
 
70
 
71
 
72
reg  [3:0] rd_a_ff   ;
73
wire [3:0] rd_a_ff_so;
74
wire [3:0] rd_a_ff_si ;
75
 
76
reg  [3:0] wr_a_ff   ;
77
wire [3:0] wr_a_ff_so;
78
wire [3:0] wr_a_ff_si ;
79
 
80
reg  [80:0] di_ff   ;
81
wire [80:0] di_ff_so;
82
wire [80:0] di_ff_si;
83
 
84
wire [80:0] listen_out_so;
85
wire [80:0] listen_out_si ;
86
reg  [80:0] listen_out     ;
87
 
88
 
89
reg        csn_rd_ff ;
90
wire       csn_rd_ff_si ;
91
wire       csn_rd_ff_so ;
92
 
93
reg        csn_wr_ff ;
94
wire       csn_wr_ff_si ;
95
wire       csn_wr_ff_so ;
96
 
97
reg        di_ff_latch_so ;
98
///////////////////////////////////////
99
// Scan chain connections            //
100
///////////////////////////////////////
101
assign wr_a_ff_si[3:0] = {si      , wr_a_ff_so[3:1]} ;
102
assign csn_wr_ff_si    = wr_a_ff_so[0] ;
103
assign di_ff_si        = {csn_wr_ff_so, di_ff_so[80:1]};
104
assign listen_out_si   = {listen_out_so[79:0], di_ff_latch_so} ;
105
assign csn_rd_ff_si    = listen_out_so[80] ;
106
assign rd_a_ff_si[3:0] = {rd_a_ff_so[2:0], csn_rd_ff_so} ;
107
assign so              = rd_a_ff_so[3] ;
108
///////////////////////////////////////
109
// Instantiate a clock headers        //
110
///////////////////////////////////////
111
 
112
wire   rd_ssclk       = rd_clk ; // clk_en & rd_clk ;
113
wire   rd_local_clk   = rd_ssclk | scan_en | hold ;
114
wire   rd_smclk       = rd_ssclk |  ~(scan_en | hold) ;
115
 
116
wire   wr_ssclk       = wr_clk ; // clk_en & wr_clk ;
117
wire   wr_local_clk   = wr_ssclk | scan_en | hold ;
118
wire   wr_smclk       = wr_ssclk |  ~(scan_en | hold) ;
119
 
120
 
121
/////////////////////////////////////////////////////
122
// csn_rd Flop                                     //
123
/////////////////////////////////////////////////////
124
 
125
reg                     csn_rd_ff_inst_mdata ;
126
wire                    csn_rd_ff_inst_smin ;
127
reg                     csn_rd_ff_scan_out ;
128
 
129
assign csn_rd_ff_inst_smin  = hold ?  csn_rd_ff_scan_out :  csn_rd_ff_si ;
130
always @(rd_smclk or rd_local_clk or csn_rd or csn_rd_ff_inst_smin ) begin
131
       if (!rd_local_clk) begin
132
          csn_rd_ff_inst_mdata = csn_rd ;
133
       end
134
       if (!rd_smclk) begin
135
          csn_rd_ff_inst_mdata = csn_rd_ff_inst_smin;
136
       end
137
end
138
always @(posedge rd_ssclk) begin
139
    csn_rd_ff_scan_out    <=  csn_rd_ff_inst_mdata ;
140
end
141
always @(rd_local_clk or csn_rd_ff_inst_mdata) begin
142
   if (rd_local_clk ) begin
143
    csn_rd_ff    <=  csn_rd_ff_inst_mdata ;
144
   end
145
end
146
assign csn_rd_ff_so =  csn_rd_ff_scan_out;
147
 
148
/////////////////////////////////////////////////////
149
 
150
/////////////////////////////////////////////////////
151
// rd_a Flop                                       //
152
/////////////////////////////////////////////////////
153
reg     [3:0]   rd_a_ff_inst_mdata ;
154
wire    [3:0]   rd_a_ff_inst_smin ;
155
reg     [3:0]   rd_a_ff_scan_out ;
156
 
157
assign rd_a_ff_inst_smin[3:0]  = hold ?  rd_a_ff_scan_out[3:0] :  rd_a_ff_si[3:0] ;
158
always @(rd_smclk or rd_local_clk or rd_a or rd_a_ff_inst_smin ) begin
159
       if (!rd_local_clk) begin
160
          rd_a_ff_inst_mdata = rd_a[3:0] ;
161
       end
162
       if (!rd_smclk) begin
163
          rd_a_ff_inst_mdata = rd_a_ff_inst_smin;
164
       end
165
end
166
always @(posedge rd_ssclk) begin
167
    rd_a_ff_scan_out[3:0]   <=  rd_a_ff_inst_mdata ;
168
end
169
always @(rd_local_clk or rd_a_ff_inst_mdata) begin
170
   if (rd_local_clk) begin
171
    rd_a_ff[3:0]   <=  rd_a_ff_inst_mdata ;
172
   end
173
end
174
assign rd_a_ff_so[3:0] = rd_a_ff_scan_out[3:0] ;
175
/////////////////////////////////////////////////////
176
 
177
/////////////////////////////////////////////////////
178
// csn_wr Flop                                     //
179
/////////////////////////////////////////////////////
180
reg                     csn_wr_ff_inst_mdata ;
181
wire                    csn_wr_ff_inst_smin ;
182
 
183
assign csn_wr_ff_inst_smin  = hold ?  csn_wr_ff :  csn_wr_ff_si ;
184
always @(wr_smclk or wr_local_clk or csn_wr or csn_wr_ff_inst_smin ) begin
185
       if (!wr_local_clk) begin
186
          csn_wr_ff_inst_mdata = csn_wr ;
187
       end
188
       if (!wr_smclk) begin
189
          csn_wr_ff_inst_mdata = csn_wr_ff_inst_smin;
190
       end
191
end
192
always @(posedge wr_ssclk) begin
193
    csn_wr_ff    <=  csn_wr_ff_inst_mdata ;
194
end
195
assign csn_wr_ff_so =  csn_wr_ff;
196
/////////////////////////////////////////////////////
197
 
198
/////////////////////////////////////////////////////
199
// wr_a Flop                                       //
200
/////////////////////////////////////////////////////
201
reg     [3:0]   wr_a_ff_inst_mdata ;
202
wire    [3:0]   wr_a_ff_inst_smin ;
203
 
204
assign wr_a_ff_inst_smin[3:0]  = hold ?  wr_a_ff[3:0] :  wr_a_ff_si[3:0] ;
205
always @(wr_smclk or wr_local_clk or wr_a or wr_a_ff_inst_smin ) begin
206
       if (!wr_local_clk) begin
207
          wr_a_ff_inst_mdata = wr_a[3:0] ;
208
       end
209
       if (!wr_smclk) begin
210
          wr_a_ff_inst_mdata = wr_a_ff_inst_smin;
211
       end
212
end
213
always @(posedge wr_ssclk) begin
214
    wr_a_ff[3:0]   <=  wr_a_ff_inst_mdata ;
215
end
216
assign wr_a_ff_so[3:0] = wr_a_ff[3:0] ;
217
/////////////////////////////////////////////////////
218
 
219
/////////////////////////////////////////////////////
220
// di Flop                                         //
221
/////////////////////////////////////////////////////
222
reg     [80:0]  di_ff_inst_mdata ;
223
wire    [80:0]  di_ff_inst_smin ;
224
 
225
assign di_ff_inst_smin[80:0]  = hold ?  di_ff[80:0] :  di_ff_si[80:0] ;
226
always @(wr_smclk or wr_local_clk or di or di_ff_inst_smin ) begin
227
       if (!wr_local_clk) begin
228
          di_ff_inst_mdata = di[80:0] ;
229
       end
230
       if (!wr_smclk) begin
231
          di_ff_inst_mdata = di_ff_inst_smin;
232
       end
233
end
234
always @(posedge wr_ssclk) begin
235
    di_ff[80:0]   <=  di_ff_inst_mdata ;
236
end
237
assign di_ff_so[80:0] = di_ff[80:0] ;
238
/////////////////////////////////////////////////////
239
 
240
wire wr_enable_l = csn_wr_ff | scan_en ;
241
wire rd_enable_l = csn_rd_ff | scan_en ;
242
 
243
// wire wr_clk_qual = wr_ssclk & ~scan_en ; 
244
always @(wr_ssclk or wr_a_ff or wr_enable_l or di_ff ) begin
245
     if (!wr_ssclk) begin
246
        if (!wr_enable_l) begin
247
               memarray[wr_a_ff] <= di_ff[80:0] ;
248
        end
249
     end
250
end
251
 
252
// wire  rd_clk_qual =  (rd_ssclk & ~scan_en) ; 
253
always @(rd_ssclk or rd_a_ff or rd_enable_l) begin
254
     if (rd_ssclk) begin
255
        if (rd_enable_l == 1'b0) begin
256
             array_out[80:0] <= memarray[rd_a_ff] ;
257
        end else if (rd_enable_l == 1'b1) begin
258
             array_out[80:0] <= 81'h1FFFFFFFFFFFFFFFFFFFF;
259
        end else begin
260
             array_out[80:0] <= 81'hXXXXXXXXXXXXXXXXXXXXX;
261
        end
262
     end
263
end
264
 
265
 
266
// synopsys translate_off
267
 
268
`ifdef  INNO_MUXEX
269
`else
270
  always @(csn_rd_ff or csn_wr_ff or rd_a_ff or wr_a_ff)   begin
271
   if ((SYNC_CLOCK_CHK1 == 0) & !csn_rd_ff & !csn_wr_ff & (rd_a_ff == wr_a_ff)) begin
272
      array_out   <= 81'hxxxxxxxxxxxxxxxxxxxxx;
273
        `ifdef MODELSIM
274
      $display ("sram_conflict", "conflict between read: %h and write: %h pointers", rd_a_ff, wr_a_ff);
275
        `else
276
      $error ("sram_conflict", "conflict between read: %h and write: %h pointers", rd_a_ff, wr_a_ff);
277
        `endif
278
   end
279
  end
280
`endif
281
 
282
///////////////////////////////////////////////////////////////
283
// Purely ERROR checking code.                               //
284
///////////////////////////////////////////////////////////////
285
reg  [3:0] rd_a_ff_del ;
286
reg        csn_rd_ff_del ;
287
reg        rd_clk_del ;
288
always @(rd_local_clk) begin
289
     if (rd_local_clk)  rd_clk_del = #300 rd_local_clk;
290
     else              rd_clk_del = #300 rd_local_clk;
291
end
292
always @(posedge rd_clk_del) begin
293
       rd_a_ff_del <= rd_a_ff ;
294
       csn_rd_ff_del <= csn_rd_ff ;
295
end
296
 
297
`ifdef  INNO_MUXEX
298
`else
299
  always @(csn_rd_ff_del or csn_wr_ff or rd_a_ff_del or wr_a_ff or rd_clk_del or wr_ssclk)   begin
300
   if (SYNC_CLOCK_CHK2 == 0) begin
301
       if (rd_clk_del & !wr_ssclk & !csn_rd_ff_del & !csn_wr_ff & (rd_a_ff_del == wr_a_ff)) begin
302
        `ifdef MODELSIM
303
              $display ("sram_conflict", "conflict between read: %h and write: %h pointers ", rd_a_ff_del, wr_a_ff);
304
        `else
305
              $error ("sram_conflict", "conflict between read: %h and write: %h pointers ", rd_a_ff_del, wr_a_ff);
306
        `endif
307
       end
308
   end
309
  end
310
`endif
311
 
312
reg  [3:0] wr_a_ff_del ;
313
reg        csn_wr_ff_del ;
314
reg        wr_clk_del ;
315
always @(wr_ssclk) begin
316
     if (wr_ssclk)  wr_clk_del = #300 wr_ssclk;
317
     else              wr_clk_del = #300 wr_ssclk;
318
end
319
always @(posedge wr_clk_del) begin
320
       wr_a_ff_del <= wr_a_ff ;
321
       csn_wr_ff_del <= csn_wr_ff ;
322
end
323
 
324
`ifdef  INNO_MUXEX
325
`else
326
  always @(csn_rd_ff or csn_wr_ff_del or rd_a_ff or wr_a_ff_del or rd_local_clk or wr_clk_del)   begin
327
   if (SYNC_CLOCK_CHK3 == 0) begin
328
       if (rd_local_clk & !wr_clk_del & !csn_rd_ff & !csn_wr_ff_del & (rd_a_ff == wr_a_ff_del)) begin
329
      $display ("sram_conflict", "conflict between read: %h and write: %h pointers ", rd_a_ff, wr_a_ff_del);
330
       end
331
   end
332
  end
333
`endif
334
 
335
///////////////////////////////////////////////////////////////
336
// end the ERROR checking code.                              // 
337
///////////////////////////////////////////////////////////////
338
///////////////////////////////////////
339
 
340
 
341
// synopsys translate_on
342
 
343
///////////////////////////////////
344
// Transparent latch with reset
345
///////////////////////////////////
346
 
347
always @(array_out or rd_ssclk) begin
348
     if (rd_ssclk) begin
349
        array_out_latch <= array_out ;
350
     end
351
end
352
 
353
always @(di_ff_so[0] or wr_ssclk) begin
354
     if (!wr_ssclk) begin
355
        di_ff_latch_so <= di_ff_so[0] ;
356
     end
357
end
358
 
359
 
360
assign do  = testmux_sel ? di_ff : array_out_latch ;
361
 
362
/////////////////////////////////////////////////////
363
// listen_out Flop                                 //
364
/////////////////////////////////////////////////////
365
reg     [80:0]  listen_out_ff_inst_mdata ;
366
wire    [80:0]  listen_out_ff_inst_smin ;
367
 
368
assign listen_out_ff_inst_smin[80:0]  = hold ?  do[80:0] :  listen_out_si[80:0] ;
369
always @(rd_smclk or rd_local_clk or do or listen_out_ff_inst_smin ) begin
370
       if (!rd_local_clk) begin
371
          listen_out_ff_inst_mdata = do[80:0] ;
372
       end
373
       if (!rd_smclk) begin
374
          listen_out_ff_inst_mdata = listen_out_ff_inst_smin;
375
       end
376
end
377
always @(posedge rd_ssclk) begin
378
    listen_out[80:0]   <=  listen_out_ff_inst_mdata ;
379
end
380
assign listen_out_so[80:0] = listen_out[80:0] ;
381
 
382
// synopsys translate_off 
383
 
384
`ifdef  INNO_MUXEX
385
`else
386
   always @(posedge rd_clk) begin
387
     if ((MARGIN_WARNING == 0) & margin != 5'b10101) begin
388
        `ifdef MODELSIM
389
          $display ("sram_margin", "margin is not set to the default value") ;
390
        `else
391
          $error ("sram_margin", "margin is not set to the default value") ;
392
        `endif
393
     end
394
   end
395
`endif
396
 
397
// synopsys translate_on 
398
 
399
endmodule

powered by: WebSVN 2.1.0

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