simplified PCIEWRAPPER3.bsv

simplified PCIEWRAPPER3.bsv

/*
   ../scripts/importbvi.py
   -I
   PcieWrap
   -P
   pcieWrap
   -n
   sys_reset
   -r
   sys_reset
   -n
   sys_clk
   -c
   sys_clk
   -n
   user_clk
   -c
   user_clk
   -n
   user_reset
   -r
   user_reset
   -n
   int_dclk_out
   -c
   int_dclk_out
   -n
   int_oobclk_out
   -c
   int_oobclk_out
   -n
   int_pipe_rxusrclk_out
   -c
   int_pipe_rxusrclk_out
   -n
   int_qplloutclk_out
   -c
   int_qplloutclk_out
   -n
   int_rxoutclk_out
   -c
   int_rxoutclk_out
   -n
   int_userclk1_out
   -n
   int_userclk2_out
   -c
   int_userclk1_out
   -c
   int_userclk2_out
   -n
   int_pclk_out_slave
   -c
   int_pclk_out_slave
   -n
   int_qplloutrefclk_out
   -c
   int_qplloutrefclk_out
   -f
   common
   -f
   int_qplllock
   -f
   int_pclk_sel
   -f
   pipe_userclk1
   -f
   pipe_userclk2
   -f
   cfg_mgmt_type1
   -f
   cfg_req_pm_transition
   -f
   pci_exp
   -f
   pipe
   -f
   user
   -o
   ../xilinx/PCIEWRAPPER3.bsv
   -p
   lanes
   ../../out/nfsume/pcie3_7x_0/pcie3_7x_0_stub.v
*/

import Clocks::*;
import DefaultValue::*;
import XilinxCells::*;
import GetPut::*;
import AxiBits::*;

(* always_ready, always_enabled *)
interface PciewrapCfg#(numeric type lanes);
    method Action      interrupt_int(Bit#(4) v);
    method Action      interrupt_msix_address(Bit#(64) v);
    method Action      interrupt_msix_data(Bit#(32) v);
    method Bit#(2)     interrupt_msix_enable();
    method Bit#(1)     interrupt_msix_fail();
    method Action      interrupt_msix_int(Bit#(1) v);
    method Bit#(2)     interrupt_msix_mask();
    method Bit#(1)     interrupt_msix_sent();
    method Bit#(6)     interrupt_msix_vf_enable();
    method Bit#(6)     interrupt_msix_vf_mask();
    method Action      interrupt_pending(Bit#(2) v);
    method Bit#(1)     interrupt_sent();
endinterface
(* always_ready, always_enabled *)
interface PciewrapCommon#(numeric type lanes);
    method Action      commands_in(Bit#(26) v);
    method Bit#(17)     commands_out();
endinterface
(* always_ready, always_enabled *)
interface PciewrapInt_pclk_sel#(numeric type lanes);
    method Action      slave(Bit#(8) v);
endinterface
(* always_ready, always_enabled *)
interface PciewrapInt_qplllock#(numeric type lanes);
    method Bit#(2)     out();
endinterface
(* always_ready, always_enabled *)
interface PciewrapM_axis_cq#(numeric type lanes);
    method Bit#(256)     tdata();
    method Bit#(8)     tkeep();
    method Bit#(1)     tlast();
    method Action      tready(Bit#(22) v);
    method Bit#(85)     tuser();
    method Bit#(1)     tvalid();
endinterface
(* always_ready, always_enabled *)
interface PciewrapM_axis_rc#(numeric type lanes);
    method Bit#(256)     tdata();
    method Bit#(8)     tkeep();
    method Bit#(1)     tlast();
    method Action      tready(Bit#(22) v);
    method Bit#(75)     tuser();
    method Bit#(1)     tvalid();
endinterface
(* always_ready, always_enabled *)
interface PciewrapPci_exp#(numeric type lanes);
    method Action      rxn(Bit#(8) v);
    method Action      rxp(Bit#(8) v);
    method Bit#(8)     txn();
    method Bit#(8)     txp();
endinterface
(* always_ready, always_enabled *)
interface PciewrapPipe#(numeric type lanes);
    method Action      rx_0_sigs(Bit#(84) v);
    method Action      rx_1_sigs(Bit#(84) v);
    method Action      rx_2_sigs(Bit#(84) v);
    method Action      rx_3_sigs(Bit#(84) v);
    method Action      rx_4_sigs(Bit#(84) v);
    method Action      rx_5_sigs(Bit#(84) v);
    method Action      rx_6_sigs(Bit#(84) v);
    method Action      rx_7_sigs(Bit#(84) v);
    method Bit#(70)     tx_0_sigs();
    method Bit#(70)     tx_1_sigs();
    method Bit#(70)     tx_2_sigs();
    method Bit#(70)     tx_3_sigs();
    method Bit#(70)     tx_4_sigs();
    method Bit#(70)     tx_5_sigs();
    method Bit#(70)     tx_6_sigs();
    method Bit#(70)     tx_7_sigs();
endinterface
(* always_ready, always_enabled *)
interface PciewrapS_axis_cc#(numeric type lanes);
    method Action      tdata(Bit#(256) v);
    method Action      tkeep(Bit#(8) v);
    method Action      tlast(Bit#(1) v);
    method Bit#(4)     tready();
    method Action      tuser(Bit#(33) v);
    method Action      tvalid(Bit#(1) v);
endinterface
(* always_ready, always_enabled *)
interface PciewrapS_axis_rq#(numeric type lanes);
    method Action      tdata(Bit#(256) v);
    method Action      tkeep(Bit#(8) v);
    method Action      tlast(Bit#(1) v);
    method Bit#(4)     tready();
    method Action      tuser(Bit#(60) v);
    method Action      tvalid(Bit#(1) v);
endinterface
(* always_ready, always_enabled *)
interface PciewrapUser#(numeric type lanes);
    method Bit#(1)     app_rdy();
    method Bit#(1)     lnk_up();
endinterface
(* always_ready, always_enabled *)
interface PcieWrap#(numeric type lanes);
    interface PciewrapCfg#(lanes)     cfg;
    interface PciewrapCommon#(lanes)     common;
    interface Clock     int_dclk_out;
    interface Clock     int_oobclk_out;
    interface Clock     int_pclk_out_slave;
    interface PciewrapInt_pclk_sel#(lanes)     int_pclk_sel;
    interface Clock     int_pipe_rxusrclk_out;
    interface PciewrapInt_qplllock#(lanes)     int_qplllock;
    interface Clock     int_qplloutclk_out;
    interface Clock     int_qplloutrefclk_out;
    interface Clock     int_rxoutclk_out;
    interface Clock     int_userclk1_out;
    interface Clock     int_userclk2_out;
    interface PciewrapM_axis_cq#(lanes)     m_axis_cq;
    interface PciewrapM_axis_rc#(lanes)     m_axis_rc;
    interface PciewrapPci_exp#(lanes)     pci_exp;
    interface PciewrapPipe#(lanes)     pipe;
    interface PciewrapS_axis_cc#(lanes)     s_axis_cc;
    interface PciewrapS_axis_rq#(lanes)     s_axis_rq;
    interface PciewrapUser#(lanes)     user;
    interface Clock     user_clk;
    method Reset     user_reset();
endinterface
import "BVI" pcie3_7x_0 =
module mkPcieWrap#(Clock sys_clk, Reset sys_reset)(PcieWrap#(lanes));
    let lanes = valueOf(lanes);
    output_clock user_clk(user_clk);
    output_reset user_reset(user_reset);
    default_clock sys_clk(sys_clk) = sys_clk;
     /* from clock*/
    default_reset sys_reset(sys_reset) = sys_reset;
    interface PciewrapCfg     cfg;
        method interrupt_int(cfg_interrupt_int) enable((*inhigh*) EN_cfg_interrupt_int) clocked_by (user_clk) reset_by (user_reset);
        method interrupt_msix_address(cfg_interrupt_msix_address) enable((*inhigh*) EN_cfg_interrupt_msix_address) clocked_by (user_clk) reset_by (user_reset);
        method interrupt_msix_data(cfg_interrupt_msix_data) enable((*inhigh*) EN_cfg_interrupt_msix_data) clocked_by (user_clk) reset_by (user_reset);
        method cfg_interrupt_msix_enable interrupt_msix_enable() clocked_by (user_clk) reset_by (user_reset);
        method cfg_interrupt_msix_fail interrupt_msix_fail() clocked_by (user_clk) reset_by (user_reset);
        method interrupt_msix_int(cfg_interrupt_msix_int) enable((*inhigh*) EN_cfg_interrupt_msix_int) clocked_by (user_clk) reset_by (user_reset);
        method cfg_interrupt_msix_mask interrupt_msix_mask() clocked_by (user_clk) reset_by (user_reset);
        method cfg_interrupt_msix_sent interrupt_msix_sent() clocked_by (user_clk) reset_by (user_reset);
        method cfg_interrupt_msix_vf_enable interrupt_msix_vf_enable() clocked_by (user_clk) reset_by (user_reset);
        method cfg_interrupt_msix_vf_mask interrupt_msix_vf_mask() clocked_by (user_clk) reset_by (user_reset);
        method interrupt_pending(cfg_interrupt_pending) enable((*inhigh*) EN_cfg_interrupt_pending) clocked_by (user_clk) reset_by (user_reset);
        method cfg_interrupt_sent interrupt_sent() clocked_by (user_clk) reset_by (user_reset);
    endinterface
    interface PciewrapCommon     common;
        method commands_in(common_commands_in) enable((*inhigh*) EN_common_commands_in) clocked_by (user_clk) reset_by (user_reset);
        method common_commands_out commands_out();
    endinterface
    output_clock int_dclk_out(int_dclk_out);
    output_clock int_oobclk_out(int_oobclk_out);
    output_clock int_pclk_out_slave(int_pclk_out_slave);
    interface PciewrapInt_pclk_sel     int_pclk_sel;
        method slave(int_pclk_sel_slave) enable((*inhigh*) EN_int_pclk_sel_slave) clocked_by (user_clk) reset_by (user_reset);
    endinterface
    output_clock int_pipe_rxusrclk_out(int_pipe_rxusrclk_out);
    interface PciewrapInt_qplllock     int_qplllock;
        method int_qplllock_out out();
    endinterface
    output_clock int_qplloutclk_out(int_qplloutclk_out);
    output_clock int_qplloutrefclk_out(int_qplloutrefclk_out);
    output_clock int_rxoutclk_out(int_rxoutclk_out);
    output_clock int_userclk1_out(int_userclk1_out);
    output_clock int_userclk2_out(int_userclk2_out);
    interface PciewrapM_axis_cq     m_axis_cq;
        method m_axis_cq_tdata tdata() clocked_by (user_clk) reset_by (user_reset);
        method m_axis_cq_tkeep tkeep() clocked_by (user_clk) reset_by (user_reset);
        method m_axis_cq_tlast tlast() clocked_by (user_clk) reset_by (user_reset);
        method tready(m_axis_cq_tready) enable((*inhigh*) EN_m_axis_cq_tready) clocked_by (user_clk) reset_by (user_reset);
        method m_axis_cq_tuser tuser() clocked_by (user_clk) reset_by (user_reset);
        method m_axis_cq_tvalid tvalid() clocked_by (user_clk) reset_by (user_reset);
    endinterface
    interface PciewrapM_axis_rc     m_axis_rc;
        method m_axis_rc_tdata tdata() clocked_by (user_clk) reset_by (user_reset);
        method m_axis_rc_tkeep tkeep() clocked_by (user_clk) reset_by (user_reset);
        method m_axis_rc_tlast tlast() clocked_by (user_clk) reset_by (user_reset);
        method tready(m_axis_rc_tready) enable((*inhigh*) EN_m_axis_rc_tready) clocked_by (user_clk) reset_by (user_reset);
        method m_axis_rc_tuser tuser() clocked_by (user_clk) reset_by (user_reset);
        method m_axis_rc_tvalid tvalid() clocked_by (user_clk) reset_by (user_reset);
    endinterface
    interface PciewrapPci_exp     pci_exp;
        method rxn(pci_exp_rxn) enable((*inhigh*) EN_pci_exp_rxn)  clocked_by (sys_clk) reset_by (sys_reset);
        method rxp(pci_exp_rxp) enable((*inhigh*) EN_pci_exp_rxp)  clocked_by (sys_clk) reset_by (sys_reset);
        method pci_exp_txn txn() clocked_by (sys_clk) reset_by (sys_reset);
        method pci_exp_txp txp() clocked_by (sys_clk) reset_by (sys_reset);
    endinterface
    interface PciewrapPipe     pipe;
        method rx_0_sigs(pipe_rx_0_sigs) enable((*inhigh*) EN_pipe_rx_0_sigs)  clocked_by (sys_clk) reset_by (sys_reset);
        method rx_1_sigs(pipe_rx_1_sigs) enable((*inhigh*) EN_pipe_rx_1_sigs)  clocked_by (sys_clk) reset_by (sys_reset);
        method rx_2_sigs(pipe_rx_2_sigs) enable((*inhigh*) EN_pipe_rx_2_sigs)  clocked_by (sys_clk) reset_by (sys_reset);
        method rx_3_sigs(pipe_rx_3_sigs) enable((*inhigh*) EN_pipe_rx_3_sigs)  clocked_by (sys_clk) reset_by (sys_reset);
        method rx_4_sigs(pipe_rx_4_sigs) enable((*inhigh*) EN_pipe_rx_4_sigs)  clocked_by (sys_clk) reset_by (sys_reset);
        method rx_5_sigs(pipe_rx_5_sigs) enable((*inhigh*) EN_pipe_rx_5_sigs)  clocked_by (sys_clk) reset_by (sys_reset);
        method rx_6_sigs(pipe_rx_6_sigs) enable((*inhigh*) EN_pipe_rx_6_sigs)  clocked_by (sys_clk) reset_by (sys_reset);
        method rx_7_sigs(pipe_rx_7_sigs) enable((*inhigh*) EN_pipe_rx_7_sigs)  clocked_by (sys_clk) reset_by (sys_reset);
        method pipe_tx_0_sigs tx_0_sigs();
        method pipe_tx_1_sigs tx_1_sigs();
        method pipe_tx_2_sigs tx_2_sigs();
        method pipe_tx_3_sigs tx_3_sigs();
        method pipe_tx_4_sigs tx_4_sigs();
        method pipe_tx_5_sigs tx_5_sigs();
        method pipe_tx_6_sigs tx_6_sigs();
        method pipe_tx_7_sigs tx_7_sigs();
    endinterface
    interface PciewrapS_axis_cc     s_axis_cc;
        method tdata(s_axis_cc_tdata) enable((*inhigh*) EN_s_axis_cc_tdata) clocked_by (user_clk) reset_by (user_reset);
        method tkeep(s_axis_cc_tkeep) enable((*inhigh*) EN_s_axis_cc_tkeep) clocked_by (user_clk) reset_by (user_reset);
        method tlast(s_axis_cc_tlast) enable((*inhigh*) EN_s_axis_cc_tlast) clocked_by (user_clk) reset_by (user_reset);
        method s_axis_cc_tready tready() clocked_by (user_clk) reset_by (user_reset);
        method tuser(s_axis_cc_tuser) enable((*inhigh*) EN_s_axis_cc_tuser) clocked_by (user_clk) reset_by (user_reset);
        method tvalid(s_axis_cc_tvalid) enable((*inhigh*) EN_s_axis_cc_tvalid) clocked_by (user_clk) reset_by (user_reset);
    endinterface
    interface PciewrapS_axis_rq     s_axis_rq;
        method tdata(s_axis_rq_tdata) enable((*inhigh*) EN_s_axis_rq_tdata) clocked_by (user_clk) reset_by (user_reset);
        method tkeep(s_axis_rq_tkeep) enable((*inhigh*) EN_s_axis_rq_tkeep) clocked_by (user_clk) reset_by (user_reset);
        method tlast(s_axis_rq_tlast) enable((*inhigh*) EN_s_axis_rq_tlast) clocked_by (user_clk) reset_by (user_reset);
        method s_axis_rq_tready tready() clocked_by (user_clk) reset_by (user_reset);
        method tuser(s_axis_rq_tuser) enable((*inhigh*) EN_s_axis_rq_tuser) clocked_by (user_clk) reset_by (user_reset);
        method tvalid(s_axis_rq_tvalid) enable((*inhigh*) EN_s_axis_rq_tvalid) clocked_by (user_clk) reset_by (user_reset);
    endinterface
    interface PciewrapUser     user;
        method user_app_rdy app_rdy() clocked_by (user_clk) reset_by (user_reset);
        method user_lnk_up lnk_up() clocked_by (user_clk) reset_by (user_reset);
    endinterface

    schedule (cfg.interrupt_int, cfg.interrupt_msix_address, cfg.interrupt_msix_data, cfg.interrupt_msix_enable, cfg.interrupt_msix_fail, cfg.interrupt_msix_int, cfg.interrupt_msix_mask, cfg.interrupt_msix_sent, cfg.interrupt_msix_vf_enable, cfg.interrupt_msix_vf_mask, cfg.interrupt_pending, cfg.interrupt_sent, common.commands_in, common.commands_out, int_pclk_sel.slave, int_qplllock.out, m_axis_cq.tdata, m_axis_cq.tkeep, m_axis_cq.tlast, m_axis_cq.tready, m_axis_cq.tuser, m_axis_cq.tvalid, m_axis_rc.tdata, m_axis_rc.tkeep, m_axis_rc.tlast, m_axis_rc.tready, m_axis_rc.tuser, m_axis_rc.tvalid, pci_exp.rxn, pci_exp.rxp, pci_exp.txn, pci_exp.txp, pipe.rx_0_sigs, pipe.rx_1_sigs, pipe.rx_2_sigs, pipe.rx_3_sigs, pipe.rx_4_sigs, pipe.rx_5_sigs, pipe.rx_6_sigs, pipe.rx_7_sigs, pipe.tx_0_sigs, pipe.tx_1_sigs, pipe.tx_2_sigs, pipe.tx_3_sigs, pipe.tx_4_sigs, pipe.tx_5_sigs, pipe.tx_6_sigs, pipe.tx_7_sigs, s_axis_cc.tdata, s_axis_cc.tkeep, s_axis_cc.tlast, s_axis_cc.tready, s_axis_cc.tuser, s_axis_cc.tvalid, s_axis_rq.tdata, s_axis_rq.tkeep, s_axis_rq.tlast, s_axis_rq.tready, s_axis_rq.tuser, s_axis_rq.tvalid, user.app_rdy, user.lnk_up) CF (cfg.interrupt_int, cfg.interrupt_msix_address, cfg.interrupt_msix_data, cfg.interrupt_msix_enable, cfg.interrupt_msix_fail, cfg.interrupt_msix_int, cfg.interrupt_msix_mask, cfg.interrupt_msix_sent, cfg.interrupt_msix_vf_enable, cfg.interrupt_msix_vf_mask, cfg.interrupt_pending, cfg.interrupt_sent, common.commands_in, common.commands_out, int_pclk_sel.slave, int_qplllock.out, m_axis_cq.tdata, m_axis_cq.tkeep, m_axis_cq.tlast, m_axis_cq.tready, m_axis_cq.tuser, m_axis_cq.tvalid, m_axis_rc.tdata, m_axis_rc.tkeep, m_axis_rc.tlast, m_axis_rc.tready, m_axis_rc.tuser, m_axis_rc.tvalid, pci_exp.rxn, pci_exp.rxp, pci_exp.txn, pci_exp.txp, pipe.rx_0_sigs, pipe.rx_1_sigs, pipe.rx_2_sigs, pipe.rx_3_sigs, pipe.rx_4_sigs, pipe.rx_5_sigs, pipe.rx_6_sigs, pipe.rx_7_sigs, pipe.tx_0_sigs, pipe.tx_1_sigs, pipe.tx_2_sigs, pipe.tx_3_sigs, pipe.tx_4_sigs, pipe.tx_5_sigs, pipe.tx_6_sigs, pipe.tx_7_sigs, s_axis_cc.tdata, s_axis_cc.tkeep, s_axis_cc.tlast, s_axis_cc.tready, s_axis_cc.tuser, s_axis_cc.tvalid, s_axis_rq.tdata, s_axis_rq.tkeep, s_axis_rq.tlast, s_axis_rq.tready, s_axis_rq.tuser, s_axis_rq.tvalid, user.app_rdy, user.lnk_up);
endmodule

/*
   ../scripts/importbvi.py
   -I
   PcieWrap
   -P
   pcieWrap
   -n
   sys_reset
   -r
   sys_reset
   -n
   sys_clk
   -c
   sys_clk
   -n
   user_clk
   -c
   user_clk
   -n
   user_reset
   -r
   user_reset
   -n
   int_dclk_out
   -c
   int_dclk_out
   -n
   int_oobclk_out
   -c
   int_oobclk_out
   -n
   int_pipe_rxusrclk_out
   -c
   int_pipe_rxusrclk_out
   -n
   int_qplloutclk_out
   -c
   int_qplloutclk_out
   -n
   int_rxoutclk_out
   -c
   int_rxoutclk_out
   -n
   int_userclk1_out
   -n
   int_userclk2_out
   -c
   int_userclk1_out
   -c
   int_userclk2_out
   -n
   int_pclk_out_slave
   -c
   int_pclk_out_slave
   -n
   int_qplloutrefclk_out
   -c
   int_qplloutrefclk_out
   -f
   common
   -f
   int_qplllock
   -f
   int_pclk_sel
   -f
   pipe_userclk1
   -f
   pipe_userclk2
   -f
   cfg_mgmt_type1
   -f
   cfg_req_pm_transition
   -f
   pci_exp
   -f
   pipe
   -f
   user
   -o
   ../xilinx/PCIEWRAPPER3.bsv
   -p
   lanes
   ../../out/nfsume/pcie3_7x_0/pcie3_7x_0_stub.v
*/

import Clocks::*;
import DefaultValue::*;
import XilinxCells::*;
import GetPut::*;
import AxiBits::*;

(* always_ready, always_enabled *)
interface PciewrapCfg#(numeric type lanes);
    method Action      config_space_enable(Bit#(1) v);
    method Bit#(3)     current_speed();
    method Bit#(2)     dpa_substate_change();
    method Action      ds_bus_number(Bit#(8) v);
    method Action      ds_device_number(Bit#(5) v);
    method Action      ds_function_number(Bit#(3) v);
    method Action      ds_port_number(Bit#(8) v);
    method Action      dsn(Bit#(64) v);
    method Action      err_cor_in(Bit#(1) v);
    method Bit#(1)     err_cor_out();
    method Bit#(1)     err_fatal_out();
    method Bit#(1)     err_nonfatal_out();
    method Action      err_uncor_in(Bit#(1) v);
    method Bit#(8)     ext_function_number();
    method Action      ext_read_data(Bit#(32) v);
    method Action      ext_read_data_valid(Bit#(1) v);
    method Bit#(1)     ext_read_received();
    method Bit#(10)     ext_register_number();
    method Bit#(4)     ext_write_byte_enable();
    method Bit#(32)     ext_write_data();
    method Bit#(1)     ext_write_received();
    method Bit#(12)     fc_cpld();
    method Bit#(8)     fc_cplh();
    method Bit#(12)     fc_npd();
    method Bit#(8)     fc_nph();
    method Bit#(12)     fc_pd();
    method Bit#(8)     fc_ph();
    method Action      fc_sel(Bit#(3) v);
    method Action      flr_done(Bit#(2) v);
    method Bit#(2)     flr_in_process();
    method Bit#(6)     function_power_state();
    method Bit#(8)     function_status();
    method Action      hot_reset_in(Bit#(1) v);
    method Bit#(1)     hot_reset_out();
    method Action      interrupt_int(Bit#(4) v);
    method Action      interrupt_msix_address(Bit#(64) v);
    method Action      interrupt_msix_data(Bit#(32) v);
    method Bit#(2)     interrupt_msix_enable();
    method Bit#(1)     interrupt_msix_fail();
    method Action      interrupt_msix_int(Bit#(1) v);
    method Bit#(2)     interrupt_msix_mask();
    method Bit#(1)     interrupt_msix_sent();
    method Bit#(6)     interrupt_msix_vf_enable();
    method Bit#(6)     interrupt_msix_vf_mask();
    method Action      interrupt_pending(Bit#(2) v);
    method Bit#(1)     interrupt_sent();
    method Bit#(2)     link_power_state();
    method Action      link_training_enable(Bit#(1) v);
    method Bit#(1)     ltr_enable();
    method Bit#(6)     ltssm_state();
    method Bit#(3)     max_payload();
    method Bit#(3)     max_read_req();
    method Action      mgmt_addr(Bit#(19) v);
    method Action      mgmt_byte_enable(Bit#(4) v);
    method Action      mgmt_read(Bit#(1) v);
    method Bit#(32)     mgmt_read_data();
    method Bit#(1)     mgmt_read_write_done();
    method Action      mgmt_write(Bit#(1) v);
    method Action      mgmt_write_data(Bit#(32) v);
    method Bit#(1)     msg_received();
    method Bit#(8)     msg_received_data();
    method Bit#(5)     msg_received_type();
    method Action      msg_transmit(Bit#(1) v);
    method Action      msg_transmit_data(Bit#(32) v);
    method Bit#(1)     msg_transmit_done();
    method Action      msg_transmit_type(Bit#(3) v);
    method Bit#(4)     negotiated_width();
    method Bit#(2)     obff_enable();
    method Action      per_func_status_control(Bit#(3) v);
    method Bit#(16)     per_func_status_data();
    method Action      per_function_number(Bit#(3) v);
    method Action      per_function_output_request(Bit#(1) v);
    method Bit#(1)     per_function_update_done();
    method Bit#(1)     phy_link_down();
    method Bit#(2)     phy_link_status();
    method Bit#(1)     pl_status_change();
    method Action      power_state_change_ack(Bit#(1) v);
    method Bit#(1)     power_state_change_interrupt();
    method Bit#(2)     rcb_status();
    method Action      subsys_vend_id(Bit#(16) v);
    method Bit#(2)     tph_requester_enable();
    method Bit#(6)     tph_st_mode();
    method Action      vf_flr_done(Bit#(6) v);
    method Bit#(6)     vf_flr_in_process();
    method Bit#(18)     vf_power_state();
    method Bit#(12)     vf_status();
    method Bit#(6)     vf_tph_requester_enable();
    method Bit#(18)     vf_tph_st_mode();
endinterface
(* always_ready, always_enabled *)
interface PciewrapCfg_mgmt_type1#(numeric type lanes);
    method Action      cfg_reg_access(Bit#(1) v);
endinterface
(* always_ready, always_enabled *)
interface PciewrapCfg_req_pm_transition#(numeric type lanes);
    method Action      l23_ready(Bit#(1) v);
endinterface
(* always_ready, always_enabled *)
interface PciewrapCommon#(numeric type lanes);
    method Action      commands_in(Bit#(26) v);
    method Bit#(17)     commands_out();
endinterface
(* always_ready, always_enabled *)
interface PciewrapInt_pclk_sel#(numeric type lanes);
    method Action      slave(Bit#(8) v);
endinterface
(* always_ready, always_enabled *)
interface PciewrapInt_qplllock#(numeric type lanes);
    method Bit#(2)     out();
endinterface
(* always_ready, always_enabled *)
interface PciewrapM_axis_cq#(numeric type lanes);
    method Bit#(256)     tdata();
    method Bit#(8)     tkeep();
    method Bit#(1)     tlast();
    method Action      tready(Bit#(22) v);
    method Bit#(85)     tuser();
    method Bit#(1)     tvalid();
endinterface
(* always_ready, always_enabled *)
interface PciewrapM_axis_rc#(numeric type lanes);
    method Bit#(256)     tdata();
    method Bit#(8)     tkeep();
    method Bit#(1)     tlast();
    method Action      tready(Bit#(22) v);
    method Bit#(75)     tuser();
    method Bit#(1)     tvalid();
endinterface
(* always_ready, always_enabled *)
interface PciewrapPci_exp#(numeric type lanes);
    method Action      rxn(Bit#(8) v);
    method Action      rxp(Bit#(8) v);
    method Bit#(8)     txn();
    method Bit#(8)     txp();
endinterface
(* always_ready, always_enabled *)
interface PciewrapPcie#(numeric type lanes);
    method Action      cq_np_req(Bit#(1) v);
    method Bit#(6)     cq_np_req_count();
    method Bit#(4)     rq_seq_num();
    method Bit#(1)     rq_seq_num_vld();
    method Bit#(6)     rq_tag();
    method Bit#(1)     rq_tag_vld();
    method Bit#(2)     tfc_npd_av();
    method Bit#(2)     tfc_nph_av();
endinterface
(* always_ready, always_enabled *)
interface PciewrapPipe#(numeric type lanes);
    method Action      rx_0_sigs(Bit#(84) v);
    method Action      rx_1_sigs(Bit#(84) v);
    method Action      rx_2_sigs(Bit#(84) v);
    method Action      rx_3_sigs(Bit#(84) v);
    method Action      rx_4_sigs(Bit#(84) v);
    method Action      rx_5_sigs(Bit#(84) v);
    method Action      rx_6_sigs(Bit#(84) v);
    method Action      rx_7_sigs(Bit#(84) v);
    method Bit#(70)     tx_0_sigs();
    method Bit#(70)     tx_1_sigs();
    method Bit#(70)     tx_2_sigs();
    method Bit#(70)     tx_3_sigs();
    method Bit#(70)     tx_4_sigs();
    method Bit#(70)     tx_5_sigs();
    method Bit#(70)     tx_6_sigs();
    method Bit#(70)     tx_7_sigs();
endinterface
(* always_ready, always_enabled *)
interface PciewrapS_axis_cc#(numeric type lanes);
    method Action      tdata(Bit#(256) v);
    method Action      tkeep(Bit#(8) v);
    method Action      tlast(Bit#(1) v);
    method Bit#(4)     tready();
    method Action      tuser(Bit#(33) v);
    method Action      tvalid(Bit#(1) v);
endinterface
(* always_ready, always_enabled *)
interface PciewrapS_axis_rq#(numeric type lanes);
    method Action      tdata(Bit#(256) v);
    method Action      tkeep(Bit#(8) v);
    method Action      tlast(Bit#(1) v);
    method Bit#(4)     tready();
    method Action      tuser(Bit#(60) v);
    method Action      tvalid(Bit#(1) v);
endinterface
(* always_ready, always_enabled *)
interface PciewrapUser#(numeric type lanes);
    method Bit#(1)     app_rdy();
    method Bit#(1)     lnk_up();
endinterface
(* always_ready, always_enabled *)
interface PcieWrap#(numeric type lanes);
    interface PciewrapCfg#(lanes)     cfg;
    interface PciewrapCfg_mgmt_type1#(lanes)     cfg_mgmt_type1;
    interface PciewrapCfg_req_pm_transition#(lanes)     cfg_req_pm_transition;
    interface PciewrapCommon#(lanes)     common;
    interface Clock     int_dclk_out;
    interface Clock     int_oobclk_out;
    interface Clock     int_pclk_out_slave;
    interface PciewrapInt_pclk_sel#(lanes)     int_pclk_sel;
    interface Clock     int_pipe_rxusrclk_out;
    interface PciewrapInt_qplllock#(lanes)     int_qplllock;
    interface Clock     int_qplloutclk_out;
    interface Clock     int_qplloutrefclk_out;
    interface Clock     int_rxoutclk_out;
    interface Clock     int_userclk1_out;
    interface Clock     int_userclk2_out;
    interface PciewrapM_axis_cq#(lanes)     m_axis_cq;
    interface PciewrapM_axis_rc#(lanes)     m_axis_rc;
    interface PciewrapPci_exp#(lanes)     pci_exp;
    interface PciewrapPcie#(lanes)     pcie;
    interface PciewrapPipe#(lanes)     pipe;
    interface PciewrapS_axis_cc#(lanes)     s_axis_cc;
    interface PciewrapS_axis_rq#(lanes)     s_axis_rq;
    interface PciewrapUser#(lanes)     user;
    interface Clock     user_clk;
    method Reset     user_reset();
endinterface
import "BVI" pcie3_7x_0 =
module mkPcieWrap#(Clock sys_clk, Reset sys_reset)(PcieWrap#(lanes));
    let lanes = valueOf(lanes);
    output_clock user_clk(user_clk);
    output_reset user_reset(user_reset);
    default_clock sys_clk(sys_clk) = sys_clk;
     /* from clock*/
    default_reset sys_reset(sys_reset) = sys_reset;
    interface PciewrapCfg     cfg;
        method config_space_enable(cfg_config_space_enable) enable((*inhigh*) EN_cfg_config_space_enable) clocked_by (user_clk) reset_by (user_reset);
        method cfg_current_speed current_speed() clocked_by (user_clk) reset_by (user_reset);
        method cfg_dpa_substate_change dpa_substate_change() clocked_by (user_clk) reset_by (user_reset);
        method ds_bus_number(cfg_ds_bus_number) enable((*inhigh*) EN_cfg_ds_bus_number) clocked_by (user_clk) reset_by (user_reset);
        method ds_device_number(cfg_ds_device_number) enable((*inhigh*) EN_cfg_ds_device_number) clocked_by (user_clk) reset_by (user_reset);
        method ds_function_number(cfg_ds_function_number) enable((*inhigh*) EN_cfg_ds_function_number) clocked_by (user_clk) reset_by (user_reset);
        method ds_port_number(cfg_ds_port_number) enable((*inhigh*) EN_cfg_ds_port_number) clocked_by (user_clk) reset_by (user_reset);
        method dsn(cfg_dsn) enable((*inhigh*) EN_cfg_dsn) clocked_by (user_clk) reset_by (user_reset);
        method err_cor_in(cfg_err_cor_in) enable((*inhigh*) EN_cfg_err_cor_in) clocked_by (user_clk) reset_by (user_reset);
        method cfg_err_cor_out err_cor_out() clocked_by (user_clk) reset_by (user_reset);
        method cfg_err_fatal_out err_fatal_out() clocked_by (user_clk) reset_by (user_reset);
        method cfg_err_nonfatal_out err_nonfatal_out() clocked_by (user_clk) reset_by (user_reset);
        method err_uncor_in(cfg_err_uncor_in) enable((*inhigh*) EN_cfg_err_uncor_in) clocked_by (user_clk) reset_by (user_reset);
        method cfg_ext_function_number ext_function_number() clocked_by (user_clk) reset_by (user_reset);
        method ext_read_data(cfg_ext_read_data) enable((*inhigh*) EN_cfg_ext_read_data) clocked_by (user_clk) reset_by (user_reset);
        method ext_read_data_valid(cfg_ext_read_data_valid) enable((*inhigh*) EN_cfg_ext_read_data_valid) clocked_by (user_clk) reset_by (user_reset);
        method cfg_ext_read_received ext_read_received() clocked_by (user_clk) reset_by (user_reset);
        method cfg_ext_register_number ext_register_number() clocked_by (user_clk) reset_by (user_reset);
        method cfg_ext_write_byte_enable ext_write_byte_enable() clocked_by (user_clk) reset_by (user_reset);
        method cfg_ext_write_data ext_write_data() clocked_by (user_clk) reset_by (user_reset);
        method cfg_ext_write_received ext_write_received() clocked_by (user_clk) reset_by (user_reset);
        method cfg_fc_cpld fc_cpld() clocked_by (user_clk) reset_by (user_reset);
        method cfg_fc_cplh fc_cplh() clocked_by (user_clk) reset_by (user_reset);
        method cfg_fc_npd fc_npd() clocked_by (user_clk) reset_by (user_reset);
        method cfg_fc_nph fc_nph() clocked_by (user_clk) reset_by (user_reset);
        method cfg_fc_pd fc_pd() clocked_by (user_clk) reset_by (user_reset);
        method cfg_fc_ph fc_ph() clocked_by (user_clk) reset_by (user_reset);
        method fc_sel(cfg_fc_sel) enable((*inhigh*) EN_cfg_fc_sel) clocked_by (user_clk) reset_by (user_reset);
        method flr_done(cfg_flr_done) enable((*inhigh*) EN_cfg_flr_done) clocked_by (user_clk) reset_by (user_reset);
        method cfg_flr_in_process flr_in_process() clocked_by (user_clk) reset_by (user_reset);
        method cfg_function_power_state function_power_state() clocked_by (user_clk) reset_by (user_reset);
        method cfg_function_status function_status() clocked_by (user_clk) reset_by (user_reset);
        method hot_reset_in(cfg_hot_reset_in) enable((*inhigh*) EN_cfg_hot_reset_in) clocked_by (user_clk) reset_by (user_reset);
        method cfg_hot_reset_out hot_reset_out() clocked_by (user_clk) reset_by (user_reset);
        method interrupt_int(cfg_interrupt_int) enable((*inhigh*) EN_cfg_interrupt_int) clocked_by (user_clk) reset_by (user_reset);
        method interrupt_msix_address(cfg_interrupt_msix_address) enable((*inhigh*) EN_cfg_interrupt_msix_address) clocked_by (user_clk) reset_by (user_reset);
        method interrupt_msix_data(cfg_interrupt_msix_data) enable((*inhigh*) EN_cfg_interrupt_msix_data) clocked_by (user_clk) reset_by (user_reset);
        method cfg_interrupt_msix_enable interrupt_msix_enable() clocked_by (user_clk) reset_by (user_reset);
        method cfg_interrupt_msix_fail interrupt_msix_fail() clocked_by (user_clk) reset_by (user_reset);
        method interrupt_msix_int(cfg_interrupt_msix_int) enable((*inhigh*) EN_cfg_interrupt_msix_int) clocked_by (user_clk) reset_by (user_reset);
        method cfg_interrupt_msix_mask interrupt_msix_mask() clocked_by (user_clk) reset_by (user_reset);
        method cfg_interrupt_msix_sent interrupt_msix_sent() clocked_by (user_clk) reset_by (user_reset);
        method cfg_interrupt_msix_vf_enable interrupt_msix_vf_enable() clocked_by (user_clk) reset_by (user_reset);
        method cfg_interrupt_msix_vf_mask interrupt_msix_vf_mask() clocked_by (user_clk) reset_by (user_reset);
        method interrupt_pending(cfg_interrupt_pending) enable((*inhigh*) EN_cfg_interrupt_pending) clocked_by (user_clk) reset_by (user_reset);
        method cfg_interrupt_sent interrupt_sent() clocked_by (user_clk) reset_by (user_reset);
        method cfg_link_power_state link_power_state() clocked_by (user_clk) reset_by (user_reset);
        method link_training_enable(cfg_link_training_enable) enable((*inhigh*) EN_cfg_link_training_enable) clocked_by (user_clk) reset_by (user_reset);
        method cfg_ltr_enable ltr_enable() clocked_by (user_clk) reset_by (user_reset);
        method cfg_ltssm_state ltssm_state() clocked_by (user_clk) reset_by (user_reset);
        method cfg_max_payload max_payload() clocked_by (user_clk) reset_by (user_reset);
        method cfg_max_read_req max_read_req() clocked_by (user_clk) reset_by (user_reset);
        method mgmt_addr(cfg_mgmt_addr) enable((*inhigh*) EN_cfg_mgmt_addr) clocked_by (user_clk) reset_by (user_reset);
        method mgmt_byte_enable(cfg_mgmt_byte_enable) enable((*inhigh*) EN_cfg_mgmt_byte_enable) clocked_by (user_clk) reset_by (user_reset);
        method mgmt_read(cfg_mgmt_read) enable((*inhigh*) EN_cfg_mgmt_read) clocked_by (user_clk) reset_by (user_reset);
        method cfg_mgmt_read_data mgmt_read_data() clocked_by (user_clk) reset_by (user_reset);
        method cfg_mgmt_read_write_done mgmt_read_write_done() clocked_by (user_clk) reset_by (user_reset);
        method mgmt_write(cfg_mgmt_write) enable((*inhigh*) EN_cfg_mgmt_write) clocked_by (user_clk) reset_by (user_reset);
        method mgmt_write_data(cfg_mgmt_write_data) enable((*inhigh*) EN_cfg_mgmt_write_data) clocked_by (user_clk) reset_by (user_reset);
        method cfg_msg_received msg_received() clocked_by (user_clk) reset_by (user_reset);
        method cfg_msg_received_data msg_received_data() clocked_by (user_clk) reset_by (user_reset);
        method cfg_msg_received_type msg_received_type() clocked_by (user_clk) reset_by (user_reset);
        method msg_transmit(cfg_msg_transmit) enable((*inhigh*) EN_cfg_msg_transmit) clocked_by (user_clk) reset_by (user_reset);
        method msg_transmit_data(cfg_msg_transmit_data) enable((*inhigh*) EN_cfg_msg_transmit_data) clocked_by (user_clk) reset_by (user_reset);
        method cfg_msg_transmit_done msg_transmit_done() clocked_by (user_clk) reset_by (user_reset);
        method msg_transmit_type(cfg_msg_transmit_type) enable((*inhigh*) EN_cfg_msg_transmit_type) clocked_by (user_clk) reset_by (user_reset);
        method cfg_negotiated_width negotiated_width() clocked_by (user_clk) reset_by (user_reset);
        method cfg_obff_enable obff_enable() clocked_by (user_clk) reset_by (user_reset);
        method per_func_status_control(cfg_per_func_status_control) enable((*inhigh*) EN_cfg_per_func_status_control) clocked_by (user_clk) reset_by (user_reset);
        method cfg_per_func_status_data per_func_status_data() clocked_by (user_clk) reset_by (user_reset);
        method per_function_number(cfg_per_function_number) enable((*inhigh*) EN_cfg_per_function_number) clocked_by (user_clk) reset_by (user_reset);
        method per_function_output_request(cfg_per_function_output_request) enable((*inhigh*) EN_cfg_per_function_output_request) clocked_by (user_clk) reset_by (user_reset);
        method cfg_per_function_update_done per_function_update_done() clocked_by (user_clk) reset_by (user_reset);
        method cfg_phy_link_down phy_link_down() clocked_by (user_clk) reset_by (user_reset);
        method cfg_phy_link_status phy_link_status() clocked_by (user_clk) reset_by (user_reset);
        method cfg_pl_status_change pl_status_change() clocked_by (user_clk) reset_by (user_reset);
        method power_state_change_ack(cfg_power_state_change_ack) enable((*inhigh*) EN_cfg_power_state_change_ack) clocked_by (user_clk) reset_by (user_reset);
        method cfg_power_state_change_interrupt power_state_change_interrupt() clocked_by (user_clk) reset_by (user_reset);
        method cfg_rcb_status rcb_status() clocked_by (user_clk) reset_by (user_reset);
        method subsys_vend_id(cfg_subsys_vend_id) enable((*inhigh*) EN_cfg_subsys_vend_id) clocked_by (user_clk) reset_by (user_reset);
        method cfg_tph_requester_enable tph_requester_enable() clocked_by (user_clk) reset_by (user_reset);
        method cfg_tph_st_mode tph_st_mode() clocked_by (user_clk) reset_by (user_reset);
        method vf_flr_done(cfg_vf_flr_done) enable((*inhigh*) EN_cfg_vf_flr_done) clocked_by (user_clk) reset_by (user_reset);
        method cfg_vf_flr_in_process vf_flr_in_process() clocked_by (user_clk) reset_by (user_reset);
        method cfg_vf_power_state vf_power_state() clocked_by (user_clk) reset_by (user_reset);
        method cfg_vf_status vf_status() clocked_by (user_clk) reset_by (user_reset);
        method cfg_vf_tph_requester_enable vf_tph_requester_enable() clocked_by (user_clk) reset_by (user_reset);
        method cfg_vf_tph_st_mode vf_tph_st_mode() clocked_by (user_clk) reset_by (user_reset);
    endinterface
    interface PciewrapCfg_mgmt_type1     cfg_mgmt_type1;
        method cfg_reg_access(cfg_mgmt_type1_cfg_reg_access) enable((*inhigh*) EN_cfg_mgmt_type1_cfg_reg_access) clocked_by (user_clk) reset_by (user_reset);
    endinterface
    interface PciewrapCfg_req_pm_transition     cfg_req_pm_transition;
        method l23_ready(cfg_req_pm_transition_l23_ready) enable((*inhigh*) EN_cfg_req_pm_transition_l23_ready) clocked_by (user_clk) reset_by (user_reset);
    endinterface
    interface PciewrapCommon     common;
        method commands_in(common_commands_in) enable((*inhigh*) EN_common_commands_in) clocked_by (user_clk) reset_by (user_reset);
        method common_commands_out commands_out();
    endinterface
    output_clock int_dclk_out(int_dclk_out);
    output_clock int_oobclk_out(int_oobclk_out);
    output_clock int_pclk_out_slave(int_pclk_out_slave);
    interface PciewrapInt_pclk_sel     int_pclk_sel;
        method slave(int_pclk_sel_slave) enable((*inhigh*) EN_int_pclk_sel_slave) clocked_by (user_clk) reset_by (user_reset);
    endinterface
    output_clock int_pipe_rxusrclk_out(int_pipe_rxusrclk_out);
    interface PciewrapInt_qplllock     int_qplllock;
        method int_qplllock_out out();
    endinterface
    output_clock int_qplloutclk_out(int_qplloutclk_out);
    output_clock int_qplloutrefclk_out(int_qplloutrefclk_out);
    output_clock int_rxoutclk_out(int_rxoutclk_out);
    output_clock int_userclk1_out(int_userclk1_out);
    output_clock int_userclk2_out(int_userclk2_out);
    interface PciewrapM_axis_cq     m_axis_cq;
        method m_axis_cq_tdata tdata() clocked_by (user_clk) reset_by (user_reset);
        method m_axis_cq_tkeep tkeep() clocked_by (user_clk) reset_by (user_reset);
        method m_axis_cq_tlast tlast() clocked_by (user_clk) reset_by (user_reset);
        method tready(m_axis_cq_tready) enable((*inhigh*) EN_m_axis_cq_tready) clocked_by (user_clk) reset_by (user_reset);
        method m_axis_cq_tuser tuser() clocked_by (user_clk) reset_by (user_reset);
        method m_axis_cq_tvalid tvalid() clocked_by (user_clk) reset_by (user_reset);
    endinterface
    interface PciewrapM_axis_rc     m_axis_rc;
        method m_axis_rc_tdata tdata() clocked_by (user_clk) reset_by (user_reset);
        method m_axis_rc_tkeep tkeep() clocked_by (user_clk) reset_by (user_reset);
        method m_axis_rc_tlast tlast() clocked_by (user_clk) reset_by (user_reset);
        method tready(m_axis_rc_tready) enable((*inhigh*) EN_m_axis_rc_tready) clocked_by (user_clk) reset_by (user_reset);
        method m_axis_rc_tuser tuser() clocked_by (user_clk) reset_by (user_reset);
        method m_axis_rc_tvalid tvalid() clocked_by (user_clk) reset_by (user_reset);
    endinterface
    interface PciewrapPci_exp     pci_exp;
        method rxn(pci_exp_rxn) enable((*inhigh*) EN_pci_exp_rxn)  clocked_by (sys_clk) reset_by (sys_reset);
        method rxp(pci_exp_rxp) enable((*inhigh*) EN_pci_exp_rxp)  clocked_by (sys_clk) reset_by (sys_reset);
        method pci_exp_txn txn() clocked_by (sys_clk) reset_by (sys_reset);
        method pci_exp_txp txp() clocked_by (sys_clk) reset_by (sys_reset);
    endinterface
    interface PciewrapPcie     pcie;
        method cq_np_req(pcie_cq_np_req) enable((*inhigh*) EN_pcie_cq_np_req) clocked_by (user_clk) reset_by (user_reset);
        method pcie_cq_np_req_count cq_np_req_count() clocked_by (user_clk) reset_by (user_reset);
        method pcie_rq_seq_num rq_seq_num() clocked_by (user_clk) reset_by (user_reset);
        method pcie_rq_seq_num_vld rq_seq_num_vld() clocked_by (user_clk) reset_by (user_reset);
        method pcie_rq_tag rq_tag() clocked_by (user_clk) reset_by (user_reset);
        method pcie_rq_tag_vld rq_tag_vld() clocked_by (user_clk) reset_by (user_reset);
        method pcie_tfc_npd_av tfc_npd_av() clocked_by (user_clk) reset_by (user_reset);
        method pcie_tfc_nph_av tfc_nph_av() clocked_by (user_clk) reset_by (user_reset);
    endinterface
    interface PciewrapPipe     pipe;
        method rx_0_sigs(pipe_rx_0_sigs) enable((*inhigh*) EN_pipe_rx_0_sigs)  clocked_by (sys_clk) reset_by (sys_reset);
        method rx_1_sigs(pipe_rx_1_sigs) enable((*inhigh*) EN_pipe_rx_1_sigs)  clocked_by (sys_clk) reset_by (sys_reset);
        method rx_2_sigs(pipe_rx_2_sigs) enable((*inhigh*) EN_pipe_rx_2_sigs)  clocked_by (sys_clk) reset_by (sys_reset);
        method rx_3_sigs(pipe_rx_3_sigs) enable((*inhigh*) EN_pipe_rx_3_sigs)  clocked_by (sys_clk) reset_by (sys_reset);
        method rx_4_sigs(pipe_rx_4_sigs) enable((*inhigh*) EN_pipe_rx_4_sigs)  clocked_by (sys_clk) reset_by (sys_reset);
        method rx_5_sigs(pipe_rx_5_sigs) enable((*inhigh*) EN_pipe_rx_5_sigs)  clocked_by (sys_clk) reset_by (sys_reset);
        method rx_6_sigs(pipe_rx_6_sigs) enable((*inhigh*) EN_pipe_rx_6_sigs)  clocked_by (sys_clk) reset_by (sys_reset);
        method rx_7_sigs(pipe_rx_7_sigs) enable((*inhigh*) EN_pipe_rx_7_sigs)  clocked_by (sys_clk) reset_by (sys_reset);
        method pipe_tx_0_sigs tx_0_sigs();
        method pipe_tx_1_sigs tx_1_sigs();
        method pipe_tx_2_sigs tx_2_sigs();
        method pipe_tx_3_sigs tx_3_sigs();
        method pipe_tx_4_sigs tx_4_sigs();
        method pipe_tx_5_sigs tx_5_sigs();
        method pipe_tx_6_sigs tx_6_sigs();
        method pipe_tx_7_sigs tx_7_sigs();
    endinterface
    interface PciewrapS_axis_cc     s_axis_cc;
        method tdata(s_axis_cc_tdata) enable((*inhigh*) EN_s_axis_cc_tdata) clocked_by (user_clk) reset_by (user_reset);
        method tkeep(s_axis_cc_tkeep) enable((*inhigh*) EN_s_axis_cc_tkeep) clocked_by (user_clk) reset_by (user_reset);
        method tlast(s_axis_cc_tlast) enable((*inhigh*) EN_s_axis_cc_tlast) clocked_by (user_clk) reset_by (user_reset);
        method s_axis_cc_tready tready() clocked_by (user_clk) reset_by (user_reset);
        method tuser(s_axis_cc_tuser) enable((*inhigh*) EN_s_axis_cc_tuser) clocked_by (user_clk) reset_by (user_reset);
        method tvalid(s_axis_cc_tvalid) enable((*inhigh*) EN_s_axis_cc_tvalid) clocked_by (user_clk) reset_by (user_reset);
    endinterface
    interface PciewrapS_axis_rq     s_axis_rq;
        method tdata(s_axis_rq_tdata) enable((*inhigh*) EN_s_axis_rq_tdata) clocked_by (user_clk) reset_by (user_reset);
        method tkeep(s_axis_rq_tkeep) enable((*inhigh*) EN_s_axis_rq_tkeep) clocked_by (user_clk) reset_by (user_reset);
        method tlast(s_axis_rq_tlast) enable((*inhigh*) EN_s_axis_rq_tlast) clocked_by (user_clk) reset_by (user_reset);
        method s_axis_rq_tready tready() clocked_by (user_clk) reset_by (user_reset);
        method tuser(s_axis_rq_tuser) enable((*inhigh*) EN_s_axis_rq_tuser) clocked_by (user_clk) reset_by (user_reset);
        method tvalid(s_axis_rq_tvalid) enable((*inhigh*) EN_s_axis_rq_tvalid) clocked_by (user_clk) reset_by (user_reset);
    endinterface
    interface PciewrapUser     user;
        method user_app_rdy app_rdy() clocked_by (user_clk) reset_by (user_reset);
        method user_lnk_up lnk_up() clocked_by (user_clk) reset_by (user_reset);
    endinterface

    schedule (cfg.config_space_enable, cfg.current_speed, cfg.dpa_substate_change, cfg.ds_bus_number, cfg.ds_device_number, cfg.ds_function_number, cfg.ds_port_number, cfg.dsn, cfg.err_cor_in, cfg.err_cor_out, cfg.err_fatal_out, cfg.err_nonfatal_out, cfg.err_uncor_in, cfg.ext_function_number, cfg.ext_read_data, cfg.ext_read_data_valid, cfg.ext_read_received, cfg.ext_register_number, cfg.ext_write_byte_enable, cfg.ext_write_data, cfg.ext_write_received, cfg.fc_cpld, cfg.fc_cplh, cfg.fc_npd, cfg.fc_nph, cfg.fc_pd, cfg.fc_ph, cfg.fc_sel, cfg.flr_done, cfg.flr_in_process, cfg.function_power_state, cfg.function_status, cfg.hot_reset_in, cfg.hot_reset_out, cfg.interrupt_int, cfg.interrupt_msix_address, cfg.interrupt_msix_data, cfg.interrupt_msix_enable, cfg.interrupt_msix_fail, cfg.interrupt_msix_int, cfg.interrupt_msix_mask, cfg.interrupt_msix_sent, cfg.interrupt_msix_vf_enable, cfg.interrupt_msix_vf_mask, cfg.interrupt_pending, cfg.interrupt_sent, cfg.link_power_state, cfg.link_training_enable, cfg.ltr_enable, cfg.ltssm_state, cfg.max_payload, cfg.max_read_req, cfg.mgmt_addr, cfg.mgmt_byte_enable, cfg.mgmt_read, cfg.mgmt_read_data, cfg.mgmt_read_write_done, cfg.mgmt_write, cfg.mgmt_write_data, cfg.msg_received, cfg.msg_received_data, cfg.msg_received_type, cfg.msg_transmit, cfg.msg_transmit_data, cfg.msg_transmit_done, cfg.msg_transmit_type, cfg.negotiated_width, cfg.obff_enable, cfg.per_func_status_control, cfg.per_func_status_data, cfg.per_function_number, cfg.per_function_output_request, cfg.per_function_update_done, cfg.phy_link_down, cfg.phy_link_status, cfg.pl_status_change, cfg.power_state_change_ack, cfg.power_state_change_interrupt, cfg.rcb_status, cfg.subsys_vend_id, cfg.tph_requester_enable, cfg.tph_st_mode, cfg.vf_flr_done, cfg.vf_flr_in_process, cfg.vf_power_state, cfg.vf_status, cfg.vf_tph_requester_enable, cfg.vf_tph_st_mode, cfg_mgmt_type1.cfg_reg_access, cfg_req_pm_transition.l23_ready, common.commands_in, common.commands_out, int_pclk_sel.slave, int_qplllock.out, m_axis_cq.tdata, m_axis_cq.tkeep, m_axis_cq.tlast, m_axis_cq.tready, m_axis_cq.tuser, m_axis_cq.tvalid, m_axis_rc.tdata, m_axis_rc.tkeep, m_axis_rc.tlast, m_axis_rc.tready, m_axis_rc.tuser, m_axis_rc.tvalid, pci_exp.rxn, pci_exp.rxp, pci_exp.txn, pci_exp.txp, pcie.cq_np_req, pcie.cq_np_req_count, pcie.rq_seq_num, pcie.rq_seq_num_vld, pcie.rq_tag, pcie.rq_tag_vld, pcie.tfc_npd_av, pcie.tfc_nph_av, pipe.rx_0_sigs, pipe.rx_1_sigs, pipe.rx_2_sigs, pipe.rx_3_sigs, pipe.rx_4_sigs, pipe.rx_5_sigs, pipe.rx_6_sigs, pipe.rx_7_sigs, pipe.tx_0_sigs, pipe.tx_1_sigs, pipe.tx_2_sigs, pipe.tx_3_sigs, pipe.tx_4_sigs, pipe.tx_5_sigs, pipe.tx_6_sigs, pipe.tx_7_sigs, s_axis_cc.tdata, s_axis_cc.tkeep, s_axis_cc.tlast, s_axis_cc.tready, s_axis_cc.tuser, s_axis_cc.tvalid, s_axis_rq.tdata, s_axis_rq.tkeep, s_axis_rq.tlast, s_axis_rq.tready, s_axis_rq.tuser, s_axis_rq.tvalid, user.app_rdy, user.lnk_up) CF (cfg.config_space_enable, cfg.current_speed, cfg.dpa_substate_change, cfg.ds_bus_number, cfg.ds_device_number, cfg.ds_function_number, cfg.ds_port_number, cfg.dsn, cfg.err_cor_in, cfg.err_cor_out, cfg.err_fatal_out, cfg.err_nonfatal_out, cfg.err_uncor_in, cfg.ext_function_number, cfg.ext_read_data, cfg.ext_read_data_valid, cfg.ext_read_received, cfg.ext_register_number, cfg.ext_write_byte_enable, cfg.ext_write_data, cfg.ext_write_received, cfg.fc_cpld, cfg.fc_cplh, cfg.fc_npd, cfg.fc_nph, cfg.fc_pd, cfg.fc_ph, cfg.fc_sel, cfg.flr_done, cfg.flr_in_process, cfg.function_power_state, cfg.function_status, cfg.hot_reset_in, cfg.hot_reset_out, cfg.interrupt_int, cfg.interrupt_msix_address, cfg.interrupt_msix_data, cfg.interrupt_msix_enable, cfg.interrupt_msix_fail, cfg.interrupt_msix_int, cfg.interrupt_msix_mask, cfg.interrupt_msix_sent, cfg.interrupt_msix_vf_enable, cfg.interrupt_msix_vf_mask, cfg.interrupt_pending, cfg.interrupt_sent, cfg.link_power_state, cfg.link_training_enable, cfg.ltr_enable, cfg.ltssm_state, cfg.max_payload, cfg.max_read_req, cfg.mgmt_addr, cfg.mgmt_byte_enable, cfg.mgmt_read, cfg.mgmt_read_data, cfg.mgmt_read_write_done, cfg.mgmt_write, cfg.mgmt_write_data, cfg.msg_received, cfg.msg_received_data, cfg.msg_received_type, cfg.msg_transmit, cfg.msg_transmit_data, cfg.msg_transmit_done, cfg.msg_transmit_type, cfg.negotiated_width, cfg.obff_enable, cfg.per_func_status_control, cfg.per_func_status_data, cfg.per_function_number, cfg.per_function_output_request, cfg.per_function_update_done, cfg.phy_link_down, cfg.phy_link_status, cfg.pl_status_change, cfg.power_state_change_ack, cfg.power_state_change_interrupt, cfg.rcb_status, cfg.subsys_vend_id, cfg.tph_requester_enable, cfg.tph_st_mode, cfg.vf_flr_done, cfg.vf_flr_in_process, cfg.vf_power_state, cfg.vf_status, cfg.vf_tph_requester_enable, cfg.vf_tph_st_mode, cfg_mgmt_type1.cfg_reg_access, cfg_req_pm_transition.l23_ready, common.commands_in, common.commands_out, int_pclk_sel.slave, int_qplllock.out, m_axis_cq.tdata, m_axis_cq.tkeep, m_axis_cq.tlast, m_axis_cq.tready, m_axis_cq.tuser, m_axis_cq.tvalid, m_axis_rc.tdata, m_axis_rc.tkeep, m_axis_rc.tlast, m_axis_rc.tready, m_axis_rc.tuser, m_axis_rc.tvalid, pci_exp.rxn, pci_exp.rxp, pci_exp.txn, pci_exp.txp, pcie.cq_np_req, pcie.cq_np_req_count, pcie.rq_seq_num, pcie.rq_seq_num_vld, pcie.rq_tag, pcie.rq_tag_vld, pcie.tfc_npd_av, pcie.tfc_nph_av, pipe.rx_0_sigs, pipe.rx_1_sigs, pipe.rx_2_sigs, pipe.rx_3_sigs, pipe.rx_4_sigs, pipe.rx_5_sigs, pipe.rx_6_sigs, pipe.rx_7_sigs, pipe.tx_0_sigs, pipe.tx_1_sigs, pipe.tx_2_sigs, pipe.tx_3_sigs, pipe.tx_4_sigs, pipe.tx_5_sigs, pipe.tx_6_sigs, pipe.tx_7_sigs, s_axis_cc.tdata, s_axis_cc.tkeep, s_axis_cc.tlast, s_axis_cc.tready, s_axis_cc.tuser, s_axis_cc.tvalid, s_axis_rq.tdata, s_axis_rq.tkeep, s_axis_rq.tlast, s_axis_rq.tready, s_axis_rq.tuser, s_axis_rq.tvalid, user.app_rdy, user.lnk_up);
endmodule


rename to make units more apparent

rename to make units more apparent

// Copyright (c) 2013 Quanta Research Cambridge, Inc.

// Permission is hereby granted, free of charge, to any person
// obtaining a copy of this software and associated documentation
// files (the "Software"), to deal in the Software without
// restriction, including without limitation the rights to use, copy,
// modify, merge, publish, distribute, sublicense, and/or sell copies
// of the Software, and to permit persons to whom the Software is
// furnished to do so, subject to the following conditions:

// The above copyright notice and this permission notice shall be
// included in all copies or substantial portions of the Software.

// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
// EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
// NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS
// BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN
// ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
// CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
// SOFTWARE.

import FIFO::*;
import FIFOF::*;
import Vector::*;
import GetPut::*;
import ClientServer::*;

import Arith::*;
import Pipe::*;
import MemTypes::*;
import MemreadEngine::*;
import Pipe::*;
import HostInterface::*; // for DataBusWidth

`ifdef NumEngineServers
typedef `NumEngineServers NumEngineServers;
`else
typedef 1 NumEngineServers;
`endif
`ifdef NumOutstandingRequests
typedef `NumOutstandingRequests NumOutstandingRequests;
`else
typedef 2 NumOutstandingRequests;
`endif
`ifdef MemreadEngineBufferSize
Integer memreadEngineBufferSize=`MemreadEngineBufferSize;
`else
Integer memreadEngineBufferSize=256;
`endif

interface MemreadRequest;
   method Action startRead(Bit#(32) pointer, Bit#(32) offset, Bit#(32) numWords, Bit#(32) burstLen, Bit#(32) iterCnt);
   method Action getStateDbg();
endinterface

interface Memread;
   interface MemreadRequest request;
   interface MemReadClient#(DataBusWidth) dmaClient;
endinterface

interface MemreadIndication;
   method Action started(Bit#(32) numWords);
   method Action reportStateDbg(Bit#(32) reportType, Bit#(32) finished, Bit#(32) dataPipeNotEmpty);
   method Action readDone(Bit#(32) mismatchCount);
endinterface

typedef TDiv#(DataBusWidth,32) DataBusWords;

module mkMemread#(MemreadIndication indication) (Memread);

   Reg#(SGLId)   pointer <- mkReg(0);
   Reg#(Bit#(32))       numWords <- mkReg(0);
   Reg#(Bit#(32))       burstLen <- mkReg(0);
   Reg#(Bit#(32))    mismatchCnt <- mkReg(0);
   FIFO#(void)                cf <- mkSizedFIFO(1);

   Reg#(Bit#(32))                                   iterCnt <- mkReg(0);
   Reg#(Bit#(32))                                readOffset <- mkReg(0);
   Vector#(NumEngineServers, Reg#(Bit#(32)))       iterCnts <- replicateM(mkReg(0));
   Vector#(NumEngineServers, Reg#(Bit#(32)))    wordsToRead <- replicateM(mkReg(0));
   Vector#(NumEngineServers, Reg#(Bit#(32))) mismatchCounts <- replicateM(mkReg(0));
   MemreadEngineV#(DataBusWidth,NumOutstandingRequests,NumEngineServers) re <- mkMemreadEngineBuff(memreadEngineBufferSize);
   Vector#(NumEngineServers, FIFOF#(Bit#(32))) mismatchFifos <- replicateM(mkFIFOF);
   Bit#(MemOffsetSize) chunkBytes = (extend(numWords)/fromInteger(valueOf(NumEngineServers)))*4;

   Vector#(NumEngineServers, RangePipeIfc#(Bit#(32)))     rangePipeIfcs <- replicateM(mkRangePipeOut);
   function PipeOut#(a) getRangePipePipe(RangePipeIfc#(a) rpi); return rpi.pipe; endfunction
   Vector#(NumEngineServers, PipeOut#(Vector#(1,Bit#(32)))) rangePipes = map(mapPipe(replicate), map(getRangePipePipe, rangePipeIfcs));
   Vector#(NumEngineServers, PipeOut#(Vector#(DataBusWords,Bit#(32)))) srcGenPipes <- mapM(mkUnfunnel, rangePipes);
   function Vector#(DataBusWords,Bit#(32)) split(Bit#(DataBusWidth) v); return unpack(v); endfunction
   Vector#(NumEngineServers, PipeOut#(Vector#(DataBusWords,Bit#(32)))) readPipes <- mapM(mkMapPipe(split), re.dataPipes);

   function Vector#(n, Bool) vcompare(Vector#(n, a) x, Vector#(n, a) y) provisos (Eq#(a));
      return map(uncurry(eq), zip(x,y));
   endfunction
   Vector#(NumEngineServers, PipeOut#(Vector#(DataBusWords, Bool)))  mismatchPipes <- mapM(uncurry(mkJoinBuffered(vcompare)), zip(readPipes, srcGenPipes));

   Vector#(NumEngineServers, Reg#(Bool)) finishedReg <- replicateM(mkReg(False));

   for(Integer i = 0; i < valueOf(NumEngineServers); i=i+1) begin
      rule start (iterCnts[i] > 0);
	 re.readServers[i].request.put(MemengineCmd{sglId:pointer, base:extend(readOffset)+(fromInteger(i)*chunkBytes), len:truncate(chunkBytes), burstLen:truncate(burstLen*4)});
	 iterCnts[i] <= iterCnts[i]-1;
	 Bit#(32) base = (readOffset/4)+(fromInteger(i)*(truncate(chunkBytes)/4));
	 Bit#(32) limit = base + truncate(chunkBytes)/4;
	 let rangeConfig = RangeConfig { xbase: base, xlimit: limit, xstep: 1 };
	 rangePipeIfcs[i].start(rangeConfig);
	 $display("start %d, %d, %h", i, iterCnts[i], readOffset);
	 finishedReg[i] <= False;
      endrule
      rule finish;
	 $display("finish %d", i);
	 let rv <- re.readServers[i].response.get;
	 finishedReg[i] <= True;
      endrule
      rule check;
	 let bv <- toGet(mismatchPipes[i]).get();
	 let mismatch = !bv[0] || !bv[1];
	 if (mismatch) $display("mismatch bv[0] %d bv[1] %d\n", bv[0], bv[1]);
	 let mc = mismatchCounts[i] + (mismatch ? 1 : 0);

	 let newValuesToRead = wordsToRead[i] - fromInteger(valueOf(DataBusWords));

	 if (wordsToRead[i] <= fromInteger(valueOf(DataBusWords))) begin
	    $display("mismatch count %d", mc);
	    mismatchFifos[i].enq(mc);
	    mc = 0; // restart count
	    newValuesToRead = truncate(chunkBytes/4);
	 end
	 mismatchCounts[i] <= mc;
	 wordsToRead[i] <= newValuesToRead;

      endrule
   end

   PipeOut#(Vector#(NumEngineServers, Bit#(32))) mismatchCountsPipe <- mkJoinVector(id, map(toPipeOut, mismatchFifos));
   PipeOut#(Bit#(32)) mismatchCountPipe <- mkReducePipe(uncurry(add), mismatchCountsPipe);

   FIFO#(Bit#(2)) reportStateFifo <- mkFIFO();
   rule reportState;
      let v <- toGet(reportStateFifo).get();
	 Vector#(NumEngineServers, Bool) notEmpty = map(pipeOutNotEmpty, re.dataPipes);
	 indication.reportStateDbg(extend(v),
				   extend(pack(readVReg(finishedReg))),
				   extend(pack(notEmpty)));
   endrule

   rule indicate_finish;
      let mc <- toGet(mismatchCountPipe).get();
      mc = mc + mismatchCnt;
      if (iterCnt == 1) begin
	 cf.deq;
	 indication.readDone(mc);
	 mc = 0;
      end
      mismatchCnt <= mc;
      reportStateFifo.enq(1);
      iterCnt <= iterCnt - 1;
   endrule

   interface dmaClient = re.dmaClient;
   interface MemreadRequest request;
      method Action startRead(Bit#(32) rp, Bit#(32) off, Bit#(32) nw, Bit#(32) bl, Bit#(32) ic);
	 indication.started(nw);
	 pointer <= rp;
	 cf.enq(?);
	 numWords  <= nw;
	 burstLen  <= bl;
	 iterCnt <= ic;
	 readOffset <= off*4;
	 for(Integer i = 0; i < valueOf(NumEngineServers); i=i+1) begin
	    iterCnts[i] <= ic;
	    mismatchCounts[i] <= 0;
	    wordsToRead[i] <= truncate(chunkBytes/4);
	    finishedReg[i] <= False;
	 end
	 reportStateFifo.enq(0);
      endmethod
      method Action getStateDbg();
	 reportStateFifo.enq(2);
      endmethod
   endinterface
endmodule

// Copyright (c) 2013 Quanta Research Cambridge, Inc.

// Permission is hereby granted, free of charge, to any person
// obtaining a copy of this software and associated documentation
// files (the "Software"), to deal in the Software without
// restriction, including without limitation the rights to use, copy,
// modify, merge, publish, distribute, sublicense, and/or sell copies
// of the Software, and to permit persons to whom the Software is
// furnished to do so, subject to the following conditions:

// The above copyright notice and this permission notice shall be
// included in all copies or substantial portions of the Software.

// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
// EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
// NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS
// BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN
// ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
// CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
// SOFTWARE.

import FIFO::*;
import FIFOF::*;
import Vector::*;
import GetPut::*;
import ClientServer::*;

import Arith::*;
import Pipe::*;
import MemTypes::*;
import MemreadEngine::*;
import Pipe::*;
import HostInterface::*; // for DataBusWidth

`ifdef NumEngineServers
typedef `NumEngineServers NumEngineServers;
`else
typedef 1 NumEngineServers;
`endif
`ifdef NumOutstandingRequests
typedef `NumOutstandingRequests NumOutstandingRequests;
`else
typedef 2 NumOutstandingRequests;
`endif
`ifdef MemreadEngineBufferSize
Integer memreadEngineBufferSize=`MemreadEngineBufferSize;
`else
Integer memreadEngineBufferSize=256;
`endif

interface MemreadRequest;
   method Action startRead(Bit#(32) pointer, Bit#(32) offset, Bit#(32) numWords, Bit#(32) burstLen, Bit#(32) iterCnt);
   method Action getStateDbg();
endinterface

interface Memread;
   interface MemreadRequest request;
   interface MemReadClient#(DataBusWidth) dmaClient;
endinterface

interface MemreadIndication;
   method Action started(Bit#(32) numWords);
   method Action reportStateDbg(Bit#(32) reportType, Bit#(32) finished, Bit#(32) dataPipeNotEmpty);
   method Action readDone(Bit#(32) mismatchCount);
endinterface

typedef TDiv#(DataBusWidth,32) DataBusWords;

module mkMemread#(MemreadIndication indication) (Memread);

   Reg#(SGLId)   pointer <- mkReg(0);
   Reg#(Bit#(32))       numWords <- mkReg(0);
   Reg#(Bit#(32))       burstLen <- mkReg(0);
   Reg#(Bit#(32))    mismatchCnt <- mkReg(0);
   FIFO#(void)                cf <- mkSizedFIFO(1);

   Reg#(Bit#(32))                                   iterCnt <- mkReg(0);
   Reg#(Bit#(32))                                readOffset <- mkReg(0);
   Vector#(NumEngineServers, Reg#(Bit#(32)))       iterCnts <- replicateM(mkReg(0));
   Vector#(NumEngineServers, Reg#(Bit#(32)))   valuesToRead <- replicateM(mkReg(0));
   Vector#(NumEngineServers, Reg#(Bit#(32))) mismatchCounts <- replicateM(mkReg(0));
   MemreadEngineV#(DataBusWidth,NumOutstandingRequests,NumEngineServers) re <- mkMemreadEngineBuff(memreadEngineBufferSize);
   Vector#(NumEngineServers, FIFOF#(Bit#(32))) mismatchFifos <- replicateM(mkFIFOF);
   Bit#(MemOffsetSize) chunk = (extend(numWords)/fromInteger(valueOf(NumEngineServers)))*4;

   Vector#(NumEngineServers, RangePipeIfc#(Bit#(32)))     rangePipeIfcs <- replicateM(mkRangePipeOut);
   function PipeOut#(a) getRangePipePipe(RangePipeIfc#(a) rpi); return rpi.pipe; endfunction
   Vector#(NumEngineServers, PipeOut#(Vector#(1,Bit#(32)))) rangePipes = map(mapPipe(replicate), map(getRangePipePipe, rangePipeIfcs));
   Vector#(NumEngineServers, PipeOut#(Vector#(DataBusWords,Bit#(32)))) srcGenPipes <- mapM(mkUnfunnel, rangePipes);
   function Vector#(DataBusWords,Bit#(32)) split(Bit#(DataBusWidth) v); return unpack(v); endfunction
   Vector#(NumEngineServers, PipeOut#(Vector#(DataBusWords,Bit#(32)))) readPipes <- mapM(mkMapPipe(split), re.dataPipes);

   function Vector#(n, Bool) vcompare(Vector#(n, a) x, Vector#(n, a) y) provisos (Eq#(a));
      return map(uncurry(eq), zip(x,y));
   endfunction
   Vector#(NumEngineServers, PipeOut#(Vector#(DataBusWords, Bool)))  mismatchPipes <- mapM(uncurry(mkJoinBuffered(vcompare)), zip(readPipes, srcGenPipes));

   Vector#(NumEngineServers, Reg#(Bool)) finishedReg <- replicateM(mkReg(False));

   for(Integer i = 0; i < valueOf(NumEngineServers); i=i+1) begin
      rule start (iterCnts[i] > 0);
	 re.readServers[i].request.put(MemengineCmd{sglId:pointer, base:extend(readOffset)+(fromInteger(i)*chunk), len:truncate(chunk), burstLen:truncate(burstLen*4)});
	 iterCnts[i] <= iterCnts[i]-1;
	 Bit#(32) base = (readOffset/4)+(fromInteger(i)*(truncate(chunk)/4));
	 Bit#(32) limit = base + truncate(chunk)/4;
	 let rangeConfig = RangeConfig { xbase: base, xlimit: limit, xstep: 1 };
	 rangePipeIfcs[i].start(rangeConfig);
	 $display("start %d, %d, %h", i, iterCnts[i], readOffset);
	 finishedReg[i] <= False;
      endrule
      rule finish;
	 $display("finish %d", i);
	 let rv <- re.readServers[i].response.get;
	 finishedReg[i] <= True;
      endrule
      rule check;
	 let bv <- toGet(mismatchPipes[i]).get();
	 let mismatch = !bv[0] || !bv[1];
	 if (mismatch) $display("mismatch bv[0] %d bv[1] %d\n", bv[0], bv[1]);
	 let mc = mismatchCounts[i] + (mismatch ? 1 : 0);

	 let newValuesToRead = valuesToRead[i] - fromInteger(valueOf(DataBusWords));

	 if (valuesToRead[i] <= fromInteger(valueOf(DataBusWords))) begin
	    $display("mismatch count %d", mc);
	    mismatchFifos[i].enq(mc);
	    mc = 0; // restart count
	    newValuesToRead = truncate(chunk/4);
	 end
	 mismatchCounts[i] <= mc;
	 valuesToRead[i] <= newValuesToRead;

      endrule
   end

   PipeOut#(Vector#(NumEngineServers, Bit#(32))) mismatchCountsPipe <- mkJoinVector(id, map(toPipeOut, mismatchFifos));
   PipeOut#(Bit#(32)) mismatchCountPipe <- mkReducePipe(uncurry(add), mismatchCountsPipe);

   FIFO#(Bit#(2)) reportStateFifo <- mkFIFO();
   rule reportState;
      let v <- toGet(reportStateFifo).get();
	 Vector#(NumEngineServers, Bool) notEmpty = map(pipeOutNotEmpty, re.dataPipes);
	 indication.reportStateDbg(extend(v),
				   extend(pack(readVReg(finishedReg))),
				   extend(pack(notEmpty)));
   endrule

   rule indicate_finish;
      let mc <- toGet(mismatchCountPipe).get();
      mc = mc + mismatchCnt;
      if (iterCnt == 1) begin
	 cf.deq;
	 indication.readDone(mc);
	 mc = 0;
      end
      mismatchCnt <= mc;
      reportStateFifo.enq(1);
      iterCnt <= iterCnt - 1;
   endrule

   interface dmaClient = re.dmaClient;
   interface MemreadRequest request;
      method Action startRead(Bit#(32) rp, Bit#(32) off, Bit#(32) nw, Bit#(32) bl, Bit#(32) ic);
	 indication.started(nw);
	 pointer <= rp;
	 cf.enq(?);
	 numWords  <= nw;
	 burstLen  <= bl;
	 iterCnt <= ic;
	 readOffset <= off*4;
	 for(Integer i = 0; i < valueOf(NumEngineServers); i=i+1) begin
	    iterCnts[i] <= ic;
	    mismatchCounts[i] <= 0;
	    valuesToRead[i] <= truncate(chunk/4);
	    finishedReg[i] <= False;
	 end
	 reportStateFifo.enq(0);
      endmethod
      method Action getStateDbg();
	 reportStateFifo.enq(2);
      endmethod
   endinterface
endmodule


Cleanup logic memory request interface

Cleanup logic memory request interface

// Copyright (c) 2013 Quanta Research Cambridge, Inc.

// Permission is hereby granted, free of charge, to any person
// obtaining a copy of this software and associated documentation
// files (the "Software"), to deal in the Software without
// restriction, including without limitation the rights to use, copy,
// modify, merge, publish, distribute, sublicense, and/or sell copies
// of the Software, and to permit persons to whom the Software is
// furnished to do so, subject to the following conditions:

// The above copyright notice and this permission notice shall be
// included in all copies or substantial portions of the Software.

// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
// EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
// NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS
// BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN
// ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
// CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
// SOFTWARE.
import FIFOF::*;
import Adapter::*;
import Vector::*;
import Connectable::*;
import BRAMFIFO::*;
import GetPut::*;
import ClientServer::*;

import ToolConfig::*;
import Pipe::*;
import ToolMemory::*;
import DefaultValue::*;

`include "ProjectConfig.bsv"

typedef 44 MemOffsetSize;
`ifdef MemTagSize
typedef `MemTagSize MemTagSize;
`else
typedef 6 MemTagSize;
`endif
typedef `BurstLenSize BurstLenSize;

`ifndef USE_ACP
`ifdef PCIE3
// as configured, the Xilinx gen3 PCIe core supports 5 bit tags, and
// we need to use unique tags for all transactions in flight. Since
// MemServer uses the same tag numbers for reads and writes, we use
// tag[4] to distinguish the two, leaving 4 bits for unique tags.
// TODO: There is an option for longer tags in the gen3 core.
typedef 16 MemServerTags;
`else
typedef 32 MemServerTags;
`endif
`else
typedef 8 MemServerTags;
`endif
`ifdef DataBusWidth
typedef TDiv#(`DataBusWidth,8) ByteEnableSize;
`else
typedef TDiv#(64,8) ByteEnableSize;
`endif

// memory request with physical addresses.
// these can be transmitted directly to the bus master
typedef struct {
   Bit#(addrWidth) addr;
   Bit#(BurstLenSize) burstLen;
   Bit#(MemTagSize) tag;
`ifdef BYTE_ENABLES
   Bit#(TDiv#(dataBusWidth,8)) firstbe; // maybe we only need lastbe
   Bit#(TDiv#(dataBusWidth,8)) lastbe;
`endif
   } PhysMemRequest#(numeric type addrWidth, numeric type dataBusWidth) deriving (Bits);

instance DefaultValue#(PhysMemRequest#(addrWidth,dataBusWidth));
   defaultValue = PhysMemRequest { addr: 0, burstLen: 0, tag: 0
`ifdef BYTE_ENABLES
                                  , firstbe: maxBound, lastbe: maxBound
`endif
      };
endinstance

// memory payload
typedef struct {
   Bit#(dsz) data;
   Bit#(MemTagSize) tag;
   Bool last;
   } MemData#(numeric type dsz) deriving (Bits);

typeclass ReqByteEnables#(type t, numeric type besz);
   function Bit#(besz) reqFirstByteEnable(t req);
   function Bit#(besz) reqLastByteEnable(t req);
endtypeclass
instance ReqByteEnables#(PhysMemRequest#(addrWidth,dataBusWidth),TDiv#(dataBusWidth,8));
`ifdef BYTE_ENABLES
   function Bit#(TDiv#(dataBusWidth,8)) reqFirstByteEnable(PhysMemRequest#(addrWidth,dataBusWidth) req); return req.firstbe; endfunction
   function Bit#(TDiv#(dataBusWidth,8)) reqLastByteEnable(PhysMemRequest#(addrWidth,dataBusWidth) req); return req.lastbe; endfunction
`else
   function Bit#(TDiv#(dataBusWidth,8)) reqFirstByteEnable(PhysMemRequest#(addrWidth,dataBusWidth) req); return maxBound; endfunction
   function Bit#(TDiv#(dataBusWidth,8)) reqLastByteEnable(PhysMemRequest#(addrWidth,dataBusWidth) req); return maxBound; endfunction
`endif
endinstance

///////////////////////////////////////////////////////////////////////////////////
//

typedef struct {
   Bit#(dsz) data;
   Bit#(MemTagSize) tag;
   Bool first;
   Bool last;
   } MemDataF#(numeric type dsz) deriving (Bits);

//
///////////////////////////////////////////////////////////////////////////////////

//
///////////////////////////////////////////////////////////////////////////////////
//

interface PhysMemSlave#(numeric type addrWidth, numeric type dataWidth);
   interface PhysMemReadServer#(addrWidth, dataWidth) read_server;
   interface PhysMemWriteServer#(addrWidth, dataWidth) write_server;
endinterface

interface PhysMemMaster#(numeric type addrWidth, numeric type dataWidth);
   interface PhysMemReadClient#(addrWidth, dataWidth) read_client;
   interface PhysMemWriteClient#(addrWidth, dataWidth) write_client;
endinterface

interface PhysMemReadClient#(numeric type asz, numeric type dsz);
   interface Get#(PhysMemRequest#(asz,dsz))    readReq;
   interface Put#(MemData#(dsz)) readData;
endinterface

interface PhysMemWriteClient#(numeric type asz, numeric type dsz);
   interface Get#(PhysMemRequest#(asz,dsz))    writeReq;
   interface Get#(MemData#(dsz)) writeData;
   interface Put#(Bit#(MemTagSize))       writeDone;
endinterface

interface PhysMemReadServer#(numeric type asz, numeric type dsz);
   interface Put#(PhysMemRequest#(asz,dsz)) readReq;
   interface Get#(MemData#(dsz))     readData;
endinterface

interface PhysMemWriteServer#(numeric type asz, numeric type dsz);
   interface Put#(PhysMemRequest#(asz,dsz)) writeReq;
   interface Put#(MemData#(dsz))     writeData;
   interface Get#(Bit#(MemTagSize))           writeDone;
endinterface

//
///////////////////////////////////////////////////////////////////////////////////

instance Connectable#(PhysMemReadClient#(asz,dsz), PhysMemReadServer#(asz,dsz));
   module mkConnection#(PhysMemReadClient#(asz,dsz) source, PhysMemReadServer#(asz,dsz) sink)(Empty);
      rule mr_request;
         let req <- source.readReq.get();
         sink.readReq.put(req);
      endrule
      rule mr_response;
         let resp <- sink.readData.get();
         source.readData.put(resp);
      endrule
   endmodule
endinstance

instance Connectable#(PhysMemWriteClient#(asz,dsz), PhysMemWriteServer#(asz,dsz));
   module mkConnection#(PhysMemWriteClient#(asz,dsz) source, PhysMemWriteServer#(asz,dsz) sink)(Empty);
      rule mw_request;
         let req <- source.writeReq.get();
         sink.writeReq.put(req);
      endrule
      rule mw_response;
         let resp <- source.writeData.get();
         sink.writeData.put(resp);
      endrule
      rule mw_done;
         let resp <- sink.writeDone.get();
         source.writeDone.put(resp);
      endrule
   endmodule
endinstance

instance Connectable#(PhysMemMaster#(addrWidth, busWidth), PhysMemSlave#(addrWidth, busWidth));
   module mkConnection#(PhysMemMaster#(addrWidth, busWidth) m, PhysMemSlave#(addrWidth, busWidth) s)(Empty);
      mkConnection(m.read_client.readReq, s.read_server.readReq);
      mkConnection(s.read_server.readData, m.read_client.readData);
      mkConnection(m.write_client.writeReq, s.write_server.writeReq);
      mkConnection(m.write_client.writeData, s.write_server.writeData);
      mkConnection(s.write_server.writeDone, m.write_client.writeDone);
   endmodule
endinstance

// this is used for debugging MemToPcie/PcieToMem in BsimTop.bsv
instance Connectable#(PhysMemMaster#(32, busWidth), PhysMemSlave#(40, busWidth));
   module mkConnection#(PhysMemMaster#(32, busWidth) m, PhysMemSlave#(40, busWidth) s)(Empty);
      //mkConnection(m.read_client.readReq, s.read_server.readReq);
      rule readreq;
         let req <- m.read_client.readReq.get();
         s.read_server.readReq.put(PhysMemRequest { addr: extend(req.addr), burstLen: req.burstLen, tag: req.tag
`ifdef BYTE_ENABLES
                                                   , firstbe: req.firstbe, lastbe: req.lastbe
`endif
            });
      endrule

      mkConnection(s.read_server.readData, m.read_client.readData);
      //mkConnection(m.write_client.writeReq, s.write_server.writeReq);
      rule writereq;
         let req <- m.write_client.writeReq.get();
         s.write_server.writeReq.put(PhysMemRequest { addr: extend(req.addr), burstLen: req.burstLen, tag: req.tag
`ifdef BYTE_ENABLES
                                                     , firstbe: req.firstbe, lastbe: req.lastbe
`endif
        });
      endrule
      mkConnection(m.write_client.writeData, s.write_server.writeData);
      mkConnection(s.write_server.writeDone, m.write_client.writeDone);
   endmodule
endinstance

function Bool isQuadWordAligned(Bit#(7) lower_addr);
   return (lower_addr[2:0]==3'b0);
endfunction

function Put#(t) null_put();
   return (interface Put;
              method Action put(t x) if (False);
                 noAction;
              endmethod
           endinterface);
endfunction

function Get#(t) null_get();
   return (interface Get;
              method ActionValue#(t) get() if (False);
                 return ?;
              endmethod
           endinterface);
endfunction

function  PhysMemWriteClient#(addrWidth, busWidth) null_phys_mem_write_client();
   return (interface PhysMemWriteClient;
              interface Get writeReq = null_get;
              interface Get writeData = null_get;
              interface Put writeDone = null_put;
           endinterface);
endfunction

function  PhysMemReadClient#(addrWidth, busWidth) null_phys_mem_read_client();
   return (interface PhysMemReadClient;
              interface Get readReq = null_get;
              interface Put readData = null_put;
           endinterface);
endfunction

// Copyright (c) 2013 Quanta Research Cambridge, Inc.

// Permission is hereby granted, free of charge, to any person
// obtaining a copy of this software and associated documentation
// files (the "Software"), to deal in the Software without
// restriction, including without limitation the rights to use, copy,
// modify, merge, publish, distribute, sublicense, and/or sell copies
// of the Software, and to permit persons to whom the Software is
// furnished to do so, subject to the following conditions:

// The above copyright notice and this permission notice shall be
// included in all copies or substantial portions of the Software.

// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
// EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
// NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS
// BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN
// ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
// CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
// SOFTWARE.
import FIFOF::*;
import Adapter::*;
import Vector::*;
import Connectable::*;
import BRAMFIFO::*;
import GetPut::*;
import ClientServer::*;

import ToolConfig::*;
import Pipe::*;
import ToolMemory::*;
import DefaultValue::*;

`include "ProjectConfig.bsv"

typedef Bit#(32) SGLId;
typedef 44 MemOffsetSize;
`ifdef MemTagSize
typedef `MemTagSize MemTagSize;
`else
typedef 6 MemTagSize;
`endif
typedef `BurstLenSize BurstLenSize;

`ifndef USE_ACP
`ifdef PCIE3
// as configured, the Xilinx gen3 PCIe core supports 5 bit tags, and
// we need to use unique tags for all transactions in flight. Since
// MemServer uses the same tag numbers for reads and writes, we use
// tag[4] to distinguish the two, leaving 4 bits for unique tags.
// TODO: There is an option for longer tags in the gen3 core.
typedef 16 MemServerTags;
`else
typedef 32 MemServerTags;
`endif
`else
typedef 8 MemServerTags;
`endif
`ifdef DataBusWidth
typedef TDiv#(`DataBusWidth,8) ByteEnableSize;
`else
typedef TDiv#(64,8) ByteEnableSize;
`endif

// memory request with physical addresses.
// these can be transmitted directly to the bus master
typedef struct {
   Bit#(addrWidth) addr;
   Bit#(BurstLenSize) burstLen;
   Bit#(MemTagSize) tag;
`ifdef BYTE_ENABLES
   Bit#(TDiv#(dataBusWidth,8)) firstbe; // maybe we only need lastbe
   Bit#(TDiv#(dataBusWidth,8)) lastbe;
`endif
   } PhysMemRequest#(numeric type addrWidth, numeric type dataBusWidth) deriving (Bits);

instance DefaultValue#(PhysMemRequest#(addrWidth,dataBusWidth));
   defaultValue = PhysMemRequest { addr: 0, burstLen: 0, tag: 0
`ifdef BYTE_ENABLES
                                  , firstbe: maxBound, lastbe: maxBound
`endif
      };
endinstance

// memory request with "virtual" addresses.
// these need to be translated before they can be send to the bus
typedef struct {
   SGLId sglId;
   Bit#(MemOffsetSize) offset;
   Bit#(BurstLenSize) burstLen;
   Bit#(MemTagSize)  tag;
`ifdef BYTE_ENABLES
   Bit#(ByteEnableSize) firstbe; // maybe we only need lastbe
   Bit#(ByteEnableSize) lastbe;
`endif
   } MemRequest deriving (Bits);

instance DefaultValue#(MemRequest);
   defaultValue = MemRequest {
      sglId: 0, offset: 0, burstLen: 0, tag: 0
`ifdef BYTE_ENABLES
      , firstbe: maxBound, lastbe: maxBound
`endif
      };
endinstance

// memory payload
typedef struct {
   Bit#(dsz) data;
   Bit#(MemTagSize) tag;
   Bool last;
   } MemData#(numeric type dsz) deriving (Bits);

typeclass ReqByteEnables#(type t, numeric type besz);
   function Bit#(besz) reqFirstByteEnable(t req);
   function Bit#(besz) reqLastByteEnable(t req);
endtypeclass
instance ReqByteEnables#(PhysMemRequest#(addrWidth,dataBusWidth),TDiv#(dataBusWidth,8));
`ifdef BYTE_ENABLES
   function Bit#(TDiv#(dataBusWidth,8)) reqFirstByteEnable(PhysMemRequest#(addrWidth,dataBusWidth) req); return req.firstbe; endfunction
   function Bit#(TDiv#(dataBusWidth,8)) reqLastByteEnable(PhysMemRequest#(addrWidth,dataBusWidth) req); return req.lastbe; endfunction
`else
   function Bit#(TDiv#(dataBusWidth,8)) reqFirstByteEnable(PhysMemRequest#(addrWidth,dataBusWidth) req); return maxBound; endfunction
   function Bit#(TDiv#(dataBusWidth,8)) reqLastByteEnable(PhysMemRequest#(addrWidth,dataBusWidth) req); return maxBound; endfunction
`endif
endinstance
instance ReqByteEnables#(MemRequest,ByteEnableSize);
`ifdef BYTE_ENABLES
   function Bit#(ByteEnableSize) reqFirstByteEnable(MemRequest req); return req.firstbe; endfunction
   function Bit#(ByteEnableSize) reqLastByteEnable(MemRequest req); return req.lastbe; endfunction
`else
   function Bit#(ByteEnableSize) reqFirstByteEnable(MemRequest req); return maxBound; endfunction
   function Bit#(ByteEnableSize) reqLastByteEnable(MemRequest req); return maxBound; endfunction
`endif
endinstance

///////////////////////////////////////////////////////////////////////////////////
//

typedef struct {
   Bit#(dsz) data;
   Bit#(MemTagSize) tag;
   Bool first;
   Bool last;
   } MemDataF#(numeric type dsz) deriving (Bits);

typedef struct {
   Bit#(MemTagSize) tag;
   Bit#(32)         cycles;
   } MemRequestCycles deriving (Bits);

//
///////////////////////////////////////////////////////////////////////////////////

///////////////////////////////////////////////////////////////////////////////////
//

interface MemReadClient#(numeric type dsz);
   interface Get#(MemRequest)    readReq;
   interface Put#(MemData#(dsz)) readData;
endinterface

interface MemWriteClient#(numeric type dsz);
   interface Get#(MemRequest)    writeReq;
   interface Get#(MemData#(dsz)) writeData;
   interface Put#(Bit#(MemTagSize))       writeDone;
endinterface

interface MemReadServer#(numeric type dsz);
   interface Put#(MemRequest) readReq;
   interface Get#(MemData#(dsz))     readData;
endinterface

interface MemWriteServer#(numeric type dsz);
   interface Put#(MemRequest) writeReq;
   interface Put#(MemData#(dsz))     writeData;
   interface Get#(Bit#(MemTagSize))           writeDone;
endinterface

interface MemServer#(numeric type dataWidth);
   interface MemReadServer#(dataWidth) readServer;
   interface MemWriteServer#(dataWidth) writeServer;
endinterface

//
///////////////////////////////////////////////////////////////////////////////////
//

interface PhysMemSlave#(numeric type addrWidth, numeric type dataWidth);
   interface PhysMemReadServer#(addrWidth, dataWidth) read_server;
   interface PhysMemWriteServer#(addrWidth, dataWidth) write_server;
endinterface

interface PhysMemMaster#(numeric type addrWidth, numeric type dataWidth);
   interface PhysMemReadClient#(addrWidth, dataWidth) read_client;
   interface PhysMemWriteClient#(addrWidth, dataWidth) write_client;
endinterface

interface PhysMemReadClient#(numeric type asz, numeric type dsz);
   interface Get#(PhysMemRequest#(asz,dsz))    readReq;
   interface Put#(MemData#(dsz)) readData;
endinterface

interface PhysMemWriteClient#(numeric type asz, numeric type dsz);
   interface Get#(PhysMemRequest#(asz,dsz))    writeReq;
   interface Get#(MemData#(dsz)) writeData;
   interface Put#(Bit#(MemTagSize))       writeDone;
endinterface

interface PhysMemReadServer#(numeric type asz, numeric type dsz);
   interface Put#(PhysMemRequest#(asz,dsz)) readReq;
   interface Get#(MemData#(dsz))     readData;
endinterface

interface PhysMemWriteServer#(numeric type asz, numeric type dsz);
   interface Put#(PhysMemRequest#(asz,dsz)) writeReq;
   interface Put#(MemData#(dsz))     writeData;
   interface Get#(Bit#(MemTagSize))           writeDone;
endinterface

//
///////////////////////////////////////////////////////////////////////////////////

instance Connectable#(MemReadClient#(dsz), MemReadServer#(dsz));
   module mkConnection#(MemReadClient#(dsz) source, MemReadServer#(dsz) sink)(Empty);
      rule mr_request;
         let req <- source.readReq.get();
         sink.readReq.put(req);
      endrule
      rule mr_response;
         let resp <- sink.readData.get();
         source.readData.put(resp);
      endrule
   endmodule
endinstance

instance Connectable#(MemWriteClient#(dsz), MemWriteServer#(dsz));
   module mkConnection#(MemWriteClient#(dsz) source, MemWriteServer#(dsz) sink)(Empty);
      rule mw_request;
         let req <- source.writeReq.get();
         sink.writeReq.put(req);
      endrule
      rule mw_response;
         let resp <- source.writeData.get();
         sink.writeData.put(resp);
      endrule
      rule mw_done;
         let resp <- sink.writeDone.get();
         source.writeDone.put(resp);
      endrule
   endmodule
endinstance

instance Connectable#(PhysMemReadClient#(asz,dsz), PhysMemReadServer#(asz,dsz));
   module mkConnection#(PhysMemReadClient#(asz,dsz) source, PhysMemReadServer#(asz,dsz) sink)(Empty);
      rule mr_request;
         let req <- source.readReq.get();
         sink.readReq.put(req);
      endrule
      rule mr_response;
         let resp <- sink.readData.get();
         source.readData.put(resp);
      endrule
   endmodule
endinstance

instance Connectable#(PhysMemWriteClient#(asz,dsz), PhysMemWriteServer#(asz,dsz));
   module mkConnection#(PhysMemWriteClient#(asz,dsz) source, PhysMemWriteServer#(asz,dsz) sink)(Empty);
      rule mw_request;
         let req <- source.writeReq.get();
         sink.writeReq.put(req);
      endrule
      rule mw_response;
         let resp <- source.writeData.get();
         sink.writeData.put(resp);
      endrule
      rule mw_done;
         let resp <- sink.writeDone.get();
         source.writeDone.put(resp);
      endrule
   endmodule
endinstance

instance Connectable#(PhysMemMaster#(addrWidth, busWidth), PhysMemSlave#(addrWidth, busWidth));
   module mkConnection#(PhysMemMaster#(addrWidth, busWidth) m, PhysMemSlave#(addrWidth, busWidth) s)(Empty);
      mkConnection(m.read_client.readReq, s.read_server.readReq);
      mkConnection(s.read_server.readData, m.read_client.readData);
      mkConnection(m.write_client.writeReq, s.write_server.writeReq);
      mkConnection(m.write_client.writeData, s.write_server.writeData);
      mkConnection(s.write_server.writeDone, m.write_client.writeDone);
   endmodule
endinstance

// this is used for debugging MemToPcie/PcieToMem in BsimTop.bsv
instance Connectable#(PhysMemMaster#(32, busWidth), PhysMemSlave#(40, busWidth));
   module mkConnection#(PhysMemMaster#(32, busWidth) m, PhysMemSlave#(40, busWidth) s)(Empty);
      //mkConnection(m.read_client.readReq, s.read_server.readReq);
      rule readreq;
         let req <- m.read_client.readReq.get();
         s.read_server.readReq.put(PhysMemRequest { addr: extend(req.addr), burstLen: req.burstLen, tag: req.tag
`ifdef BYTE_ENABLES
                                                   , firstbe: req.firstbe, lastbe: req.lastbe
`endif
            });
      endrule

      mkConnection(s.read_server.readData, m.read_client.readData);
      //mkConnection(m.write_client.writeReq, s.write_server.writeReq);
      rule writereq;
         let req <- m.write_client.writeReq.get();
         s.write_server.writeReq.put(PhysMemRequest { addr: extend(req.addr), burstLen: req.burstLen, tag: req.tag
`ifdef BYTE_ENABLES
                                                     , firstbe: req.firstbe, lastbe: req.lastbe
`endif
        });
      endrule
      mkConnection(m.write_client.writeData, s.write_server.writeData);
      mkConnection(s.write_server.writeDone, m.write_client.writeDone);
   endmodule
endinstance

function Bool isQuadWordAligned(Bit#(7) lower_addr);
   return (lower_addr[2:0]==3'b0);
endfunction

function Put#(t) null_put();
   return (interface Put;
              method Action put(t x) if (False);
                 noAction;
              endmethod
           endinterface);
endfunction

function Get#(t) null_get();
   return (interface Get;
              method ActionValue#(t) get() if (False);
                 return ?;
              endmethod
           endinterface);
endfunction

function  PhysMemWriteClient#(addrWidth, busWidth) null_phys_mem_write_client();
   return (interface PhysMemWriteClient;
              interface Get writeReq = null_get;
              interface Get writeData = null_get;
              interface Put writeDone = null_put;
           endinterface);
endfunction

function  PhysMemReadClient#(addrWidth, busWidth) null_phys_mem_read_client();
   return (interface PhysMemReadClient;
              interface Get readReq = null_get;
              interface Put readData = null_put;
           endinterface);
endfunction

function  MemWriteClient#(busWidth) null_mem_write_client();
   return (interface MemWriteClient;
              interface Get writeReq = null_get;
              interface Get writeData = null_get;
              interface Put writeDone = null_put;
           endinterface);
endfunction

function  MemReadClient#(busWidth) null_mem_read_client();
   return (interface MemReadClient;
              interface Get readReq = null_get;
              interface Put readData = null_put;
           endinterface);
endfunction


gen2 support

gen2 support

// Copyright (c) 2014 Quanta Research Cambridge, Inc.

// Permission is hereby granted, free of charge, to any person
// obtaining a copy of this software and associated documentation
// files (the "Software"), to deal in the Software without
// restriction, including without limitation the rights to use, copy,
// modify, merge, publish, distribute, sublicense, and/or sell copies
// of the Software, and to permit persons to whom the Software is
// furnished to do so, subject to the following conditions:

// The above copyright notice and this permission notice shall be
// included in all copies or substantial portions of the Software.

// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
// EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
// NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS
// BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN
// ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
// CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
// SOFTWARE.

////////////////////////////// common /////////////////////////////////

`ifndef DataBusWidth
`define DataBusWidth 64
`endif

typedef `PhysAddrWidth PhysAddrWidth;
typedef `SlaveDataBusWidth SlaveDataBusWidth;
typedef `DataBusWidth DataBusWidth;
typedef `NumberOfMasters NumberOfMasters;
typedef `NumberOfTiles NumberOfTiles;

////////////////////////////// Bsim /////////////////////////////////
`ifdef BsimHostTypeIF

import Vector            :: *;
import AxiMasterSlave    :: *;
import MemTypes          :: *;

// this interface should allow for different master and slave bus paraters;
interface BsimHost#(numeric type clientAddrWidth, numeric type clientBusWidth, numeric type clientIdWidth,
		    numeric type serverAddrWidth, numeric type serverBusWidth, numeric type serverIdWidth,
		    numeric type nSlaves);
   interface PhysMemMaster#(clientAddrWidth, clientBusWidth)  mem_client;
   interface Vector#(nSlaves,PhysMemSlave#(serverAddrWidth,  serverBusWidth))  mem_servers;
   interface Clock derivedClock;
   interface Reset derivedReset;
endinterface

typedef BsimHost#(32,32,12,40,DataBusWidth,6,NumberOfMasters) HostType;
`endif

////////////////////////////// Xsim /////////////////////////////////
`ifdef XsimHostTypeIF

import Vector            :: *;
import AxiMasterSlave    :: *;
import MemTypes          :: *;

// this interface should allow for different master and slave bus paraters;
interface XsimHost;
   interface Clock derivedClock;
   interface Reset derivedReset;
endinterface

typedef XsimHost HostType;
`endif

////////////////////////////// PciE /////////////////////////////////
`ifndef PcieHostIF
`ifdef PcieHostTypeIF
`define PcieHostIF
`endif
`endif

`ifdef PcieHostIF

import Vector            :: *;
import GetPut            :: *;
import ClientServer      :: *;
import BRAM              :: *;
import PCIE              :: *;
import Bscan             :: *;
import PcieCsr           :: *;
import PcieTracer        :: *;
import MemTypes          :: *;
`ifndef BSIM
`ifdef XILINX
`ifdef PCIE1
import PCIEWRAPPER       :: *;
import PcieEndpointX7    :: *;
`endif // pcie1
`ifdef PCIE2
import PCIEWRAPPER2       :: *;
import PcieEndpointX7Gen2 :: *;
`endif // pcie2
`ifdef PCIE3
import PCIEWRAPPER3      :: *;
import Pcie3EndpointX7   :: *;
`endif
`elsif ALTERA
import PcieEndpointS5    :: *;
`elsif VSIM
import PcieEndpointS5    :: *;
`endif
`endif
typedef 40 PciePhysAddrWidth;
interface PcieHost#(numeric type dsz, numeric type nSlaves);
   interface Vector#(16,ReadOnly_MSIX_Entry)     msixEntry;
   interface PhysMemMaster#(32,32)                   master;
   interface Vector#(nSlaves,PhysMemSlave#(PciePhysAddrWidth,dsz))  slave;
   interface Put#(Tuple2#(Bit#(64),Bit#(32)))    interruptRequest;
   interface Client#(TLPData#(16), TLPData#(16)) pci;
   interface Put#(TimestampedTlpData) trace;
`ifndef PCIE_NO_BSCAN
   interface BscanTop bscanif;
`else
   interface BRAMServer#(Bit#(TAdd#(TlpTraceAddrSize,1)), TimestampedTlpData) traceBramServer;
`endif
endinterface

interface PcieHostTop;
   interface Clock tepClock125;
   interface Reset tepReset125;
   interface PcieHost#(DataBusWidth, NumberOfMasters) tpciehost;
`ifdef XILINX
   interface Clock tsys_clk_200mhz;
   interface Clock tsys_clk_200mhz_buf;
   interface Clock tpci_clk_100mhz_buf;
   interface PcieEndpointX7#(PcieLanes) tep7;
`elsif ALTERA
   interface PcieEndpointS5#(PcieLanes) tep7;
`elsif VSIM
   interface PcieEndpointS5#(PcieLanes) tep7;
`endif
   interface Clock portalClock;
   interface Reset portalReset;
   interface Clock derivedClock;
   interface Reset derivedReset;
endinterface
`endif

`ifdef PcieHostTypeIF
typedef PcieHostTop HostType;
`endif

////////////////////////////// Zynq /////////////////////////////////
`ifdef ZynqHostTypeIF
import PS7LIB::*;
import Bscan::*;

interface HostType;
    interface PS7 ps7;
    interface Clock portalClock;
    interface Reset portalReset;
    interface Clock derivedClock;
    interface Reset derivedReset;
    interface BscanTop bscan;
endinterface

//export PS7LIB::*;
//export BscanTop;
//export HostType;
//export DataBusWidth;
//export NumberOfMasters;
//export PhysAddrWidth;
`endif

// Copyright (c) 2014 Quanta Research Cambridge, Inc.

// Permission is hereby granted, free of charge, to any person
// obtaining a copy of this software and associated documentation
// files (the "Software"), to deal in the Software without
// restriction, including without limitation the rights to use, copy,
// modify, merge, publish, distribute, sublicense, and/or sell copies
// of the Software, and to permit persons to whom the Software is
// furnished to do so, subject to the following conditions:

// The above copyright notice and this permission notice shall be
// included in all copies or substantial portions of the Software.

// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
// EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
// NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS
// BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN
// ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
// CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
// SOFTWARE.

////////////////////////////// common /////////////////////////////////

`ifndef DataBusWidth
`define DataBusWidth 64
`endif

typedef `PhysAddrWidth PhysAddrWidth;
typedef `SlaveDataBusWidth SlaveDataBusWidth;
typedef `DataBusWidth DataBusWidth;
typedef `NumberOfMasters NumberOfMasters;
typedef `NumberOfTiles NumberOfTiles;

////////////////////////////// Bsim /////////////////////////////////
`ifdef BsimHostTypeIF

import Vector            :: *;
import AxiMasterSlave    :: *;
import MemTypes          :: *;

// this interface should allow for different master and slave bus paraters;
interface BsimHost#(numeric type clientAddrWidth, numeric type clientBusWidth, numeric type clientIdWidth,
		    numeric type serverAddrWidth, numeric type serverBusWidth, numeric type serverIdWidth,
		    numeric type nSlaves);
   interface PhysMemMaster#(clientAddrWidth, clientBusWidth)  mem_client;
   interface Vector#(nSlaves,PhysMemSlave#(serverAddrWidth,  serverBusWidth))  mem_servers;
   interface Clock derivedClock;
   interface Reset derivedReset;
endinterface

typedef BsimHost#(32,32,12,40,DataBusWidth,6,NumberOfMasters) HostType;
`endif

////////////////////////////// Xsim /////////////////////////////////
`ifdef XsimHostTypeIF

import Vector            :: *;
import AxiMasterSlave    :: *;
import MemTypes          :: *;

// this interface should allow for different master and slave bus paraters;
interface XsimHost;
   interface Clock derivedClock;
   interface Reset derivedReset;
endinterface

typedef XsimHost HostType;
`endif

////////////////////////////// PciE /////////////////////////////////
`ifndef PcieHostIF
`ifdef PcieHostTypeIF
`define PcieHostIF
`endif
`endif

`ifdef PcieHostIF

import Vector            :: *;
import GetPut            :: *;
import ClientServer      :: *;
import BRAM              :: *;
import PCIE              :: *;
import Bscan             :: *;
import PcieCsr           :: *;
import PcieTracer        :: *;
import MemTypes          :: *;
`ifndef BSIM
`ifdef XILINX
`ifdef PCIE3
import PCIEWRAPPER3      :: *;
import Pcie3EndpointX7   :: *;
`else // pcie3
import PCIEWRAPPER       :: *;
import PcieEndpointX7    :: *;
`endif // pcie3
`elsif ALTERA
import PcieEndpointS5    :: *;
`elsif VSIM
import PcieEndpointS5    :: *;
`endif
`endif
typedef 40 PciePhysAddrWidth;
interface PcieHost#(numeric type dsz, numeric type nSlaves);
   interface Vector#(16,ReadOnly_MSIX_Entry)     msixEntry;
   interface PhysMemMaster#(32,32)                   master;
   interface Vector#(nSlaves,PhysMemSlave#(PciePhysAddrWidth,dsz))  slave;
   interface Put#(Tuple2#(Bit#(64),Bit#(32)))    interruptRequest;
   interface Client#(TLPData#(16), TLPData#(16)) pci;
   interface Put#(TimestampedTlpData) trace;
`ifndef PCIE_NO_BSCAN
   interface BscanTop bscanif;
`else
   interface BRAMServer#(Bit#(TAdd#(TlpTraceAddrSize,1)), TimestampedTlpData) traceBramServer;
`endif
endinterface

interface PcieHostTop;
   interface Clock tepClock125;
   interface Reset tepReset125;
   interface PcieHost#(DataBusWidth, NumberOfMasters) tpciehost;
`ifdef XILINX
   interface Clock tsys_clk_200mhz;
   interface Clock tsys_clk_200mhz_buf;
   interface Clock tpci_clk_100mhz_buf;
   interface PcieEndpointX7#(PcieLanes) tep7;
`elsif ALTERA
   interface PcieEndpointS5#(PcieLanes) tep7;
`elsif VSIM
   interface PcieEndpointS5#(PcieLanes) tep7;
`endif
   interface Clock portalClock;
   interface Reset portalReset;
   interface Clock derivedClock;
   interface Reset derivedReset;
endinterface
`endif

`ifdef PcieHostTypeIF
typedef PcieHostTop HostType;
`endif

////////////////////////////// Zynq /////////////////////////////////
`ifdef ZynqHostTypeIF
import PS7LIB::*;
import Bscan::*;

interface HostType;
    interface PS7 ps7;
    interface Clock portalClock;
    interface Reset portalReset;
    interface Clock derivedClock;
    interface Reset derivedReset;
    interface BscanTop bscan;
endinterface

//export PS7LIB::*;
//export BscanTop;
//export HostType;
//export DataBusWidth;
//export NumberOfMasters;
//export PhysAddrWidth;
`endif