DUNE-DAQ
DUNE Trigger and Data Acquisition software
Loading...
Searching...
No Matches
FIBV2IONode.cpp
Go to the documentation of this file.
1
10
11#include <map>
12#include <string>
13#include <utility>
14#include <vector>
15
16namespace dunedaq {
17namespace timing {
18
19UHAL_REGISTER_DERIVED_NODE(FIBV2IONode)
20
21//-----------------------------------------------------------------------------
22FIBV2IONode::FIBV2IONode(const uhal::Node& aNode) :
23 IONode(aNode, "i2c", "i2c", "SI5345", {"PLL", "BKP DATA"}, {"i2c_sfp0", "i2c_sfp1", "i2c_sfp2", "i2c_sfp3", "i2c_sfp4", "i2c_sfp5", "i2c_sfp6", "i2c_sfp7"}) {
24}
25//-----------------------------------------------------------------------------
26
27
28//-----------------------------------------------------------------------------
31//-----------------------------------------------------------------------------
32
33//-----------------------------------------------------------------------------
34std::string
36{
37 return "UID_PROM";
38}
39//-----------------------------------------------------------------------------
40
41//-----------------------------------------------------------------------------
42void
43FIBV2IONode::configure_pll(const std::string& /*clock_config_file*/) const
44{
45 TLOG() << "No text config for CDCLVD110";
46}
47//-----------------------------------------------------------------------------
48
49//-----------------------------------------------------------------------------
50std::string
51FIBV2IONode::get_status(bool print_out) const
52{
53 std::stringstream status;
54 auto subnodes = read_sub_nodes(getNode("csr.stat"));
55 status << format_reg_table(subnodes, "FIB IO state") << std::endl;
56
57 if (print_out)
58 TLOG() << status.str();
59
60 return status.str();
61}
62//-----------------------------------------------------------------------------
63
64
65//-----------------------------------------------------------------------------
66void
67FIBV2IONode::reset(const ClockSource& clock_source) const {
68
69 // Soft reset
71
72 millisleep(1000);
73
74 getNode("csr.ctrl.rst").write(0x1);
75 getNode("csr.ctrl.rst").write(0x0);
76
77 getClient().dispatch();
78
79 getNode("csr.ctrl.clk_enable").write(0x0);
80
81 if (clock_source == kInput0)
82 {
83 getNode("csr.ctrl.clk_select").write(0x0);
84 }
85 else if (clock_source == kInput1)
86 {
87 getNode("csr.ctrl.clk_select").write(0x1);
88 }
89 else
90 {
91 // TODO :throw something here
92 }
93
94 TLOG() << "Reset done";
95}
96//-----------------------------------------------------------------------------
97
98//-----------------------------------------------------------------------------
99std::string
100FIBV2IONode::get_sfp_status(uint32_t sfp_id, bool print_out) const { // NOLINT(build/unsigned)
101 std::stringstream status;
102
103 validate_sfp_id(sfp_id);
104
105 std::string sfp_i2c_bus = "i2c_sfp" + std::to_string(sfp_id);
106 auto sfp = get_i2c_device<I2CSFPSlave>(sfp_i2c_bus, "SFP_EEProm");
107 status << "FIB V2 SFP " << sfp_id << ":" << std::endl;
108 status << sfp->get_status();
109
110 if (print_out)
111 TLOG() << status.str();
112
113 return status.str();
114}
115//-----------------------------------------------------------------------------
116
117//-----------------------------------------------------------------------------
118void
119FIBV2IONode::switch_sfp_soft_tx_control_bit(uint32_t sfp_id, bool turn_on) const { // NOLINT(build/unsigned)
120 validate_sfp_id(sfp_id);
121
122 // on this board the 8 downstream sfps have their own i2c bus
123 std::string sfp_i2c_bus = "i2c_sfp" + std::to_string(sfp_id);
124 auto sfp = get_i2c_device<I2CSFPSlave>(sfp_i2c_bus, "SFP_EEProm");
125 sfp->switch_soft_tx_control_bit(turn_on);
126}
127//-----------------------------------------------------------------------------
128
129//-----------------------------------------------------------------------------
130void
131FIBV2IONode::switch_sfp_tx(uint32_t sfp_id, bool turn_on) const { // NOLINT(build/unsigned)
132
133 validate_sfp_id(sfp_id);
134
135 auto sfp_tx_control_flags = getNode("csr.ctrl.sfp_tx_disable").read(); // NOLINT(build/unsigned)
136 getClient().dispatch();
137
138 uint8_t current_sfp_tx_control_flags=sfp_tx_control_flags.value();
139 uint8_t new_sfp_tx_control_flags; // NOLINT(build/unsigned)
140
141 if (turn_on)
142 {
143 new_sfp_tx_control_flags = current_sfp_tx_control_flags & ~(1UL << sfp_id);
144 }
145 else
146 {
147 new_sfp_tx_control_flags = current_sfp_tx_control_flags | (1UL << sfp_id);
148 }
149
150 getNode("csr.ctrl.sfp_tx_disable").write(new_sfp_tx_control_flags);
151 getClient().dispatch();
152}
153//-----------------------------------------------------------------------------
154
155//-----------------------------------------------------------------------------
156void
158{
159 mon_data.lol = false; // no monitoring of this in CDCLVD110
160 mon_data.los = false;
161}
162//-----------------------------------------------------------------------------
163
164//-----------------------------------------------------------------------------
165std::string
166FIBV2IONode::get_pll_status(bool print_out) const
167{
168 std::stringstream status;
169 status << "No status yet for CDCLVD110 on FIBv2";
170
171 if (print_out)
172 TLOG() << status.str();
173
174 return status.str();
175}
176
177//-----------------------------------------------------------------------------
178//std::unique_ptr<const CDCLVD110Node>
179//FIBV2IONode::get_pll() const
180//{
181// return &getNode<CDCLVD110Node>("clock_gen"); //TODO: future node
182//}
183//-----------------------------------------------------------------------------
184
185//-----------------------------------------------------------------------------
186void
187FIBV2IONode::validate_sfp_id(uint32_t sfp_id) const { // NOLINT(build/unsigned)
188 // on this board we have 8 downstream SFPs
189 if (sfp_id > 7) {
190 throw InvalidSFPId(ERS_HERE, format_reg_value(sfp_id));
191 }
192}
193//-----------------------------------------------------------------------------
194
195//-----------------------------------------------------------------------------
196//void
197//FIBV2IONode::get_info(timinghardwareinfo::TimingFIBMonitorData& mon_data) const
198//{
199
200// auto stat_subnodes = read_sub_nodes(getNode("csr.stat"));
201// auto ctrl_subnodes = read_sub_nodes(getNode("csr.ctrl"));
202
203// mon_data.mmcm_ok = stat_subnodes.at("mmcm_ok").value();
204// mon_data.mmcm_sticky = stat_subnodes.at("mmcm_sticky").value();
205
206// mon_data.pll_ok = stat_subnodes.at("pll_ok").value();
207// mon_data.pll_sticky = stat_subnodes.at("pll_sticky").value();
208
209// mon_data.active_sfp_mux = ctrl_subnodes.at("inmux").value();
210
211// //mon_data.sfp_los_flags = read_sfp_los_flags();
212// //mon_data.sfp_fault_flags = read_sfp_fault_flags();
213// }
214//-----------------------------------------------------------------------------
215
216//-----------------------------------------------------------------------------
217// void
218// FIBV2IONode::get_info(opmonlib::InfoCollector& ci, int level) const
219// {
220
221// if (level >= 2) {
222// timinghardwareinfo::TimingPLLMonitorData pll_mon_data;
223// get_pll()->get_info(pll_mon_data);
224// ci.add(pll_mon_data);
225
226// for (uint i=0; i < 8; ++i)
227// {
228// opmonlib::InfoCollector sfp_ic;
229
230// std::string sfp_i2c_bus = "i2c_sfp" + std::to_string(i);
231// auto sfp = get_i2c_device<I2CSFPSlave>(sfp_i2c_bus, "SFP_EEProm");
232
233// try
234// {
235// sfp->get_info(sfp_ic, level);
236// }
237// catch (timing::SFPUnreachable& e)
238// {
239// // It is valid that an SFP may not be installed, currently no good way of knowing whether they it should be
240// TLOG_DEBUG(2) << "Failed to communicate with SFP " << i << " on I2C switch channel " << (1UL << i) << " on i2c bus" << m_sfp_i2c_buses.at(0);
241// continue;
242// }
243// ci.add("sfp_"+std::to_string(i),sfp_ic);
244// }
245// }
246// if (level >= 1) {
247// timinghardwareinfo::TimingFIBMonitorData mon_data;
248// this->get_info(mon_data);
249// ci.add(mon_data);
250// }
251// }
252//-----------------------------------------------------------------------------
253} // namespace timing
254} // namespace dunedaq
#define ERS_HERE
Class for the FIB board.
std::string get_pll_status(bool print_out=false) const override
Print status of on-board PLL.
void validate_sfp_id(uint32_t sfp_id) const
Get the PLL chip.
void switch_sfp_soft_tx_control_bit(uint32_t sfp_id, bool turn_on) const override
control tx laser of on-board SFP softly (I2C command)
std::string get_status(bool print_out=false) const override
Get status string, optionally print.
void switch_sfp_tx(uint32_t sfp_id, bool turn_on) const override
Switch on or off the SFP tx laser via the I2C IO expander controlling the sfp tx disable pin....
void configure_pll(const std::string &clock_config_file="") const override
Configure clock chip.
std::string get_sfp_status(uint32_t sfp_id, bool print_out=false) const override
Print status of on-board SFP.
void reset(const ClockSource &clock_source) const override
Reset IO, with clock file look up.
std::string get_uid_address_parameter_name() const override
Get the UID address parameter name.
void get_info(timinghardwareinfo::TimingPLLMonitorData &mon_data) const override
Base class for timing IO nodes.
Definition IONode.hpp:44
virtual void write_soft_reset_register() const
Write soft reset register.
Definition IONode.cpp:296
std::unique_ptr< const T > get_i2c_device(const std::string &i2c_bus_name, const std::string &i2c_device_name) const
Get the an I2C chip.
Definition IONode.hxx:6
std::map< std::string, uhal::ValWord< uint32_t > > read_sub_nodes(const uhal::Node &node, bool dispatch=true) const
Read subnodes.
#define TLOG(...)
Definition macro.hpp:22
std::string format_reg_table(T data, std::string title, std::vector< std::string > headers)
Format reg-value table.
Definition toolbox.hxx:166
std::string format_reg_value(T reg_value, uint32_t base)
Definition toolbox.hxx:117
void millisleep(const double &time_in_milliseconds)
Definition toolbox.cpp:83
Including Qt Headers.