OpenCores
URL https://opencores.org/ocsvn/an-fpga-implementation-of-low-latency-noc-based-mpsoc/an-fpga-implementation-of-low-latency-noc-based-mpsoc/trunk

Subversion Repositories an-fpga-implementation-of-low-latency-noc-based-mpsoc

[/] [an-fpga-implementation-of-low-latency-noc-based-mpsoc/] [trunk/] [mpsoc/] [rtl/] [src_noc/] [debug.v] - Blame information for rev 48

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

Line No. Rev Author Line
1 48 alirezamon
`timescale 1ns / 1ps
2
 
3
/**************************************
4
* Module: debug
5
* Date:2019-04-01
6
* Author: alireza
7
*
8
* Description: this file contain modules which are used for error checking/debiging of the NoC.
9
***************************************/
10
 
11
//check if flits are recived in correct order in a VC
12
 
13
module check_flit_chanel_type_is_in_order #(
14
    parameter V=4,
15
    parameter PCK_TYPE = "SINGLE_FLIT",
16
    parameter MIN_PCK_SIZE=2
17
)(
18
    hdr_flg_in,
19
    flit_in_wr,
20
    tail_flg_in,
21
    vc_num_in,
22
    clk,
23
    reset
24
 
25
);
26
 
27
    input clk, reset;
28
    input hdr_flg_in, tail_flg_in, flit_in_wr;
29
    input [V-1 : 0] vc_num_in;
30
 
31
 
32
 
33
 
34
    wire [V-1 : 0] vc_num_hdr_wr, vc_num_tail_wr,vc_num_bdy_wr ;
35
    reg  [V-1 : 0] hdr_passed, hdr_passed_next;
36
    wire [V-1 : 0] single_flit_pck;
37
 
38
    assign  vc_num_hdr_wr =(hdr_flg_in & flit_in_wr) ?    vc_num_in : 0;
39
    assign  vc_num_tail_wr =(tail_flg_in & flit_in_wr)?    vc_num_in : 0;
40
    assign  vc_num_bdy_wr =({hdr_flg_in,tail_flg_in} == 2'b00 && flit_in_wr)?    vc_num_in : 0;
41
    assign  single_flit_pck = vc_num_hdr_wr & vc_num_tail_wr;
42
    always @(*)begin
43
        hdr_passed_next = (hdr_passed | vc_num_hdr_wr) & ~vc_num_tail_wr;
44
    end
45
 
46
    // synthesis translate_off
47
    always @ (posedge clk or posedge reset) begin
48
        if(reset)  begin
49
            hdr_passed <= 0;
50
 
51
        end else begin
52
 
53
            hdr_passed     <= hdr_passed_next;
54
            if(( hdr_passed & vc_num_hdr_wr)>0  )begin
55
                $display("%t ERROR: a header flit is received in  an active IVC %m",$time);
56
                $finish;
57
            end
58
            if((~hdr_passed & vc_num_tail_wr & ~single_flit_pck )>0 ) begin
59
                $display("%t ERROR: a tail flit is received in an inactive IVC %m",$time);
60
                $finish;
61
            end
62
            if ((~hdr_passed & vc_num_bdy_wr    )>0)begin
63
                $display("%t ERROR: a body flit is received in an inactive IVC %m",$time);
64
                $finish;
65
            end
66
            /* verilator lint_off WIDTH */
67
            if((PCK_TYPE == "SINGLE_FLIT") &  flit_in_wr & ~(hdr_flg_in &  tail_flg_in )) begin
68
                $display("%t ERROR: both tail and header flit flags must be asserted in SINGLE_FLIT mode %m",$time);
69
                $finish;
70
            end
71
            /* verilator lint_on WIDTH */
72
            if( (MIN_PCK_SIZE !=1) &  flit_in_wr & hdr_flg_in &  tail_flg_in ) begin
73
                $display("%t ERROR: A single flit packet is injected while the minimum packet size is set to %d.  %m",$time,MIN_PCK_SIZE);
74
                $finish;
75
            end
76
            //TODO check that the injected packet size meets the MIN_PCK_SIZE
77
 
78
        end//else
79
    end//always
80
    // synthesis translate_on
81
endmodule
82
 
83
 
84
 
85
 
86
 
87
 
88
module debug_mesh_tori_route_ckeck #(
89
    parameter T1=4,
90
    parameter T2=4,
91
    parameter T3=4,
92
    parameter ROUTE_TYPE = "FULL_ADAPTIVE",
93
    parameter V=4,
94
    parameter AVC_ATOMIC_EN=1,
95
    parameter SW_LOC = 0,
96
    parameter [V-1 : 0] ESCAP_VC_MASK= 4'b0001,
97
    parameter TOPOLOGY="MESH",
98
    parameter DSTPw=4,
99
    parameter RAw=4,
100
    parameter EAw=4
101
)(
102
    reset,
103
    clk,
104
    hdr_flg_in,
105
    flit_in_wr,
106
    flit_is_tail,
107
    ivc_num_getting_sw_grant,
108
    vc_num_in,
109
    current_r_addr,
110
    dest_e_addr_in,
111
    src_e_addr_in,
112
    destport_in
113
);
114
 
115
    function integer log2;
116
        input integer number; begin
117
           log2=(number <=1) ? 1: 0;
118
           while(2**log2<number) begin
119
              log2=log2+1;
120
           end
121
        end
122
    endfunction // log2 
123
 
124
 
125
    input reset,clk;
126
    input hdr_flg_in , flit_in_wr;
127
    input [V-1 : 0] vc_num_in, flit_is_tail,  ivc_num_getting_sw_grant;
128
    input [RAw-1 : 0] current_r_addr;
129
    input [EAw-1 : 0] dest_e_addr_in,src_e_addr_in;
130
    input [DSTPw-1 : 0]  destport_in;
131
 
132
    localparam
133
      NX = T1,
134
      NY = T2,
135
      RXw = log2(NX),    // number of node in x axis
136
      RYw = log2(NY),
137
      EXw = log2(NX),    // number of node in x axis
138
      EYw = log2(NY);   // number of node in y axis
139
 
140
 
141
    wire [RXw-1 : 0] current_x;
142
    wire [EXw-1 : 0] x_dst_in,x_src_in;
143
    wire [RYw-1 : 0] current_y;
144
    wire [EYw-1 : 0] y_dst_in,y_src_in;
145
 
146
    mesh_tori_router_addr_decode #(
147
        .TOPOLOGY(TOPOLOGY),
148
        .T1(T1),
149
        .T2(T2),
150
        .T3(T3),
151
        .RAw(RAw)
152
    )
153
    r_addr_decode
154
    (
155
        .r_addr(current_r_addr),
156
        .rx(current_x),
157
        .ry(current_y),
158
        .valid()
159
    );
160
 
161
    mesh_tori_endp_addr_decode #(
162
        .TOPOLOGY(TOPOLOGY),
163
        .T1(T1),
164
        .T2(T2),
165
        .T3(T3),
166
        .EAw(EAw)
167
    )
168
    dst_addr_decode
169
    (
170
        .e_addr(dest_e_addr_in),
171
        .ex(x_dst_in),
172
        .ey(y_dst_in),
173
        .el( ),
174
        .valid()
175
    );
176
 
177
    mesh_tori_endp_addr_decode #(
178
        .TOPOLOGY(TOPOLOGY),
179
        .T1(T1),
180
        .T2(T2),
181
        .T3(T3),
182
        .EAw(EAw)
183
    )
184
    src_addr_decode
185
    (
186
        .e_addr(src_e_addr_in),
187
        .ex(x_src_in),
188
        .ey(y_src_in),
189
        .el( ),
190
        .valid()
191
    );
192
 
193
 
194
localparam
195
    LOCAL =  0,
196
    NORTH =  2,
197
    SOUTH =  4;
198
 // synthesis translate_off 
199
generate
200
 
201
/* verilator lint_off WIDTH */
202
if(ROUTE_TYPE == "DETERMINISTIC")begin :dtrmn
203
/* verilator lint_on WIDTH */
204
 
205
 
206
    always@( posedge clk)begin
207
        if(flit_in_wr & hdr_flg_in )
208
               if( destport_in[1:0]==2'b11) begin
209
                    $display ( "%t\t  ERROR: destport port %x is illegal for determistic routing.  %m",$time,destport_in );
210
                    $finish;
211
               end
212
        end//if
213
    end//always
214
 
215
 
216
/* verilator lint_off WIDTH */
217
if(ROUTE_TYPE == "FULL_ADAPTIVE")begin :full_adpt
218
/* verilator lint_on WIDTH */
219
 
220
        reg [V-1 : 0] not_empty;
221
        always@( posedge clk or posedge reset) begin
222
            if(reset) begin
223
               not_empty <=0;
224
            end else begin
225
               if(hdr_flg_in & flit_in_wr) begin
226
                    not_empty <= not_empty | vc_num_in;
227
                    if( ((AVC_ATOMIC_EN==1)&& (SW_LOC!= LOCAL)) || (SW_LOC== NORTH) || (SW_LOC== SOUTH) )begin
228
                        if((vc_num_in  & ~ESCAP_VC_MASK)>0) begin // adaptive VCs
229
                            if( (not_empty & vc_num_in)>0) $display("%t  :Error AVC allocated nonatomicly in %d port %m",$time,SW_LOC);
230
                        end
231
                    end//( AVC_ATOMIC_EN || SW_LOC== NORTH || SW_LOC== SOUTH )
232
 
233
                        if((vc_num_in  & ESCAP_VC_MASK)>0 && (SW_LOC== SOUTH || SW_LOC== NORTH) )  begin // escape vc
234
                            // if (a & b) $display("%t  :Error EVC allocation violate subfunction routing rules %m",$time);
235
                            if ((current_x - x_dst_in) !=0 && (current_y- y_dst_in) !=0) $display("%t  :Error EVC allocation violate subfunction routing rules src_x=%d src_y=%d dst_x%d   dst_y=%d %m",$time,x_src_in, y_src_in, x_dst_in,y_dst_in);
236
                        end
237
 
238
                end//hdr_wr_in
239
                if((flit_is_tail & ivc_num_getting_sw_grant)>0)begin
240
                    not_empty <= not_empty & ~ivc_num_getting_sw_grant;
241
                end//tail wr out
242
            end//reset
243
        end//always
244
    end //SW_LOC
245
 
246
 
247
    /* verilator lint_off WIDTH */
248
    if(TOPOLOGY=="MESH")begin :mesh
249
    /* verilator lint_on WIDTH */
250
        wire  [EXw-1 : 0] low_x,high_x;
251
        wire  [EYw-1 : 0] low_y,high_y;
252
 
253
 
254
 
255
        assign low_x = (x_src_in < x_dst_in)?  x_src_in : x_dst_in;
256
        assign low_y = (y_src_in < y_dst_in)?  y_src_in : y_dst_in;
257
        assign high_x = (x_src_in < x_dst_in)?  x_dst_in : x_src_in;
258
        assign high_y = (y_src_in < y_dst_in)?  y_dst_in : y_src_in;
259
 
260
 
261
        always@( posedge clk)begin
262
               if((current_x <low_x) | (current_x > high_x) | (current_y <low_y) | (current_y > high_y) )
263
                    if(flit_in_wr & hdr_flg_in )begin
264
                        $display ( "%t\t  ERROR: non_minimal routing %m",$time );
265
                        $finish;
266
                    end
267
 
268
        end
269
 
270
 
271
    end// mesh  
272
  endgenerate
273
 
274
  // synthesis translate_on
275
 
276
  endmodule
277
 
278
 
279
 module debug_mesh_edges #(
280
    parameter T1=2,
281
    parameter T2=2,
282
    parameter T3=3,
283
    parameter T4=3,
284
    parameter RAw=4,
285
    parameter P=5
286
 )(
287
    clk,
288
    current_r_addr,
289
    flit_out_wr_all
290
 );
291
 
292
    function integer log2;
293
        input integer number; begin
294
           log2=(number <=1) ? 1: 0;
295
           while(2**log2<number) begin
296
              log2=log2+1;
297
           end
298
        end
299
    endfunction // log2 
300
 
301
    input clk;
302
    input  [RAw-1 :  0]  current_r_addr;
303
    input  [P-1 :  0]  flit_out_wr_all;
304
 
305
    localparam
306
        RXw = log2(T1),    // number of node in x axis
307
        RYw = log2(T2);    // number of node in y axis
308
 
309
 
310
  wire [RXw-1 : 0] current_rx;
311
  wire [RYw-1 : 0] current_ry;
312
 
313
    mesh_tori_router_addr_decode #(
314
        .TOPOLOGY("MESH"),
315
        .T1(T1),
316
        .T2(T2),
317
        .T3(T3),
318
        .RAw(RAw)
319
    )
320
    addr_decode
321
    (
322
        .r_addr(current_r_addr),
323
        .rx(current_rx),
324
        .ry(current_ry),
325
        .valid()
326
    );
327
 
328
 
329
    localparam
330
        EAST = 1,
331
        NORTH = 2,
332
        WEST = 3,
333
        SOUTH = 4;
334
  // synthesis translate_off 
335
        always @(posedge clk) begin
336
        /* verilator lint_off WIDTH */
337
                if(current_rx == {RXw{1'b0}}         && flit_out_wr_all[WEST]) $display ( "%t\t  ERROR: a packet is going to the WEST in a router located in first column in mesh topology %m",$time );
338
                if(current_rx == T1-1     && flit_out_wr_all[EAST]) $display ( "%t\t   ERROR: a packet is going to the EAST in a router located in last column in mesh topology %m",$time );
339
                if(current_ry == {RYw{1'b0}}         && flit_out_wr_all[NORTH])$display ( "%t\t  ERROR: a packet is going to the NORTH in a router located in first row in mesh topology %m",$time );
340
                if(current_ry == T2-1    && flit_out_wr_all[SOUTH])$display ( "%t\t  ERROR: a packet is going to the SOUTH in a router located in last row in mesh topology %m",$time);
341
      /* verilator lint_on WIDTH */
342
        end//always
343
  // synthesis translate_on  
344
endmodule
345
 
346
 
347
/*******************
348
 *
349
 * *****************/
350
 
351
 module check_destination_addr #(
352
    parameter TOPOLOGY = "MESH",
353
    parameter T1=2,
354
    parameter T2=2,
355
    parameter T3=2,
356
    parameter T4=2,
357
    parameter EAw=2,
358
    parameter SELF_LOOP_EN="NO"
359
 )(
360
     dest_is_valid,
361
     dest_e_addr,
362
     current_e_addr
363
 );
364
 
365
    input [EAw-1 : 0]  dest_e_addr,current_e_addr;
366
    output dest_is_valid;
367
 
368
    // general rules
369
    /* verilator lint_off WIDTH */
370
    wire valid_dst  = (SELF_LOOP_EN   == "NO")? dest_e_addr  !=  current_e_addr : 1'b1;
371
    /* verilator lint_on WIDTH */
372
    wire valid;
373
    generate
374
    /* verilator lint_off WIDTH */
375
    if(TOPOLOGY=="MESH" || TOPOLOGY == "TORUS" || TOPOLOGY=="RING" || TOPOLOGY == "LINE") begin : mesh
376
   /* verilator lint_on WIDTH */
377
        mesh_tori_endp_addr_decode #(
378
                .TOPOLOGY(TOPOLOGY),
379
                .T1(T1),
380
                .T2(T2),
381
                .T3(T3),
382
                .EAw(EAw)
383
        )
384
        mesh_tori_endp_addr_decode(
385
                .e_addr(dest_e_addr),
386
                .ex(),
387
                .ey(),
388
                .el(),
389
                .valid(valid)
390
        );
391
       assign  dest_is_valid = valid_dst & valid;
392
 
393
    end else begin : tree
394
        assign  dest_is_valid = valid_dst;
395
    end
396
    endgenerate
397
 
398
 endmodule
399
 
400
 
401
 
402
module  endp_addr_encoder #(
403
    parameter TOPOLOGY ="MESH",
404
    parameter T1=4,
405
    parameter T2=4,
406
    parameter T3=4,
407
    parameter EAw=4,
408
    parameter NE=16
409
)
410
(
411
    id,
412
    code
413
 );
414
 
415
    function integer log2;
416
      input integer number; begin
417
         log2=(number <=1) ? 1: 0;
418
         while(2**log2<number) begin
419
            log2=log2+1;
420
         end
421
      end
422
    endfunction // log2 
423
 
424
    localparam NEw= log2(NE);
425
 
426
     input [NEw-1 :0] id;
427
     output [EAw-1 : 0] code;
428
 
429
     generate
430
     /* verilator lint_off WIDTH */
431
     if(TOPOLOGY == "FATTREE" || TOPOLOGY == "TREE" ) begin : tree
432
     /* verilator lint_on WIDTH */
433
       fattree_addr_encoder #(
434
        .K(T1),
435
        .L(T2)
436
       )
437
       addr_encoder
438
       (
439
        .id(id),
440
        .code(code)
441
       );
442
 
443
     /* verilator lint_off WIDTH */
444
     end else if  (TOPOLOGY == "MESH" || TOPOLOGY == "TORUS" || TOPOLOGY == "RING" || TOPOLOGY == "LINE") begin :tori
445
     /* verilator lint_on WIDTH */
446
        mesh_tori_addr_encoder #(
447
            .NX(T1),
448
            .NY(T2),
449
            .NL(T3),
450
            .NE(NE),
451
            .EAw(EAw),
452
            .TOPOLOGY(TOPOLOGY)
453
        )
454
        addr_encoder
455
        (
456
            .id(id),
457
            .code(code)
458
        );
459
     end else if (TOPOLOGY == "FMESH") begin :fmesh
460
        fmesh_addr_encoder #(
461
            .NX(T1),
462
            .NY(T2),
463
            .NL(T3),
464
            .NE(NE),
465
            .EAw(EAw)
466
        )
467
        addr_encoder
468
        (
469
        .id(id),
470
        .code(code)
471
        );
472
 
473
     end else begin :custom
474
 
475
        assign code =id;
476
 
477
     end
478
     endgenerate
479
endmodule
480
 
481
 
482
module endp_addr_decoder  #(
483
        parameter TOPOLOGY ="MESH",
484
        parameter T1=4,
485
        parameter T2=4,
486
        parameter T3=4,
487
        parameter EAw=4,
488
        parameter NE=16
489
        )
490
        (
491
        id,
492
        code
493
        );
494
 
495
    function integer log2;
496
        input integer number; begin
497
            log2=(number <=1) ? 1: 0;
498
            while(2**log2<number) begin
499
                log2=log2+1;
500
            end
501
        end
502
    endfunction // log2 
503
 
504
    localparam NEw= log2(NE);
505
 
506
    output [NEw-1 :0] id;
507
    input  [EAw-1 : 0] code;
508
 
509
    generate
510
    /* verilator lint_off WIDTH */
511
    if(TOPOLOGY == "FATTREE" || TOPOLOGY == "TREE" ) begin : tree
512
    /* verilator lint_on WIDTH */
513
        fattree_addr_decoder #(
514
                .K(T1),
515
                .L(T2)
516
 
517
            )decoder(
518
                .id(id),
519
                .code(code)
520
            );
521
    /* verilator lint_off WIDTH */
522
    end else if  (TOPOLOGY == "MESH" || TOPOLOGY == "TORUS" || TOPOLOGY == "RING" || TOPOLOGY == "LINE") begin :tori
523
    /* verilator lint_on WIDTH */
524
        mesh_tori_addr_coder #(
525
            .NX    (T1   ),
526
            .NY    (T2   ),
527
            .NL    (T3   ),
528
            .NE    (NE   ),
529
            .EAw   (EAw  )
530
            ) addr_coder (
531
            .id    (id   ),
532
            .code  (code ));
533
     end else if (TOPOLOGY == "FMESH") begin :fmesh
534
        fmesh_addr_coder #(
535
            .NX(T1),
536
            .NY(T2),
537
            .NL(T3),
538
            .NE(NE),
539
            .EAw(EAw)
540
        )
541
        addr_coder
542
        (
543
        .id(id),
544
        .code(code)
545
        );
546
 
547
    end else begin :custom
548
 
549
        assign id = code;
550
 
551
    end
552
    endgenerate
553
endmodule
554
 
555
 

powered by: WebSVN 2.1.0

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