19 #include <chi/chi_tlm.h>
20 #include <tlm/scc/pe/intor_if.h>
21 #include <scc/ordered_semaphore.h>
23 #include <scc/sc_variable.h>
25 #include <tlm_utils/peq_with_get.h>
27 #include <unordered_map>
33 public sc_core::sc_module,
38 using payload_type = chi::chi_protocol_types::tlm_payload_type;
39 using phase_type = chi::chi_protocol_types::tlm_phase_type;
41 sc_core::sc_in<bool> clk_i{
"clk_i"};
43 sc_core::sc_export<tlm::scc::pe::intor_fw_b> fw_i{
"fw_i"};
45 sc_core::sc_port<tlm::scc::pe::intor_bw_b, 1, sc_core::SC_ZERO_OR_MORE_BOUND> bw_o{
"bw_o"};
47 void b_snoop(payload_type& trans, sc_core::sc_time& t)
override;
49 tlm::tlm_sync_enum nb_transport_bw(payload_type& trans, phase_type& phase, sc_core::sc_time& t)
override;
51 void invalidate_direct_mem_ptr(sc_dt::uint64 start_range, sc_dt::uint64 end_range)
override;
53 size_t get_transferwith_in_bytes()
const {
return transfer_width_in_bytes; }
63 void transport(payload_type& trans,
bool blocking)
override;
70 void snoop_resp(payload_type& trans,
bool sync =
false)
override;
87 sc_core::sc_attribute<unsigned> src_id{
"src_id", 1};
89 sc_core::sc_attribute<unsigned> tgt_id{
"tgt_id", 0};
91 sc_core::sc_attribute<bool> data_interleaving{
"data_interleaving",
true};
93 sc_core::sc_attribute<bool> strict_income_order{
"strict_income_order",
true};
95 sc_core::sc_attribute<bool> use_legacy_mapping{
"use_legacy_mapping",
false};
98 void end_of_elaboration()
override { clk_if =
dynamic_cast<sc_core::sc_clock*
>(clk_i.get_interface()); }
100 unsigned calculate_beats(payload_type& p) {
102 return p.get_data_length() < transfer_width_in_bytes ? 1 : p.get_data_length() / transfer_width_in_bytes;
105 void snoop_dispatch();
107 void snoop_handler(payload_type* trans);
109 const size_t transfer_width_in_bytes;
111 std::string instance_name;
115 sc_core::sc_port_b<chi::chi_fw_transport_if<chi_protocol_types>>& socket_fw;
120 : peq(sc_core::sc_gen_unique_name(name.c_str())) {}
122 std::unordered_map<uintptr_t, tx_state*> tx_state_by_trans;
124 std::vector<tx_state*> tx_state_pool;
126 std::unordered_map<unsigned, scc::ordered_semaphore> active_tx_by_id;
130 tlm_utils::peq_with_get<payload_type> snp_peq{
"snp_peq"}, snp_dispatch_que{
"snp_dispatch_que"};
132 unsigned thread_avail{0}, thread_active{0};
142 sc_core::sc_event any_tx_finished;
144 sc_core::sc_time clk_period{10, sc_core::SC_NS};
149 void send_comp_ack(payload_type& trans, tx_state*& txs);
150 void clk_counter() { m_clock_counter++; }
151 unsigned get_clk_cnt() {
return m_clock_counter; }
153 void create_data_ext(payload_type& trans);
155 void exec_read_write_protocol(
const unsigned int txn_id, payload_type& trans,
157 void exec_atomic_protocol(
const unsigned int txn_id, payload_type& trans,
159 void send_cresp_response(payload_type& trans);
162 unsigned m_clock_counter{0};
163 unsigned m_prev_clk_cnt{0};
165 sc_core::sc_clock* clk_if{
nullptr};
176 sc_core::sc_port_policy POL = sc_core::SC_ONE_OR_MORE_BOUND>
181 using payload_type = base::payload_type;
182 using phase_type = base::phase_type;
191 this->instance_name = socket.name();
void transport(payload_type &trans, bool blocking) override
The forward transport function. It behaves blocking and is re-entrant.
void snoop_resp(payload_type &trans, bool sync=false) override
triggers a non-blocking snoop response if the snoop callback does not do so.
chi_rn_initiator(const sc_core::sc_module_name &nm, chi::chi_initiator_socket< BUSWIDTH, TYPES, N, POL > &socket_)
the constructor
The ordered_semaphore primitive channel class.
TLM2.0 components modeling CHI.
tlm::tlm_fw_transport_if< TYPES > chi_fw_transport_if
alias declaration for the forward interface
The AXI protocol traits class. Since the protocoll defines additional non-ignorable phases a dedicate...