DUNE-DAQ
DUNE Trigger and Data Acquisition software
Loading...
Searching...
No Matches
DFApplication.cpp
Go to the documentation of this file.
1
28#include "appmodel/TRBConf.hpp"
33
35
40#include "confmodel/Service.hpp"
41
42#include "logging/Logging.hpp"
43#include "oks/kernel.hpp"
44
45#include <fmt/core.h>
46#include <string>
47#include <vector>
48
49namespace dunedaq {
50namespace appmodel {
51
52
53inline void
55 const conffwk::ConfigObject* netConn,
56 conffwk::ConfigObject& sidNetObj)
57{
58 sidNetObj.set_obj("netconn", netConn);
59 sidNetObj.set_objs("source_ids", { &smartapp->get_source_id()->config_object() });
60}
61
62
63inline void
65 const TPReplayApplication* rapp,
66 std::vector<conffwk::ConfigObject>* netConn,
67 std::vector<conffwk::ConfigObject>* sidNetObj,
68 std::vector<std::shared_ptr<conffwk::ConfigObject>> sidObjs,
69 const NetworkConnectionDescriptor* descriptor,
70 std::string smartapp_uid)
71{
72 std::vector<const conffwk::ConfigObject*> source_id_objs;
73
74 for (auto tp_sid : rapp->get_tp_source_ids()) {
75 // get name extension
76 std::string name = tp_sid->UID();
77 size_t pos = name.find_last_of('-');
78 std::string ext;
79 if (pos != std::string::npos) {
80 ext = name.substr(pos);
81 }
82
83 // set Network connections
84 std::string dreqNetUid(smartapp_uid + ext);
85 netConn->emplace_back(
86 obj_fac.create_net_obj(descriptor, dreqNetUid));
87 netConn->back().set_by_val<std::string>("data_type", descriptor->get_data_type());
88 netConn->back().set_by_val<std::string>("connection_type", descriptor->get_connection_type());
89 auto serviceObj = descriptor->get_associated_service()->config_object();
90 netConn->back().set_obj("associated_service", &serviceObj);
91
92 // set SourceID to Network connections
93 std::string sidToNetUid(smartapp_uid + ext + "-sids");
94 sidNetObj->emplace_back(
95 obj_fac.create("SourceIDToNetworkConnection", sidToNetUid));
96 sidNetObj->back().set_obj("netconn", &netConn->back());
97
98 // set SourceID objs
99 sidObjs.push_back(std::make_shared<conffwk::ConfigObject>(tp_sid->config_object()));
100 sidNetObj->back().set_objs("source_ids", { sidObjs.back().get() });
101 }
102}
103
104inline void
106 const ReadoutApplication* roapp,
107 const conffwk::ConfigObject* netConn,
108 conffwk::ConfigObject& sidNetObj,
109 std::vector<std::shared_ptr<conffwk::ConfigObject>> sidObjs)
110{
111 sidNetObj.set_obj("netconn", netConn);
112
113 std::vector<const conffwk::ConfigObject*> source_id_objs;
114 std::vector<uint32_t> app_source_ids;
115
116 for (auto d2d_conn_res : roapp->get_contains()) {
117
118 // get the readout groups and the interfaces and streams therein; 1 reaout group corresponds to 1 data reader
119 // module
120 auto d2d_conn = d2d_conn_res->cast<confmodel::DetectorToDaqConnection>();
121
122 if (!d2d_conn) {
123 continue;
124 }
125
126 // Loop over senders
127 for (auto dros : d2d_conn->get_streams()) {
128
129 auto stream = dros->cast<confmodel::DetectorStream>();
130 if (!stream)
131 continue;
132 app_source_ids.push_back(stream->get_source_id());
133 }
134 }
135
136 for (auto& source_id : app_source_ids) {
137 std::string streamSidUid(roapp->UID() + "SourceIDConf" + std::to_string(source_id));
138 auto stream_sid_obj = std::make_shared<conffwk::ConfigObject>(obj_fac.create("SourceIDConf", streamSidUid));
139 stream_sid_obj->set_by_val<uint32_t>("sid", source_id);
140 stream_sid_obj->set_by_val<std::string>("subsystem", "Detector_Readout");
141 sidObjs.push_back(stream_sid_obj);
142 source_id_objs.push_back(sidObjs.back().get());
143 }
144
145 for (auto tp_sid : roapp->get_tp_source_ids()) {
146 sidObjs.push_back(std::make_shared<conffwk::ConfigObject>(tp_sid->config_object()));
147 source_id_objs.push_back(sidObjs.back().get());
148 }
149 /*
150 std::string trgSidUid(roapp->UID() + "TRGSourceIDConf" + std::to_string(roapp->get_tp_source_id()));
151 auto trig_sid_obj = std::make_shared<conffwk::ConfigObject>(obj_fac.create("SourceIDConf", trgSidUid));
152 trig_sid_obj->set_by_val<uint32_t>("sid", roapp->get_tp_source_id());
153 trig_sid_obj->set_by_val<std::string>("subsystem", "Trigger");
154 source_id_objs.push_back(sidObjs.back().get());
155 */
156
157 sidNetObj.set_objs("source_ids", source_id_objs);
158}
159
160inline void
162 const FakeDataApplication* fdapp,
163 const conffwk::ConfigObject* netConn,
164 conffwk::ConfigObject& sidNetObj,
165 std::vector<std::shared_ptr<conffwk::ConfigObject>> sidObjs)
166{
167 sidNetObj.set_obj("netconn", netConn);
168
169 std::vector<const conffwk::ConfigObject*> source_id_objs;
170 std::vector<uint32_t> app_source_ids;
171
172 for (auto fdp_res : fdapp->get_contains()) {
173
174 // get the readout groups and the interfaces and streams therein; 1 reaout group corresponds to 1 data reader
175 // module
176 auto fdpc = fdp_res->cast<appmodel::FakeDataProdConf>();
177
178 if (!fdpc) {
179 continue;
180 }
181
182 app_source_ids.push_back(fdpc->get_source_id());
183 }
184
185 for (auto& source_id : app_source_ids) {
186 std::string streamSidUid(fdapp->UID() + "SourceIDConf" + std::to_string(source_id));
187 auto stream_sid_obj = std::make_shared<conffwk::ConfigObject>(obj_fac.create("SourceIDConf", streamSidUid));
188 stream_sid_obj->set_by_val<uint32_t>("sid", source_id);
189 stream_sid_obj->set_by_val<std::string>("subsystem", "Detector_Readout");
190 sidObjs.push_back(stream_sid_obj);
191 source_id_objs.push_back(sidObjs.back().get());
192 }
193
194 sidNetObj.set_objs("source_ids", source_id_objs);
195}
196
197std::vector<const confmodel::DaqModule*>
199{
200
201 ConfigObjectFactory obj_fac(this);
202
203 std::vector<const confmodel::DaqModule*> modules;
204
205 // Containers for module specific config objects for output/input
206 // Prepare TRB output objects
207 std::vector<const conffwk::ConfigObject*> trbOutputObjs;
208 std::vector<const conffwk::ConfigObject*> trbSidNetObjs;
209
210 // -- First, we process expected Queue and Network connections and create their objects.
211
212 // Process the queue rules looking for the TriggerRecord queue between TRB and DataWriterModule
213 const QueueDescriptor* trQDesc = nullptr;
214 for (auto rule : get_queue_rules()) {
215 auto destination_class = rule->get_destination_class();
216 if (destination_class == "DataWriterModule") {
217 trQDesc = rule->get_descriptor();
218 }
219 }
220 if (trQDesc == nullptr) { // BadConf if no descriptor between TRB and DataWriterModule
221 throw(BadConf(ERS_HERE, "Could not find queue descriptor rule for TriggerRecords!"));
222 }
223 // Create queue connection config object
224 auto trQueueObj = obj_fac.create_queue_obj(trQDesc, UID());
225
226 // Place trigger record queue object into vector of output objs of TRB module
227 trbOutputObjs.push_back(&trQueueObj);
228
229 // Process the network rules looking for the Fragments and TriggerDecision inputs for TRB
230 const NetworkConnectionDescriptor* fragNetDesc = nullptr;
231 const NetworkConnectionDescriptor* trigdecNetDesc = nullptr;
232 const NetworkConnectionDescriptor* tokenNetDesc = nullptr;
233 for (auto rule : get_network_rules()) {
234 auto descriptor = rule->get_descriptor();
235 auto data_type = descriptor->get_data_type();
236 if (data_type == "Fragment") {
237 fragNetDesc = rule->get_descriptor();
238 } else if (data_type == "TriggerDecision") {
239 trigdecNetDesc = rule->get_descriptor();
240 } else if (data_type == "TriggerDecisionToken") {
241 tokenNetDesc = rule->get_descriptor();
242 }
243 }
244 if (fragNetDesc == nullptr) { // BadConf if no descriptor for Fragments into TRB
245 throw(BadConf(ERS_HERE, "Could not find network descriptor rule for input Fragments!"));
246 }
247 if (trigdecNetDesc == nullptr) { // BadCond if no descriptor for TriggerDecisions into TRB
248 throw(BadConf(ERS_HERE, "Could not find network descriptor rule for input TriggerDecisions!"));
249 }
250 if (tokenNetDesc == nullptr) { // BadCond if no descriptor for Tokens out of DataWriterModule
251 throw(BadConf(ERS_HERE, "Could not find network descriptor rule for output TriggerDecisionTokens!"));
252 }
253 if (get_source_id() == nullptr) {
254 throw(BadConf(ERS_HERE, "Could not retrieve SourceIDConf"));
255 }
256 // Create network connection config object
257 auto fragNetObj = obj_fac.create_net_obj(fragNetDesc, UID());
258 auto trigdecNetObj = obj_fac.create_net_obj(trigdecNetDesc, UID());
259 auto tokenNetObj = obj_fac.create_net_obj(tokenNetDesc, "");
260
261 // Process special Network rules!
262 // Looking for DataRequest rules from ReadoutAppplications in current Session
263 auto sessionApps = session->get_enabled_applications();
264 std::vector<conffwk::ConfigObject> dreqNetObjs;
265 std::vector<conffwk::ConfigObject> sidNetObjs;
266 std::vector<std::shared_ptr<conffwk::ConfigObject>> sidObjs;
267 for (auto app : sessionApps) {
268 auto smartapp = app->cast<appmodel::SmartDaqApplication>();
269 auto roapp = app->cast<appmodel::ReadoutApplication>();
270 auto fdapp = app->cast<appmodel::FakeDataApplication>();
271 auto ctbapp = app->cast<appmodel::CTBApplication>();
272 auto dfapp = app->cast<appmodel::DFApplication>();
273 auto rapp = app->cast<appmodel::TPReplayApplication>();
274 if (smartapp == nullptr || dfapp != nullptr) {
275 continue;
276 }
277 auto src_id_check = smartapp->get_source_id();
278 if (roapp == nullptr
279 && fdapp == nullptr
280 && src_id_check == nullptr
281 && rapp == nullptr
282 && ctbapp == nullptr) {
283 continue;
284 }
285
286 auto roQRules = smartapp->get_network_rules();
287 for (auto rule : roQRules) {
288 auto descriptor = rule->get_descriptor();
289 auto data_type = descriptor->get_data_type();
290 if (data_type == "DataRequest") {
291 if (rapp != nullptr) {
292 fill_sourceid_object_from_app(obj_fac, rapp, &dreqNetObjs, &sidNetObjs, sidObjs, descriptor, smartapp->UID());
293 }
294 // contrary to all the other applications
295 // the CTB has 2 network connections, so this logic has to be splitted
296 else if (ctbapp) {
297 auto sources = ctbapp->get_sources();
298 for ( const auto & s : sources ) {
299 std::string dreqNetUid(descriptor->get_uid_base() + smartapp->UID()+ '_' + s.first);
300 dreqNetObjs.emplace_back( obj_fac.create_net_obj(descriptor, dreqNetUid) );
301
302 std::string sidToNetUid(descriptor->get_uid_base() + smartapp->UID() + "_" + s.first);
303 sidNetObjs.emplace_back( obj_fac.create("SourceIDToNetworkConnection", sidToNetUid ) );
304 sidNetObjs.back().set_obj("netconn", & dreqNetObjs.back());
305 sidNetObjs.back().set_objs("source_ids", { & s.second->config_object() });
306 } // loop over CTB sources
307 } else {
308
309 dreqNetObjs.emplace_back(obj_fac.create_net_obj(descriptor, smartapp->UID()));
310
311 std::string sidToNetUid(descriptor->get_uid_base() + smartapp->UID() + "-sids");
312 sidNetObjs.emplace_back(
313 obj_fac.create("SourceIDToNetworkConnection", sidToNetUid));
314 if (roapp != nullptr) {
315 fill_sourceid_object_from_app(obj_fac, roapp, &dreqNetObjs.back(), sidNetObjs.back(), sidObjs);
316 } else if (fdapp != nullptr) {
317 fill_sourceid_object_from_app(obj_fac, fdapp, &dreqNetObjs.back(), sidNetObjs.back(), sidObjs);
318 } else {
319 fill_sourceid_object_from_app(smartapp, &dreqNetObjs.back(), sidNetObjs.back());
320 }
321 } // else from if (ctbapp)
322 } // If network rule has DataRequest type of data
323 } // Loop over Apps network rules
324 } // loop over Session specific Apps
325
326 // Get pointers to objects here, after vector has been filled so they don't move on us
327 for (auto& obj : dreqNetObjs) {
328 trbOutputObjs.push_back(&obj);
329 }
330 for (auto& obj : sidNetObjs) {
331 trbSidNetObjs.push_back(&obj);
332 }
333
334 // -- Second, we create the Module objects and assign their configs, with the precreated
335 // -- connection config objects above.
336
337 // Get TRB Config Object
338 auto trbConf = get_trb();
339 if (trbConf == nullptr) {
340 throw(BadConf(ERS_HERE, "No DataWriterModule or TRB configuration given"));
341 }
342 auto trbConfObj = trbConf->config_object();
343 trbConfObj.set_by_val<uint32_t>("source_id", get_source_id()->get_sid());
344 // Prepare TRB Module Object and assign its Config Object.
345 std::string trbUid(UID() + "-trb");
346 conffwk::ConfigObject trbObj = obj_fac.create("TRBModule", trbUid);
347 trbObj.set_obj("configuration", &trbConfObj);
348 trbObj.set_objs("inputs", { &trigdecNetObj, &fragNetObj });
349 trbObj.set_objs("outputs", trbOutputObjs);
350 trbObj.set_objs("request_connections", trbSidNetObjs);
351 // Push TRB Module Object from confdb
352 modules.push_back(obj_fac.get_dal<TRBModule>(trbUid));
353
354 // Get DataWriterModule Config Object (only one for now, maybe more later?)
355 auto dwrConfs = get_data_writers();
356 if (dwrConfs.size() == 0) {
357 throw(BadConf(ERS_HERE, "No DataWriterModule or TRB configuration given"));
358 }
359 uint dw_idx = 0;
360 for (auto dwrConf : dwrConfs) {
361 // auto fnParamsObj = dwrConf->get_data_store_params()->get_filename_params()->config_object();
362 // fnParamsObj.set_by_val<std::string>("writer_identifier", fmt::format("{}_datawriter-{}", UID(), dw_idx));
363 auto dwrConfObj = dwrConf->config_object();
364
365 // Prepare DataWriterModule Module Object and assign its Config Object.
366 std::string dwrUid(fmt::format("{}-dw-{}", UID(), dw_idx));
367 conffwk::ConfigObject dwrObj = obj_fac.create("DataWriterModule", dwrUid);
368 dwrObj.set_by_val("writer_identifier", fmt::format("{}_dw_{}", UID(), dw_idx));
369 dwrObj.set_obj("configuration", &dwrConfObj);
370 dwrObj.set_objs("inputs", { &trQueueObj });
371 dwrObj.set_objs("outputs", { &tokenNetObj });
372 // Push DataWriterModule Module Object from confdb
373 modules.push_back(obj_fac.get_dal<DataWriterModule>(dwrUid));
374 ++dw_idx;
375 }
376
377 return modules;
378}
379
380} // namespace appmodel
381} // namespace dunedaq
#define ERS_HERE
conffwk::ConfigObject create_net_obj(const NetworkConnectionDescriptor *ndesc, std::string uid) const
Helper function that gets a network connection config.
const T * get_dal(std::string uid) const
conffwk::ConfigObject create_queue_obj(const QueueDescriptor *qdesc, std::string uid="") const
conffwk::ConfigObject create(const std::string &class_name, const std::string &id) const
const std::vector< const dunedaq::appmodel::DataWriterConf * > & get_data_writers() const
Get "data_writers" relationship value.
const dunedaq::appmodel::TRBConf * get_trb() const
Get "trb" relationship value. Configuration of the TRB to be generated my get_modules()
std::vector< const dunedaq::confmodel::DaqModule * > generate_modules(const confmodel::Session *) const override
const std::vector< const dunedaq::appmodel::SourceIDConf * > & get_tp_source_ids() const
Get "tp_source_ids" relationship value.
const std::vector< const dunedaq::appmodel::NetworkConnectionRule * > & get_network_rules() const
Get "network_rules" relationship value.
const std::vector< const dunedaq::appmodel::QueueConnectionRule * > & get_queue_rules() const
Get "queue_rules" relationship value.
const dunedaq::appmodel::SourceIDConf * get_source_id() const
Get "source_id" relationship value.
uint32_t get_sid() const
Get "sid" attribute value.
const std::vector< const dunedaq::appmodel::SourceIDConf * > & get_tp_source_ids() const
Get "tp_source_ids" relationship value.
void set_by_val(const std::string &name, T value)
Set attribute value.
void set_objs(const std::string &name, const std::vector< const ConfigObject * > &o, bool skip_non_null_check=false)
Set relationship multi-value.
void set_obj(const std::string &name, const ConfigObject *o, bool skip_non_null_check=false)
Set relationship single-value.
const TARGET * cast() const noexcept
Casts object to different class.
const ConfigObject & config_object() const
const std::string & UID() const noexcept
const std::vector< const dunedaq::confmodel::ResourceBase * > & get_contains() const
Get "contains" relationship value. A resource set is a container of resources to easily implement gro...
conffwk entry point
void fill_sourceid_object_from_app(const SmartDaqApplication *smartapp, const conffwk::ConfigObject *netConn, conffwk::ConfigObject &sidNetObj)
Including Qt Headers.