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/] [main_comp.v] - Diff between revs 48 and 54

Only display areas with differences | Details | Blame | View Log

Rev 48 Rev 54
 `timescale  1ns/1ps
 `timescale  1ns/1ps
 
 
 
 
/**********************************************************************
/**********************************************************************
**      File:  main_comp.v
**      File:  main_comp.v
**
**
**      Copyright (C) 2014-2017  Alireza Monemi
**      Copyright (C) 2014-2017  Alireza Monemi
**
**
**      This file is part of ProNoC
**      This file is part of ProNoC
**
**
**      ProNoC ( stands for Prototype Network-on-chip)  is free software:
**      ProNoC ( stands for Prototype Network-on-chip)  is free software:
**      you can redistribute it and/or modify it under the terms of the GNU
**      you can redistribute it and/or modify it under the terms of the GNU
**      Lesser General Public License as published by the Free Software Foundation,
**      Lesser General Public License as published by the Free Software Foundation,
**      either version 2 of the License, or (at your option) any later version.
**      either version 2 of the License, or (at your option) any later version.
**
**
**      ProNoC is distributed in the hope that it will be useful, but WITHOUT
**      ProNoC is distributed in the hope that it will be useful, but WITHOUT
**      ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
**      ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
**      or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU Lesser General
**      or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU Lesser General
**      Public License for more details.
**      Public License for more details.
**
**
**      You should have received a copy of the GNU Lesser General Public
**      You should have received a copy of the GNU Lesser General Public
**      License along with ProNoC. If not, see <http:**www.gnu.org/licenses/>.
**      License along with ProNoC. If not, see <http:**www.gnu.org/licenses/>.
**
**
**
**
**      Description:
**      Description:
**      This file contains several general RTL modules such as
**      This file contains several general RTL modules such as
**      different types of multiplexors, converters and counters ...
**      different types of multiplexors, converters and counters ...
**
**
**************************************************************/
**************************************************************/
 
`include "pronoc_def.v"
 
 
 
module pronoc_register
 
       #(
 
        parameter W=1,
 
        parameter  RESET_TO={W{1'b0}}
 
 
 
        )(
 
            input [W-1:0] in,
 
            input reset,
 
            input clk,
 
            output [W-1:0] out
 
        );
 
 
 
    pronoc_register_reset_init #(
 
        .W(W)
 
    )reg1(
 
        .in(in),
 
        .reset(reset),
 
        .clk(clk),
 
        .out(out),
 
        .reset_to(RESET_TO[W-1 : 0])
 
    );
 
endmodule
 
 
 
 
 
 
 
module pronoc_register_reset_init
 
        #(
 
        parameter W=1
 
        )(
 
        input [W-1:0] in,
 
        input reset,
 
        input clk,
 
        output reg [W-1:0] out,
 
        input [W-1 : 0] reset_to
 
        );
 
 
 
 
 
        always @ (`pronoc_clk_reset_edge )begin
 
            if(`pronoc_reset)   out<=reset_to;
 
            else        out<=in;
 
        end
 
 
 
endmodule
 
 
 
 
 
module pronoc_register_reset_init_ld_en
 
        #(
 
        parameter W=1
 
        )(
 
        input [W-1:0] in,
 
        input reset,
 
        input clk,
 
        input ld,
 
        output reg [W-1:0] out,
 
        input [W-1 : 0] reset_to
 
        );
 
 
 
        always @ (`pronoc_clk_reset_edge )begin
 
            if(`pronoc_reset)   out<=reset_to;
 
            else  if(ld)      out<=in;
 
        end
 
endmodule
 
 
 
 
 
module pronoc_register_ld_en
 
       #(
 
        parameter W=1,
 
        parameter  RESET_TO={W{1'b0}}
 
 
 
        )(
 
            input [W-1:0] in,
 
            input reset,
 
            input clk,
 
            input ld,
 
            output [W-1:0] out
 
        );
 
 
 
    pronoc_register_reset_init_ld_en  #(
 
        .W(W)
 
    )reg1(
 
        .in(in),
 
        .reset(reset),
 
        .clk(clk),
 
        .ld(ld),
 
        .out(out),
 
        .reset_to(RESET_TO[W-1 : 0])
 
    );
 
endmodule
 
 
 
 
 
 
/*********************************
/*********************************
 
 
 
 
 
 
    multiplexer
    multiplexer
 
 
 
 
 
 
********************************/
********************************/
 
 
module one_hot_mux #(
module one_hot_mux #(
        parameter   IN_WIDTH      = 20,
        parameter   IN_WIDTH      = 20,
        parameter   SEL_WIDTH =   5,
        parameter   SEL_WIDTH =   5,
        parameter   OUT_WIDTH = IN_WIDTH/SEL_WIDTH
        parameter   OUT_WIDTH = IN_WIDTH/SEL_WIDTH
 
 
    )
    )
    (
    (
        input [IN_WIDTH-1       :0] mux_in,
        input [IN_WIDTH-1       :0] mux_in,
        output[OUT_WIDTH-1  :0] mux_out,
        output[OUT_WIDTH-1  :0] mux_out,
        input[SEL_WIDTH-1   :0] sel
        input[SEL_WIDTH-1   :0] sel
 
 
    );
    );
 
 
    wire [IN_WIDTH-1    :0] mask;
    wire [IN_WIDTH-1    :0] mask;
    wire [IN_WIDTH-1    :0] masked_mux_in;
    wire [IN_WIDTH-1    :0] masked_mux_in;
    wire [SEL_WIDTH-1:0]    mux_out_gen [OUT_WIDTH-1:0];
    wire [SEL_WIDTH-1:0]    mux_out_gen [OUT_WIDTH-1:0];
 
 
    genvar i,j;
    genvar i,j;
 
 
    //first selector masking
    //first selector masking
    generate    // first_mask = {sel[0],sel[0],sel[0],....,sel[n],sel[n],sel[n]}
    generate    // first_mask = {sel[0],sel[0],sel[0],....,sel[n],sel[n],sel[n]}
        for(i=0; i<SEL_WIDTH; i=i+1) begin : mask_loop
        for(i=0; i<SEL_WIDTH; i=i+1) begin : mask_loop
            assign mask[(i+1)*OUT_WIDTH-1 : (i)*OUT_WIDTH]  =   {OUT_WIDTH{sel[i]} };
            assign mask[(i+1)*OUT_WIDTH-1 : (i)*OUT_WIDTH]  =   {OUT_WIDTH{sel[i]} };
        end
        end
 
 
        assign masked_mux_in    = mux_in & mask;
        assign masked_mux_in    = mux_in & mask;
 
 
        for(i=0; i<OUT_WIDTH; i=i+1) begin : lp1
        for(i=0; i<OUT_WIDTH; i=i+1) begin : lp1
            for(j=0; j<SEL_WIDTH; j=j+1) begin : lp2
            for(j=0; j<SEL_WIDTH; j=j+1) begin : lp2
                assign mux_out_gen [i][j]   =   masked_mux_in[i+OUT_WIDTH*j];
                assign mux_out_gen [i][j]   =   masked_mux_in[i+OUT_WIDTH*j];
            end
            end
            assign mux_out[i] = | mux_out_gen [i];
            assign mux_out[i] = | mux_out_gen [i];
        end
        end
    endgenerate
    endgenerate
 
 
endmodule
endmodule
 
 
 
 
 
 
 
 
 
 
 
 
/******************************
/******************************
 
 
    One hot demultiplexer
    One hot demultiplexer
 
 
****************************/
****************************/
 
 
 
 
module one_hot_demux    #(
module one_hot_demux    #(
        parameter IN_WIDTH=5,
        parameter IN_WIDTH=5,
        parameter SEL_WIDTH=4,
        parameter SEL_WIDTH=4,
        parameter OUT_WIDTH=IN_WIDTH*SEL_WIDTH
        parameter OUT_WIDTH=IN_WIDTH*SEL_WIDTH
    )
    )
    (
    (
        input   [SEL_WIDTH-1        :   0] demux_sel,//selectore
        input   [SEL_WIDTH-1        :   0] demux_sel,//selectore
        input   [IN_WIDTH-1         :   0] demux_in,//repeated
        input   [IN_WIDTH-1         :   0] demux_in,//repeated
        output  [OUT_WIDTH-1        :   0]  demux_out
        output  [OUT_WIDTH-1        :   0]  demux_out
    );
    );
 
 
    genvar i,j;
    genvar i,j;
    generate
    generate
    for(i=0;i<SEL_WIDTH;i=i+1)begin :loop1
    for(i=0;i<SEL_WIDTH;i=i+1)begin :loop1
        for(j=0;j<IN_WIDTH;j=j+1)begin :loop2
        for(j=0;j<IN_WIDTH;j=j+1)begin :loop2
                assign demux_out[i*IN_WIDTH+j] =     demux_sel[i]   &   demux_in[j];
                assign demux_out[i*IN_WIDTH+j] =     demux_sel[i]   &   demux_in[j];
        end//for j
        end//for j
    end//for i
    end//for i
    endgenerate
    endgenerate
 
 
 
 
 
 
endmodule
endmodule
 
 
/**************************
/**************************
 
 
 
 
    custom_or
    custom_or
 
 
 
 
***************************/
***************************/
 
 
 
 
module custom_or #(
module custom_or #(
    parameter IN_NUM        =   4,
    parameter IN_NUM        =   4,
    parameter OUT_WIDTH =   5
    parameter OUT_WIDTH =   5
)(
)(
    or_in,
    or_in,
    or_out
    or_out
);
);
 
 
    localparam IN_WIDTH  = IN_NUM*OUT_WIDTH;
    localparam IN_WIDTH  = IN_NUM*OUT_WIDTH;
 
 
    input [IN_WIDTH-1       :   0]  or_in;
    input [IN_WIDTH-1       :   0]  or_in;
    output[OUT_WIDTH-1      :   0]  or_out;
    output[OUT_WIDTH-1      :   0]  or_out;
 
 
    wire        [IN_NUM-1       :   0] in_sep   [OUT_WIDTH-1        :   0];
    wire        [IN_NUM-1       :   0] in_sep   [OUT_WIDTH-1        :   0];
    genvar i,j;
    genvar i,j;
    generate
    generate
    for (i=0;i<OUT_WIDTH;i=i+1) begin: sep_loop
    for (i=0;i<OUT_WIDTH;i=i+1) begin: sep_loop
        for (j=0;j<IN_NUM;j=j+1) begin: sep_loop
        for (j=0;j<IN_NUM;j=j+1) begin: sep_loop
            assign in_sep[i][j]= or_in [j*OUT_WIDTH+i];
            assign in_sep[i][j]= or_in [j*OUT_WIDTH+i];
        end
        end
        assign or_out[i]= |in_sep[i];
        assign or_out[i]= |in_sep[i];
    end
    end
    endgenerate
    endgenerate
 
 
 
 
endmodule
endmodule
 
 
 
 
/*****************************************
/*****************************************
 
 
sum the output of all ports except the output of  port itself
sum the output of all ports except the output of  port itself
 
 
 
 
****************************************/
****************************************/
 
 
 
 
module outport_sum #(
module outport_sum #(
    parameter IN_ARRAY_WIDTH =10,
    parameter IN_ARRAY_WIDTH =10,
    parameter IN_NUM     =5,
    parameter IN_NUM     =5,
    parameter IN_WIDTH  =   IN_ARRAY_WIDTH/IN_NUM,
    parameter IN_WIDTH  =   IN_ARRAY_WIDTH/IN_NUM,
    parameter CMP_VAL   =   IN_WIDTH/(IN_NUM-1),
    parameter CMP_VAL   =   IN_WIDTH/(IN_NUM-1),
    parameter OUT_WIDTH = (IN_ARRAY_WIDTH/IN_NUM)+CMP_VAL
    parameter OUT_WIDTH = (IN_ARRAY_WIDTH/IN_NUM)+CMP_VAL
 
 
    )
    )
    (
    (
    input   [IN_ARRAY_WIDTH-1       :   0]  in,
    input   [IN_ARRAY_WIDTH-1       :   0]  in,
    output  [OUT_WIDTH-1                :   0]  out
    output  [OUT_WIDTH-1                :   0]  out
);
);
 
 
    genvar i,j;
    genvar i,j;
    wire [IN_WIDTH-1        :   0]      in_sep  [IN_NUM-1       :   0];
    wire [IN_WIDTH-1        :   0]      in_sep  [IN_NUM-1       :   0];
    wire [IN_NUM-2          :   0]      gen         [OUT_WIDTH-1    :   0];
    wire [IN_NUM-2          :   0]      gen         [OUT_WIDTH-1    :   0];
    generate
    generate
        for(i=0;i<IN_NUM; i=i+1      ) begin : lp
        for(i=0;i<IN_NUM; i=i+1      ) begin : lp
            assign in_sep[i]  = in[(IN_WIDTH*(i+1))-1   : IN_WIDTH*i];
            assign in_sep[i]  = in[(IN_WIDTH*(i+1))-1   : IN_WIDTH*i];
        end
        end
        for (j=0;j<IN_NUM-1;j=j+1)begin : loop1
        for (j=0;j<IN_NUM-1;j=j+1)begin : loop1
                for(i=0;i<OUT_WIDTH; i=i+1  )begin : loop2
                for(i=0;i<OUT_WIDTH; i=i+1  )begin : loop2
                    if(i>=CMP_VAL*(j+1))begin : if1
                    if(i>=CMP_VAL*(j+1))begin : if1
                        assign gen[i][j] = in_sep[j][i-CMP_VAL];
                        assign gen[i][j] = in_sep[j][i-CMP_VAL];
                    end
                    end
                    else if( i< CMP_VAL*(j+1) && i>= (CMP_VAL*j)) begin :if2
                    else if( i< CMP_VAL*(j+1) && i>= (CMP_VAL*j)) begin :if2
                        assign gen[i][j] = in_sep[IN_NUM-1][i];
                        assign gen[i][j] = in_sep[IN_NUM-1][i];
                    end
                    end
                    else    begin :els
                    else    begin :els
                        assign gen[i][j] = in_sep[j][i];
                        assign gen[i][j] = in_sep[j][i];
                    end
                    end
                end// for i
                end// for i
            end// for j
            end// for j
        for(i=0;i<OUT_WIDTH; i=i+1       ) begin : lp2
        for(i=0;i<OUT_WIDTH; i=i+1       ) begin : lp2
            assign out[i]               = |  gen[i];
            assign out[i]               = |  gen[i];
        end
        end
    endgenerate
    endgenerate
endmodule
endmodule
 
 
/***********************************
/***********************************
 
 
        module bin_to_one_hot
        module bin_to_one_hot
 
 
 
 
************************************/
************************************/
 
 
 
 
module bin_to_one_hot #(
module bin_to_one_hot #(
    parameter BIN_WIDTH     =   2,
    parameter BIN_WIDTH     =   2,
    parameter ONE_HOT_WIDTH =   2**BIN_WIDTH
    parameter ONE_HOT_WIDTH =   2**BIN_WIDTH
 
 
)
)
(
(
    input   [BIN_WIDTH-1            :   0]  bin_code,
    input   [BIN_WIDTH-1            :   0]  bin_code,
    output  [ONE_HOT_WIDTH-1        :   0] one_hot_code
    output  [ONE_HOT_WIDTH-1        :   0] one_hot_code
 );
 );
 
 
    genvar i;
    genvar i;
    generate
    generate
        for(i=0; i<ONE_HOT_WIDTH; i=i+1) begin :one_hot_gen_loop
        for(i=0; i<ONE_HOT_WIDTH; i=i+1) begin :one_hot_gen_loop
                assign one_hot_code[i] = (bin_code == i[BIN_WIDTH-1         :   0]);
                assign one_hot_code[i] = (bin_code == i[BIN_WIDTH-1         :   0]);
        end
        end
    endgenerate
    endgenerate
 
 
endmodule
endmodule
 
 
/***********************************
/***********************************
 
 
        one_hot_to_binary
        one_hot_to_binary
 
 
************************************/
************************************/
 
 
 
 
 
 
module one_hot_to_bin #(
module one_hot_to_bin #(
    parameter ONE_HOT_WIDTH =   4,
    parameter ONE_HOT_WIDTH =   4,
    parameter BIN_WIDTH     =  (ONE_HOT_WIDTH>1)? log2(ONE_HOT_WIDTH):1
    parameter BIN_WIDTH     =  (ONE_HOT_WIDTH>1)? log2(ONE_HOT_WIDTH):1
)
)
(
(
    input   [ONE_HOT_WIDTH-1        :   0] one_hot_code,
    input   [ONE_HOT_WIDTH-1        :   0] one_hot_code,
    output  [BIN_WIDTH-1            :   0]  bin_code
    output  [BIN_WIDTH-1            :   0]  bin_code
 
 
);
);
 
 
 
 
    function integer log2;
    function integer log2;
      input integer number; begin
      input integer number; begin
         log2=(number <=1) ? 1: 0;
         log2=(number <=1) ? 1: 0;
         while(2**log2<number) begin
         while(2**log2<number) begin
            log2=log2+1;
            log2=log2+1;
         end
         end
      end
      end
    endfunction // log2 
    endfunction // log2 
 
 
localparam MUX_IN_WIDTH =   BIN_WIDTH* ONE_HOT_WIDTH;
localparam MUX_IN_WIDTH =   BIN_WIDTH* ONE_HOT_WIDTH;
 
 
wire [MUX_IN_WIDTH-1        :   0]  bin_temp ;
wire [MUX_IN_WIDTH-1        :   0]  bin_temp ;
 
 
genvar i;
genvar i;
generate
generate
    if(ONE_HOT_WIDTH>1)begin :if1
    if(ONE_HOT_WIDTH>1)begin :if1
        for(i=0; i<ONE_HOT_WIDTH; i=i+1) begin :mux_in_gen_loop
        for(i=0; i<ONE_HOT_WIDTH; i=i+1) begin :mux_in_gen_loop
            assign bin_temp[(i+1)*BIN_WIDTH-1 : i*BIN_WIDTH] =  i[BIN_WIDTH-1:0];
            assign bin_temp[(i+1)*BIN_WIDTH-1 : i*BIN_WIDTH] =  i[BIN_WIDTH-1:0];
        end
        end
 
 
 
 
        one_hot_mux #(
        one_hot_mux #(
            .IN_WIDTH   (MUX_IN_WIDTH),
            .IN_WIDTH   (MUX_IN_WIDTH),
            .SEL_WIDTH  (ONE_HOT_WIDTH)
            .SEL_WIDTH  (ONE_HOT_WIDTH)
 
 
        )
        )
        one_hot_to_bcd_mux
        one_hot_to_bcd_mux
        (
        (
            .mux_in     (bin_temp),
            .mux_in     (bin_temp),
            .mux_out        (bin_code),
            .mux_out        (bin_code),
            .sel            (one_hot_code)
            .sel            (one_hot_code)
 
 
        );
        );
     end else begin :els
     end else begin :els
       // assign  bin_code = one_hot_code;
       // assign  bin_code = one_hot_code;
       assign  bin_code = 1'b0;
       assign  bin_code = 1'b0;
     end
     end
 
 
endgenerate
endgenerate
 
 
endmodule
endmodule
 
 
 
 
 
 
/****************************************
/****************************************
 
 
            binary_mux
            binary_mux
 
 
***************************************/
***************************************/
 
 
module binary_mux #(
module binary_mux #(
        parameter   IN_WIDTH         =   20,
        parameter   IN_WIDTH         =   20,
        parameter   OUT_WIDTH       =   5
        parameter   OUT_WIDTH       =   5
    )
    )
    (
    (
        mux_in,
        mux_in,
        mux_out,
        mux_out,
        sel
        sel
 
 
    );
    );
 
 
 
 
    function integer log2;
    function integer log2;
      input integer number; begin
      input integer number; begin
         log2=(number <=1) ? 1: 0;
         log2=(number <=1) ? 1: 0;
         while(2**log2<number) begin
         while(2**log2<number) begin
            log2=log2+1;
            log2=log2+1;
         end
         end
      end
      end
    endfunction // log2 
    endfunction // log2 
 
 
     localparam  IN_NUM          =   IN_WIDTH/OUT_WIDTH,
     localparam  IN_NUM          =   IN_WIDTH/OUT_WIDTH,
                 SEL_WIDTH_BIN   = (IN_NUM>1)?  log2(IN_NUM): 1;
                 SEL_WIDTH_BIN   = (IN_NUM>1)?  log2(IN_NUM): 1;
 
 
 
 
    input   [IN_WIDTH-1         :0] mux_in;
    input   [IN_WIDTH-1         :0] mux_in;
    output  [OUT_WIDTH-1        :0] mux_out;
    output  [OUT_WIDTH-1        :0] mux_out;
    input   [SEL_WIDTH_BIN-1    :0] sel;
    input   [SEL_WIDTH_BIN-1    :0] sel;
    genvar i;
    genvar i;
 
 
 
 
        generate
        generate
                if(IN_NUM>1) begin :if1
                if(IN_NUM>1) begin :if1
                        wire [OUT_WIDTH-1       :0] mux_in_2d [IN_NUM -1    :0];
                        wire [OUT_WIDTH-1       :0] mux_in_2d [IN_NUM -1    :0];
                        for (i=0; i< IN_NUM; i=i+1) begin : loop
                        for (i=0; i< IN_NUM; i=i+1) begin : loop
                                assign mux_in_2d[i] =mux_in[((i+1)*OUT_WIDTH)-1 :   i*OUT_WIDTH];
                                assign mux_in_2d[i] =mux_in[((i+1)*OUT_WIDTH)-1 :   i*OUT_WIDTH];
                        end
                        end
                        assign mux_out = mux_in_2d[sel];
                        assign mux_out = mux_in_2d[sel];
                end else  begin :els
                end else  begin :els
                        assign mux_out = mux_in;
                        assign mux_out = mux_in;
                end
                end
        endgenerate
        endgenerate
 
 
endmodule
endmodule
 
 
 
 
 
 
module  accumulator #(
module  accumulator #(
    parameter INw= 20,
    parameter INw= 20,
    parameter OUTw=4,
    parameter OUTw=4,
    parameter NUM =5
    parameter NUM =5
)
)
(
(
    in_all,
    in_all,
    out
    out
);
);
 
 
    function integer log2;
    function integer log2;
      input integer number; begin
      input integer number; begin
         log2=(number <=1) ? 1: 0;
         log2=(number <=1) ? 1: 0;
         while(2**log2<number) begin
         while(2**log2<number) begin
            log2=log2+1;
            log2=log2+1;
         end
         end
      end
      end
    endfunction // log2 
    endfunction // log2 
 
 
    localparam N= INw/NUM,
    localparam N= INw/NUM,
               SUMw= log2(NUM)+N;
               SUMw= log2(NUM)+N;
    input [INw-1  :   0] in_all;
    input [INw-1  :   0] in_all;
    output[OUTw-1 :   0] out;
    output[OUTw-1 :   0] out;
 
 
    wire [N-1   :   0] in [NUM-1    :   0];
    wire [N-1   :   0] in [NUM-1    :   0];
    reg [SUMw-1 :   0] sum;
    reg [SUMw-1 :   0] sum;
 
 
 
 
    genvar i;
    genvar i;
    generate
    generate
    for (i=0; i<NUM; i=i+1)begin : lp
    for (i=0; i<NUM; i=i+1)begin : lp
        assign in[i] = in_all[(i+1)*N-1 : i*N];
        assign in[i] = in_all[(i+1)*N-1 : i*N];
    end
    end
 
 
    if(  SUMw ==  OUTw) begin :  equal
    if(  SUMw ==  OUTw) begin :  equal
        assign out = sum;
        assign out = sum;
    end else if(SUMw >  OUTw) begin : bigger
    end else if(SUMw >  OUTw) begin : bigger
        assign out = (sum[SUMw-1 : OUTw] > 0 ) ? {OUTw{1'b1}} : sum[OUTw-1  :   0] ;
        assign out = (sum[SUMw-1 : OUTw] > 0 ) ? {OUTw{1'b1}} : sum[OUTw-1  :   0] ;
    end else begin : less
    end else begin : less
          assign out = {{(OUTw-SUMw){1'b0}},  sum} ;
          assign out = {{(OUTw-SUMw){1'b0}},  sum} ;
    end
    end
 
 
 
 
 
 
    endgenerate
    endgenerate
 
 
  // This is supposed to be synyhesized as "sum=in[0]+in[1]+...in[Num-1]"; 
  // This is supposed to be synyhesized as "sum=in[0]+in[1]+...in[Num-1]"; 
  // It works with Quartus, Verilator and Modelsim compilers  
  // It works with Quartus, Verilator and Modelsim compilers  
    integer k;
    integer k;
    always @(*)begin
    always @(*)begin
        sum=0;
        sum=0;
        for (k=0;k<NUM;k=k+1)begin
        for (k=0;k<NUM;k=k+1)begin
             sum= sum + {{(SUMw-N){1'b0}},in[k]};
             sum= sum + {{(SUMw-N){1'b0}},in[k]};
        end
        end
    end
    end
    //In case your compiler could not synthesize or wrongly synthesizes it try this
    //In case your compiler could not synthesize or wrongly synthesizes it try this
    //assumming the maximum NUM as parameter can be 20:
    //assumming the maximum NUM as parameter can be 20:
    /*
    /*
    generate
    generate
     wire [N-1   :   0] tmp [19    :   0];
     wire [N-1   :   0] tmp [19    :   0];
     for (i=0; i<NUM; i=i+1)begin : lp
     for (i=0; i<NUM; i=i+1)begin : lp
        assign tmp[i] = in_all[(i+1)*N-1 : i*N];
        assign tmp[i] = in_all[(i+1)*N-1 : i*N];
     end
     end
     for (i=NUM; i<20; i=i+1)begin : lp2
     for (i=NUM; i<20; i=i+1)begin : lp2
        assign tmp[i] = {N{1'b0}};
        assign tmp[i] = {N{1'b0}};
     end
     end
 
 
    always @(*)begin
    always @(*)begin
              sum= tmp[0] + tmp[1]+ tmp[2] + ...+ tmp[19];
              sum= tmp[0] + tmp[1]+ tmp[2] + ...+ tmp[19];
    end
    end
    endgenerate
    endgenerate
    */
    */
 
 
endmodule
endmodule
 
 
 
 
 
 
/******************************
/******************************
 
 
    set_bits_counter
    set_bits_counter
 
 
*******************************/
*******************************/
 
 
 
 
module set_bits_counter #(
module set_bits_counter #(
    parameter IN_WIDTH =120,
    parameter IN_WIDTH =120,
    parameter OUT_WIDTH = log2(IN_WIDTH+1)
    parameter OUT_WIDTH = log2(IN_WIDTH+1)
    )
    )
    (
    (
    input   [IN_WIDTH-1         :   0]  in,
    input   [IN_WIDTH-1         :   0]  in,
    output  [OUT_WIDTH-1        :   0]  out
    output  [OUT_WIDTH-1        :   0]  out
 
 
);
);
 
 
    function integer log2;
    function integer log2;
      input integer number; begin
      input integer number; begin
         log2=(number <=1) ? 1: 0;
         log2=(number <=1) ? 1: 0;
         while(2**log2<number) begin
         while(2**log2<number) begin
            log2=log2+1;
            log2=log2+1;
         end
         end
      end
      end
    endfunction // log2 
    endfunction // log2 
 
 
 
 
    wire    [IN_WIDTH-2     :   0]  addrin2;
    wire    [IN_WIDTH-2     :   0]  addrin2;
    wire    [OUT_WIDTH-1    :   0]  addrout [IN_WIDTH-2         :   0];
    wire    [OUT_WIDTH-1    :   0]  addrout [IN_WIDTH-2         :   0];
    wire    [OUT_WIDTH-1    :   0]  addrin1 [IN_WIDTH-1         :   0];
    wire    [OUT_WIDTH-1    :   0]  addrin1 [IN_WIDTH-1         :   0];
 
 
 
 
    assign out          = addrin1 [IN_WIDTH-1];
    assign out          = addrin1 [IN_WIDTH-1];
 
 
    genvar i;
    genvar i;
    //always @(*)begin
    //always @(*)begin
    assign  addrin1[0] = {{(OUT_WIDTH-1){1'b0}},in[0]};
    assign  addrin1[0] = {{(OUT_WIDTH-1){1'b0}},in[0]};
    generate
    generate
        for (i=0; i<IN_WIDTH-1; i=i+1) begin : loop
        for (i=0; i<IN_WIDTH-1; i=i+1) begin : loop
                assign  addrin1[i+1]  = addrout[i];
                assign  addrin1[i+1]  = addrout[i];
                assign  addrin2[i]    = in[i+1];
                assign  addrin2[i]    = in[i+1];
                assign  addrout[i]    = addrin1[i] + addrin2 [i];
                assign  addrout[i]    = addrin1[i] + addrin2 [i];
        end
        end
    endgenerate
    endgenerate
 
 
endmodule
endmodule
 
 
 
 
 
 
 
 
 
 
 
 
/******************************
/******************************
 
 
    check_single_bit_assertation
    check_single_bit_assertation
 
 
*******************************/
*******************************/
 
 
 
 
module check_single_bit_assertation #(
module is_onehot0 #(
    parameter IN_WIDTH =2
    parameter IN_WIDTH =2
 
 
    )
    )
    (
    (
    input   [IN_WIDTH-1         :   0]  in,
    input   [IN_WIDTH-1         :   0]  in,
    output  result
    output  result
 
 
    );
    );
 
 
    function integer log2;
    function integer log2;
      input integer number; begin
      input integer number; begin
         log2=(number <=1) ? 1: 0;
         log2=(number <=1) ? 1: 0;
         while(2**log2<number) begin
         while(2**log2<number) begin
            log2=log2+1;
            log2=log2+1;
         end
         end
      end
      end
    endfunction // log2 
    endfunction // log2 
 
 
 
 
 
 
    localparam OUT_WIDTH = log2(IN_WIDTH+1);
    localparam OUT_WIDTH = log2(IN_WIDTH+1);
 
 
    wire [OUT_WIDTH-1   :   0]  sum;
    wire [OUT_WIDTH-1   :   0]  sum;
 
 
    parallel_counter #(
 
        .IN_WIDTH (IN_WIDTH)
    accumulator #(
    )counter
        .INw(IN_WIDTH),
 
        .OUTw(OUT_WIDTH),
 
        .NUM(IN_WIDTH)
 
    )
 
    accum
    (
    (
        .in(in),
        .in_all(in),
        .out(sum)
        .out(sum)
    );
    );
 
 
 
 
 
    /*
 
    parallel_counter #(
 
        .IN_WIDTH (IN_WIDTH)
 
    )counter
 
    (
 
        .in(in),
 
        .out(sum)
 
    );
 
    */
 
 
    assign result = (sum <=1)? 1'b1: 1'b0;
    assign result = (sum <=1)? 1'b1: 1'b0;
 
 
 
 
endmodule
endmodule
 
 
/**********************************
/**********************************
 
 
fast_minimum_number
fast_minimum_number
 
 
***********************************/
***********************************/
 
 
 
 
module fast_minimum_number#(
module fast_minimum_number#(
    parameter NUM_OF_INPUTS     =   8,
    parameter NUM_OF_INPUTS     =   8,
    parameter DATA_WIDTH            =   5,
    parameter DATA_WIDTH            =   5,
    parameter IN_ARRAY_WIDTH    =   NUM_OF_INPUTS   * DATA_WIDTH
    parameter IN_ARRAY_WIDTH    =   NUM_OF_INPUTS   * DATA_WIDTH
)
)
(
(
    input  [IN_ARRAY_WIDTH-1            :   0] in_array,
    input  [IN_ARRAY_WIDTH-1            :   0] in_array,
    output [NUM_OF_INPUTS-1             :   0]  min_out
    output [NUM_OF_INPUTS-1             :   0]  min_out
);
);
 
 
    genvar i,j;
    genvar i,j;
    wire [DATA_WIDTH-1                  :   0]  numbers             [NUM_OF_INPUTS-1            :0];
    wire [DATA_WIDTH-1                  :   0]  numbers             [NUM_OF_INPUTS-1            :0];
    wire [NUM_OF_INPUTS-2               :   0]  comp_array          [NUM_OF_INPUTS-1            :0];
    wire [NUM_OF_INPUTS-2               :   0]  comp_array          [NUM_OF_INPUTS-1            :0];
 
 
    generate
    generate
    if(NUM_OF_INPUTS==1)begin:if1
    if(NUM_OF_INPUTS==1)begin:if1
        assign min_out = 1'b1;
        assign min_out = 1'b1;
    end
    end
    else begin : els//(vc num >1)
    else begin : els//(vc num >1)
        for(i=0; i<NUM_OF_INPUTS;  i=i+1) begin : loop_i
        for(i=0; i<NUM_OF_INPUTS;  i=i+1) begin : loop_i
                assign numbers[i]   = in_array  [(i+1)* DATA_WIDTH-1: i*DATA_WIDTH];
                assign numbers[i]   = in_array  [(i+1)* DATA_WIDTH-1: i*DATA_WIDTH];
                for(j=0; j<NUM_OF_INPUTS-1;  j=j+1) begin : loop_j
                for(j=0; j<NUM_OF_INPUTS-1;  j=j+1) begin : loop_j
                            if(i>j) begin :if1 assign comp_array [i][j] = ~ comp_array [j][i-1]; end
                            if(i>j) begin :if1 assign comp_array [i][j] = ~ comp_array [j][i-1]; end
                            else   begin :els     assign comp_array [i]   [j] = numbers[i]<= numbers[j+1]; end
                            else   begin :els     assign comp_array [i]   [j] = numbers[i]<= numbers[j+1]; end
                end//for j
                end//for j
                assign min_out[i]=  & comp_array[i];
                assign min_out[i]=  & comp_array[i];
        end//for i
        end//for i
    end//else
    end//else
    endgenerate
    endgenerate
 
 
endmodule
endmodule
 
 
 
 
 
 
 
 
 
 
/********************************************
/********************************************
 
 
        Carry-based reduction parallel counter
        Carry-based reduction parallel counter
 
 
 
 
********************************************/
********************************************/
module parallel_counter  #(
module parallel_counter  #(
    parameter IN_WIDTH =120 // max 127
    parameter IN_WIDTH =120 // max 127
)
)
(
(
    in,
    in,
    out
    out
);
);
 
 
 
 
 
 
    function integer log2;
    function integer log2;
      input integer number; begin
      input integer number; begin
         log2=(number <=1) ? 1: 0;
         log2=(number <=1) ? 1: 0;
         while(2**log2<number) begin
         while(2**log2<number) begin
            log2=log2+1;
            log2=log2+1;
         end
         end
      end
      end
    endfunction // log2 
    endfunction // log2 
 
 
  localparam OUT_WIDTH = log2(IN_WIDTH+1);
  localparam OUT_WIDTH = log2(IN_WIDTH+1);
  localparam PCIw      = (IN_WIDTH < 8   )? 7    :
  localparam PCIw      = (IN_WIDTH < 8   )? 7    :
                         (IN_WIDTH < 16  )? 15   :
                         (IN_WIDTH < 16  )? 15   :
                         (IN_WIDTH < 31  )? 31   :
                         (IN_WIDTH < 31  )? 31   :
                         (IN_WIDTH < 36  )? 63   :   127;
                         (IN_WIDTH < 36  )? 63   :   127;
 
 
 
 
   localparam PCOw      = (IN_WIDTH < 8  )? 3   :
   localparam PCOw      = (IN_WIDTH < 8  )? 3   :
                         (IN_WIDTH < 16  )? 4   :
                         (IN_WIDTH < 16  )? 4   :
                         (IN_WIDTH < 31  )? 5   :
                         (IN_WIDTH < 31  )? 5   :
                         (IN_WIDTH < 36  )? 6   :   7;
                         (IN_WIDTH < 36  )? 6   :   7;
 
 
input   [IN_WIDTH-1         :   0]  in;
input   [IN_WIDTH-1         :   0]  in;
output  [OUT_WIDTH-1        :   0]  out;
output  [OUT_WIDTH-1        :   0]  out;
 
 
wire [PCIw-1    :   0]  pc_in;
wire [PCIw-1    :   0]  pc_in;
wire [PCOw-1    :   0]  pc_out;
wire [PCOw-1    :   0]  pc_out;
 
 
generate
generate
    if(PCIw > IN_WIDTH ) begin :w1
    if(PCIw > IN_WIDTH ) begin :w1
        assign   pc_in = {{(PCIw-IN_WIDTH){1'b0}},in};
        assign   pc_in = {{(PCIw-IN_WIDTH){1'b0}},in};
    end else begin:els
    end else begin:els
         assign   pc_in=in;
         assign   pc_in=in;
    end // if 
    end // if 
 
 
    if(PCIw == 7) begin :w7
    if(PCIw == 7) begin :w7
 
 
        PC_7_3   pc (
        PC_7_3   pc (
            .in(pc_in),
            .in(pc_in),
            .out(pc_out)
            .out(pc_out)
        );
        );
 
 
    end else if(PCIw == 15) begin :w15
    end else if(PCIw == 15) begin :w15
          PC_15_4   pc (
          PC_15_4   pc (
            .in(pc_in),
            .in(pc_in),
            .out(pc_out)
            .out(pc_out)
           );
           );
 
 
    end else if(PCIw == 31) begin :w31
    end else if(PCIw == 31) begin :w31
        PC_31_5   pc (
        PC_31_5   pc (
            .in(pc_in),
            .in(pc_in),
            .out(pc_out)
            .out(pc_out)
        );
        );
    end else if(PCIw == 63) begin :w63
    end else if(PCIw == 63) begin :w63
         PC_63_6   pc (
         PC_63_6   pc (
            .in(pc_in),
            .in(pc_in),
            .out(pc_out)
            .out(pc_out)
        );
        );
 
 
    end else  begin :w127
    end else  begin :w127
         PC_127_7 pc (
         PC_127_7 pc (
            .in(pc_in),
            .in(pc_in),
            .out(pc_out)
            .out(pc_out)
        );
        );
    end
    end
 
 
 endgenerate
 endgenerate
 
 
 assign out = pc_out[OUT_WIDTH-1    :   0];
 assign out = pc_out[OUT_WIDTH-1    :   0];
 
 
endmodule
endmodule
 
 
 
 
 
 
//carry-sum generation blocks
//carry-sum generation blocks
module CS_GEN (
module CS_GEN (
    in,
    in,
    abc,
    abc,
    s
    s
);
);
    input   [6  :   0] in;
    input   [6  :   0] in;
    output  s;
    output  s;
    output  [2  :   0] abc;
    output  [2  :   0] abc;
 
 
    wire      a,b,c,s;
    wire      a,b,c,s;
    wire    [3  :   0] in1;
    wire    [3  :   0] in1;
    wire    [2  :   0] in2;
    wire    [2  :   0] in2;
    wire    [2  :   0] j1;
    wire    [2  :   0] j1;
    wire    [1  :   0] j2;
    wire    [1  :   0] j2;
 
 
    assign {in2,in1} =  in;
    assign {in2,in1} =  in;
/* verilator lint_off WIDTH */
/* verilator lint_off WIDTH */
    assign j1= in1[3]+in1[2]+in1[1]+in1[0];
    assign j1= in1[3]+in1[2]+in1[1]+in1[0];
    assign j2= in2[2]+in2[1]+in2[0];
    assign j2= in2[2]+in2[1]+in2[0];
/* verilator lint_on WIDTH */
/* verilator lint_on WIDTH */
 
 
    //s is asserted when both in1 and in2 have odd number of ones.
    //s is asserted when both in1 and in2 have odd number of ones.
    assign s    = j1[0] ^ j2[0];
    assign s    = j1[0] ^ j2[0];
    // a is asserted when there are at least two ones in in1 (i.e., j1 >= 2);
    // a is asserted when there are at least two ones in in1 (i.e., j1 >= 2);
    assign  a   =   (j1 >   3'd1);
    assign  a   =   (j1 >   3'd1);
 
 
    //b is asserted when there are at least two ones in in2 (i.e., j2 >= 2);
    //b is asserted when there are at least two ones in in2 (i.e., j2 >= 2);
    assign  b   =   (j2 >   2'd1);
    assign  b   =   (j2 >   2'd1);
 
 
    // C is asserted when when j1 equals 4 or when  s is asserted
    // C is asserted when when j1 equals 4 or when  s is asserted
    assign c    =   (j1==4) | (j1[0] & j2[0]);
    assign c    =   (j1==4) | (j1[0] & j2[0]);
 
 
    assign abc = {a,b,c};
    assign abc = {a,b,c};
endmodule
endmodule
 
 
/*************************
/*************************
 
 
 (7,3) parallel counter
 (7,3) parallel counter
 
 
*************************/
*************************/
 
 
module PC_7_3 (
module PC_7_3 (
    in,
    in,
    out
    out
 
 
);
);
    input   [6    : 0]  in;
    input   [6    : 0]  in;
    output  [2    : 0]  out;
    output  [2    : 0]  out;
 
 
    wire    [2    : 0] abc;
    wire    [2    : 0] abc;
 
 
    CS_GEN cs(
    CS_GEN cs(
        .in(in),
        .in(in),
        .abc(abc),
        .abc(abc),
        .s(out[0])
        .s(out[0])
    );
    );
 
 
    assign out[2:1] = abc[2]+abc[1]+abc[0];
    assign out[2:1] = abc[2]+abc[1]+abc[0];
 
 
 
 
 
 
 
 
endmodule
endmodule
 
 
/*************************
/*************************
 
 
    (15,4) parallel counter
    (15,4) parallel counter
 
 
*************************/
*************************/
 
 
module PC_15_4 (
module PC_15_4 (
    in,
    in,
    out
    out
 
 
);
);
    input   [14   : 0]  in;
    input   [14   : 0]  in;
    output  [3    : 0]  out;
    output  [3    : 0]  out;
 
 
    wire    [2:0]   abc0,abc1;
    wire    [2:0]   abc0,abc1;
    wire            s0,s1,b2;
    wire            s0,s1,b2;
 
 
    CS_GEN cs0(
    CS_GEN cs0(
        .in     (in  [6  :   0]),
        .in     (in  [6  :   0]),
        .abc    (abc0),
        .abc    (abc0),
        .s      (s0)
        .s      (s0)
    );
    );
 
 
     CS_GEN cs1(
     CS_GEN cs1(
        .in     (in  [13  :   7]),
        .in     (in  [13  :   7]),
        .abc    (abc1),
        .abc    (abc1),
        .s      (s1)
        .s      (s1)
    );
    );
 
 
    assign {b2,out[0]}  =in  [14] + s0 +s1;
    assign {b2,out[0]}  =in  [14] + s0 +s1;
 
 
    PC_7_3 pc_sub(
    PC_7_3 pc_sub(
        .in({abc0,abc1,b2}),
        .in({abc0,abc1,b2}),
        .out(out[3:1])
        .out(out[3:1])
    );
    );
 
 
 
 
 
 
 
 
endmodule
endmodule
 
 
 
 
// (31,5) parallel counter
// (31,5) parallel counter
module PC_31_5 (
module PC_31_5 (
    in,
    in,
    out
    out
 
 
);
);
    localparam CS_NUM   =   5;
    localparam CS_NUM   =   5;
 
 
    input   [30         : 0]  in;
    input   [30         : 0]  in;
    output  [4          : 0]  out;
    output  [4          : 0]  out;
 
 
 
 
    wire    [CS_NUM-1   : 0]   s;
    wire    [CS_NUM-1   : 0]   s;
    wire    [(CS_NUM*7)-1   :   0]  cs_in;
    wire    [(CS_NUM*7)-1   :   0]  cs_in;
    wire    [14         :   0]  pc_15_in;
    wire    [14         :   0]  pc_15_in;
 
 
    assign cs_in ={s[3:0] ,in };
    assign cs_in ={s[3:0] ,in };
 
 
    genvar i;
    genvar i;
    generate
    generate
    for (i=0;i<CS_NUM;i=i+1) begin: lp
    for (i=0;i<CS_NUM;i=i+1) begin: lp
        CS_GEN cs(
        CS_GEN cs(
            .in     (cs_in     [(i+1)*7-1  :  i*7]),
            .in     (cs_in     [(i+1)*7-1  :  i*7]),
            .abc    (pc_15_in  [(i+1)*3-1  :  i*3]),
            .abc    (pc_15_in  [(i+1)*3-1  :  i*3]),
            .s      (s      [i])
            .s      (s      [i])
        );
        );
 
 
    end//for
    end//for
    endgenerate
    endgenerate
 
 
    PC_15_4 pc_15(
    PC_15_4 pc_15(
        .in    (pc_15_in ),
        .in    (pc_15_in ),
        .out   (out[4:1])
        .out   (out[4:1])
    );
    );
 
 
    assign out[0] = s[4];
    assign out[0] = s[4];
 
 
 endmodule
 endmodule
 
 
/*************************
/*************************
 
 
 (63,6) parallel counter
 (63,6) parallel counter
 
 
**************************/
**************************/
 
 
module PC_63_6 (
module PC_63_6 (
    in,
    in,
    out
    out
 
 
);
);
    localparam CS_NUM   =   10;
    localparam CS_NUM   =   10;
 
 
    input   [62         : 0]  in;
    input   [62         : 0]  in;
    output  [5          : 0]  out;
    output  [5          : 0]  out;
 
 
 
 
    wire    [CS_NUM-1   : 0]   s;
    wire    [CS_NUM-1   : 0]   s;
    wire    [(CS_NUM*7)-1   :   0]  cs_in;
    wire    [(CS_NUM*7)-1   :   0]  cs_in;
    wire    [30         : 0]  pc_31_in;
    wire    [30         : 0]  pc_31_in;
 
 
    assign cs_in ={s[7:0] ,in };
    assign cs_in ={s[7:0] ,in };
 
 
    genvar i;
    genvar i;
    generate
    generate
    for (i=0;i<CS_NUM;i=i+1) begin:lp
    for (i=0;i<CS_NUM;i=i+1) begin:lp
        CS_GEN cs(
        CS_GEN cs(
            .in     (cs_in     [(i+1)*7-1  :  i*7]),
            .in     (cs_in     [(i+1)*7-1  :  i*7]),
            .abc    (pc_31_in  [(i+1)*3-1  :  i*3]),
            .abc    (pc_31_in  [(i+1)*3-1  :  i*3]),
            .s      (s      [i])
            .s      (s      [i])
        );
        );
 
 
    end//for
    end//for
    endgenerate
    endgenerate
 
 
    assign {pc_31_in[30],out[0]}    =   s[7]+s[8]+s[9];
    assign {pc_31_in[30],out[0]}    =   s[7]+s[8]+s[9];
 
 
    PC_31_5 pc_31(
    PC_31_5 pc_31(
        .in(pc_31_in ),
        .in(pc_31_in ),
        .out(out[5:1])
        .out(out[5:1])
    );
    );
 endmodule
 endmodule
 
 
/*************************
/*************************
 
 
 (127,7) parallel counter
 (127,7) parallel counter
 
 
*************************/
*************************/
 
 
module PC_127_7 (
module PC_127_7 (
    in,
    in,
    out
    out
 
 
);
);
    localparam CS_NUM   =   21;
    localparam CS_NUM   =   21;
 
 
    input   [126        : 0]  in;
    input   [126        : 0]  in;
    output  [6          : 0]  out;
    output  [6          : 0]  out;
 
 
 
 
    wire    [CS_NUM-1       : 0]   s;
    wire    [CS_NUM-1       : 0]   s;
    wire    [(CS_NUM*7)-1   : 0]  cs_in;//147
    wire    [(CS_NUM*7)-1   : 0]  cs_in;//147
    wire    [62             : 0]  pc_63_in;
    wire    [62             : 0]  pc_63_in;
 
 
    assign cs_in ={s[19:0] ,in };
    assign cs_in ={s[19:0] ,in };
 
 
    genvar i;
    genvar i;
    generate
    generate
    for (i=0;i<CS_NUM;i=i+1) begin :lp
    for (i=0;i<CS_NUM;i=i+1) begin :lp
        CS_GEN cs(
        CS_GEN cs(
            .in     (cs_in     [(i+1)*7-1  :  i*7]),
            .in     (cs_in     [(i+1)*7-1  :  i*7]),
            .abc    (pc_63_in  [(i+1)*3-1  :  i*3]),
            .abc    (pc_63_in  [(i+1)*3-1  :  i*3]),
            .s      (s      [i])
            .s      (s      [i])
        );
        );
 
 
    end//for
    end//for
    endgenerate
    endgenerate
 
 
    assign {out[0]}    =   s[20];
    assign {out[0]}    =   s[20];
 
 
    PC_63_6 pc63(
    PC_63_6 pc63(
        .in(pc_63_in),
        .in(pc_63_in),
        .out(out[6:1])
        .out(out[6:1])
    );
    );
 
 
 
 
 endmodule
 endmodule
 
 
 
 
module start_delay_gen #(
module start_delay_gen #(
    parameter NC     =    64 //number of cores
    parameter NC     =    64 //number of cores
 
 
)(
)(
    clk,
    clk,
    reset,
    reset,
    start_i,
    start_i,
    start_o
    start_o
);
);
 
 
    input reset,clk,start_i;
    input reset,clk,start_i;
    output [NC-1    :    0] start_o;
    output [NC-1    :    0] start_o;
    reg start_i_reg;
    reg start_i_reg;
    wire start;
    wire start;
    wire cnt_increase;
    wire cnt_increase;
    reg  [NC-1    :    0] start_o_next;
    reg  [NC-1    :    0] start_o_next;
    reg [NC-1    :    0] start_o_reg;
    reg [NC-1    :    0] start_o_reg;
 
 
    assign start= start_i_reg|start_i;
    assign start= start_i_reg|start_i;
 
 
generate
generate
if(NC > 2) begin :l1
if(NC > 2) begin :l1
    always @(*)begin
    always @(*)begin
        if(NC[0]==1'b0)begin // odd
        if(NC[0]==1'b0)begin // odd
            start_o_next={start_o[NC-3:0],start_o[NC-2],start};
            start_o_next={start_o[NC-3:0],start_o[NC-2],start};
        end else begin //even
        end else begin //even
            start_o_next={start_o[NC-3:0],start_o[NC-1],start};
            start_o_next={start_o[NC-3:0],start_o[NC-1],start};
 
 
        end
        end
    end
    end
 end
 end
else begin :l2
else begin :l2
         always @(*) start_o_next = {NC{start}};
         always @(*) start_o_next = {NC{start}};
end
end
 
 
endgenerate
endgenerate
 
 
    reg [2:0] counter;
    reg [2:0] counter;
    assign cnt_increase=(counter==3'd0);
    assign cnt_increase=(counter==3'd0);
    always @(posedge clk or posedge reset) begin
    always @ (`pronoc_clk_reset_edge )begin
        if(reset) begin
        if(`pronoc_reset)  begin
            start_o_reg <= {NC{1'b0}};
            start_o_reg <= {NC{1'b0}};
            start_i_reg <= 1'b0;
            start_i_reg <= 1'b0;
            counter <= 3'd0;
            counter <= 3'd0;
        end else begin
        end else begin
            counter <= counter+3'd1;
            counter <= counter+3'd1;
            start_i_reg <= start_i;
            start_i_reg <= start_i;
            if(cnt_increase | start) start_o_reg <= start_o_next;
            if(cnt_increase | start) start_o_reg <= start_o_next;
 
 
 
 
        end//reset
        end//reset
    end //always
    end //always
 
 
    assign start_o=(cnt_increase | start)? start_o_reg : {NC{1'b0}};
    assign start_o=(cnt_increase | start)? start_o_reg : {NC{1'b0}};
 
 
endmodule
endmodule
 
 
 
 
 
 
 
 
 
 

powered by: WebSVN 2.1.0

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