// Copyright lowRISC contributors.
// Licensed under the Apache License, Version 2.0, see LICENSE for details.
// SPDX-License-Identifier: Apache-2.0
//
// ------------------- W A R N I N G: A U T O - G E N E R A T E D   C O D E !! -------------------//
// PLEASE DO NOT HAND-EDIT THIS FILE. IT HAS BEEN AUTO-GENERATED WITH THE FOLLOWING COMMAND:
//
//    hw/ip/prim/util/generate_prim_mubi.py
//
// Double-synchronizer flop for multibit signals with additional output buffers.

`include "prim_assert.sv"

module prim_mubi${n_bits}_sync
  import prim_mubi_pkg::*;
#(
  // Number of separately buffered output signals.
  // The buffer cells have a don't touch constraint
  // on them such that synthesis tools won't collapse
  // all copies into one signal.
  parameter int NumCopies = 1,
  // This instantiates the synchronizer flops if set to 1.
  // In special cases where the receiver is in the same clock domain as the sender,
  // this can be set to 0. However, it is recommended to leave this at 1.
  parameter bit AsyncOn = 1,
  // Reset value for the sync flops
  parameter mubi${n_bits}_t ResetValue = MuBi${n_bits}False
) (
  input                          clk_i,
  input                          rst_ni,
  input  mubi${n_bits}_t                 mubi_i,
  output mubi${n_bits}_t [NumCopies-1:0] mubi_o
);

  `ASSERT_INIT(NumCopiesMustBeGreaterZero_A, NumCopies > 0)

  logic [MuBi${n_bits}Width-1:0] mubi;
  if (AsyncOn) begin : gen_flops
    prim_flop_2sync #(
      .Width(MuBi${n_bits}Width),
      .ResetValue(MuBi${n_bits}Width'(ResetValue))
    ) u_prim_flop_2sync (
      .clk_i,
      .rst_ni,
      .d_i(mubi_i),
      .q_o(mubi)
    );
  end else begin : gen_no_flops
    logic unused_clk;
    logic unused_rst;
    assign unused_clk = clk_i;
    assign unused_rst = rst_ni;
    assign mubi = mubi_i;
  end

  for (genvar j = 0; j < NumCopies; j++) begin : gen_buffs
    logic [MuBi${n_bits}Width-1:0] mubi_out;
    for (genvar k = 0; k < MuBi${n_bits}Width; k++) begin : gen_bits
      prim_buf u_prim_buf (
        .in_i(mubi[k]),
        .out_o(mubi_out[k])
      );
    end
    assign mubi_o[j] = mubi${n_bits}_t'(mubi_out);
  end

  ////////////////
  // Assertions //
  ////////////////

  // The outputs should be known at all times.
  `ASSERT_KNOWN(OutputsKnown_A, mubi_o)

  // If the multibit signal is in a transient state, we expect it
  // to be stable again within one clock cycle.
  // DV will exclude these three assertions by name, thus added a module name prefix to make it
  // harder to accidentally replicate in other modules.
  `ASSERT(PrimMubi${n_bits}SyncCheckTransients_A,
      !(mubi_i inside {MuBi${n_bits}True, MuBi${n_bits}False})
      |=>
      (mubi_i inside {MuBi${n_bits}True, MuBi${n_bits}False}))

  // If a signal departs from passive state, we expect it to move to the active state
  // with only one transient cycle in between.
  `ASSERT(PrimMubi${n_bits}SyncCheckTransients0_A,
      $past(mubi_i == MuBi${n_bits}False) &&
      !(mubi_i inside {MuBi${n_bits}True, MuBi${n_bits}False})
      |=>
      (mubi_i == MuBi${n_bits}True))

  `ASSERT(PrimMubi${n_bits}SyncCheckTransients1_A,
      $past(mubi_i == MuBi${n_bits}True) &&
      !(mubi_i inside {MuBi${n_bits}True, MuBi${n_bits}False})
      |=>
      (mubi_i == MuBi${n_bits}False))

endmodule : prim_mubi${n_bits}_sync
