DUNE-DAQ
DUNE Trigger and Data Acquisition software
Loading...
Searching...
No Matches
dunedaq::timing::MasterNode Class Reference

Class for PD-II/DUNE master timing nodes. More...

#include <MasterNode.hpp>

Inheritance diagram for dunedaq::timing::MasterNode:
[legend]
Collaboration diagram for dunedaq::timing::MasterNode:
[legend]

Public Member Functions

 MasterNode (const uhal::Node &node)
 
virtual ~MasterNode ()
 
std::string get_status (bool print_out=false) const override
 Print the status of the timing node.
 
std::string get_status_with_date (uint32_t clock_frequency_hz, bool print_out=false) const
 Print the status of the timing node.
 
void switch_endpoint_sfp (uint32_t address, bool turn_on) const override
 Control the tx line of endpoint sfp.
 
void enable_upstream_endpoint () const override
 Enable RTT endpoint.
 
void send_fl_cmd (uint32_t command, uint32_t channel, uint32_t number_of_commands=1) const override
 Send a fixed length command.
 
uint32_t measure_endpoint_rtt (uint32_t address, bool control_sfp=true) const override
 Measure the endpoint round trip time.
 
void apply_endpoint_delay (uint32_t address, uint32_t coarse_delay, uint32_t fine_delay, uint32_t phase_delay, bool measure_rtt=false, bool control_sfp=true) const override
 Apply delay to endpoint.
 
void sync_timestamp (TimestampSource source) const override
 Set timestamp to current machine time.
 
uint64_t read_timestamp () const override
 Read the current timestamp word.
 
void set_timestamp (TimestampSource source) const override
 Set the timestamp to current time.
 
void get_info (timingfirmwareinfo::MasterMonitorData &mon_data) const
 Fill the PD-I master monitoring structure.
 
void reset_command_counters () const
 Read some data from endpoint registers.
 
std::vector< uint32_t > transmit_async_packet (const std::vector< uint32_t > &packet, int timeout=500) const
 Send an async packet.
 
void write_endpoint_data (uint16_t endpoint_address, uint8_t reg_address, std::vector< uint8_t > data, bool address_mode) const
 Write some data to endpoint registers.
 
std::vector< uint32_t > read_endpoint_data (uint16_t endpoint_address, uint8_t reg_address, uint8_t data_length, bool address_mode) const
 Read some data from endpoint registers.
 
void disable_timestamp_broadcast () const
 Disable timestamp sending.
 
void enable_timestamp_broadcast () const
 Enable timestamp sending.
 
timingfirmware::EndpointCheckResult scan_endpoint (uint16_t endpoint_address, bool control_sfp) const override
 Scan endpoint.
 
void configure_endpoint_command_decoder (uint16_t endpoint_address, uint8_t slot, uint8_t command) const
 Configure endpoint command decoder.
 
uint32_t get_required_major_firmware_version () const override
 Required major firmware version.
 
uint32_t get_required_minor_firmware_version () const override
 Required minor firmware version.
 
uint32_t get_required_patch_firmware_version () const override
 Required patch firmware version.
 
virtual void apply_endpoint_delay (const ActiveEndpointConfig &ept_config, bool measure_rtt=false) const
 Apply delay to endpoint.
 
- Public Member Functions inherited from dunedaq::timing::MasterNodeInterface
 MasterNodeInterface (const uhal::Node &node)
 
virtual ~MasterNodeInterface ()
 
virtual void enable_periodic_fl_cmd (uint32_t channel, double rate, bool poisson, uint32_t clock_frequency_hz) const
 Configure fake trigger generator.
 
virtual void enable_periodic_fl_cmd (uint32_t command, uint32_t channel, double rate, bool poisson, uint32_t clock_frequency_hz) const
 Configure fake trigger generator.
 
virtual void disable_periodic_fl_cmd (uint32_t channel) const
 Clear fake trigger configuration.
 
- Public Member Functions inherited from dunedaq::timing::TimingNode
 TimingNode (const uhal::Node &node)
 
virtual ~TimingNode ()
 
std::map< std::string, uhal::ValWord< uint32_t > > read_sub_nodes (const uhal::Node &node, bool dispatch=true) const
 Read subnodes.
 
void reset_sub_nodes (const uhal::Node &node, uint32_t aValue=0x0, bool dispatch=true) const
 Reset subnodes.
 

Static Public Attributes

static const uint32_t required_major_firmware_version = 7
 
static const uint32_t required_minor_firmware_version = 7
 
static const uint32_t required_patch_firmware_version = 0
 

Private Member Functions

std::string get_status_tables () const
 Get the status tables.
 

Detailed Description

Class for PD-II/DUNE master timing nodes.

Definition at line 38 of file MasterNode.hpp.

Constructor & Destructor Documentation

◆ MasterNode()

dunedaq::timing::MasterNode::MasterNode ( const uhal::Node & node)
explicit

Definition at line 22 of file MasterNode.cpp.

24{}

◆ ~MasterNode()

dunedaq::timing::MasterNode::~MasterNode ( )
virtual

Definition at line 28 of file MasterNode.cpp.

28{}

Member Function Documentation

◆ apply_endpoint_delay() [1/2]

void dunedaq::timing::MasterNodeInterface::apply_endpoint_delay ( const ActiveEndpointConfig & ept_config,
bool measure_rtt = false ) const
virtual

Apply delay to endpoint.

Reimplemented from dunedaq::timing::MasterNodeInterface.

Definition at line 94 of file MasterNodeInterface.cpp.

29{
30 std::string lEptIdD = ept_config.id;
31 uint32_t ept_address = ept_config.adr; // NOLINT(build/unsigned)
32 uint32_t coarse_Delay = ept_config.cdelay; // NOLINT(build/unsigned)
33 uint32_t fine_delay = ept_config.fdelay; // NOLINT(build/unsigned)
34 uint32_t phase_delay = ept_config.pdelay; // NOLINT(build/unsigned)
35 apply_endpoint_delay(ept_address, coarse_Delay, fine_delay, phase_delay, measure_rtt);
36}
void apply_endpoint_delay(uint32_t address, uint32_t coarse_delay, uint32_t fine_delay, uint32_t phase_delay, bool measure_rtt=false, bool control_sfp=true) const override
Apply delay to endpoint.

◆ apply_endpoint_delay() [2/2]

void dunedaq::timing::MasterNode::apply_endpoint_delay ( uint32_t address,
uint32_t coarse_delay,
uint32_t fine_delay,
uint32_t phase_delay,
bool measure_rtt = false,
bool control_sfp = true ) const
overridevirtual

Apply delay to endpoint.

Implements dunedaq::timing::MasterNodeInterface.

Definition at line 205 of file MasterNode.cpp.

211{
212
213 auto global = getNode<MasterGlobalNode>("global");
214 auto echo = getNode<EchoMonitorNode>("echo_mon");
215
216 if (measure_rtt) {
217 if (control_sfp) {
218 // Switch off all TX SFPs
219 // switch_endpoint_sfp(0xffff, false);
220
221 // Turn on the current target
223
224 millisleep(100);
225 }
226
227 try
228 {
229 global.enable_upstream_endpoint();
230 }
231 catch (const timing::ReceiverNotReady& e)
232 {
233 if (control_sfp) {
235 }
236 throw e;
237 }
238
239 uint64_t endpoint_rtt = echo.send_echo_and_measure_delay(); // NOLINT(build/unsigned)
240 TLOG() << "Pre delay adjustment RTT: " << format_reg_value(endpoint_rtt, 10);
241 }
242
243 uint32_t sequence = 0xab;
244 uint32_t address_mode = 1;
245
246 std::vector<uint32_t> tx_packet = { address & 0xff,
247 address >> 8UL,
248 sequence,
249
250 // packet to write coarse delay
251 (0x1 << 7UL) | 0x72, // write transaction on 0x72
252 (address_mode << 7UL) | 0x1, // transaction length of 0x1
253 ((fine_delay & 0xf) << 4UL) | (coarse_delay & 0xf),
254
255 // packet to write fine delay
256 (0x1 << 7UL) | 0x73, // write transaction on 0x73
257 (address_mode << 7UL) | 0x1, // transaction length of 0x1
258 (fine_delay >> 4UL) & 0xff,
259
260 // packet to set skew done
261 (0x1 << 7UL) | 0x70, // write transaction on 0x70
262 (address_mode << 7UL) | 0x1, // transaction length of 0x1
263 0x3, // deskew done
264
265 // packet to resync
266 (0x1 << 7UL) | 0x70, // write transaction on 0x70
267 (address_mode << 7UL) | 0x1, // transaction length of 0x1
268 0x4, // resync
269 };
270
271 tx_packet.back() = tx_packet.back() | (0x1 << 8UL);
272
273 transmit_async_packet(tx_packet, -1);
274
275 if (measure_rtt) {
276 try
277 {
278 global.enable_upstream_endpoint();
279 }
280 catch (const timing::ReceiverNotReady& e)
281 {
282 if (control_sfp)
283 {
285 }
286 throw e;
287 }
288
289 uint64_t endpoint_rtt = echo.send_echo_and_measure_delay(); // NOLINT(build/unsigned)
290 TLOG() << "Post delay adjustment RTT: " << format_reg_value(endpoint_rtt, 10);
291
292 if (control_sfp)
294 }
295}
std::vector< uint32_t > transmit_async_packet(const std::vector< uint32_t > &packet, int timeout=500) const
Send an async packet.
void switch_endpoint_sfp(uint32_t address, bool turn_on) const override
Control the tx line of endpoint sfp.
#define TLOG(...)
Definition macro.hpp:22
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
Invalid address

◆ configure_endpoint_command_decoder()

void dunedaq::timing::MasterNode::configure_endpoint_command_decoder ( uint16_t endpoint_address,
uint8_t slot,
uint8_t command ) const

Configure endpoint command decoder.

Definition at line 596 of file MasterNode.cpp.

597{
598 write_endpoint_data(endpoint_address, 0x60+slot, {command}, true);
599}
void write_endpoint_data(uint16_t endpoint_address, uint8_t reg_address, std::vector< uint8_t > data, bool address_mode) const
Write some data to endpoint registers.

◆ disable_timestamp_broadcast()

void dunedaq::timing::MasterNode::disable_timestamp_broadcast ( ) const

Disable timestamp sending.

Definition at line 506 of file MasterNode.cpp.

507{
508 getNode("global.csr.ctrl.ts_en").write(0x0);
509 getClient().dispatch();
510}

◆ enable_timestamp_broadcast()

void dunedaq::timing::MasterNode::enable_timestamp_broadcast ( ) const

Enable timestamp sending.

Definition at line 514 of file MasterNode.cpp.

515{
516 getNode("global.csr.ctrl.ts_en").write(0x1);
517 getClient().dispatch();
518}

◆ enable_upstream_endpoint()

void dunedaq::timing::MasterNode::enable_upstream_endpoint ( ) const
overridevirtual

Enable RTT endpoint.

Implements dunedaq::timing::MasterNodeInterface.

Definition at line 130 of file MasterNode.cpp.

131{
132 auto global = getNode<MasterGlobalNode>("global");
133 global.enable_upstream_endpoint();
134}

◆ get_info()

void dunedaq::timing::MasterNode::get_info ( timingfirmwareinfo::MasterMonitorData & mon_data) const
virtual

Fill the PD-I master monitoring structure.

Implements dunedaq::timing::MasterNodeInterface.

Definition at line 330 of file MasterNode.cpp.

331{
332 mon_data.timestamp = read_timestamp();
333
334 auto control = read_sub_nodes(getNode("global.csr.ctrl"), false);
335 auto state = read_sub_nodes(getNode("global.csr.stat"), false);
336 getClient().dispatch();
337
338 mon_data.ts_bcast_enable = control.at("ts_en").value();
339 mon_data.ts_valid = state.at("ts_valid").value();
340 mon_data.ts_tx_err = state.at("ts_tx_err").value();
341 mon_data.tx_err = state.at("tx_err").value();
342 mon_data.ctrs_rdy = state.at("ctrs_rdy").value();
343
344// ic.add(mon_data);
345
346// uint number_of_commands = 0xff;
347
348// getNode("cmd_ctrs.addr").write(0x0);
349// auto counters = getNode("cmd_ctrs.data").readBlock(number_of_commands);
350// getClient().dispatch();
351
352// for (uint i = 0; i < number_of_commands; ++i) { // NOLINT(build/unsigned)
353
354// timingfirmwareinfo::SentCommandCounter cmd_counter;
355// opmonlib::InfoCollector cmd_counter_ic;
356
357// cmd_counter.counts = counters.at(i);
358
359// std::stringstream channel;
360// channel << "cmd_0x" << std::hex << i;
361
362// cmd_counter_ic.add(cmd_counter);
363// ic.add(channel.str(), cmd_counter_ic);
364// }
365
366// getNode<FLCmdGeneratorNode>("scmd_gen").get_info(ic, level);
367}
uint64_t read_timestamp() const override
Read the current timestamp word.
std::map< std::string, uhal::ValWord< uint32_t > > read_sub_nodes(const uhal::Node &node, bool dispatch=true) const
Read subnodes.

◆ get_required_major_firmware_version()

uint32_t dunedaq::timing::MasterNode::get_required_major_firmware_version ( ) const
inlineoverridevirtual

Required major firmware version.

Implements dunedaq::timing::MasterNodeInterface.

Definition at line 156 of file MasterNode.hpp.

static const uint32_t required_major_firmware_version

◆ get_required_minor_firmware_version()

uint32_t dunedaq::timing::MasterNode::get_required_minor_firmware_version ( ) const
inlineoverridevirtual

Required minor firmware version.

Implements dunedaq::timing::MasterNodeInterface.

Definition at line 161 of file MasterNode.hpp.

static const uint32_t required_minor_firmware_version

◆ get_required_patch_firmware_version()

uint32_t dunedaq::timing::MasterNode::get_required_patch_firmware_version ( ) const
inlineoverridevirtual

Required patch firmware version.

Implements dunedaq::timing::MasterNodeInterface.

Definition at line 166 of file MasterNode.hpp.

static const uint32_t required_patch_firmware_version

◆ get_status()

std::string dunedaq::timing::MasterNode::get_status ( bool print_out = false) const
overridevirtual

Print the status of the timing node.

Implements dunedaq::timing::TimingNode.

Definition at line 77 of file MasterNode.cpp.

78{
79 std::stringstream status;
80 auto raw_timestamp = getNode<TimestampGeneratorNode>("tstamp").read_raw_timestamp();
81 status << "Timestamp: 0x" << std::hex << tstamp2int(raw_timestamp) << std::endl << std::endl;
83
84 if (print_out)
85 TLOG() << status.str();
86 return status.str();
87}
std::string get_status_tables() const
Get the status tables.
uint64_t tstamp2int(uhal::ValVector< uint32_t > raw_timestamp)
Definition toolbox.cpp:175

◆ get_status_tables()

std::string dunedaq::timing::MasterNode::get_status_tables ( ) const
private

Get the status tables.

Definition at line 33 of file MasterNode.cpp.

34{
35 std::stringstream status;
36
37 status << getNode<TimestampGeneratorNode>("tstamp").get_status();
38 status << std::endl;
39
40 status << getNode<MasterGlobalNode>("global").get_status();
41 status << std::endl;
42
43 status << getNode<FLCmdGeneratorNode>("scmd_gen").get_cmd_counters_table();
44 status << std::endl;
45
46 getNode("cmd_ctrs.addr").write(0x0);
47 auto counters = getNode("cmd_ctrs.data").readBlock(0xff);
48 getClient().dispatch();
49
50 std::vector<uint32_t> non_zero_counters;
51 std::vector<std::string> counter_labels;
52
53 for (uint i=0; i < counters.size(); ++i)
54 {
55 auto counter = counters.at(i);
56 if (counter > 0)
57 {
58 counter_labels.push_back(format_reg_value(i));
59 non_zero_counters.push_back(counter);
60 }
61 }
62
63 std::vector<std::vector<uint32_t>> counters_container = { non_zero_counters }; // NOLINT(build/unsigned)
64
65 status << format_counters_table(counters_container, { "Sent cmd counters" }, "Master cmd counters (>0)", counter_labels);
66 status << std::endl;
67
68 auto acmd_buf = read_sub_nodes(getNode("acmd_buf.stat"));
69 status << format_reg_table(acmd_buf, "Master acmd buffer");
70
71 return status.str();
72}
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_counters_table(std::vector< T > counter_nodes, std::vector< std::string > counter_node_titles, std::string table_title, std::vector< std::string > counter_labels, std::string counter_labels_header)
Format reg-value table.
Definition toolbox.hxx:216

◆ get_status_with_date()

std::string dunedaq::timing::MasterNode::get_status_with_date ( uint32_t clock_frequency_hz,
bool print_out = false ) const

Print the status of the timing node.

Definition at line 92 of file MasterNode.cpp.

93{
94 std::stringstream status;
95 auto raw_timestamp = getNode<TimestampGeneratorNode>("tstamp").read_raw_timestamp();
96 status << "Timestamp: 0x" << std::hex << tstamp2int(raw_timestamp) << " -> " << format_timestamp(raw_timestamp, clock_frequency_hz) << std::endl
97 << std::endl;
99
100 if (print_out)
101 TLOG() << status.str();
102 return status.str();
103}
std::string format_timestamp(uhal::ValVector< uint32_t > raw_timestamp, uint32_t clock_frequency_hz)
Definition toolbox.cpp:233

◆ measure_endpoint_rtt()

uint32_t dunedaq::timing::MasterNode::measure_endpoint_rtt ( uint32_t address,
bool control_sfp = true ) const
overridevirtual

Measure the endpoint round trip time.

Returns
{ description_of_the_return_value }

Implements dunedaq::timing::MasterNodeInterface.

Definition at line 165 of file MasterNode.cpp.

166{
167
168 auto global = getNode<MasterGlobalNode>("global");
169 auto echo = getNode<EchoMonitorNode>("echo_mon");
170
171 if (control_sfp)
172 {
173 // Switch off all TX SFPs
174 //switch_endpoint_sfp(0xffff, false);
175
176 // Turn on the current target
178
179 millisleep(100);
180
181 try
182 {
183 global.enable_upstream_endpoint();
184 }
185 catch (const timing::ReceiverNotReady& e)
186 {
187 if (control_sfp) {
189 }
190 throw e;
191 }
192 }
193
194 uint32_t endpoint_rtt = echo.send_echo_and_measure_delay(); // NOLINT(build/unsigned)
195
196 if (control_sfp)
198
199 return endpoint_rtt;
200}

◆ read_endpoint_data()

std::vector< uint32_t > dunedaq::timing::MasterNode::read_endpoint_data ( uint16_t endpoint_address,
uint8_t reg_address,
uint8_t data_length,
bool address_mode ) const

Read some data from endpoint registers.

Definition at line 475 of file MasterNode.cpp.

476{
477 if (data_length > 0x3f || data_length == 0)
478 {
479 TLOG() << "invalid data length";
480 // TODO throw something
481 }
482
483 // TODO make sequence a function argument?
484 uint32_t sequence = 0xab;
485 std::vector<uint32_t> tx_packet = { static_cast<uint32_t>(endpoint_address & 0xff),
486 static_cast<uint32_t>(endpoint_address >> 8UL),
487 sequence,
488 // bit 7 = 0 -> read
489 reg_address,
490 static_cast<uint32_t>((0x1 << 8UL) | (address_mode << 7UL) | (0x3f & data_length))
491 };
492
493 auto result = transmit_async_packet(tx_packet);
494
495 // get parts we actually want
496 std::vector<uint32_t> result_data (result.begin()+3, result.begin()+3+data_length);
497
498 // strip off the bit 8 which is high for last byte
499 result_data.back() = result_data.back() & 0xff;
500
501 return result_data;
502}

◆ read_timestamp()

uint64_t dunedaq::timing::MasterNode::read_timestamp ( ) const
overridevirtual

Read the current timestamp word.

Returns
{ description_of_the_return_value }

Implements dunedaq::timing::MasterNodeInterface.

Definition at line 314 of file MasterNode.cpp.

315{
316 return getNode<TimestampGeneratorNode>("tstamp").read_timestamp();
317}

◆ reset_command_counters()

void dunedaq::timing::MasterNode::reset_command_counters ( ) const

Read some data from endpoint registers.

Definition at line 371 of file MasterNode.cpp.

372{
373 auto global = getNode<MasterGlobalNode>("global");
374 global.reset_command_counters();
375}

◆ scan_endpoint()

timingfirmware::EndpointCheckResult dunedaq::timing::MasterNode::scan_endpoint ( uint16_t endpoint_address,
bool control_sfp ) const
overridevirtual

Scan endpoint.

Implements dunedaq::timing::MasterNodeInterface.

Definition at line 523 of file MasterNode.cpp.

524{
525 timingfirmware::EndpointCheckResult result;
526 auto global = getNode<MasterGlobalNode>("global");
527 auto echo = getNode<EchoMonitorNode>("echo_mon");
528
529 timingfirmware::EndpointCheckResult endpoint_result;
530 endpoint_result.address = endpoint_address;
531
532 // is endpoint sfp switched on?
533 // are any relevant muxes set to correct channel?
534 if (control_sfp)
535 {
536 switch_endpoint_sfp(endpoint_address, true);
537
538 millisleep(100);
539 }
540
541 try
542 {
543 global.enable_upstream_endpoint();
544 }
545 catch (const timing::ReceiverNotReady& e)
546 {
547 switch_endpoint_sfp(endpoint_address, false);
548
549 //ers::error(MonitoredEndpointDead(ERS_HERE, endpoint_address));
550
551 return endpoint_result;
552 }
553
554 endpoint_result.alive = true;
555 endpoint_result.round_trip_time = echo.send_echo_and_measure_delay();
556 TLOG_DEBUG(5) << "Endpoint at address " << endpoint_address << " alive. RTT: " << endpoint_result.round_trip_time;
557
558 auto ept_state = read_endpoint_data(endpoint_address, 0x71, 0x1, 0x1).at(0) & 0xf;
559 TLOG_DEBUG(5) << "Endpoint at address " << endpoint_address << " state: 0x" << std::hex << ept_state;
560 endpoint_result.state = ept_state;
561
562 if (ept_state == 0x6)
563 {
564 TLOG_DEBUG(5) << "Endpoint at address " << endpoint_address << ", applying delays of: " << 0x0;
565 ers::info(MonitoredEndpointDelaySet(ERS_HERE, 0x0, endpoint_address, ept_state));
566 apply_endpoint_delay(endpoint_address, 0x0, 0x0, 0x0, false, false);
567
568 endpoint_result.applied_delay = 0x0;
569
570 auto ept_state_after_delays = read_endpoint_data(endpoint_address, 0x71, 0x1, 0x1).at(0) & 0xf;
571 TLOG_DEBUG(5) << "Endpoint at address " << endpoint_address << ", state after delays apply: " << ept_state_after_delays;
572 endpoint_result.state_after_delay_apply = ept_state_after_delays;
573
574 endpoint_result.round_trip_time_after_delay_apply = echo.send_echo_and_measure_delay();
575 TLOG_DEBUG(5) << "Endpoint at address " << endpoint_address << ", RTT after delays apply: " << endpoint_result.round_trip_time_after_delay_apply;
576 }
577 else if (ept_state == 0x7 || ept_state == 0x8)
578 {
579 TLOG_DEBUG(5) << "Endpoint at address " << endpoint_address << ", delays not needed";
580 }
581 else
582 {
583 ers::error(MonitoredEndpointUnexpectedState(ERS_HERE, endpoint_address, ept_state));
584 }
585
586 if (control_sfp)
587 {
588 switch_endpoint_sfp(endpoint_address, false);
589 }
590
591 return endpoint_result;
592}
#define ERS_HERE
std::vector< uint32_t > read_endpoint_data(uint16_t endpoint_address, uint8_t reg_address, uint8_t data_length, bool address_mode) const
Read some data from endpoint registers.
#define TLOG_DEBUG(lvl,...)
Definition Logging.hpp:112
void info(const Issue &issue)
Definition ers.hpp:95
void error(const Issue &issue)
Definition ers.hpp:81

◆ send_fl_cmd()

void dunedaq::timing::MasterNode::send_fl_cmd ( uint32_t command,
uint32_t channel,
uint32_t number_of_commands = 1 ) const
overridevirtual

Send a fixed length command.

Implements dunedaq::timing::MasterNodeInterface.

Definition at line 139 of file MasterNode.cpp.

142{
143 for (uint32_t i = 0; i < number_of_commands; i++) { // NOLINT(build/unsigned)
144 getNode<FLCmdGeneratorNode>("scmd_gen").send_fl_cmd(command, channel);
145
146 auto ts_l = getNode("cmd_log.tstamp_l").read();
147 auto ts_h = getNode("cmd_log.tstamp_h").read();
148 auto sent_cmd = getNode("cmd_log.cmd").read();
149 getClient().dispatch();
150
151 if (sent_cmd.value() != command)
152 {
153 TLOG() << "cmd in sent log: 0x" << std::hex << command << ", does not match requested 0x: " << sent_cmd.value();
154 // TODO throw something
155 }
156 uint64_t timestamp = (uint64_t)ts_h.value() << 32 | ts_l.value();
157 TLOG() << "Command sent " << "(" << format_reg_value(command) << ") from generator "
158 << format_reg_value(channel) << " @time " << std::hex << std::showbase << timestamp;
159 }
160}

◆ set_timestamp()

void dunedaq::timing::MasterNode::set_timestamp ( TimestampSource source) const
overridevirtual

Set the timestamp to current time.

Implements dunedaq::timing::MasterNodeInterface.

Definition at line 322 of file MasterNode.cpp.

323{
324 getNode<TimestampGeneratorNode>("tstamp").set_timestamp(source);
325}

◆ switch_endpoint_sfp()

void dunedaq::timing::MasterNode::switch_endpoint_sfp ( uint32_t address,
bool turn_on ) const
overridevirtual

Control the tx line of endpoint sfp.

Implements dunedaq::timing::MasterNodeInterface.

Definition at line 108 of file MasterNode.cpp.

109{
110 uint32_t sequence = 0xab;
111 uint32_t address_mode = 1;
112
113 std::vector<uint32_t> tx_packet = { address & 0xff,
114 address >> 8UL,
115 sequence,
116
117 // packet to reset rx
118 (0x1 << 7UL) | 0x70, // write transaction on 0x70
119 (address_mode << 7UL) | 0x1, // transaction length of 0x1
120 turn_on,
121 };
122 tx_packet.back() = tx_packet.back() | (0x1 << 8UL);
123
124 auto result = transmit_async_packet(tx_packet, -1);
125}

◆ sync_timestamp()

void dunedaq::timing::MasterNode::sync_timestamp ( TimestampSource source) const
overridevirtual

Set timestamp to current machine time.

Implements dunedaq::timing::MasterNodeInterface.

Definition at line 300 of file MasterNode.cpp.

301{
303 TLOG() << "Timestamp broadcast disabled";
304
305 set_timestamp(source);
306
308 TLOG() << "Timestamp broadcast enabled";
309}
void set_timestamp(TimestampSource source) const override
Set the timestamp to current time.
void enable_timestamp_broadcast() const
Enable timestamp sending.
void disable_timestamp_broadcast() const
Disable timestamp sending.

◆ transmit_async_packet()

std::vector< uint32_t > dunedaq::timing::MasterNode::transmit_async_packet ( const std::vector< uint32_t > & packet,
int timeout = 500 ) const

Send an async packet.

Definition at line 380 of file MasterNode.cpp.

381{
382 // TODO: check for valid packet
383
384 reset_sub_nodes(getNode("acmd_buf.txbuf"));
385
386 TLOG_DEBUG(11) << "tx packet: ";
387 for (auto t : packet)
388 TLOG_DEBUG(11) << std::hex << "0x" << t;
389
390 getNode("acmd_buf.txbuf").writeBlock(packet);
391 getClient().dispatch();
392
393 // we do not expect a reply
394 if (timeout < 0)
395 {
396 std::vector<uint32_t> empty_vector;
397 return empty_vector;
398 }
399
400 uhal::ValWord<uint32_t> buffer_ready; // NOLINT(build/unsigned)
401 uhal::ValWord<uint32_t> buffer_timeout; // NOLINT(build/unsigned)
402
403 // start time counting
404 auto start = std::chrono::high_resolution_clock::now();
405
406 // Wait for the buffer to be happy
407 while (true) {
408
409 buffer_ready = getNode("acmd_buf.stat.ready").read();
410 buffer_timeout = getNode("acmd_buf.stat.timeout").read();
411 getClient().dispatch();
412
413 TLOG_DEBUG(10) << "async buffer ready: 0x" << buffer_ready.value() << ", timeout: " << buffer_timeout.value();
414
415 if (buffer_timeout)
416 throw VLCommandReplyTimeout(ERS_HERE);
417
418 if (buffer_ready)
419 break;
420
421 auto now = std::chrono::high_resolution_clock::now();
422 auto us_since_start = std::chrono::duration_cast<std::chrono::microseconds>(now - start);
423
424 if (us_since_start.count() > timeout)
425 throw VLCommandReplyBufferFlagTimeout(ERS_HERE, timeout);
426
427 std::this_thread::sleep_for(std::chrono::microseconds(50));
428 }
429
430 auto rx_packet = getNode("acmd_buf.rxbuf").readBlock(0x20);
431 getClient().dispatch();
432
433 if (rx_packet.at(0) != 0xff || rx_packet.at(1) != 0xff || rx_packet.at(2) != packet.at(2))
434 {
435 ers::warning(InvalidVLCommandReplyPacket(ERS_HERE, rx_packet.at(0), rx_packet.at(1), rx_packet.at(2)));
436 }
437
438 TLOG_DEBUG(11) << "async result: ";
439 for (auto r : rx_packet)
440 TLOG_DEBUG(11) << std::hex << "0x" << r;
441
442 return rx_packet.value();
443}
void reset_sub_nodes(const uhal::Node &node, uint32_t aValue=0x0, bool dispatch=true) const
Reset subnodes.
static int64_t now()
void warning(const Issue &issue)
Definition ers.hpp:115

◆ write_endpoint_data()

void dunedaq::timing::MasterNode::write_endpoint_data ( uint16_t endpoint_address,
uint8_t reg_address,
std::vector< uint8_t > data,
bool address_mode ) const

Write some data to endpoint registers.

Definition at line 448 of file MasterNode.cpp.

449{
450 auto data_length = data.size();
451 if (data_length > 0x3f || data_length == 0)
452 {
453 TLOG() << "invalid data length";
454 }
455
456 // TODO make sequence a function argument?
457 uint32_t sequence = 0xab;
458
459 std::vector<uint32_t> tx_packet = { static_cast<uint32_t>(endpoint_address & 0xff),
460 static_cast<uint32_t>(endpoint_address >> 8UL),
461 sequence,
462 // bit 7 = 1 -> write
463 static_cast<uint32_t>((0x1 << 7UL) | reg_address),
464 static_cast<uint32_t>((address_mode << 7UL) | (0x3f & data_length))
465 };
466 tx_packet.insert(tx_packet.end(), data.begin(), data.end());
467 tx_packet.back() = tx_packet.back() | (0x1 << 8UL);
468
469 auto result = transmit_async_packet(tx_packet);
470}

Member Data Documentation

◆ required_major_firmware_version

const uint32_t dunedaq::timing::MasterNode::required_major_firmware_version = 7
static

Definition at line 168 of file MasterNode.hpp.

◆ required_minor_firmware_version

const uint32_t dunedaq::timing::MasterNode::required_minor_firmware_version = 7
static

Definition at line 169 of file MasterNode.hpp.

◆ required_patch_firmware_version

const uint32_t dunedaq::timing::MasterNode::required_patch_firmware_version = 0
static

Definition at line 170 of file MasterNode.hpp.


The documentation for this class was generated from the following files: