data/full_repos/permissive/214858095/FPGA_Exploration/spartan6/B205mini/ISE_Project/lib/rfnoc/axi_rate_change.v
[Errno 2] No such file or directory: 'preprocess.output'
1: b'%Error: data/full_repos/permissive/214858095/FPGA_Exploration/spartan6/B205mini/ISE_Project/lib/rfnoc/axi_rate_change.v:90: Cannot find file containing module: \'setting_reg\'\n  setting_reg #(.my_addr(SR_N_ADDR), .width($clog2(MAX_N+1)), .at_reset(DEFAULT_N)) set_n (\n  ^~~~~~~~~~~\n        ... Looked in:\n             data/full_repos/permissive/214858095/FPGA_Exploration/spartan6/B205mini/ISE_Project/lib/rfnoc,data/full_repos/permissive/214858095/setting_reg\n             data/full_repos/permissive/214858095/FPGA_Exploration/spartan6/B205mini/ISE_Project/lib/rfnoc,data/full_repos/permissive/214858095/setting_reg.v\n             data/full_repos/permissive/214858095/FPGA_Exploration/spartan6/B205mini/ISE_Project/lib/rfnoc,data/full_repos/permissive/214858095/setting_reg.sv\n             setting_reg\n             setting_reg.v\n             setting_reg.sv\n             obj_dir/setting_reg\n             obj_dir/setting_reg.v\n             obj_dir/setting_reg.sv\n%Error: data/full_repos/permissive/214858095/FPGA_Exploration/spartan6/B205mini/ISE_Project/lib/rfnoc/axi_rate_change.v:96: Cannot find file containing module: \'setting_reg\'\n  setting_reg #(.my_addr(SR_M_ADDR), .width($clog2(MAX_M+1)), .at_reset(DEFAULT_M)) set_m (\n  ^~~~~~~~~~~\n%Error: data/full_repos/permissive/214858095/FPGA_Exploration/spartan6/B205mini/ISE_Project/lib/rfnoc/axi_rate_change.v:102: Cannot find file containing module: \'setting_reg\'\n  setting_reg #(.my_addr(SR_CONFIG_ADDR), .width(1), .at_reset(1\'b1)) set_config (\n  ^~~~~~~~~~~\n%Error: data/full_repos/permissive/214858095/FPGA_Exploration/spartan6/B205mini/ISE_Project/lib/rfnoc/axi_rate_change.v:110: Cannot find file containing module: \'setting_reg\'\n  setting_reg #(\n  ^~~~~~~~~~~\n%Error: data/full_repos/permissive/214858095/FPGA_Exploration/spartan6/B205mini/ISE_Project/lib/rfnoc/axi_rate_change.v:130: Cannot find file containing module: \'cvita_hdr_decoder\'\n  cvita_hdr_decoder cvita_hdr_decoder_in_header (\n  ^~~~~~~~~~~~~~~~~\n%Error: data/full_repos/permissive/214858095/FPGA_Exploration/spartan6/B205mini/ISE_Project/lib/rfnoc/axi_rate_change.v:141: Cannot find file containing module: \'axi_fifo\'\n  axi_fifo #(.WIDTH(16), .SIZE(0)) axi_fifo_word_cnt (\n  ^~~~~~~~\n%Error: data/full_repos/permissive/214858095/FPGA_Exploration/spartan6/B205mini/ISE_Project/lib/rfnoc/axi_rate_change.v:152: Cannot find file containing module: \'axi_fifo_flop\'\n  axi_fifo_flop #(.WIDTH(WIDTH+1+128)) axi_fifo_flop_input (\n  ^~~~~~~~~~~~~\n%Warning-WIDTH: data/full_repos/permissive/214858095/FPGA_Exploration/spartan6/B205mini/ISE_Project/lib/rfnoc/axi_rate_change.v:263: Operator ADD expects 16 bits on the RHS, but RHS\'s EQ generates 1 bits.\n                                                                                                                                   : ... In instance axi_rate_change\n                  word_cnt_div_n_tdata  <= word_cnt_div_n + (word_cnt_div_n_frac == n);\n                                                          ^\n                ... Use "/* verilator lint_off WIDTH */" and lint_on around source to disable this message.\n%Error: data/full_repos/permissive/214858095/FPGA_Exploration/spartan6/B205mini/ISE_Project/lib/rfnoc/axi_rate_change.v:298: Cannot find file containing module: \'axi_drop_partial_packet\'\n  axi_drop_partial_packet #(\n  ^~~~~~~~~~~~~~~~~~~~~~~\n%Warning-WIDTH: data/full_repos/permissive/214858095/FPGA_Exploration/spartan6/B205mini/ISE_Project/lib/rfnoc/axi_rate_change.v:420: Operator ADD expects 64 bits on the RHS, but RHS\'s VARREF \'time_incr\' generates 17 bits.\n                                                                                                                                   : ... In instance axi_rate_change\n              vita_time_out    <= vita_time_accum + time_incr;\n                                                  ^\n%Warning-WIDTH: data/full_repos/permissive/214858095/FPGA_Exploration/spartan6/B205mini/ISE_Project/lib/rfnoc/axi_rate_change.v:422: Operator ADD expects 64 bits on the RHS, but RHS\'s VARREF \'time_incr\' generates 17 bits.\n                                                                                                                                   : ... In instance axi_rate_change\n            vita_time_accum    <= vita_time_accum + time_incr;\n                                                  ^\n%Error: data/full_repos/permissive/214858095/FPGA_Exploration/spartan6/B205mini/ISE_Project/lib/rfnoc/axi_rate_change.v:436: Cannot find file containing module: \'cvita_hdr_encoder\'\n  cvita_hdr_encoder cvita_hdr_encoder (\n  ^~~~~~~~~~~~~~~~~\n%Error: data/full_repos/permissive/214858095/FPGA_Exploration/spartan6/B205mini/ISE_Project/lib/rfnoc/axi_rate_change.v:452: Cannot find file containing module: \'axi_fifo_flop\'\n  axi_fifo_flop #(.WIDTH(WIDTH+1)) axi_fifo_flop_from_user_0 (\n  ^~~~~~~~~~~~~\n%Error: data/full_repos/permissive/214858095/FPGA_Exploration/spartan6/B205mini/ISE_Project/lib/rfnoc/axi_rate_change.v:461: Cannot find file containing module: \'axi_fifo_flop\'\n  axi_fifo_flop #(.WIDTH(WIDTH+1+128)) axi_fifo_flop_output (\n  ^~~~~~~~~~~~~\n%Error: Exiting due to 11 error(s), 3 warning(s)\n'
module axi_rate_change #(
  parameter WIDTH                   = 32,
  parameter MAX_N                   = 2**16,
  parameter MAX_M                   = 2**16,
  parameter MAXIMIZE_OUTPUT_PKT_LEN = 1,

  parameter SR_N_ADDR               = 0,
  parameter SR_M_ADDR               = 1,
  parameter SR_CONFIG_ADDR          = 2,
  parameter SR_TIME_INCR_ADDR       = 3,
  parameter DEFAULT_N               = 1,
  parameter DEFAULT_M               = 1
)(
  input clk, input reset, input clear,
  output clear_user,
  input [15:0] src_sid, input [15:0] dst_sid,
  input set_stb, input [7:0] set_addr, input [31:0] set_data,
  input [WIDTH-1:0] i_tdata, input i_tlast, input i_tvalid, output i_tready, input [127:0] i_tuser,
  output [WIDTH-1:0] o_tdata, output o_tlast, output o_tvalid, input o_tready, output [127:0] o_tuser,
  output [WIDTH-1:0] m_axis_data_tdata, output m_axis_data_tlast, output m_axis_data_tvalid, input m_axis_data_tready,
  input [WIDTH-1:0] s_axis_data_tdata, input s_axis_data_tlast, input s_axis_data_tvalid, output s_axis_data_tready,




  output reg warning_long_throttle,
  output reg error_extra_outputs,
  output reg error_drop_pkt_lockup
);

  reg [$clog2(MAX_N+1)-1:0] n = DEFAULT_N;
  reg [$clog2(MAX_M+1)-1:0] m = DEFAULT_M;

  wire [WIDTH-1:0] i_reg_tdata;
  wire i_reg_tvalid, i_reg_tready, i_reg_tlast;
  wire i_reg_tvalid_int, i_reg_tready_int, i_reg_tlast_int;

  reg throttle = 1'b1, first_header, partial_first_word;
  reg [15:0] word_cnt_div_n;
  reg [$clog2(MAX_N+1)-1:0] word_cnt_div_n_frac = 1;
  reg [$clog2(MAX_N+1)-1:0] in_pkt_cnt = 1;

  reg send_done;
  reg rate_changed;


  wire [$clog2(MAX_N+1)-1:0] sr_n;
  wire n_changed;
  setting_reg #(.my_addr(SR_N_ADDR), .width($clog2(MAX_N+1)), .at_reset(DEFAULT_N)) set_n (
    .clk(clk), .rst(reset), .strobe(set_stb), .addr(set_addr), .in(set_data),
    .out(sr_n), .changed(n_changed));

  wire [$clog2(MAX_M+1)-1:0] sr_m;
  wire m_changed;
  setting_reg #(.my_addr(SR_M_ADDR), .width($clog2(MAX_M+1)), .at_reset(DEFAULT_M)) set_m (
    .clk(clk), .rst(reset), .strobe(set_stb), .addr(set_addr), .in(set_data),
    .out(sr_m), .changed(m_changed));

  wire sr_config;
  wire enable_clear_user;
  setting_reg #(.my_addr(SR_CONFIG_ADDR), .width(1), .at_reset(1'b1)) set_config (
    .clk(clk), .rst(reset), .strobe(set_stb), .addr(set_addr), .in(set_data),
    .out(sr_config), .changed());
  assign enable_clear_user = sr_config;


  wire [$clog2(MAX_N+1)-1:0] sr_time_incr;
  reg  [$clog2(MAX_N+1)-1:0] time_incr;
  setting_reg #(
    .my_addr(SR_TIME_INCR_ADDR), .width($clog2(MAX_N+1)), .at_reset(0)
  ) set_time_incr (
    .clk(clk), .rst(reset), .strobe(set_stb), .addr(set_addr), .in(set_data),
    .out(sr_time_incr), .changed());



  wire [127:0] i_reg_tuser;
  wire has_time_in, eob_in, eob_in_header;
  wire [15:0] payload_length_in;
  reg [15:0] payload_length_out;
  wire [63:0] vita_time_in;
  cvita_hdr_decoder cvita_hdr_decoder_in_header (
    .header(i_reg_tuser), .pkt_type(), .eob(eob_in_header),
    .has_time(has_time_in), .seqnum(), .length(), .payload_length(payload_length_in),
    .src_sid(), .dst_sid(), .vita_time(vita_time_in));

  assign eob_in = eob_in_header | rate_changed;

  reg [15:0] word_cnt_div_n_tdata;
  wire [15:0] word_cnt_div_n_fifo_tdata;
  reg word_cnt_div_n_tvalid;
  wire word_cnt_div_n_tready, word_cnt_div_n_fifo_tvalid, word_cnt_div_n_fifo_tready;
  axi_fifo #(.WIDTH(16), .SIZE(0)) axi_fifo_word_cnt (
    .clk(clk), .reset(reset), .clear(clear),
    .i_tdata(word_cnt_div_n_tdata), .i_tvalid(word_cnt_div_n_tvalid), .i_tready(word_cnt_div_n_tready),
    .o_tdata(word_cnt_div_n_fifo_tdata), .o_tvalid(word_cnt_div_n_fifo_tvalid), .o_tready(word_cnt_div_n_fifo_tready),
    .space(), .occupied());



  axi_fifo_flop #(.WIDTH(WIDTH+1+128)) axi_fifo_flop_input (
    .clk(clk), .reset(reset), .clear(clear),
    .i_tdata({i_tlast,i_tdata,i_tuser}), .i_tvalid(i_tvalid), .i_tready(i_tready),
    .o_tdata({i_reg_tlast,i_reg_tdata,i_reg_tuser}), .o_tvalid(i_reg_tvalid_int), .o_tready(i_reg_tready),
    .space(), .occupied());

  assign i_reg_tready     = i_reg_tready_int & word_cnt_div_n_tready & ~throttle;
  assign i_reg_tvalid     = i_reg_tvalid_int & word_cnt_div_n_tready & ~throttle;


  assign i_reg_tlast_int  = (word_cnt_div_n_frac == n) | (eob_in & i_reg_tlast);


  reg [1:0] input_state;
  localparam RECV_INIT                = 0;
  localparam RECV                     = 1;
  localparam RECV_WAIT_FOR_SEND_DONE  = 2;

  always @(posedge clk) begin
    if (reset | clear) begin
      n                     <= DEFAULT_N;
      m                     <= DEFAULT_M;
      rate_changed          <= 1'b0;
      first_header          <= 1'b1;
      partial_first_word    <= 1'b1;
      payload_length_out    <= 'd0;
      word_cnt_div_n        <= 0;
      word_cnt_div_n_frac   <= 1;
      throttle              <= 1'b1;
      word_cnt_div_n_tvalid <= 1'b0;
      word_cnt_div_n_tdata  <= 'd0;
      input_state           <= RECV_INIT;
    end else begin
      if (word_cnt_div_n_tvalid & word_cnt_div_n_tready) begin
        word_cnt_div_n_tvalid <= 1'b0;
      end

      case (input_state)
        RECV_INIT : begin
          n                      <= sr_n;
          m                      <= sr_m;

          time_incr              <= sr_time_incr == 0 ? sr_n : sr_time_incr;
          rate_changed           <= 1'b0;
          first_header           <= 1'b1;
          partial_first_word     <= 1'b1;
          payload_length_out     <= 'd0;
          word_cnt_div_n         <= 0;
          word_cnt_div_n_frac    <= 1;
          if (i_reg_tvalid_int & word_cnt_div_n_tready) begin
            throttle             <= 1'b0;
            input_state          <= RECV;
          end
        end












        RECV : begin

          if (m_changed) begin
            rate_changed           <= 1'b1;
          end
          if (i_reg_tvalid & i_reg_tready) begin




            if (word_cnt_div_n_frac == n) begin
              word_cnt_div_n       <= word_cnt_div_n + 1;
              word_cnt_div_n_frac  <= 1;
            end else begin
              word_cnt_div_n_frac  <= word_cnt_div_n_frac + 1;
            end

            first_header           <= 1'b0;
            if (first_header) begin
              payload_length_out   <= payload_length_in;
            end else if (MAXIMIZE_OUTPUT_PKT_LEN) begin
              if (payload_length_out < payload_length_in) begin
                payload_length_out <= payload_length_in;
              end
            end

            if (partial_first_word & (word_cnt_div_n_frac == n)) begin
              partial_first_word   <= 1'b0;
            end




            if (i_reg_tlast & eob_in & partial_first_word) begin
              input_state          <= RECV_INIT;
            end else begin
              if (i_reg_tlast) begin





                if (eob_in) begin
                  word_cnt_div_n_tdata  <= word_cnt_div_n + (word_cnt_div_n_frac == n);
                  word_cnt_div_n_tvalid <= 1'b1;
                  throttle              <= 1'b1;
                  if (enable_clear_user) begin
                    input_state         <= RECV_WAIT_FOR_SEND_DONE;
                  end else begin
                    input_state         <= RECV_INIT;
                  end
                end
              end
            end
          end
        end



        RECV_WAIT_FOR_SEND_DONE : begin
          if (send_done) begin
            input_state <= RECV_INIT;
          end
        end
        default : begin
          input_state   <= RECV_INIT;
        end
      endcase
    end
  end

  assign clear_user = send_done & enable_clear_user;


  axi_drop_partial_packet #(
    .WIDTH(WIDTH+1),
    .HOLD_LAST_WORD(1),
    .MAX_PKT_SIZE(MAX_N),
    .SR_PKT_SIZE_ADDR(SR_N_ADDR),
    .DEFAULT_PKT_SIZE(DEFAULT_N))
  axi_drop_partial_packet (
    .clk(clk), .reset(reset), .clear(clear | send_done),
    .flush(word_cnt_div_n_tvalid & word_cnt_div_n_tready),
    .set_stb(set_stb), .set_addr(set_addr), .set_data(set_data),
    .i_tdata({i_reg_tlast,i_reg_tdata}), .i_tvalid(i_reg_tvalid), .i_tlast(i_reg_tlast_int), .i_tready(i_reg_tready_int),
    .o_tdata({m_axis_data_tlast,m_axis_data_tdata}), .o_tvalid(m_axis_data_tvalid), .o_tlast(), .o_tready(m_axis_data_tready));


  reg [1:0] output_state;
  localparam SEND_INIT = 0;
  localparam SEND      = 1;

  wire [WIDTH-1:0] o_reg_tdata;
  wire [127:0] o_reg_tuser;
  wire o_reg_tvalid, o_reg_tready, o_reg_tlast, o_reg_tlast_int;

  reg [15:0] out_payload_cnt = (WIDTH/8);
  reg [15:0] word_cnt_div_m;
  reg [$clog2(MAX_M+1)-1:0] word_cnt_div_m_frac = 1;
  reg [$clog2(MAX_M+1)-1:0] out_pkt_cnt = 1;






  wire last_word_in_burst = word_cnt_div_n_fifo_tvalid &
                            (word_cnt_div_m == word_cnt_div_n_fifo_tdata) &
                            (word_cnt_div_m_frac == m);

  always @(posedge clk) begin
    if (reset | clear) begin
      word_cnt_div_m      <= 1;
      word_cnt_div_m_frac <= 1;
      out_payload_cnt     <= (WIDTH/8);
      send_done           <= 1'b0;
      output_state        <= SEND_INIT;
    end else begin

      case (output_state)
        SEND_INIT : begin
          word_cnt_div_m      <= 1;
          word_cnt_div_m_frac <= 1;
          out_payload_cnt     <= (WIDTH/8);
          send_done           <= 1'b0;
          output_state        <= SEND;
        end
        SEND : begin
          if (o_reg_tvalid & o_reg_tready) begin
            if (o_reg_tlast) begin

              out_payload_cnt <= (WIDTH/8);
            end else begin
              out_payload_cnt <= out_payload_cnt + (WIDTH/8);
            end



            if (word_cnt_div_m_frac == m) begin
              word_cnt_div_m      <= word_cnt_div_m + 1;
              word_cnt_div_m_frac <= 1;
            end else begin
              word_cnt_div_m_frac <= word_cnt_div_m_frac + 1;
            end
            if (last_word_in_burst) begin
              send_done    <= 1'b1;
              output_state <= SEND_INIT;
            end
          end
        end
        default : begin
          output_state <= SEND_INIT;
        end
      endcase
    end
  end


  assign word_cnt_div_n_fifo_tready = o_reg_tvalid & o_reg_tready & last_word_in_burst;


  localparam VT_INIT       = 0;
  localparam VT_INCREMENT  = 1;
  reg vt_state;

  reg has_time_out, has_time_clear;
  reg [63:0] vita_time_out, vita_time_accum;

  always @(posedge clk) begin
    if (reset | clear) begin
      vt_state               <= VT_INIT;
    end else begin
      case (vt_state)
        VT_INIT : begin
          has_time_clear       <= 1'b0;
          if (i_reg_tvalid & i_reg_tready & first_header) begin
            vita_time_out      <= vita_time_in;
            vita_time_accum    <= vita_time_in;
            has_time_out       <= has_time_in;
            vt_state           <= VT_INCREMENT;
          end
        end
        VT_INCREMENT : begin

          if (i_reg_tvalid & ~has_time_in) begin
            has_time_clear     <= 1'b1;
          end
          if (o_reg_tvalid & o_reg_tready) begin
            if (o_reg_tlast) begin
              if (has_time_clear) begin
                has_time_out   <= 1'b0;
              end
              vita_time_out    <= vita_time_accum + time_incr;
            end
            vita_time_accum    <= vita_time_accum + time_incr;
            if (last_word_in_burst) begin
              vt_state         <= VT_INIT;
            end
          end
        end
        default : begin
          vt_state             <= VT_INIT;
        end
      endcase
    end
  end


  cvita_hdr_encoder cvita_hdr_encoder (
    .pkt_type(2'd0), .eob(last_word_in_burst), .has_time(has_time_out),
    .seqnum(12'd0), .payload_length(16'd0),
    .src_sid(src_sid), .dst_sid(dst_sid),
    .vita_time(vita_time_out),
    .header(o_reg_tuser));


  assign o_reg_tlast      = o_reg_tlast_int |

                            (out_payload_cnt == payload_length_out) |

                            last_word_in_burst;

  axi_fifo_flop #(.WIDTH(WIDTH+1)) axi_fifo_flop_from_user_0 (
    .clk(clk), .reset(reset), .clear(clear),


    .i_tdata({1'b0,s_axis_data_tdata}), .i_tvalid(s_axis_data_tvalid), .i_tready(s_axis_data_tready),
    .o_tdata({o_reg_tlast_int,o_reg_tdata}), .o_tvalid(o_reg_tvalid), .o_tready(o_reg_tready),
    .space(), .occupied());


  axi_fifo_flop #(.WIDTH(WIDTH+1+128)) axi_fifo_flop_output (
    .clk(clk), .reset(reset), .clear(clear),
    .i_tdata({o_reg_tlast,o_reg_tdata,o_reg_tuser}), .i_tvalid(o_reg_tvalid), .i_tready(o_reg_tready),
    .o_tdata({o_tlast,o_tdata,o_tuser}), .o_tvalid(o_tvalid), .o_tready(o_tready),
    .space(), .occupied());


  reg [23:0] counter_header_fifo_full, counter_throttle, counter_drop_pkt_lockup;
  reg [2:0] counter_header_fifo_empty;
  always @(posedge clk) begin
    if (reset) begin
      warning_long_throttle       <= 1'b0;
      error_extra_outputs         <= 1'b0;
      error_drop_pkt_lockup       <= 1'b0;
      counter_throttle            <= 0;
      counter_header_fifo_full    <= 0;
      counter_drop_pkt_lockup     <= 0;
      counter_header_fifo_empty   <= 0;
    end else begin

      if (throttle) begin
        counter_throttle          <= counter_throttle + 1;
        if (counter_throttle == 2**24-1) begin
          warning_long_throttle   <= 1'b1;
        end
      end else begin
        counter_throttle          <= 0;
      end

      if (word_cnt_div_n_fifo_tvalid & (word_cnt_div_m > word_cnt_div_n_fifo_tdata)) begin
        error_extra_outputs         <= 1'b1;
      end

      if (~i_reg_tready_int & m_axis_data_tready) begin
        counter_drop_pkt_lockup     <= counter_drop_pkt_lockup + 1;
        if (counter_drop_pkt_lockup == 2**24-1) begin
          error_drop_pkt_lockup     <= 1'b1;
        end
      end else begin
        counter_drop_pkt_lockup     <= 0;
      end
    end
  end

endmodule
module axi_rate_change #(
  parameter WIDTH                   = 32,
  parameter MAX_N                   = 2**16,
  parameter MAX_M                   = 2**16,
  parameter MAXIMIZE_OUTPUT_PKT_LEN = 1,

  parameter SR_N_ADDR               = 0,
  parameter SR_M_ADDR               = 1,
  parameter SR_CONFIG_ADDR          = 2,
  parameter SR_TIME_INCR_ADDR       = 3,
  parameter DEFAULT_N               = 1,
  parameter DEFAULT_M               = 1
)(
  input clk, input reset, input clear,
  output clear_user,
  input [15:0] src_sid, input [15:0] dst_sid,
  input set_stb, input [7:0] set_addr, input [31:0] set_data,
  input [WIDTH-1:0] i_tdata, input i_tlast, input i_tvalid, output i_tready, input [127:0] i_tuser,
  output [WIDTH-1:0] o_tdata, output o_tlast, output o_tvalid, input o_tready, output [127:0] o_tuser,
  output [WIDTH-1:0] m_axis_data_tdata, output m_axis_data_tlast, output m_axis_data_tvalid, input m_axis_data_tready,
  input [WIDTH-1:0] s_axis_data_tdata, input s_axis_data_tlast, input s_axis_data_tvalid, output s_axis_data_tready,




  output reg warning_long_throttle,
  output reg error_extra_outputs,
  output reg error_drop_pkt_lockup
);


  reg [$clog2(MAX_N+1)-1:0] n = DEFAULT_N;
  reg [$clog2(MAX_M+1)-1:0] m = DEFAULT_M;

  wire [WIDTH-1:0] i_reg_tdata;
  wire i_reg_tvalid, i_reg_tready, i_reg_tlast;
  wire i_reg_tvalid_int, i_reg_tready_int, i_reg_tlast_int;

  reg throttle = 1'b1, first_header, partial_first_word;
  reg [15:0] word_cnt_div_n;
  reg [$clog2(MAX_N+1)-1:0] word_cnt_div_n_frac = 1;
  reg [$clog2(MAX_N+1)-1:0] in_pkt_cnt = 1;

  reg send_done;
  reg rate_changed;


  wire [$clog2(MAX_N+1)-1:0] sr_n;
  wire n_changed;
  setting_reg #(.my_addr(SR_N_ADDR), .width($clog2(MAX_N+1)), .at_reset(DEFAULT_N)) set_n (
    .clk(clk), .rst(reset), .strobe(set_stb), .addr(set_addr), .in(set_data),
    .out(sr_n), .changed(n_changed));

  wire [$clog2(MAX_M+1)-1:0] sr_m;
  wire m_changed;
  setting_reg #(.my_addr(SR_M_ADDR), .width($clog2(MAX_M+1)), .at_reset(DEFAULT_M)) set_m (
    .clk(clk), .rst(reset), .strobe(set_stb), .addr(set_addr), .in(set_data),
    .out(sr_m), .changed(m_changed));

  wire sr_config;
  wire enable_clear_user;
  setting_reg #(.my_addr(SR_CONFIG_ADDR), .width(1), .at_reset(1'b1)) set_config (
    .clk(clk), .rst(reset), .strobe(set_stb), .addr(set_addr), .in(set_data),
    .out(sr_config), .changed());
  assign enable_clear_user = sr_config;


  wire [$clog2(MAX_N+1)-1:0] sr_time_incr;
  reg  [$clog2(MAX_N+1)-1:0] time_incr;
  setting_reg #(
    .my_addr(SR_TIME_INCR_ADDR), .width($clog2(MAX_N+1)), .at_reset(0)
  ) set_time_incr (
    .clk(clk), .rst(reset), .strobe(set_stb), .addr(set_addr), .in(set_data),
    .out(sr_time_incr), .changed());



  wire [127:0] i_reg_tuser;
  wire has_time_in, eob_in, eob_in_header;
  wire [15:0] payload_length_in;
  reg [15:0] payload_length_out;
  wire [63:0] vita_time_in;
  cvita_hdr_decoder cvita_hdr_decoder_in_header (
    .header(i_reg_tuser), .pkt_type(), .eob(eob_in_header),
    .has_time(has_time_in), .seqnum(), .length(), .payload_length(payload_length_in),
    .src_sid(), .dst_sid(), .vita_time(vita_time_in));

  assign eob_in = eob_in_header | rate_changed;

  reg [15:0] word_cnt_div_n_tdata;
  wire [15:0] word_cnt_div_n_fifo_tdata;
  reg word_cnt_div_n_tvalid;
  wire word_cnt_div_n_tready, word_cnt_div_n_fifo_tvalid, word_cnt_div_n_fifo_tready;
  axi_fifo #(.WIDTH(16), .SIZE(0)) axi_fifo_word_cnt (
    .clk(clk), .reset(reset), .clear(clear),
    .i_tdata(word_cnt_div_n_tdata), .i_tvalid(word_cnt_div_n_tvalid), .i_tready(word_cnt_div_n_tready),
    .o_tdata(word_cnt_div_n_fifo_tdata), .o_tvalid(word_cnt_div_n_fifo_tvalid), .o_tready(word_cnt_div_n_fifo_tready),
    .space(), .occupied());



  axi_fifo_flop #(.WIDTH(WIDTH+1+128)) axi_fifo_flop_input (
    .clk(clk), .reset(reset), .clear(clear),
    .i_tdata({i_tlast,i_tdata,i_tuser}), .i_tvalid(i_tvalid), .i_tready(i_tready),
    .o_tdata({i_reg_tlast,i_reg_tdata,i_reg_tuser}), .o_tvalid(i_reg_tvalid_int), .o_tready(i_reg_tready),
    .space(), .occupied());

  assign i_reg_tready     = i_reg_tready_int & word_cnt_div_n_tready & ~throttle;
  assign i_reg_tvalid     = i_reg_tvalid_int & word_cnt_div_n_tready & ~throttle;


  assign i_reg_tlast_int  = (word_cnt_div_n_frac == n) | (eob_in & i_reg_tlast);


  reg [1:0] input_state;
  localparam RECV_INIT                = 0;
  localparam RECV                     = 1;
  localparam RECV_WAIT_FOR_SEND_DONE  = 2;

  always @(posedge clk) begin
    if (reset | clear) begin
      n                     <= DEFAULT_N;
      m                     <= DEFAULT_M;
      rate_changed          <= 1'b0;
      first_header          <= 1'b1;
      partial_first_word    <= 1'b1;
      payload_length_out    <= 'd0;
      word_cnt_div_n        <= 0;
      word_cnt_div_n_frac   <= 1;
      throttle              <= 1'b1;
      word_cnt_div_n_tvalid <= 1'b0;
      word_cnt_div_n_tdata  <= 'd0;
      input_state           <= RECV_INIT;
    end else begin
      if (word_cnt_div_n_tvalid & word_cnt_div_n_tready) begin
        word_cnt_div_n_tvalid <= 1'b0;
      end

      case (input_state)
        RECV_INIT : begin
          n                      <= sr_n;
          m                      <= sr_m;

          time_incr              <= sr_time_incr == 0 ? sr_n : sr_time_incr;
          rate_changed           <= 1'b0;
          first_header           <= 1'b1;
          partial_first_word     <= 1'b1;
          payload_length_out     <= 'd0;
          word_cnt_div_n         <= 0;
          word_cnt_div_n_frac    <= 1;
          if (i_reg_tvalid_int & word_cnt_div_n_tready) begin
            throttle             <= 1'b0;
            input_state          <= RECV;
          end
        end












        RECV : begin

          if (m_changed) begin
            rate_changed           <= 1'b1;
          end
          if (i_reg_tvalid & i_reg_tready) begin




            if (word_cnt_div_n_frac == n) begin
              word_cnt_div_n       <= word_cnt_div_n + 1;
              word_cnt_div_n_frac  <= 1;
            end else begin
              word_cnt_div_n_frac  <= word_cnt_div_n_frac + 1;
            end

            first_header           <= 1'b0;
            if (first_header) begin
              payload_length_out   <= payload_length_in;
            end else if (MAXIMIZE_OUTPUT_PKT_LEN) begin
              if (payload_length_out < payload_length_in) begin
                payload_length_out <= payload_length_in;
              end
            end

            if (partial_first_word & (word_cnt_div_n_frac == n)) begin
              partial_first_word   <= 1'b0;
            end




            if (i_reg_tlast & eob_in & partial_first_word) begin
              input_state          <= RECV_INIT;
            end else begin
              if (i_reg_tlast) begin





                if (eob_in) begin
                  word_cnt_div_n_tdata  <= word_cnt_div_n + (word_cnt_div_n_frac == n);
                  word_cnt_div_n_tvalid <= 1'b1;
                  throttle              <= 1'b1;
                  if (enable_clear_user) begin
                    input_state         <= RECV_WAIT_FOR_SEND_DONE;
                  end else begin
                    input_state         <= RECV_INIT;
                  end
                end
              end
            end
          end
        end



        RECV_WAIT_FOR_SEND_DONE : begin
          if (send_done) begin
            input_state <= RECV_INIT;
          end
        end
        default : begin
          input_state   <= RECV_INIT;
        end
      endcase
    end
  end

  assign clear_user = send_done & enable_clear_user;


  axi_drop_partial_packet #(
    .WIDTH(WIDTH+1),
    .HOLD_LAST_WORD(1),
    .MAX_PKT_SIZE(MAX_N),
    .SR_PKT_SIZE_ADDR(SR_N_ADDR),
    .DEFAULT_PKT_SIZE(DEFAULT_N))
  axi_drop_partial_packet (
    .clk(clk), .reset(reset), .clear(clear | send_done),
    .flush(word_cnt_div_n_tvalid & word_cnt_div_n_tready),
    .set_stb(set_stb), .set_addr(set_addr), .set_data(set_data),
    .i_tdata({i_reg_tlast,i_reg_tdata}), .i_tvalid(i_reg_tvalid), .i_tlast(i_reg_tlast_int), .i_tready(i_reg_tready_int),
    .o_tdata({m_axis_data_tlast,m_axis_data_tdata}), .o_tvalid(m_axis_data_tvalid), .o_tlast(), .o_tready(m_axis_data_tready));


  reg [1:0] output_state;
  localparam SEND_INIT = 0;
  localparam SEND      = 1;

  wire [WIDTH-1:0] o_reg_tdata;
  wire [127:0] o_reg_tuser;
  wire o_reg_tvalid, o_reg_tready, o_reg_tlast, o_reg_tlast_int;

  reg [15:0] out_payload_cnt = (WIDTH/8);
  reg [15:0] word_cnt_div_m;
  reg [$clog2(MAX_M+1)-1:0] word_cnt_div_m_frac = 1;
  reg [$clog2(MAX_M+1)-1:0] out_pkt_cnt = 1;






  wire last_word_in_burst = word_cnt_div_n_fifo_tvalid &
                            (word_cnt_div_m == word_cnt_div_n_fifo_tdata) &
                            (word_cnt_div_m_frac == m);

  always @(posedge clk) begin
    if (reset | clear) begin
      word_cnt_div_m      <= 1;
      word_cnt_div_m_frac <= 1;
      out_payload_cnt     <= (WIDTH/8);
      send_done           <= 1'b0;
      output_state        <= SEND_INIT;
    end else begin

      case (output_state)
        SEND_INIT : begin
          word_cnt_div_m      <= 1;
          word_cnt_div_m_frac <= 1;
          out_payload_cnt     <= (WIDTH/8);
          send_done           <= 1'b0;
          output_state        <= SEND;
        end
        SEND : begin
          if (o_reg_tvalid & o_reg_tready) begin
            if (o_reg_tlast) begin

              out_payload_cnt <= (WIDTH/8);
            end else begin
              out_payload_cnt <= out_payload_cnt + (WIDTH/8);
            end



            if (word_cnt_div_m_frac == m) begin
              word_cnt_div_m      <= word_cnt_div_m + 1;
              word_cnt_div_m_frac <= 1;
            end else begin
              word_cnt_div_m_frac <= word_cnt_div_m_frac + 1;
            end
            if (last_word_in_burst) begin
              send_done    <= 1'b1;
              output_state <= SEND_INIT;
            end
          end
        end
        default : begin
          output_state <= SEND_INIT;
        end
      endcase
    end
  end


  assign word_cnt_div_n_fifo_tready = o_reg_tvalid & o_reg_tready & last_word_in_burst;


  localparam VT_INIT       = 0;
  localparam VT_INCREMENT  = 1;
  reg vt_state;

  reg has_time_out, has_time_clear;
  reg [63:0] vita_time_out, vita_time_accum;

  always @(posedge clk) begin
    if (reset | clear) begin
      vt_state               <= VT_INIT;
    end else begin
      case (vt_state)
        VT_INIT : begin
          has_time_clear       <= 1'b0;
          if (i_reg_tvalid & i_reg_tready & first_header) begin
            vita_time_out      <= vita_time_in;
            vita_time_accum    <= vita_time_in;
            has_time_out       <= has_time_in;
            vt_state           <= VT_INCREMENT;
          end
        end
        VT_INCREMENT : begin

          if (i_reg_tvalid & ~has_time_in) begin
            has_time_clear     <= 1'b1;
          end
          if (o_reg_tvalid & o_reg_tready) begin
            if (o_reg_tlast) begin
              if (has_time_clear) begin
                has_time_out   <= 1'b0;
              end
              vita_time_out    <= vita_time_accum + time_incr;
            end
            vita_time_accum    <= vita_time_accum + time_incr;
            if (last_word_in_burst) begin
              vt_state         <= VT_INIT;
            end
          end
        end
        default : begin
          vt_state             <= VT_INIT;
        end
      endcase
    end
  end


  cvita_hdr_encoder cvita_hdr_encoder (
    .pkt_type(2'd0), .eob(last_word_in_burst), .has_time(has_time_out),
    .seqnum(12'd0), .payload_length(16'd0),
    .src_sid(src_sid), .dst_sid(dst_sid),
    .vita_time(vita_time_out),
    .header(o_reg_tuser));


  assign o_reg_tlast      = o_reg_tlast_int |

                            (out_payload_cnt == payload_length_out) |

                            last_word_in_burst;

  axi_fifo_flop #(.WIDTH(WIDTH+1)) axi_fifo_flop_from_user_0 (
    .clk(clk), .reset(reset), .clear(clear),


    .i_tdata({1'b0,s_axis_data_tdata}), .i_tvalid(s_axis_data_tvalid), .i_tready(s_axis_data_tready),
    .o_tdata({o_reg_tlast_int,o_reg_tdata}), .o_tvalid(o_reg_tvalid), .o_tready(o_reg_tready),
    .space(), .occupied());


  axi_fifo_flop #(.WIDTH(WIDTH+1+128)) axi_fifo_flop_output (
    .clk(clk), .reset(reset), .clear(clear),
    .i_tdata({o_reg_tlast,o_reg_tdata,o_reg_tuser}), .i_tvalid(o_reg_tvalid), .i_tready(o_reg_tready),
    .o_tdata({o_tlast,o_tdata,o_tuser}), .o_tvalid(o_tvalid), .o_tready(o_tready),
    .space(), .occupied());


  reg [23:0] counter_header_fifo_full, counter_throttle, counter_drop_pkt_lockup;
  reg [2:0] counter_header_fifo_empty;
  always @(posedge clk) begin
    if (reset) begin
      warning_long_throttle       <= 1'b0;
      error_extra_outputs         <= 1'b0;
      error_drop_pkt_lockup       <= 1'b0;
      counter_throttle            <= 0;
      counter_header_fifo_full    <= 0;
      counter_drop_pkt_lockup     <= 0;
      counter_header_fifo_empty   <= 0;
    end else begin

      if (throttle) begin
        counter_throttle          <= counter_throttle + 1;
        if (counter_throttle == 2**24-1) begin
          warning_long_throttle   <= 1'b1;
        end
      end else begin
        counter_throttle          <= 0;
      end

      if (word_cnt_div_n_fifo_tvalid & (word_cnt_div_m > word_cnt_div_n_fifo_tdata)) begin
        error_extra_outputs         <= 1'b1;
      end

      if (~i_reg_tready_int & m_axis_data_tready) begin
        counter_drop_pkt_lockup     <= counter_drop_pkt_lockup + 1;
        if (counter_drop_pkt_lockup == 2**24-1) begin
          error_drop_pkt_lockup     <= 1'b1;
        end
      end else begin
        counter_drop_pkt_lockup     <= 0;
      end
    end
  end

endmodule