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

Subversion Repositories can

[/] [can/] [trunk/] [rtl/] [verilog/] [can_fifo.v] - Blame information for rev 51

Go to most recent revision | Details | Compare with Previous | View Log

Line No. Rev Author Line
1 11 mohor
//////////////////////////////////////////////////////////////////////
2
////                                                              ////
3
////  can_fifo.v                                                  ////
4
////                                                              ////
5
////                                                              ////
6
////  This file is part of the CAN Protocol Controller            ////
7
////  http://www.opencores.org/projects/can/                      ////
8
////                                                              ////
9
////                                                              ////
10
////  Author(s):                                                  ////
11
////       Igor Mohor                                             ////
12
////       igorm@opencores.org                                    ////
13
////                                                              ////
14
////                                                              ////
15
////  All additional information is available in the README.txt   ////
16
////  file.                                                       ////
17
////                                                              ////
18
//////////////////////////////////////////////////////////////////////
19
////                                                              ////
20
//// Copyright (C) 2002, 2003 Authors                             ////
21
////                                                              ////
22
//// This source file may be used and distributed without         ////
23
//// restriction provided that this copyright statement is not    ////
24
//// removed from the file and that any derivative work contains  ////
25
//// the original copyright notice and the associated disclaimer. ////
26
////                                                              ////
27
//// This source file is free software; you can redistribute it   ////
28
//// and/or modify it under the terms of the GNU Lesser General   ////
29
//// Public License as published by the Free Software Foundation; ////
30
//// either version 2.1 of the License, or (at your option) any   ////
31
//// later version.                                               ////
32
////                                                              ////
33
//// This source is distributed in the hope that it will be       ////
34
//// useful, but WITHOUT ANY WARRANTY; without even the implied   ////
35
//// warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR      ////
36
//// PURPOSE.  See the GNU Lesser General Public License for more ////
37
//// details.                                                     ////
38
////                                                              ////
39
//// You should have received a copy of the GNU Lesser General    ////
40
//// Public License along with this source; if not, download it   ////
41
//// from http://www.opencores.org/lgpl.shtml                     ////
42
////                                                              ////
43 28 mohor
//// The CAN protocol is developed by Robert Bosch GmbH and       ////
44
//// protected by patents. Anybody who wants to implement this    ////
45
//// CAN IP core on silicon has to obtain a CAN protocol license  ////
46
//// from Bosch.                                                  ////
47
////                                                              ////
48 11 mohor
//////////////////////////////////////////////////////////////////////
49
//
50
// CVS Revision History
51
//
52
// $Log: not supported by cvs2svn $
53 51 mohor
// Revision 1.13  2003/03/01 22:53:33  mohor
54
// Actel APA ram supported.
55
//
56 48 mohor
// Revision 1.12  2003/02/19 14:44:03  mohor
57
// CAN core finished. Host interface added. Registers finished.
58
// Synchronization to the wishbone finished.
59
//
60 39 mohor
// Revision 1.11  2003/02/14 20:17:01  mohor
61
// Several registers added. Not finished, yet.
62
//
63 35 mohor
// Revision 1.10  2003/02/11 00:56:06  mohor
64
// Wishbone interface added.
65
//
66 31 mohor
// Revision 1.9  2003/02/09 02:24:33  mohor
67
// Bosch license warning added. Error counters finished. Overload frames
68
// still need to be fixed.
69
//
70 28 mohor
// Revision 1.8  2003/01/31 01:13:38  mohor
71
// backup.
72
//
73 24 mohor
// Revision 1.7  2003/01/17 17:44:31  mohor
74
// Fifo corrected to be synthesizable.
75
//
76 23 mohor
// Revision 1.6  2003/01/15 13:16:47  mohor
77 31 mohor
// When a frame with "remote request" is received, no data is stored
78
// to fifo, just the frame information (identifier, ...). Data length
79
// that is stored is the received data length and not the actual data
80
// length that is stored to fifo.
81 23 mohor
//
82 18 mohor
// Revision 1.5  2003/01/14 17:25:09  mohor
83
// Addresses corrected to decimal values (previously hex).
84
//
85 17 mohor
// Revision 1.4  2003/01/14 12:19:35  mohor
86
// rx_fifo is now working.
87
//
88 16 mohor
// Revision 1.3  2003/01/09 21:54:45  mohor
89
// rx fifo added. Not 100 % verified, yet.
90
//
91 14 mohor
// Revision 1.2  2003/01/09 14:46:58  mohor
92
// Temporary files (backup).
93
//
94 13 mohor
// Revision 1.1  2003/01/08 02:10:55  mohor
95
// Acceptance filter added.
96 11 mohor
//
97
//
98
//
99 13 mohor
//
100 11 mohor
 
101
// synopsys translate_off
102
`include "timescale.v"
103
// synopsys translate_on
104
`include "can_defines.v"
105
 
106
module can_fifo
107
(
108
  clk,
109
  rst,
110
 
111
  wr,
112
 
113
  data_in,
114 14 mohor
  addr,
115 11 mohor
  data_out,
116 48 mohor
  fifo_selected,
117 11 mohor
 
118
  reset_mode,
119 14 mohor
  release_buffer,
120 35 mohor
  extended_mode,
121
  overrun,
122 39 mohor
  info_empty,
123
  info_cnt
124 13 mohor
 
125 11 mohor
);
126
 
127
parameter Tp = 1;
128
 
129
input         clk;
130
input         rst;
131
input         wr;
132
input   [7:0] data_in;
133 14 mohor
input   [7:0] addr;
134 11 mohor
input         reset_mode;
135
input         release_buffer;
136 14 mohor
input         extended_mode;
137 48 mohor
input         fifo_selected;
138 11 mohor
 
139 13 mohor
output  [7:0] data_out;
140 35 mohor
output        overrun;
141
output        info_empty;
142 39 mohor
output  [6:0] info_cnt;
143 11 mohor
 
144 48 mohor
`ifdef ACTEL_APA_RAM
145
`else
146 51 mohor
`ifdef XILINX_RAM
147
`else
148 48 mohor
  reg     [7:0] fifo [0:63];
149
  reg     [3:0] length_fifo[0:63];
150
  reg           overrun_info[0:63];
151
`endif
152 51 mohor
`endif
153 11 mohor
 
154
reg     [5:0] rd_pointer;
155
reg     [5:0] wr_pointer;
156 14 mohor
reg     [5:0] read_address;
157 16 mohor
reg     [5:0] wr_info_pointer;
158
reg     [5:0] rd_info_pointer;
159 13 mohor
reg           wr_q;
160
reg     [3:0] len_cnt;
161 16 mohor
reg     [6:0] fifo_cnt;
162 24 mohor
reg     [6:0] info_cnt;
163 16 mohor
reg           latch_overrun;
164 11 mohor
 
165 48 mohor
wire    [3:0] length_info;
166 13 mohor
wire          write_length_info;
167 16 mohor
wire          fifo_empty;
168
wire          fifo_full;
169 24 mohor
wire          info_full;
170 11 mohor
 
171 13 mohor
assign write_length_info = (~wr) & wr_q;
172
 
173
// Delayed write signal
174
always @ (posedge clk or posedge rst)
175
begin
176
  if (rst)
177
    wr_q <= 0;
178
  else if (reset_mode)
179
    wr_q <=#Tp 0;
180
  else
181
    wr_q <=#Tp wr;
182
end
183
 
184
 
185
// length counter
186
always @ (posedge clk or posedge rst)
187
begin
188
  if (rst)
189
    len_cnt <= 0;
190
  else if (reset_mode | write_length_info)
191
    len_cnt <=#Tp 1'b0;
192 16 mohor
  else if (wr & (~fifo_full))
193 13 mohor
    len_cnt <=#Tp len_cnt + 1'b1;
194
end
195
 
196
 
197
// wr_info_pointer
198
always @ (posedge clk or posedge rst)
199
begin
200
  if (rst)
201
    wr_info_pointer <= 0;
202
  else if (reset_mode)
203
    wr_info_pointer <=#Tp 0;
204 24 mohor
  else if (write_length_info & (~info_full))
205 13 mohor
    wr_info_pointer <=#Tp wr_info_pointer + 1'b1;
206
end
207
 
208
 
209
 
210
// rd_info_pointer
211 11 mohor
always @ (posedge clk or posedge rst)
212
begin
213
  if (rst)
214 13 mohor
    rd_info_pointer <= 0;
215 11 mohor
  else if (reset_mode)
216 13 mohor
    rd_info_pointer <=#Tp 0;
217 16 mohor
  else if (release_buffer & (~fifo_empty))
218 13 mohor
    rd_info_pointer <=#Tp rd_info_pointer + 1'b1;
219 11 mohor
end
220
 
221
 
222
// rd_pointer
223
always @ (posedge clk or posedge rst)
224
begin
225
  if (rst)
226
    rd_pointer <= 0;
227 16 mohor
  else if (release_buffer & (~fifo_empty))
228 48 mohor
    rd_pointer <=#Tp rd_pointer + length_info;
229 11 mohor
  else if (reset_mode)
230
    rd_pointer <=#Tp 0;
231
end
232
 
233
 
234
// wr_pointer
235
always @ (posedge clk or posedge rst)
236
begin
237
  if (rst)
238
    wr_pointer <= 0;
239 16 mohor
  else if (wr & (~fifo_full))
240 13 mohor
    wr_pointer <=#Tp wr_pointer + 1'b1;
241 11 mohor
  else if (reset_mode)
242
    wr_pointer <=#Tp 0;
243
end
244
 
245
 
246 16 mohor
// latch_overrun
247
always @ (posedge clk or posedge rst)
248
begin
249
  if (rst)
250
    latch_overrun <= 0;
251
  else if (reset_mode | write_length_info)
252
    latch_overrun <=#Tp 0;
253
  else if (wr & fifo_full)
254
    latch_overrun <=#Tp 1'b1;
255
end
256
 
257
 
258
// Counting data in fifo
259
always @ (posedge clk or posedge rst)
260
begin
261
  if (rst)
262
    fifo_cnt <= 0;
263
  else if (wr & (~release_buffer) & (~fifo_full))
264
    fifo_cnt <=#Tp fifo_cnt + 1'b1;
265
  else if ((~wr) & release_buffer & (~fifo_empty))
266 48 mohor
    fifo_cnt <=#Tp fifo_cnt - length_info;
267 16 mohor
  else if (wr & release_buffer & (~fifo_full) & (~fifo_empty))
268 48 mohor
    fifo_cnt <=#Tp fifo_cnt - length_info + 1'b1;
269 16 mohor
  else if (reset_mode)
270
    fifo_cnt <=#Tp 0;
271
end
272
 
273
assign fifo_full = fifo_cnt == 64;
274
assign fifo_empty = fifo_cnt == 0;
275
 
276
 
277 48 mohor
// Counting data in length_fifo and overrun_info fifo
278 24 mohor
always @ (posedge clk or posedge rst)
279
begin
280
  if (rst)
281
    info_cnt <= 0;
282
  else if (write_length_info ^ release_buffer)
283
    begin
284
      if (release_buffer & (~info_empty))
285
        info_cnt <=#Tp info_cnt - 1'b1;
286
      else if (write_length_info & (~info_full))
287
        info_cnt <=#Tp info_cnt + 1'b1;
288
    end
289
end
290
 
291
assign info_full = info_cnt == 64;
292
assign info_empty = info_cnt == 0;
293 16 mohor
 
294 24 mohor
 
295 14 mohor
// Selecting which address will be used for reading data from rx fifo
296
always @ (extended_mode or rd_pointer or addr)
297
begin
298
  if (extended_mode)      // extended mode
299
    begin
300 17 mohor
      read_address <= rd_pointer + (addr - 8'd16);
301 14 mohor
    end
302
  else                    // normal mode
303
    begin
304 17 mohor
      read_address <= rd_pointer + (addr - 8'd20);
305 14 mohor
    end
306
end
307 11 mohor
 
308
 
309 14 mohor
 
310 48 mohor
`ifdef ACTEL_APA_RAM
311
  actel_ram_64x8_sync fifo
312
  (
313
    .DO      (data_out),
314
    .RCLOCK  (clk),
315
    .WCLOCK  (clk),
316
    .DI      (data_in),
317
    .PO      (),                       // parity not used
318
    .WRB     (~(wr & (~fifo_full))),
319
    .RDB     (~fifo_selected),
320
    .WADDR   (wr_pointer),
321
    .RADDR   (read_address)
322
  );
323 14 mohor
 
324
 
325 48 mohor
  actel_ram_64x4_sync info_fifo
326
  (
327
    .DO      (length_info),
328
    .RCLOCK  (clk),
329
    .WCLOCK  (clk),
330
    .DI      (len_cnt),
331
    .PO      (),                       // parity not used
332
    .WRB     (~(write_length_info & (~info_full))),
333
    .RDB     (1'b0),                   // always enabled
334
    .WADDR   (wr_info_pointer),
335
    .RADDR   (rd_info_pointer)
336
  );
337 14 mohor
 
338
 
339 48 mohor
  actel_ram_64x1_sync overrun_fifo
340
  (
341
    .DO      (overrun),
342
    .RCLOCK  (clk),
343
    .WCLOCK  (clk),
344
    .DI      (latch_overrun | (wr & fifo_full)),
345
    .PO      (),                       // parity not used
346
    .WRB     (~(write_length_info & (~info_full))),
347
    .RDB     (1'b0),                   // always enabled
348
    .WADDR   (wr_info_pointer),
349
    .RADDR   (rd_info_pointer)
350
  );
351
`else
352 51 mohor
`ifdef XILINX_RAM
353
 
354
/*
355
  ram_64x8_sync fifo
356
  (
357
    .addra(wr_pointer),
358
    .addrb(read_address),
359
    .clka(clk),
360
    .clkb(clk),
361
    .dina(data_in),
362
    .doutb(data_out),
363
    .wea(wr & (~fifo_full))
364
  );
365
*/
366
 
367
  RAMB4_S8_S8 fifo
368
  (
369
    .DOA(),
370
    .DOB(data_out),
371
    .ADDRA({3'h0, wr_pointer}),
372
    .CLKA(clk),
373
    .DIA(data_in),
374
    .ENA(1'b1),
375
    .RSTA(1'b0),
376
    .WEA(wr & (~fifo_full)),
377
    .ADDRB({3'h0, read_address}),
378
    .CLKB(clk),
379
    .DIB(8'h0),
380
    .ENB(1'b1),
381
    .RSTB(1'b0),
382
    .WEB(1'b0)
383
  );
384
 
385
 
386
 
387
/*
388
  ram_64x4_sync info_fifo
389
  (
390
    .addra(wr_info_pointer),
391
    .addrb(rd_info_pointer),
392
    .clka(clk),
393
    .clkb(clk),
394
    .dina(len_cnt),
395
    .doutb(length_info),
396
    .wea(write_length_info & (~info_full))
397
  );
398
*/
399
  RAMB4_S4_S4 info_fifo
400
  (
401
    .DOA(),
402
    .DOB(length_info),
403
    .ADDRA({4'h0, wr_info_pointer}),
404
    .CLKA(clk),
405
    .DIA(len_cnt),
406
    .ENA(1'b1),
407
    .RSTA(1'b0),
408
    .WEA(write_length_info & (~info_full)),
409
    .ADDRB({4'h0, rd_info_pointer}),
410
    .CLKB(clk),
411
    .DIB(4'h0),
412
    .ENB(1'b1),
413
    .RSTB(1'b0),
414
    .WEB(1'b0)
415
  );
416
 
417
/*
418
  ram_64x1_sync overrun_fifo
419
  (
420
    .addra(wr_info_pointer),
421
    .addrb(rd_info_pointer),
422
    .clka(clk),
423
    .clkb(clk),
424
    .dina(latch_overrun | (wr & fifo_full)),
425
    .doutb(overrun),
426
    .wea(write_length_info & (~info_full))
427
  );
428
*/
429
 
430
 
431
  RAMB4_S1_S1 overrun_fifo
432
  (
433
    .DOA(),
434
    .DOB(overrun),
435
    .ADDRA({6'h0, wr_info_pointer}),
436
    .CLKA(clk),
437
    .DIA(latch_overrun | (wr & fifo_full)),
438
    .ENA(1'b1),
439
    .RSTA(1'b0),
440
    .WEA(write_length_info & (~info_full)),
441
    .ADDRB({6'h0, rd_info_pointer}),
442
    .CLKB(clk),
443
    .DIB(1'h0),
444
    .ENB(1'b1),
445
    .RSTB(1'b0),
446
    .WEB(1'b0)
447
  );
448
 
449
 
450
 
451
 
452
`else
453 48 mohor
  // writing data to fifo
454
  always @ (posedge clk)
455
  begin
456
    if (wr & (~fifo_full))
457
      fifo[wr_pointer] <=#Tp data_in;
458
  end
459
 
460
  // reading from fifo
461
  assign data_out = fifo[read_address];
462
 
463
 
464
  // writing length_fifo
465
  always @ (posedge clk)
466
  begin
467
    if (write_length_info & (~info_full))
468
      length_fifo[wr_info_pointer] <=#Tp len_cnt;
469
  end
470
 
471
  // reading length_fifo
472
  assign length_info = length_fifo[rd_info_pointer];
473
 
474
  // overrun_info
475
  always @ (posedge clk)
476
  begin
477
    if (write_length_info & (~info_full))
478
      overrun_info[wr_info_pointer] <=#Tp latch_overrun | (wr & fifo_full);
479
  end
480
 
481
 
482
  // reading overrun
483
  assign overrun = overrun_info[rd_info_pointer];
484
 
485
 
486
`endif
487 51 mohor
`endif
488 48 mohor
 
489
 
490
 
491
 
492
 
493 11 mohor
endmodule

powered by: WebSVN 2.1.0

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