1 #include "otsdaq-core/ConfigurationInterface/ConfigurationManager.h"
2 #include "otsdaq-core/Macros/TablePluginMacros.h"
3 #include "otsdaq-core/TablePluginDataFormats/ARTDAQBuilderTable.h"
4 #include "otsdaq-core/TablePluginDataFormats/XDAQContextTable.h"
13 #define ARTDAQ_FCL_PATH std::string(getenv("USER_DATA")) + "/" + "ARTDAQConfigurations/"
14 #define ARTDAQ_FILE_PREAMBLE "builder"
17 #define OUT out << tabStr << commentStr
18 #define PUSHTAB tabStr += "\t"
19 #define POPTAB tabStr.resize(tabStr.size() - 1)
20 #define PUSHCOMMENT commentStr += "# "
21 #define POPCOMMENT commentStr.resize(commentStr.size() - 2)
24 ARTDAQBuilderTable::ARTDAQBuilderTable(
void) :
TableBase(
"ARTDAQBuilderTable")
32 ARTDAQBuilderTable::~ARTDAQBuilderTable(
void) {}
38 mkdir((ARTDAQ_FCL_PATH).c_str(), 0755);
40 __COUT__ <<
"*&*&*&*&*&*&*&*&*&*&*&*&*&*&*&*&*&*&*&*&*&*" << __E__;
41 __COUT__ << configManager->__SELF_NODE__ << __E__;
46 std::vector<const XDAQContextTable::XDAQContext*> builderContexts =
47 contextConfig->getEventBuilderContexts();
51 for(
auto& builderContext : builderContexts)
55 builderContext->contextUID_,
56 builderContext->applications_[0].applicationUID_);
59 builderContext->contextUID_,
60 builderContext->applications_[0].applicationUID_);
62 __COUT__ <<
"Path for this aggregator config is " << builderContext->contextUID_
63 <<
"/" << builderContext->applications_[0].applicationUID_ <<
"/"
64 << builderConfigNode.getValueAsString() << __E__;
69 contextConfig->getARTDAQAppRank(builderContext->contextUID_),
70 contextConfig->getContextAddress(builderContext->contextUID_),
71 contextConfig->getARTDAQDataPort(configManager, builderContext->contextUID_),
77 std::string ARTDAQBuilderTable::getFHICLFilename(
const ConfigurationTree& builderNode)
79 __COUT__ <<
"ARTDAQ Builder UID: " << builderNode.getValue() << __E__;
80 std::string filename = ARTDAQ_FCL_PATH + ARTDAQ_FILE_PREAMBLE +
"-";
81 std::string uid = builderNode.getValue();
82 for(
unsigned int i = 0; i < uid.size(); ++i)
83 if((uid[i] >=
'a' && uid[i] <=
'z') || (uid[i] >=
'A' && uid[i] <=
'Z') ||
84 (uid[i] >=
'0' && uid[i] <=
'9'))
89 __COUT__ <<
"fcl: " << filename << __E__;
97 unsigned int selfRank,
99 unsigned int selfPort,
222 std::string filename = getFHICLFilename(builderNode);
228 std::string tabStr =
"";
229 std::string commentStr =
"";
231 out.open(filename, std::fstream::out | std::fstream::trunc);
234 __SS__ <<
"Failed to open ARTDAQ Builder fcl file: " << filename << __E__;
240 OUT <<
"###########################################################" << __E__;
242 OUT <<
"# artdaq builder fcl configuration file produced by otsdaq." << __E__;
243 OUT <<
"# Creation timestamp: " << StringMacros::getTimestampString() << __E__;
244 OUT <<
"# Original filename: " << filename << __E__;
245 OUT <<
"# otsdaq-ARTDAQ Builder UID: " << builderNode.getValue() << __E__;
247 OUT <<
"###########################################################" << __E__;
251 if(builderNode.isDisconnected())
261 auto services = builderNode.getNode(
"servicesLink");
262 if(!services.isDisconnected())
264 OUT <<
"services: {\n";
268 OUT <<
"scheduler: {\n";
271 OUT <<
"fileMode: " << services.getNode(
"schedulerFileMode").getValue() <<
"\n";
272 OUT <<
"errorOnFailureToPut: "
273 << (services.getNode(
"schedulerErrorOnFailtureToPut").getValue<
bool>()
282 OUT <<
"NetMonTransportServiceInterface: {\n";
285 OUT <<
"service_provider: " <<
287 services.getNode(
"NetMonTrasportServiceInterfaceServiceProvider").getValue()
289 OUT <<
"destinations: {\n";
292 auto destinationsGroup =
293 services.getNode(
"NetMonTrasportServiceInterfaceDestinationsLink");
294 if(!destinationsGroup.isDisconnected())
298 auto destinations = destinationsGroup.getChildren();
299 for(
auto& destination : destinations)
301 auto destinationContextUID =
302 destination.second.getNode(
"destinationARTDAQContextLink")
305 unsigned int destinationRank =
306 contextConfig->getARTDAQAppRank(destinationContextUID);
308 contextConfig->getContextAddress(destinationContextUID);
309 unsigned int port = contextConfig->getARTDAQDataPort(
310 configManager, destinationContextUID);
313 OUT << destination.second.getNode(
"destinationKey").getValue()
317 OUT <<
"transferPluginType: "
318 << destination.second.getNode(
"transferPluginType").getValue()
321 OUT <<
"destination_rank: " << destinationRank << __E__;
325 OUT <<
"max_fragment_size_bytes: "
326 << destination.second
327 .getNode(
"ARTDAQGlobalTableLink/maxFragmentSizeBytes")
328 .getValue<
unsigned long long>()
333 __SS__ <<
"The field ARTDAQGlobalTableLink/maxFragmentSizeBytes "
334 "could not be accessed. Make sure the link is valid."
339 OUT <<
"host_map: [\n";
343 OUT <<
"rank: " << destinationRank << __E__;
344 OUT <<
"host: \"" << host <<
"\"" << __E__;
345 OUT <<
"portOffset: " << std::to_string(port) << __E__;
350 OUT <<
"rank: " << selfRank << __E__;
351 OUT <<
"host: \"" << selfHost <<
"\"" << __E__;
352 OUT <<
"portOffset: " << std::to_string(selfPort) << __E__;
362 catch(
const std::runtime_error& e)
364 __SS__ <<
"Are the Net Monitor Transport Service destinations valid? "
365 "Error occurred looking for Event Builder transport service "
366 "destinations for UID '"
367 << builderNode.getValue() <<
"': " << e.what() << __E__;
383 auto daq = builderNode.getNode(
"daqLink");
384 if(!daq.isDisconnected())
391 OUT <<
"event_builder: {\n";
395 OUT <<
"max_fragment_size_bytes: "
396 << daq.getNode(
"daqEventBuilderMaxFragmentSizeBytes")
397 .getValue<
unsigned long long>()
399 OUT <<
"buffer_count: "
400 << daq.getNode(
"daqEventBuilderBufferCount").getValue<
unsigned long long>()
403 auto parametersLink = daq.getNode(
"daqEventBuilderParametersLink");
404 if(!parametersLink.isDisconnected())
406 auto parameters = parametersLink.getChildren();
407 for(
auto& parameter : parameters)
409 if(!parameter.second.getNode(TableViewColumnInfo::COL_NAME_STATUS)
413 OUT << parameter.second.getNode(
"daqParameterKey").getValue() <<
": "
414 << parameter.second.getNode(
"daqParameterValue").getValue() <<
"\n";
416 if(!parameter.second.getNode(TableViewColumnInfo::COL_NAME_STATUS)
423 OUT <<
"sources: {\n";
426 auto sourcesGroup = daq.getNode(
"daqEventBuilderSourcesLink");
427 if(!sourcesGroup.isDisconnected())
431 auto sources = sourcesGroup.getChildren();
432 for(
auto& source : sources)
434 auto sourceContextUID =
435 source.second.getNode(
"sourceARTDAQContextLink")
438 unsigned int sourceRank =
439 contextConfig->getARTDAQAppRank(sourceContextUID);
440 std::string host = contextConfig->getContextAddress(sourceContextUID);
442 contextConfig->getARTDAQDataPort(configManager, sourceContextUID);
445 OUT << source.second.getNode(
"sourceKey").getValue() <<
": {\n";
448 OUT <<
"transferPluginType: "
449 << source.second.getNode(
"transferPluginType").getValue()
452 OUT <<
"source_rank: " << sourceRank << __E__;
456 OUT <<
"max_fragment_size_bytes: "
458 .getNode(
"ARTDAQGlobalTableLink/maxFragmentSizeBytes")
459 .getValue<
unsigned long long>()
464 __SS__ <<
"The field ARTDAQGlobalTableLink/maxFragmentSizeBytes "
465 "could not be accessed. Make sure the link is valid."
470 OUT <<
"host_map: [\n";
474 OUT <<
"rank: " << sourceRank << __E__;
475 OUT <<
"host: \"" << host <<
"\"" << __E__;
476 OUT <<
"portOffset: " << std::to_string(port) << __E__;
481 OUT <<
"rank: " << selfRank << __E__;
482 OUT <<
"host: \"" << selfHost <<
"\"" << __E__;
483 OUT <<
"portOffset: " << std::to_string(selfPort) << __E__;
493 catch(
const std::runtime_error& e)
495 __SS__ <<
"Are the DAQ sources valid? Error occurred looking for Event "
496 "Builder DAQ sources for UID '"
497 << builderNode.getValue() <<
"': " << e.what() << __E__;
507 OUT <<
"metrics: {\n";
510 auto metricsGroup = daq.getNode(
"daqMetricsLink");
511 if(!metricsGroup.isDisconnected())
513 auto metrics = metricsGroup.getChildren();
515 for(
auto& metric : metrics)
517 if(!metric.second.getNode(TableViewColumnInfo::COL_NAME_STATUS)
521 OUT << metric.second.getNode(
"metricKey").getValue() <<
": {\n";
524 OUT <<
"metricPluginType: "
525 << metric.second.getNode(
"metricPluginType").getValue() <<
"\n";
526 OUT <<
"level: " << metric.second.getNode(
"metricLevel").getValue()
529 auto metricParametersGroup =
530 metric.second.getNode(
"metricParametersLink");
531 if(!metricParametersGroup.isDisconnected())
533 auto metricParameters = metricParametersGroup.getChildren();
534 for(
auto& metricParameter : metricParameters)
536 if(!metricParameter.second
537 .getNode(TableViewColumnInfo::COL_NAME_STATUS)
541 OUT << metricParameter.second.getNode(
"metricParameterKey")
544 << metricParameter.second.getNode(
"metricParameterValue")
548 if(!metricParameter.second
549 .getNode(TableViewColumnInfo::COL_NAME_STATUS)
557 if(!metric.second.getNode(TableViewColumnInfo::COL_NAME_STATUS)
571 auto outputs = builderNode.getNode(
"outputsLink");
572 if(!outputs.isDisconnected())
574 OUT <<
"outputs: {\n";
578 auto outputPlugins = outputs.getChildren();
579 for(
auto& outputPlugin : outputPlugins)
581 if(!outputPlugin.second.getNode(TableViewColumnInfo::COL_NAME_STATUS)
585 std::string moduleType =
586 outputPlugin.second.getNode(
"outputModuleType").getValue();
588 OUT << outputPlugin.second.getNode(
"outputKey").getValue() <<
": {\n";
591 OUT <<
"module_type: " << moduleType <<
"\n";
593 auto pluginParameterLink =
594 outputPlugin.second.getNode(
"outputModuleParameterLink");
595 if(!pluginParameterLink.isDisconnected())
597 auto pluginParameters = pluginParameterLink.getChildren();
598 for(
auto& pluginParameter : pluginParameters)
600 if(!pluginParameter.second
601 .getNode(TableViewColumnInfo::COL_NAME_STATUS)
605 OUT << pluginParameter.second.getNode(
"outputParameterKey").getValue()
607 << pluginParameter.second.getNode(
"outputParameterValue")
611 if(!pluginParameter.second
612 .getNode(TableViewColumnInfo::COL_NAME_STATUS)
619 auto destinationsGroup =
620 outputPlugin.second.getNode(
"outputModuleDestinationLink");
621 if(!destinationsGroup.isDisconnected())
625 if(moduleType.find(
"BinaryNetOuput") == std::string::npos)
627 __SS__ <<
"Illegal output module type '" << moduleType
628 <<
"' to include destinations. Only modules of type "
630 <<
"are allowed to have destinations." << __E__;
634 OUT <<
"destinations: {\n";
637 auto destinations = destinationsGroup.getChildren();
638 for(
auto& destination : destinations)
641 auto destinationContextUID =
642 destination.second.getNode(
"destinationARTDAQContextLink")
645 unsigned int destinationRank =
646 contextConfig->getARTDAQAppRank(destinationContextUID);
648 contextConfig->getContextAddress(destinationContextUID);
649 unsigned int port = contextConfig->getARTDAQDataPort(
650 configManager, destinationContextUID);
653 OUT << destination.second.getNode(
"destinationKey").getValue()
657 OUT <<
"transferPluginType: "
658 << destination.second.getNode(
"transferPluginType")
662 OUT <<
"destination_rank: " << destinationRank << __E__;
666 OUT <<
"max_fragment_size_bytes: "
667 << destination.second
669 "ARTDAQGlobalTableLink/"
670 "maxFragmentSizeBytes")
671 .getValue<
unsigned long long>()
678 "ARTDAQGlobalTableLink/maxFragmentSizeBytes could "
679 "not be accessed. Make sure the link is valid."
684 OUT <<
"host_map: [\n";
688 OUT <<
"rank: " << destinationRank << __E__;
689 OUT <<
"host: \"" << host <<
"\"" << __E__;
690 OUT <<
"portOffset: " << std::to_string(port) << __E__;
695 OUT <<
"rank: " << selfRank << __E__;
696 OUT <<
"host: \"" << selfHost <<
"\"" << __E__;
697 OUT <<
"portOffset: " << std::to_string(selfPort) << __E__;
706 catch(
const std::runtime_error& e)
708 __SS__ <<
"Error encountered populating parameters for "
709 "output module destination '"
711 <<
"'... Please verify fields. Here was the error: "
712 << e.what() << __E__;
719 catch(
const std::runtime_error& e)
721 __SS__ <<
"Are the Output module destinations valid? "
722 "Error occurred looking for Event Builder output module "
723 "destinations for UID '"
724 << outputPlugin.second.getValue() <<
"': " << e.what()
733 if(!outputPlugin.second.getNode(TableViewColumnInfo::COL_NAME_STATUS)
744 auto physics = builderNode.getNode(
"physicsLink");
745 if(!physics.isDisconnected())
748 OUT <<
"physics: {\n";
752 auto analyzers = physics.getNode(
"analyzersLink");
753 if(!analyzers.isDisconnected())
756 OUT <<
"analyzers: {\n";
759 auto modules = analyzers.getChildren();
760 for(
auto& module : modules)
762 if(!module.second.getNode(TableViewColumnInfo::COL_NAME_STATUS)
766 OUT << module.second.getNode(
"analyzerKey").getValue() <<
": {\n";
768 OUT <<
"module_type: "
769 << module.second.getNode(
"analyzerModuleType").getValue() <<
"\n";
770 auto moduleParameterLink =
771 module.second.getNode(
"analyzerModuleParameterLink");
772 if(!moduleParameterLink.isDisconnected())
774 auto moduleParameters = moduleParameterLink.getChildren();
775 for(
auto& moduleParameter : moduleParameters)
777 if(!moduleParameter.second
778 .getNode(TableViewColumnInfo::COL_NAME_STATUS)
782 OUT << moduleParameter.second.getNode(
"analyzerParameterKey")
785 << moduleParameter.second.getNode(
"analyzerParameterValue")
789 if(!moduleParameter.second
790 .getNode(TableViewColumnInfo::COL_NAME_STATUS)
798 if(!module.second.getNode(TableViewColumnInfo::COL_NAME_STATUS)
806 auto producers = physics.getNode(
"producersLink");
807 if(!producers.isDisconnected())
810 OUT <<
"producers: {\n";
813 auto modules = producers.getChildren();
814 for(
auto& module : modules)
816 if(!module.second.getNode(TableViewColumnInfo::COL_NAME_STATUS)
820 OUT << module.second.getNode(
"producerKey").getValue() <<
": {\n";
822 OUT <<
"module_type: "
823 << module.second.getNode(
"producerModuleType").getValue() <<
"\n";
824 auto moduleParameterLink =
825 module.second.getNode(
"producerModuleParameterLink");
826 if(!moduleParameterLink.isDisconnected())
828 auto moduleParameters = moduleParameterLink.getChildren();
829 for(
auto& moduleParameter : moduleParameters)
831 if(!moduleParameter.second
832 .getNode(TableViewColumnInfo::COL_NAME_STATUS)
836 OUT << moduleParameter.second.getNode(
"producerParameterKey")
839 << moduleParameter.second.getNode(
"producerParameterValue")
843 if(!moduleParameter.second
844 .getNode(TableViewColumnInfo::COL_NAME_STATUS)
852 if(!module.second.getNode(TableViewColumnInfo::COL_NAME_STATUS)
860 auto filters = physics.getNode(
"filtersLink");
861 if(!filters.isDisconnected())
864 OUT <<
"filters: {\n";
867 auto modules = filters.getChildren();
868 for(
auto& module : modules)
870 if(!module.second.getNode(TableViewColumnInfo::COL_NAME_STATUS)
874 OUT << module.second.getNode(
"filterKey").getValue() <<
": {\n";
876 OUT <<
"module_type: "
877 << module.second.getNode(
"filterModuleType").getValue() <<
"\n";
878 auto moduleParameterLink =
879 module.second.getNode(
"filterModuleParameterLink");
880 if(!moduleParameterLink.isDisconnected())
882 auto moduleParameters = moduleParameterLink.getChildren();
883 for(
auto& moduleParameter : moduleParameters)
885 if(!moduleParameter.second
886 .getNode(TableViewColumnInfo::COL_NAME_STATUS)
890 OUT << moduleParameter.second.getNode(
"filterParameterKey")
893 << moduleParameter.second.getNode(
"filterParameterValue")
897 if(!moduleParameter.second
898 .getNode(TableViewColumnInfo::COL_NAME_STATUS)
906 if(!module.second.getNode(TableViewColumnInfo::COL_NAME_STATUS)
914 auto otherParameterLink = physics.getNode(
"physicsOtherParametersLink");
915 if(!otherParameterLink.isDisconnected())
918 auto physicsParameters = otherParameterLink.getChildren();
919 for(
auto& parameter : physicsParameters)
921 if(!parameter.second.getNode(TableViewColumnInfo::COL_NAME_STATUS)
925 OUT << parameter.second.getNode(
"physicsParameterKey").getValue() <<
": "
926 << parameter.second.getNode(
"physicsParameterValue").getValue()
929 if(!parameter.second.getNode(TableViewColumnInfo::COL_NAME_STATUS)
940 auto source = builderNode.getNode(
"sourceLink");
941 if(!source.isDisconnected())
943 OUT <<
"source: {\n";
946 OUT <<
"module_type: " << source.getNode(
"sourceModuleType").getValue() <<
"\n";
947 OUT <<
"waiting_time: " << source.getNode(
"sourceWaitingTime").getValue() <<
"\n";
948 OUT <<
"resume_after_timeout: "
949 << (source.getNode(
"sourceResumeAfterTimeout").getValue<
bool>() ?
"true"
958 OUT <<
"process_name: "
959 << builderNode.getNode(
960 "ARTDAQGlobalTableForProcessNameLink/processNameForBuilders")